BFC、IFC、GFC、FFC

BFC

BFC是浏览器在践行渲染标准的时候的术语。为什么这么说呢?

BFC有几个参数组成:
1、Box:css布局的基本单位。
Box是css布局的对象和基本单位。直观来说,就是一个页面是由很多个Box组成的。元素的类型和display属性,决定了这个Box的类型。不同类型的Box,会参与不同的Formating Context(一个决定如何渲染文档的容器),因此Box内的元素会以不同的方式渲染。我们就可以把Box称为盒。

2、盒子的种类:
box-level 分为block-level和inline-level两种。
block-level: display属性为block,list-item,table的元素,会生成block-level box,并且参与block formating context。
inline-level: display属性为inline,inline-block,inline-table的元素,会生成inline-level box,并且参与inline formating context。
注意: 行内元素永远是行内元素,块级元素永远是块级元素,即使使用样式把行内元素改为块级元素,但在渲染的时候还是按照是行内元素来渲染。

3、Formating Context
Formating Context是W3C css2.1规范中提出的一个概念,它是页面中的一块渲染区域,并且有一套渲染规则,它决定了其子元素如何定位,以及和其他元素的关系和相互作用。最常见的Formating Context是Bolck Formating Context(简称BFC)和Inline Formating Context(简称IFC)。

4、哪些元素会生成BFC?

  • 根元素;
  • float属性不为none;
  • position属性为absolute和fixed;
  • display为inline-block,table-cell,table-caption,flex,inline-flex;
  • overflow不为visible

5、示例


<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Documenttitle>
    <style type="text/css">
        /* 此时body根元素就生了一个BFC */

        body {
            width: 300px;
            position: relative;
        }

        .aside {
            width: 100px;
            height: 150px;
            float: left;
            background: #ffbbbb;
        }

        .main {
            width: 200px;
            height: 100px;
            background: #dddddd;
        }
    style>
head>

<body>
    <div class="aside">asidediv>
    <div class="main">maindiv>
body>

html>

此时效果:
BFC、IFC、GFC、FFC_第1张图片

aside浮动脱离文档流,同时也生成了BFC,main正常,此时main与aside部分重叠。
我们对css部分进行修改:

.main {
            width: 200px;
            height: 100px;
            background: #dddddd;
            overflow: hidden;/*修改操作:新增*/
        }

此时的效果:
BFC、IFC、GFC、FFC_第2张图片

通过触发main生成BFC,此时aside与main不再重叠,实现了自适应两栏布局。

上述的依据原理:
BFC布局规则:
1、每个元素的margin box的左边,与已包含border box的左边相接触(对于从左往右的格式,否则相反),即便存在浮动也是如此。
2、BFC区域不会与float box重叠。

6、清除内部浮动


<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Documenttitle>
    <style type="text/css">
        .far {
            width: 300px;
            border: 5px solid #ffcccc;
        }

        .child {
            border: 5px solid #ffcccc;
            width: 100px;
            height: 100px;
            float: left;
        }
    style>
head>

<body>
    <div class="far">
        <div class="child">div>
        <div class="child">div>
    div>
body>

html>

效果:
BFC、IFC、GFC、FFC_第3张图片

此时child浮动,脱离文档流,far没有高度。
一般我们这么修改:

.far {
            width: 300px;
            border: 5px solid #ffcccc;
            overflow: hidden;
        }

此时效果:
BFC、IFC、GFC、FFC_第4张图片
此时far生成BFC,那么far在计算高度时,far内的浮动元素child也会参与计算。

上述依据:
计算BFC高度时,浮动元素也会参与计算。

7、防止垂直margin重叠


<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <meta http-equiv="X-UA-Compatible" content="ie=edge">
    <title>Documenttitle>
    <style type="text/css">
        p {
            width: 200px;
            line-height: 100px;
            background: #ffcccc;
            margin: 100px;
            text-align: center;
        }
    style>
head>

<body>
    <p>hehep>
    <p>hahap>
body>

html>

效果:
BFC、IFC、GFC、FFC_第5张图片

此时的hehe的margin-bottom和haha的margin-top重叠了,取两者中更大的一个。

上述发生的原因:
Box垂直方向的距离有margin决定,属于同一个BFC的两个相邻的margin会发生重叠

根据发生的原因,我们把第二个p再生成一个BFC就可以解决:

    <p>hehep>
    <div style="overflow: hidden;">
        <p>hahap>
    div>

效果是:
BFC、IFC、GFC、FFC_第6张图片

8、总结:

  • 以上几个例子都体现了,BFC就是页面上一个隔离的独立容器,容器里面的子元素不会影响到外面的元素,反之也如此。
  • IFC(inline formating context)直译为“内联格式化上下文”,IFC的line box(线框),高度由其包含行内元素中最高的实际高度计算而来(不受垂直方向的padding/margin影响)。
  • FFC(flxe formating context)直译为“自适应格式化上下文”,display值为flex或者inline-flex的元素将会生成自适应容器(flex container)。
  • GFC(GridLayout formating context)直译为“网络布局格式化上下文”,当为一个元素设置display值为grid的时候,此元素将会获得一个独立的渲染区域,我们可以通过在网格容器(grid container)上定义网格定义行(grid definition rows)和网格定义列(grid definition columns)属性各在网格项目(grid item)上定义网格行(grid row)和网格列(grid columns)为每一个网格项目(grid item)定义位置和空间。

9、GridLayout
GFC是模拟table设计的,和table又有什么区别呢?首先同样是一个二维的表格,但GridLayout会有更加丰富的属性来控制行列,控制对齐以及更为精细的渲染语义和控制。

你可能感兴趣的:(css)