当前位置:   article > 正文

Flex布局图文详解与示例代码_flex 布局

flex 布局

Flex 布局,即 Flex Box(弹性布局),是一种较为灵活、强大的页面 CSS 布局方式。在深入学习 Flex 布局前,我们需要了解一些 Flex 相关的概念和术语。

Flex 布局的优点:

  • 简便、完整、响应式
  • 浏览器支持良好
  • 传统盒状模型中,难以实现的垂直等布局等 ,Flex布局可以完美解决。

一、基础概念


首先,我们需要了解一下 Flex 布局中的一些概念和术语:

  • flex 容器(flex container)
  • flex 项目(flex item)
  • 主轴(main axis)
  • 交叉轴(cross axis)
  • 占用主轴空间(main size)
  • 占用交叉轴空间(cross size)
  • 线轴起止点(main start、main end、cross start、cross end)

在图1-1 非常清晰的展示了这些概念的相互关系。

图1-1 Flex 容器

1.1 容器与项目

使用 Flex 布局的元素(display: flex),称之为 Flex 容器(Flex Container),简称 "容器"。Flex 的布局发生在父容器和子容器之间,因此,元素一旦被申明为 Flex 布局后,它的所有子元素自动成为容器成员。通常,我们将容器内的成员统称为 Flex 项目(Flex item),简称 "项目"。

本文约定:"容器" 指的是 Flex 容器;"项目" 指的是 Flex 项目。

1.2 主轴、交叉轴

容器中默认存在两条线轴,即:主轴(main axis)交叉轴(cross axis)。主轴与交叉轴是垂直关系,值得注意的是主轴不一定是水平方向,而是由 flex-direction 属性所决定的。

  • main axis:主轴。
  • cross axis:交叉轴。

1.3 轴线起始位置

  • main start:主轴开始位置
  • main end:主轴结束位置
  • cross start:交叉轴开始位置
  • cross ennd:交叉轴结束位置

1.4 主轴、交叉轴空间

项目(flex item)默认是沿主轴方向排列的,单个项目占据主轴的空间称之为 main size,占据交叉轴的空间称之为 cross size

  • main size:占据主轴的空间
  • cross size:占据交叉轴的空间

二、容器、项目属性


本小节,主要介绍一下容器属性及项目属性。通过本章节,相信你会加深对 Flex 布局理解。为了形象说明这些属性的含义,作者 Billow 尽可能在每个示例中做到图文并茂。

2.1 容器属性

下表展示了容器的属性和取值。

属性取值说明
displayflex定义一个 Flex 容器,弹性盒子
inline-flex定义一个内联元素为 Flex 容器
flex-direction

row (默认)

从左到右

row-reverse 

从右到左

column 

从上到下
column-reverse从下到上
flex-wrap

nowrap (默认,不换行)

wrap(换行)

wrap-reverse(反向换行)

flex项目在一个轴线排不下情况,该如何换行。
flex-flow<flex-direction> <flex-wrap>

 flex-direction 与 flex-wrap 的缩写形式。

justify-content

flex-start(默认,左对齐)

flex-end(右对齐)

center(居中)

space-between 

space-around

flex项目在主轴上的对齐方式。

align-items

flex-start

flex-end

center

stretch

baseline

定义项目在交叉轴上对齐方式
align-content

flex-start

flex-end

center

space-between

space-around

stetch

定义多条线轴对齐方式,若只有一条线轴。

若仅有一条线轴,该属性无效。

2.1.1 flex-direction

  1. .container {
  2. flex-direction: row | row-reverse | column | column-reverse;
  3. }

flex-direction 属性,定义了在哪个方向上排列项目。flex-direction有四个取值,分别为:

取值说明
row由左到右。(默认)
row-reverse从右到左。
column从上到下。
column-reverse从下到上。

图2-1 容器定义 flex-direction 属性示例图

