如下从浮动
到BFC
的段落 摘自MDN 网络开发者css
float CSS属性指定一个元素应沿其容器的左侧或右侧放置,容许文本和内联元素环绕它。该元素从网页的正常流动中移除,尽管仍然保持部分的流动性(与绝对定位相反)。html
一个浮动元素是float的值不为none的元素。前端
/* Keyword values */ float: left; float: right; float: none; float: inline-start; float: inline-end; /* Global values */ float: inherit; float: initial; float: unset;
因为float意味着使用块布局,它在某些状况下修改display
值的计算值:git
指定值 | 计算值 |
---|---|
inline |
block |
inline-block |
block |
inline-table |
table |
table-row |
block |
table-row-group |
block |
table-column |
block |
table-column-group |
block |
table-cell |
block |
table-caption |
block |
table-header-group |
block |
table-footer-group |
block |
flex |
flex , 可是float对这样的元素不起做用 |
inline-flex |
inline-flex , 可是float对这样的元素不起做用 |
other | unchanged |
备注:若是要在 JavaScript 中把float属性看成element.style
对象的一个成员来操做,那么在Firefox 34 和更老的版本中,你必须拼写成cssFloat。另外还要注意到在 Internet Explorer 8 和更老的IE当中,要使用styleFloat
属性。这是DOM驼峰命名和CSS所用的连字符分隔命名法对应关系中的一个特例(这是由于在 JavaScript 中"float"是一个保留字,由于一样的缘由,"class"被改为了"className" 、"for"被改为了"htmlFor")。github
float
属性的值被指定为单一的关键字,值从下面的值列表中选择。web
left
canvas
代表元素必须浮动在其所在的块容器左侧的关键字。浏览器
right
网络
代表元素必须浮动在其所在的块容器右侧的关键字。app
none
代表元素不进行浮动的关键字。
inline-start
关键字,代表元素必须浮动在其所在块容器的开始一侧,在ltr脚本中是左侧,在rtl脚本中是右侧。
inline-end
关键字,代表元素必须浮动在其所在块容器的结束一侧,在ltr脚本中是右侧,在rtl脚本中是左侧。
left | right | none | inline-start | inline-end
例子
<style type="text/css"> div { border: solid red; max-width: 70ex; } h4 { float: left; margin: 0; } </style> <div> <h4>HELLO!</h4> This is some text. This is some text. This is some text. This is some text. This is some text. This is some text. This is some text. This is some text. This is some text. This is some text. This is some text. This is some text. </div>
正如咱们前面提到的那样,当一个元素浮动以后,它会被移出正常的文档流,而后向左或者向右平移,一直平移直到碰到了所处的容器的边框,或者碰到另一个浮动的元素。
在下面的图片中,有三个红色的正方形。其中有两个向左浮动,一个向右浮动。要注意到第二个向左浮动的正方形被放在第一个向左浮动的正方形的右边。若是还有更多的正方形这样浮动,它们会继续向右堆放,直到填满容器一整行,以后换行至下一行。
在前面的例子当中,浮动的元素的高度比它们所在的容器元素(是块元素)的高度小。然而若是块元素内的文本过短,不足以把块元素的大小撑到高度大于全部浮动元素的高度,咱们可能会看到意想不到的效果。例如,若是上面图片中的文字只有"Lorem ipsum dolor sit amet,",而且接下来是另一个和"Floats Example"这个标题同样风格的标题元素,那么第二个标题元素会出如今红色的正方形之间。然而在大多数这种状况下,咱们但愿这个标题元素是靠左对齐的。为了实现这个效果,咱们须要清除浮动。
这个例子中,最简单的清除浮动方式就是给咱们想要确保左对齐的新标题元素添加clear
属性:
h2.secondHeading { clear: both; }
然而这个方法只是在同一块级格式化上下文(block formatting context)中没有其余元素的时候才是有效的。若是咱们的 H2
有兄弟元素是向左浮动和向右浮动的边栏,那么使用clear
会致使这个标题元素出如今边栏的下方,这显然不是咱们指望的结果。
若是不能使用清除浮动,另外一种作法是浮动容器的限制块级格式化上下文。再次列举上面的例子,有三个红色的正方形和一个P
元素。咱们能够设置P
元素的overflow
属性值变成hidden
或者auto
,由于这样可让容器元素伸展到可以包含红色正方形,而不是让他们超出块元素的底部。
p.withRedBoxes { overflow: hidden; height: auto; }
Note: 设置overflow
为scroll
也可让块元素撑大来包含全部的浮动子元素,可是这样不论内容有多少都会显示出一个滚动条。即便 height
默认值为 auto
,咱们仍是设置了,是为了代表容器应该增大高度以便包裹住里面的内容。
clear
CSS 属性指定一个元素是否能够在它以前的浮动元素旁边,或者必须向下移动(清除浮动) 在它的下面。clear 属性适用于浮动和非浮动元素。
clear: none; clear: left; clear: right; clear: both; clear: inline-start; clear: inline-end; clear: inherit;
当应用于非浮动块时,它将非浮动块的边框边界移动到全部相关浮动元素外边界的下方。这个行为做用时会致使margin collapsing不起做用。
当应用于浮动元素时,它将元素的外边界移动到全部相关的浮动元素外边界的下方。这会影响后面浮动元素的布局,后面的浮动元素的位置没法高于它以前的元素。
要被清除的相关浮动元素指 在相同块级格式化上下文中的前置浮动。
注释:若是你想要一个元素将全部浮动元素包含在内,你既能够将这个容器设置为浮动,又能够经过 ::after
伪元素设置clear属性
做为替代。
/* best practical*/ /* old */ .clearfix:before, .clearfix:after{ overflow: hidden; display: table; visibility: hidden; content: ''; clear: both; } /* new */ .clearfix::before, .clearfix::after{ overflow: hidden; display: table; visibility: hidden; content: ''; clear: both; } /* new clearfix */ .clearfix::after { content: ""; display: table; clear: both; overflow: hidden; visibility: hidden; } /* old clearfix */ .clearfix:after { content: ""; display: block; clear: both; }
clear: none clear: left clear: right clear: both clear: inherit
none
元素不会向下移动清除以前的浮动。
left
元素被向下移动用于清除以前的左浮动。
right
元素被向下移动用于清除以前的右浮动。
both
元素被向下移动用于清除以前的左右浮动。
inline-start
inline-start是一个关键字,
表示该元素向下移动以清除其包含块的起始侧上的浮动。即在某个区域的左侧浮动或右侧浮动。
inline-end
inline-end
是一个关键字,表示该元素向下移动以清除其包含块的末端的浮点,`即在某个区域的右侧浮动或左侧浮动。
注意: 给div添加'wrapper'类,使其添加一个边框,以便更好观察到实体的此属性被清除。
HTML Content
<div class="wrapper"> <p class="black">Lorem ipsum dolor sit amet, consectetuer adipiscing elit. Phasellus sit amet diam. Duis mattis varius dui. Suspendisse eget dolor.</p> <p class="red">Lorem ipsum dolor sit amet, consectetuer adipiscing elit.</p> <p class="left">This paragraph clears left.</p> </div>
CSS Content
.wrapper{ border:1px solid black; padding:10px; } .left { border: 1px solid black; clear: left; } .black { float: left; margin: 0; background-color: black; color: #fff; width: 20%; } .red { float: left; margin: 0; background-color: red; width:20%; } p { width: 50%; }
若是上例中,样式中的float: left 都改成了float:right的话,则相应clear: right。
而若是左浮动和右浮动都有的样式,则clear: both。(both:二者)
块格式化上下文(Block Formatting Context,BFC) 是Web页面的可视化CSS渲染的一部分,是布局过程当中生成块级盒子的区域,也是浮动元素与其余元素的交互限定区域。
下列方式会建立块格式化上下文:
根元素或包含根元素的元素。
浮动元素(元素的 float
值不是 none
)。
绝对定位元素(元素的 position
(position属性用于指定一个元素在文档中的定位方式。top,right,bottom 和 left 属性则决定了该元素的最终位置。) 为 absolute
(绝对定位)或 fixed
(固定定位)。
行内块元素(元素的 display
为 inline-block
。
表格单元格(元素的 display
为 table-cell
,HTML表格单元格默认为该值)
表格标题(元素的 display
为 table-caption
,HTML表格标题默认为该值)
匿名表格单元格元素(元素的 display
为 table、``table-row
、 table-row-group、``table-header-group、``table-footer-group
(分别是HTML table、row、tbody、thead、tfoot的默认属性)或 inline-table
)
overflow
值不为 visible
的块元素。
display
值为 flow-root
的元素。
contain
值为 layout
、content
或 strict
的元素。
弹性元素(display
为 flex
或 inline-flex
元素的直接子元素)
网格元素(display
为 grid
或 inline-grid
元素的直接子元素)
多列容器(元素的 column-count
或 column-width
不为 auto,包括 ``column-count
为 1
)
column-span
为 all
的元素始终会建立一个新的BFC,即便该元素没有包裹在一个多列容器中( 标准变动,Chrome bug)。
建立了块格式化上下文的元素中的全部内容都会被包含到该BFC中。
块格式化上下文
对浮动定位
与清除浮动
都很重要。浮动定位和清除浮动时只会应用于同一个BFC内的元素。浮动不会影响其它BFC中元素的布局,而清除浮动只能清除同一BFC中在它前面的元素的浮动。外边距折叠
(Margin collapsing)也只会发生在属于同一BFC的块级元素之间。
如下开始,就不是摘自MDN,而是换成摘自博客园小马哥&的相关博文,再加以整理和添加本身的一点思路而成。
级别 | 元素 |
---|---|
行内元素 | a,b,strong,span,img,label,button,input,select,textarea |
块级元素 | header,form,ul,ol,table,article,div,hr,aside,figure,canvas,video,audio,footer |
web网页的制做,就像是一个“流”,从上而下,像“织毛衣”。
标准文档流下的微观现象:
标准流里面的限制很是多,致使不少页面效果没法实现。若是咱们如今就要并排、而且就要设置宽高,那该怎么办呢?办法是:移民!脱离标准流!
css中一共有三种手段,使一个元素脱离标准文档流:
按布局来讲,通常都不会是一个盒子单独浮动起来,每每是横向区域的盒子一块儿浮动。且为了避免影响接下来的文档标准流,每每也要收尾作出清除浮动。
在页面布局的时候,每一个结构中的父元素的高度,咱们通常不会设置。(为何?)
试想一想,若是我初版的页面的写完了,感受很是爽,忽然隔了一个月,产品经理说页面某一块的区域,须要加点内容,或者以为图片要缩小一下。这样的需求在工做中很是常见的。真想打他啊。那么此时做为一个前端小白,确定是去每一个地方加内容,改图片,而后修改父盒子的高度。那问题来了,这样不影响开发效率吗?答案是确定的。
因此父盒子咱们通常不设置高度,而由子元素的内容去撑起父盒子的高度。那么当这个子元素是浮动的时候,父盒子没有高度,浮动子元素是不会填充父盒子的高度的,这个时候就会有下一栏的盒子跑过来到浮动子元素的下面被覆盖摭挡了,很是影响页面布局。
浮动元素确实能实现咱们页面元素并排的效果,这是它的好处,但同时它还带来了页面布局极大的错乱!!!因此咱们要在浮动完以后再作一步清除浮动的操做(并不影响浮动子元素以前的布局,只是为了下排的布局不乱。)
.clearfix:after{ /*要写这三句话去实现*/ content: '.'; clear: both; display: block; }
值 | 描述 |
---|---|
visible | 默认值。内容不会被修剪,会呈如今元素框以外。 |
hidden | 内容会被修剪,而且其他内容是不可见的。 |
scroll | 内容会被修剪,可是浏览器会显示滚动条以便查看其他的内容。 |
auto | 若是内容被修剪,则浏览器会显示滚动条以便查看其他的内容。 |
inherit | 规定应该从父元素继承 overflow 属性的值。 |
逐渐演变成overflow:hidden清除法。其实它是一个BFC区域。
end 2018-06-01