CSS的學習入門很容易,只要1年甚至半年的時候,咱們就能根據設計圖迅速切出頁面,能熟練使用些CSS hack,這個階段咱們的成長很快,天天都能汲取新知識。這其實是CSS很是初級的階段,也是廣大頁面仔們(包括我本人😳)最爲浮躁,最自覺得是,最以爲CSS不過如此的階段。因此咱們要增長學習的深度,深刻掌握細節和原理,當咱們對CSS的底層表現有必定的理解與認識的時候,遇到一些看似奇怪的問題,能夠輕鬆搞定~css
咱們在研究佈局以前,首先須要瞭解幾個很重要的概念和屬性:html
文檔流指的是元素排版佈局過程當中,元素會自動從左往右,從上往下的流式排列。並最終窗體自上而下分紅一行行,並在每行中從左至右的順序排放元素。HTML中所有元素都是盒模型,盒模型佔用必定的空間,依次排放在HTML中,造成了文檔流。css3
float
、position:absolute|fixed
是脫離文檔流的。脫離文檔流是指,這個標籤脫離了文檔流的管理。不受文檔流的佈局約束了,而且更重要的一點是,當一個元素脫離文檔流後,這個標籤在原文檔流中所佔的空間也被清除掉了,依然在文檔流中的其餘元素將忽略該元素並填補其原先的空間。瀏覽器
<div>、<p>、<h1>...<h6>、<ol>、<ul>、<dl>、<table>、<address>、<blockquote> 、<form>
<span>、<a>、<strong>、<em>
是CSS中最重要的用於控制佈局的屬性,每一個元素都有一個默認的值,這與元素的類型有關。對於大多數元素它們的默認值一般是block
(塊級元素)或inline
(行內元素)。app
display:none
和visibility
屬性不同。display:none
的元素不會佔據它原本應該顯示的空間,可是設置成visibility: hidden;
還會佔據空間。ide
若是兩個相鄰元素都在其上設置外邊距,而且兩個外邊距接觸,則兩個外邊距中的較大者保留,較小的一個消失佈局
static:默認值。元素框正常生成。塊級元素生成一個矩形框,做爲文檔流的一部分;行內元素則會建立一個或多個行框,置於其父元素中。學習
relative:元素框相對於以前正常文檔流中的位置發生偏移,而且原先的位置仍然被佔據。發生偏移的時候,可能會覆蓋其餘元素。flex
最初,設計浮動時,其實並非爲了佈局的,而是爲了實現文字環繞的特效。相似於ps中的圖層同樣,浮動的元素會在浮動層上面進行排布,而在原先文檔流中的元素位置,會被以某種方式進行刪除,可是仍是會影響佈局,因此要記得清除浮動。spa
浮動爲何會被使用在佈局中呢?由於設置浮動後的元素會造成BFC(使得內部的元素不會被外部所幹擾),而且元素的寬度也再也不自適應父元素寬度,而是適應自身內容。這樣就能夠,輕鬆地實現多欄佈局的效果。浮動一般用於建立多個列布局,而且因爲它有良好的瀏覽器兼容性,已經被使用了至關一段時間。
彈性佈局:用來爲盒狀模型提供最大的靈活性,採用 Flex 佈局的元素,稱爲 Flex 容器(flex container)。它的全部子元素自動成爲容器成員,稱爲 Flex 項目(flex item)。
容器默認存在兩根軸:水平的主軸(main axis)和垂直的交叉軸(cross axis)。主軸的開始位置(與邊框的交叉點)叫作main start,結束位置叫作main end;交叉軸的開始位置叫作cross start,結束位置叫作cross end。
項目(flex item)默認沿主軸排列。單個item佔據的主軸空間叫作main size,佔據的交叉軸空間叫作cross size。
屬性決定主軸的方向(即item的排列方向)
默認狀況下,項目(item)都排在一條線(又稱"軸線")上。flex-wrap屬性定義,若是一條軸線排不下,如何換行。
flex-flow
屬性是flex-direction
屬性和flex-wrap
屬性的簡寫形式,默認值爲row nowrap
justify-content
屬性定義了項目在主軸上的對齊方式。
.box {
justify-content: flex-start | flex-end | center | space-between | space-around;
}
複製代碼
align-items
屬性定義項目在交叉軸上如何對齊。
.box {
align-items: flex-start | flex-end | center | baseline | stretch;
}
複製代碼
具體的對齊方式與交叉軸的方向有關,下面假設交叉軸從上到下。
align-content
屬性定義了多根軸線的對齊方式。若是項目只有一根軸線,該屬性不起做用
.box {
align-content: flex-start | flex-end | center | space-between | space-around | stretch;
}
複製代碼
order
屬性定義項目的排列順序。數值越小,排列越靠前,默認爲0。
flex-grow
屬性定義項目的放大比例,默認爲0,即若是存在剩餘空間,也不放大 若是全部項目的flex-grow屬性都爲1,則它們將等分剩餘空間(若是有的話)。若是一個項目的flex-grow屬性爲2,其餘項目都爲1,則前者佔據的剩餘空間將比其餘項多一倍。
flex-shrink
屬性定義了項目的縮小比例,默認爲1,即若是空間不足,該項目將縮小。 若是全部項目的flex-shrink屬性都爲1,當空間不足時,都將等比例縮小。若是一個項目的flex-shrink屬性爲0,其餘項目都爲1,則空間不足時,前者不縮小。負值對該屬性無效
flex-basis
屬性用於設置或檢索彈性盒伸縮基準值。定義了在分配多餘空間以前,項目佔據的主軸空間(main size)。瀏覽器根據這個屬性,計算主軸是否有多餘空間。它的默認值爲auto,即項目的原本大小。
它能夠設爲一個長度單位或者一個百分比,規定靈活項目的初始長度。
div:nth-of-type(2) {
flex-basis: 80px;
}
複製代碼
flex
屬性是flex-grow
, flex-shrink
和 flex-basis
的簡寫,默認值爲0 1 auto
。後兩個屬性可選。 該屬性有兩個快捷值:auto
(1 1 auto
) 和 none
(0 0 auto
)。
建議優先使用這個屬性,而不是單獨寫三個分離的屬性,由於瀏覽器會推算相關值。
align-self
屬性容許單個項目有與其餘項目不同的對齊方式,可覆蓋align-items
屬性。默認值爲auto
,表示繼承父元素的align-items
屬性,若是沒有父元素,則等同於stretch
。
該屬性可能取6個值,除了auto,其餘都與align-items屬性徹底一致。
常見的這兩種單列布局的特色都是定寬,水平居中的,設置width或max-width和margin:auto便可;
三列布局的特徵是左右兩側固定寬度,中間列自適應寬度。
將兩個側邊欄分別向左向右浮動,經過設置中間的主欄的margin爲它們留出空間,造成三列布局
.left{
float: left;
width: 200px;
}
.right{
float: right;
width: 200px;
}
.main{
margin-left: 220px; /*預留出定寬兩欄的空間*/
margin-right: 220px;
}
複製代碼
只設置一個浮動便可獲得兩列布局
經過將兩個側邊欄的position設置爲absolute,而後將左邊欄的left設置爲0,右邊欄的right設置爲0,主欄設置margin爲邊欄留出空間,便可獲得三列布局。
.left{
position: absolute;
left: 0;
width: 200px;
}
.right{
position: absolute;
right: 0;
width: 200px;
}
.main{
margin-left: 220px;
margin-right: 220px;
}
複製代碼
一樣,將定位元素改成一個能夠獲得兩列布局。
<div class="container">
<div class="main"></div>
<div class="left"></div>
<div class="right"></div>
</div>
複製代碼
.main{
float: left;
width: 100%;
}
.left{
float: left;
width: 200px;
margin-left: -100%;
position: relative;
left: -200px;
}
.right{
float: left;
width: 300px;
margin-left: -300px;
position: relative;
right: -300px;
}
.container {
padding: 0 300px 0 200px;
}
複製代碼
二列的實現方法:
若是是左邊帶有側欄的二列布局,則去掉right,不設置主面板的padding-right值。
雙飛翼佈局和聖盃佈局的思想有些類似,都利用了浮動和負邊距,但雙飛翼佈局在主欄外加了一層div並設置margin用來容納側欄,兩側欄的負邊距都是相對於外層div而言,main的margin值變化便不會影響兩個側欄,這樣就省略了將側欄拉到主欄那一行後進行的relative定位(由於雙飛翼佈局留白就在父元素的內容區,而聖盃佈局的留白在父元素內容區以外)。
<div class="wrapper">
<div class="main"></div>
</div>
<div class="left"></div>
<div class="right"></div>
複製代碼
.wrapper {
float: left;
width: 100%;
}
.main {
margin: 0 300px 0 200px;
}
.left {
float: left;
width: 200px;
margin-left: -100%;
}
.right {
float: left;
width: 300px;
margin-left: -300px;
}
複製代碼
二列的實現方法:
若是是左邊帶有側欄的二欄佈局,則去掉右側欄,不要設置main-wrap的margin-right值,其餘操做相同。反之亦然。
Flex 是 Flexible Box 的縮寫,意爲「彈性佈局」,用來爲盒狀模型提供最大的靈活性。除了在PC端兼容性較差,沒有太大的缺陷,多用於移動端佈局。
.layout {
display: flex;
}
.main {
flex: 1;
}
.aside {
width: 200px;
}
複製代碼
這是你們很常見的居中方式,元素會佔據你所指定的寬度,而後剩餘的寬度會一分爲二成爲左右外邊距。不過問題是,當瀏覽器窗口比元素的寬度還要窄時,瀏覽器會顯示水平滾動條。
在這種狀況下使用 max-width 替代 width 可使瀏覽器更好地處理小窗口的狀況。這點在移動設備上顯得尤其重要~
調整窗口大小看一下二者的區別吧 居中在佈局中很常見,咱們假設DOM文檔結構以下,子元素要在父元素中居中:
<div class="parent">
<div class="child"></div>
</div>
複製代碼
垂直居中對於子元素是單行內聯文本、多行內聯文本以及塊狀元素採用的方案是不一樣的。