是否可以@keyframes使用javascript,jQuery或其他方式获取/设置CSS3 动画的当前动画百分比?
@keyframes
举例来说,有一个divwith类叫做.spin,它使用也称为的关键帧简单地旋转了一个圆圈spin。
div
.spin
spin
我曾尝试使用,以获得动画的当前百分比值$('.spin').css('animation'),$('.spin').css('animation: spin')以及其他一些方法,但他们都警觉空
$('.spin').css('animation')
$('.spin').css('animation: spin')
我也有兴趣在不断变化的,在每一个预定的关键帧%的原创动画和我曾尝试喜欢的东西$('.spin').css('animation', '..new definition here...'),并$('.spin').css('spin', '50%', '...new definition here...)没有用。
$('.spin').css('animation', '..new definition here...')
$('.spin').css('spin', '50%', '...new definition here...)
有任何想法吗?
我大致实现了我想要在CSS3中使用纯JavaScript的功能。
为了让我的实验提出实现这些目标的方法,我创建了一个基本的CSS3动画,它围绕一条小的圆形路径旋转了一个圆圈。我的目标是在单击按钮时将动画的原点更改为新位置
为了实现 获得动画百分比值的第一个目标,我简单地使用以下方法对当前百分比进行setInterval了近似,即显示了当前的近似百分比。每40毫秒运行一次,以与动画的持续时间相对应(milliseconds/ 100)
setInterval
(milliseconds/ 100)
var result = document.getElementById('result'), currentPercent = 0; var showPercent = window.setInterval(function() { if(currentPercent < 100) { currentPercent += 1; } else { currentPercent = 0; } result.innerHTML = currentPercent; }, 40);
请注意此解决方案:
为了实现 为动画的%值设置新定义 的第二个目标 ,它花费了一些更复杂的解决方案。浏览了数十篇文章和网页(下面列出的重要文章)后,我设法提出了以下解决方案:
var circle = document.getElementById('circle'), button = document.getElementById('button'); var result = document.getElementById('result'), totalCurrentPercent = 0, currentPercent = 0; var showPercent = window.setInterval(function() { if(currentPercent < 100) { currentPercent += 1; } else { currentPercent = 0; } result.innerHTML = currentPercent; }, 40); function findKeyframesRule(rule) { var ss = document.styleSheets; for (var i = 0; i < ss.length; ++i) { for (var j = 0; j < ss[i].cssRules.length; ++j) { if (ss[i].cssRules[j].type == window.CSSRule.WEBKIT_KEYFRAMES_RULE && ss[i].cssRules[j].name == rule) { return ss[i].cssRules[j]; } } } return null; } function change(anim) { var keyframes = findKeyframesRule(anim), length = keyframes.cssRules.length; var keyframeString = []; for(var i = 0; i < length; i ++) { keyframeString.push(keyframes[i].keyText); } var keys = keyframeString.map(function(str) { return str.replace('%', ''); }); totalCurrentPercent += currentPercent; if(totalCurrentPercent > 100) { totalCurrentPercent -= 100; } var closest = getClosest(keys); var position = keys.indexOf(closest), firstPercent = keys[position]; for(var i = 0, j = keyframeString.length; i < j; i ++) { keyframes.deleteRule(keyframeString[i]); } var multiplier = firstPercent * 3.6; keyframes.insertRule("0% { -webkit-transform: translate(100px,100px) rotate(" + (multiplier + 0) + "deg) translate(-100px,-100px) rotate(" + (multiplier + 0) + "deg); background-color:red; }"); keyframes.insertRule("13% { -webkit-transform: translate(100px,100px) rotate(" + (multiplier + 45) + "deg) translate(-100px,-100px) rotate(" + (multiplier + 45) + "deg); }"); keyframes.insertRule("25% { -webkit-transform: translate(100px,100px) rotate(" + (multiplier + 90) + "deg) translate(-100px,-100px) rotate(" + (multiplier + 90) + "deg); }"); keyframes.insertRule("38% { -webkit-transform: translate(100px,100px) rotate(" + (multiplier + 135) + "deg) translate(-100px,-100px) rotate(" + (multiplier + 135) + "deg); }"); keyframes.insertRule("50% { -webkit-transform: translate(100px,100px) rotate(" + (multiplier + 180) + "deg) translate(-100px,-100px) rotate(" + (multiplier + 180) + "deg); }"); keyframes.insertRule("63% { -webkit-transform: translate(100px,100px) rotate(" + (multiplier + 225) + "deg) translate(-100px,-100px) rotate(" + (multiplier + 225) + "deg); }"); keyframes.insertRule("75% { -webkit-transform: translate(100px,100px) rotate(" + (multiplier + 270) + "deg) translate(-100px,-100px) rotate(" + (multiplier + 270) + "deg); }"); keyframes.insertRule("88% { -webkit-transform: translate(100px,100px) rotate(" + (multiplier + 315) + "deg) translate(-100px,-100px) rotate(" + (multiplier + 315) + "deg); }"); keyframes.insertRule("100% { -webkit-transform: translate(100px,100px) rotate(" + (multiplier + 360) + "deg) translate(-100px,-100px) rotate(" + (multiplier + 360) + "deg); }"); circle.style.display = "inherit"; circle.style.webkitAnimationName = anim; window.clearInterval(showPercent); currentPercent = 0; showPercent = self.setInterval(function() { if(currentPercent < 100) { currentPercent += 1; } else { currentPercent = 0; } result.innerHTML = currentPercent; }, 40); } button.onclick = function() { circle.style.webkitAnimationName = "none"; circle.style.display = "none"; setTimeout(function () { change("rotate"); }, 0); } function getClosest(keyframe) { var curr = keyframe[0]; var diff = Math.abs (totalCurrentPercent - curr); for (var val = 0; val < keyframe.length; val++) { var newdiff = Math.abs(totalCurrentPercent - keyframe[val]); if (newdiff < diff) { diff = newdiff; curr = keyframe[val]; } } return curr; }
有关此解决方案的注意事项:
@keyvalue
- -编辑 - -
如果您仅使用CSS过渡, 或者可以将动画更改为仅使用过渡,则可以使用这种更简单的方法 。您可以通过以下方式暂停过渡:复制过渡所更改的属性,将属性设置为更改后的属性,然后删除为其设置动画的类。当然,如果您使用同一对象进行动画/暂停,则将需要为第一个单击设置动画,然后在下次单击时将其暂停。您也可以轻松地完成纯JavaScript等效
注: 对!important,除非你有动画类比jQuery选择更平整选择,又名像在CSS属性的改变是必要的`div
!important
,而不是只
{。由于#defaultID和#defaultID.animationClass都是一个级别,因此此示例需要!important`
。由于
和
都是一个级别,因此此示例需要