您的位置:首页 > Web前端 > CSS

题目:谈一谈你对CSS盒模型的认识

2019-06-15 14:46 1426 查看

专业的面试,一定会问

CSS
盒模型。对于这个题目,我们要回答一下几个方面:

  1. 基本概念:
    content
    padding
    margin
  2. 标准盒模型、
    IE
    盒模型的区别。不要漏说了
    IE
    盒模型,通过这个问题,可以筛选一部分人
  3. CSS
    如何设置这两种模型(即:如何设置某个盒子为其中一个模型)?如果回答了上面的第二条,还会继续追问这一条。
  4. JS
    如何设置、获取盒模型对应的宽和高?这一步,已经有很多人答不上来了。
  5. 实例题:根据盒模型解释边距重叠

前四个方面是逐渐递增,第五个方面,却鲜有人知。

  1. BFC
    (边距重叠解决方案)或
    IFC

如果能回答第五条,就会引出第六条。

BFC
是面试频率较高的。

总结:以上几点,从上到下,知识点逐渐递增,知识面从理论、

CSS
JS
,又回到
CSS
理论

接下来,我们把上面的六条,依次讲解。

标准盒模型和IE盒子模型

标准盒子模型:

IE
盒子模型:

上图显示:

CSS
盒子模型 (
Box Model
) 规定了元素处理元素的几种方式:

  • width
    height
    内容的宽度、高度(不是盒子的宽度、高度)。
  • padding
    :内边距。
  • border
    :边框。
  • margin
    :外边距。

CSS
盒模型和
IE
盒模型的区别:

  • 标准盒子模型中,width 和 height 指的是内容区域的宽度和高度。增加内边距、边框和外边距不会影响内容区域的尺寸,但是会增加元素框的总尺寸。
  • IE盒子模型中,width 和 height 指的是内容区域+border+padding的宽度和高度。

CSS如何设置这两种模型

代码如下:

/* 设置当前盒子为 标准盒模型(默认) */
box-sizing: content-box;

/* 设置当前盒子为 IE盒模型 */
box-sizing: border-box;

备注:盒子默认为标准盒模型。

JS如何设置、获取盒模型对应的宽和高

方式一:通过

DOM
节点的
style
样式获取

element.style.width/height;

缺点:通过这种方式,只能获取行内样式,不能获取

内嵌
的样式和
外链
的样式。

这种方式有局限性,但应该了解。

方式二(通用型)

window.getComputedStyle(element).width/height;

方式二能兼容

Chrome
、火狐。是通用型方式。

方式三(IE独有的)

element.currentStyle.width/height;

和方式二相同,但这种方式只有IE独有。获取到的即时运行完之后的宽高(三种css样式都可以获取)。

方式四

element.getBoundingClientRect().width/height;

api
的作用是:获取一个元素的绝对位置。绝对位置是视窗
viewport
左上角的绝对位置。此
api
可以拿到四个属性:
left
top
width
height

总结:

上面的四种方式,要求能说出来区别,以及哪个的通用型更强。

margin塌陷/margin重叠

标准文档流中,竖直方向的margin不叠加,只取较大的值作为margin(水平方向的

margin
是可以叠加的,即水平方向没有塌陷现象)。

PS:如果不在标准流,比如盒子都浮动了,那么两个盒子之间是没有

margin
重叠的现象的。

我们来看几个例子。

兄弟元素之间

如下图所示:

子元素和父元素之间

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>

* {
margin: 0;
padding: 0;
}

.father {
background: green;

}

/* 给儿子设置margin-top为10像素 */
.son {
height: 100px;
margin-top: 10px;
background: red;
}

</style>
</head>
<body>
<div class="father">
<div class="son"></div>
</div>
</body>
</html>

上面的代码中,儿子的

height
100p
x,
magin-top
10px
。注意,此时父亲的
height
100
,而不是
110
。因为儿子和父亲在竖直方向上,共一个
margin

儿子这个盒子:

父亲这个盒子:

上方代码中,如果我们给父亲设置一个属性:

overflow: hidden
,就可以避免这个问题,此时父亲的高度是110px,这个用到的就是BFC(下一段讲解)。

善于使用父亲的padding,而不是儿子的margin

其实,这一小段讲的内容与上一小段相同,都是讲父子之间的margin重叠。

