CSS里實現(xiàn)水平居中非常容易,inline元素用text-align:center;,block元素用margin:auto;就行了佃蚜。但要實現(xiàn)垂直居中確是一大難題。本篇收集了一些已知的方案着绊,整理出來谐算,以備將來取用。代碼可以從GitHub上下載归露。
- Flex彈性盒子
- absolute絕對定位
- vh視口單位
- 偽元素
Flex彈性盒子
Flex彈性盒子應(yīng)該是解決垂直居中的最佳方案洲脂,隨著IE10的逐漸沒落,惹人煩的兼容性問題正逐漸被克服靶擦。用法很簡單腮考,給需要垂直居中的元素的父容器設(shè)置display:flex,并指定align-items: center;就搞定了:
body {
…
display: flex;
align-items: center;
}
main {
…
display: flex;
align-items: center;
justify-content: center;
flex-direction: column;
}
<body>
<main>
<div>用flex實現(xiàn)</div>
<p>垂直居中</p>
</main>
</body>
我們想將main垂直居中玄捕,只需給它的父元素body設(shè)display:flex;和align-items: center;即可踩蔚。main里有一個div和一個p,想將這兩個元素在main里垂直居中枚粘,同樣只需給它們的父元素main設(shè)display:flex;和align-items: center;馅闽。另外justify-content和flex-direction用于調(diào)整這兩個子元素水平居中的排列順序。(如果對彈性盒子及其屬性不熟悉馍迄,可以參照CSS3 flex盒子語法介紹福也,也可以點例子頁面試一下)
absolute絕對定位
一種很常見的方法是用絕對定位配合負(fù)值margin。思路是設(shè)成absolute后攀圈,指定top和left為50%暴凑,將元素的左上角定位點放到頁面正中心。然后用負(fù)值margin一半的元素寬高度將元素拉回頁面正中心:
main {
position: absolute;
width: 18em;
height: 10em;
top: 50%;
left: 50%;
margin-top: -9em;
margin-left: -5em;
…
}
但缺點是你需要事先指定元素的width和height赘来,否則無法給負(fù)margin設(shè)值现喳,顯得不夠靈活凯傲。其實不必固定元素的寬高,改用translate()位移來替代負(fù)margin嗦篱,實現(xiàn)將元素拉回頁面正中心:(如果對變形元素不熟冰单,可以參照CSS3 transform介紹)
main {
position: absolute;
top: 50%;
left: 50%;
transform: translate(-50%, -50%);
…
}
<main>
<div>用absolute實現(xiàn)</div>
<p>垂直居中</p>
</main>
用絕對定位absolute讓需要垂直居中的元素脫離文檔流,指定top和left各50%將元素左上角定位點設(shè)到頁面正中心灸促。然后用translate()各負(fù)50%诫欠,將元素拉回頁面正中心。思路和負(fù)margin是一致的浴栽,優(yōu)勢是不必固定元素的寬高了荒叼。缺點是absolute絕對定位威力太大,要考慮是否會對頁面布局造成影響典鸡。
vh視口單位
上例中translate()將元素回拉的前提是甩挫,absolute絕對定位來設(shè)top和left各50%。但如果看到absolute絕對定位就覺得不舒服椿每,可以改成vh視口單位來設(shè)元素左上角的定位點伊者。
vh就是視口高度,vw是視口寬度间护。例如1vh表示視口高度的1%亦渗。
vmin是視口寬高的小值,例如vh<vw時汁尺,1vmin等價于1vh法精。反之1vmin等價于1vw。
vmax是視口寬高的大值痴突,例如vh<vw時搂蜓,1vmax等價于1vw。反之1vmax等價于1vh辽装。
所以我們可以用vh替代absolute絕對定位:
main {
width: 9em;
margin: 50vh auto 0;
transform: translateY(-50%);
…
}
<main>
<div>用vh實現(xiàn)</div>
<p>垂直居中</p>
</main>
因為去掉了absolute帮碰,失去了包裹性,所以需要指定width大小拾积。margin-top設(shè)為50vh殉挽,表示視口高度的50%位置。然后用translateY(-50%)將元素拉上去拓巧。之所以用translateY因為水平位置已經(jīng)指定margin為auto實現(xiàn)了居中斯碌,所以水平位置不用回拉。
偽元素
如果待居中的元素是inline-block的話肛度,可以給父元素加上偽元素傻唾,配合inline-block / vertical-align實現(xiàn)居中:
.week-title {
height: 6.6%;
text-align: center;
}
.week-title::before { //父容器加上偽元素,配合inline-block / vertical-align
content: '';
height: 100%;
display: inline-block;
vertical-align: middle;
}
.week-title div { //待居中的元素需要是inline-block
width: 12.5%;
display: inline-block;
vertical-align: middle;
}