图2-1 完整代码:

  1. <!DOCTYPE html>
  2. <html>
  3. <head>
  4. <style>
  5. .flex-container-row {
  6. display: flex;
  7. flex-direction: row;
  8. }
  9. .flex-container-row-reverse {
  10. display: flex;
  11. flex-direction: row-reverse;
  12. }
  13. .flex-container-column {
  14. display: flex;
  15. flex-direction: column;
  16. }
  17. .flex-container-column-reverse {
  18. display: flex;
  19. flex-direction: column-reverse;
  20. }
  21. .flex-item {
  22. border:1px solid #fff;
  23. height:60px;
  24. width:60px;
  25. text-align:center;
  26. line-height:60px;
  27. background: #f66;
  28. color:white;
  29. }
  30. .flex-item.blue {
  31. border:1px solid #fff;
  32. background: #33f;
  33. }
  34. </style>
  35. </head>
  36. <body>
  37. <div class="flex-container-row">
  38. <div class="flex-item">1.刘邦</div>
  39. <div class="flex-item">2.吕雉</div>
  40. <div class="flex-item">3.项羽</div>
  41. <div class="flex-item">4.虞姬</div>
  42. </div>
  43. <div class="flex-container-row-reverse">
  44. <div class="flex-item blue"></div>
  45. <div class="flex-item blue"></div>
  46. <div class="flex-item blue"></div>
  47. <div class="flex-item blue"></div>
  48. </div>
  49. <div class="flex-container-column">
  50. <div class="flex-item"></div>
  51. <div class="flex-item"></div>
  52. <div class="flex-item"></div>
  53. </div>
  54. <div class="flex-container-column-reverse">
  55. <div class="flex-item blue">苏洵</div>
  56. <div class="flex-item blue">苏轼</div>
  57. <div class="flex-item blue">苏辙</div>
  58. </div>
  59. </body>
  60. </html>

2.1.2 flex-wrap

flex-wrap 定义了项目在轴线上的排列方式,在默认情况下,项目都排列在一条轴线上,不会换行,可以通过 flex-wrap 来定义换行的方式。

取值说明
nowrap默认值,不换行
wrap项目沿着轴线方向排列,一行排不下后,换行排列。        
wrap-reverse反向换行。例如:在主轴线上,第一行会在第二行的下放。

 图2-2 容器定义 flex-wrap 示例

图2-2 完整代码:

  1. <!DOCTYPE html>
  2. <html>
  3. <head>
  4. <style>
  5. .flex-container-nowrap {
  6. display: flex;
  7. flex-wrap: nowrap;
  8. }
  9. .flex-container-wrap {
  10. display: flex;
  11. flex-wrap: wrap;
  12. margin-top:10px;
  13. }
  14. .flex-container-wrap-reverse {
  15. display: flex;
  16. flex-wrap: wrap-reverse;
  17. margin-top:10px;
  18. }
  19. .flex-item {
  20. border:1px solid #fff;
  21. height:60px;
  22. width:120px;
  23. text-align:center;
  24. line-height:60px;
  25. background: #f66;
  26. color:white;
  27. font-size:18px;
  28. }
  29. .flex-item.blue {
  30. border:1px solid #fff;
  31. background: #33f;
  32. }
  33. .flex-item.gray {
  34. border:1px solid #fff;
  35. background: #666;
  36. }
  37. .flex-item.circle {
  38. border-radius: 10%;
  39. }
  40. h3 {
  41. color: #666;
  42. }
  43. </style>
  44. </head>
  45. <body>
  46. <h3>nowrap</h3>
  47. <div class="flex-container-nowrap">
  48. <div class="flex-item">1</div>
  49. <div class="flex-item">2</div>
  50. <div class="flex-item">3</div>
  51. <div class="flex-item">4</div>
  52. <div class="flex-item">5</div>
  53. <div class="flex-item">6</div>
  54. <div class="flex-item">7</div>
  55. <div class="flex-item">8</div>
  56. </div>
  57. <h3>wrap</h3>
  58. <div class="flex-container-wrap">
  59. <div class="flex-item gray">1</div>
  60. <div class="flex-item gray">2</div>
  61. <div class="flex-item gray">3</div>
  62. <div class="flex-item gray">4</div>
  63. <div class="flex-item gray">5</div>
  64. <div class="flex-item gray">6</div>
  65. <div class="flex-item gray">7</div>
  66. <div class="flex-item gray">8</div>
  67. </div>
  68. <h3>wrap-reverse</h3>
  69. <div class="flex-container-wrap-reverse">
  70. <div class="flex-item blue circle">1</div>
  71. <div class="flex-item blue circle">2</div>
  72. <div class="flex-item blue circle">3</div>
  73. <div class="flex-item blue circle">4</div>
  74. <div class="flex-item blue circle">5</div>
  75. <div class="flex-item blue circle">6</div>
  76. <div class="flex-item blue circle">7</div>
  77. <div class="flex-item blue circle">8</div>
  78. </div>
  79. </body>
  80. </html>

