【问题标题】:Space between Column's children in FlutterFlutter中Column的孩子之间的空间
【发布时间】:2019-03-17 09:55:05
【问题描述】:

我有一个 Column 小部件,其中有两个 TextField 小部件作为子小部件,我希望它们之间有一些空间。

我已经尝试过mainAxisAlignment: MainAxisAlignment.spaceAround,但结果不是我想要的。

【问题讨论】:

  • 简单地把SizedBox(height: 15.0, ), 两个TextField之间
  • margin: EdgeInsets.only(left: 200.0, top: 300.0))

标签: dart flutter flutter-layout


【解决方案1】:

您可以在这两个小部件之间使用Padding 小部件,或者使用Padding 小部件包装这些小部件。

更新

SizedBox 小部件可以在两个小部件之间使用,以在两个小部件之间添加空间,它使代码比填充小部件更具可读性。

例如:

Column(
  children: <Widget>[
    Widget1(),
    SizedBox(height: 10),
    Widget2(),
  ],
),

【讨论】:

  • 我当然希望column-class 包含该属性。在所有孩子之间获取填充将浪费编码时间。
  • 当填充小部件仅采用单个子参数时,如何将两个小部件包装在一个填充小部件中?
  • @ScottF 答案说Padding 小部件介于 2 个小部件之间。并不是说这 2 个小部件成为 Padding 的子级。
  • 它直接说“或者用 Padding 小部件包装这些小部件”....
  • @ScottF 将子元素设为列或行,将两个小部件作为子元素。
【解决方案2】:

您可以在小部件之间放置一个带有特定heightSizedBox,如下所示:

Column(
  children: <Widget>[
    FirstWidget(),
    SizedBox(height: 100),
    SecondWidget(),
  ],
),

为什么更喜欢这个而不是在Padding 中包装小部件?可读性!视觉样板更少,缩进更少,代码遵循典型的阅读顺序。

【讨论】:

  • 添加一个大小的框就像添加一个空视图对吗?不会导致任何问题吗?
  • SizedBox 只是一个普通的小部件,它在布局期间尝试达到所需的大小,但不渲染任何东西。所有像 Text 或 Container 这样的叶子小部件都是空的,所以没关系。
【解决方案3】:

您可以使用 Wrap() 小部件而不是 Column() 在子小部件之间添加空间。并使用间距属性在子小部件之间提供相等的间距

Wrap(
  spacing: 20, // to apply margin in the main axis of the wrap
  runSpacing: 20, // to apply margin in the cross axis of the wrap
  children: <Widget>[
     Text('child 1'),
     Text('child 2')
  ]
)

【讨论】:

  • 使用runSpacing 而不是spacing 来表示垂直间隔项目之间的间隙
  • 这对我有用。我认为这是最好的解决方案,但是使用 Wrap() 而不是 Column() 的缺点是什么?
  • Column 是一个扩展的小部件,而 Wrap 不是。所以当你想扩展父级的整个空间时,你应该使用扩展的小部件,如 Column 或 Row 等。这取决于你的情况
  • 是的,这比单独包装每个孩子要好得多。好建议。
  • 哪个更适合 Flutter Web?
【解决方案4】:

有很多方法,我在这里列出一些。

  1. 使用 SizedBox 并提供一些高度:

     Column(
       children: <Widget>[
         Widget1(),
         SizedBox(height: 10), // <-- Set height
         Widget2(),
       ],
     )
    
  2. 使用Spacer

     Column(
       children: <Widget>[
         Widget1(),
         Spacer(), // <-- Spacer
         Widget2(),
       ],
     )
    
  3. 使用Expanded

     Column(
       children: <Widget>[
         Widget1(),
         Expanded(child: SizedBox.shrink()), // <-- Expanded
         Widget2(),
       ],
     )
    
  4. 设置mainAxisAlignment

     Column(
       mainAxisAlignment: MainAxisAlignment.spaceAround, // <-- alignments
       children: <Widget>[
         Widget1(),
         Widget2(),
       ],
     )
    
  5. 使用Wrap

     Wrap(
       direction: Axis.vertical, 
       spacing: 20, // <-- Spacing between children
       children: <Widget>[
         Widget1(),
         Widget2(),
       ],
     )
    

