纯CSS翻转动画需父容器设perspective、翻转容器设transform-style: preserve-3d,前后两面绝对定位叠加,后表面初始化rotateY(180deg),用transition控制rotateY(0deg→180deg)实现立体翻转。
transform: rotateY() 实现 HTML5 元素翻转纯 CSS 实现翻转动画不需要 JavaScript,核心是 transform: rotateY(180deg) 配合 transform-style: preserve-3d。常见错误是父容器没设 perspective,导致翻转看起来像平面缩放而非立体翻转。
关键点:
perspective 必须加在翻转容器的父级(比如 ),不能只加在翻转元素自身
-
transform-style: preserve-3d 要设在直接包裹前后两面的容器上(如 )
- 前后两面需用
position: absolute 叠在一起,且后表面要加 transform: rotateY(180deg) 初始化
- 翻转动画建议用
transform: rotateY(0deg) → rotateY(180deg) 控制,避免用 backface-visibility: hidden 误删内容
正面
背面
JavaScript 控制翻转状态时注意事件触发时机
用 JS 切换 is-flipped 类名是最常用方式,但容易忽略动画未结束就重复点击导致状态错乱。比如快速连点两次,card 可能卡在 90° 中间态或翻回原样。
稳妥做法:
立即学习“前端免费学习笔记(深入)”;
- 翻转开始前加
pointer-events: none 禁用交互,动画结束后再恢复
- 监听
transitionend 事件,而不是靠 setTimeout 估算时间
- 检查当前是否正在动画中,用
getComputedStyle(el).transform 不可靠,优先用类名或 data 属性标记状态
移动端 Safari 的 rotateY 兼容性陷阱
iOS 15.4 之前,Safari 对 transform: rotateY() 的硬件加速支持不稳定,尤其在 position: fixed 或 overflow: scroll 区域内翻转,可能出现闪烁、卡顿甚至白屏。
绕过方案:
- 强制开启 GPU 加速:给翻转容器加
transform: translateZ
(0) 或 will-change: transform
- 避免在
body 滚动区域直接翻转;把翻转容器包进 position: relative 的局部容器里
- 不用
rotateY,改用 rotate3d(0, 1, 0, 180deg) —— Safari 对这个写法兼容更稳
- 真机测试必须覆盖 iOS 14–16,模拟器不可信
翻转动画性能差?先查这三处
翻转卡顿通常不是因为动画本身复杂,而是布局或渲染链路被意外打断:
- 翻转元素内部有大量重排(比如动态插入 DOM、频繁读取
offsetHeight)
- 用了
box-shadow 或 filter: blur() 等高开销属性,且没加 transform: translateZ(0) 升级为合成层
- 父级设置了
overflow: hidden,而翻转角度导致边缘裁剪触发额外光栅化
Chrome DevTools 的 “Rendering” 面板打开“FPS Meter”和“Layer Borders”,能一眼看出哪些元素没走合成层。