圣杯布局和双飞翼布局的布局要求
- 三列布局,两边宽度固定,中间宽度自适应
- 中间栏在浏览器中要优先渲染 (这就对DOM结构有了要求,center的div必须在最上面)
- 允许任意列的高度最高
圣杯布局
CSS布局
body {
// min-widthd的计算为 left-div-width * 2 + right-div-width
// 因为在left-div之中采用了relative定位(也可以使用transform)
// 200 * 2 + 150
min-width: 550px;
}
// 或者也可在container上设置min-width
#container {
padding-left: 200px;
padding-right: 150px;
}
#container::after {
content: '';
display: block;
visibility: hidden;
clear: both;
}
#container .column {
float: left;
}
#center {
width: 100%;
background: yellow;
}
#left {
width: 200px;
margin-left: -100%;
position: relative;
left: -200px;
background: aqua;
}
#right {
width: 150px;
margin-right: -150px;
background: aqua;
}
#footer {
clear: both;
}
DOM结构
<body>
<div id="header"></div>
<div id="container">
<div id="center" class="column">center</div>
<div id="left" class="column">left</div>
<div id="right" class="column">right</div>
</div>
<div id="footer"></div>
</body>
双飞翼布局
双飞翼CSS代码
body {
// 对于双飞翼布局而言,min-width的计算只需要left-div-width + right-div-width即可
// 此处为200 + 150
// 但为了实际效果增加了一定的宽度
min-width: 500px;
}
#container {
width: 100%;
}
.column {
float: left;
}
#center {
margin-left: 200px;
margin-right: 150px;
}
#left {
width: 200px;
margin-left: -100%;
}
#right {
width: 150px;
margin-left: -150px;
}
#footer {
clear: both;
}
双飞翼DOM结构
<body>
<div id="header"></div>
<div id="container" class="column">
<div id="center"></div>
</div>
<div id="left" class="column"></div>
<div id="right" class="column"></div>
<div id="footer"></div>
<body>
使用box-sizing可以去掉container
新的CSS布局
body {
min-width: 500px;
}
.column {
float: left;
}
// 利用padding取代margin
// 但是存在一个问题就是padding是可能有颜色的,若padding有颜色且两边的不足以盖掉padding的高度时会有缺陷
#center {
padding-left: 200px;
padding-right: 150px;
box-sizing: border-box;
width: 100%;
}
#left {
width: 200px;
margin-left: -100%;
}
#right {
width: 150px;
margin-left: -150px;
}
#footer {
clear: both;
}
新的DOM结构
<body>
<div id="header"></div>
<div id="center" class='column'></div>
<div id="left" class="column"></div>
<div id="right" class="column"></div>
<div id="footer"></div>
<body>
使用flex布局
flex布局的CSS代码
#container {
display: flex;
}
#center {
flex: 1;
}
#left {
// flex: flex-grow flex-shrink flex-basis
flex: 0 0 200px;
// order属性用于改变div的顺序
order: -1;
}
#right {
flex: 0 0 150px;
}
flex布局的DOM结构
<div id="container">
<div id="center"></div>
<div id="left"></div>
<div id="right"></div>
</div>
使用绝对定位来进行布局
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>实现三栏水平布局之绝对定位布局</title>
<style type="text/css">
.container{
position: relative;
}
.main,.right,.left{
top: 0;
height: 130px;
}
.main{
margin: 0 300px 0 200px;
background-color: blue;
}
.right{
position: absolute;
width: 300px;
right: 0;
background-color: red;
}
.left{
position: absolute;
width: 200px;
background-color: green;
left: 0;
}
</style>
</head>
<body>
// 注意此处会出现问题,因为此处的main区块并没有使用float或是绝对定位,所以在main之前的空格字符会占据一行,此时的三栏顶部是不对齐的,可以将空格去掉或是将父元素的字体大小设为0来解决这个问题。
<div class="container">
<div class="main">main</div>
<div class="left">left</div>
<div class="right">right</div>
</div>
</body>
</html>
利用BFC原理来实现圣杯布局
BFC原理中指出,BFC块不与外部float的块有重叠部分,所以可以让左右两栏float,且宽度固定,中间栏是一个BFC,实现中间栏自适应
总结
对比双飞翼布局和圣杯布局可以发现,圣杯布局的DOM结构更易理解,但是所需的min-width较大,这是由于左边的div采用了margin-left和relative的结果,导致在计算min-width时需要计算两边左边div的宽度。
若不考虑兼容性问题,那么使用border-box和flex两者是最简单的
网友评论