细说BFC
1、BFC是什么?
BFC: Block Formatting Context, 名为 "块级格式化上下文"
2、BFC特点?
BFC是一个完全独立的空间
BFC空间里子元素,不影响外面布局。
3、BFC如何触发
- 根元素
- display: inline-block、table-cell、flex
- float: 不为none
- position: absolute、fixed
- overflow:非visible
1、visible
2、hidden
3、auto
4、scroll
5、inherit
记忆公式:
BFC = OFDP // overflow float display postion
4、BFC效果
- 内部的浮动元素高度也会被算上
- 内部不影响外部也不被外部元素影响,但是内部元素该怎么排列还是怎么排列
- 内部左右margin不会合并坍塌
- 同一个BFC相互影响
5、BFC使用场景
5.1、解决高度坍塌问题(Demo-15)
.wrap{
overflow: auto;
width: 500px;
margin-bottom: 20px;
}
.wrap1{
border: 2px solid black;
}
.wrap2{
border: 2px solid black;
overflow: auto;
}
.box1{
float: left;
width: 50px;
height: 50px;
background-color: greenyellow;
}
<div class="wrap">
<span>没触发BFC,Float浮动元素,容器没有高度</span>
<div class="wrap1">
<div class="box1"></div>
</div>
</div>
<div class="wrap">
<span>触发BFC,Float浮动元素,容器有高度</span>
<div class="wrap2">
<div class="box1"></div>
</div>
</div>
注意:本例子只讨论容器,不讨论box1是否触发BFC
容器wrap1,因为子元素float脱离文档流,高度不算,所以容器wrap1只有border,容器没被撑开;
容器wrap2,子元素float脱离文档流,但是容器wrap2设置了overflow:auto,触发了BFC; 所以浮动元素的高度也会被计算,所以容器被撑开了
PS:文档流中,父元素的高度默认被子元素撑开,子元素浮动,脱离文档流没法撑开父元素高度,导致高度坍塌
5.2、解决margin重叠问题(Demo-16)
margin重叠:兄弟元素,垂直方向上下margin会合并,取较大值,水平不会
<div class="wrap">
<div class="wrap1">
<div class="box1"></div>
<div class="box2"></div>
</div>
<div class="wrap2">
<div class="box3"></div>
<div class="wrap3">
<div class="box4"></div>
</div>
</div>
</div>
.wrap{
display: flex;
}
.wrap1{
width: 300px;
height: 300px;
border: 2px solid black;
margin-right: 20px;
}
.wrap2{
width: 300px;
height: 300px;
border: 2px solid black;
overflow: auto;
}
.wrap3{
overflow: auto;
}
.box1{
width: 50px;
height: 50px;
background-color: red;
margin-bottom: 50px;
}
.box2{
width: 50px;
height: 50px;
background-color: black;
margin-top: 40px;
}
.box3{
width: 50px;
height: 50px;
background-color: red;
margin-bottom: 50px;
}
.box4{
width: 50px;
height: 40px;
background-color: red;
margin-top: 50px;
}
1、box1设置了margin-bottom: 50px; box2设置了margin-top: 40px; 二者实际的margin只有50px,说明二者margin合并了且显示比较大的值
2、右图box3和box4设置同样的margin,但是间距明显大很多,是因为利用了BFC,box3和box4属于不同BFC(box4属于wrap3这个BFC),所以解决了margin合并问题
我们需要知道这个知识点,但是实际没必要这么做:第一改变了HTML结构,第二直接通过margin合并取最大值这一特点就可以解决
5.3、解决margin坍塌问题(Demo-17)
margin塌陷:父子元素,垂直方向的margin会取较大值
<div class="wrap">
<div class="wrap1">
<div class="box1">box1</div>
</div>
<div class="wrap2">
<div class="box2">box2</div>
</div>
</div>
</div>
.wrap{
width: 400px;
background-color: yellowgreen;
margin:5px;
border:2px solid yellowgreen;
}
.wrap1{
width: 300px;
height: 300px;
margin-right: 20px;
margin-top: 70px;
background-color: red;
}
.box1{
width: 50px;
height: 50px;
margin-top: 50px;
background-color: black;
color:white
}
.wrap2{
width: 300px;
height: 300px;
margin-top: 70px;
background-color: red;
overflow: hidden;
}
.box2{
width: 50px;
height: 50px;
margin-top: 50px;
background-color: black;
color:white
}
box1的margin-top:50px,并未生效,就是因为margin坍塌导致的;
box2的margin-top:50px,生效了,是因为box2的父容器wrap2设置了overflow: hidden,触发了BFC
【 知识补充,margin塌陷 】
父盒子若同时满足下面3个条件:
1、父盒子里面没有文字
2、父盒子没有边框(border)
3、父盒子没有padding-top
给子元素设置margin-top的时候,就会产生margin坍塌:父子元素,垂直方向的margin会取较大值
- 水平方向margin不会重叠
<div class="wrap">
<div class="box1">box1</div>
<div class="box2">box2</div>
</div>
.wrap{
width: 400px;
background-color: yellowgreen;
margin:5px;
border:2px solid yellowgreen;
display: flex;
}
.box1{
width: 50px;
height: 50px;
margin-right: 50px;
background-color: black;
color:white
}
.box2{
width: 50px;
height: 50px;
margin-left: 50px;
background-color: black;
color:white
}