因为HTML流式文档的特性,页面布局往往是新手最为头疼的问题之一。 每个HTML元素都会渲染为一个Box,可分为inline Box和block Box。 根据display属性的不同,Box的呈现方式又有所不同。 本文首先引入CSS盒模型,然后通过不同的display属性分别介绍Box常见的呈现方式。

Box Sizing:元素大小的计算方式

在HTML中,任何HTML元素都会被呈现为一个矩形。该矩形由内容、内边距、边框、外边距构成。举个例子:

<style>
.box-demo{
  width: 100px;
  height: 100px;
  border: 50px solid green;
  padding: 30px;
  margin: 50px;
  background: yellow;
}
</style>
<div class="box-demo"></div>

上述的<div>中,内容、边距与边框如下图所示:

  • 黄色的背景作用于内容内边距构成的矩形,其宽高为160px:宽度100px+两侧的内边距30pxX2;
  • 绿色部分为边框,宽度为50px
  • 与浏览器边框的距离为外边距,宽度为50px

例子中width属性定义的是内容的宽度,不包含边距、边框。然而在IE中width定义的是内容+内边距+边框的宽度。 这是由box-sizing属性来定义的,前者的默认值为content-box',后者的默认值为border-box`。

Display:渲染类型

了解了box-sizing之后,我们回到display属性。display指定了元素渲染Box的类型(type of rendering box)。我们来看它常用的取值:

  • none: 隐藏元素;
  • inline:行内元素,顾名思义,用于把一个元素放在行的内部;
  • block:块元素,用于显示占用一行的块;
  • inline-block:以block的方式渲染,以inline的方式放置;
  • table-cell:以表格元素的方式显示。

隐藏元素

none是最容易理解的取值。当一个元素的displayCSS属性被设为none时,该元素不会被渲染,也不会占位,就像不存在一样。对布局不会产生任何影响。

行内元素

行内(inline)元素不会打断文本流,默认(UA)显示为inline的元素包括:<span><a><em>等。它们的出现不会使得后续元素另起一行。行内元素可以设置marginpadding,但margin只在水平方向上起作用:

div{
  display: inline;
  background: red;
  padding: 10px;
  margin: 10px;
}

上图中,红色背景的是一个<div>,其大小为内容大小+padding;左右的空隙即为外边距margin。可以看到在Chrome中,这个inline<div>遮挡了出现在它前面的文本,同时被出现在它后面的文本所遮挡。这正是流式文档的特性。

另外,对inline元素设置widthheight是不起作用的。

块元素

块(block)元素会中断当前的文本流,另起一行,并在父元素中尽可能地占据最大宽度。常见的块元素有<p>,<div>,<section>等。通常块元素不可包含在行内元素内部。例如下面的两个<p>标签,不论内容是否足够,都会占据整个body的宽:

行内块

行内块(inline-block)将会产生一个块元素,并以行内元素的方式放置。什么意思呢?该元素的样式是以块元素的方式来渲染的,例如可以设置宽和高,然后以行内元素的方式放置在其上下文中,就像在行内元素的位置上替换成这个块元素一样。

MDN:The element generates a block element box that will be flowed with surrounding content as if it were a single inline box.

同样地,我们在一行文本内加入一个<div>,这次将它的display设为inline-block

div{
  display: inline-block;
  background: yellow;
  padding: 10px;
  margin: 10px;
  height: 20px;
}

此时,垂直方向的marginheight都起作用了:

  • 蓝色部分为内容,可以看到其高度为20px
  • 绿色部分为10pxpadding
  • 接着,border为空;
  • 红色为10pxmargin

inline-blockinline的不同在于:垂直方向上的margin也会起作用,并且可以设置widthheightinline-block是非常常用的样式设置。

表格元素

display设为table-cell的元素与<td>标签的行为一致,即:可设置padding,不接受margin,可伸缩的width

IE6/7不支持table-cell,然而WinXP已经下架。Win7的标配是IE8。现在可以放心地使用table-cell了!

利用table-cell属性可以在不写<table>标签的情况下完成表格布局:

<style>
.left, .right{
  display: table-cell;
  line-height: 50px;
}
.left{
  background: yellow;
  min-width: 150px;
}
.right{
  background: lightgreen;
  width: 100%;
}
</style>

<div>
  <div class="left">This is left cell</div>
  <div class="right">This is right cell</div>
</div>

左侧固定150px宽度,右侧自适应:

本文采用 知识共享署名 4.0 国际许可协议(CC-BY 4.0)进行许可,转载注明来源即可: https://harttle.land/2015/05/28/css-display.html。如有疏漏、谬误、侵权请通过评论或 邮件 指出。