【讨论】:

  • 这对了解所有不同的方法非常有帮助。感谢分享!
【解决方案5】:

只需像这样使用填充来包装它:

Column(
  children: <Widget>[
  Padding(
    padding: EdgeInsets.all(8.0),
    child: Text('Hello World!'),
  ),
  Padding(
    padding: EdgeInsets.all(8.0),
    child: Text('Hello World2!'),
  )
]);

您也可以使用 Container(padding...) 或 SizeBox(height: x.x)。最后一个是最常见的,但它取决于您希望如何管理小部件的空间,如果空间确实是小部件的一部分,我喜欢使用填充,例如使用 sizebox 作为列表。

【讨论】:

  • 有没有办法做css grid-gap之类的事情?
【解决方案6】:

我在这里没有看到这个解决方案,所以为了完整起见,我会发布它。

您也可以使用map 包裹子代Padding

Column(
      children: [Text('child 1'), Text('child 2')]
          .map(
            (e) => Padding(
              padding: const EdgeInsets.all(8),
              child: e,
            ),
          )
          .toList(),
    );

【讨论】:

  • 这比在每个小部件后添加sizedBox() 更好。
  • @abrsh 有时很有用,但它并没有真正在 项之间添加空格,而是在它们周围添加空格。
【解决方案7】:
Column(
  children: <Widget>[
    FirstWidget(),
    Spacer(),
    SecondWidget(),
  ]
)

Spacer 创建一个灵活的空间以插入到 [Flexible] 小部件中。 (像一个列)

【讨论】:

  • 请在您的答案中添加一些解释,以帮助其他人更好地理解它。仅代码的答案被认为是不礼貌的,它可能无法帮助 OP 理解您试图帮助解决的问题。
【解决方案8】:

出于代码可读性的目的,使用 SizedBox above 的方式相同,您可以以相同的方式使用 Padding 小部件,而不必使其成为任何 Column 子级的父小部件

Column(
  children: <Widget>[
    FirstWidget(),
    Padding(padding: EdgeInsets.only(top: 40.0)),
    SecondWidget(),
  ]
)