值得注意的是,当我们将 flex-wrap 设置为 nowrap 后,并将每一个项目的宽度设置为 120px ,但是,但主轴宽度无法容纳所有项目后,项目的实际宽度会被收缩,在flex项目属性中,我们会详细解释。

2.1.3 flex-flow

flex-flow 是 flex-direction 与 flex-wrap 的缩写形式。

语法:flex-flow: <flex-direction>  <flex-wrap>

例子:

flex-flow: row nowrap (默认值,项目沿着主轴排列,不换行。)

flex-flow: column  wrap-reverse(项目沿着交叉轴排列,反向换行)

2.1.4 justify-content

justify-content 定义了项目在主轴上的对齐方式。共有5个取值,如下表所示。

取值说明
flex-start左对齐
flex-end右对齐
center居中
space-between两端对齐,项目间隔相等
space-around项目间隔相等,两端也有间隔。

图2-3 容器定义  justify-content 示例

下图很好的解释了 space-between 与 space-around 的区别,space-between 会使项目两端对齐,并且项目之间的间距相同。space-around 同样会是的项目间距相同,不同之处是与两端也会有间距。

可以看出 space-around 项目与项目之间的距离是两端间距的2倍。你可以理解为:margin-left、margn-right 设置了相同的值。

图2-4 space-between 与 space-around 的区别

