【发布时间】:2013-10-20 10:32:47
【问题描述】:
我有以下代码沿其路径为对象(“标记”)设置动画,该路径是坐标数组(x,y,t,其中 t 是此坐标与下一个坐标之间的时间,以 ms 为单位-- 考虑对象的加速/减速。路径是由用户的鼠标移动生成的,需要高精度)。该项目使用 d3.js 为 SVG 制作动画。
function Animation(tag,path) {
this.tag = tag;
this.path = path;
}
Animation.prototype = {
start : function () {
console.log('Animation created');
var i = 0;
var nextTime = this.path[0].t;
var thisClass = this;
setTimeout(function(){}, nextTime );
console.log('Beginning animation');
function step() {
setTimeout( function(){
if(i == thisClass.path.length -1 ) {
var now = new Date();
console.log('Animation for '+ thisClass.tag.attr('id') + ' played at ' + (now - globalTimer) + 'ms.');
return;
}
if(i === 0) {
var now = new Date();
console.log('Animation for '+ thisClass.tag.attr('id') + ' started at ' + (now - globalTimer) + 'ms.');
}
thisClass.tag
.attr('cx', thisClass.path[i].x)
.attr('cy', thisClass.path[i].y);
i++;
requestAnimationFrame(step);
}, thisClass.path.t);
}
requestAnimationFrame(step);
}
};
另一个类负责安排每个动画的播放时间。例如,在 30 秒的时间段内,必须播放 3 个动画,时间分别为 :03、:09、:25。当需要播放动画时,调度器调用它:
new Animation(Tag, Path).start();
问题:虽然调度程序按时正确调用每个动画,但没有按时执行函数step()的实例——它们似乎都发生在记录周期的最后, 一次全部。所以虽然有人希望我的日志看起来像这样:
动画制作
开始动画
动画播放
动画创建
开始动画
动画播放
...
...相反,它看起来像这样:
动画制作
开始动画
动画创建
开始动画(2)动画播放
(编辑:http://puu.sh/4Ucw9.png了解更多细节。“动画推送”出现在new Animation(...)之后,所以理论上,在动画完成之后。如你所见,三个标签(c0,c1, c2) 应该分别在不同的 ms 标记处调用,但所有三个的动画都从 7019ms 开始)
动画应该在被调用时播放,而不是在时间段结束时播放。似乎他们正在排队,然后立即全部执行,但据我了解,我没有告诉他们这样做。我怀疑requestAnimationFrame 在某种程度上是关键,但我昨天才开始使用它,所以我仍然不能 100% 确定它的作用以及如何使用它。有谁知道怎么回事?
【问题讨论】:
-
使用原始动画帧有什么特别的原因吗?您可以使用 D3 的转换来完成所有这些工作。
-
我不能 100% 确定我会继续使用原始动画帧,但到目前为止,它们是最容易管理和实施的。它们有点乱,是的,但我宁愿先让原型的基础工作,然后让代码变得更好、更快、更漂亮。
-
我是说使用过渡会更容易。
-
"Path" 记录用户的鼠标移动。这意味着完全任意的加速度、减速度、方向等。是否可以有效地使用转换忠实地重新创建所有这些?
-
是的,虽然我同意它可能不适合这个特定目的。无论如何,我不确定您的问题与 D3 有什么关系。
标签: javascript jquery animation d3.js