Block Formatting Contexts(BFC)

2012年3月16日

Block Formatting Contexts(简称BFC)在页面构建中,我觉得是比较重要的东西,如果对它做过深入了解,一些各浏览器部分奇怪的BUG也会迎刃而解。W3C中对BFC做了个解释。在可视化格式模型中,BFC扮演了很重要的角色,它决定了元素如何对其内容进行定位,以及与其他元素的关系和相互作用。所以对于页面构建者来说,理清flow,floats,clear和margins之间的关系,对它们有些深入理解是很重要的事。
要触发BFC,至少要满足以下一个条件:

那BFC到底有什么特别的地方呢?

在创建了 Block Formatting Context 的元素中:

其子元素会一个接一个地放置。垂直方向上他们的起点是一个包含块的顶部,两个相邻的元素之间的垂直距离取决于 ‘margin’ 特性。在BFC中相邻的块级元素的垂直边距会折叠(collapse)。
每一个元素左外边与包含块的左边相接触(对于从右到左的格式化,右外边接触右边), 即使存在浮动也是如此(尽管一个元素的内容区域会由于浮动而压缩),除非这个元素也创建了一个新的BFC(这种情况这个元素由于浮动本身就会变得更窄)。
通过以上可以总结出两点:

  1. BFC可以包含浮动元素,并且不会和浮动元素重叠。
  2. BFC里面的元素的垂直边距不会和BFC的外边距叠加。

在IE 6中, hasLayout创建(或多或少)了一个BFC。在这里先不讨论有关haslayout的一些知识了。
关于BFC的一些误区:

以前在网上看到有人总结说BFC可以阻止边距叠加,这种说法太绝对了,比如如下:
box A
box B

div{overflow:hidden;margin:10px;}

这时候A、B的边距还是会叠加的,是10px。但是如果样式是这样的话:

div{float:left:margin:10px;}

div{display:inline-block;margin:10px;}

A、B的边距就是20px了,此时就没出现边距叠加。其实这里会叠加的margin是BFC里的子元素的margin和它的叠加(即第一个节点的margin-top和最后一个节点的margin-bottom),不会影响到BFC自身的叠加。这时有人会以为,这里是因为创建了BFC,所以才阻止了边距叠加。其实这时候边距不叠加是它本身没有满足W3C中关于边距叠加的条件

2个元素边距叠加发生的条件是:

所以上述的两个A、B模块显然是没有满足第一个条件,所以不会发生边距叠加,与它是不是BFC模块无关。参考文章:http://www.css-101.org/block-formatting-contexts/index.php