如何在列表视图顶部添加一行

Posted

技术标签:

【中文标题】如何在列表视图顶部添加一行【英文标题】:how to add a row on top of listview 【发布时间】:2020-09-30 09:41:48 【问题描述】:

我是 Flutter 的新手,我有一个行列表,这些行是列表视图的一部分,其中包含列表中的字符串,我想在列表视图顶部添加一个单独的标题以放置不同的内容,但我由于 listview 与 futureBuilder 相结合而不断出现错误,我应该添加什么样的代码?

`body: FutureBuilder<Album>(
    future: futureAlbum,
    builder: (context, AsyncSnapshot snapshot) 
      if (snapshot.hasData) 
        return Container(
          child: ListView.builder(
              itemBuilder: (context, index) 
                return Card(
                    child: Container(
                  width: double.infinity,
                  padding: EdgeInsets.all(5),
                  child: Row(
                    mainAxisAlignment: MainAxisAlignment.spaceBetween,
                    children: [
                      Container(
                        padding: EdgeInsets.all(10),
                        child: Column(
                          crossAxisAlignment: CrossAxisAlignment.center,
                          children: [
                            Text(
                              _sell[index]["text"],
                              style: TextStyle(fontSize: 20),
                            ),
                            Text(
                              (snapshot.data.sellprice[index]).toString(),
                              style: TextStyle(fontSize: 20,color:Colors.grey),
                            ),
                          ],
                        ),
                      ),
                      Container(
                        padding: EdgeInsets.all(10),
                        child: Column(
                          crossAxisAlignment: CrossAxisAlignment.center,
                          children: [
                            Text(
                              _buy[index]["text"],
                              style: TextStyle(fontSize: 20),
                            ),
                            Text(
                              _buy[index]["symbol"],
                              style: TextStyle(
                                  fontSize: 20, color: Colors.grey),
                            ),
                          ],
                        ),
                      ),
                      Container(
                        padding: EdgeInsets.all(10),
                        child: Column(
                          crossAxisAlignment: CrossAxisAlignment.center,
                          children: [
                            Text(
                              _currency[index]["text"],
                              style: TextStyle(fontSize: 17),
                            ),
                            Text(
                              _currency[index]["symbol"],
                              style: TextStyle(
                                  fontSize: 17, color: Colors.grey),
                            ),
                          ],
                        ),
                      ),
                      Container(
                        child: Column(
                          crossAxisAlignment: CrossAxisAlignment.center,
                          children: [
                            Image.asset(
                              _picture[index],
                              height: 50,
                              width: 50,
                            ),
                          ],
                        ),
                      ),
                    ],
                  ),
                ),);
              ,
              itemCount: 7),

  `

【问题讨论】:

【参考方案1】:

尝试类似:

body: FutureBuilder<Album>(
future: futureAlbum,
builder: (context, AsyncSnapshot snapshot) 
  if (snapshot.hasData) 
    return Container(
      child: ListView.builder(
          itemBuilder: (context, index) 
            return Card(
                child: Container(
              width: double.infinity,
              padding: EdgeInsets.all(5),
              child: _content(index),
            ),);
          ,
          itemCount: 7),
  







_content(index)
    if(index ==  0)
      return /*Different header*/
     else 
      return  Row(
        mainAxisAlignment: MainAxisAlignment.spaceBetween,
        children: [
          Container(
            padding: EdgeInsets.all(10),
            child: Column(
              crossAxisAlignment: CrossAxisAlignment.center,
              children: [
                Text(
                  _sell[index]["text"],
                  style: TextStyle(fontSize: 20),
                ),
                Text(
                  (snapshot.data.sellprice[index]).toString(),
                  style: TextStyle(fontSize: 20,color:Colors.grey),
                ),
              ],
            ),
          ),
          Container(
            padding: EdgeInsets.all(10),
            child: Column(
              crossAxisAlignment: CrossAxisAlignment.center,
              children: [
                Text(
                  _buy[index]["text"],
                  style: TextStyle(fontSize: 20),
                ),
                Text(
                  _buy[index]["symbol"],
                  style: TextStyle(
                      fontSize: 20, color: Colors.grey),
                ),
              ],
            ),
          ),
          Container(
            padding: EdgeInsets.all(10),
            child: Column(
              crossAxisAlignment: CrossAxisAlignment.center,
              children: [
                Text(
                  _currency[index]["text"],
                  style: TextStyle(fontSize: 17),
                ),
                Text(
                  _currency[index]["symbol"],
                  style: TextStyle(
                      fontSize: 17, color: Colors.grey),
                ),
              ],
            ),
          ),
          Container(
            child: Column(
              crossAxisAlignment: CrossAxisAlignment.center,
              children: [
                Image.asset(
                  _picture[index],
                  height: 50,
                  width: 50,
                ),
              ],
            ),
          ),
        ],
      ),
    
  

【讨论】:

【参考方案2】:

假设您的标题小部件是HeaderWidget 类型(可以是另一个ContainerRow 或自定义小部件)。然后你必须问自己以​​下问题:当我在列表视图中滚动足够远时,标题会消失还是总是停留在顶部?

可滚动:

ListView.builder(
  itemBuilder: (context, i) => i < 1 ? HeaderWidget() : buildChild(i-1),
  itemCount: 7,
)

不可滚动/固定:

Column(
  children: <Widget>[
    HeaderWidget(),
    ListView.builder(
      itemBuilder: (context, i) => buildChild(i),
      itemCount: 7,
    ),
  ],
)

【讨论】:

【参考方案3】:

对我有用的是将 ListView 和标题包装在一个列中。我为了让 ListView 覆盖剩余的高度,将其包裹在 Expanded 小部件中,如下所示:

Column(
 children: <Widget>[
   Text("Header Title")
     Expanded(
      child: ListView.builder(
        itemCount: data.length,
        itemBuilder: (BuildContext context, int index)
          return (
            Container()
         )
       
     )
   ),
],

)

【讨论】:

以上是关于如何在列表视图顶部添加一行的主要内容,如果未能解决你的问题,请参考以下文章

一行代码为特定状态绑定SwiftUI视图动画

从列表视图的顶部到底部拖动项目时如何提高速度?

如何将Firebase Recycler视图从最新(列表顶部)排序到最旧[重复]

如何剪切面具上的列表视图?

如何绑定列表视图

在 Listview 的第一行添加 ViewFlipper