我有一个对象,我想在画布上画画。它将使用 requestAnimationFrame
开始一个游戏循环。
Contoso.ts
class Contoso
{
//private ctx: CanvasRenderingContext2D;
Initialize(ctx: CanvasRenderingContext2D) {
//this.ctx = ctx;
Render();
}
Render() {
//...snip doing any actual drawing for the purpose of this question
requestAnimationFrame(this.Render);
}
}
app.ts
var contoso: Contoso;
contoso = new Contoso();
contoso.Initialize(canvas);
当有人第一次调用 Initialize
జజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజ requestAnimationFrame
能够正确调用 Render
.
第二次 requestAnimationFrame
电话 Render
జజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజజ this.Render
是 undefined
然后它就崩溃了。
就好像对象在最初调用了 Initialize
.
这是怎么回事?
你输了 this
语境。两种可能的修复方法。
class Contoso
{
/* ... */
// Use () => syntax so Render always gets 'this' context
// from the class instance
Render = () => {
//...snip doing any actual drawing for the purpose of this question
requestAnimationFrame(this.Render);
}
}
备用的修复方法可能会稍微清晰一些,但有一个缺点,就是要做更多的分配(你可能不想每一帧分配一个闭包!)。
Render() {
//...snip doing any actual drawing for the purpose of this question
requestAnimationFrame(() => this.Render);
}
使用箭头语法(lambda)。
requestAnimationFrame(() => this.Render());
在Firefox 49.0.1上使用Ryan Cavanaugh的解决方案时,我得到了一个错误信息:
语法错误:方法定义错误
为行。
Render = ()=> { .
我找到的解决方法是这样的。
class Test{
constructor(){
this.Render = ()=> {
requestAnimationFrame( this.Render );
};
}
}
我发现的最好的方法。
requestAnimationFrame(this.Render.bind(this));
.bind(this)
创建了一个新的函数,该函数有它的 this
关键字设置为提供的值。