Flutter 线性布局

线性布局 (Row、Column)

Row和Column, 即: 水平方向和垂直方向排列子组件;

构造方法

两个轴向:

  • mainAxis: 主轴, 即本组件主体的方向
  • crossAxis: 纵轴, 即垂直于主轴的方向

Row

主轴: 水平方向

1
2
3
4
5
6
7
8
9
10
const Row({
Key? key,
MainAxisAlignment mainAxisAlignment = MainAxisAlignment.start,
MainAxisSize mainAxisSize = MainAxisSize.max,
CrossAxisAlignment crossAxisAlignment = CrossAxisAlignment.center,
TextDirection? textDirection,
VerticalDirection verticalDirection = VerticalDirection.down,
TextBaseline? textBaseline, // NO DEFAULT: we don't know what the text's baseline should be
List<Widget> children = const <Widget>[],
})

Column

主轴: 垂直方向

1
2
3
4
5
6
7
8
9
10
const Column({
Key? key,
MainAxisAlignment mainAxisAlignment = MainAxisAlignment.start,
MainAxisSize mainAxisSize = MainAxisSize.max,
CrossAxisAlignment crossAxisAlignment = CrossAxisAlignment.center,
TextDirection? textDirection,
VerticalDirection verticalDirection = VerticalDirection.down,
TextBaseline? textBaseline,
List<Widget> children = const <Widget>[],
})

可以发现构造方法基本一样, 接下来看下具体参数的作用

参数大致含义

  • mainAxisAlignment: 表示子组件在主轴(Row为水平方向)的对齐方式, 参考系textDirection
    • .start: 表示沿textDirection阅读方向的初始方向对齐
    • .end: 和.start正好相反
    • .center: 表示居中对齐
    • .spaceBetween: 平均分控件之间 0:x:x:0
    • .spaceAround: 平均分周围 x:xx:xx:x
    • .spaceEvenly: 平均分所有间隙 x:x:x:x
  • mainAxisSize: 表示在主轴(Row为水平方向)的占用空间
    • .max: 表示尽可能多的占用水平方向的空间,此时无论子 widgets 实际占用多少水平空间,Row的宽度始终等于水平方向的最大宽度;
    • .min: 表示尽可能少的占用水平空间,当子组件没有占满水平剩余空间,则Row的实际宽度等于所有子组件占用的的水平空间;
  • crossAxisAlignment: 表示子组件在纵轴(Row为垂直方向)的对齐方式, 高度等于子组件高度中最大值, 参考系是verticalDirection
    • .start
    • .end
    • .center
    • .stretch
    • .baseline
  • textDirection: 表示主轴(Row为水平)的布局方向(阅读方向)
    • .ltr: 中文、英语
    • .rtl: 阿拉伯语、Hebrew
  • verticalDirection: 表示纵轴(Row为垂直)的布局方向
    • .up: 表示从底部到顶部, start在底部
    • .down: 表示从顶部到底部, start在顶部
  • textBaseline: 基线对齐
  • children: 子组件数组

demo

Row和Column都只会在主轴方向占用尽可能大的空间,而纵轴的长度则取决于子组件长度中最大的, 比如在Row的高度, Column的宽度等

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
Column(
// 排除纵轴的默认居中对齐的干扰
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Row(
// RTL.start
mainAxisAlignment: MainAxisAlignment.start,
textDirection: TextDirection.rtl,
children: const <Widget>[
Text(" RTL "),
Text(" 主轴.start "),
Text(" Hello "),
Text(" World "),
],
),
Row(
// LTR.start
mainAxisAlignment: MainAxisAlignment.start,
textDirection: TextDirection.ltr,
children: const <Widget>[
Text(" LTR "),
Text(" 主轴.start "),
Text(" Hello "),
Text(" World "),
],
),
Container(
color: Colors.green, // 设置一个颜色
child: Row(
// 宽度为最小值, 对齐无效果
mainAxisSize: MainAxisSize.min,
mainAxisAlignment: MainAxisAlignment.center,
children: const <Widget>[
Text(" AxisSize.min "),
Text(" 主轴.center "),
Text(" Hello "),
Text(" World "),
],
),
),
Container(
color: Colors.cyan, // 设置一个颜色
child: Row(
// 宽度为最大值, 对齐有效果
mainAxisSize: MainAxisSize.max,
mainAxisAlignment: MainAxisAlignment.center,
children: const <Widget>[
Text(" AxisSize.max "),
Text(" 主轴.center "),
Text(" Hello "),
Text(" World "),
],
),
),
Row(
// 纵轴 由下向上布局, 开头对齐
crossAxisAlignment: CrossAxisAlignment.start,
verticalDirection: VerticalDirection.up,
children: const <Widget>[
Text(" 纵轴.start "),
Text(" vertical.up "),
Text(" Hello ", style: TextStyle(fontSize: 30.0)),
Text(" World "),
],
),
Row(
// 纵轴 由上向下布局, 开头对齐
crossAxisAlignment: CrossAxisAlignment.start,
verticalDirection: VerticalDirection.down,
children: const <Widget>[
Text(" 纵轴.start "),
Text(" vertical.down "),
Text(" Hello ", style: TextStyle(fontSize: 30.0)),
Text(" World "),
],
),
Row(
// 纵轴 由上向下布局, 居中对齐
crossAxisAlignment: CrossAxisAlignment.center,
verticalDirection: VerticalDirection.down,
children: const <Widget>[
Text(" 纵轴.center "),
Text(" vertical.down "),
Text(" Hello ", style: TextStyle(fontSize: 30.0)),
Text(" World "),
],
),
],
);

效果

如果Row里面嵌套Row,或者Column里面再嵌套Column,那么只有最外面的Row或Column会占用尽可能大的空间,里面Row或Column所占用的空间为实际大小

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
Container(
color: Colors.blue,
child: Padding(
padding: const EdgeInsets.all(16.0),
child: Row(
mainAxisSize: MainAxisSize.max,
children: <Widget>[
Container(
color: Colors.orange,
child: Row(
mainAxisSize: MainAxisSize.max,
children: const <Widget>[
Text(" Hello "),
Text(" World "),
],
),
)
],
),
),
);

效果:

文章目录
  1. 1. 线性布局 (Row、Column)
    1. 1.0.1. 构造方法
      1. 1.0.1.1. Row
      2. 1.0.1.2. Column
    2. 1.0.2. 参数大致含义
    3. 1.0.3. demo