CSS中有两种类型的长度——相对长度和绝对长度。重要的是要知道它们之间的区别,以便理解他们控制的元素将变得有多大。
绝对长度单位
以下都是绝对长度单位——它们与其他任何东西都没有关系,通常被认为总是相同的大小。
单位 | 名称 | 等价换算 |
---|---|---|
cm | 厘米 | 1cm = 96px/2.54 |
mm | 毫米 | 1mm = 1/10th of 1cm |
Q | 四分之一毫米 | 1Q = 1/40th of 1cm |
in | 英寸 | 1in = 2.54cm = 96px |
pc | 十二点活字 | 1pc = 1/16th of 1in |
pt | 点 | 1pt = 1/72th of 1in |
px | 像素 | 1px = 1/96th of 1in |
这些值中的大多数在用于打印时比用于屏幕输出时更有用。例如,我们通常不会在屏幕上使用cm。惟一一个我们经常使用的值,估计就是px(像素)。
相对长度单位
相对长度单位相对于其他一些东西,比如父元素的字体大小,或者视图端口的大小。使用相对单位的好处是,经过一些仔细的规划,您可以使文本或其他元素的大小与页面上的其他内容相对应。下表列出了web开发中一些最有用的单位。
单位 | 相对于 |
---|---|
em | 在 font-size 中使用是相对于父元素的字体大小,在其他属性中使用是相对于自身的字体大小,如 width |
ex | 字符“x”的高度 |
ch | 数字“0”的宽度 |
rem | 根元素的字体大小 |
lh | 元素的line-height |
vw | 视窗宽度的1% |
vh | 视窗高度的1% |
vmin | 视窗较小尺寸的1% |
vmax | 视图大尺寸的1% |
相对值的好处
在web环境下,用户可以设置浏览器窗口的大小,而CSS必须适应这种窗口大小。此外,当客户打开后,用户还可以缩放网页,CSS还需要适应新的限制,也就是说,不能在刚创建网页时就应用样式,而是等到要将网页渲染到屏幕上去,才能去计算样式。
这给CSS增加了一个抽象层,我们无法根据理想的条件给元素添加样式,而是要设置无论元素处于任意条件,都能够生效的原则。现在的Web环境下,网页需要既可以在4英寸的手机屏幕上渲染,也可以把30英寸的大屏幕上渲染。
在很长时间里,网页设计者通过聚焦到“像素级完美”的设计来降低这种复杂性,他们会创建一个紧凑的容器,通常是居中的一栏,大约800px,然后再像之前的本地应用或者印刷出版物那样,在那些限制里面进行设计。
智能手机的出现,开发人员再也无法假装每个用户访问网站的体验都能一样,不管我们喜欢与否,都得抛弃以前那种固定宽度的栏目设计,开始考虑响应式设计。
CSS带来的抽象性也带来了额外的复杂性。如果给一个元素设置800px的宽度,在小窗口下会是什么样?水平菜单如果无法在一行显示会是什么样?在写CSS的时候,我们既要考虑整体性,也要考虑差异性。当有很多方法解决同一个问题时,我们要选择能够兼顾更多情况的方法。
相对单位就是CSS用来解决这种抽象的一种工具,我们可以基于窗口大小来等比例缩放字号,而不是固定为14px,或者将网页上的任何元素的大小都相对于基础字号来设置,然后只用改一行代码就能缩放整个网页。
em
em 单位的意思是“父元素的字体大小”。
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<style>
body {
font-size: 20px;
}
p {
font-size: 1em;
margin: 0;
padding: 0;
}
</style>
<body>
<p>这是一个P标签</p>
</body>
</html>
我们在这里设置了body的font-size为20px,p标签的font-size为1em,浏览器将其乘以字号,也就是1*20px,也就是说最终p标签的font-size最终渲染为16px。
提示:如果知道字号的像素值,但是想用em声明,可以用一个简单的公式换算:用想要的像素大小除以父级(继承)的像素字号。比如,想要一个10px的字体,元素继承的字体是12px,则计算结果是10/12=0.8333em,如果想要一个16px的字体,父级字体是12px,则计算结果是16/12=1.333em。
对大多数浏览器来说,默认的字号为16px。
rem
当浏览器解析HTML文档时,会在内存里面将页面的所有元素表示为DOM(文档对象模型)。它是一个树结构,其中每个元素都由一个节点表示。<html>元素是顶级(根)节点,它下面是子节点<head>和<body>,再下面是逐级嵌套的后代节点。
在文档中,根节点是所有其他元素的祖先节点。根节点有一个伪类选择器(:root),可以用来选中它自己。这等价于类型选择器html,但是:root的优先级相当于一个类名,而不是一个标签。
rem是root em的缩写。rem不是相当于当前元素,而是相当于根元素的单位。不管在文档的什么位置使用rem,1.2rem都会有相同的计算值:1.2乘以根元素的字号。下面我们来一个例子:
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Title</title> </head> <style> html { font-size: 30px; } body { font-size: 12px; } p { font-size: 2rem; margin: 0; padding: 0; } </style> <body> <p>这是一个P标签</p> </body> </html>
在这个例子中,根元素的字号设置为30px,p标签的字号设置为2rem,计算为60px。
与em相比,rem降低了复杂性。实际上,rem结合了px和em的优点,既保留了相对单位的优势,又简单易用,那么是不是应该全用rem,抛弃其他选择呢?答案是否定的。
提示:拿不准的时候,用rem设置字号,用px设置边框,用em设置其他大部分属性。
视口的相对单位
前面的em和rem都是相对于font-size定义的,但CSS里不止有这一种相对单位,还有相对于浏览器视口定义长度的相对单位。
具体有下面几种单位:
- vh:视口高度的1/100
- vw:视口宽度的1/100
- vim:视口宽,高中较小的一方的1/100
- vmax:视口宽,高中较大的一方的1/100
比如,50wx等于视口宽度的一半,25vh等于视口高度的25%。vmin取决于宽和高中较小的一方,这可以保证元素在屏幕方向变化时适应屏幕。在横屏时,vmin取决于高度,在竖屏时,则取决于宽度。
下面我们看代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<style>
p {
width: 50vw;
height: 50vh;
border: 1px solid red;
}
</style>
<body>
<p>这是一个P标签</p>
</body>
</html>
我们来缩小看下
我们可以看到,不管是放大还是缩小,这个P标签的高度和宽度都是占据可视化窗口的一半。
使用calc定义字号
calc()函数内可以对两个及其以上的值进行基本运算。当要结合不同单位的值时,calc()特别实用,它支持的运算包括:加(+),减(-),乘(*),除(/)。加好和减号两边必须有空白。
下面看一下代码:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<style>
:root {
font-size: calc(0.5em + 1vw);
}
</style>
<body>
<p>这是一个P标签</p>
</body>
</html>
现在打开网页,慢慢缩放浏览器,字体会平滑地缩放。0.5em保证了最小字号,1vw则确保了字体会随着视口缩放。
参考资料:
- 《深入解析CSS》
- 《CSS权威指南》
- https://developer.mozilla.org/zh-CN/docs/Learn/CSS/Building_blocks/Values_and_units