上一篇梳理了擁有單個子元素佈局的Widget,今天來梳理一下擁有多個子元素佈局的Widget。 Row Row組件常見屬性如下: mainAxisAlignment:主軸的排列方式 crossAxisAlignment:次軸的排列方式 mainAxisSize:... ...
如需轉載,請註明出處:Flutter學習筆記(23)--多個子元素的佈局Widget(Rwo、Column、Stack、IndexedStack、Table、Wrap)
上一篇梳理了擁有單個子元素佈局的Widget,今天來梳理一下擁有多個子元素佈局的Widget。
-
Row
Row組件常見屬性如下:
mainAxisAlignment:主軸的排列方式
crossAxisAlignment:次軸的排列方式
mainAxisSize:主軸應該占據多少空間,取值max為最大,min為最小
children:組件子元素,它的本質是一個List列表
對於Row來說,水平方向是主軸,垂直方向是次軸。
首先來看一下mainAxisAlignment屬性值都有哪些
enum MainAxisAlignment { start,//將子控制項放在主軸開始的位置 end,//將子控制項放在主軸結束的位置 center,//將子控制項放在主軸中間的位置 spaceBetween,//將主軸空白位置進行均分,排列子元素,首尾沒有空隙 spaceAround,//將主軸空白區域均分,使中間各個子控制項間距相等,首尾子控制項間距為中間子控制項間距的一半 spaceEvenly,//將主軸空白區域均分,使各個子空間間距相等 }
Demo示例:
import 'package:flutter/material.dart'; void main() => runApp(DemoApp()); class DemoApp extends StatelessWidget { @override Widget build(BuildContext context) { return new MaterialApp( title: 'Children Demo', home: new Scaffold( appBar: AppBar( title: new Text('Children Demo'), ), body: new Row( mainAxisAlignment: MainAxisAlignment.spaceAround, children: <Widget>[ new Text('11111111111'), new Text('22222222222'), new Text('33333333333') ], ), ), ); } }
-
Column
Column組件常見屬性如下:
mainAxisAlignment:主軸的排列方式
crossAxisAlignment:次軸的排列方式
mainAxisSize:主軸應該占據多少空間,取值max為最大,min為最小
children:組件子元素,它的本質是一個List列表
對Column來說,垂直方向是主軸,水平方向是次軸,使用上和Row大同小異
Demo示例:
import 'package:flutter/material.dart'; void main() => runApp(DemoApp()); class DemoApp extends StatelessWidget { @override Widget build(BuildContext context) { return new MaterialApp( title: 'Children Demo', home: new Scaffold( appBar: AppBar( title: new Text('Children Demo'), ), body: new Column( mainAxisAlignment: MainAxisAlignment.spaceAround, children: <Widget>[ new Text('11111111111'), new Text('22222222222'), new Text('33333333333') ], ), ), ); } }
-
Stack
Stack/alignment:
Stack組件的每一個子組件要麼定位,要麼不定位,定位的子組件是用Positioned組件包裹的,Stack組件本身包含所有不定位的子組件,子組件根據alignment屬性定位(預設為左上角)。然後根據定位的子組件的top、right、bottom、left屬性將他們放置在Stack組件上。
Stack既然是允許子元素堆疊的組件,那麼定位堆疊位置的屬性值有哪些呢?
alignment屬性值:bottomCenter 底部中間位置、bottomLeft 底部左側位置、bottomRight 底部右側位置、center 正中間位置、centerLeft 中間居左位置、centerRight 中間居右位置、topCenter 上部居中位置、topLeft 上部居左位置、topRight 上部居右位置
Demo示例:
import 'package:flutter/material.dart'; void main() => runApp(DemoApp()); class DemoApp extends StatelessWidget { @override Widget build(BuildContext context) { return new MaterialApp( title: 'Children Demo', home: new Scaffold( appBar: AppBar( title: new Text('Children Demo'), ), body: new Center( child: new Stack( alignment: Alignment.centerLeft, children: <Widget>[ new Container( width: 200.0, height: 200.0, color: Colors.blue, ), new Text('這是一段文本') ], ), ), ), ); } }
Stack/Positioned:
上面的示例是通過系統提供的定位來給子元素進行堆疊,但是實際工作中,上面的幾類屬性值往往不能滿足我們UI的需求,UI可能會要求子元素放在任何你想不到的位置,那麼這時候就需要用到我們Positioned來進行定位了。
Positioned屬性值:top 子元素相對頂部邊界距離,left 子元素相對左側邊界距離,right 子元素相對右側邊界距離,bottom 子元素相對底部邊界距離。
Demo示例:
import 'package:flutter/material.dart'; void main() => runApp(DemoApp()); class DemoApp extends StatelessWidget { @override Widget build(BuildContext context) { return new MaterialApp( title: 'Children Demo', home: new Scaffold( appBar: AppBar( title: new Text('Children Demo'), ), body: new Center( child: new Stack( children: <Widget>[ new Container( width: 200.0, height: 200.0, color: Colors.blue, ), new Positioned( top: 20.0, left: 50.0, child: new Text('這是一段文本') ) ], ), ), ), ); } }
-
IndexedStack
IndexedStack繼承自Stack,它的作用是顯示第index個child,其他的child都是不可見的,所以IndexedStack的尺寸永遠是和最大的子節點尺寸一致。由於IndexedStack是繼承自Stack,所以它只比Stack多了一個index屬性,即對應child的索引。
Demo示例:
import 'package:flutter/material.dart'; void main() => runApp(DemoApp()); class DemoApp extends StatelessWidget { @override Widget build(BuildContext context) { return new MaterialApp( title: 'Children Demo', home: new Scaffold( appBar: AppBar( title: new Text('Children Demo'), ), body: new Center( child: new IndexedStack( index: 1, children: <Widget>[ new Container( width: 200.0, height: 200.0, color: Colors.blue, ), new Positioned( top: 20.0, left: 50.0, child: new Text('這是一段文本') ) ], ), ), ), ); } }
-
Table
Table表格佈局,每一行的高度由其內容決定,每一列的寬度由columnWidths屬性單獨控制。
Table組件常見屬性如下:
columnWidths:設置每一列的寬度。
defaultColumnWidth:預設的每一列寬度,預設情況下均分。
textDirection:文字方向。
border:表格邊框。
defaultVerticalAlignment:預設垂直方向的對齊方式,top 放置在頂部、middle 垂直居中、bottom 放置在底部、baseline 文本baseline對齊、fill 充滿整個cell
import 'package:flutter/material.dart'; void main() => runApp(DemoApp()); class DemoApp extends StatelessWidget { @override Widget build(BuildContext context) { return new MaterialApp( title: 'Children Demo', home: new Scaffold( appBar: AppBar( title: new Text('Children Demo'), ), body: new Table( defaultVerticalAlignment: TableCellVerticalAlignment.bottom, // 設置表格有多少列,並且指定列寬 columnWidths:const <int,TableColumnWidth> { 0:FixedColumnWidth(40.0), 1:FixedColumnWidth(40.0), 2:FixedColumnWidth(60.0), 3:FixedColumnWidth(60.0), 4:FixedColumnWidth(130.0), }, // 設置表格邊框樣式 border: TableBorder.all( color: Colors.blue, width: 2.0, style: BorderStyle.solid ), children: const <TableRow>[ // 添加第一行數據 TableRow( children: <Widget>[ SizedBox( child: Text('姓名'), height: 30, ), Text('性別'), Text('年齡'), Text('身高'), Text('備註'), ], ), // 添加第二行數據 TableRow( children: <Widget>[ Text('張三'), Text('男'), Text('20'), Text('186'), Text('學渣'), ], ), // 添加第三行數據 TableRow( children: <Widget>[ Text('李四'), Text('男'), Text('20'), Text('188'), Text('學酥'), ], ), // 添加第四行數據 TableRow( children: <Widget>[ Text('王五'), Text('男'), Text('21'), Text('177'), Text('學霸'), ], ), // 添加第五行數據 TableRow( children: <Widget>[ Text('小梅'), Text('女'), Text('22'), Text('170'), Text('學神,需要重點培養'), ], ), ], ), ), ); } }
-
Wrap
import 'package:flutter/material.dart'; void main() => runApp(DemoApp()); class DemoApp extends StatelessWidget { @override Widget build(BuildContext context) { return new MaterialApp( title: 'Children Demo', home: new Scaffold( appBar: AppBar( title: new Text('Children Demo'), ), body: new Wrap( spacing: 3.0, runSpacing: 20.0,//縱軸方向的間距 alignment: WrapAlignment.end,//縱軸方向的對其方式 children: <Widget>[ new Chip( avatar: CircleAvatar( backgroundColor: Colors.blue, child: new Text('A'), ), label: new Text('文本一'), ), new Chip( avatar: CircleAvatar( backgroundColor: Colors.blue, child: new Text('B'), ), label: new Text('文本二'), ), new Chip( avatar: CircleAvatar( backgroundColor: Colors.blue, child: new Text('C'), ), label: new Text('文本三'), ), new Chip( avatar: CircleAvatar( backgroundColor: Colors.blue, child: new Text('D'), ), label: new Text('文本四'), ), new Chip( avatar: CircleAvatar( backgroundColor: Colors.blue, child: new Text('E'), ), label: new Text('文本五'), ), ], ), ), ); } }