【讨论】:

    【解决方案9】:

    如果您不想用每个小部件包装 Padding 或重复 SizedBox。

    试试这个:

    Column(
            children: [
              Widget(),
              Widget(),
              Widget(),
              Widget(),
            ]
                .map((e) => Padding(
                      child: e,
                      padding: const EdgeInsets.symmetric(vertical: 10),
                    ))
                .toList(),
          ),
    

    这将使用填充而不重复地扭曲所有小部件。

    【讨论】:

    • 答案需要支持信息以便更好地理解。
    • @pmadhu 我添加了更多细节
    【解决方案10】:

    你可以用不同的方式解决这个问题。

    如果你使用 Row/Column 那么你必须使用 ma​​inAxisAlignment: MainAxisAlignment.spaceEvenly

    如果你使用 Wrap Widget 你必须使用 runSpacing: 5, spacing: 10、

    在任何你可以使用SizeBox()

    【讨论】:

      【解决方案11】:

      列默认没有高度, 您可以将列包装到容器中,并将特定高度添加到容器中。 然后您可以使用以下内容:

      Container(
         width: double.infinity,//Your desire Width
         height: height,//Your desire Height
         child: Column(
            mainAxisAlignment: MainAxisAlignment.spaceBetween,
            children: <Widget>[
               Text('One'),
               Text('Two')
            ],
         ),
      ),
      

      【讨论】:

        【解决方案12】:

        您还可以使用辅助函数在每个孩子之后添加间距。

        List<Widget> childrenWithSpacing({
          @required List<Widget> children,
          double spacing = 8,
        }) {
          final space = Container(width: spacing, height: spacing);
          return children.expand((widget) => [widget, space]).toList();
        }
        

        那么,返回的列表可以用作列的子列

        Column(
          children: childrenWithSpacing(
            spacing: 14,
            children: [
              Text('This becomes a text with an adjacent spacing'),
              if (true == true) Text('Also, makes it easy to add conditional widgets'),
            ],
          ),
        );
        

        我不确定如果让孩子们通过辅助函数来实现相同的目标是错误的还是会降低性能?

        【讨论】:

          【解决方案13】:
          Column(children: <Widget>[
             Container(margin: EdgeInsets.only(top:12, child: yourWidget)),
             Container(margin: EdgeInsets.only(top:12, child: yourWidget))
          ]);
          

          【讨论】:

            【解决方案14】:

            您可能必须在列的子级之间使用 SizedBox() 小部件。 希望对你有用

            【讨论】:

            【解决方案15】:

            大小框在这种情况下没有帮助,手机处于横向模式。

            body: Column(
                  mainAxisAlignment: MainAxisAlignment.spaceBetween,
                  crossAxisAlignment: CrossAxisAlignment.stretch,
                  children: <Widget>[
                    Expanded(
                       child: Container(
                        margin: EdgeInsets.all(15.0),
                        decoration: BoxDecoration(
                          color: Color(0xFF1D1E33),
                          borderRadius: BorderRadius.circular(10.0),
                        ),
                      ),
                    ),
                    Expanded(
                       child: Container(
                        margin: EdgeInsets.all(15.0),
                        decoration: BoxDecoration(
                          color: Color(0xFF1D1E33),
                          borderRadius: BorderRadius.circular(10.0),
                        ),
                      ),
                    ),
                    Expanded(
                       child: Container(
                        margin: EdgeInsets.all(15.0),
                        decoration: BoxDecoration(
                          color: Color(0xFF1D1E33),
                          borderRadius: BorderRadius.circular(10.0),
                        ),
                      ),
                    ),
                  ],
                 )
            

            【讨论】:

              【解决方案16】:

              这是另一个涉及 for 循环的选项。

              Column(
                children: <Widget>[
                  for (var i = 0; i < widgets.length; i++)
                    Column(
                      children: [
                        widgets[i], // The widget you want to create or place goes here.
                        SizedBox(height: 10) // Any kind of padding or other widgets you want to put.
                      ])
                ],
              ),
              

              【讨论】:

                【解决方案17】:

                你可以试试这个:

                
                import 'package:flutter/material.dart';
                
                class CustomColumn extends Column {
                  CustomColumn({
                    Key? key,
                    MainAxisAlignment mainAxisAlignment = MainAxisAlignment.start,
                    MainAxisSize mainAxisSize = MainAxisSize.max,
                    CrossAxisAlignment crossAxisAlignment = CrossAxisAlignment.center,
                    TextDirection? textDirection,
                    VerticalDirection verticalDirection = VerticalDirection.down,
                    TextBaseline? textBaseline,
                    List children = const [],
                    EdgeInsetsGeometry? rowPadding,
                  }) : super(
                          children: children.map((e) => Padding(padding : rowPadding ?? EdgeInsets.only(bottom:12), child : e)).toList(),
                          key: key,
                          mainAxisAlignment: mainAxisAlignment,
                          mainAxisSize: mainAxisSize,
                          crossAxisAlignment: crossAxisAlignment,
                          textDirection: textDirection,
                          verticalDirection: verticalDirection,
                          textBaseline: textBaseline,
                        );
                }
                

                然后打电话

                
                CustomColumn(children: [
                                    item1,
                                    item2,
                                    item3,
                                  ])
                

                【讨论】:

                  【解决方案18】:

                  你可以使用Padding包裹每个子widget,然后设置Padding的top或者bottom

                  如果你不想写很多相同的数字,你可以这样做:

                  Column(
                    children: [
                      child1, 
                      child2, 
                      ..., 
                      childN
                    ].map((e) => Padding(padding: EdgeInsets.only(top: 10), child: e)).toList()
                  );
                  

                  【讨论】:

                    猜你喜欢
                    • 2020-07-04
                    • 2021-10-25
                    • 2020-10-11
                    • 1970-01-01
                    • 1970-01-01
                    • 1970-01-01
                    • 2019-10-10
                    • 2019-04-08
                    • 2019-03-26
                    相关资源
                    最近更新 更多