Javascript 此关键字失去了对当前模块的引用
我正在开发BackboneJS模块。在视图中,我将插件应用于当前元素。我正在传递设置为当前视图属性的选项对象setOptions。在这个对象中,我还调用了一个函数this.foo。但它给了我以下错误:foo的未定义。下面是我的代码Javascript 此关键字失去了对当前模块的引用,javascript,jquery,backbone.js,Javascript,Jquery,Backbone.js,我正在开发BackboneJS模块。在视图中,我将插件应用于当前元素。我正在传递设置为当前视图属性的选项对象setOptions。在这个对象中,我还调用了一个函数this.foo。但它给了我以下错误:foo的未定义。下面是我的代码 var b = Backbone.View.extend({ setOptions: { opt1: 'Option 1', opt2: 'Option 2', opt3: 'Option 3',
var b = Backbone.View.extend({
setOptions: {
opt1: 'Option 1',
opt2: 'Option 2',
opt3: 'Option 3',
opt4: 'Option 4',
callback: this.foo // this returns foo of undefined
},
initialize: function () {
this.setPlugin();
},
setPlugin: function () {
this.$el.pluginName(this.setOptions);
},
foo: function () {
console.log('FOO');
}
});
为了解决这个问题,我编写了一个函数setOptions。并返回设置插件选项的对象文字。这次This.foo函数调用成功,但在foo中,对This的引用指向此。$el。我希望这个关键字指向当前模块,而不是那个元素。我需要这个,因为我想在foo中调用更多函数,但是我不能,因为对这个关键字的引用被更改了。我该怎么做
下面是我第二次尝试的代码
var b = Backbone.View.extend({
initialize: function () {
this.setPlugin();
},
setPlugin: function () {
this.$el.pluginName(this.setOptions());
},
setOptions: function () {
return {
opt1: 'Option 1',
opt2: 'Option 2',
opt3: 'Option 3',
opt4: 'Option 4',
callback: this.foo
}
},
foo: function () {
// here "this" reference to this.$el but not current module
console.log('FOO');
}
});
问题是,在创建对象之前,不能从同一对象引用对象的属性。因此,在您的例子中,当视图对象被构造时,它会被行回调:this.foo在对象中还没有创建这样的属性。因此出现了错误 最简单的解决方法是使用getter函数:
setOptions: function() {
return {
opt1: 'Option 1',
opt2: 'Option 2',
opt3: 'Option 3',
opt4: 'Option 4',
callback: _.bind(this.foo, this)
}
},
然后像这样使用它:
setPlugin: function () {
this.$el.pluginName(this.setOptions());
},
下面是正在发生的事情查看评论:
这里有一个修正:
// Fake "plugin" function.
function pluginName(options) {
options.callback.call(document.body);
}
var view = {
initialize: function () {
this.setPlugin();
},
setPlugin: function () {
pluginName(this.setOptions());
},
setOptions: function () {
return {
opt1: 'Option 1',
opt2: 'Option 2',
opt3: 'Option 3',
opt4: 'Option 4',
// The 'bind' method creates an other callback for you, by making
// the 'this' value equal to whatever you pass it as the first argument.
callback: this.foo.bind(this) // or use Underscore's '_.bind()' method as mentioned below.
}
},
foo: function () {
console.log('FOO');
console.log(this); // 'this' here is the 'view' object.
}
};
下面是另一个修复方法:
// Fake "plugin" function.
function pluginName(options) {
options.callback.call(document.body);
}
var view = {
initialize: function () {
this.setPlugin();
},
setPlugin: function () {
pluginName(this.setOptions());
},
setOptions: function () {
var self = this;
return {
opt1: 'Option 1',
opt2: 'Option 2',
opt3: 'Option 3',
opt4: 'Option 4',
// Similar to the 'bind' method but manually.
callback: function() {
self.foo();
}
}
},
foo: function () {
console.log('FOO');
console.log(this); // 'this' here is the 'view' object.
}
};
我已经在使用这个解决方案了。但它也有一个问题。请仔细阅读我的问题。@2619请尝试回调:\ uu.bindthis.foo,this以将this.foo绑定到模块上下文。我尝试过,但现在得到了未捕获的错误类型错误:无法读取undefinedWhat is pluginName的属性“ownerDocument”?jquery插件?是的,它是jquery插件。AFAIU foo是从jquery插件构造函数调用的。在这种情况下,您无法更改此In-foo回调的上下文,因为它完全取决于插件如何调用它。显然,插件在与插件绑定的DOM元素的上下文中调用foo。所以改变上下文的唯一方法就是修改插件的代码。
// Fake "plugin" function.
function pluginName(options) {
options.callback.call(document.body);
}
var view = {
initialize: function () {
this.setPlugin();
},
setPlugin: function () {
pluginName(this.setOptions());
},
setOptions: function () {
var self = this;
return {
opt1: 'Option 1',
opt2: 'Option 2',
opt3: 'Option 3',
opt4: 'Option 4',
// Similar to the 'bind' method but manually.
callback: function() {
self.foo();
}
}
},
foo: function () {
console.log('FOO');
console.log(this); // 'this' here is the 'view' object.
}
};