“This is the fourth day of my participation in the Gwen Challenge in November. Check out the details: The Last Gwen Challenge in 2021.”

In iOS, we use UITableView to implement lists. The corresponding widget in Flutter is ListView. We use ListView to initially implement a simple list interface;

The use of the ListView

model

To display a list, we need to display a data model in the list. Here we create an article. Dart file and create a model in it:

class Article {
  const Article(this.name, this.iconUrl); // constructor
  final String name;
  final String iconUrl;
}
Copy the code

There is another way to create a model, as follows:

class Article {
  const Article({this.name, this.iconUrl}); // Constructor optional assignment
  final String? name; / /? Air safety
  final String? iconUrl;
}
Copy the code

So, what’s the difference between these two approaches?

  • const Article(this.name, this.iconUrl);Is a constructor that initializesnameandiconUrlMust assign;
  • const Article({this.name, this.iconUrl});Is also a constructor whose initializationnameandiconUrlYou can skip the assignment, but note that either of the following two conditions must be met:
    • nameandiconUrlMust have default values;
    • nameandiconUrlSet to empty security;

The List data source

Dart creates an array directly in the article. Dart file to hold the Article class as the data source for the list.

final List<Article> datas = [] // The details are not released
Copy the code

At this point,article.dartThe documents are as follows:

ListView

Before we use ListView, we need to know that when we use ListView, we usually do not directly create the construction, but use its named constructor to create; Create code as follows:

ListView.builder(itemBuilder: itemBuilder)
Copy the code

Builder is when we create the ListView, we need a render; ItemBuilder is a method callback; By definition

required IndexedWidgetBuilder itemBuilder,
Copy the code

We know that it returns IndexedWidgetBuilder:

typedef IndexedWidgetBuilder = Widget Function(BuildContext context, int index);
Copy the code

This function returns a Widget, and we notice that the function has two parameters, context and index. At this point, we immediately realize from previous iOS development experience that this function is similar to the cellForRow method in UITableView;

Based on this function, we create a method that returns the Widget:

	Widget _itemForRow(BuildContext context, int index) {
    return null
  }

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('Flutter engineering'),
      ),
      body: ListView.builder(
          itemBuilder: _itemForRow,
          itemCount: datas.length,
      ),
    );
  }
Copy the code
  • _Means internal access, inside the file!
  • _itemForRowMethod returns each of themcellThe view;
  • itemCountMethod to pass the number of data in the entire list;

Show article title

Let’s start by simply returning a Text widget to display the article title:

Widget _itemForRow(BuildContext context, int index) {
    return Text(datas[index].name);
}
Copy the code

Note that if the name attribute is null-safe, then forced unpacking is required:

Widget _itemForRow(BuildContext context, int index) {
    returnText(datas[index].name!) ; }Copy the code

Operation effect:

Show cover picture

When loading the Image, we use the Image widget;

Image.net work (' ')Copy the code

We change the _itemForRow function code to look like this:

  Widget _itemForRow(BuildContext context, int index) {
    return Container(
      color: Colors.white,
      margin: const EdgeInsets.all(10),
      child: Image.network(datas[index].iconUrl),
    );
  }
Copy the code

Container is a common widget that facilitates layout

Display effect:

Display title and cover

We found that the Child of the Container widget can display only one widget, so we can’t display the title and cover of the article at the same time.

So, is there a component that can hold multiple components? We want the title to appear at the bottom of the cover. The cover and title are arranged vertically. In this case, we have the Column widget to do this, and the Column widget has the children property, which is an array that holds multiple widgets at once:

  Widget _itemForRow(BuildContext context, int index) {
    return Container(
      color: Colors.white,
      margin: const EdgeInsets.all(10),
      child: Column(
        children: [
          Image.network(datas[index].iconUrl),
          Container(height: 10,),
          Text(
            datas[index].name,
            style: const TextStyle(
              fontSize: 20() [() [(). }Copy the code

Container(height: 10,), : 10 pixels between the cover and the title, the same effect that a SizedBox widget can achieve;

The effect is as follows:The complete code is as follows:

class ListViewDemo extends StatelessWidget {
  // _ internal refers to file internal!
  Widget _itemForRow(BuildContext context, int index) {
    return Container(
      color: Colors.white,
      margin: const EdgeInsets.all(10),
      child: Column(
        children: [
          Image.network(datas[index].iconUrl),
          const SizedBox(height: 10,),
          Text(
            datas[index].name,
            style: const TextStyle(
              fontWeight: FontWeight.w800,
              fontSize: 20() [() [(). }@override
  Widget build(BuildContext context) {
    return Scaffold(
      backgroundColor: Colors.grey,
      appBar: AppBar(
        title: const Text('Use of ListView'), ), body: ListView.builder( itemBuilder: _itemForRow, itemCount: datas.length, ), ); }}Copy the code

The little knowledge Flutter

There are only three component layouts:

  • The vertical
  • Across the
  • Fold the