css前端

重排与重绘:CSS 动画为什么会卡

把浏览器渲染中的样式计算、布局、重绘和合成拆开解释,说明哪些 CSS 属性更容易触发布局开销,以及为什么 transform 和 opacity 通常更适合做动画。

·更新于 ·阅读约 2 分钟·计算中...
重排与重绘:CSS 动画为什么会卡

动画卡顿时,很多人会机械地背一句“多用 transformopacity”。这句话方向没错,但如果不了解浏览器渲染链路,就很难判断自己改的是“布局成本”还是“像素绘制成本”。

在这里插入图片描述

目录

浏览器大致做了什么

浏览器渲染页面时,通常会经历这样一条链路:

  1. 计算样式
  2. 计算布局(layout,也常被称为 reflow)
  3. 重绘像素
  4. 合成图层并显示

MDN 的动画性能文档也把 layout 标成了有时被称为 reflow 的步骤。理解这条链路后,性能优化就不是背口诀,而是判断“你改的属性会走到哪一步”。

什么是重排

重排是重新计算元素的位置和几何尺寸,比如宽高、间距、文档流位置。

常见触发源:

  • widthheight
  • marginpadding
  • border
  • topleft
  • display
  • 插入、删除、移动 DOM
  • 先写样式再立刻读 offsetWidthscrollHeight 之类布局信息

重排开销通常比单纯重绘更大,因为浏览器可能要重新计算一片区域,甚至影响后续兄弟元素和父元素布局。

什么是重绘

重绘是布局不变,但需要重新把像素画出来。

常见例子:

  • color
  • background
  • box-shadow
  • outline

这类修改一般不需要重新计算盒子位置,但仍要重新绘制视觉结果。

为什么 transform 和 opacity 常更适合动画

MDN 把 transformopacity 归到了更接近合成阶段的属性。它们通常只需要样式计算,很多情况下甚至不用重新布局或重绘整块内容,因此更容易保持流畅。

一个典型对比:

.bad {
  left: 200px;
}

.better {
  transform: translateX(200px);
}

left 更容易把元素重新拉回布局计算,transform 更像是在现有结果上做位移。

这也是为什么大多数进入、离开、悬浮动效都优先使用:

transition: transform 200ms ease, opacity 200ms ease;

会把动画写卡的几种模式

1. 动画直接改布局属性

.panel {
  transition: width 300ms ease;
}

如果这个面板会推开周围内容,浏览器就要持续重算布局。页面结构越复杂,越容易卡。

2. 频繁读写交替

element.style.width = "200px"
const height = element.offsetHeight

先写再读,浏览器可能被迫立刻刷新布局结果,这类“强制同步布局”在滚动监听和拖拽里尤其常见。

3. 滥用 will-change

.card {
  will-change: transform;
}

will-change 不是默认优化开关。提前告诉浏览器做准备会占资源,只有真正频繁变化、且你确认收益明显的元素才值得加。

该怎么优化

  • 位移、缩放、淡入淡出,优先改 transformopacity
  • 减少会影响周边布局的动画
  • 避免在热点逻辑里频繁交替读写布局信息
  • 必要时把动画元素和普通文档流解耦
  • 用浏览器性能面板看真实瓶颈,不凭感觉优化

如果你的“卡顿”其实伴随着遮罩层、弹窗层级错乱,可能不只是性能问题,还要检查 Stacking Context 与 z-index

一个更稳的展开思路

很多抽屉或 tooltip 会从下面这样开始:

.drawer {
  height: 0;
  overflow: hidden;
  transition: height 250ms ease;
}

它能工作,但在复杂页面里通常不够省。若产品允许,改成“外层固定布局,内层用 transform / opacity 做视觉移动”往往更流畅。

结论

  • 重排关注几何与布局,通常更贵。
  • 重绘关注像素更新,通常比重排便宜,但也不是零成本。
  • transformopacity 更适合多数 UI 动画,因为更容易停留在更轻的渲染阶段。
  • 性能优化应该先看渲染链路,再看属性选择,而不是只背 API 名单。

如果你下一步是在做 Tailwind 或组件动画,可以配合看 Tailwind CSS 4 入门Framer Motion 指南

参考资料

9 分钟

css中的3d使用:深入理解 CSS Perspective 与 Transform-Style

和是 CSS 3D 变换中不可或缺的两个属性。赋予了场景深度,模拟了观察者的视觉体验;而则决定了子元素如何在 3D 空间中呈现。掌握这两个属性的用法,将为您的网页设计带来更丰富的视觉层次和更具吸引力的交互体验。现在,不妨动手尝试一下,释放您的创意,打造出令人惊叹的 3D 世界吧!

10 分钟

深入理解CSS对齐属性:align-items, align-self, justify-items, justify-self

属性作用对象方向适用布局覆盖关系容器垂直Flex/Grid被align-self覆盖align-self子项垂直Flex/Grid覆盖容器水平Grid被覆盖子项水平Grid覆盖记忆口诀想调垂直用align,想调水平用justify容器设置用-items,单个调整用-selfGri

5 分钟

CSS 继承与重置:initial、inherit、unset 怎么选

把 initial、inherit、unset 的差异放到真实 CSS 场景里讲清楚,并说明哪些属性默认会继承、哪些不会,避免把重置和继承写反。

订阅 FreeMac

每周精选:免费 Mac 软件评测、可信来源更新、替代方案和少折腾指南。