Grid佈局概念
CSS Gird已經被W3C納入到css3的一個佈局模組中,被稱為CSS Grid Layout Module,一般習慣稱為網格佈局。
網格佈局可以將應用程式分割成不同的空間,定義它們的大小、位置和層級。
簡單來說,網格佈局就像表格一樣可以讓元素按列和行對齊排列,不同的是,網格佈局沒有內容結構,比如一個網格佈局的子元素可以定位自己的位置,可以是實現類似定位的效果。
相容性
可以看到幾大瀏覽器都已經支援了Grid佈局,接下來我們來一步步的來玩轉Grid佈局
grid vs flex
我們知道flex和grid都是css3新的佈局方式,如果瀏覽器都支援兩種佈局,你會選擇那種呢?當我們瞭解兩者以後就能做出正確的選擇了。
flex佈局是一維佈局,grid佈局是二維佈局。
網格容器和網格項
我們知道給一個元素設定了display:flex
就指定了flex彈性佈局,實現grid佈局一樣簡單,給元素設定display:grid
就可以了。
<style>
.container{
display: grid;
}
</style>
<div class="container">
<div class="item"></div>
<div class="item"></div>
<div class="item"></div>
<div class="item"></div>
</div>
複製程式碼
container
就是一個網格容器,裡面的item
就是網格項
網格術語
網格線 grid lines
網格線組成了網格,是網格水平和垂直的分界線。
網格軌道 grid track
就是兩條網格線之間的空間,可以理解成表格裡面的行或者列,網格里面為grid-row
和grid-column
,網格軌道可以設定大小,來控制高度或者寬度。
上圖grid-column2
和grid-column3
之間的區域就是一個網格軌道
網格單元格 grid cell
就是四條網格線之間的空間,是最小的單位。
網格區域
也是四條網格線組成的空間,可能包含一個或者多個單元格。
實現一個grid佈局
瞭解網格個相關概念,接下來我們來建立一個簡單的grid佈局。
上面我們說網格軌道的時候說了可以給網格軌道設定大小,可以控制高度或者寬度。
html
<div class="grid">
<div class="item-1">1</div>
<div class="item-2">2</div>
<div class="item-3">3</div>
<div class="item-4">4</div>
<div class="item-5">5</div>
<div class="item-6">6</div>
</div>
複製程式碼
css
$bgcloors: #b03532 #33a8a5 #30997a #6a478f #da6f2b #3d8bb1;
.grid{
display: grid;
grid-template-columns: 300px 200px 150px;
grid-template-rows: 150px 100px;
div{
color: #fff;
font-size: 30px;
padding: 20px;
}
@for $i from 1 through length($bgcloors){
.item-#{$i}{
background: nth($bgcloors, $i)
}
}
}
複製程式碼
我們來分析下上面的css
1、給grid
元素設定了 display: grid
來宣告使用grid佈局
2、使用grid-template-columns
來設定列寬,分別為 300px 200px 150px
3、使用grid-template-rows
來設定行高,分別為150px 100px
以上程式碼我們是實現了一個兩行三列的grid佈局,此時瀏覽器顯示如下
我們可以看到網格線的樣子
進階
fr
grid-template-columns
和grid-template-rows
不只是可以設定具體的數值,還可以設定百分比、rem一類的,還可以設定一個新單位 fr
,
它是來幹什麼的呢?我們先看
我們先把上面demo裡面的css檔案改下
$bgcloors: #b03532 #33a8a5 #30997a #6a478f #da6f2b #3d8bb1;
.grid{
display: grid;
grid-template-columns: 1fr 2fr 1fr;
grid-template-rows: repeat(2,1fr);
div{
color: #fff;
font-size: 30px;
padding: 20px;
}
@for $i from 1 through length($bgcloors){
.item-#{$i}{
background: nth($bgcloors, $i)
}
}
}
複製程式碼
以上實現了彈性佈局,fr用來實現彈性佈局, 我們這裡使用裡repeat(2, 1fr)
,表示重複兩次,都是1fr
grid-gap
grid-gap用來這是網格項間隙
css修改如下
$bgcloors: #b03532 #33a8a5 #30997a #6a478f #da6f2b #3d8bb1;
.grid{
display: grid;
grid-template-columns: 1fr 2fr 1fr;
grid-template-rows: repeat(2,1fr);
grid-gap: 40px;
div{
color: #fff;
font-size: 30px;
padding: 20px;
}
@for $i from 1 through length($bgcloors){
.item-#{$i}{
background: nth($bgcloors, $i)
}
}
}
複製程式碼
展示如下
網格佈局屬性 grid-placement-properties
恭喜你,從一開始一步步的實現了一個網格佈局,可以發現所有的樣式都寫在網格容器裡面的,當我們實現一些複雜佈局的時候,就顯得有點力不從心了,接下來我們來介紹下寫在網格項中的屬性。
網格佈局屬性主要用來放置容器內的網格專案,就是單一專案的位置。網格佈局屬性主要有以下四個屬性:
1、grid-column-start 設定垂直方向的開始位置網格線
2、grid-column-end 設定垂直方向的結束位置網格線
3、grid-row-start 設定水平方向的開始位置網格線
4、grid-row-end 設定水平方向的結束位置網格線
複製程式碼
以上的簡寫方式
1、grid-column: grid-column-start / grid-column-end
2、grid-row: grid-row-start / grid-row-end
複製程式碼
終極簡寫
grid-area: grid-row-start / grid-column-start / grid-row-end / grid-colun-end
複製程式碼
是不是有點蒙,我們可以大概看下,先來看deme
還是熟悉的html佈局
<div class="grid">
<div class="item-1">1</div>
<div class="item-2">2</div>
<div class="item-3">3</div>
<div class="item-4">4</div>
<div class="item-5">5</div>
<div class="item-6">6</div>
</div>
複製程式碼
css
$bgcloors: #b03532 #33a8a5 #30997a #6a478f #da6f2b #3d8bb1;
.grid{
display: grid;
grid-template-columns: 300px 200px 150px;
grid-template-rows: 150px 100px;
div{
color: #fff;
font-size: 30px;
padding: 20px;
}
@for $i from 1 through length($bgcloors){
.item-#{$i}{
background: nth($bgcloors, $i)
}
}
.item-2{ // 看這裡看這裡
grid-column-start: 2;
grid-column-end: 4;
grid-row-start: 1;
grid-row-end: 2;
}
.item-6{ // 你要先看上面再看這裡
grid-area: 3 / 1 / 4 / 4;
}
}
複製程式碼
先來看看我們的成果
顯示網格線的圖片
參考上圖,我們來分析下css
1、grid元素宣告grid佈局,grid-template-columns
和grid-template-rows
來建立一個兩行三列的網格,但是渲染的結果卻是三行三列,為什麼?我們先接著往下分析
2、css檔案中單獨設定item-2
網格項的位置,
grid-column-start:2
垂直線開始位置為2
grid-column-end:4
垂直線結束位置為4
grid-row-start:1
水平線開始位置為1
grid-row-end:2
水平線結束位置為2
3、通過單獨設定item-2
的位置,把本身要在第一行的item-3
給擠下來了,然後 3、4、5按照300 200 150 排列
4、這時候兩件三列排列完了,但是還有個元素,此時剩下的元素就會獨自佔一行的位置,它的大小一樣會按照網格容器定義的行高列寬來渲染
5、最後我們給item-6
來設定了終極簡寫方式,
終極簡寫:行開始 / 列開始 / 行結束 / 列結束,然後我們把位置對應上
grid-area:3 / 1 / 4 / 4
通過設定網格項樣式屬性,我們可以就實現很多複雜的佈局結構了。
幾種佈局
最後我們結合上面所學到的實現幾個常見佈局
1、左右固定,中間自適應
設定網格容器的 grid-template-columns: 100px 1fr 100px
或者grid-template-columns: 100px auto 100px
就可以實現,再簡單不過了
html
<div class="container">
<div class="left">left</div>
<div class="middle">middle</div>
<div class="right">right</div>
</div>
複製程式碼
css
.container{
display: grid;
grid-template-columns: 100px 1fr 100px;
height: 200px;
}
.container div{
text-align: center;
}
.left{
background: greenyellow;
}
.middle{
background: lightblue;
}
.right{
background: greenyellow;
}
複製程式碼
2、九宮格
使用grid-gap
設定網格項間距 使用fr
來平分
html
<div class="container">
<div class="item">1</div>
<div class="item">2</div>
<div class="item">3</div>
<div class="item">4</div>
<div class="item">5</div>
<div class="item">6</div>
<div class="item">7</div>
<div class="item">8</div>
<div class="item">9</div>
</div>
複製程式碼
css
.container{
display: grid;
grid-template-columns: repeat(3, 1fr);
grid-template-rows: repeat(3, 1fr);
height: 400px;
width: 400px;
grid-gap: 8px;
}
.item{
background: lightskyblue;
}
複製程式碼
顯示如下
3、聖盃、雙飛翼
使用grid-area
設定header
元素和footer
元素位置,結合grid-template-columns
和grid-template-rows
實現佈局
html
<div class="container">
<div class="header">header</div>
<div class="left">left</div>
<div class="body">body</div>
<div class="right">right</div>
<div class="footer">footer</div>
</div>
複製程式碼
css
.container{
display: grid;
grid-template-columns: 100px 1fr 100px;
grid-template-rows: 50px 300px 50px;
}
.header{
grid-area: 1 / 1 / 2 / 4;
}
.footer{
grid-area: 3 / 1 / 4 / 4;
}
.header{
background: lightsalmon;
}
.left{
background: lightseagreen;
}
.body{
background: lightslategray;
}
.right{
background: lightyellow;
}
.footer{
background: yellowgreen;
}
複製程式碼