今天主要来介绍CSS中Flex和Grid的相关应用,这两个对于网页排版来说是非常好用的工具。
Flex——有弹性的盒子
Flex是一种一维空间的设置,可以设置子级元素在同一行或者同一列的样式。
使用时要用display:flex来设置一下。
Flex Box
- 控制盒子的流向
对于盒子的流向,我们可以利用flex-direction来设置,常用的参数值如下:
row 按行从左向右排列;row-reverse按行从右向左排列;
column按列从上向下排列;column-reverse按列从下到上排列。
如果设置为row是这样:
那么设置为row-reverse就是如下所示:
同理,如果column是如下所示:
那么column-reverse就是如下所示:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Flex——有弹性的盒子</title>
<style>
.box {
display: flex;
/* 这里的参数值还可以写为row/row-reverse/column-reverse */
flex-direction: column;
justify-content:space-evenly;
align-items:flex-end;
}
.A {
background-color: blue;width: 100px;height: 100px;
}
.B {
background-color: green;width: 100px;height: 100px;
}
.C {
background-color: pink;width: 100px;height: 100px;
}
</style>
</head>
<body>
<div class="box">
<div class="A"></div>
<div class="B"></div>
<div class="C"></div>
</div>
</body>
</html>
- 同一行中主轴方向的设置
主轴就是水平方向的中线,围绕主轴可以对于对齐方式和空隙结构,利用justify-content进行设置。
如果使用flex-start/flex-end/center,子级元素之间就没有空隙,并且分别为左对齐、右对齐和居中的效果,如下所示:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Flex——有弹性的盒子</title>
<style>
.box {
display: flex;
/
flex-direction: row;
/* 这里还可以设置为flex-start/center */
justify-content:flex-end;
align-items:flex-end;
}
.A {
background-color: blue;width: 100px;height: 100px;
}
.B {
background-color: green;width: 100px;height: 100px;
}
.C {
background-color: pink;width: 100px;height: 100px;
}
</style>
</head>
<body>
<div class="box">
<div class="A"></div>
<div class="B"></div>
<div class="C"></div>
</div>
</body>
</html>
如果想要得到有空隙的效果,可以使用如下的值:space-between/space-around/space-evenly,它们的效果分别如下所示:
如上,space-between是指空隙仅仅存在于子级元素之间。
space-around和space-evenly看起来没有太大的差别,这里找到了一张图片介绍了它们的不同之处。
就是这样的区别,图源:(如有侵权,请联系删除)Day 14: space-around vs space-evenly | SamanthaMing.comhttps://www.samanthaming.com/flexbox30/14-space-around-vs-space-evenly/
- 同一行中副轴方向的设置
所谓副轴,就是中轴线,即垂直方向的中线。想要设置在纵向的位置,就可以使用align-items进行设置,常用的值有以下几个:flex-start/flex-end/center/stretch,它们的效果分别如下:
flex-start:上边缘对齐
flex-end:下边缘对齐
center:中心对齐
stretch:占据能够占据的所有空间
flex-start/flex-end/center时的代码如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Flex——有弹性的盒子</title>
<style>
.box {
display: flex;
flex-direction: row;
justify-content:space-evenly;
/* 上/下/中间对齐,还可以写flex-start/flex-end */
align-items:center;
}
.A {
background-color: blue;width: 100px;height: 200px;
}
.B {
background-color: green;width: 100px;height: 100px;
}
.C {
background-color: pink;width: 100px;height: 300px;
}
</style>
</head>
<body>
<div class="box">
<div class="A"></div>
<div class="B"></div>
<div class="C"></div>
</div>
</body>
</html>
当align-items的值设置为stretch时,我将box类的高度设置为600px,并取消了对于ABC类高度的设定,意在让大家看看stretch时能够占据所有可以占据的空间,代码如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Flex——有弹性的盒子</title>
<style>
.box {
display: flex;
flex-direction: row;
justify-content:space-evenly;
align-items:stretch;
height: 600px;
}
.A {
background-color: blue;width: 100px;
}
.B {
background-color: green;width: 100px;
}
.C {
background-color: pink;width: 100px;
}
</style>
</head>
<body>
<div class="box">
<div class="A"></div>
<div class="B"></div>
<div class="C"></div>
</div>
</body>
</html>
- 特殊元素的设置
上述的设置都是对于所有子级元素的设置,如果想要将其中的某一些设置为其它值该怎么办呢?这里我们可以使用align-self进行设置。例如,我想达到如下的效果:
就像这里,蓝色的盒子和粉色的盒子都是下边缘对齐,但是绿色盒子是上边缘对齐,这种效果我们应当如何设置?
我们先将三个盒子的align-items设置为flex-end,再写一个绿色盒子专属的选择器,将align-self设置为flex-start,根据选择器的优先级, 绿色盒子会上边缘对齐,代码如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Flex——有弹性的盒子</title>
<style>
.box {
display: flex;
flex-direction: row;
justify-content:space-evenly;
align-items:flex-end;
height: 400px;
}
.A {
background-color: blue;width: 100px;height: 200px;
}
.B {
background-color: green;width: 100px;height: 100px;
/* 特殊元素设置,根据选择器的优先级应当执行flex-start */
align-self: flex-start;
}
.C {
background-color: pink;width: 100px;height: 300px;
}
</style>
</head>
<body>
<div class="box">
<div class="A"></div>
<div class="B"></div>
<div class="C"></div>
</div>
</body>
</html>
Flexibility
接下来介绍一些Flex的性质:
flex-basis:弹性盒的原始长度
flex-grow:反映存在空间时的伸展能力
flex-shrink:反映空间不足时的收缩能力
例如,我将三个盒子的初始长度设置为1000px,将收缩能力设置为2,1,1,即意味着第一个盒子收缩的长度时第二个和第三个盒子的2倍。
通过点击F12进入调试工具,我们发现三个盒子的宽度依次为260px、630px、630px,也就是说分别收缩了740px、370px、370px。
现在我再将盒子的宽度设置为100px,将伸展能力设置为2,1,1,即意味着第一个盒子的伸展量时第二个和第三个盒子的2倍。
通过点击F12进入调试工具,我们发现三个盒子的宽度依次为710px、405px、405px,也就是说分别收缩了610px、305px、305px。
Grid——将网页划分为网格
如果说Flex的适用范围仅仅是一维空间,那么Grid就是二维平面的网页布局工具。
要使用grid,我们需要先进行display:grid设置。
栅格划分
例如下面的效果:
想要达到这种效果,可以利用如下对行和列分别进行划分:
grid-template-rows/grid-template-columns
设置的时候,需要几行/几列就在对应行/列属性后面写几个值。这里的值,既可以写具体的xxpx,又可以写xxfr(可以理解为xx份),还可以将二者混用。混用的时候,先给绝对长度的分配地方,剩下的就按照分数比例进行空间分配。上面的效果完整的代码如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Grid</title>
<style>
.grid-container {
display: grid;
/* 列的划分 */
grid-template-rows: repeat(2,200px);
/* 行的划分 */
grid-template-columns: 200px 200px 200px;
}
.A {
background-color: blue;
}
.B {
background-color: red;
}
.C {
background-color: green;
}
.D {
background-color: gold;
}
.E {
background-color: salmon;
}
.F {
background-color: black;
}
</style>
</head>
<body>
<div class="grid-container">
<div class="A"></div>
<div class="B"></div>
<div class="C"></div>
<div class="D"></div>
<div class="E"></div>
<div class="F"></div>
</div>
</body>
</html>
对了,相同的值可以用repeat来写,即repeat(个数,长度)。
当然这个时候盒子也可以有自身的宽度和高度,就像下面这样:
只需要写一个对于所有子级元素的选择器,在其中设置宽度和高度就可以了。
那么这些子级元素是不是就只能在左上角呢,能不能改变它们的位置呢?我们可以通过和Flex中相同的属性来进行设置,即justify-items和align-items,设置参数值同Flex不再赘述,这里仅仅举例说明居中时的代码。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Grid</title>
<style>
.grid-container {
display: grid;
grid-template-rows: repeat(2,200px);
grid-template-columns: 200px 200px 200px;
/* 在水平方向居中 */
justify-items:center;
/* 在垂直方向居中 */
align-items: center;
}
.item {
height: 100px;width: 100px;
}
.A {
background-color: blue;
}
.B {
background-color: red;
}
.C {
background-color: green;
}
.D {
background-color: gold;
}
.E {
background-color: salmon;
}
.F {
background-color: black;
}
</style>
</head>
<body>
<div class="grid-container">
<div class="A item"></div>
<div class="B item"></div>
<div class="C item"></div>
<div class="D item"></div>
<div class="E item"></div>
<div class="F item"></div>
</div>
</body>
</html>
间隔设置
这样的间隔设置可以利用column-gap和row-gap分别进行实现,当然如果二者相等可以直接使用gap进行实现。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Grid</title>
<style>
.grid-container {
display: grid;
grid-template-rows: repeat(2,200px);
grid-template-columns: 200px 200px 200px;
/* 间隔 */
gap:24px
}
.A {
background-color: blue;
}
.B {
background-color: red;
}
.C {
background-color: green;
}
.D {
background-color: gold;
}
.E {
background-color: salmon;
}
.F {
background-color: black;
}
</style>
</head>
<body>
<div class="grid-container">
<div class="A"></div>
<div class="B"></div>
<div class="C"></div>
<div class="D"></div>
<div class="E"></div>
<div class="F"></div>
</div>
</body>
</html>
跨行/跨列选择栅格
例如这里的蓝色盒子横跨了两列,我们如何进行设置呢?
我们可以利用grid-column-start和grid-column-end进行设置,前者是开始的位置,后者是结束的位置。将这两个参数值合起来,也可以简写为grid-column,这样写就需要两个参数值,第一个是起始位置,第二个是结束位置。
通过调试工具,我们能够看到,这里的起始位置或者结束位置是对于栅格边缘来说的。
如图,我们要让蓝色盒子横跨两列,也就是说从第一条纵边开始,到第三条纵边结束,所以始末位置分别应该设置为1和3。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Grid</title>
<style>
.grid-container {
display: grid;
grid-template-rows: repeat(3,200px);
grid-template-columns: 200px 200px 200px;
gap:24px
}
.A {
/* 跨列 */
grid-column-start: 1;
grid-column-end: 3;
background-color: blue;
}
.B {
background-color: red;
}
.C {
background-color: green;
}
.D {
background-color: gold;
}
.E {
background-color: salmon;
}
.F {
background-color: black;
}
</style>
</head>
<body>
<div class="grid-container">
<div class="A"></div>
<div class="B"></div>
<div class="C"></div>
<div class="D"></div>
<div class="E"></div>
<div class="F"></div>
</div>
</body>
</html>
当然也有其它写法,比如横跨两列就可以用grid-column:1/span 2来解决,效果是一样的。
如果想要横跨一整行,有没有什么好办法呢?细心的小伙伴发现了纵向的边缘从左向右是整数依次递增,从右向左是负数依次递减。所以,最简单的办法就是grid-column:1/-1。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Grid</title>
<style>
.grid-container {
display: grid;
grid-template-rows: repeat(3,200px);
grid-template-columns: 200px 200px 200px;
gap:24px
}
.A {
grid-column: 1/-1;
background-color: blue;
}
.B {
background-color: red;
}
.C {
background-color: green;
}
.D {
background-color: gold;
}
.E {
background-color: salmon;
}
.F {
background-color: black;
}
</style>
</head>
<body>
<div class="grid-container">
<div class="A"></div>
<div class="B"></div>
<div class="C"></div>
<div class="D"></div>
<div class="E"></div>
<div class="F"></div>
</div>
</body>
</html>
页面设计
如果一个页面,上面需要设计为header,左边要设计为sidebar,中右部要设计为content,下边要设计为footer,有没有什么直观一点的好方法呢?使用grid-template-areas和grid-area结合的方法就可以解决。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Grid页面设计</title>
<style>
.item {
display:grid;
grid-template-rows: repeat(4,200px);
grid-template-columns: 200px 200px 200px 200px;
grid-template-areas:
"header header header header"
"sidebar content content content"
"sidebar content content content"
"footer footer footer footer";
}
.item1 {
background-color: rgb(167,224,8);
grid-area: header;
}
.item2 {
background-color: rgb(197,35,109);
grid-area: sidebar;
}
.item3 {
background-color: rgb(0,0,227);
grid-area: content;
}
.item4 {
background-color: rgb(226,227,9);
grid-area: footer;
}
</style>
</head>
<body>
<div class="item">
<div class="item1"></div>
<div class="item1"></div>
<div class="item1"></div>
<div class="item1"></div>
<div class="item2"></div>
<div class="item3"></div>
<div class="item3"></div>
<div class="item3"></div>
<div class="item2"></div>
<div class="item3"></div>
<div class="item3"></div>
<div class="item3"></div>
<div class="item4"></div>
<div class="item4"></div>
<div class="item4"></div>
<div class="item4"></div>
</div>
</body>
</html>
在上面这段代码之中,grid-template-areas的属性值就非常直观的反映了页面的样式。
今天的分享就到这里了,感谢大家收看,欢迎大家提出宝贵的意见和建议。