line-height
字符实际大小和font-size的关系:
下图中不同字体font-size都是100px设置line-height的值
1.line-height的默认值是normal,上一条中说过,它的高度是ascender+ descender+line gap
2.line-height可以设置为具体的值,比如100px,这个值可以大于content-area的值,也可以小于content-area的值,line-height和content-area的差值叫leading(字体设置时,可以指定初始的leading,即line gap),这个值会等分为两半分别显示在content-area的上方和下方,leading为负值时,也是上下平分
我们看下leading为负值的例子:
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>test</title>
<style>
.div1 {
font-size: 100px;
line-height: 50px;
background-color: red;
}
</style>
</head>
<body>
<div class="div1">div1</div>
</body>
</html>
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>test</title>
<style>
.div1 {
font-size: 100px;
line-height: 50px;
background-color: red;
height: 100px;
}
</style>
</head>
<body>
<div class="div1">div1</div>
</body>
</html>
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>test</title>
<style>
.div1 {
font-size: 100px;
line-height: 50px;
background-color: red;
border: 1px blue solid;
}
.div2 {
font-size: 100px;
line-height: 50px;
background-color: red;
border: 1px blue solid;
}
</style>
</head>
<body>
<div class="div1">div1</div>
<div class="div2">div2</div>
</body>
</html>
3.line-height还可以设置成一个数字
line-height:1 就是一个很糟糕的实践。当 line-height 的值是一个数字时,其实就是相对 font-size 的倍数,而不是相对于 content-area。所以 line-height:1 很有可能使得 virtual-area(line-height) 比 content-area 矮,从而引发很多其他的问题
vertical-align
vertical-align用于调整行内元素(inline,inline-block)在行内的对齐方式,从而改变行内元素的位置,可以用它来实现垂直居中显示等效果
vertical-align对block元素无效
- vertical-align默认是基线(baseline)对齐,即元素的基线跟父元素的基线对齐
字母x的下边缘即基线
1.父元素没有行内元素之前,可以想象里面加个字符x,x的下边缘就是基线(比底部高一点),有了行内子元素,基线是最后一个行内子元素的基线
2.非图片行内元素、非空且overflow属性为visible(默认是visible)的行内元素,基线是最后一个作为内容存在的行内子元素的基线
3.图片、空的行内元素、非空但overflow属性不为visible的行内元素,基线在元素底部
4.纯文字可以看做是特殊的inline元素(跟外面包着span一样)
示例1-图片或空的行内元素底部间隙
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>test</title>
<style>
.div1 {
background: red;
}
.div2 {
display: inline-block;
height: 50px;
width: 50px;
background: blue;
}
</style>
</head>
<body>
<div class="div1">
<div class="div2"></div>
</div>
</body>
</html>
没加入div2前,div1的基线可以在里面加个x确定,加入空的div2(inline-block),div2的基线在底部,它的底部要跟x的底部对齐,所以底下会留有空隙
解决这个空隙的几个方法:
1.div2设置vertical-align: bottom
2.div1设置 font-size: 0px; 字体高度为0,自然没有了基线和底部的距离
3.div2显示为block,block元素不存在基线对齐
如果在div2前面先加入一个x,html按顺序渲染,先渲染字符x,此时行基线在x底部,再加入div2,div2的底部要对齐x的底部,就会撑高div1,保证基线对齐,所以效果跟单独一个div2一样
同样,在后面加入一个x效果也一样
把div2换成img效果也一样
示例2:
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>test</title>
<style>
.div1 {
display: inline-block;
height: 50px;
width: 50px;
background: red;
}
.div2 {
display: inline-block;
height: 50px;
width: 50px;
background: blue;
}
</style>
</head>
<body>
<div class="div1">
</div>
<div class="div2">
div2
</div>
</body>
</html>
效果图:
html按顺序渲染,加入div1后,此行的基线在div1底部,再加入div2,div2的的基线在里面的x字符底部,div2的基线要跟整行的基线对齐,所以出现这个效果,如果div1里面有内容,两个div会并排对齐
- vertical-align:top/bottom
vertical-align:top/bottom是把设置了此属性的行内子元素的上/下边缘(如果定义了height,就是height的边缘,否则是line-height的边缘)跟此行的上/下边缘对齐
实例1
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>test</title>
<style>
.div1 {
height: 100px;
background: red;
}
.div2 {
display: inline-block;
height: 50px;
width: 50px;
background: blue;
vertical-align: bottom;
}
</style>
</head>
<body>
<div class="div1">
<div class="div2">
div2
</div>
</div>
</body>
</html>
运行后发现,vertical-align: bottom没有改变div2的位置,这是因为,div2只是显示在div1的一行里,vertical-align定义的是行内的对齐,div2定义了height,div1的这一行里只有div2,所以高度跟div2一致,他们的显示区域重合,所以top或bottom对齐都是没用的,因为本来就一样高,top和bottom都是重合对齐的
我们在div1里加上line-height试试:
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>test</title>
<style>
.div1 {
height: 100px;
background: red;
line-height: 100px;
}
.div2 {
display: inline-block;
height: 50px;
width: 50px;
background: blue;
vertical-align: bottom;
}
</style>
</head>
<body>
<div class="div1">
<div class="div2">
div2
</div>
</div>
</body>
</html>
效果图:
div1的行高设置为整个div1高度,div2的下边缘要与之对齐,由于line-height的继承性,div2的line-height也是100px,div2中的文字会居中(leading上下平分),所以div2的文字会超出下边缘
我们设置div2的line-height: normal;,效果图如下:
这时候就完全对齐了,div2也可以容纳多行文字,从左上角首行开始显示
再看一个例子
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>test</title>
</head>
<body>
<style type="text/css" rel="stylesheet">
.content {
height: 200px;
background-color: red;
line-height: 200px;
}
</style>
<div class="content">
<span style="background-color: blue;vertical-align: top;line-height: 1;">abcdxp</span>
</div>
</body>
</html>
显示效果:
span的line-height设置为font-size的1倍,但是content-area大于font-size,所以span会往上超出一点
- 指定具体数值来调整元素垂直对齐(正数升高,负数下降)
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<style type="text/css">
</style>
</head>
<body>
<img src="./test.png" style="width: 100px;height: 100px;">
<span style="vertical-align: 40px;">链家地产</span>
</body>
</html>
- vertical-align:middle
将子元素盒子的垂直中点与父盒子的baseline加上父盒子的x-height的一半位置对齐(baseline再向下偏移x-height的一半,x-height是父元素中x元素font-size的一半,要去除这个一半,可以设置父元素fontsize为0)
把上例中vertical-align: 40px改为vertical-align:middle,效果如下:
如何使用 vertical-align:middle让行内子元素在父元素中垂直居中呢?
示例1:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<style type="text/css">
div {
display: inline-block;
}
</style>
</head>
<body>
<div class="div1" style="background-color: aqua;height:100px;width: 100px;">
<div class="div2" style="background-color: blueviolet;height:50px;width: 50px; vertical-align: middle;"></div>
</div>
</body>
</html>
效果图:
并没有垂直居中,是因为div2只是div1中的一行,只能在这一行里偏移,所以必须设置div1的行高足够才能偏移,把父元素行高设置为100px可以实现近似居中(还向下偏移了div1中x字符高度的一半),再把div1的fontsize设置为0就可以居中
- 可以利用display:table和vetical-align使得内容垂直居中
<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>display:table实现垂直居中</title>
</head>
<body>
<style type="text/css" rel="stylesheet">
.table {
display: table;
margin: 5px;
width: 500px;
height: 300px;
background-color: #ccc;
}
.cell {
display: table-cell;
padding: 10px;
vertical-align: middle;
}
</style>
<div class="table">
<div class="cell">内容内容内容内容内容内内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容内容</div>
</div>
</body>
</html>
即使cell里面是一个div,也会垂直居中