用 CSS 實現元素垂直居中

做者:知乎用戶
連接:https://www.zhihu.com/question/20543196/answer/275464838
來源:知乎
著做權歸做者全部。商業轉載請聯繫做者得到受權,非商業轉載請註明出處。

說明

  • .center表示要被居中的元素,.wrap 表示要居中的元素的父元素(包含.center元素的元素)。

爲了便於理解和敘述同一:css

  • 對於文本內容居中的狀況,.wrap就是指包含文字的元素(例如<i>文字</i> ,i標籤就是.wrap )。

文本內容會在外部建立一個行框(line-box),能夠將文本看做是一個(外框隱形)的行內元素html

  • 將文本內容包含在一個容器中(‘父親’),而後再將該容器在另外一個容器(‘祖父’)內居中不看做是文本內容居中,而是該文本內容外部容器的居中(‘父親’在’祖父‘內居中)。

 

  • 須知某些狀況不設置元素寬高、邊框色/背景,沒法看出居中效果,也就無所謂居中與否

例如父容器不設置背景或邊框,沒法看出子元素是否居中,示例代碼只是寫出了該居中方法所須要的那部分樣式佈局

  • inline元素,準確來講,是不可替換(non-replace)的inline元素,不能設置豎直方向上的margin和padding,下不贅述。(margin同理)

參看margin規定padding規定 ,之因此不能設置margin/padding,是由於post

padding的值是根據目標元素的width計算出來的,而inline中的non-replace元素的width是不肯定的。字體

  • CSS兼容性狀況未做說明,具體自行查閱caniuse
  • 推薦使用那些沒必要使用到精確數值(如50px,20rem這種狀況,百分比值50%除外)的方法。

 

行內內容的居中

如何讓一個容器的行內內容(文本和行內元素--inline/inlineblock)居中。(固然inline-block比較特殊,即有行內屬性,又有塊級屬性)flex

text-align:center水平居中

塊級元素上設置text-align:center,其內部的inline或inline-block的子元素以及文本內容會在父元素內居中。spa

line-height垂直居中

line-height設置了行間的距離(行高),將要居中的元素的line-heigth值設置爲和其塊級父元素的height值同樣時,其內部內容會垂直居中。code

用於單行的行內元素的垂直居中orm

.wrap{ height:100px; line-height: 100px; } 

注意:htm

  • line-height不能使用負值
  • 在塊級元素使用line-height是定義該元素基線之間的最小距離而不是最大距離。

vertical-align:middle垂直居中

vertical-align的使用效果要分爲如下不一樣狀況:

  • 行內元素inline/linline-block/inline-table內部內容的居中

使用僞元素(也能夠.wrap的父元素和兄弟元素進行居中,將下面代碼中的.wrap::before換成.wrap的兄弟元素的選擇器便可)

