在我们前端开发时,经常会遇到不同的场景页面布局问题,页面框架搭建是前端开发基础,也是十分重要的一环。本文先是对页面开发基本流程思路进行了总结,在此基础上对 CSS 布局常见方案进行梳理,涉及水平垂直居中、单列布局、两栏布局、圣杯布局、双飞翼布局、等高布局以及粘带布局。

常见的版心宽度:
行间距分为四条线:顶线、中线、基线、底线。

行间距是基线到基线的距离,设置给行高。
行内元素水平垂直居中常用方法有两种:
块级元素居中分为:
公共代码
<head>
<meta charset="utf-8">
<title>公共代码</title>
<style>
.father{
width: 500px;
height: 300px;
border: 1px solid red;
}
.son{
width: 100px;
height: 100px;
background-color:red;
}
</style>
</head>
<body>
<div class="father">
<div class="son"></div>
</div>
</body>

水平居中:margin:0 auto

垂直居中:margin-top

.son {
margin: 0 auto;
margin-top:100px;
}
.father {
position: relative;
}
.son {
position: absolute;
left: 50%;
margin-left: -50%;
top: 50%;
margin-top: -50%;
}
.father {
position: relative;
}
.son {
position: absolute;
margin: auto;
left: 0;
right: 0;
top: 0;
bottom: 0;
}
不固定宽高的方法是可以覆盖上面固定宽高的方法
.father{
position: relative;
}
.son{
position: absolute;
left: 50%;
transform: translateX(-50%);
top: 50%;
transform: translateY(-50%);
}
.father{
text-align: center;
}
.son {
display: inline-block;
}
.father{
display: table-cell;
vertical-align: middle;
}
.father {
display: flex;
justify-content: center;
align-items: center;
}
头部、内容、底部

<head>
<meta charset="utf-8">
<title>单列布局-普通布局</title>
<style>
.header{
margin:0 auto;
max-width: 960px;
height:100px;
background-color:pink;
}
.container{
margin: 0 auto;
max-width: 960px;
height: 500px;
background-color: aquamarine;
}
.footer{
margin: 0 auto;
max-width: 960px;
height: 100px;
background-color:skyblue;
}
</style>
</head>
<body>
<div class="header"></div>
<div class="content"></div>
<div class="footer"></div>
</body>
内容区域(版心)为 960px,采用 margin:0 auto 实现水平居中

<head>
<meta charset="utf-8">
<title>普通布局-内容居中</title>
<style>
.header{
margin:0 auto;
height:100px;
background-color:pink;
}
.content{
margin: 0 auto;
height: 500px;
width:960px;
background-color: aquamarine;
}
.footer{
margin: 0 auto;
height: 100px;
background-color: skyblue;
}
</style>
</head>
<body>
<div class="header"></div>
<div class="center">
<div class="content"></div>
</div>
<div class="footer"></div>
</body>
所谓两栏布局是指:左侧定宽,右侧自适应。
实现思路:
普通流体 BFC 后(float:left)和浮动元素不会产生交集,顺着浮动元素形成自己的封闭上下文。

<head>
<meta charset="utf-8">
<title>两栏布局-float</title>
<style>
.left {
width: 300px;
background-color: pink;
float: left;
height:500px;
}
.right {
width:100%;
background-color: aquamarine;
height:500px;
}
</style>
</head>
<body>
<div class="warp">
<div class="left">定宽</div>
<div class="right">自适应</div>
</div>
</body>
实现思路:父元素开启弹性空间,左盒子设置固定宽度,右盒子 flex:1

<head>
<meta charset="utf-8">
<title>两栏布局-flex</title>
<style>
.warp{
display:flex;
}
.left {
width: 300px;
background-color: pink;
height:500px;
}
.right {
background-color: aquamarine;
height:500px;
flex:1
}
</style>
</head>
<body>
<div class="warp">
<div class="left">定宽</div>
<div class="right">自适应</div>
</div>
</body>


<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>flex布局</title>
<style>
*{
margin: 0;
padding: 0;
}
.box{
min-width: 800px;
height: 600px;
background: gray;
display: flex;
}
.left{
width:200px;
height: 600px;
background: pink;
order:-1
}
.center{
height: 600px;
background: aquamarine;
width:100%;
flex:1
order:1
}
.right{
width:200px;
height: 600px;
background: skyblue;
order:2
}
</style>
</head>
<body>
<div class="box">
<div class="center">中哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈中</div>
<div class="left">左</div>
<div class="right">右</div>
</div>
</body>
</html>
三个盒子都设置浮动

左盒子走负 margin-left:100%,右盒子走负自身的宽度

大盒子 padding left 和 right 左右盒子宽度

左右盒子相对定位,left,right - 往回走

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>圣杯布局</title>
<style type="text/css">
*{
margin: 0;
padding: 0;
}
.box{
min-width: 800px;
height: 600px;
padding-left:200px;
padding-right:200px;
}
.left{
float:left;
width:200px;
height: 600px;
margin-left:-100%;
background: pink;
position:relative;
left:-200px;
}
.center{
float:left;
width: 100%;
height: 600px;
background: aquamarine;
}
.right{
float:left;
width:200px;
height: 600px;
margin-left:-200px;
background: skyblue;
position:relative;
right:-200px;
}
</style>
</head>
<body>
<div class="box">
<div class="center">中哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈中</div>
<div class="left">左</div>
<div class="right">右</div>
</body>
</html>
三个盒子都设置浮动

