transitionend未触发最常见原因是过渡未启动:属性值无真实变化、display/height:auto等不可插值属性变更、hover中声明transition但默认态缺失、js连续设样式未强制重排、或监听前元素已被移除。

transitionend 为什么根本没反应
最常见的情况是:过渡压根没启动。浏览器只在「样式值真实变化」且「该属性可动画」时才触发 transitionend,否则静默跳过。
-
display: none→block、height: auto→100px这类不可插值的变更,不会触发任何过渡,自然也没事件 - 目标属性写在
:hover规则里,但默认态没声明transition→ 移出时无过渡上下文,transitionend不触发 - JS 中连续设置样式(如先改
el.style.transform,再设el.style.transition),浏览器来不及渲染,直接跳终态 - 用
el.classList.remove("fade")瞬间清掉含transition的类,起始值丢失,过渡被绕过
transitionend 触发了但监听不到
不是没发生,而是你没监听到——事件名不兼容、冒泡干扰、或监听时机错了。
- 旧版 Safari 用
webkitTransitionEnd,Firefox 早期用transitionend,IE10+ 才统一;别硬写死,用getComputedStyle或 feature detect 动态绑定 - 父元素也绑了
transitionend,子元素过渡结束会冒泡上来,e.target不是你想监听的元素 → 必须校验e.target === element - 监听前就执行了
el.remove()或el.style.display = 'none'→ 元素已不在 DOM,事件永不派发
transitionend 触发了但只响应一次或漏掉关键属性
一个过渡可能涉及多个属性(比如 transform 和 opacity 同时变),浏览器对每个可动画属性各派发一次 transitionend。
- 用
transition: all 0.3s时,哪怕只改了opacity,transform、color等其他属性只要值有微小变化(比如继承值被重算),也会触发额外回调 - 必须检查
e.propertyName,只处理你关心的属性:if (e.propertyName !== 'transform') return - 没加
{ once: true }选项,快速反复 hover/leave 会堆叠多个监听器,后续回调乱序或重复执行
transition 被 JS 中断后怎么收尾
用户快速移开鼠标、JS 主动移除类、或调用 el.style.transition = 'none',都会让过渡中途终止——此时 transitionend 永远不会来。
- 中断逻辑里必须手动同步终态:
el.style.transform = 'translateX(100px)'; el.style.transition = 'none'; - 回调中要改样式?先临时禁用过渡:
el.style.transition = 'none'; el.style.opacity = '0';,再恢复,否则会触发新过渡套娃 - 别等
transitionend来清理状态,中断路径和完成路径都要有独立 cleanup,比如统一调用cleanupAnimation(el)
transition 必须常驻基础类)、DOM 存活期(避免提前移除)、以及 JS 主动干预点(中断即终态)。漏掉任意一环,transitionend 就成薛定谔的事件。前端入门到VUE实战笔记:立即使用
在学习笔记中,你将探索 前端 的入门与实战技巧!











