三欄式佈局是眾多網頁的常規佈局之一,我們在採用三欄式佈局時所提出的要求一般是左欄與右欄定寬,中間部分寬度自適應,中間部分作為內容主體,我們需要將其放在左欄與右欄之前來達到優先渲染的效果。 2006年Matthew Levine在《A LIST APART》上發表了一篇名為 "《In Search o ...
三欄式佈局是眾多網頁的常規佈局之一,我們在採用三欄式佈局時所提出的要求一般是左欄與右欄定寬,中間部分寬度自適應,中間部分作為內容主體,我們需要將其放在左欄與右欄之前來達到優先渲染的效果。
2006年Matthew Levine在《A LIST APART》上發表了一篇名為《In Search of the Holy Grail》的文章,提出了聖杯佈局的思路。利用負外邊距來實現我們需要的效果,充分體現了CSS的藝術與負外邊距的強大。
之後淘寶提出了為了實現同樣的效果提出了雙飛翼佈局的思路,同樣使用了負外邊距來移動欄目從而達到目的。因此,聖杯佈局和雙飛翼佈局有著相似的思路,但是在某些細節上也有不同點。
相同點
首先,我們建立好左中右三欄,因為中間欄需要優先渲染,我們將其放在最前面。
<div id="content">
<div id="main">main</div>
<div id="left">left</div>
<div id="right">right</div>
</div>
要實現左中右的水平排列,我們要將塊狀元素浮動。
#main,#left,#right{
float: left;
}
假設左欄定寬200px,右欄定寬120px。(為了看清楚效果,我們暫時為三欄設置一個背景色,同時設置不同的高度以便觀察div之間是否重疊)
#main,#left,#right{
float: left;
}
#left{
background-color: red;
height: 100px;
width: 200px;
margin-left: -100%;
}
#main{
background-color: green;
height: 150px;
width: 100%;
}
#right{
background-color: blue;
height: 100px;
width: 120px;
}
得到如下效果:
接下來就要使用到強大的負外邊距了,我們先處理左欄,因為中間欄的寬度為100%,所以左欄被擠到下麵去了。現在left要到最左邊的位置,所以我們在left的樣式下輸入:
margin-left: -100%;
可以看到left已經順利的被拉回來了。
right同理,它靠在最右邊。所以輸入:
margin-left:-120px;
得到效果:
以上的步驟,聖杯佈局和雙飛翼佈局是一模一樣的。
不同點
聖杯佈局
經過以上的設置,出現了一個問題,就是left、right都和main重疊了,我們需要把main縮回來,現在它的寬度充滿了整個父元素content,並且隨著父元素的變化而變化,我們對父元素進行設置。
#content{
padding: 0 120px 0 200px;
}
但是left和right都在content里,也受到影響被拉進來了。
所以我們要分別讓left往左移,right往右移到它們該在的位置上去,為了讓它們移動,我們需要在left和right的樣式下設置:
position: relative;
並且對left設置:
left: -200px;
對right設置:
right:-120px;
這樣我們就能的到我們所想要的三欄式佈局的效果了。
聖杯佈局CSS代碼:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>三欄式佈局</title>
<style type="text/css">
*{
margin:0;
padding:0;
}
#main,#left,#right{
float: left;
}
#left{
background-color: red;
height: 100px;
width: 200px;
margin-left: -100%;
position: relative;
left: -200px;
}
#main{
background-color: green;
height: 150px;
width: 100%;
}
#right{
background-color: blue;
height: 100px;
width: 120px;
margin-left: -120px;
position: relative;
right: -120px;
}
#content{
padding: 0 120px 0 200px;
}
</style>
</head>
<body>
<div id="content">
<div id="main">main</div>
<div id="left">left</div>
<div id="right">right</div>
</div>
</body>
</html>
雙飛翼佈局
面臨同樣的問題,聖杯佈局是對三欄的父元素的內邊距進行了設置,而雙飛翼佈局則是從另一個角度入手。既然左右兩邊要被left和right獨享,那main就不要這兩邊了,那就不會重疊了。
我們創造一個新的div在main的裡面,並且把內容都放在這個main的子元素里。
<div id="main"><div id="main_in">main</div></div>
並且給它設置左右的外邊距,讓出左右欄目的位置就可以實現我們需要的效果了。
#main_in{
background-color: grey;
height: 150px;
margin-left: 200px;
margin-right: 120px;
}
效果如下:
(去掉main的背景色即可,效果圖沒有去掉是為了方便展示main_in的效果!)
雙飛翼佈局代碼:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>三欄式佈局</title>
<style type="text/css">
*{
margin:0;
padding:0;
}
#main,#left,#right{
float: left;
}
#left{
background-color: red;
height: 100px;
width: 200px;
margin-left: -100%;
}
#main{
background-color: green;
height: 150px;
width: 100%;
}
#right{
background-color: blue;
height: 100px;
width: 120px;
margin-left: -120px;
}
#main_in{
background-color: grey;
height: 150px;
margin-left: 200px;
margin-right: 120px;
}
</style>
</head>
<body>
<div id="content">
<div id="main"><div id="main_in">main</div></div>
<div id="left">left</div>
<div id="right">right</div>
</div>
</body>
</html>