Flutter ListView.builder 创建一个无限滚动。如何将其设置为在内容结束时停止?

Posted

技术标签:

【中文标题】Flutter ListView.builder 创建一个无限滚动。如何将其设置为在内容结束时停止?【英文标题】:Flutter ListView.builder creates an infinite scroll. How can I set it to stop at the end of content? 【发布时间】:2018-09-01 13:59:42 【问题描述】:

我正在使用ListView.buildler 将小部件分层,使其成为垂直滚动。这种方法的唯一问题是当滚动到达我的内容的末尾时。它会自动回到顶部。目前我有这个:

    new ListView.builder(
    scrollDirection: Axis.vertical,
    key: new Key(randomString(20)),
    reverse: false,
    primary: true,
    itemBuilder: (BuildContext context, int index) 
        return new Column(
        children: <Widget>[
            new Padding(
            padding: _bookPadding,
            child: new Container(
                width: 106.0,
                height: 162.0,
                child: new FadeInImage(
                    placeholder: new AssetImage('assets/loading.gif'),
                    image: this.book.cover)
            ),
            ),
            const Divider(),
            new Padding(
                padding: _bookPadding,
                child: new Text(
                    this.book.bookName,
                    style: getTextStyle())),
            const Divider(),
            new Padding(
            padding: _bookPadding,
            child: new Text(
                'By ' + this.book.author,
                style: getTextStyle(), ),
            ),
           ....

是否可以在 ListView.builder 到达末尾时将其设置为不换行?

【问题讨论】:

返回 null 结束 ListView。 我不确定如何在 ListView 中返回 null。每当小部件或子级尝试返回 null 时,Flutter 都会抱怨。 Dart/Flutter - Flutter - Why ListView is going infinite的可能重复 【参考方案1】:

这最终变得非常容易。不知道我是如何从文档中错过的,我只需要添加一个 Item count = non-null。就我而言,由于我在一个 Column 小部件中构建所有内容,因此在列表视图构建器中,这就是我的构建器的样子:

new ListView.builder(
    scrollDirection: Axis.vertical,
    key: new Key(randomString(20)),
    primary: true,
    itemCount: 1,
    itemBuilder: (BuildContext context, int index) 
        return new Column(
        children: <Widget>[ .....

我确实想知道这个实现是否是一个糟糕的模式。当 Column 的每个子项变为可见时,ListView.Builder 是否仍会呈现 Component Column 的每个嵌套子项?

来自文档:“创建按需创建的可滚动的线性小部件数组。 此构造函数适用于具有大量(或无限)子级的列表视图,因为仅对那些实际可见的子级调用构建器。”

【讨论】:

为什么要把孩子放在一个专栏里?将它们直接放在 itembuilder 中对我来说更有意义。 itembuilder 的好处是它只构建需要的小部件,现在它构建 Column。 Column 将立即构建其所有子级。此外,如果您有一个只有 1 个项目的 ListView,您可能需要一个 SingleChildScrollView。您需要使用 Column 的任何内容吗? @Rene 是的,起初我正在使用 Column 小部件,但发现它没有提供我想要的 Scrollable 功能,包装它 ListView.builder 提供了我想要的滚动。我最初认为它可能会将加载属性/好处扩展到小部件子级。但是,正如我上面提到的“质疑”实现,很明显,当设置 itemCount=1 时,它确实正在加载整个项目。我同意,我会将此实现迁移到 SIngleChildScrollView 或将它们直接放在项目构建器中。 我刚刚回答了一个更容易实现代码的示例。你也可以试试。【参考方案2】:

您可以跳过很多代码。有时 itemBuilder 非常好,特别是当您有很多小部件并且可以通过索引轻松识别您的项目时,但您也可以直接使用子项。来自ListView documentation 的示例:

new ListView(
  shrinkWrap: true,
  padding: const EdgeInsets.all(20.0),
  children: <Widget>[
    const Text('I\'m dedicating every day to you'),
    const Text('Domestic life was never quite my style'),
    const Text('When you smile, you knock me out, I fall apart'),
    const Text('And I thought I was so smart'),
  ],
)

【讨论】:

以上是关于Flutter ListView.builder 创建一个无限滚动。如何将其设置为在内容结束时停止?的主要内容,如果未能解决你的问题,请参考以下文章

如何在 Flutter 中添加 ListView.builder 的填充顶部?

Flutter - ListView.builder:初始滚动位置

Flutter:ListView.builder 创建列

Flutter - 另一个 Listview 中的 Listview.builder

Flutter:ListView.builder 中的自动垂直高度

Flutter 应用程序,ListView.builder 首次运行时出现错误。需要重启应用(ListView.builder 和 image_picker)