左盒子走负 margin-left:100%,右盒子走负自身的宽度

调整中间盒子 margin

<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>双飞翼布局</title>
<style type="text/css">
*{
margin: 0;
padding: 0;
}
.box{
min-width: 800px;
height: 600px;
}
.left{
float:left;
width:200px;
height: 600px;
margin-left:-100%;
background: pink;
}
.content{
margin-left:200px;
margin-right:200px;
background-color: yellowgreen;
}
.center{
float:left;
width: 100%;
height: 600px;
background: aquamarine;
}
.right{
float:left;
width:200px;
height: 600px;
margin-left:-200px;
background: skyblue;
}
</style>
</head>
<body>
<div class="box">
<div class="center">
<div class="content">
中哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈哈中
</div>
</div>
<div class="left">左</div>
<div class="right">右</div>
</body>
</html>
圣杯布局双飞翼布局总结:
等高布局是指子元素在父元素中高度相等的布局方式。

正值内边距 + 负值外边距,padding 和 margin 相互抵消的效果
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>等高布局-正值内边距+负值外边距</title>
<style type="text/css">
*{
margin:0;
padding:0;
}
.left,
.right {
width:50%;
float:left;
text-align:center;
background-color:aquamarine;
padding-bottom:9999px;
margin-bottom:-9999px;
}
.right{
background-color: pink;
}
.container {
width:1200px;
margin:0 auto;
overflow:hidden;
}
</style>
</head>
<body>
<div class="container">
<div class="left">111111111111</div>
<div class="right">
333333333333333333333333333333333333333333333333
333333333333333333333333333333333333333333333333
333333333333333333333333333333333333333333333333
</div>
</div>
</body>
</html>
弊端:使用 table 布局对一些属性设置有一定限制
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>等高布局-table布局</title>
<style type="text/css">
*{
margin:0;
padding:0;
}
.center,
.left,
.right {
width:33.3%;
text-align:center;
display: table-cell;
background-color:aquamarine;
}
.container {
display:table;
width:1200px;
margin:0 auto;
}
</style>
</head>
<body>
<div class="container">
<div class="left">111111111111</div>
<div class="center">22222222222222222222222222</div>
<div class="right">
333333333333333333333333333333333333333333333333
333333333333333333333333333333333333333333333333
333333333333333333333333333333333333333333333333
</div>
</div>
</body>
</html>
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>等高布局-flex布局</title>
<style type="text/css">
*{
margin:0;
padding:0;
}
.center,
.left,
.right {
text-align:center;
background-color:aquamarine;
flex:1
}
.container {
display:flex;
width:1200px;
margin:0 auto;
}
</style>
</head>
<body>
<div class="container">
<div class="left">111111111111</div>
<div class="center">22222222222222222222222222</div>
<div class="right">
333333333333333333333333333333333333333333333333
333333333333333333333333333333333333333333333333
333333333333333333333333333333333333333333333333
</div>
</div>
</body>
</html>
4、grid 布局
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>grid布局</title>
<style>
*{
margin:0;
padding:0;
}
.center,
.left,
.right {
text-align:center;
background-color:aquamarine;
flex:1
}
.container {
display:grid;
grid-auto-flow: column;
width:1200px;
margin:0 auto;
}
</style>
</head>
<body>
<div class="container">
<div class="left">111111111111</div>
<div class="center">22222222222222222222222222</div>
<div class="right">
333333333333333333333333333333333333333333333333
333333333333333333333333333333333333333333333333
333333333333333333333333333333333333333333333333
</div>
</div>
</body>
</html>
当 main 的高度足够长的时候,footer 会跟在其后面。 当 main 元素比较短的时候 (比如小于屏幕宽度),footer 元素能够粘带在屏幕底部。

实现思路: 用一个元素将 footer 以外的内容包起来,设置负的 margin-bottom,他正好等于 footer 的高度。
<html>
<head>
<meta charset="UTF-8">
<title>粘带布局-负margin-bottom</title>
<style>
html, body {
height: 100%;
margin: 0;
text-align:center;
}
#wrap{
width: 100%;
min-height:100%;
background-color: pink;
}
#main{
padding-bottom: 30px;
}
#footer{
width: 100%;
height: 30px;
background-color: aquamarine;
margin-top: -30px;
}
</style>
</head>
<body>
<div>
<div>
<p>main</p>
<p>main</p>
</div>
</div>
<div>footer</div>
</body>
</html>
<html>
<head>
<meta charset="UTF-8">
<title>粘带布局-footer 上用负的 margin-top</title>
<style>
html, body {
height: 100%;
margin: 0;
text-align:center;
}
#wrap{
width: 100%;
min-height:100%;
background-color: pink;
}
#main{
padding-bottom: 30px;
}
#footer{
width: 100%;
height: 30px;
background-color: aquamarine;
margin-top: -30px;
}
</style>
</head>
<body>
<div>
<div>
<p>main</p>
<p>main</p>
</div>
</div>
<div>footer</div>
</body>
</html>
<html>
<head>
<meta charset="UTF-8">
<title>粘带布局-flex</title>
<style>
html, body {
margin: 0;
padding:0;
text-align:center;
}
#warp{
height:100%;
display: flex;
flex-direction: column;
}
#main{
background-color: pink;
flex:1;
}
#footer{
background-color: aquamarine;
height: 30px;
}
</style>
</head>
<body>
<div>
<div>
<p>main</p>
<p>main</p>
</div>
</div>
<div>footer</div>
</body>
</html>
