用 requestAnimationFrame 写动画发现有些问题想请教一下各位

2017-11-03 16:45:42 +08:00
 cheroky

主要就是想再 rAF 之后调用其它的函数,开始感觉很简单,但是一写发现不会。。 最刚开始的想法 callback 放在 rAF 的结束条件中发现会死循环。 我想着按照回调队列,能不能让一个函数始终在队列末尾,然后我现在解决办法是动画完了进入结束条件之后会改变一个状态变量然后 return,然后写一个判断函数放入 setTimeout(),判断函数如下:

engageToWhere(shelf,cb) {
        this.animate_state = "ANIMATE";
        //...
        this._animation(targetY,diff>=0?0:1); //动画
        function checkIfIdle() {
            if (self.animate_state==='ANIMATE') {
                setTimeout(checkIfIdle,0);
            } else {
                cb();
            }
        }
        checkIfIdle();
        
    }

虽然功能是实现了,但是觉得实现方法有待商榷,百度了很久也没有说关于这个的事情,只在 stackoverflow 看到有类似的问题,不知道在实际工作中应该怎么判断动画结束??

2218 次点击
所在节点    JavaScript
7 条回复
jamesliu96
2017-11-03 17:00:31 +08:00
既然 raf 有现有的结束条件,为什么还要 animate_state ?

进入结束条件之后调用回调一次,不执行 raf,怎么会出现死循环?
cheroky
2017-11-03 17:09:11 +08:00
@jamesliu96 我也觉得奇怪,可能是我方法有点问题,我把_animation 贴出来

```
_animation(target,direction) {
var top = this.entity.offsetTop;
//console.log(top,target,direction);
if(direction) {
top-=18;
} else {
top++;
}
if((!direction && top>=target) || (direction && top<=target)) {
this.animate_state = "IDLE";
return;
//callback() 在这死循环
}
var bindAnimation = this._animation.bind(this,target,direction);

this.entity.style.top = top+'px';
requestAnimationFrame(bindAnimation);
}
```
jamesliu96
2017-11-03 17:20:33 +08:00
@cheroky 是不是 callback() 之后没 return ?
cheroky
2017-11-03 17:34:28 +08:00
@jamesliu96 0.0 真的没写 return,试了下可以了!!!但就是不太懂为啥得写 return ?我看 stackoverflow 上也没写 return,误人子弟啊
jamesliu96
2017-11-03 17:36:35 +08:00
@cheroky 老哥我就看了一眼,猜到应该是这个原因。不 return 就又调用 raf 了啊。
cheroky
2017-11-03 17:38:52 +08:00
@jamesliu96 是我蠢了蠢了。。。多谢多谢
erlking
2017-11-03 18:29:29 +08:00
结束条件加 cancelAnimationFrame(bindAnimation); 应该就好了

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/403301

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX