diff --git a/zh-cn/application-dev/ui/figures/direction.png b/zh-cn/application-dev/ui/figures/direction.png new file mode 100644 index 0000000000000000000000000000000000000000..702c9b07fa00b8685415bb83879ead774001ee56 Binary files /dev/null and b/zh-cn/application-dev/ui/figures/direction.png differ diff --git a/zh-cn/application-dev/ui/figures/flex.png b/zh-cn/application-dev/ui/figures/flex.png new file mode 100644 index 0000000000000000000000000000000000000000..848ceef3873ed6f83466d9ab42f6aa68cb341fe9 Binary files /dev/null and b/zh-cn/application-dev/ui/figures/flex.png differ diff --git a/zh-cn/application-dev/ui/figures/justifyContent.png b/zh-cn/application-dev/ui/figures/justifyContent.png new file mode 100644 index 0000000000000000000000000000000000000000..2e997f9cba6ce5c2ad93c1f2e33728b7db17bdd3 Binary files /dev/null and b/zh-cn/application-dev/ui/figures/justifyContent.png differ diff --git a/zh-cn/application-dev/ui/ui-ts-layout-flex.md b/zh-cn/application-dev/ui/ui-ts-layout-flex.md index 3119d2392aff37157176c3d0f0bede914ac75d30..92783b661f0c1afc6d07afb15793251ab4a1f70c 100644 --- a/zh-cn/application-dev/ui/ui-ts-layout-flex.md +++ b/zh-cn/application-dev/ui/ui-ts-layout-flex.md @@ -1,408 +1,340 @@ # 弹性布局 -弹性布局(Flex布局)是自适应布局中使用最为灵活的布局。弹性布局提供一种更加有效的方式来对容器中的子组件进行排列、对齐和分配空白空间。 -开发者可以通过Flex的接口创建容器组件,进而对容器内的其他元素进行弹性布局。 +弹性布局(Flex布局)是自适应布局中使用最为灵活的布局。弹性布局提供一种更加有效的方式来对容器中的子组件进行排列、对齐和分配空白空间。弹性布局 -- 容器 -- 子组件 -- 主轴 -- 交叉轴 -## 创建弹性布局 +- 容器: [Flex组件](../reference/arkui-ts/ts-container-flex.md)作为Flex布局的容器,用于设置布局相关属性。 +- 子组件: Flex组件内的子组件自动成为布局的子组件。 +- 主轴: 水平方向的轴线,子组件默认沿着主轴排列。主轴开始的位置称为主轴起始端,结束位置称为主轴终点端。 +- 交叉轴: 垂直方向的轴线。交叉始的位置称为主轴首部,结束位置称为交叉轴尾部。 - `Flex(options?: { direction?: FlexDirection, wrap?: FlexWrap, justifyContent?: FlexAlign, alignItems?: ItemAlign, alignContent?: FlexAlign })` + ![](figures/flex.png) -通过参数direction定义弹性布局的布局方向,justifyContent定义子组件在弹性布局方向上的对齐方式, alignContent定义子组件在与布局方向垂直的方向上的对齐方式,wrap定义内容超过一行时是否换行。 +## 容器组件属性 -## 弹性布局方向 +通过Flex组件提供的Flex接口创建弹性布局。如下: -弹性布局的方向分为水平方向和垂直方向。子组件排列的方向是主轴,与主轴垂直的方向是交叉轴。通过direction参数设置容器主轴的方向,可选值有: +`Flex(options?: { direction?: FlexDirection, wrap?: FlexWrap, justifyContent?: FlexAlign, alignItems?: ItemAlign, alignContent?: FlexAlign })` -* FlexDirection. Row(默认值):主轴为水平方向,子组件从起始端沿着水平方向开始排布。 - - -```ts - Flex({ direction: FlexDirection.Row }) { - Text('1').width('33%').height(50).backgroundColor(0xF5DEB3) - Text('2').width('33%').height(50).backgroundColor(0xD2B48C) - Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) - } - .height(70) - .width('90%') - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - - -![zh-cn_image_0000001218579606](figures/zh-cn_image_0000001218579606.png) +### 弹性布局方向 +参数direction决定主轴的方向,即子组件的排列方向。可选值有: -* FlexDirection. RowReverse:主轴为水平方向,子组件从终点端沿着FlexDirection. Row相反的方向开始排布。 +![](figures/direction.png) - +- FlexDirection.Row(默认值):主轴为水平方向,子组件从起始端沿着水平方向开始排布。 -```ts - Flex({ direction: FlexDirection.RowReverse }) { + ```ts + Flex({ direction: FlexDirection.Row }) { Text('1').width('33%').height(50).backgroundColor(0xF5DEB3) Text('2').width('33%').height(50).backgroundColor(0xD2B48C) Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) - } - .height(70) - .width('90%') - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001218739566](figures/zh-cn_image_0000001218739566.png) + } + .height(70) + .width('90%') + .padding(10) + .backgroundColor(0xAFEEEE) + ``` + ![zh-cn_image_0000001218579606](figures/zh-cn_image_0000001218579606.png) + +- FlexDirection.RowReverse:主轴为水平方向,子组件从终点端沿着FlexDirection. Row相反的方向开始排布。 + + ```ts + Flex({ direction: FlexDirection.RowReverse }) { + Text('1').width('33%').height(50).backgroundColor(0xF5DEB3) + Text('2').width('33%').height(50).backgroundColor(0xD2B48C) + Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) + } + .height(70) + .width('90%') + .padding(10) + .backgroundColor(0xAFEEEE) + ``` -* FlexDirection. Column:主轴为垂直方向,子组件从起始端沿着垂直方向开始排布。 + ![zh-cn_image_0000001218739566](figures/zh-cn_image_0000001218739566.png) - +- FlexDirection.Column:主轴为垂直方向,子组件从起始端沿着垂直方向开始排布。 -```ts - Flex({ direction: FlexDirection.Column }) { + ```ts + Flex({ direction: FlexDirection.Column }) { Text('1').width('100%').height(50).backgroundColor(0xF5DEB3) Text('2').width('100%').height(50).backgroundColor(0xD2B48C) Text('3').width('100%').height(50).backgroundColor(0xF5DEB3) - } - .height(70) - .width('90%') - .padding(10) - .backgroundColor(0xAFEEEE) - ``` + } + .height(70) + .width('90%') + .padding(10) + .backgroundColor(0xAFEEEE) + ``` - - -![zh-cn_image_0000001263019457](figures/zh-cn_image_0000001263019457.png) + ![zh-cn_image_0000001263019457](figures/zh-cn_image_0000001263019457.png) -* FlexDirection. ColumnReverse:主轴为垂直方向,子组件从终点端沿着FlexDirection. Column相反的方向开始排布。 +- FlexDirection.ColumnReverse:主轴为垂直方向,子组件从终点端沿着FlexDirection. Column相反的方向开始排布。 - - -```ts - Flex({ direction: FlexDirection.ColumnReverse }) { + ```ts + Flex({ direction: FlexDirection.ColumnReverse }) { Text('1').width('100%').height(50).backgroundColor(0xF5DEB3) Text('2').width('100%').height(50).backgroundColor(0xD2B48C) Text('3').width('100%').height(50).backgroundColor(0xF5DEB3) - } - .height(70) - .width('90%') - .padding(10) - .backgroundColor(0xAFEEEE) - ``` + } + .height(70) + .width('90%') + .padding(10) + .backgroundColor(0xAFEEEE) + ``` - - -![zh-cn_image_0000001263339459](figures/zh-cn_image_0000001263339459.png) - -## 弹性布局换行 + ![zh-cn_image_0000001263339459](figures/zh-cn_image_0000001263339459.png) -默认情况下,子组件在Flex容器中都排在一条线(又称"轴线")上。通过wrap参数设置其他换行方式,可选值有: +### 弹性布局换行 -* FlexWrap. NoWrap(默认值): 不换行。如果子组件的宽度总和大于父元素的宽度,则子组件会被压缩宽度。 +默认情况下,子组件在Flex容器中都排在一条线(又称"轴线")上。通过wrap参数设置子组件换行方式。可选值有: - +- FlexWrap. NoWrap(默认值): 不换行。如果子组件的宽度总和大于父元素的宽度,则子组件会被压缩宽度。 -```ts - Flex({ wrap: FlexWrap.NoWrap }) { + ```ts + Flex({ wrap: FlexWrap.NoWrap }) { Text('1').width('50%').height(50).backgroundColor(0xF5DEB3) Text('2').width('50%').height(50).backgroundColor(0xD2B48C) Text('3').width('50%').height(50).backgroundColor(0xF5DEB3) - } - .width('90%') - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001263139409](figures/zh-cn_image_0000001263139409.png) - -* FlexWrap. Wrap:换行,每一行子组件按照主轴方向排列。 - - - -```ts - Flex({ wrap: FlexWrap.Wrap }) { + } + .width('90%') + .padding(10) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001263139409](figures/zh-cn_image_0000001263139409.png) + +- FlexWrap. Wrap:换行,每一行子组件按照主轴方向排列。 + + ```ts + Flex({ wrap: FlexWrap.Wrap }) { Text('1').width('50%').height(50).backgroundColor(0xF5DEB3) Text('2').width('50%').height(50).backgroundColor(0xD2B48C) Text('3').width('50%').height(50).backgroundColor(0xD2B48C) - } - .width('90%') - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001218419614](figures/zh-cn_image_0000001218419614.png) - -* FlexWrap. WrapReverse:换行,每一行子组件按照主轴反方向排列。 - - - -```ts - Flex({ wrap: FlexWrap.WrapReverse}) { + } + .width('90%') + .padding(10) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001218419614](figures/zh-cn_image_0000001218419614.png) + +- FlexWrap. WrapReverse:换行,每一行子组件按照主轴反方向排列。 + + ```ts + Flex({ wrap: FlexWrap.WrapReverse}) { Text('1').width('50%').height(50).backgroundColor(0xF5DEB3) Text('2').width('50%').height(50).backgroundColor(0xD2B48C) Text('3').width('50%').height(50).backgroundColor(0xF5DEB3) - } - .width('90%') - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001263259399](figures/zh-cn_image_0000001263259399.png) + } + .width('90%') + .padding(10) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001263259399](figures/zh-cn_image_0000001263259399.png) -## 弹性布局对齐方式 +### 弹性布局对齐方式 -### 主轴对齐 +#### 主轴对齐 -可以通过justifyContent参数设置在主轴的对齐方式,可选值有: +通过justifyContent参数设置在主轴方向的对齐方式,存在下面六种情况: -* FlexAlign. Start(默认值): 子组件在主轴方向首端对齐, 第一个子组件与父元素边沿对齐,其他元素与前一个元素对齐。 +![](figures/justifyContent.png) - +- FlexAlign.Start(默认值): 子组件在主轴方向起始端对齐, 第一个子组件与父元素边沿对齐,其他元素与前一个元素对齐。 -```ts - Flex({ justifyContent: FlexAlign.Start }) { - Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) + ```ts + Flex({ justifyContent: FlexAlign.Start }) { + Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) + Text('2').width('20%').height(50).backgroundColor(0xD2B48C) Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) - } - .width('90%') - .padding({ top: 10, bottom: 10 }) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001218259634](figures/mainStart.png) - -* FlexAlign. Center: 子组件在主轴方向居中对齐。 - - - -```ts - Flex({ justifyContent: FlexAlign.Center }) { + } + .width('90%') + .padding({ top: 10, bottom: 10 }) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001218259634](figures/mainStart.png) + +- FlexAlign.Center: 子组件在主轴方向居中对齐。 + + ```ts + Flex({ justifyContent: FlexAlign.Center }) { Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) Text('2').width('20%').height(50).backgroundColor(0xD2B48C) Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) - } - .width('90%') - .padding({ top: 10, bottom: 10 }) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001218579608](figures/mainCenter.png) - -* FlexAlign. End: 子组件在主轴方向尾部对齐, 最后一个子组件与父元素边沿对齐,其他元素与后一个元素对齐。 - - - -```ts - Flex({ justifyContent: FlexAlign.End }) { + } + .width('90%') + .padding({ top: 10, bottom: 10 }) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001218579608](figures/mainCenter.png) + +- FlexAlign.End: 子组件在主轴方向终点端对齐, 最后一个子组件与父元素边沿对齐,其他元素与后一个元素对齐。 + + ```ts + Flex({ justifyContent: FlexAlign.End }) { Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) Text('2').width('20%').height(50).backgroundColor(0xD2B48C) Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) - } - .width('90%') - .padding({ top: 10, bottom: 10 }) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001218739568](figures/mainEnd.png) - -* FlexAlign. SpaceBetween: Flex主轴方向均匀分配弹性元素,相邻子组件之间距离相同。第一个子组件和最后一个子组件与父元素边沿对齐。 - - - -```ts - Flex({ justifyContent: FlexAlign.SpaceBetween }) { + } + .width('90%') + .padding({ top: 10, bottom: 10 }) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001218739568](figures/mainEnd.png) + +- FlexAlign.SpaceBetween: Flex主轴方向均匀分配弹性元素,相邻子组件之间距离相同。第一个子组件和最后一个子组件与父元素边沿对齐。 + + ```ts + Flex({ justifyContent: FlexAlign.SpaceBetween }) { Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) Text('2').width('20%').height(50).backgroundColor(0xD2B48C) Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) - } - .width('90%') - .padding({ top: 10, bottom: 10 }) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001263019461](figures/mainSpacebetween.png) - -* FlexAlign. SpaceAround: Flex主轴方向均匀分配弹性元素,相邻子组件之间距离相同。 第一个子组件到行首的距离和最后一个子组件到行尾的距离是相邻元素之间距离的一半。 - - - -```ts - Flex({ justifyContent: FlexAlign.SpaceAround }) { + } + .width('90%') + .padding({ top: 10, bottom: 10 }) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001263019461](figures/mainSpacebetween.png) + +- FlexAlign.SpaceAround: Flex主轴方向均匀分配弹性元素,相邻子组件之间距离相同。第一个子组件到主轴起始端的距离和最后一个子组件到主轴终点端的距离是相邻元素之间距离的一半。 + + ```ts + Flex({ justifyContent: FlexAlign.SpaceAround }) { Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) Text('2').width('20%').height(50).backgroundColor(0xD2B48C) Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) - } - .width('90%') - .padding({ top: 10, bottom: 10 }) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001263339461](figures/mainSpacearound.png) - -* FlexAlign. SpaceEvenly: Flex主轴方向元素等间距布局,相邻子组件之间的间距、第一个子组件与行首的间距、最后一个子组件到行尾的间距均相等。 - - - -```ts - Flex({ justifyContent: FlexAlign.SpaceEvenly }) { + } + .width('90%') + .padding({ top: 10, bottom: 10 }) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001263339461](figures/mainSpacearound.png) + +- FlexAlign.SpaceEvenly: Flex主轴方向元素等间距布局,相邻子组件之间的间距、第一个子组件与主轴起始端的间距、最后一个子组件到主轴终点端的间距均相等。 + + ```ts + Flex({ justifyContent: FlexAlign.SpaceEvenly }) { Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) Text('2').width('20%').height(50).backgroundColor(0xD2B48C) Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) - } - .width('90%') - .padding({ top: 10, bottom: 10 }) - .backgroundColor(0xAFEEEE) - ``` + } + .width('90%') + .padding({ top: 10, bottom: 10 }) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001263139411](figures/mainSpaceevenly.png) - - -![zh-cn_image_0000001263139411](figures/mainSpaceevenly.png) - -### 交叉轴对齐 +#### 交叉轴对齐 -#### 容器组件设置交叉轴对齐 -可以通过flex组件的alignItems参数设置子组件在交叉轴的对齐方式,可选值有: +容器和子组件都可以设置交叉轴对齐方式,且子组件设置的对齐方式优先级较高。 -* ItemAlign. Auto: 使用Flex容器中默认配置。 +##### 容器组件设置交叉轴对齐 +可以通过Flex组件的alignItems参数设置子组件在交叉轴的对齐方式,可选值有: - +- ItemAlign.Auto: 使用Flex容器中默认配置。 -```ts - Flex({ alignItems: ItemAlign.Auto }) { + ```ts + Flex({ alignItems: ItemAlign.Auto }) { Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) Text('2').width('33%').height(40).backgroundColor(0xD2B48C) Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) - } - .size({width: '90%', height: 80}) - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001218419616](figures/zh-cn_image_0000001218419616.png) + } + .size({width: '90%', height: 80}) + .padding(10) + .backgroundColor(0xAFEEEE) + ``` -* ItemAlign. Start: 交叉轴方向首部对齐。 + ![zh-cn_image_0000001218419616](figures/zh-cn_image_0000001218419616.png) - +- ItemAlign.Start: 交叉轴方向首部对齐。 -```ts - Flex({ alignItems: ItemAlign.Start }) { + ```ts + Flex({ alignItems: ItemAlign.Start }) { Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) Text('2').width('33%').height(40).backgroundColor(0xD2B48C) Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) - } - .size({width: '90%', height: 80}) - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001263259401](figures/zh-cn_image_0000001263259401.png) - -* ItemAlign. Center: 交叉轴方向居中对齐。 - - - -```ts - Flex({ alignItems: ItemAlign.Center }) { + } + .size({width: '90%', height: 80}) + .padding(10) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001263259401](figures/zh-cn_image_0000001263259401.png) + +- ItemAlign.Center: 交叉轴方向居中对齐。 + + ```ts + Flex({ alignItems: ItemAlign.Center }) { Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) Text('2').width('33%').height(40).backgroundColor(0xD2B48C) Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) - } - .size({width: '90%', height: 80}) - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001218259636](figures/zh-cn_image_0000001218259636.png) - -* ItemAlign. End:交叉轴方向底部对齐。 - - - -```ts - Flex({ alignItems: ItemAlign.End }) { + } + .size({width: '90%', height: 80}) + .padding(10) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001218259636](figures/zh-cn_image_0000001218259636.png) + +- ItemAlign.End:交叉轴方向底部对齐。 + + ```ts + Flex({ alignItems: ItemAlign.End }) { Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) Text('2').width('33%').height(40).backgroundColor(0xD2B48C) Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) - } - .size({width: '90%', height: 80}) - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - + } + .size({width: '90%', height: 80}) + .padding(10) + .backgroundColor(0xAFEEEE) + ``` + ![zh-cn_image_0000001218579610](figures/zh-cn_image_0000001218579610.png) -![zh-cn_image_0000001218579610](figures/zh-cn_image_0000001218579610.png) - -* ItemAlign. Stretch:交叉轴方向拉伸填充,在未设置尺寸时,拉伸到容器尺寸。 +- ItemAlign.Stretch:交叉轴方向拉伸填充,在未设置尺寸时,拉伸到容器尺寸。 - - -```ts - Flex({ alignItems: ItemAlign.Stretch }) { + ```ts + Flex({ alignItems: ItemAlign.Stretch }) { Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) Text('2').width('33%').height(40).backgroundColor(0xD2B48C) Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) - } - .size({width: '90%', height: 80}) - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001218739570](figures/zh-cn_image_0000001218739570.png) - -* ItemAlign. Baseline:交叉轴方向文本基线对齐。 - - - -```ts - Flex({ alignItems: ItemAlign.Baseline }) { + } + .size({width: '90%', height: 80}) + .padding(10) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001218739570](figures/zh-cn_image_0000001218739570.png) + +- ItemAlign. Baseline:交叉轴方向文本基线对齐。 + + ```ts + Flex({ alignItems: ItemAlign.Baseline }) { Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) Text('2').width('33%').height(40).backgroundColor(0xD2B48C) Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) - } - .size({width: '90%', height: 80}) - .padding(10) - .backgroundColor(0xAFEEEE) - ``` - - - -![zh-cn_image_0000001263019463](figures/zh-cn_image_0000001263019463.png) - -#### 子组件设置交叉轴对齐 - + } + .size({width: '90%', height: 80}) + .padding(10) + .backgroundColor(0xAFEEEE) + ``` + + ![zh-cn_image_0000001263019463](figures/zh-cn_image_0000001263019463.png) + +##### 子组件设置交叉轴对齐 子组件的alignSelf属性也可以设置子组件在父容器交叉轴的对齐格式,且会覆盖Flex布局容器中alignItems默认配置。如下例所示: ```ts -Flex({ direction: FlexDirection.Row, alignItems: ItemAlign.Center }) { +Flex({ direction: FlexDirection.Row, alignItems: ItemAlign.Center }) { //容器组件设置子组件居中 Text('alignSelf Start').width('25%').height(80) .alignSelf(ItemAlign.Start) .backgroundColor(0xF5DEB3) @@ -426,141 +358,113 @@ Flex({ direction: FlexDirection.Row, alignItems: ItemAlign.Center }) { 上例中,Flex容器中alignItems设置交叉轴子组件的对齐方式为居中,子组件自身设置了alignSelf属性的情况,覆盖父组件的alignItem值,表现为alignSelf的定义。 -### 内容对齐 +#### 内容对齐 可以通过alignContent参数设置子组件各行在交叉轴剩余空间内的对齐方式,只在多行的flex布局中生效,可选值有: -* FlexAlign. Start: 子组件各行与交叉轴起点对齐。 - - - -``` +- FlexAlign.Start: 子组件各行与交叉轴起点对齐。 - Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.Start }) { + ``` + Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.Start }) { Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) Text('2').width('60%').height(20).backgroundColor(0xD2B48C) Text('3').width('40%').height(20).backgroundColor(0xD2B48C) Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) Text('5').width('20%').height(20).backgroundColor(0xD2B48C) - } - .width('90%') - .height(100) - .backgroundColor(0xAFEEEE) - ``` - - - - -![crossStart.png](figures/crossStart.png) - -* FlexAlign. Center: 子组件各行在交叉轴方向居中对齐。 + } + .width('90%') + .height(100) + .backgroundColor(0xAFEEEE) + ``` + + ![crossStart.png](figures/crossStart.png) - +- FlexAlign.Center: 子组件各行在交叉轴方向居中对齐。 -```ts - Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.Center }) { + ```ts + Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.Center }) { Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) Text('2').width('60%').height(20).backgroundColor(0xD2B48C) Text('3').width('40%').height(20).backgroundColor(0xD2B48C) Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) Text('5').width('20%').height(20).backgroundColor(0xD2B48C) - } - .width('90%') - .height(100) - .backgroundColor(0xAFEEEE) - ``` - - - -![crossCenter.png](figures/crossCenter.png) - -* FlexAlign. End: 子组件各行与交叉轴终点对齐。 + } + .width('90%') + .height(100) + .backgroundColor(0xAFEEEE) + ``` + + ![crossCenter.png](figures/crossCenter.png) - +- FlexAlign.End: 子组件各行与交叉轴终点对齐。 -```ts - Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.End }) { + ```ts + Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.End }) { Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) Text('2').width('60%').height(20).backgroundColor(0xD2B48C) Text('3').width('40%').height(20).backgroundColor(0xD2B48C) Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) Text('5').width('20%').height(20).backgroundColor(0xD2B48C) - } - .width('90%') - .height(100) - .backgroundColor(0xAFEEEE) - ``` - - - -![crossEnd.png](figures/crossEnd.png) + } + .width('90%') + .height(100) + .backgroundColor(0xAFEEEE) + ``` + + ![crossEnd.png](figures/crossEnd.png) -* FlexAlign. SpaceBetween: 子组件各行与交叉轴两端对齐,各行间垂直间距平均分布。 +- FlexAlign.SpaceBetween: 子组件各行与交叉轴两端对齐,各行间垂直间距平均分布。 - - -```ts - Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.SpaceBetween }) { + ```ts + Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.SpaceBetween }) { Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) Text('2').width('60%').height(20).backgroundColor(0xD2B48C) Text('3').width('40%').height(20).backgroundColor(0xD2B48C) Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) Text('5').width('20%').height(20).backgroundColor(0xD2B48C) - } - .width('90%') - .height(100) - .backgroundColor(0xAFEEEE) - ``` - - - -![crossSpacebetween.png](figures/crossSpacebetween.png) - -* FlexAlign. SpaceAround: 子组件各行间距相等,是元素首尾行与交叉轴两端距离的两倍。 + } + .width('90%') + .height(100) + .backgroundColor(0xAFEEEE) + ``` + + ![crossSpacebetween.png](figures/crossSpacebetween.png) - +- FlexAlign.SpaceAround: 子组件各行间距相等,是元素首尾行与交叉轴两端距离的两倍。 -```ts - Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.SpaceAround }) { + ```ts + Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.SpaceAround }) { Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) Text('2').width('60%').height(20).backgroundColor(0xD2B48C) Text('3').width('40%').height(20).backgroundColor(0xD2B48C) Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) Text('5').width('20%').height(20).backgroundColor(0xD2B48C) - } - .width('90%') - .height(100) - .backgroundColor(0xAFEEEE) - ``` - - - - -![crossSpacearound.png](figures/crossSpacearound.png) - -* FlexAlign. SpaceEvenly: 子组件各行间距,子组件首尾行与交叉轴两端距离都相等。 + } + .width('90%') + .height(100) + .backgroundColor(0xAFEEEE) + ``` + + ![crossSpacearound.png](figures/crossSpacearound.png) - +- FlexAlign.SpaceEvenly: 子组件各行间距,子组件首尾行与交叉轴两端距离都相等。 -```ts - Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.SpaceAround }) { + ```ts + Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.SpaceAround }) { Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) Text('2').width('60%').height(20).backgroundColor(0xD2B48C) Text('3').width('40%').height(20).backgroundColor(0xD2B48C) Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) Text('5').width('20%').height(20).backgroundColor(0xD2B48C) - } - .width('90%') - .height(100) - .backgroundColor(0xAFEEEE) - ``` - - - - -![crossSpaceevenly.png](figures/crossSpaceevenly.png) + } + .width('90%') + .height(100) + .backgroundColor(0xAFEEEE) + ``` + + ![crossSpaceevenly.png](figures/crossSpaceevenly.png) -## 弹性布局的自适应拉伸 +### 弹性布局的自适应拉伸 在弹性布局父组件尺寸不够大的时候,通过子组件的下面几个属性设置其再父容器的占比,达到自适应布局能力。 1. flexBasis: 设置子组件在父容器主轴方向上的基准尺寸。如果设置了该值,则子项占用的空间为设置的值;如果没设置或者为auto,那子项的空间为width/height的值。 diff --git a/zh-cn/application-dev/ui/ui-ts-layout-linear.md b/zh-cn/application-dev/ui/ui-ts-layout-linear.md index ec8132c0e3fe5b2b78017321b08a8bfa52f9da8d..0e89b56ad71bb008cae24b6b3151ea7464cd7862 100644 --- a/zh-cn/application-dev/ui/ui-ts-layout-linear.md +++ b/zh-cn/application-dev/ui/ui-ts-layout-linear.md @@ -46,96 +46,94 @@ struct BlankExample { 自适应缩放是指在各种不同大小设备中,子组件按照预设的比例,尺寸随容器尺寸的变化而变化。在线性布局中有下列方法实现: 1. 父容器尺寸确定时,设置了layoutWeight属性的子组件与兄弟元素占主轴尺寸按照权重进行分配,忽略元素本身尺寸设置,在任意尺寸设备下,自适应占满剩余空间。 - - ```ts - @Entry - @Component - struct layoutWeightExample { - build() { - Column() { - Text('1:2:3').width('100%') - Row() { - Column() { - Text('layoutWeight(1)') - .textAlign(TextAlign.Center) - }.layoutWeight(2).backgroundColor(0xffd306).height('100%') - - Column() { - Text('layoutWeight(2)') - .textAlign(TextAlign.Center) - }.layoutWeight(4).backgroundColor(0xffed97).height('100%') - - Column() { - Text('layoutWeight(6)') - .textAlign(TextAlign.Center) - }.layoutWeight(6).backgroundColor(0xffd306).height('100%') - - }.backgroundColor(0xffd306).height('30%') - - Text('2:5:3').width('100%') - Row() { - Column() { - Text('layoutWeight(2)') - .textAlign(TextAlign.Center) - }.layoutWeight(2).backgroundColor(0xffd306).height('100%') - - Column() { - Text('layoutWeight(5)') - .textAlign(TextAlign.Center) - }.layoutWeight(5).backgroundColor(0xffed97).height('100%') - - Column() { - Text('layoutWeight(3)') - .textAlign(TextAlign.Center) - }.layoutWeight(3).backgroundColor(0xffd306).height('100%') - }.backgroundColor(0xffd306).height('30%') + ```ts + @Entry + @Component + struct layoutWeightExample { + build() { + Column() { + Text('1:2:3').width('100%') + Row() { + Column() { + Text('layoutWeight(1)') + .textAlign(TextAlign.Center) + }.layoutWeight(2).backgroundColor(0xffd306).height('100%') + + Column() { + Text('layoutWeight(2)') + .textAlign(TextAlign.Center) + }.layoutWeight(4).backgroundColor(0xffed97).height('100%') + + Column() { + Text('layoutWeight(6)') + .textAlign(TextAlign.Center) + }.layoutWeight(6).backgroundColor(0xffd306).height('100%') + + }.backgroundColor(0xffd306).height('30%') + + Text('2:5:3').width('100%') + Row() { + Column() { + Text('layoutWeight(2)') + .textAlign(TextAlign.Center) + }.layoutWeight(2).backgroundColor(0xffd306).height('100%') + + Column() { + Text('layoutWeight(5)') + .textAlign(TextAlign.Center) + }.layoutWeight(5).backgroundColor(0xffed97).height('100%') + + Column() { + Text('layoutWeight(3)') + .textAlign(TextAlign.Center) + }.layoutWeight(3).backgroundColor(0xffd306).height('100%') + }.backgroundColor(0xffd306).height('30%') + } } } - } - ``` + ``` - ![](figures/layoutWeight.gif) + ![](figures/layoutWeight.gif) -2. 父容器尺寸确定时,使用百分比设置子组件以及兄弟组件的width宽度,可以保证各自元素在任意尺寸下的自适应占比。 - - ```ts - @Entry - @Component - struct WidthExample { - build() { - Column() { - Row() { - Column() { - Text('left width 20%') - .textAlign(TextAlign.Center) - }.width('20%').backgroundColor(0xffd306).height('100%') - - Column() { - Text('center width 50%') - .textAlign(TextAlign.Center) - }.width('50%').backgroundColor(0xffed97).height('100%') - - Column() { - Text('right width 30%') - .textAlign(TextAlign.Center) - }.width('30%').backgroundColor(0xffd306).height('100%') - }.backgroundColor(0xffd306).height('30%') +3. 父容器尺寸确定时,使用百分比设置子组件以及兄弟组件的width宽度,可以保证各自元素在任意尺寸下的自适应占比。 + + ```ts + @Entry + @Component + struct WidthExample { + build() { + Column() { + Row() { + Column() { + Text('left width 20%') + .textAlign(TextAlign.Center) + }.width('20%').backgroundColor(0xffd306).height('100%') + + Column() { + Text('center width 50%') + .textAlign(TextAlign.Center) + }.width('50%').backgroundColor(0xffed97).height('100%') + + Column() { + Text('right width 30%') + .textAlign(TextAlign.Center) + }.width('30%').backgroundColor(0xffd306).height('100%') + }.backgroundColor(0xffd306).height('30%') + } } } - } - ``` + ``` - ![](figures/width.gif) + ![](figures/width.gif) -上例中,在任意大小的设备中,子组件的宽度占比固定。 + 上例中,在任意大小的设备中,子组件的宽度占比固定。 ## 定位能力 -* 相对定位 +- 相对定位 使用组件的[offset属性](../reference/arkui-ts/ts-universal-attributes-location.md)可以实现相对定位,设置元素相对于自身的偏移量。设置该属性,不影响父容器布局,仅在绘制时进行位置调整。使用线性布局和offset可以实现大部分布局的开发。 - ```ts @Entry @@ -171,10 +169,10 @@ struct BlankExample { ![](figures/offset.gif) -* 绝对定位 + +- 绝对定位 线性布局中可以使用组件的[positon属性](../reference/arkui-ts/ts-universal-attributes-location.md)实现绝对布局(AbsoluteLayout),设置元素左上角相对于父容器左上角偏移位置。对于不同尺寸的设备,使用绝对定位的适应性会比较差,在屏幕的适配上有缺陷。 - ```ts @Entry @@ -219,86 +217,90 @@ struct BlankExample { 自适应延伸是在不同尺寸设备下,当页面显示内容个数不一并延伸到屏幕外时,可通过滚动条拖动展示。适用于线性布局中内容无法一屏展示的场景。常见以下两类实现方法。 -* List组件 +- List组件 List子项过多一屏放不下时,未展示的子项通过滚动条拖动显示。通过scrollBar属性设置滚动条的常驻状态,edgeEffect属性设置拖动到极限的回弹效果。 - -```ts - @Entry - @Component - struct ListExample1 { - @State arr: string[] = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "10", "11", "12", "13", "14", "15"] - @State alignListItem: ListItemAlign = ListItemAlign.Start - - build() { - Column() { - List({ space: 20, initialIndex: 0 }) { - ForEach(this.arr, (item) => { - ListItem() { - Text('' + item) - .width('100%') - .height(100) - .fontSize(16) - .textAlign(TextAlign.Center) - .borderRadius(10) - .backgroundColor(0xFFFFFF) - } - .border({ width: 2, color: Color.Green }) - }, item => item) - } - .border({ width: 2, color: Color.Red, style: BorderStyle.Dashed }) - .scrollBar(BarState.On) // 滚动条常驻 - .edgeEffect(EdgeEffect.Spring) // 滚动到边缘再拖动回弹效果 - - }.width('100%').height('100%').backgroundColor(0xDCDCDC).padding(20) + + 纵向List: + ```ts + @Entry + @Component + struct ListExample1 { + @State arr: string[] = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "10", "11", "12", "13", "14", "15"] + @State alignListItem: ListItemAlign = ListItemAlign.Start + + build() { + Column() { + List({ space: 20, initialIndex: 0 }) { + ForEach(this.arr, (item) => { + ListItem() { + Text('' + item) + .width('100%') + .height(100) + .fontSize(16) + .textAlign(TextAlign.Center) + .borderRadius(10) + .backgroundColor(0xFFFFFF) + } + .border({ width: 2, color: Color.Green }) + }, item => item) + } + .border({ width: 2, color: Color.Red, style: BorderStyle.Dashed }) + .scrollBar(BarState.On) // 滚动条常驻 + .edgeEffect(EdgeEffect.Spring) // 滚动到边缘再拖动回弹效果 + + }.width('100%').height('100%').backgroundColor(0xDCDCDC).padding(20) + } } - } ``` ![](figures/listcolumn.gif) -```ts - @Entry - @Component - struct ListExample2 { - @State arr: string[] = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "10", "11", "12", "13", "14", "15"] - @State alignListItem: ListItemAlign = ListItemAlign.Start - - build() { - Column() { - List({ space: 20, initialIndex: 0 }) { - ForEach(this.arr, (item) => { - ListItem() { - Text('' + item) - .height('100%') - .width(100) - .fontSize(16) - .textAlign(TextAlign.Center) - .borderRadius(10) - .backgroundColor(0xFFFFFF) - } - .border({ width: 2, color: Color.Green }) - }, item => item) - } - .border({ width: 2, color: Color.Red, style: BorderStyle.Dashed }) - .scrollBar(BarState.On) // 滚动条常驻 - .edgeEffect(EdgeEffect.Spring) // 滚动到边缘再拖动回弹效果 - .listDirection(Axis.Horizontal) // 列表水平排列 - }.width('100%').height('100%').backgroundColor(0xDCDCDC).padding(20) - } - } - ``` + 横向List: + ```ts + @Entry + @Component + struct ListExample2 { + @State arr: string[] = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "10", "11", "12", "13", "14", "15"] + @State alignListItem: ListItemAlign = ListItemAlign.Start + + build() { + Column() { + List({ space: 20, initialIndex: 0 }) { + ForEach(this.arr, (item) => { + ListItem() { + Text('' + item) + .height('100%') + .width(100) + .fontSize(16) + .textAlign(TextAlign.Center) + .borderRadius(10) + .backgroundColor(0xFFFFFF) + } + .border({ width: 2, color: Color.Green }) + }, item => item) + } + .border({ width: 2, color: Color.Red, style: BorderStyle.Dashed }) + .scrollBar(BarState.On) // 滚动条常驻 + .edgeEffect(EdgeEffect.Spring) // 滚动到边缘再拖动回弹效果 + .listDirection(Axis.Horizontal) // 列表水平排列 + }.width('100%').height('100%').backgroundColor(0xDCDCDC).padding(20) + } + } + ``` + ![](figures/listrow.gif) - Scroll组件 - 线性布局中,当子组件的布局尺寸超过父组件的尺寸时,内容可以滚动,再内容外层包裹一个可滚动的容器组件Scroll, - + 线性布局中,当子组件的布局尺寸超过父组件的尺寸时,内容可以滚动。在Column或者Row外层包裹一个可滚动的容器组件Scroll实现。 -```ts + 纵向Scroll: + + ```ts @Entry @Component struct ScrollExample { @@ -330,10 +332,11 @@ struct BlankExample { } ``` - ![](figures/scrollrow.gif) - + ![](figures/scrollcolumn.gif) -```ts + 横向Scroll: + + ```ts @Entry @Component struct ScrollExample { @@ -356,7 +359,7 @@ struct BlankExample { }.height('100%') } .backgroundColor(0xDCDCDC) - .scrollable(ScrollDirection.Horizontal) // 滚动方向纵向 + .scrollable(ScrollDirection.Horizontal) // 滚动方向横向 .scrollBar(BarState.On) // 滚动条常驻显示 .scrollBarColor(Color.Gray) // 滚动条颜色 .scrollBarWidth(30) // 滚动条宽度 @@ -364,5 +367,4 @@ struct BlankExample { } } ``` - - ![](figures/scrollcolumn.gif) + ![](figures/scrollrow.gif)