Flutter_App开发

Flutter Dio请求列表+上拉刷新+下拉加载

2019-12-20  本文已影响0人  坤哥爱卿

1.数据请求

数据请求我这边用的是Dio库,支持Restful接口。
代码如下:
var dioUrl =
          'http://www.phonegap100.com/appapi.php?a=getPortalList&catid=20&page=${this._page}';
      Response response = await Dio().get(dioUrl);
      var arr = json.decode(response.data)['result'];
      print(arr);
列表展示用的是ListView.builder()
代码如下
ListView.builder(
              itemCount: this._list.length,
              itemBuilder: (context, index) {
                return ListTile(
                  title: Text('${this._list[index]['title']}'),
                );
              })

2.下拉刷新

下拉刷新就是在ListView外面套一层RefreshIndicator,然后在其中的onRefresh方法中实现下拉刷新的功能
代码如下
注意:onRefresh是Future类型
//下拉刷新
  Future<void> _onRefresh() async {
    await Future.delayed(Duration(milliseconds: 1000), () {
      print('请求数据完成');
      this._page = 1;
      _getListData();
    });
  }

3.加载更多

加载更多就是在ListView的controller属性中传入一个_scrollController类型为ScrollController,_scrollController可以获取滚动条下拉的距离和获取整个页面的高度,以此来判断是否滑动到最底部了(距离底部一定距离就开始刷新效果比较好,所以代码中减了40)
ScrollController _scrollController = new ScrollController();

//监听滑动
    _scrollController.addListener(() {
      //获取滚动条下拉的距离
      print(_scrollController.position.pixels);
      //获取整个页面的高度
      print(_scrollController.position.maxScrollExtent);
      if (_scrollController.position.pixels >
          _scrollController.position.maxScrollExtent - 40) {
        //开始加载更多
        this._getListData();
      }
    });
完整代码如下
import 'dart:convert';
import 'dart:math';

import 'package:flutter/material.dart';
import 'package:dio/dio.dart';

class DioRequestResultPage extends StatefulWidget {
  DioRequestResultPage({Key key}) : super(key: key);

  @override
  _DioRequestResultPageState createState() => _DioRequestResultPageState();
}

class _DioRequestResultPageState extends State<DioRequestResultPage> {
  List _list = [];
  int _page = 1;
  bool hasMore = true; //判断有没有数据
  ScrollController _scrollController = new ScrollController();

  @override
  void initState() {
    // TODO: implement initState
    super.initState();
    this._getListData();

    //监听滑动
    _scrollController.addListener(() {
      //获取滚动条下拉的距离
      print(_scrollController.position.pixels);
      //获取整个页面的高度
      print(_scrollController.position.maxScrollExtent);
      if (_scrollController.position.pixels >
          _scrollController.position.maxScrollExtent - 40) {
        //开始加载更多
        this._getListData();
      }
    });
  }

  void _getListData() async {
    if (this.hasMore) {
      var dioUrl =
          'http://www.phonegap100.com/appapi.php?a=getPortalList&catid=20&page=${this._page}';
      Response response = await Dio().get(dioUrl);
      var arr = json.decode(response.data)['result'];
      print(arr);
      setState(() {
        if (this._page == 1) {
          this._list = arr;
        } else {
          this._list.addAll(arr);
        }
        this._page++;
      });

      //判断是否为最后一页
      if (arr.length < 20) {
        setState(() {
          this.hasMore = false;
        });
      }
    }
  }

  //下拉刷新
  Future<void> _onRefresh() async {
    await Future.delayed(Duration(milliseconds: 1000), () {
      print('请求数据完成');
      this._page = 1;
      _getListData();
    });
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('Dio Get请求渲染数据demo'),
      ),
      body: this._list.length > 0
          ? RefreshIndicator(
              onRefresh: _onRefresh,
              child: ListView.builder(
                controller: _scrollController,
                itemCount: this._list.length,
                itemBuilder: (context, index) {
                  //列表渲染到最后一条的时候加一个圈圈
                  if (index == this._list.length - 1) {
                    //拉到底
                    return Column(
                      children: <Widget>[
                        ListTile(
                          title: Text('${this._list[index]['title']}', maxLines: 1),
                        ),
                        Divider(),
                        _getMoreWidget()
                      ],
                    );
                  } 
                  else {
                    return Column(
                      children: <Widget>[
                        ListTile(
                          title: Text('${this._list[index]['title']}', maxLines: 1),
                        ),
                        Divider()
                      ],
                    );
                  }
                },
              ),
            )
          : Text('加载中...'),
    );
  }

  //加载中的圈圈
  Widget _getMoreWidget() {
    if (hasMore) {
      return Center(
        child: Padding(
          padding: EdgeInsets.all(10.0),
          child: Row(
            mainAxisAlignment: MainAxisAlignment.center,
            crossAxisAlignment: CrossAxisAlignment.center,
            children: <Widget>[
              Text(
                '加载中...',
                style: TextStyle(fontSize: 16.0),
              ),
              CircularProgressIndicator(
                strokeWidth: 1.0,
              )
            ],
          ),
        ),
      );
    } else {
      return Center(
        child: Text("--我是有底线的--"),
      );
    }
  }
}

上一篇 下一篇

猜你喜欢

热点阅读