记录自学flutter点点滴滴

Flutter 学习之旅(二十) 可滚动控件 ListVi

2020-08-21  本文已影响0人  Tsm_2020

ListView 可以说是App中最常用的几个控件之一了,先来看一下他的构造参数

  ListView({

/// ScrollView 公共参数
    Key key,
    Axis scrollDirection = Axis.vertical,
    bool reverse = false,
    ScrollController controller,
    bool primary,
    ScrollPhysics physics,
    DragStartBehavior dragStartBehavior = DragStartBehavior.start,    ScrollViewKeyboardDismissBehavior keyboardDismissBehavior = ScrollViewKeyboardDismissBehavior.manual,
  

///ListView 参数
    bool shrinkWrap = false,
    EdgeInsetsGeometry padding,
    this.itemExtent,
    bool addAutomaticKeepAlives = true,
    bool addRepaintBoundaries = true,
    bool addSemanticIndexes = true,
    double cacheExtent,
    List<Widget> children = const <Widget>[],
    int semanticChildCount,

  }) 

这里ScrollView公用的参数在前面已经写了很多次了,这里就不再赘述了,
下面来说一下ListView 新建参数

itemExtent

子条目沿主轴方向的长度,如果主轴方向是垂直的,则itemExtent的长度为item的高度,如果指定itemExtent的高度的话会加快ListView 的构建速度,不用每次填充条目的时候还要计算它的高度

shrinkWrap

表示是否按照子条目的高度来确定ListView 的高度,默认为false,如果在无限高的布局中shrinkWrap必须为true,例如ScrollView 嵌套 ListView 中,shrinkWrap就必须为true

addAutomaticKeepAlives

是否将子条目包裹在AutomaticKeepAlive 中,如果为true,他在移出窗口后也不会被回收,而是被KeepAliveNotification保存,如果想要手动管理KeepAlive状态,必须给false,

addRepaintBoundaries

表示是否将列子条目包裹在RepaintBoundary组件中。当可滚动组件滚动时,将列表项包裹在RepaintBoundary中可以避免列表项重绘,但是当列表项重绘的开销非常小(如一个颜色块,或者一个较短的文本)时,不添加RepaintBoundary反而会更高效。和addAutomaticKeepAlive一样,如果列表项自己维护其KeepAlive状态,那么此参数必须置为false。

我学习flutter的整个过程都记录在里面了
https://www.jianshu.com/c/36554cb4c804

class _TsmListViewPage extends State<TsmListViewPage> {
  List<String> list_str;
  String endTag;

  List<String> page = [
    '条目1',
    '条目2',
    '条目3',
    '条目4',
    '条目5',
    '条目6',
    '条目7',
    '条目8',
    '条目9',
    '条目10'
  ];

  @override
  void initState() {
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: Text('ListView 学习'),
        centerTitle: true,
      ),
      body: getBody(),
    );
  }

  getBody() {
    if ((list_str ??= []).length == 0) {
      return getEmptyView();
    }
    return getListBody();
  }

  getListBody() {
    if (list_str.length < 100) {
      loadDate();
    }
    return ListView.separated(
        itemCount: list_str.length,
        separatorBuilder: (context, index) => Divider(),
        itemBuilder: (context, index) {
          if (list_str[index] == endTag) {
            return Container(
              padding: const EdgeInsets.all(16.0),
              alignment: Alignment.center,
              child: SizedBox(
                  width: 24.0,
                  height: 24.0,
                  child: CircularProgressIndicator(strokeWidth: 2.0)),
            );
          } else {
            return Container(
              width: double.infinity,
              alignment: Alignment.center,
              padding: const EdgeInsets.all(10),
              child:inflateText(list_str[index], Colors.blueAccent, 16),
            );
          }
        });
  }

  loadDate() {
    Future.delayed(Duration(seconds: 2)).then((e) {
      setState(() {
        list_str ??= [];
        if(list_str.length==0){
          list_str.add(endTag);
        }
        list_str.insertAll(list_str.length-1, page);

        if(list_str.length>100){
          list_str.removeAt(list_str.length-1);
          list_str.add("没有更多条目了");
        }
      });
    });
  }

  getEmptyView() {
    return Container(
      color: Colors.white,
      child: Center(
        child: GestureDetector(
          child: Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: <Widget>[
              Icon(Icons.adjust),
              SizedBox(
                height: 10,
              ),
              inflateText('点击刷新', Colors.redAccent, 14),
            ],
          ),
          onTap: () {
            loadDate();
            printString("开始刷新");
          },
        ),
      ),
    );
  }
}

这里面有个特殊的用法,如果想要实现一个listview有多种条目,可以在build的时候根据index 判断,
然后使用不同的widget,其他的没有什么可以说的了,

我学习flutter的整个过程都记录在里面了
https://www.jianshu.com/c/36554cb4c804

最后附上demo 地址

https://github.com/tsm19911014/tsm_flutter

上一篇下一篇

猜你喜欢

热点阅读