先上图

下拉刷新
跟原生开发一样,下拉刷新在flutter
里提供的有组件实现 RefreshIndicator
一直不明白为啥组件中都提供下拉刷新,但就是没有上拉加载!!
我这请求接口数据用的是 http 库,是个第三方的是需要安装的 https://pub.dev/packages/http
用法如下
- class MyHomePage extends StatefulWidget {
- MyHomePage({Key key}) : super(key: key);
- @override
- MyHomeWidget2 createState() => MyHomeWidget2();
- }
- class MyHomeWidget2 extends State<MyHomePage> {
- int page = 1;
- List data = new List();
- var baseUrl = "https://cnodejs.org/api/v1";
- @override
- void initState() {
- super.initState();
- this._onRefresh();
- }
- _fetchData() async {
- var response = await http.get(
- '${this.baseUrl}/topics?mdrender=false&limit=10&page=${this.page}');
- var json = await convert.jsonDecode(response.body);
- return json['data'];
- }
- Future<dynamic> _onRefresh() {
- data.clear();
- this.page = 1;
- return _fetchData().then((data) {
- setState(() => this.data.addAll(data));
- });
- }
- @override
- Widget build(BuildContext context) {
- return Scaffold(
- body: RefreshIndicator( // 在ListView外包一层 RefreshIndicator 组件
- onRefresh: _onRefresh, // 添加onRefresh方法
- child: ListView.separated(
- itemCount: this.data.length,
- itemBuilder: (context, index) {
- var _data = this.data[index];
- return ListTile(
- leading: Image.network(_data["author"]["avatar_url"]),
- title: Text(_data["title"]),
- subtitle: Text(_data["author"]["loginname"] +
- " created at " +
- new DateTime.now().toString()), // 为了看每次数据变动,这里直接取当前时间
- trailing: Icon(Icons.chevron_right));
- },
- separatorBuilder: (context, index) {
- return Divider();
- },
- )
- ));
- }
- }
链接文原: https://tomoya92.github.io/2019/07/17/flutter-refresh-loadmore/
上拉加载
上拉加载原理还是一样的,给ListView加一个 ScrollController 组件,然后通过事件监听滚动条的高度来显示和隐藏加载更多的组件
先将加载更多的组件写好
- Widget _loadMoreWidget() {
- return new Padding(
- padding: const EdgeInsets.all(15.0), // 外边距
- child: new Center(
- child: new CircularProgressIndicator()
- ),
- );
- }
初始化一个 ScrollController
组件,将其设置给 ListView 组件的 controller 属性上
- ScrollController _scrollController = new ScrollController();
-
- child: ListView.separated(
- controller: _scrollController,
- //...
- )
然后通过重写 dispost() 方法来处理加载更多组件的释放
- @override
- void dispose() {
- _scrollController.dispose();
- super.dispose();
- }
最后通过数据源来控制界面渲染哪个组件,当数据源循环渲染的 index 跟数据源一样长时(其实少1,下标从0开始的)就渲染加载更多组件,让其显示出来,同时调用加载更多方法,获取数据,再通过state实现组件ui的更新
完整代码如下
- class MyHomePage extends StatefulWidget {
- MyHomePage({Key key}) : super(key: key);
- @override
- MyHomeWidget2 createState() => MyHomeWidget2();
- }
- class MyHomeWidget2 extends State<MyHomePage> {
- int page = 1;
- bool isLoadmore = false;
- List data = new List();
- var baseUrl = "https://cnodejs.org/api/v1";
- ScrollController _scrollController = new ScrollController();
- @override
- void initState() {
- super.initState();
- this._onRefresh();
- _scrollController.addListener(() {
- if (_scrollController.position.pixels == _scrollController.position.maxScrollExtent) {
- _onLoadmore();
- }
- });
- }
- _fetchData() async {
- var response = await http.get(
- '${this.baseUrl}/topics?mdrender=false&limit=10&page=${this.page}');
- var json = await convert.jsonDecode(response.body);
- return json['data'];
- }
- Future<dynamic> _onRefresh() {
- data.clear();
- this.page = 1;
- return _fetchData().then((data) {
- setState(() => this.data.addAll(data));
- });
- }
- Future<dynamic> _onLoadmore() {
- this.page++;
- return _fetchData().then((data) {
- setState((){
- this.data.addAll(data);
- isLoadmore = false;
- });
- });
- }
- @override
- void dispose() {
- _scrollController.dispose();
- super.dispose();
- }
- Widget _loadMoreWidget() {
- return new Padding(
- padding: const EdgeInsets.all(15.0),
- child: new Center(
- child: new CircularProgressIndicator()
- ),
- );
- }
- @override
- Widget build(BuildContext context) {
- return Scaffold(
- body: RefreshIndicator(
- onRefresh: _onRefresh,
- child: ListView.separated(
- controller: _scrollController,
- itemCount: this.data.length,
- itemBuilder: (context, index) {
- if (index == data.length - 1) {
- return _loadMoreWidget();
- } else {
- var _data = this.data[index];
- return ListTile(
- leading: Image.network(_data["author"]["avatar_url"]),
- title: Text(_data["title"]),
- subtitle: Text(_data["author"]["loginname"] +
- " created at " +
- new DateTime.now().toString()),
- trailing: Icon(Icons.chevron_right));
- }
- },
- separatorBuilder: (context, index) {
- return Divider();
- },
- )
- ));
- }
- }
总结
以上所述是小编给大家介绍的Flutter ListView 上拉加载更多下拉刷新功能实现方法,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对w3xue网站的支持!
如果你觉得本文对你有帮助,欢迎转载,烦请注明出处,谢谢!