css布局是工作中最常碰到的,同时也是笔试 or 面试中会被问到的问题,故在本文整理了css多种布局方式,以供参考。
此篇较长四千五百字左右,读者可分三部分阅读,水平居中布局,垂直居中布局,水平居中对齐。
水平居中布局
水平居中布局,指当前元素在父级元素中的水平方向上是居中,如:
实现水平居中的方法有很多,我们一个一个来看。
1、inline-block + text-align
-
设置子元素为一个
inline-block
元素 -
设置父元素
text-align: center;
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine; /*海蓝色*/
text-align: center;
}
#children {
width: 100px;
height: 100px;
background-color: pink; /*粉色*/
display: inline-block;
}
解读:
1、给父元素设置 text-align: center;
是何用意?
css 属性 text-align
的作用是定义行内内容(例如 文字)如何相对于它的块父元素对齐。
text-align
的值有很多,最常用的:
-
left
左对齐 -
right
右对齐
-
center
居中对齐
所以,通过text-align: center;
,就可以让内部的行内子元素居中对齐了。
注意⚠️:text-align
并不控制块元素自己的对齐,而是只控制它的行内内容的对齐。
拓展阅读:text-align。
2、给子元素设置 display: inline-block;
是何用意?
通过第一步,我们了解了,要想子元素居中,该元素就需要是一个行内元素,但是子元素children
是一个div
块级元素,所以我们就需要把它变为行内元素,变为行内元素很简单,设置display: inline;
即可,但是从css
中我们可以看到,该元素设置了width
& height
,inline 行内元素设置宽度和高度是不生效的,所以,我们就必须设置 display: inline-block;
将其变为行内块元素,结合行内元素和块级元素的特点,既能设置宽高,又为一个行内元素,此时居中效果就生效了。
拓展阅读:inline、block、inline-block。
优点:
浏览器兼容性好。
由于text-align:center;
和 display: inline-block
都为css2中的内容,老版本的浏览器对于CSS2的支持是很友好的。
缺点:
text-align
具有继承性,会导致子元素中的文本也是居中显示的。
如下,在子元素中添加文本:
<div id="parent">
<div id="children">文本</div>
</div>
效果:
会看到,文本内容自动水平居中了。
如果不想要文本水平居中的效果该怎么办?如想要文本左对齐,那么就需要在子元素中设置text-align: left;
了。
2、margin + block
-
设置子元素的margin
margin: 0 auto;
-
设置子元素为一个
block
元素
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
margin: 0 auto;
display: block;
}
解读:
1、给子元素设置 margin: 0 auto;
是何用意?
margin是一个简写属性,当给一个元素设置 margin: 0 auto;
时,设置的其实是:
-
margin-top
为 0 -
margin-right
为 auto
-
margin-bottom
为 0 -
margin-left
为 auto
如果两侧均为auto的话,则平分剩余空间,那么设置左右为auto后,元素自然而然就水平居中了。
2、为何需要给子元素设置 display: block;
?
阅读了第一条的解释后,有些同学可能会很迷惑,设置 margin: 0 auto;
就可以将元素设置为居中对齐了,为什么还要再次设置 diaplay: block;
呢?
是这样的,当元素的 display
为 inline
、inline-block
、inline-table
时,给元素的 margin
设置为 auto
时,最终设置的值,等价于 0
。所以一旦要使用 margin: 0 auto;
进行水平居中布局,就避免让元素为以上三种 display
,直接设置为 block
就好了。当然,如果子元素本身就为块级元素,那么就不需要再单独设置 display
为 block
了。所以上面代码中的 display: block;
可以删除掉。
优点:
只需要对子元素进行特殊设置,就可以实现水平居中布局。
缺点:
如果子元素脱离文档流,那么会导致margin
失效
在css中进行以下几个设置时,元素会脱离文档流:
-
float: left;
-
float: right;
-
position: absolute;
-
position: fixed;
3、position + 负margin
-
设置父元素为相对定位
-
设置子元素为绝对定位
-
设置子元素
left
为50%
-
设置子元素
margin
为-1/2*width
(宽度一半的负值)
代码如下:
<div id="parent">
<div id="children"></div>
</div>
parent {
width: 300px;
height: 200px;
background-color: aquamarine;
position: relative;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
position: absolute;
left: 50%;
margin-left: -50px;
}
解读:
1、为了让子元素相对于父元素进行定位,所以设置父元素相对定位、子元素绝对定位
2、为了让元素在中间,所以设置子元素的 left
为 50%
。让子元素距离父元素的左边的距离是 父元素宽度的一半,即 150px
。
3、由于 150px
过大,会导致子元素位置向右偏,如:
4、所以,要设置,让元素向左移动自己宽度的一半,回到正中间,所以设置了 margin-left
为 -50px
。
优点:
无论父元素是否脱离文档流,都不影响子元素水平居中的效果。
缺点:
必须要明确子元素的宽度,否则没有办法设置 margin-left
的值。
4、position + translateX
-
设置父元素为相对定位
-
设置子元素为绝对定位
-
设置子元素
left
为50%
-
设置子元素
translateX
为-50%
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
position: relative;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
position: absolute;
left: 50%;
transform: translateX(-50%);
}
解读:
和上一个的方法一样,需要让子元素向左移动自己的宽度的一半,除了用 margin
之外,也可以使用 translateX
让元素在水平方向上偏移,当给 translateX
的参数设置为 -50%
时,即为向左移动自己宽度的一半。
优点:
无论父元素是否脱离文档流,都不影响子元素水平居中的效果。
缺点:
transform
是 CSS3中新增的属性,所以不兼容部分老浏览器。
兼容性查询:https://www.caniuse.com/#search=transform
5、flex + justify-content
-
设置父元素的
dispaly
为flex
-
设置父元素的
justify-content
为center
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
display: flex;
justify-content: center;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
}
解读:
设置 display
为 flex
的父元素其主轴上元素的排列方式为居中。
优点:
无论父元素是否脱离文档流,都不影响子元素水平居中的效果。
缺点:
1、flex
是 CSS3中新增的内容,所以不兼容部分老浏览器。
兼容性查询:https://www.caniuse.com/#search=flex
2、使用此种方式,会让父元素内的其他子元素也全部水平居中,如下,在父元素中添加其他子元素:
<div id="parent">
<div id="children"></div>
<div id="other-item"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
display: flex;
justify-content: center;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
}
#other-item {
width: 100px;
height: 30px;
background-color: salmon;
}
效果如下:
若父元素内有其他子元素不需要水平居中处理,则可以考虑不使用这种方式。
垂直居中布局
垂直居中布局,指当前元素在父级元素中的垂直方向上时居中,如:
以下为实现垂直居中的方法
1、vertical-align+table-cell
-
设置父元素的
vertical-align
为middle
-
设置父元素的
display
为table-cell
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
display: table-cell;
vertical-align: middle;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
}
解读:
1、属性 vertical-align
用来指定行内元素(inline)或表格单元格(table-cell)元素的垂直对齐方式,当给 table-cell
元素设置 vertical-align: middle;
时,表示让该单元格元素内部的盒模型在该行内居中对齐。
2、由1可知,元素需为 table-cell
,所以设置 display
为 table-cell
优点:
浏览器兼容性好。
由于 vertical-align: middle;
和 display: table-cell;
都为css2中的内容,老版本的浏览器对于CSS2的支持是很友好的。
缺点:
vertical-align
会导致父级元素中的全部元素都一起居中显示。
如下,在父元素中添加元素:
<div id="parent">
文本
<div id="children"></div>
<div id="other-item"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
display: table-cell;
vertical-align: middle;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
}
#other-item {
width: 100px;
height: 30px;
background-color: salmon;
}
效果:
所以当父元素中拥有其他元素时,就不太适合使用这种方案实现垂直居中布局了。
2、position+负margin
-
设置父元素为相对定位
-
设置子元素为绝对定位
-
设置子元素
left
为50%
-
设置子元素
top
为-1/2*height
(高度一半的负值)
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
position: relative;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
position: absolute;
top: 50%;
margin-top: -50px;
}
解读:
1、为了让子元素相对于父元素进行定位,所以设置父元素相对定位、子元素绝对定位
2、为了让元素在中间,所以设置子元素的 top
为 50%
。让子元素距离父元素的左边的距离是 父元素宽度的一半,即 100px
。
3、由于 100px
过大,会导致子元素位置向下偏,如:
4、所以,要设置,让元素向上移动自己高度的一半,回到正中间,所以设置了 margin-top
为 -50px
。
优点:
无论父元素是否脱离文档流,都不影响子元素水平居中的效果。
缺点:
必须要明确子元素的宽度,否则没有办法设置 margin-left
的值。
3、position+translateY
-
设置父元素为相对定位
-
设置子元素为绝对定位
-
设置子元素
left
为50%
-
设置子元素
translateY
为-50%
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
position: relative;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
position: absolute;
top: 50%;
transform: translateY(-50%);
}
解读:
和上一个的方法一样,需要让子元素向上移动自己的高度的一半,除了用 margin
之外,也可以使用 translateY
让元素在垂直方向上偏移,当给 translateY
的参数设置为 -50%
时,即为向上移动自己高度的一半。
优点:
无论父元素是否脱离文档流,都不影响子元素水平居中的效果。
缺点:
transform
是 CSS3中新增的属性,所以不兼容部分老浏览器。
兼容性查询:https://www.caniuse.com/#search=transform
4、flex + align-items
-
设置父元素的
dispaly
为flex
-
设置父元素的
align-items
为center
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
display: flex;
align-items: center;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
}
解读:
设置 display
为 flex
的父元素其交叉轴上元素的排列方式为居中。
优点:
无论父元素是否脱离文档流,都不影响子元素水平居中的效果。
缺点:
1、flex
是 CSS3中新增的内容,所以不兼容部分老浏览器。
兼容性查询:https://www.caniuse.com/#search=flex
2、使用此种方式,会让父元素内的其他子元素也全部垂直居中,如下,在父元素中添加其他子元素:
<div id="parent">
<div id="children"></div>
<div id="other-item"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
display: flex;
justify-content: center;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
}
#other-item {
width: 100px;
height: 30px;
background-color: salmon;
}
效果如下:
若父元素内有其他子元素不需要垂直居中处理,则可以考虑不使用这种方式。
居中 (水平+垂直) 布局
居中布局,即为元素在父元素的水平方向上和居中方向都对齐,效果如下:
想要实现居中对齐,整合上面的水平布局方法和垂直居中即可,故不再对解读、优点、缺点进行书写。
1、table+margin+table-cell+vertical-align
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
display: table-cell;
vertical-align: middle;
text-align: center;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
display: inline-block;
}
2、position+负margin
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
position: relative;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
position: absolute;
left: 50%;
top: 50%;
margin-top: -50px;
margin-left: -50px;
}
3、position+translateX+translateY
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
position: relative;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
position: absolute;
left: 50%;
top: 50%;
transform: translateX(-50%) translateY(-50%);
}
4、flex+justify-content+align-items
代码如下:
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
display: flex;
justify-content: center;
align-items: center;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
}
5、position+margin
<div id="parent">
<div id="children"></div>
</div>
#parent {
width: 300px;
height: 200px;
background-color: aquamarine;
position: relative;
}
#children {
width: 100px;
height: 100px;
background-color: pink;
position: absolute;
top: 0;
right: 0;
bottom: 0;
left: 0;
margin: auto;
}
最后听一首悦耳的歌放松放松,回忆学到的东西。
点击下面播放音乐
New Boy (Live片段).mp300:0000:13#让生活多一点生机
长按二维码关注,一起努力。
助力寻人启事
微信公众号回复 加群 一起学习。