# Flex 布局(下)

《上篇》中的 4 个属性:flex-direction、flex-wrap、justify-content、align-items ,都是在 flex container(容器,即父元素)身上的,而接下来的几个属性,则是用在 flex item(项,即子元素)身上的。

# 1. align-self

为某一个 item 指定 align-self ,可以让不遵守父容器的 align-items 属性,从而让它和 “它的兄弟们” 显得与众不同。

即,item 的 align-self 的设置会覆盖其继承自 container 的 align-items 。

例如,它的兄弟们遵照父元素的设置都对其交叉轴的起始,而其中某个孩子却位于交叉轴的末端。

[flex-13.png]

.item {
    align-self: auto | flex-start | flex-end | center | baseline | stretch;
}

# 2. flex-grow

flex-grow 用来设置当前 item 的放大比例。默认为 0,即如果存在剩余空间,也不放大。

注意

当 flex-grow “起作用” 时,子元素的宽度就不是你所指定的子元素的 width 的值那么宽了,它会被拉长。

有这样一种很常见情况,container 中的所有的 item 的长度都没 “占满” container 的长度,那么很显然,父元素 container 的剩下的、多余的长度为:

剩余空间 = 父宽 - 子1宽 - 子2宽 - 子3宽 - ...

默认情况下,各个子元素的 flex-grow 的值都是 0 ,这种情况下,各个子元素都会对父元素的剩余空间视而不见。父元素的剩余空间空着也就空着了。

如果有一个或多个子元素设置了 flex-grow ,且值为非零,那么 flex 会把各个子元素的 flex-grow 的值累加起来,然后将父元素的剩余空间按 x/N 分配给各个子元素,从而 “消灭” 掉父元素的剩余空间。

TIP

这个思路和负载均衡中的权重的逻辑一样。

.item {
  flex-grow: <number>; /* default 0 */
}

注意

这种情况下,各个相关子元素的 width 会被拉长,不再是你当初指定的 width 那么长了。

最极端的情况是,有且仅有一个子元素设置了 flex-grow: 1,其他子元素没有设置,即 flex-grow: 0,这种情况下父元素的所有剩余空间就都 “给” 那一个元素。

# 3. flex-basis

子元素的 flex-basis 属性是子元素 width 属性的替代品,它和 width 属性一样,值为具体的数字或 auto 。

.item {
  flex-grow: <number>; /* default 0 */
}

之所以 “多此一举” 又弄出一个一摸一样作用的属性来替代 width 属性是一因为在前面 flex-grow 属性中,大家也能感觉到:使用 width 属性有点 “奇怪” ,因为当你指定了一个子元素的 width 之后,它的实际的 width 可能和你指定的不一样!它可能会被拉长(也有可能会被压缩)

因此,CSS 提出了一个语义更合理的属性来替代 flex item 的 width 属性值,从而让这个宽度的设置不那么 “别扭” 。

# 4. flex-shrink

flex-shrink 和 上面的 flex-grow 的作用类似,只不过它是用在父容器宽度不够的情况下,压缩子元素的。

如果 父宽 < 子1宽 + 子2宽 + 子3宽 + ... ,而且,你又没有使用 flex-wrap 来要求子元素(沿交叉轴)换行,那么父元素 “欠” 下的宽度就需要从子元素那里 “补” 出来。

即,这种情况下,子元素的实际宽度会小于你当初设置的 width(这也是在 flex 中使用 flex-basis 来代替 width 的原因,省得你想着 “别扭”)

各个子元素的 flex-shirnk 的属性值默认为 1 ,即,当父元素的宽度不够(且又不让换行)时,各个子元素被压缩,分摊父元素不够的宽度的 1/N 。

.item {
  flex-shrink: <number>; /* default 1 */
}

如果有某个(或某些个)子元素的 flex-shirnk 被设为 0 ,那意味着它(或它们)不参与为父元素 “还债” 的过程。

# 5. 三合一属性:flex

flex 属性是 flex-grow, flex-shrink 和 flex-basis 的简写,默认值为 0 1 auto 。后两个属性可选。

.item {
  flex: none | [ <'flex-grow'> <'flex-shrink'>? || <'flex-basis'> ]
}

该属性有两个快捷值:

  • auto:等同于 1 1 auto
  • none:等同于 0 0 auto