
3.1 线性布局Column与Row
线性布局指的是页面布局中的控件摆放方式是以线性的方式摆放的,线性排列有纵向(或称为垂直方向)、横向(水平方向),如图3-1所示。

图3-1 线性布局说明图
在Flutter中,使用Row和Column组件来实现水平或垂直方向的布局,Row组件处理水平方向的布局,Column组件处理垂直方向的布局。
Row和Column都有两根轴,MainAxisAlignment(主轴)和CrossAxisAlignment(交叉轴),是相对而言的。对于Column组件来讲,其作用是将子Widget在垂直方向线性排列,所以它的主轴就是垂直方向,水平方向就是它的交叉轴。对于Row来讲,其主轴就是水平方向,交叉轴就是垂直方向。
使用Column组件将三个文本Text在垂直方向上线性排列,代码如下。


3-1 Column的基本使用效果图

使用Row组件将三个按钮在水平方向上线性排列,代码如下。


3-2 Row的基本使用效果图
3.1.1 Column与Row的宽与高自适应
在代码清单3-1与代码清单3-2使用的效果中,Scaffold的body没有对子Widget的宽高做限定,所以对于Column与Row,默认情况下在主轴方向是填充,在交叉轴上是包裹,如图3-2分析所示(Android Studio Flutter Inspector工具)。

图3-2 Column Row的填充分析效果图
许多应用场景期望在主轴方向也是包裹内容的,如图3-3所示,可通过配置属性mainAxisSize来进行修改,代码如下。


图3-3 Column Row主轴内容包裹分析效果图
如图3-4所示,当Column与Row的父布局有了宽高的限制后,Column与Row在主轴与交叉轴方向上都是填充父布局的,代码如下。

图3-4 Column Row填充父布局分析效果图


3.1.2 Column与Row中子Widget的对齐方式分析
对方式需要结合主轴与交叉轴来描述,默认情况下如图3-5所示,Column与Row在主轴方向都是将子Widget以开始的位置对齐,在交叉轴方向都是居中对齐。

图3-5 Column Row填充父布局分析效果图
可通过mainAxisAlignment属性来修改Column与Row的主轴方向的子Widget对齐方式,如代码清单3-4所示,是Column默认配置的对齐方式。


配置的Column中所有的子Widget中心对齐,代码如下。


3-3 Column中子widget居中对齐效果图
配置的Row中所有的子Widget中心对齐,代码如下。


3-4 Row中子Widget居中对齐效果图
主轴方向通过属性mainAxisAlignment来决定子Widgt的对齐方式,配置的是MainAxis Alignment枚举类型,它的取值如表3-1所示。
表3-1 MainAxisAlignment主轴alignment对齐方式

交叉轴方向通过属性crossAxisAlignment来决定子Widgt的对齐方式,配置的是CrossAxisAlignment枚举类型,它的取值如表3-2所示。
表3-2 CrossAxisAlignment交叉轴alignment对齐方式

Column与Row的属性textDirection是用来配置方向的,在中文环境下默认是从左向右,也就是取值为TextDirection.ltr,当配置为TextDirection.rtl时则为从右向左。所以在本书中讲述到的开始位置对齐,对于Column来讲与左对齐效果一至,对于Row来讲,与顶部对齐效果一致,其他的类比推理即可。
3.1.3 Column与Row中子Widget按比例权重布局
如图3-6所示,线性布局Row中两个按钮水平排列,默认按钮是包裹子文本的大小,结合Expanded组件使用后,第二个Button填充了水平方向剩余的所有的空白区域,代码如下。



图3-6 Row中子Widget填充剩余空间效果图
如图3-7所示,线性布局Column中两个按钮水平排列,默认按钮是包裹子文本的大小,结合Expanded组件使用后,第二个Button填充了垂直方向剩余的所有空白区域,代码如下。

图3-7 Column中子Widget填充剩余空间效果图


如果想要Column三个子Widget的高度相等,并且平均分配Column的空间,可结合Expanded组件来实现这种效果,代码如下。


3-5 Column中子的Widget等比例效果图
此处通过Expanded中配置的flex值,来决定子当前Expanded的子Widget占用的height,如在此处的三个区域内容中,Expanded分别配置flex为1,也就是会将当前Column的高度height平均分配成3份,然后每个子Widget占用一份,也就达到了等比分布的需求。同理应用在Row中,处理的比例分布就是水平方向。