我们来看一个奇怪的现象。现在有下面这样一个结构:(

div
中放一个
p

1b5d8
<div>
<p></p>
</div>

上面的结构中,我们尝试通过给儿子

p
一个
margin-top:50px;
的属性,让其与父亲保持50px的上边距。结果却看到了下面的奇怪的现象:

此时我们给父亲

div
加一个
border
属性,就正常了:

如果父亲没有

border
,那么儿子的
margin
实际上踹的是“流”,踹的是这“行”。所以,父亲整体也掉下来了。

margin这个属性,本质上描述的是兄弟和兄弟之间的距离; 最好不要用这个marign表达父子之间的距离。

所以,如果要表达父子之间的距离,我们一定要善于使用父亲的padding,而不是儿子的`margin。

BFC(边距重叠解决方案)

BFC(Block Formatting Context)
:块级格式化上下文。你可以把它理解成一个独立的区域。

另外还有个概念叫

IFC
。不过,
BFC
问得更多。

BFC 的原理/BFC的布局规则【非常重要】

BFC
的原理,其实也就是
BFC
的渲染规则(能说出以下四点就够了)。包括:

  1. BFC 内部的子元素,在垂直方向,边距会发生重叠
  2. BFC在页面中是独立的容器,外面的元素不会影响里面的元素,反之亦然。(稍后看
    举例1
  3. BFC区域不与旁边的
    float box
    区域重叠
    。(可以用来清除浮动带来的影响)。(稍后看
    举例2
  4. 计算
    BFC
    的高度时,浮动的子元素也参与计算。(稍后看
    举例3

如何生成BFC

有以下几种方法:

  • 方法1:
    overflow
    : 不为
    visible
    ,可以让属性是
    hidden
    auto
    。【最常用】
  • 方法2:浮动中:
    float
    的属性值不为
    none
    。意思是,只要设置了浮动,当前元素就创建了
    BFC
  • 方法3:定位中:只要
    posiiton
    的值不是 s
    tatic
    或者是
    relative
    即可,可以是
    absolute
    fixed
    ,也就生成了一个
    BFC
  • 方法4:
    display
    inline-block
    ,
    table-cell
    ,
    table-caption
    ,
    flex
    ,
    inline-flex

BFC 的应用

**举例1:**解决 margin 重叠

当父元素和子元素发生

margin
重叠时,解决办法:给子元素或父元素创建BFC

比如说,针对下面这样一个

div
结构:

<div class="father">
<p class="son">
</p>
</div>

上面的

div
结构中,如果父元素和子元素发生
margin
重叠,我们可以给子元素创建一个
BFC
,就解决了:

<div class="father">
<p class="son" style="overflow: hidden">
</p>
</div>

因为第二条:BFC区域是一个独立的区域,不会影响外面的元素

举例2:BFC区域不与float区域重叠:

针对下面这样一个div结构;

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>

.father-layout {
background: pink;
}

.father-layout .left {
float: left;
width: 100px;
height: 100px;
background: green;
}

.father-layout .right {
height: 150px;  /*右侧标准流里的元素,比左侧浮动的元素要高*/
background: red;
}

</style>
</head>
<body>

<section class="father-layout">
<div class="left">
左侧,生命壹号
</div>
<div class="right">
右侧,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,
</div>
</section>

</body>
</html>

效果如下:

上图中,由于右侧标准流里的元素,比左侧浮动的元素要高,导致右侧有一部分会跑到左边的下面去。

如果要解决这个问题,可以将右侧的元素创建BFC,因为第三条:BFC区域不与

float box
区域重叠。解决办法如下:(将right区域添加overflow属性)

<div class="right" style="overflow: hidden">
右侧,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,smyhvae,
</div>

上图表明,解决之后,

father-layout
的背景色显现出来了,说明问题解决了。

**举例3:**清除浮动

现在有下面这样的结构:

<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Document</title>
<style>

.father {
background: pink;
}

.son {
float: left;
background: green;
}

</style>
</head>
<body>

<section class="father">
<div class="son">
生命壹号
</div>

</section>
</body>
</html>

效果如下:

上面的代码中,儿子浮动了,但由于父亲没有设置高度,导致看不到父亲的背景色(此时父亲的高度为0)。正所谓有高度的盒子,才能关住浮动

如果想要清除浮动带来的影响,方法一是给父亲设置高度,然后采用隔墙法。方法二是 BFC:给父亲增加

overflow=hidden
属性即可, 增加之后,效果如下:

为什么父元素成为BFC之后,就有了高度呢?这就回到了第四条:计算BFC的高度时,浮动元素也参与计算。意思是,在计算BFC的高度时,子元素的float box也会参与计算

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: