rem需动态控制html font-size才能响应式,推荐clamp(14px, 2.5vw, 18px);em在padding/margin中参照自身font-size,易因嵌套失控;px适用于边框、圆角等需物理像素精度的场景。

rem 不能自动响应,必须显式控制 html 的 font-size
很多人以为写个 html { font-size: 16px } 就算用了 rem,其实这只是锁死一个固定值——和 px 没本质区别。真正让 rem “动起来”的,是后续对这个值的动态干预。
推荐直接用 html { font-size: clamp(14px, 2.5vw, 18px); }:小屏保可读(≥14px),大屏不撑爆(≤18px),中间随视口平滑过渡。Safari 13.1+ 和 Chrome 88+ 均支持良好。
若需兼容 Safari 12 或更低版本,JS 是底线方案:document.documentElement.style.fontSize 必须在 DOMContentLoaded 后立即执行;否则首屏渲染取不到视口宽度,用户会看到闪动或错位。
别用 font-size: 62.5% 这类写法——它依赖用户系统默认字号,且与 macOS + Safari 的字体缩放功能冲突,实测会导致部分用户文字突然变小。
立即学习“前端免费学习笔记(深入)”;
em 在 padding/margin 中参照的是自身 font-size,不是父级
这是 em 最常翻车的地方:它在 font-size 属性里看父元素,但在 padding、margin、border-radius 等属性里,看的是**当前元素自身的 font-size**(哪怕这个值是继承来的)。
例如:.btn { font-size: 14px; padding: 0.75em; } 中的 0.75em 是 10.5px;但如果漏写 font-size,按钮就继承 body 的 16px,padding 变成 12px——主题换字体时所有按钮内边距全乱。
安全使用 em 的前提:
- 组件自身显式声明了
font-size - 嵌套层级 ≤ 2
- 仅用于需随文等比缩放的场景(如图标、
line-height无单位值除外)
绝对陷阱:line-height: 1.5em —— 它会二次乘以自身字号,正确写法是 line-height: 1.5(无单位)。
px 不是过时单位,而是像素级精准场景的唯一选择
边框、阴影、圆角这些需要物理像素对齐的属性,一律用 px。比如 border: 1px solid #ccc 写成 0.0625rem(按 16px 算)既难读又无意义;border-radius: 4px 换成 0.25rem 只会增加维护成本。
移动端触控区域也有硬性要求:iOS 人机交互指南明确建议导航栏高度为 44px,确保手指能准确点击。这类尺寸用 rem 或 em 会因根字号波动而失准。
高 DPI 屏幕(如 Retina)上,1px 边框可能模糊,此时应配合 transform: scale(0.5) + 2px 实现锐利效果,但基础定义仍需 px。
混用单位最危险的不是数值错,而是参照系打架
单位选错不会报错,但会让样式在缩放、嵌套或主题切换时突然失衡。典型现象:
- 用
rem写字体大小,却用px写line-height:根字号一调,行高不动,行距立刻崩塌 - 全局用
rem,但某个弹窗组件 JS 动态设置了父容器的font-size:里面所有em值被带偏,按钮文字变小、间距变大 - 卡片里
padding: 1em,标题用1.5rem、正文用px:等于放弃间距逻辑一致性
真正要警惕的,是“伪响应”——表面用了 rem,实际没管根字号变化,也没约束 em 的嵌套深度,结果调试时得逐层回溯计算链。一套设计系统里,基础间距变量(如 $space-md)必须统一用 rem 或统一用 em,不能并存。


















