【问题标题】:Flutter remove space between GridView rowFlutter删除GridView行之间的空间
【发布时间】:2026-01-02 06:40:01
【问题描述】:

我正在尝试创建一个凸起按钮的网格视图,但网格的行之间存在大量空间,如下图所示:

我正在使用页面底部的代码实现 GridView:

如你所见,我设置了:

SliverGridDelegateWithMaxCrossAxisExtent(maxCrossAxisExtent: 150, mainAxisSpacing: 4, crossAxisSpacing: 4), 

我本来希望设置主轴间距和横轴间距应该删除这些空间。

我还尝试在一个大小合适的框中返回 gridview 并将其更改为 SliverGridWithFixedCount,但似乎没有任何更改。

我不确定我在布局中做错了什么?

感谢您的帮助

body: Column(
        children: <Widget>[
          Flexible(
            child: filtersGridView(),
          ),
        ],
      ),
    );
  }
}


class filtersGridView extends StatefulWidget {
  @override
  _filtersGridViewState createState() => _filtersGridViewState();
}

class _filtersGridViewState extends State<filtersGridView> {

  final List <DocumentSnapshot> documents;
  _filtersGridViewState({this.documents});

  @override
  Widget build(BuildContext context) {
    return StreamBuilder(
      stream: Firestore.instance.collection('categories').snapshots(),
      builder: (BuildContext context, AsyncSnapshot snapshot) {
        if (!snapshot.hasData) {
          return Center(child: const Text('Loading events...'));
        }
        return GridView.builder(
          gridDelegate:
          SliverGridDelegateWithMaxCrossAxisExtent(maxCrossAxisExtent: 150, mainAxisSpacing: 4, crossAxisSpacing: 4),
          itemBuilder: (BuildContext context, int index) {
            return Column(children: <Widget>[
              InkWell(
                onTap: () {

                },
                child: SizedBox(
                  height: 30,
                  child: RaisedButton(
                    color: Colors.white,
                    child: Row(
                      children: <Widget>[
                        Text(snapshot.data.documents[index]['name'].toString(), textAlign: TextAlign.center, style: TextStyle(fontSize:  15, color: Colors.black,),),
                         ],
                    ),

【问题讨论】:

  • 谢谢,但文字不是问题。我在图像中理解文本溢出,但这不是我的问题。我只是将文本大小设置为 2,行之间的空间仍然存在。
  • 对不起,好吧,你为什么要使用maxCrossAxisExtent: 150
  • 我只是在玩设置,正如我在问题中所说,我也尝试使用固定数量的列,但这也不会改变它。
  • 实际上,使用Wrap 小部件可以更轻松地完成您想要完成的任务。 wrap 小部件类似于 Row 或 Column 小部件,具有一个额外的优点是它可以根据屏幕上可用的空间调整其子级。你考虑过这个解决方案吗?示例:flutter-widget.live/widgets/Wrap

标签: flutter flutter-layout flutter-gridview


【解决方案1】:

如果您担心按钮内部的填充 - 这是由于材质按钮的最小宽度设置被设置为 88

另外,根据我的经验,我注意到材质按钮周围有一些奇怪的边距。我用materialTapTargetSize: MaterialTapTargetSize.shrinkWrap解决了这个问题。

ButtonTheme(
  minWidth: 0,
  height: 30,
  child: RaisedButton(
    materialTapTargetSize: MaterialTapTargetSize.shrinkWrap,
    // ...
  )
)

如果您希望按钮在高度上填充整个 maxCrossAxisExtent - 请使用分配了自定义约束的 RawMaterialButton


更新

我认为问题出在按钮上,但我突然想到这实际上与 GridView 委托有关。

SliverGridDelegateWithMaxCrossAxisExtent 如何按照 Flutter 文档工作:

This delegate creates grids with equally sized and spaced tiles.

委托的childAspectRatio 属性的默认值为1.0,即 - 一个正方形。您将获得一个完美的逻辑布局 - 1:1 块的网格。

要解决这个问题,您需要提出正确的 childAspectRatio 值。

一些伪代码:cellHeight = cellWidth / childAspectRatio

例如 childAspectRatio: 2 将显示如下大小的单元格:

        2
-----------------
|               |
|               | 1
|               |
-----------------

如果这有帮助,请告诉我。

【讨论】:

  • 谢谢。我删除了按钮,但按钮还是一样
  • 嗨,George,谢谢,我也刚刚解决了。我改变了像这样的纵横比 SliverGridDelegateWithFixedCrossAxisCount(childAspectRatio: 3, crossAxisCount: 3,),
【解决方案2】:

试试这个希望,它会起作用,

GridView.builder(
        itemCount: 6,
        gridDelegate:
            SliverGridDelegateWithFixedCrossAxisCount(crossAxisCount: 3,),
        itemBuilder: (context, index) {
          return Padding(
            padding: const EdgeInsets.all(8.0),
            child: Container(
              child: Flex(
                direction: Axis.vertical,
                children: <Widget>[
                  Expanded(flex: 5, child: InkWell(
                    onTap: (){},
                  )),
                  Expanded(
                      flex: 5,
                      child: RaisedButton(
                        onPressed: () {},
                        child: Text('Bt'),
                      ))
                ],
              ),
            ),
          );
        },
      ),

【讨论】:

    【解决方案3】:

    childAspectRatio 的值增加到 2,

                          primary: false,
                          scrollDirection: Axis.vertical,
                          // padding: const EdgeInsets.all(10),
                          crossAxisSpacing: 10,
                          mainAxisSpacing: 10,
                          maxCrossAxisExtent: 180.0,
                          shrinkWrap: true,
                          childAspectRatio: 2,
                          children: <Widget>[
                            container(),
                            container(),
                            container(),
                          ])
    

    【讨论】: