Flutter basics: the use of listview

Introduction

Listview is one of the most commonly used scrolling components in flutter, which can easily realize the linear arrangement of multiple subcomponents in one direction. Let's take a look at its default constructor:

ListView({
    
    
    Key key,
    Axis scrollDirection = Axis.vertical,
    bool reverse = false,
    ScrollController controller,
    bool primary,
    ScrollPhysics physics,
    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,
    DragStartBehavior dragStartBehavior = DragStartBehavior.start,
    ScrollViewKeyboardDismissBehavior keyboardDismissBehavior = ScrollViewKeyboardDismissBehavior.manual,
    String restorationId,
    Clip clipBehavior = Clip.hardEdge,
  })
  • scrollDirection : The direction of list scrolling, optional Axis.vertical, Axis.horizontal represent vertical sliding and horizontal sliding, the default is vertical.
  • reverse : Whether to display in reverse order, the default is to display in forward order.
  • controller : The controller of listview, which can be used to monitor the sliding state.
  • physics : physics has several options,
AlwaysScrollableScrollPhysics() always swipe
NeverScrollableScrollPhysics() no scrolling
BouncingScrollPhysics() The content exceeds one screen, and there is a rebound effect when pulled to the top
ClampingScrollPhysics() Wrap content, there will be no snapback
  • shrinkWrap : Whether the length of the list only wraps the length of its content, the default is false. Note that when the listview is included in a component with an indeterminate length, it must be set to true, otherwise an error will be reported.
  • children : An array of components that store child elements.

A brief introduction to some commonly used parameters, let's take a look at the commonly used methods.

default constructor

The child elements of the default constructor are written directly in the children list, and it accepts Widget. This method is more suitable for situations with fewer elements, and it is also very useful for situations with large differences in sub-elements.

ListView(
  shrinkWrap: true, 
  padding: const EdgeInsets.all(20.0),
  children: <Widget>[
    new Text('item1'),
    new Text('item2'),
    new Text('item3'),
  ],
);

ListView.builder

  new ListView.builder(
              itemBuilder: (BuildContext context, int index) {
    
    
                return getItem(index);
              },
              itemCount: data.length,
              itemExtent: 50.0, //强制高度为50.0
              shrinkWrap: true,
              physics: BouncingScrollPhysics(),
            )
  • itemBuilder : The builder of the sub-element, the parameters include context and index (the current list position), and the return value is a widget. When the list scrolls to a specific index position, the builder will be called to build the list item.
  • itemCount : The number of sub-items, here returns the length of the test data. The listview elements are infinite when this parameter is not used.

Rewrite the initState method and add test data:

  List data = [];
  @override
  void initState() {
    
    
    super.initState();
    setState(() {
    
    
      for (int i = 0; i < 100; i++) {
    
    
        data.add("item $i");
      }
    });
  }

Then there is the getItem method for constructing sub-elements, where GestureDetector is used to handle click events, and toast uses the fluttertoast: ^3.1.3 package.

  Widget getItem(int index) {
    
    
    return new GestureDetector(
      onTap: () {
    
    
        //处理点击事件
        showToast(data[index]);
      },
      child: new Container(
        padding: const EdgeInsets.all(14.0),
        child: new Text(data[index]),
      ),
    );
  }

ListView.separated

The main difference between ListView.separated and ListView.builder is that it provides a mandatory parameter separatorBuilder to generate the dividing line, the example is as follows:

 new ListView.separated(
              itemBuilder: (BuildContext context, int index) {
    
    
                return getItem(index);
              },
              separatorBuilder: (BuildContext context, int index) {
    
    
                return new Divider(
                  endIndent: 50,
                  height: 1,
                  thickness: 1,
                );
              },
              itemCount: data.length,
              shrinkWrap: true,
              physics: ClampingScrollPhysics(),
            )

Divider is the dividing line, the parameters are

  • height : The height occupied by the dividing line .

  • thickness : The thickness of the dividing line.

  • indent : The length of the blank space at the start and end of the dividing line.

  • endIndent : The length of the blank at the end of the dividing line.

  • color : The color of the line.

    另外:itemCount在这种模式下是必填参数,与ListView.builder不同。ListView.builder的方式要
    添加分割线的话可以在itemBuilder中添加(即添加到子元素中)。
    

complete example

Finally paste the complete sample code:

import 'package:flutter/material.dart';
import 'package:flutter/rendering.dart';
import 'package:fluttertoast/fluttertoast.dart';

void main() {
    
    
  runApp(new ListViewApp());
}

class ListViewApp extends StatelessWidget {
    
    
  @override
  Widget build(BuildContext context) {
    
    
    // TODO: implement build
    return new MaterialApp(
      theme: ThemeData.light(),
      home: new ListViewWidget(),
      title: "listViewSample",
    );
  }
}

class ListViewWidget extends StatefulWidget {
    
    
  @override
  ListState createState() => new ListState();
}

class ListState extends State<ListViewWidget> {
    
    
  List data = [];

  @override
  void initState() {
    
    
    super.initState();
    setState(() {
    
    
      for (int i = 0; i < 100; i++) {
    
    
        data.add("item $i");
      }
    });
  }

  @override
  Widget build(BuildContext context) {
    
    
    // TODO: implement build
    return new Scaffold(
        appBar: new AppBar(
          backgroundColor: Colors.blue,
          title: new Center(
            child: new Text('listViewTitle'),
          ),
        ),
        body: new Column(
          children: [

            new Expanded(
                child: new ListView.separated(
              itemBuilder: (BuildContext context, int index) {
    
    
                return getItem(index);
              },
              separatorBuilder: (BuildContext context, int index) {
    
    
                return new Divider(
                  endIndent: 50,
                  height: 1,
                  thickness: 1,
                );
              },
              itemCount: data.length,
              shrinkWrap: true,
              physics: ClampingScrollPhysics(),
            )),

          ],
        ));

     
  }

  Widget getItem(int index) {
    
    
    return new GestureDetector(
      onTap: () {
    
    
        //处理点击事件
        showToast(data[index]);
      },
      child: new Container(
        padding: const EdgeInsets.all(14.0),
        child: new Text(data[index]),
      ),
    );
  }

  void showToast(String toast) {
    
    
    Fluttertoast.showToast(
      msg: toast,
      toastLength: Toast.LENGTH_SHORT,
      gravity: ToastGravity.BOTTOM,
      timeInSecForIos: 1,
    );
  }
}

running result:

insert image description here

Guess you like

Origin blog.csdn.net/weixin_40652755/article/details/109491469