- flex容器
- 基本特性(同grid容器)
- flex容器与grid容器的富余空间管理对比
- flex-container与其margin
- flex-flow:如何在container中放置item?
- align-items:在容器中统一管理item的富余空间
- flex-item:容器中的每一项
- flex-basis
- 默认值:auto
- flex-basis设置的是item在主轴上的大小
- 与width/height、min/max-width/height
- flex-item与margin
- flex-grow和flex-shrink
- 默认值
- 关于生长和压缩的计算
- flex-grow、flex-shrink针对的也是主轴上怎么进行伸缩
- 和justify/align-content 的比较
- align-self
- 绝对项目与相对项目
- flex和grid总结
- 盒子模型方面
- 富余空间
- 容器富余空间管理
- item富余空间管理
- flex与侧轴
- 其它
- 附表:flex系统中的关键字值和默认值
[toc]
## flex容器
### 基本特性(同grid容器)
关键词:`独占一行`、`margin自动填充`
首先设置了`display:flex`元素容器并不会改变它本身的盒子模型(不会转换为border-box什么的,和grid-container是一致的)。
![](https://box.kancloud.cn/4aed642a9851309cd34e7eebc38dbfc8_754x436.png)
![](https://box.kancloud.cn/9e51576dfed396602655a853c0cb86e4_800x168.png)
### flex容器与grid容器的富余空间管理对比
flex容器和grid容器的富余空间管理**都是**针对flex/grid容器**所开辟的空间**的。
flex容器的富余空间是指除去所有flex-item项所占据的空间外的剩余空间。
![](https://box.kancloud.cn/acbb413dc121d9dcaa565047173ba67c_800x168.png)
>[danger] **注意:** 富余空间并不是图中`flex-container`的margin部分。
grid容器的富余空间是指除去grid网格外的剩余空间(注意,不是gird-item,嗯,是所有grid-item的集合再加上grid-gap)
![](https://box.kancloud.cn/c9a190077d7dbc9aa8f09871d2cf6bb4_831x321.png)
>[danger] **注意:** 富余空间并不是图中`grid-container`的margin部分。
---
上面我们知道了富余空间是什么,那么怎么操作富余空间呢,
我们可以通过`justify-content/align-content`(grid/flex都有)来操作父容器的富余空间
另外在API记忆上,flex和grid系统一样都些个类似的属性**值**,它们对应的效果分别是:
- 靠左 grid是start flex要带前缀 flex-start
- 居中 都是center
- 靠右 grid是end flex要带前缀 flex-end
- 让每一个item大小一样(space-around)
- 第一个和最后一个item分别占据容器开辟的空间的首尾,中间的item之间间距相等(space-between)
- space-evenly:让每个item之间的间距相等(包括首尾)
以上是几个最常用的,除此之外还有很多[点我](https://developer.mozilla.org/en-US/docs/Web/CSS/align-content)
还需要注意的一点是,grid的align/justify-content都还有一个`stretch`的值(虽然貌似毫无卵用)
,而**flex**只有align-content有这个值,且这个值是align-content的**初始值**。
### flex-container与其margin
我们已经知道一旦元素设置了`display:flex`就会成为一个`flex-container`,它会独占一行,且如果border-box的大小不足以独占一行会用margin填充。
So我们仍然可以对`flex-container`使用`margin:auto`来使其居中什么的。
![](https://box.kancloud.cn/20c619c517e5057af834e3f699b26c6e_808x165.png)
> **再次强调:** 请注意区分flex-container的富余空间和margin,他们并不是同一个东西
### flex-flow:如何在container中放置item?
`flex-flow`是`flex-direction`和`flex-wrap`的复合起来的属性。
其中flex-direction决定的是内部item是从左往右排列(row)还是从上往下排列(column),**一旦决定了direction,我们也就顺道决定了这个flex的主轴**
![](https://box.kancloud.cn/4ff8fa68cbf504a03f2106dbfa0e4251_1084x510.png)
而flex-wrap决定的是item排列时,若空间不够了,换不换行。(若不换行就会被压缩)
并且这两个属性都值都可以添加一个`-reverse`后缀,这表示颠倒排列的顺序。
### align-items:在容器中统一管理item的富余空间
`align-items` 这个属性能统一处理item中的**侧轴的**富余空间。(**注意是item自己内部的富余空间**)
注意,这个属性并不能对某个item进行订制,而是会对所有item的富余空间进行相同的安排(操作)。
另外它和grid系统的api不同,这货**只有**`align-items`,是的,只有,**并没有`justify-items`!!**。(grid是有的)
MDN官网截图为证
![](https://box.kancloud.cn/311bfc00da1710c37de756aef77c9e5e_829x279.png)
## flex-item:容器中的每一项
### flex-basis
#### 默认值:auto
一个flex-item的基础大小,默认值为`auto`,也就是每个item自己的内容大小。
需要注意的是,flex-item并不像gird-item,它并不是一个margin-box,而是一个正常的盒模型。
![](https://box.kancloud.cn/3274b1abf0fdf2516065ed4fb8255fd7_350x240.png)
#### flex-basis设置的是item在主轴上的大小
flex-basis指定并不一定是一个item的宽度,确切的说它决定的是一个item在主轴上的长度。
例如我们将`flex-direction`设置为`column`时(主轴变更为y轴)
![](https://box.kancloud.cn/df1a52127bab468c7517003413e1e65b_691x205.png)
#### 与width/height、min/max-width/height
嘛,其实basis就是width or height(根据主轴不同,有肯能是width也有可能是height)。
当设置了basis你最好就不要再设置width or height,嗯,貌似有什么兼容性bug一类的。
另外你最好也不要给这些item设置border、padding、margin,特别是当你想要使用grow或则shrink的时候,这会导致效果的不可预期。
### flex-item与margin
给flex-item设置相应的margin auto能达到和justify-content相同的效果,不过这样的话,父容器若还有justify-content就不再影响到flex-item了。
![](https://box.kancloud.cn/c01c2d655502bdd595eb95e165f5b0d8_808x283.png)
### flex-grow和flex-shrink
嗯,这是整个flex布局中最精华的部分了,正是因为这两个属性,才让Flex所代表的**伸缩**二字名副其实。
#### 默认值
```
flex-grow:0;
flex-shrink:1;
```
其中grow是生长的意思,shrink是压缩的意思,默认情况下,item不会生长(即使存在富余空间),但是会被压缩(flex-container开辟的空间<items所占据的空间时)
#### 关于生长和压缩的计算
当设置了生长时,每个item增加的大小是按照下面这样一个计算公式来计算的
```
可用空间 =(容器大小 - 所有相邻项目flex-basis总和)
每项伸缩大小 = 伸缩基准值 + ((可用空间 / 所有相邻项目flex-grow总和) x 此项的flex-basis值)
```
而压缩时,是按照下面这样计算的
```
//假如tem1-4的basis依次为100、200、200、200
//item1-4的shrink依次为1、2、3、1
所有项目之和 = 项目一(1x100) + 项目二(2x200) + 项目三(3x200) + 项目四(1 x 200) = 所有项目总和(1400)
项目二收缩因数 = 项目二(2 x 200px)/所有项目之和(1400) = 0.286
第二项移除空间 = 项目二收缩因数(0.286) x 负可用空间(-200px) = -57.142向下舍入为57。
```
##### flex-grow、flex-shrink针对的也是主轴上怎么进行伸缩
#### 和justify/align-content 的比较
首先justify/align-content是针对**flex容器的**富余空间的,
而`flex-grow`其实也是针对的其父,flex容器的,只不过相较于`justify-content`只是分配富余空间给item,它是对富余空间的利用的另外一种形式,它会消耗掉富余空间。
虽然说justify-content/align-content中的`stretch`也能达到差不多的效果,但它们最主要的作用还是分配富余空间给每个item。
另外flex-grow **并不能影响侧轴**(的富余空间),`align-content`才能,并且它的默认值为`stretch`(也就是会让item铺满整个侧轴的富余空间)。
实际上关于侧轴的富余空间,因为flex只是一个一维布局,所以要是侧轴的富余空间被消耗,只会存在一种效果,那就是**stretch平铺**(**侧轴上只会有一个item**)。
---
而`flex-shrink`的功效则和富余空间完全没有关系,它是当父容器(flex-container)开辟的空间不够用的时候的选择。默认情况下,它会等比例的压缩所有item。
### align-self
首先要声明的一点是,在flex系统中,我们只能管理flex-item侧轴上的富余空间,so只有align-self这一个api没有什么justify-self!!
相较于align-item,align-self能允许我们单独管理某一个item中的富余空间
![](https://box.kancloud.cn/20a33238cec2daf53b71c5ce3eb498f1_720x421.png)
### 绝对项目与相对项目
> 相对项目
当`flex:auto`,即`flex:1 1 auto`时,flex-item既可伸又可缩,但它的实际宽度是基于basis之上的。
![](https://www.w3cplus.com/sites/default/files/blogs/2017/1702/understanding-flexbox-60.png)
> 绝对项目
当`flex:1`,即`flex: 1 1 0`时,flex-item既可伸又可缩,并且它的basis为0,**这意味着flex-item的宽度只基于flex的生长**。
![](https://www.w3cplus.com/sites/default/files/blogs/2017/1702/understanding-flexbox-61.png)
## flex和grid总结
### 盒子模型方面
>相同之处:
flex系统的flex-container和grid系统的grid-container一样,都会让元素起到block化的效果独占一行(如果手动设定了固定宽度,不够一行的部分会被margin填充)
>不同之处:
grid系统的grid-item你可以把它当做一个`margin-box`(不乱给grid-item设置grid系统中没什么意义的宽高的话)
而flex系统的flex-item只是一个普通的盒子模型。
### 富余空间
#### 容器富余空间管理
>相同之处:
都能够用`justify-content`、`align-content`管理container父容器的富余空间。
>不同之处:
1. grid的富余空间是除却网格的部分,这里的网格,不仅包括每一项item,**还包括网格的gap**。
2. flex系统中justify-content和align-content的start、end不叫start、end而叫`flex-start`和`flex-end`。
3. flex系统中只有`align-content`有`stretch`值,而grid系统中justify-content和align-content都有?(但貌似grid justify-content的stretch无效?可以在template的时候使用fr达到stretch效果,或则在template中只用grid-line分区)
4. flex系统还能通过在item上设置grow来利用富余空间,虽然只是主轴上的富余空间,侧轴上的仍然需要使用align-content。
#### item富余空间管理
flex的item只能进行侧轴上的富余空间管理。
它只有align-self,而没有justify-self
#### flex与侧轴
flex系统中的侧轴默认是平铺的`stetch`,不论是`align-content`还是`align-item`,flex-item在侧轴上永远是从头躺到尾。
### 其它
grid系统中的主轴侧轴并不会发生交换,主轴永远是x轴,侧轴永远是y轴。
## 附表:flex系统中的关键字值和默认值
>flex:none | <' flex-grow '> <' flex-shrink >'? || <' flex-basis '>
如果「flex: 0 auto」或者「flex: initial」, 则其计算值为「0 1 auto」,即「flex」**默认值**
如果缩写「flex: 1」, 则其计算值为「1 1 0%」
如果缩写「flex: auto」, 则其计算值为「1 1 auto」
如果「flex: none」, 则其计算值为「0 0 auto」
>flex-grow:<number>
默认值:flex-grow:0
>flex-shrink:<number>
默认值:flex-shrink:1
>flex-basis:<length> | <percentage> | auto | content
默认值 flex-basis:auto
`<length>`:用长度值来定义宽度,不允许负值
`<percentage>`:用百分比来定义宽度,不允许负值
`auto`:无特定宽度值,取决于其它属性值
`content`:基于内容自动计算宽度
>flex-flow:<' flex-direction '> || <' flex-wrap '>
flex-direction:row | row-reverse | column | column-reverse
默认:row
flex-wrap:wrap | wrap-reverse | nowrap | nowrap-reverse
默认:nowrap
>justify-content:flex-start | flex-end | center | space-between | space-around
默认值 :flex-start
> align-content:flex-start | flex-end | center | space-between | space-around | stretch
默认值:stretch
>align-items:flex-start | flex-end | center | baseline | stretch
默认值:stretch
>align-self:auto | flex-start | flex-end | center | baseline | stretch
默认值:auto
>order:<integer>
默认值0,可以为负值