乐趣区

深入解析CSS-FlexBox

Flexbox 是一个 CSS3 的盒子模型(box model),顾名思义它就是一个灵活的盒子(Flexible Box)。

Flexbox 模型概念

第一步要来看 Flexbox 的盒子模型,根据 W3C 文章所描述,flex 的盒子模型如下图所呈现,与一般的盒子模型不同的地方,在于 Flexbox 的盒子模型具有水平的起点与终点(main start、main end),垂直的起点与终点(cross start、cross end),水平轴与垂直轴(main axis、cross axis),然后元素具有水平尺寸与垂直尺寸(main size、cross size),这些都是相当重要的布局概念。

Flexbox 属性介绍

再来我们先看看 Flexbox 有哪些属性:

  • display
  • flex-direction
  • justify-content
  • align-items
  • align-self
  • align-content
  • flex-wrap
  • order
  • flex

display

display 是我们熟知的 CSS 属性,对于 Flexbox 来说,多了有两种方式可以设定,预设为“flex”,其布局方式与 block 几乎类似,都会强迫换行,但设定 display:flex 的子元素却具备了更多弹性的设定,此外另外一种方式则是“inline-flex”,和 inline-block 也是几乎雷同,意义上都是一个 display:flex 的元素外面包覆 display:inline 的属性,在后方的元素不会换行。

CSS:

.flex,
.inline-flex{
    width:100px;
    height:50px;
    border:1px solid #000;
}
.flex{display:flex;}
.inline-flex{display:inline-flex;}

flex-direction

flex-direction 表示 Flexbox 内容元素的“排列方向”,分别有下列四种。

  • row:预设值,由左到右,从上到下
  • row-reverse:与 row 相反
  • column:从上到下,再由左到右
  • column-reverse:与 column 相反

CSS:

.flex-row{flex-direction:row;}
.flex-row-reverse{flex-direction:row-reverse;}
.flex-column{flex-direction:column;}
.flex-column-reverse{flex-direction:column-reverse;} 

justify-content

justify-content 决定了内容元素与整个 Flexbox 的“水平对齐”位置,回想一下最上面讲的 Flexbox 盒子模型,具有 main start 与 main end 左右两个端点,justify-content 就是按照这个方式做设定,而其中的设定值总共有下列五个。

  • flex-start:预设值,对齐最左边的 main start
  • flex-end:对齐最左边的 main end
  • center:水平居中
  • space-between:平均分配内容元素,左右元素将会与 main start 和 main end 贴齐
  • space-around:平均分配内容元素,间距也是平均分配

CSS:

.flex-start{justify-content:flex-start;}
.flex-end{justify-content:flex-end;}
.center{justify-content:center;}
.space-between{justify-content:space-between;}
.space-around{justify-content:space-around;}

align-items

align-items 刚好和 justify-content 相反,align-items 决定了内容元素与整个 Flexbox 的“垂直对齐”位置,再回想一下最上面讲的 Flexbox 盒子模型,具有 cross start 与 cross end 左右两个端点,align-items 与 align-self 就是按照这个方式做设定,设定值总共有下列五个。

  • flex-start:对齐最上面的 cross start
  • flex-end:对齐最下面的 cross end
  • center:垂直居中
  • stretch:预设值,将内容元素全部撑开至 Flexbox 的高度
  • baseline:以所有内容元素的基线作为对齐标准

CSS:

.flex-start{align-items:flex-start;}
.flex-end{align-items:flex-end;}
.center{align-items:center;}
.stretch{align-items:stretch;}
.baseline{align-items:baseline;}
.flex-item{
    width:60px;
    text-align:center;
}
.item1{
    font-size:20px;
    line-height: 60px;
    background:#c00;
}
.item2{
    line-height: 30px;
    background:#095;
}
.item3{
    font-size:30px;
    line-height: 100px;
    background:#059;
}

align-self

align-self 的设定与 align-items 相同,但目的不同,align-self 的作用在于覆盖已经套用 align-items 的属性,如果照我们以前所写,因为 align-items 是针对所有子元素,所以必须要用 align-self 来进行覆盖,我们直接用上一个示例来修改就很清楚了。

CSS:

.item2{
    align-self:baseline;
    line-height: 30px;
    background:#095;
}

align-content

刚刚谈到的 align-items 是针对内容为单行的元素进行处理,如果遇到多行的元素,就要使用 align-content 这个属性,这个属性总共有六个设定值。

  • flex-start:对齐最上面的 cross start
  • flex-end:对齐最下面的 cross end
  • center:垂直居中
  • space-between:将第一行与最后一行分别对齐最上方与最下方
  • space-around:每行平均分配间距
  • stretch:预设值,内容元素全部撑开

