CSS动画中width、height、top、left、right、bottom、margin、padding、border、display切换一定会触发重排,因它们强制浏览器重新计算布局;而transform和opacity仅触复合成,不重排不重绘,是性能最优解。

直接改用 transform 和 opacity,别碰 width、left、margin 这类会触发布局计算的属性——这是最有效、成本最低的解法。
哪些CSS动画属性一定会触发重排?
只要在 @keyframes 或 transition 里修改以下任一属性,浏览器就必须重新计算元素位置和尺寸,强制执行重排:
-
width/height:影响文档流中后续元素的布局 -
top/left/right/bottom(配合position: relative或absolute):坐标变化需重新参与布局定位 -
margin/padding/border:直接改变盒模型尺寸与占位 -
display切换(如block↔none):元素进出渲染树,整棵子树重排
这些操作都在主线程上同步执行,单次重排平均耗时 2–5ms;60fps 要求每帧 ≤16.67ms,频繁重排必然掉帧。
为什么 transform 和 opacity 不重排?
因为它们不参与 Layout 阶段,只影响 Composite(合成)阶段:
立即学习“前端免费学习笔记(深入)”;
-
transform(如translateX、scaleY、rotate)会让浏览器自动将元素提升为独立图层,位移/缩放由 GPU 直接处理 -
opacity只改变图层透明度,合成器直接混合像素,无需重绘内容本身 - 现代浏览器已能智能识别
transform动画并自动升层,transform: translateZ(0)或translate3d(0,0,0)这类 hack 已无必要
实测显示:对 1000 个元素做位移动画,transform: translateX 帧率比 left 高 3 倍以上。
实际替换时要注意什么?
不是简单把 left: 100px 换成 transform: translateX(100px) 就完事,得考虑上下文行为差异:
- 原用
top/left是基于文档流偏移,而transform是相对自身原点的视觉位移,不影响其他元素布局——这点反而是优势,但需确认设计是否依赖“挤占空间”效果 - 缩放动画慎用
scale替代width/height:若需保持文字清晰度,记得加transform-origin: top left控制缩放中心,避免模糊拉伸 - 隐藏/显示场景别用
display: none,改用opacity: 0+pointer-events: none;若必须彻底移除 DOM 占位,再用 JS 控制display,但不要放进动画过程里 - 避免混用:同时写
transition: width 0.3s, transform 0.3s,width仍会拖慢整条动画链
真正卡顿的根源往往藏在看似无害的 margin-top: 2px 动画里——检查动画声明时,逐个确认每个过渡属性是否属于安全列表。



















