CSS中硬写16px等无语义数值极危险,因缺乏上下文致维护困难;应使用带用途+层级+修饰的语义化变量(如--spacing-inline-xs),配合:root定义与calc()动态计算,并为IE提供fallback。

为什么16px、24px这种数字在CSS里很危险
因为它们没名字,没人知道这个16px是“正文默认字号”还是“按钮内边距”,改的时候不敢动,查的时候要全局搜。一旦设计系统升级,所有散落的16px都得人工核对——这不是写样式,是在维护魔法咒语。
用:root定义变量不是为了炫技,是把数值和语义绑在一起:
:root {
--font-size-body: 16px;
--space-unit: 8px;
--border-radius-sm: 4px;
}之后所有地方用var(--font-size-body),而不是硬写16px。改字号?只动一行;想查哪个间距对应什么含义?看变量名就懂。
CSS变量命名必须带上下文,不能只叫--size-1
像--size-1、--color-2这类命名等于没命名——它没回答“谁用?在哪用?为什么是这个值?”。
立即学习“前端免费学习笔记(深入)”;
推荐按「用途+层级+修饰」组合命名,例如:
-
--spacing-inline-xs(行内紧凑间距) -
--elevation-shadow-md(中等阴影层级) -
--border-width-focus(焦点态边框粗细)
避免用--primary-500这种纯色值映射名,除非你真在建设计Token体系;日常项目直接用--button-border-width更直白。变量名越具体,后期维护成本越低。
别在@media里重复定义同一变量,用calc()动态计算更稳
常见错误:在不同断点里分别覆盖--space-unit,结果漏掉某个媒体查询,或者嵌套组件里取不到最新值。
更可靠的做法是定义基础值 + 用calc()按需缩放:
:root {
--space-unit: 8px;
}
@media (min-width: 768px) {
:root {
--space-unit: 12px; /* 直接重设,不依赖继承链 */
}
}
.card {
padding: calc(var(--space-unit) * 2) calc(var(--space-unit) * 3);
}注意两点:
- 变量重设必须写在
:root下,子选择器里--xxx不会冒泡上去 -
calc()里用var(--x) * N比写死24px更易维护,也方便后续统一缩放比例
IE不支持CSS变量,但没必要全量回退到预处理器变量
如果项目还要求兼容IE11,var(--x)会直接失效,变成unset或继承值,布局可能崩。
稳妥做法不是放弃变量,而是用fallback兜底:
.btn {
padding: calc(8px * 2) calc(8px * 3); /* IE fallback */
padding: calc(var(--space-unit) * 2) calc(var(--space-unit) * 3); /* 现代浏览器 */
}关键点:
- CSS解析是从上到下,后声明的会覆盖前声明的(IE跳过不认识的
var(),就用上面那行) - 不要用
postcss-custom-properties这类插件自动补fallback——它无法处理calc()里的变量,容易出错 - 真正需要响应式变化的数值(比如字体大小),优先用
clamp()或em/rem,比依赖JS或变量更轻量
变量不是银弹,它解决的是语义混乱,不是兼容性问题。该用rem的地方别硬塞var,该写两套断点的地方也别指望一个变量全包圆。