图2-3完整代码:

  1. <!DOCTYPE html>
  2. <html>
  3. <head>
  4. <style>
  5. body {
  6. padding:0;
  7. margin:0;
  8. }
  9. .flex-container-flex-start {
  10. display: flex;
  11. justify-content: flex-start;
  12. }
  13. .flex-container-flex-end {
  14. display: flex;
  15. justify-content: flex-end;
  16. }
  17. .flex-container-center {
  18. display: flex;
  19. justify-content: center;
  20. }
  21. .flex-container-space-between {
  22. display: flex;
  23. justify-content: space-between;
  24. }
  25. .flex-container-space-around {
  26. display: flex;
  27. justify-content: space-around;
  28. }
  29. .flex-item {
  30. border:1px solid #fff;
  31. height:60px;
  32. width:120px;
  33. text-align:center;
  34. line-height:60px;
  35. background: #f66;
  36. color:white;
  37. font-size:18px;
  38. }
  39. .flex-item.blue { background: #33f; }
  40. .flex-item.gray { background: #666; }
  41. .flex-item.purple { background: #f6f; }
  42. .flex-item.brown { background: #9e5b03; }
  43. .flex-item.circle {
  44. border-radius: 10%;
  45. }
  46. h3 {
  47. color: #666;
  48. margin-top:10p;
  49. border: 1px dashed #dcdcdc;
  50. }
  51. </style>
  52. </head>
  53. <body>
  54. <h3>flex-start</h3>
  55. <div class="flex-container-flex-start">
  56. <div class="flex-item">1</div>
  57. <div class="flex-item">2</div>
  58. <div class="flex-item">3</div>
  59. <div class="flex-item">4</div>
  60. <div class="flex-item">5</div>
  61. <div class="flex-item">6</div>
  62. </div>
  63. <h3>flex-end</h3>
  64. <div class="flex-container-flex-end">
  65. <div class="flex-item gray">1</div>
  66. <div class="flex-item gray">2</div>
  67. <div class="flex-item gray">3</div>
  68. <div class="flex-item gray">4</div>
  69. <div class="flex-item gray">5</div>
  70. <div class="flex-item gray">6</div>
  71. </div>
  72. <h3>center</h3>
  73. <div class="flex-container-center">
  74. <div class="flex-item blue">1</div>
  75. <div class="flex-item blue">2</div>
  76. <div class="flex-item blue">3</div>
  77. <div class="flex-item blue">4</div>
  78. <div class="flex-item blue">5</div>
  79. <div class="flex-item blue">6</div>
  80. </div>
  81. <h3>space-between</h3>
  82. <div class="flex-container-space-between">
  83. <div class="flex-item purple">1</div>
  84. <div class="flex-item purple">2</div>
  85. <div class="flex-item purple">3</div>
  86. <div class="flex-item purple">4</div>
  87. <div class="flex-item purple">5</div>
  88. <div class="flex-item purple">6</div>
  89. </div>
  90. <h3>space-around</h3>
  91. <div class="flex-container-space-around">
  92. <div class="flex-item brown">1</div>
  93. <div class="flex-item brown">2</div>
  94. <div class="flex-item brown">3</div>
  95. <div class="flex-item brown">4</div>
  96. <div class="flex-item brown">5</div>
  97. <div class="flex-item brown">6</div>
  98. </div>
  99. </body>
  100. </html>

2.1.5 align-items

align-items 属性,定义了项目在交叉轴上的对齐方式,有5个取值。

取值说明
flex-start与交叉轴的起点对齐

flex-end

与交叉轴的终点对齐
center在交叉轴上居中对齐
baseline以项目中第一行文字基线对齐
stretch在未设置高度情况下,将占满容器的高度

2.1.6 align-content

align-content 属性定义了多根主轴线在垂直方向上的对齐方式。

align-content 取值说明
flex-start与交叉轴起点对齐
flex-end与交叉轴终点对齐
center在交叉轴上居中对齐
space-between与交叉轴两端对齐,轴线之间的间隔平均分布
space-around轴线之间的间隔平均分布,包括两端
stretch默认值,轴线占满交叉轴

2.2 项目属性

项目属性默认值说明
order0定义了项目的排列顺序。
flex-grow0扩大因子,定义了项目的放大比例
flex-shrink1收缩因子,定义了项目的缩小比例
flex-basicautoflex-basis属性定义了在分配多余空间之前,项目占据的主轴空间(main size)。
flex0 1 autoflex-grow、flex-shrink、flex-basis的缩写形式
align-selfauto

align-self 属性允许单个项目有与其他项目不一样的对齐方式,

也就是说改属性可以覆盖父容器设置的 align-items 属性。

在继续讲解这些项目属性之前,我们先来了解一个非常重要的概念 — 剩余空间

图 2-5 剩余空间

为了解释剩余空间,下面给出一个示例。如图2-5所示,我们将父容器的宽度设置为 800px,容器中3个项目宽度分别为100px、200px、300px。那么,剩余空间就是:

200px = 800px - (100px + 200px + 300px)

简言之, flex-grow、flex-shrink 和 flex-basis 都是围绕如何分配剩余空间展开的。

2.2.1 order 

order 属性,定义了项目的排列顺序,数值越小越靠前。可以为0,也可以为负值。order的默认值为 0

.item { order: <integer> }

 图2-6 order 属性示例

图2-6 完整代码

  1. <!DOCTYPE html>
  2. <html>
  3. <head>
  4. <style>
  5. .flex-container {
  6. display: flex;
  7. margin-top:5px;
  8. }
  9. .item {
  10. height:60px;
  11. width:60px;
  12. text-align:center;
  13. line-height:60px;
  14. background: #f66;
  15. color:white;
  16. font-size:18px;
  17. border-radius: 100px;
  18. }
  19. .item.red {background: #f66;}
  20. .item.blue { background: #66f; }
  21. .item.gray { background: #666; }
  22. .item.purple { background: #f6f; }
  23. .item.brown { background: #9e5b03; }
  24. h3 {
  25. color: #666;
  26. margin-top:10px;
  27. border-bottom: 1px dashed #dcdcdc;
  28. }
  29. </style>
  30. </head>
  31. <body>
  32. <h3>order</h3>
  33. <div class="flex-container">
  34. <div style="order:0" class="item red" ></div>
  35. <div style="order:1" class="item blue"></div>
  36. <div style="order:2" class="item gray" ></div>
  37. <div style="order:3" class="item purple"></div>
  38. <div style="order:4" class="item brown" ></div>
  39. </div>
  40. <div class="flex-container">
  41. <div style="order:4" class="item red" ></div>
  42. <div style="order:3" class="item blue"></div>
  43. <div style="order:2" class="item gray" ></div>
  44. <div style="order:1" class="item purple"></div>
  45. <div style="order:0" class="item brown" ></div>
  46. </div>
  47. </body>
  48. </html>

2.2.2 flex-grow

扩大因子,定义项目的放大比例 。

.item { flex-grow: <number> }

2.2.3 flex-shrink

收缩因子,定义了项目的缩小比例。

.item { flex-shrink: <number> }

 图 2-7 flex-grow 与 flex-shrink 的使用

图2-7 完整代码

  1. <!DOCTYPE html>
  2. <html>
  3. <head>
  4. <style>
  5. .flex-container {
  6. display: flex;
  7. margin-top:1px;
  8. }
  9. .item {
  10. height:60px;
  11. width:60px;
  12. text-align:center;
  13. line-height:60px;
  14. background: #f66;
  15. color:white;
  16. font-size:18px;
  17. }
  18. .item.red {background: #f66;}
  19. .item.blue { background: #66f; }
  20. .item.gray { background: #666; }
  21. .item.purple { background: #f6f; }
  22. .item.brown { background: #9e5b03; }
  23. h3 {
  24. color: #666;
  25. margin-top:10px;
  26. border-bottom: 1px dashed #dcdcdc;
  27. }
  28. </style>
  29. </head>
  30. <body>
  31. <h3>flex-grow</h3>
  32. <div class="flex-container">
  33. <div style="flex-grow:0" class="item blue">0</div>
  34. <div style="flex-grow:1" class="item red" >1</div>
  35. <div style="flex-grow:2" class="item blue">2</div>
  36. <div style="flex-grow:3" class="item red" >3</div>
  37. <div style="flex-grow:4" class="item blue">4</div>
  38. <div style="flex-grow:5" class="item red" >5</div>
  39. </div>
  40. <div class="flex-container">
  41. <div style="flex-grow:0" class="item blue">0</div>
  42. <div style="flex-grow:1" class="item red" >1</div>
  43. <div style="flex-grow:0" class="item blue">0</div>
  44. </div>
  45. <h3>flex-shrink</h3>
  46. <div class="flex-container" style="width:600px;border:1px dotted #dcdcdc;">
  47. <div style="flex-shrink:0;width:100px;" class="item blue">100</div>
  48. <div style="flex-shrink:1;width:100px;" class="item red" >100</div>
  49. <div style="flex-shrink:2;width:100px;" class="item blue">100</div>
  50. </div>
  51. <div class="flex-container" style="width:600px;border:1px dotted #dcdcdc;">
  52. <div style="flex-shrink:0;width:300px;" class="item blue">300</div>
  53. <div style="flex-shrink:1;width:300px;" class="item red" >300</div>
  54. <div style="flex-shrink:1;width:300px;" class="item blue">300</div>
  55. </div>
  56. <div class="flex-container" style="width:600px;border:1px dotted #dcdcdc;">
  57. <div style="flex-shrink:0;width:300px;" class="item blue">300</div>
  58. <div style="flex-shrink:1;width:300px;" class="item red" >300</div>
  59. <div style="flex-shrink:5;width:300px;" class="item blue">300</div>
  60. </div>
  61. </body>
  62. </html>

2.2.4 flex-basis

flex-basis 属性定义了在分配多余空间之前,项目占据主轴空间。默认值为:auto,即项目本来大小。

理解这段话的重点两个字就是 "之前"。

我们将3个 item 宽度分别设置为 100px、200px、300px,并且将第3个项目的 flex-basis 设置为 400px。可以看出,效果如下图第2行所示。

图2-8 加了 flex-basis 后的剩余空间

图2-8 完整代码:

  1. <!DOCTYPE html>
  2. <html>
  3. <head>
  4. <style>
  5. .flex-container {
  6. display: flex;
  7. width: 800px;
  8. border: 1px solid red;
  9. margin-top:5px;
  10. }
  11. .item {
  12. width:60px;
  13. text-align:center;
  14. line-height:60px;
  15. color:white;
  16. font-size:18px;
  17. border:1px solid #fff;
  18. }
  19. .item.red {background: #f66;}
  20. .item.blue { background: #66f; }
  21. .item.gray { background: #666; }
  22. </style>
  23. </head>
  24. <body>
  25. <div class="flex-container">
  26. <div class="item red" style="width:100px">100px</div>
  27. <div class="item blue" style="width:200px">200px</div>
  28. <div class="item gray" style="width:300px;">300px</div>
  29. </div>
  30. <div class="flex-container">
  31. <div class="item red" style="width:100px">100px</div>
  32. <div class="item blue" style="width:200px">200px</div>
  33. <div class="item gray" style="width:300px;flex-basis:400px;">300px/400px</div>
  34. </div>
  35. </body>
  36. </html>

2.2.5 flex

flex 为 flex-grow、flex-shrink、flex-basis 的缩写形式。

flex: none | [ <'flex-grow'> <'flex-shrink'>? || <'flex-basis'> ]

默认值为: 0 1 auto

另外,改属性有两个快捷值:

flex: auto   相当于 flex: 1 1 auto

flex: none 相当于 flex: 0 0 auto

2.2.6 align-self

align-self 属性允许单个项目有与其他项目不一样的对齐方式。也就是说改属性可以覆盖父容器设置的 align-items 属性。

取值说明
auto继承父元素的 align-items 属性
flex-start与交叉轴的起点对齐

flex-end

与交叉轴的终点对齐
center在交叉轴上居中对齐
baseline以项目中第一行文字基线对齐
stretch在未设置高度情况下,将占满容器的高度

三、综合示例


为了加深对 Flex 布局的理解,下面给出几个综合性的例子。

3.1 春联

在古代,在竹简写字一般都是从右向左、从上向下的顺序。下面我们用 Flex 布局来实现这样的例子。实现从右到左,从上到下书写春联。

 图3-1 春联

图3-1 春联完整代码

  1. <!DOCTYPE html>
  2. <html>
  3. <head>
  4. <style>
  5. /*定义一个Flex容器*/
  6. #container {
  7. display: flex;
  8. flex-direction:column;
  9. flex-wrap: wrap-reverse;
  10. align-content: flex-start;
  11. height: 700px;
  12. font-family: LiSu;
  13. background: #f33;
  14. }
  15. /*每一个字的样式*/
  16. .word {
  17. height: 100px;
  18. width: 100px;
  19. line-height: 100px;
  20. font-size: 50px;
  21. text-align:center;
  22. background: #f33;
  23. border-left: 1px solid white;
  24. color:black;
  25. }
  26. </style>
  27. </head>
  28. <body>
  29. <div id="container"></div>
  30. </body>
  31. <script>
  32. var innerHtml = "";
  33. var p = "一年好运随春到"
  34. + "四季彩云滚滚来"
  35. + "一年四季春常在"
  36. + "万紫千红永开花";
  37. for(var i = 0;i < p.length;i++) {
  38. innerHtml += "<div class='word'>" + p.charAt(i) + "</div>";
  39. }
  40. document.getElementById("container").innerHTML = innerHtml;
  41. </script>
  42. </html>

与 Flex 布局相关的显式代码仅4行: 

  1. #container {
  2. display: flex; /*定义一个Flex容器*/
  3. flex-direction:column; /*每个项目(每个字)的顺序为从上到下。*/
  4. flex-wrap: wrap-reverse; /*反向换行,即:第二行在第一行的左面。*/
  5. align-content: flex-start; /*多条轴线,靠右对其。*/
  6. height: 700px;
  7. font-family: LiSu;
  8. background: #f33;
  9. }

当然,我们也可以用 flex-flow 实现:

  1. #container {
  2. display: flex; /*定义一个Flex容器*/
  3. /* flex-direction:column; */ /*每个项目(每个字)的顺序为从上到下。*/
  4. /* flex-wrap: wrap-reverse; */ /*反向换行,即:第二行在第一行的左面。*/
  5. flex-flow: column wrap-reverse;
  6. align-content: flex-start; /*多条轴线,靠右对其。*/
  7. height: 700px;
  8. font-family: LiSu;
  9. background: #f33;
  10. }

手工码字,虽然已经检查多遍,难免有不足之处,发现有错误之处,请多多指教。

本文内容由网友自发贡献,转载请注明出处:https://www.wpsshop.cn/w/我家自动化/article/detail/325649
推荐阅读
相关标签
  

闽ICP备14008679号