1# Flex Layout 2 3The flex layout is the most flexible layout used in adaptive layout. It provides simple and powerful tools for distributing space and aligning items. 4 5 6- Container: [\<Flex>](../reference/arkui-ts/ts-container-flex.md) component, used to set layout attributes. 7- Child component: any of the child items in the **\<Flex>** component. 8- Main axis: axis along which items are placed in the **\<Flex>** component. Child components are laid out along the main axis by default. The start point of the main axis is referred to as main-start, and the end point is referred to as main-end. 9- Cross axis: axis that runs perpendicular to the main axis. The start point of the cross axis is referred to as cross-start, and the end point is referred to as cross-end. 10 11The following uses **FlexDirection.Row** as an example. 12 13 14 15## Container Attributes 16 17Create a flex layout through the **Flex** API provided by the **\<Flex>** component. The sample code is as follows: 18 19`Flex(options?: { direction?: FlexDirection, wrap?: FlexWrap, justifyContent?: FlexAlign, alignItems?: ItemAlign, alignContent?: FlexAlign })` 20 21 22 23### Flex Layout Direction 24The **direction** parameter sets the direction in which items are laid out in the **\<Flex>** component and thereby defines the main axis. Available values are as follows: 25 26 27 28- **FlexDirection.Row** (default value): The main axis runs along the row horizontally, and the child components are laid out from the start edge of the main axis. 29 30 ```ts 31 Flex({ direction: FlexDirection.Row }) { 32 Text('1').width('33%').height(50).backgroundColor(0xF5DEB3) 33 Text('2').width('33%').height(50).backgroundColor(0xD2B48C) 34 Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) 35 } 36 .height(70) 37 .width('90%') 38 .padding(10) 39 .backgroundColor(0xAFEEEE) 40 ``` 41  42 43- **FlexDirection.RowReverse**: The main axis runs along the row horizontally, and the child components are laid out from the end edge of the main axis, in a direction opposite to **FlexDirection.Row**. 44 45 ```ts 46 Flex({ direction: FlexDirection.RowReverse }) { 47 Text('1').width('33%').height(50).backgroundColor(0xF5DEB3) 48 Text('2').width('33%').height(50).backgroundColor(0xD2B48C) 49 Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) 50 } 51 .height(70) 52 .width('90%') 53 .padding(10) 54 .backgroundColor(0xAFEEEE) 55 ``` 56 57  58 59- **FlexDirection.Column**: The main axis runs along the column vertically, and the child components are laid out from the start edge of the main axis. 60 61 ```ts 62 Flex({ direction: FlexDirection.Column }) { 63 Text('1').width('100%').height(50).backgroundColor(0xF5DEB3) 64 Text('2').width('100%').height(50).backgroundColor(0xD2B48C) 65 Text('3').width('100%').height(50).backgroundColor(0xF5DEB3) 66 } 67 .height(70) 68 .width('90%') 69 .padding(10) 70 .backgroundColor(0xAFEEEE) 71 ``` 72 73  74 75- **FlexDirection.ColumnReverse**: The main axis runs along the column vertically, and the child components are laid out from the end edge of the main axis, in a direction opposite to **FlexDirection.Column**. 76 77 ```ts 78 Flex({ direction: FlexDirection.ColumnReverse }) { 79 Text('1').width('100%').height(50).backgroundColor(0xF5DEB3) 80 Text('2').width('100%').height(50).backgroundColor(0xD2B48C) 81 Text('3').width('100%').height(50).backgroundColor(0xF5DEB3) 82 } 83 .height(70) 84 .width('90%') 85 .padding(10) 86 .backgroundColor(0xAFEEEE) 87 ``` 88 89  90 91### Wrapping in the Flex Layout 92 93By default, child components are laid out on a single line (also called an axis) in the flex container. You can use the **wrap** parameter to set whether child components can wrap onto multiple lines. Available values are as follows: 94 95- **FlexWrap.NoWrap** (default value): Child components are laid out on a single line. This may cause the child components to shrink to fit the container when the total width of the child components is greater than the width of the container. 96 97 ```ts 98 Flex({ wrap: FlexWrap.NoWrap }) { 99 Text('1').width('50%').height(50).backgroundColor(0xF5DEB3) 100 Text('2').width('50%').height(50).backgroundColor(0xD2B48C) 101 Text('3').width('50%').height(50).backgroundColor(0xF5DEB3) 102 } 103 .width('90%') 104 .padding(10) 105 .backgroundColor(0xAFEEEE) 106 ``` 107 108  109 110- **FlexWrap.Wrap**: Child components can break into multiple lines along the main axis. 111 112 ```ts 113 Flex({ wrap: FlexWrap.Wrap }) { 114 Text('1').width('50%').height(50).backgroundColor(0xF5DEB3) 115 Text('2').width('50%').height(50).backgroundColor(0xD2B48C) 116 Text('3').width('50%').height(50).backgroundColor(0xD2B48C) 117 } 118 .width('90%') 119 .padding(10) 120 .backgroundColor(0xAFEEEE) 121 ``` 122 123  124 125- **FlexWrap.WrapReverse**: Child components can break into multiple lines in the reverse direction to the main axis. 126 127 ```ts 128 Flex({ wrap: FlexWrap.WrapReverse}) { 129 Text('1').width('50%').height(50).backgroundColor(0xF5DEB3) 130 Text('2').width('50%').height(50).backgroundColor(0xD2B48C) 131 Text('3').width('50%').height(50).backgroundColor(0xF5DEB3) 132 } 133 .width('90%') 134 .padding(10) 135 .backgroundColor(0xAFEEEE) 136 ``` 137 138  139 140### Alignment in the Flex Layout 141 142#### Alignment on the Main Axis 143 144Use the **justifyContent** parameter to set alignment of items on the main axis. The available options are as follows: 145 146 147 148- **FlexAlign.Start** (default value): The items are aligned with each other toward the start edge of the container along the main axis. 149 150 ```ts 151 Flex({ justifyContent: FlexAlign.Start }) { 152 Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) 153 Text('2').width('20%').height(50).backgroundColor(0xD2B48C) 154 Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) 155 } 156 .width('90%') 157 .padding({ top: 10, bottom: 10 }) 158 .backgroundColor(0xAFEEEE) 159 ``` 160 161  162 163- **FlexAlign.Center**: The items are aligned with each other toward the center of the container along the main axis. 164 165 ```ts 166 Flex({ justifyContent: FlexAlign.Center }) { 167 Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) 168 Text('2').width('20%').height(50).backgroundColor(0xD2B48C) 169 Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) 170 } 171 .width('90%') 172 .padding({ top: 10, bottom: 10 }) 173 .backgroundColor(0xAFEEEE) 174 ``` 175 176  177 178- **FlexAlign.End**: The items are aligned with each other toward the end edge of the container along the main axis. 179 180 ```ts 181 Flex({ justifyContent: FlexAlign.End }) { 182 Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) 183 Text('2').width('20%').height(50).backgroundColor(0xD2B48C) 184 Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) 185 } 186 .width('90%') 187 .padding({ top: 10, bottom: 10 }) 188 .backgroundColor(0xAFEEEE) 189 ``` 190 191  192 193- **FlexAlign.SpaceBetween**: The items are evenly distributed within the container along the main axis. The first and last items are aligned with the edges of the container. 194 195 ```ts 196 Flex({ justifyContent: FlexAlign.SpaceBetween }) { 197 Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) 198 Text('2').width('20%').height(50).backgroundColor(0xD2B48C) 199 Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) 200 } 201 .width('90%') 202 .padding({ top: 10, bottom: 10 }) 203 .backgroundColor(0xAFEEEE) 204 ``` 205 206  207 208- **FlexAlign.SpaceAround**: The items are evenly distributed in the container along the main axis. The space between the first item and main-start, and that between the last item and main-end are both half of the space between two adjacent items. 209 210 ```ts 211 Flex({ justifyContent: FlexAlign.SpaceAround }) { 212 Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) 213 Text('2').width('20%').height(50).backgroundColor(0xD2B48C) 214 Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) 215 } 216 .width('90%') 217 .padding({ top: 10, bottom: 10 }) 218 .backgroundColor(0xAFEEEE) 219 ``` 220 221  222 223- **FlexAlign.SpaceEvenly**: The items are equally distributed along the main axis. The space between the first item and main-start, the space between the last item and main-end, and the space between two adjacent items are the same. 224 225 ```ts 226 Flex({ justifyContent: FlexAlign.SpaceEvenly }) { 227 Text('1').width('20%').height(50).backgroundColor(0xF5DEB3) 228 Text('2').width('20%').height(50).backgroundColor(0xD2B48C) 229 Text('3').width('20%').height(50).backgroundColor(0xF5DEB3) 230 } 231 .width('90%') 232 .padding({ top: 10, bottom: 10 }) 233 .backgroundColor(0xAFEEEE) 234 ``` 235 236  237 238#### Alignment on the Cross Axis 239 240Alignment on the cross axis can be set for both the container and child components, with that set for child components having a higher priority. 241 242##### Setting Alignment on the Cross Axis for the Container 243Use the **alignItems** parameter of the **\<Flex>** component to set alignment of items on the cross axis. The available options are as follows: 244 245- **ItemAlign.Auto**: The items are automatically aligned in the flex container. 246 247 ```ts 248 Flex({ alignItems: ItemAlign.Auto }) { 249 Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) 250 Text('2').width('33%').height(40).backgroundColor(0xD2B48C) 251 Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) 252 } 253 .size({width: '90%', height: 80}) 254 .padding(10) 255 .backgroundColor(0xAFEEEE) 256 ``` 257 258  259 260- **ItemAlign.Start**: The items are aligned with the start edge of the container along the cross axis. 261 262 ```ts 263 Flex({ alignItems: ItemAlign.Start }) { 264 Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) 265 Text('2').width('33%').height(40).backgroundColor(0xD2B48C) 266 Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) 267 } 268 .size({width: '90%', height: 80}) 269 .padding(10) 270 .backgroundColor(0xAFEEEE) 271 ``` 272 273  274 275- **ItemAlign.Start**: The items are aligned with the center of the container along the cross axis. 276 277 ```ts 278 Flex({ alignItems: ItemAlign.Center }) { 279 Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) 280 Text('2').width('33%').height(40).backgroundColor(0xD2B48C) 281 Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) 282 } 283 .size({width: '90%', height: 80}) 284 .padding(10) 285 .backgroundColor(0xAFEEEE) 286 ``` 287 288  289 290- **ItemAlign.End**: The items are aligned with the end edge of the container along the cross axis. 291 292 ```ts 293 Flex({ alignItems: ItemAlign.End }) { 294 Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) 295 Text('2').width('33%').height(40).backgroundColor(0xD2B48C) 296 Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) 297 } 298 .size({width: '90%', height: 80}) 299 .padding(10) 300 .backgroundColor(0xAFEEEE) 301 ``` 302 303  304 305- **ItemAlign.Stretch**: The items are stretched along the cross axis. If no constraints are set, the items are stretched to fill the size of the container on the cross axis. 306 307 ```ts 308 Flex({ alignItems: ItemAlign.Stretch }) { 309 Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) 310 Text('2').width('33%').height(40).backgroundColor(0xD2B48C) 311 Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) 312 } 313 .size({width: '90%', height: 80}) 314 .padding(10) 315 .backgroundColor(0xAFEEEE) 316 ``` 317 318  319 320- **ItemAlign.Baseline**: The items are aligned at the baseline of the cross axis. 321 322 ```ts 323 Flex({ alignItems: ItemAlign.Baseline }) { 324 Text('1').width('33%').height(30).backgroundColor(0xF5DEB3) 325 Text('2').width('33%').height(40).backgroundColor(0xD2B48C) 326 Text('3').width('33%').height(50).backgroundColor(0xF5DEB3) 327 } 328 .size({width: '90%', height: 80}) 329 .padding(10) 330 .backgroundColor(0xAFEEEE) 331 ``` 332 333  334 335##### Setting Alignment on the Cross Axis for Child Components 336Use the **alignSelf** attribute of child components to set their alignment in the container on the cross axis. The settings overwrite the default **alignItems** settings in the flex layout container. The sample code is as follows: 337 338```ts 339Flex({ direction: FlexDirection.Row, alignItems: ItemAlign.Center }) { // The items are aligned with the center of the container. 340 Text('alignSelf Start').width('25%').height(80) 341 .alignSelf(ItemAlign.Start) 342 .backgroundColor(0xF5DEB3) 343 Text('alignSelf Baseline') 344 .alignSelf(ItemAlign.Baseline) 345 .width('25%') 346 .height(80) 347 .backgroundColor(0xD2B48C) 348 Text('alignSelf Baseline').width('25%').height(100) 349 .backgroundColor(0xF5DEB3) 350 .alignSelf(ItemAlign.Baseline) 351 Text('no alignSelf').width('25%').height(100) 352 .backgroundColor(0xD2B48C) 353 Text('no alignSelf').width('25%').height(100) 354 .backgroundColor(0xF5DEB3) 355 356}.width('90%').height(220).backgroundColor(0xAFEEEE) 357``` 358 359 360 361In the preceding example, both **alignItems** of the **\<Flex>** component and the **alignSelf** attribute of the child component are set. In this case, the **alignSelf** settings take effect. 362 363#### Content Alignment 364 365Use the **alignContent** parameter to set how space is distributed between and around content items along the cross axis. This parameter is valid only for a flex layout that contains multiple lines. The available options are as follows: 366 367- **FlexAlign.Start**: The items are aligned toward the start edge of the cross axis in the container. 368 369 ```ts 370 Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.Start }) { 371 Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) 372 Text('2').width('60%').height(20).backgroundColor(0xD2B48C) 373 Text('3').width('40%').height(20).backgroundColor(0xD2B48C) 374 Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) 375 Text('5').width('20%').height(20).backgroundColor(0xD2B48C) 376 } 377 .width('90%') 378 .height(100) 379 .backgroundColor(0xAFEEEE) 380 ``` 381 382  383 384- **FlexAlign.Center**: The items are aligned toward the center of the cross axis in the container. 385 386 ```ts 387 Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.Center }) { 388 Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) 389 Text('2').width('60%').height(20).backgroundColor(0xD2B48C) 390 Text('3').width('40%').height(20).backgroundColor(0xD2B48C) 391 Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) 392 Text('5').width('20%').height(20).backgroundColor(0xD2B48C) 393 } 394 .width('90%') 395 .height(100) 396 .backgroundColor(0xAFEEEE) 397 ``` 398 399  400 401- **FlexAlign.End**: The items are aligned toward the end edge of the cross axis in the container. 402 403 ```ts 404 Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.End }) { 405 Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) 406 Text('2').width('60%').height(20).backgroundColor(0xD2B48C) 407 Text('3').width('40%').height(20).backgroundColor(0xD2B48C) 408 Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) 409 Text('5').width('20%').height(20).backgroundColor(0xD2B48C) 410 } 411 .width('90%') 412 .height(100) 413 .backgroundColor(0xAFEEEE) 414 ``` 415 416  417 418- **FlexAlign.SpaceBetween**: The items are evenly distributed in the container along the cross axis, with the first and last items aligned with the edges of the cross axis. 419 420 ```ts 421 Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.SpaceBetween }) { 422 Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) 423 Text('2').width('60%').height(20).backgroundColor(0xD2B48C) 424 Text('3').width('40%').height(20).backgroundColor(0xD2B48C) 425 Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) 426 Text('5').width('20%').height(20).backgroundColor(0xD2B48C) 427 } 428 .width('90%') 429 .height(100) 430 .backgroundColor(0xAFEEEE) 431 ``` 432 433  434 435- **FlexAlign.SpaceAround**: The items are evenly distributed in the container along the cross axis. The spacing before the first item and after the last item is half of the spacing between two adjacent items. 436 437 ```ts 438 Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.SpaceAround }) { 439 Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) 440 Text('2').width('60%').height(20).backgroundColor(0xD2B48C) 441 Text('3').width('40%').height(20).backgroundColor(0xD2B48C) 442 Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) 443 Text('5').width('20%').height(20).backgroundColor(0xD2B48C) 444 } 445 .width('90%') 446 .height(100) 447 .backgroundColor(0xAFEEEE) 448 ``` 449 450  451 452- **FlexAlign.SpaceEvenly**: The items are evenly distributed in the container along the cross axis. The spacing between each two adjacent items, the spacing between the start edge and the first item, and the spacing between the end edge and the last item, are the same. 453 454 ```ts 455 Flex({ justifyContent: FlexAlign.SpaceBetween, wrap: FlexWrap.Wrap, alignContent: FlexAlign.SpaceEvenly }) { 456 Text('1').width('30%').height(20).backgroundColor(0xF5DEB3) 457 Text('2').width('60%').height(20).backgroundColor(0xD2B48C) 458 Text('3').width('40%').height(20).backgroundColor(0xD2B48C) 459 Text('4').width('30%').height(20).backgroundColor(0xF5DEB3) 460 Text('5').width('20%').height(20).backgroundColor(0xD2B48C) 461 } 462 .width('90%') 463 .height(100) 464 .backgroundColor(0xAFEEEE) 465 ``` 466 467  468 469### Adaptive Stretching of Flex Layout 470 471When the size of the container in the flex layout is not large enough, the following attributes of the child component can be used to achieve adaptive layout. 472- **flexBasis**: base size of the child component in the container along the main axis. It sets the space occupied by the child component. If this attribute is not set or is set to **auto**, the space occupied by the child component is the value of width/height. 473 474 ```ts 475 Flex() { 476 Text('flexBasis("auto")') 477 .flexBasis('auto') // When width is not set and flexBasis is set to auto, the content is loose. 478 .height(100) 479 .backgroundColor(0xF5DEB3) 480 Text('flexBasis("auto")'+' width("40%")') 481 .width('40%') 482 .flexBasis('auto') // When width is set and flexBasis is set to auto, the value of width is used. 483 .height(100) 484 .backgroundColor(0xD2B48C) 485 486 Text('flexBasis(100)') // When width is not set and flexBasis is set to 100, the width is 100 vp. 487 .flexBasis(100) 488 .height(100) 489 .backgroundColor(0xF5DEB3) 490 491 Text('flexBasis(100)') 492 .flexBasis(100) 493 .width(200) // When width is set to 200 and flexBasis 100, the width is 100 vp, which means that the settings of flexBasis take precedence. 494 .height(100) 495 .backgroundColor(0xD2B48C) 496 }.width('90%').height(120).padding(10).backgroundColor(0xAFEEEE) 497 ``` 498 499  500 501- **flexGrow**: percentage of the flex layout's remaining space that is allocated to the child component. In other words, it is the grow factor of the child component. 502 503 ```ts 504 Flex() { 505 Text('flexGrow(1)') 506 .flexGrow(2) 507 .width(100) 508 .height(100) 509 .backgroundColor(0xF5DEB3) 510 511 Text('flexGrow(2)') 512 .flexGrow(2) 513 .width(100) 514 .height(100) 515 .backgroundColor(0xD2B48C) 516 517 Text('no flexGrow') 518 .width(100) 519 .height(100) 520 .backgroundColor(0xF5DEB3) 521 }.width(400).height(120).padding(10).backgroundColor(0xAFEEEE) 522 ``` 523 524  525 526In the preceding figure, the width of the parent container is 400 vp, the original width of the three child components is 100 vp, which adds up to the total width of 300 vp. The remaining space 100 vp is allocated to the child components based on their **flexGrow** settings. Child components that do not have **flexGrow** set are not involved in the allocation of remaining space. 527The first child component and the second child component receive their share of remaining space at the 2:3 ratio. The width of the first child component is 100 vp + 100 vp x 2/5 = 140 vp, and the width of the second child component is 100 vp + 100 vp x 3/5 = 160 vp. 528 529- **flexShrink**: shrink factor of the child component when the size of all child components is larger than the flex container. 530 531 ```ts 532 Flex({ direction: FlexDirection.Row }) { 533 Text('flexShrink(3)') 534 .flexShrink(3) 535 .width(200) 536 .height(100) 537 .backgroundColor(0xF5DEB3) 538 539 Text('no flexShrink') 540 .width(200) 541 .height(100) 542 .backgroundColor(0xD2B48C) 543 544 Text('flexShrink(2)') 545 .flexShrink(2) 546 .width(200) 547 .height(100) 548 .backgroundColor(0xF5DEB3) 549 }.width(400).height(120).padding(10).backgroundColor(0xAFEEEE) 550 ``` 551 552  553 554## Example Scenario 555 556With the flex layout, child components can be arranged horizontally, aligned at both edges, evenly spaced, and centered in the vertical direction. The sample code is as follows: 557 558```ts 559@Entry 560@Component 561struct FlexExample { 562 build() { 563 Column() { 564 Column({ space: 5 }) { 565 Flex({ direction: FlexDirection.Row, wrap: FlexWrap.NoWrap, justifyContent: FlexAlign.SpaceBetween, alignItems: ItemAlign.Center }) { 566 Text('1').width('30%').height(50).backgroundColor(0xF5DEB3) 567 Text('2').width('30%').height(50).backgroundColor(0xD2B48C) 568 Text('3').width('30%').height(50).backgroundColor(0xF5DEB3) 569 } 570 .height(70) 571 .width('90%') 572 .backgroundColor(0xAFEEEE) 573 }.width('100%').margin({ top: 5 }) 574 }.width('100%') 575 } 576} 577``` 578 579 580