.wrap{ display:inline-block; vertical-align: middle; } .wrap::before{ //或者::after content: ''; display: inline-block; height: 100%; display:inline-block; vertical-align: middle; } 

注意:

  • vertical-align大部分取值是相對於父元素來講的

例如vertical-align:baseline(vertical-align的默認值)是相對於父元素的基線對齊。父元素的基線取值有如下規則:

  • inline類——小寫字母x的底端
  • inline-block類,其內沒有inline類型——盒子模型的底端
  • inline-block類,其內有inline類型時——其內最後一行inline元素的基線(即最後一行小寫x的底端)

 

  • 設置爲middle也不必定是真正的對齊,某些字體的中線位置不必定頂部和底部的正中間。
  • 不一樣風格的字體常有不一樣的排版標準,所以有不一樣的基線/中線/頂線等,多種字體混合排版會讓基線發生變化(參看父元素的基線取值規則)。

 

  • 表格單元格(table-cell)元素

在單元格上設置vertical-align:middle,其內部內容將垂直居中。

塊級元素居中

block、list-item、inline-block等元素如何在其父元素中居中。

margin/padding值設置居中

最基礎的方法是設置精確的padding(父元素上)或margin(子元素上)使得子元素居中,這裏再也不示例。

clac計算數值

margin值爲 父容器寬/高的50% 減去 自身寬/高的50%:

.center{ width: 20rem;height: 20rem; margin-left:calc(50% - 10rem); margin-top:calc(50% - 10rem); } 

注意:inline水平的元素margin/padding設置僅在左右方向上有效

margin:0 auto左右居中

要居中的塊級元素(block)元素設置margin:0 auto

注意:對浮動元素、絕對定位和固定定位的元素無效 。(注意:使用絕對定位+偏移量0+margin:auto方法中使用了四個方向的值爲0偏移量例外)

 

附:

注意margin/pading

百分比值參照其 包含塊的寬度進行計算

所以使用margin:auto並不能實現垂直方向上的居中,垂直居中最好不要使用margin/pading來實現。(固然若是確切知道父容器的高度,使用精確的margin/pading數值來實現再也不此討論之列)

position:absolute居中

在父元素上設置定位,再在要居中的子元素上使用絕對定位進行居中。

最基礎的方法:計算出要居中的元素寬高與父容器寬高的差值,而後將差值除以2獲得精確的值,再用以設置精確的水平和垂直偏移量;

其次是設置水平和垂直偏移量鴿50%,然會設置水平和垂直的負margin值——取值分別爲要居中的子元素寬高的半。

以上方法均須要使用容器寬高的確切值,靈活性較差,如下方法更爲靈活:

偏移量50%+負margin值

設置50%的水平和垂直偏移,而後設置的margin-top和margin-left值是要居中元素自身寬/高的一半的負數 :

.wrap { position: relative; } .center { position: absolute; height: 100px;width:100px; top: 50%;left:50%; margin-top:-50px; margin-left:-50px; } 

偏移量50%+負50%translate值

使用位移transform:translate,將設置了50%偏移的子元素」往回」移動自身寬高的一半:

.wrap { position: relative; } .center { position: absolute; top: 50%;left:50%; transform: translate(-50%,-50%); } 

偏移量0+margin:auto

父元素設置相對或絕對定位;要居中的子元素設置絕對定位,全部偏移量爲0,外邊距爲auto:

.wrap{ positon:relative; } .center{ positon:absolute; top:0;bottom:0;left:0;right:0; margin:auto; } 

flex彈性佈局居中

父元素設置爲彈性盒子(容器),子元素就成爲了彈性元素,利用flex相關屬性進行居中。

  • 在父元素上設置相關屬性便可使子元素居中:
.wrap{ display:flex; /*使用flex盒子*/ justify-content:center;/*水平軸上居中*/ align-items:center;/*垂直軸上居中*/ } 
  • 父元素設置爲彈性容器display:flex,子元素設置magrin:auto
.wrap{ display:flex; } .child{ margin: auto; } 

 

注意:

  • 若是有多個彈性子元素,默認狀況下彈性子元素會成一橫排分佈在父元素容器中,由於
  1. flex默認將子元素水平排列到一行(flex-direction:row),使用flex-direction:column可使子元素垂直排成一列。
  2. flex默認子元素不折行顯示(flex-wrap: nowrap ),使用flex-wrap: wrap可以使子元素自動折行顯示(當一行寬/高度不足容下多個子元素時折行爲多行/列)。

 

  • align-itemsalign-content區別:
    • align-content屬性只適用於多行子元素(超過一行)的flex容器,若是隻有一行子元素,該屬性不起做用;align-items適用於任意行子元素的flex容器。
    • align-content是設置一列子元素在整個縱軸上的對其方式;而align-items是設置每一個子元素在該行的高度範圍內的側軸上的對齊方式(垂直對齊)。

align-items至關於將側軸高度按行平分,設置的是子元素在該行高度上的對其方式。

 

object-fit和object-postion居中

object-fit 只能用於可替換元素(replaced element) ,用以

指定替換元素的內容應該如何適應到其使用的高度和寬度肯定的框。

通常用作圖片的樣式。它有着相似background-image的用法:

.center{ object-fit:fill|cover|contain|none|scale-down; /*其屬性值,分別是填充(默認)、包含、覆蓋(可能被裁剪)、無變化(保持原狀)和等比例縮放*/ } 

而object-positon屬性默認值是50% 50%,也就是居中(也就是要求居中的狀況不用寫這個屬性了……),對元素定位控制,相似background-postion。

grid網格佈局居中

根據須要佈局網格,將要居中的元素「擺放」在網格中間便可。

示例製做3x3的表格內元素居中:

.wrap{ display:grid; grid-template-rows: repeat(3, 1fr); grid-template-columns: repeat(3, 1fr); } .center{ grid-row: 2; grid-column: 2; } 

 

表格內容居中

  • 表格式佈局:根據語義化原則,使用表格佈局非表格的內容已再也不合適,並且表格的<td> <th>標籤的align和valign屬性已是HTML的廢除標籤屬性,建議不要使用
  • 非表格元素模擬表格:可使用display:table-cell 模擬其爲一個表格,因爲不建議使用廢除的align和valign標籤屬性,故而也就vertical-align:middle 垂直居中具備實用性,將元素模擬成表格進行垂直居中意義也不大了,所以建議不要使用
  • 真正的表格,表格內容的居中
    • 水平:text-align:center
    • 垂直:vertical-align:middle
    • 也可使用margin/pading等其餘方法來控制表格內容的居中
相關文章
相關標籤/搜索