CSS 教程 / CSS 颜色与单位:px、em、rem 和百分比
CSS 颜色可以使用名称、十六进制值和函数(如 rgb())来书写。长度单位使用不同的参考点:px 是绝对 CSS 长度,em 取决于字体大小,rem 使用根字体大小,而百分比取决于正在设置的属性。
比较颜色名称、十六进制表示法和 RGB
teal、#008080 和 rgb(0, 128, 128) 表示相同的颜色。颜色名称易于阅读,但可用的名称是预先定义的,并且十六进制和 RGB 适合以数值方式控制红色、绿色和蓝色的量。RGB 代表红、绿、蓝。
| 符号 | 含义 | 示例用法 |
|---|---|---|
| teal | 预定义颜色名称 | color: teal; |
| #008080 | 红 00、绿 80、蓝 80 用十六进制表示 | color: #008080; |
| rgb(0, 128, 128) | 将三个组件显示为 0 到 255 的数字 | color: rgb(0, 128, 128); |
| rgb(0 128 128 / 20%) | 为相同的颜色指定 20% 不透明度 | background-color: rgb(0 128 128 / 20%); |
Alpha 描述颜色不透明度:20% 允许大部分底层颜色显示,而 100% 则是不透明的。显示结果取决于底层颜色。仅向背景添加 alpha 与对整个元素设置 opacity 不同,后者也会使其文本和子元素半透明。参见 MDN:color 属性。
理解 px、em 和 rem 的参考点
px 是一个 CSS 像素。这并不总是等同于屏幕上的一个物理像素,并且可能会根据设备的屏幕缩放和像素密度而有所不同。使用 16px 并不意味着屏幕放大功能无法使用。
在 font-size 中,em 使用继承的字体大小。在像 padding: 1em 这样的声明中,它使用元素自身的字体大小。rem 使用根元素的字体大小。以下计算假设根元素和父元素的字体大小均为 16px。更多细节,请参见 CSS 字体、字体大小和行高。
| 声明和条件 | 计算 | 结果 |
|---|---|---|
| 父元素字号为 16px 时:font-size: 1.25em | 16 × 1.25 | 20px |
| 根元素字号为 16px 时:font-size: 1.25rem | 16 × 1.25 | 20px |
| 元素自身字号为 20px 时:padding: 1em | 20 × 1 | 每个方向20px |
| 根元素字号为 16px 时:padding: 1rem | 16 × 1 | 每个方向16px |
如果你在父元素大小增加的每一步重复 font-size: 1.25em,则它会从 16 → 20 → 25px 增加。在相同的结构上重复 1.25rem,两步都是 20px。em 适用于需要与周围字母成比例的小组件,rem 适用于在整个页面共享固定参考值。应根据希望跟随的参照值选择 em 或 rem。关于单位的定义,请参考 MDN 的 CSS 值和单位指南 。
查找百分比宽度的参考
width: 50% 通常是基于包含块的内容宽度来计算的。并非所有属性的百分比都是基于相同的目标。例如,font-size: 125% 是基于从父元素继承的字体大小,因此必须与宽度的百分比分开。
.wrapper { width: 100%; max-width: 640px; padding: 1rem; }
.inner { width: 50%; font-size: 1.25rem; padding: 1em; }
下面的完整示例统一设置 border-box;本节的尺寸计算也以该设置为前提,内边距包含在声明宽度内。以 16px 根字体、足够的空间且没有边框为例,外部盒子的宽度为 640px。每侧 16px 的内边距留出 608px 的内容宽度。内部盒子的 50% 宽度为 304px,每侧 20px 内边距后,内容宽度为 264px。更多详细信息,请参见 CSS 宽度、高度、最小/最大限制和 box-sizing。
如果屏幕较窄,外部盒子的宽度也会减小。这时,内部宽度不会固定为304px,而是根据外部盒子的新内容宽度重新计算。示例中的max-width是一个次级设置,用于限制盒子宽度不能超过640px。
运行完整示例
将以下代码输入到以UTF-8保存的units.html中,并在浏览器中打开。代码包括颜色比较、嵌套单位和宽度计算。根元素100%遵循浏览器的默认字体大小,因此在下面的练习中16px的条件会首先在开发者工具中检查。
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1">
<title>Comparing colors and units</title>
<style>
html { font-size: 100%; }
* { box-sizing: border-box; }
body { margin: 16px; font-family: sans-serif; line-height: 1.7; }
.wrapper { width: 100%; max-width: 640px; padding: 1rem; background: #e9f7ef; }
.inner { width: 50%; padding: 1em; font-size: 1.25rem; background: white; }
.color-name { color: teal; }
.color-hex { color: #008080; }
.color-rgb { color: rgb(0, 128, 128); }
.alpha { padding: 1rem; background: rgb(0 128 128 / 20%); }
.nest { font-size: 16px; }
.em-step { font-size: 1.25em; }
.rem-step { font-size: 1.25rem; }
</style>
</head>
<body>
<h1>Colors and units</h1>
<h2>Three notations of the same color</h2>
<p class="color-name">Character specified by teal</p>
<p class="color-hex">Characters specified as #008080</p>
<p class="color-rgb">Character specified by rgb(0, 128, 128)</p>
<p class="alpha">Only this box's background color has 20% opacity.</p>
<h2>Width and spacing</h2>
<div class="wrapper"><div class="inner">Text and padding in the inner box</div></div>
<h2>Nested em</h2>
<div class="nest"><div class="em-step">First step<div class="em-step">Second step</div></div></div>
<h2>Nested rem</h2>
<div class="nest"><div class="rem-step">First step<div class="rem-step">Second step</div></div></div>
</body>
</html>
每次只更改一个值
- 在开发者工具中检查 html 的计算字体大小。如果是 16px,则确保嵌套的 em 为 20px·25px,嵌套的 rem 为 20px·20px。如果根字号不是 16px,只需按实际根字号重算 rem;由于 .nest 显式固定为 16px,嵌套 em 仍然是 20px 和 25px。
- 临时将 html 设置为 font-size: 20px。示例中使用 1.25rem 的 .rem-step 和 .inner 字号都变为 25px,而 .nest 保持指定的 16px,因此 em 层级为 20px·25px。 .inner 的内边距是 25px。比较后,恢复到原来的 100%。
- 将窗口放宽,检查 .wrapper 和 .inner 的盒子大小。在原始 16px 条件下,它是 640px·304px。随着窗口变窄,确保两边同时缩小。
- 检查三个彩色段落的计算颜色。它们必须都有相同的 RGB 值。确保更改 .alpha 的背景不会使文字本身也变成半透明。
如果结果不是你预期的,检查计算标准,而不是直接更改单位。父元素和根元素的字体大小、内边距、盒模型设置以及覆盖的 CSS 规则都可能产生影响。在开发者工具中所作的更改通常在刷新页面后消失,而保存到文件中的更改必须手动恢复到原始值。




