根据mdn transitionend doc ,如果 transition-property 被删除或者元素(当然是它的父元素之一)变为 display:none,则不会触发 css transition 的 transitionend 事件。
我想知道是否有任何方法可以从 javascript 端检测到这种情况(即:转换已被中断)。据我所知,没有 transitioninterrupted 事件或 transitionaborted 事件,但也许我错过了什么?
你有什么想法吗?
最好的问候
最佳答案
我尝试对此做一些研究,发现除了 transitionend
之外确实没有其他过渡事件,但我发现了 this pen它试图使用 transitionend
事件模拟 transitionstart
事件,该事件在非常短的延迟后触发。
基于该技术,我尝试模拟 transitioncancel
事件并得到了一些“不错”的结果。这是一个小演示的代码(解释在后面):
HTML
<h1>Hello World</h1>
CSS
h1 {
margin-left: 0;
opacity: 0.99999;
transition: margin-left 1s ease, opacity 0.0001ms ease;
}
h1:hover {
opacity: 1;
margin-left: 500px;
}
Javascript
var h1 = document.querySelector('h1');
var styles = getComputedStyle(h1);
var duration = resolveDuration(styles.transitionProperty,
styles.transitionDuration);
var timer = null;
h1.addEventListener('transitionend', function(e) {
if (e.propertyName === 'opacity') {
timer = setTimeout(function() {
console.log('transition cancelled!');
}, duration);
} else {
clearTimeout(timer);
}
});
function resolveDuration(property, duration) {
var properties = property.split(/,\s+/g);
var durations = duration.split(/,\s+/g);
for (var i = 0; i < properties.length; i++) {
if (properties[i] !== 'opacity') {
var unit = durations[i].replace(/\d+\.?\d*/, '');
var value = parseInt(durations[i].replace(unit, ''));
if (unit === 's') {
return value * 1000;
}
return value;
}
}
return 0;
}
解释
基本上,这是在模拟
transitionstart
之后启动setTimeout
调用,持续时间设置为transition-duration
(在resolveDuration
函数中标准化为毫秒)。当传递给
setTimeout
的函数被执行时,这意味着转换被取消了。当发出另一个
transitionend
事件时,它不是针对opacity
属性(用于伪造transitionstart
),setTimeout
调用被取消,因此不会发出假的transitioncancel
。
此解决方案的问题
需要另一个过渡属性(在本例中为
opacity
)来伪造transitionstart
。只能处理一个过渡属性。
假
transitioncancel
仅在transition-duration
之后触发,而不是在转换取消时立即触发。
查看 this fiddle有关此的演示。
关于javascript - 有没有办法检测到 css 转换已被中止/中断?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/32524991/