CSS:

.flex-start,
.flex-end,
.center,
.space-between,    
.space-around,    
.stretch{
    display:inline-flex;
    flex-wrap:wrap;
    width:180px;
    height:160px;
    margin:5px 5px 40px;
    border:1px solid #000;
    vertical-align: top;
}
.flex-start{align-content:flex-start;}
.flex-end{align-content:flex-end;}
.center{align-content:center;}
.space-between{align-content:space-between;}
.space-around{align-content:space-around;}
.stretch{align-content:stretch;}
.align-content>div{
    padding:15px;
    margin:2px;
    background:#666;
}

flex-wrap

在刚刚的示例看到一个 flex-wrap 的属性,这个属性负责的是让内容的元素换行,因为当我们把父元素的 display 设定为 flex 或 inline-flex 的时候,子元素就是以单行的方式,弹性撑满父元素,所以就要利用 flex-wrap 来换行,共有三个设定值。

  • nowrap:预设值,单行
  • wrap:多行
  • wrap-reverse:多行,但内容元素反转

CSS:

.nowrap,
.wrap,
.wrap-reverse{
    display:inline-flex;
    flex-wrap:wrap;
    width:180px;
    height:80px;
    margin:5px 5px 40px;
    border:1px solid #000;
    vertical-align: top;
}
.column{
    flex-direction:column;
    width:120px;
    height:180px;
}
.nowrap{flex-wrap:nowrap;}
.wrap{flex-wrap:wrap;}
.wrap-reverse{flex-wrap:wrap-reverse;}
.align-content div{
    width:30px;
    height:30px;
    margin:5px;
    background:#069;
}
.column div{background:#f50;}

order

刚刚在 flex-wrap 的属性里头看到了可以把元素反转,order 这个属性更是可以直接指定一个数字,就可以由小到大的排列顺序。

.item{
      width:50px;
      height:60px;
      text-align: center;
      line-height: 50px;
  }
  .order1{
      order:1;
      background:#c00;
  }
  .order2{
      order:2;
      background:#069;
  }
  .order3{
      order:3;
      background:#095;
  }
  .order4{
      order:4;
      background:#f50;
  }
  .order5{
      order:5;
      background:#777;
  }
  .order6{
      order:6;
      background:#077;
  }

flex

好酒沉瓮底,有耐心看到下面的才会看到重点喔哈哈!flex 应该是 Flexbox 里头最重要的属性了,而 flex 其实是由三个属性组合而成,依照先后顺序分别是“flex-grow”、“flex-shrink”和“flex-basis”,如果 flex 只填了一个数值(无单位),那么预设就是以 flex-grow 的方式呈现,至于三个属性的解释如下:

  • flex-grow: 数字,无单位,当子元素的 flex-basis 长度“小”于它自己在父元素分配到的长度,按照数字做相对应的“伸展”比例分配,预设值为 0,不会进行弹性变化,不可为负值,设为 1 则会进行弹性变化。
  • flex-shrink: 数字,无单位,当子元素的 flex-basis 长度“大”于它自己在父元素分配到的长度,按照数字做相对应的“压缩”比例分配,预设值为 1,设为 0 的话不会进行弹性变化,不可为负值。
  • flex-basis: 子元素的基本大小,作为父元素的大小比较基准,预设值为 0,也因为预设值为 0,所以没有设定此属性的时候,会以直接采用 flex-grow 属性,flex-basis 也可以设为 auto,如果设为 auto,就表示子元素以自己的基本大小为单位。

三个属性可以分开设定,也可以合在一起用一个 flex 统一设定,下面的例子展现出同一个 Flexbox,在不同的宽度,子元素会有不同大小的呈现。

HTML:

<div class="flex flex-300">
        <div class="item item1">1</div>
        <div class="item item2">2</div>
</div>
<div class="flex flex-150">
        <div class="item item1">1</div>
        <div class="item item2">2</div>
</div>

CSS:

.flex{
    display:inline-flex;
    height:60px;
    margin:5px 5px 40px;
    border:1px solid #000;
    vertical-align: top;
}
.flex-300{width:300px;}
.flex-150{width:80px;}
.item{
    height:60px;
    text-align: center;
    line-height: 50px;
}
.item1{
    flex:1 2 200px;
    background:#c00;
}
.item2{
    flex:2 1 100px;
    background:#069;
}

如果用动画来表现,可以看出拉长的时候红色会变得比蓝色长,但压缩的时候却是蓝色变得比红色长,如此一来就更能体会 flex 在响应式设计里头的关键角色。

以上就是 Flexbox 的完整介绍,因为有了这个属性,让在做 layout 的布局又更加弹性了!

退出移动版