背景
又雙叒叕被老大拉來頂替前端小姐姐擼程式碼,接觸到了Flex
佈局,以前只聽過沒用過,碰巧這次要揭露她的面紗,就記錄一下。接觸前端的同學都應該知道網頁佈局是CSS
的一個重點,佈局的傳統方案都是基於盒模型
的,依賴於 display
、position
、float
等屬性進行網頁佈局。然而對於那些複雜特殊的佈局實現起來不是很方便,比如讓文字行內垂直居中,我們需要容器高度height
和行高line-height
一樣。Flex佈局呼之欲出,它可以簡便、完整、響應式的實現各種佈局,下面就介紹下Flex
佈局。
瞭解一些基礎知識
什麼是 Flex 佈局
Flex 是 Flexible Box,字面意思理解為彈性盒子。
任何一個容器都可以指定為Flex佈局
.box{
display:flex;
}
.box{
display: -webkit-inline-flex;
display:inline-flex; /*行內 flex 佈局*/
}
.box{
display:-webkit-flex;
display:flex; /*Webkit 核心的瀏覽器,必須加上-webkit字首*/
}
基本概念
在使用Flex佈局之前,我們需要知道,什麼是容器,什麼是專案,什麼是主軸、交叉軸,主軸開始位置,主軸結束位置,交叉軸開始位置,交叉軸結束位置,單個專案佔據的主軸空間和交叉軸空間。
- 容器:採用 Flex 佈局的元素,簡稱容器(flex container)
- 專案:容器所有子元素自動成為容器成員,簡稱專案(flex item)
- 容器預設存在兩根軸:水平的主軸(main axis)和垂直的交叉軸(cross axis)
- 主軸的開始位置叫做 main start,結束位置叫做 main end;交叉軸的開始位置叫做 cross start,結束位置叫做 cross end
- 單個專案佔據的主軸空間叫做 main size,佔據的交叉軸空間叫做 cross size
容器的屬性
有6個屬性可以設定在容器上,分別是flex-direction
、flex-wrap
、flex-flow
、justify-content
、align-items
、align-content
。
1、flex-direction 屬性決定主軸的方向(即專案的排列方向)
.box {
flex-direction: row | row-reverse | column | column-reverse;
/*水平方向,起點在左端|水平方向,起點在右端|垂直方向,起點在上沿|垂直方向,起點在下沿*/
}
2、flex-wrap 屬性預設情況下,專案都排在一條線(又稱"軸線")上。它定義,如果一條軸線排不下,如何換行
.box{
flex-wrap: nowrap | wrap | wrap-reverse;
/*不換行|換行,第一行在上方|換行,第一行在下方*/
}
3、flex-flow 屬性是 flex-direction 屬性和 flex-wrap 屬性的簡寫形式,預設值為 row nowrap
.box{
flex-flow: flex-direction | flex-wrap;
}
4、justify-content 屬性定義了專案在主軸上的對齊方式
.box {
justify-content: flex-start | flex-end | center | space-between | space-around;
/*
左對齊|右對齊|居中對齊|兩端對齊,專案之前的間隔都相等|每個專案兩側的間隔相等。
所以,專案之間的間隔比專案與邊框的間隔大一倍
*/
}
5、align-items 屬性定義專案在交叉軸上如何對齊
.box {
align-items: flex-start | flex-end | center | baseline | stretch;
/*
起點對齊|終點對齊|中點對齊|專案的第一行文字的基線對齊|如果專案未設定高度或設為auto,
將佔滿整個容器的高度
*/
}
6、align-content 屬性定義了多根軸線的對齊方式。如果專案只有一根軸線,該屬性不起作用
.box {
align-content: flex-start | flex-end | center | space-between | space-around | stretch;
}
/*
與交叉軸的起點對齊|與交叉軸的終點對齊|與交叉軸的中點對齊|與交叉軸兩端對齊,軸線之間的間隔平均分佈|
每根軸線兩側的間隔都相等。所以,軸線之間的間隔比軸線與邊框的間隔大一倍|軸線佔滿整個交叉軸
*/
自己理解的,僅供參考:
主要配置容器的屬性:主軸方向,換行方式,專案對齊方式,簡稱方杭琪(諧音像朋友的名字)
專案的屬性
有6個屬性設定在專案上,分別是order
、flex-grow
、flex-shrink
、flex-basis
、flex
、align-self
。
1、order 屬性定義專案的排列順序。數值越小,排列越靠前,預設為0
.item {
order: <integer>;
}
2、flex-grow 屬性定義專案的放大比例,預設為0,即如果存在剩餘空間,也不放大
.item {
flex-grow: <number>;; /* default 0 */
}
3、flex-shrink 屬性定義了專案的縮小比例,預設為1,即如果空間不足,該專案將縮小
.item {
flex-shrink: <number>;; /* default 1 */
}
4、flex-basis 屬性定義了在分配多餘空間之前,專案佔據的主軸空間(main size)。瀏覽器根據這個屬性,計算主軸是否有多餘空間。它的預設值為auto,即專案的本來大小
.item {
flex-basis: <length> | auto; /* default auto */
}
5、flex 屬性是 flex-grow, flex-shrink 和 flex-basis 的簡寫,預設值為0 1 auto。後兩個屬性可選
.item {
flex: none | [ <'flex-grow'> <'flex-shrink'>? || <'flex-basis'> ]
}
6、align-self 屬性允許單個專案有與其他專案不一樣的對齊方式,可覆蓋 align-items 屬性。預設值為 auto ,表示繼承父元素的 align-items 屬性,如果沒有父元素,則等同於 stretch
.item {
align-self: auto | flex-start | flex-end | center | baseline | stretch;
}
實踐一下
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
<link href="/css/style.css" rel="stylesheet" type="text/css" />
</head>
<body>
<div class="first-face">
<span class="pip"></span>
</div>
<div class="second-face">
<span class="pip"></span>
<span class="pip"></span>
</div>
<div class="third-face">
<span class="pip"></span>
<span class="pip"></span>
<span class="pip"></span>
</div>
<div class="fourth-face">
<div class="column">
<span class="pip"></span>
<span class="pip"></span>
</div>
<div class="column">
<span class="pip"></span>
<span class="pip"></span>
</div>
</div>
<div class="fifth-face">
<div class="column">
<span class="pip"></span>
<span class="pip"></span>
</div>
<div class="column">
<span class="pip"></span>
</div>
<div class="column">
<span class="pip"></span>
<span class="pip"></span>
</div>
</div>
<div class="sixth-face">
<div class="column">
<span class="pip"></span>
<span class="pip"></span>
<span class="pip"></span>
</div>
<div class="column">
<span class="pip"></span>
<span class="pip"></span>
<span class="pip"></span>
</div>
</div>
</body>
</html>
樣式檔案 css/style.css
.first-face {
display: flex;
justify-content: center;
align-items: center;
}
.second-face {
display: flex;
justify-content: space-between;
}
.second-face .pip:nth-of-type(2) {
align-self: flex-end;
}
.third-face {
display: flex;
justify-content: space-between;
}
.third-face .pip:nth-of-type(2) {
align-self: center;
}
.third-face .pip:nth-of-type(3) {
align-self: flex-end;
}
.fourth-face, .sixth-face {
display: flex;
justify-content: space-between;
}
.fourth-face .column, .sixth-face .column {
display: flex;
flex-direction: column;
justify-content: space-between;
}
.fifth-face {
display: flex;
justify-content: space-between;
}
.fifth-face .column {
display: flex;
flex-direction: column;
justify-content: space-between;
}
.fifth-face .column:nth-of-type(2) {
justify-content: center;
}
/* OTHER STYLES */
* {
box-sizing: border-box;
}
html, body {
height: 100%;
}
body {
display: flex;
align-items: center;
justify-content: center;
vertical-align: center;
flex-wrap: wrap;
align-content: center;
font-family: 'Open Sans', sans-serif;
background: linear-gradient(top, #222, #333);
}
[class$="face"] {
margin: 16px;
padding: 4px;
background-color: #e7e7e7;
width: 104px;
height: 104px;
object-fit: contain;
box-shadow:
inset 0 5px white,
inset 0 -5px #bbb,
inset 5px 0 #d7d7d7,
inset -5px 0 #d7d7d7;
border-radius: 10%;
}
.pip {
display: block;
width: 24px;
height: 24px;
border-radius: 50%;
margin: 4px;
background-color: #333;
box-shadow: inset 0 3px #111, inset 0 -3px #555;
}
實踐結果展示
備註:感謝阮一峰大神的文章【Flex佈局教程】