RequestAnimationFrame
RequestAnimationFrame
它主要用来解决的问题我就不说啦 今天只说说如何停止一个RAF
一般来说, RAF是递归调用的
https://developer.mozilla.org/zh-CN/docs/Web/API/Window/requestAnimationFrame
window.requestAnimationFrame = window.requestAnimationFrame || window.mozRequestAnimationFrame || window.webkitRequestAnimationFrame || window.msRequestAnimationFrame;
var start = null;
var d = document.getElementById('SomeElementYouWantToAnimate');
function step(timestamp) {
if (start === null) start = timestamp;
var progress = timestamp - start;
d.style.left = Math.min(progress/10, 200) + "px";
if (progress < 2000) {
requestAnimationFrame(step);
}
}
requestAnimationFrame(step);
如何停止一个RAF呢?
我很天真的以为这样就能停止
var id;
function loop(){
timer++;
if(timer > 180){
cancelAnimationFrame(id);
}
ps.forEach(function(i) {
rotate(i, timer);
});
id = requestAnimationFrame(loop);
}
requestAnimationFrame(loop);
然后发现没有停止
通过输出raf的id发现 我cancel的id是上一次创建的raf的id
先读得博客也已经提到 当前元组的a的cancelled设为true。
所以这里停止的只是上一次raf 不影响新创建的raf
解决方法
var timer = 1;
function loop(elapsedTime) {
if (timer > 180) {
return;
}
rotate(wrapper, timer++);
requestAnimationFrame(loop);
}
requestAnimationFrame(loop);
这是stackoverflow上的解决方案 我一开始以为这不是一种好的办法, 他没有真正停止调用, 只是超过一个条件之后什么事情都不做而已
但是实际上这就是可以停止RAF
解决方法2
执行requestAnimationFrame之后再执行cancelAnimationFrame
下面将执行100次animation
var id = null,
i = 1;
function a(time) {
console.log("animation");
id = window.requestAnimationFrame(a);
if (i++ > 100) {
window.cancelAnimationFrame(id);
}
}
a();
解决方法3
其实可以换一种思路,满足条件才开始执行RAF
var move = 0, t= 0, end = 100;
var cube = document.querySelector('.cube')
function run(){
move = Tween.Cubic.easeIn(t, move, 20, end)
t++;
cube.style.left = move + 'px';
if (t < end) requestAnimationFrame(run);
}
run();