animation-fill-mode: forwards没生效的根本原因是动画未执行完或被覆盖:动画时长为0、关键帧属性缺失、高优先级样式覆盖、简写animation重置fill-mode、与transition混用冲突、js读取时机不当或强制终止动画。

animation-fill-mode: forwards 为什么没生效
写了 animation-fill-mode: forwards 却还是“弹回去”,大概率不是属性写错,而是动画根本没执行完或被覆盖了:
-
animation-duration是0s,或animation-iteration-count被设为0—— 动画压根没跑,forwards就无从谈起 -
@keyframes里漏写了某个属性:比如只在100%定义了transform,但没提opacity,那forwards不会保留opacity - 被更高优先级样式覆盖:比如动画结束后,外部 class 又写了
opacity: 1,或者 JS 直接设置了el.style.opacity = '1'—— 用开发者工具看 computed 样式确认最终值 -
animation简写覆盖了fill-mode:写animation: slideIn 0.3s会把未显式声明的animation-fill-mode强制重置为none
forwards 和 transition 混用时的冲突表现
两者机制不同,混用极易出视觉 bug:
-
animation-fill-mode只对@keyframes生效,对transition完全无效 - 如果元素同时有
transition: transform 0.2s和一个transform动画,且动画终值(如transform: translateX(200px))与 transition 的起始值不一致,可能触发一次意外过渡,看起来像“没留住” - hover 触发动画后想保持高亮?用
transition配合 class 切换更直接;复杂入场动效才用@keyframes+forwards
JS 控制动画时 forwards 的读取时机问题
动画刚结束时,getComputedStyle(el).transform 可能返回中间值,不是你期望的终值:
- 渲染尚未完成,建议用
requestAnimationFrame延迟一帧再读取 - 用
el.style.animation = 'none'强制终止动画,会立刻丢弃forwards效果,元素回归内联样式或层叠值 - 若用 JS 动态设置动画,必须连同
animation-fill-mode一起设上,否则简写animation会覆盖 CSS 中的声明
backwards 和 both 的实际生效条件
backwards 不是“提前播放”,而是在 animation-delay 期间应用首帧样式:
-
animation-delay: 1s+animation-fill-mode: backwards→ 延迟的 1 秒内,元素就显示0%关键帧的样式 - 如果
animation-delay是0s,backwards实际无效 -
both是forwards+backwards,但容易和初始 class 冲突,尤其当0%和当前样式不一致时 - 务必显式定义
0%和100%关键帧,浏览器不会自动推断缺失帧的值
前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











