How can I pass argument with requestAnimationFrame?

 ̄綄美尐妖づ 提交于 2019-12-18 03:54:37

问题


In the main program I randomly choose an object which I'd like to animate, so I call the function with the object as the argument. The first loop is okay, x is finely set, but in the next turn it becomes undefined.

Something like this:

var anim = {
        mainFunc: function(x) {
            anim.update(x);
            anim.redraw(x);
            window.requestAnimationFrame(anim.mainFunc);
        },

        update: function(x) {

        },

        redraw: function(x) {

        }
};

var n=Math.floor(Math.random() * (ArrayOfAnimObject.length));
anim.mainFunc(ArrayOfAnimObject[n]);

回答1:


You either need to create a reference or wrap the function call in another function like so:

mainFunc: function(x) {
    anim.update(x);
    anim.redraw(x);
    window.requestAnimationFrame(function() {
        anim.mainFunc(x);
    });
}



回答2:


You can also use .bind.

mainFunc: function(x) {
    anim.update(x);
    anim.redraw(x);
    window.requestAnimationFrame(anim.mainFunc.bind(anim,x));
}



回答3:


The best is probably to avoid having to do it.

The solutions that would allow you to do this will require that you create a new Function (be it the anonymous wrapper from @kalley's answer, or the bound one from @ArchyWillHe's) every frame.

In an animation loop, you want to leave the less collectable objects as possible, so that the Garbage Collector doesn't have to kick in while your animation is running, killing a few frames when it will happen.

In order to perform this, you have different strategies available, but for instance in the case exposed in OP, this x parameter should probably be attached to the anim object directly:

var anim = {
  mainFunc: function() {
    anim.update();
    anim.redraw();
    window.requestAnimationFrame(this.mainFunc);
  },

  update: function() {
    this.x ++;
  },

  redraw: function() {
    log.textContent = this.x;
  }
};
// replace it with a bound function only once
anim.mainFunc = anim.mainFunc.bind(anim);
anim.x = 0; // attach the parameter to the anim object
anim.mainFunc();
<pre id="log"></pre>

One may also prefer just keeping this parameter as a variable available for both the caller and anim:

(function() {

var anim = {
  mainFunc: function() {
    anim.update();
    anim.redraw();
    window.requestAnimationFrame(anim.mainFunc);
  },

  update: function() {
    x ++;
  },

  redraw: function() {
    log.textContent = x;
  }
};
var x = 0; // available for both us and anim's method
anim.mainFunc();

})();
<pre id="log"></pre>


来源:https://stackoverflow.com/questions/19893336/how-can-i-pass-argument-with-requestanimationframe

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!