How to pass 'this' along with a function?
I want to delegate some function calls from one object to another:
objA.feature = objA.component.feature;
(Assuming feature
is supposed to be a function both in objA and in its component)
But that clearly doesn't work, because the reference to this
gets stripped from the fun开发者_如何学Cction and ends up being a completely different object when it gets called (it actually is objA
instead of objB.component
).
You need to write something like this in order to get it to work:
objA.feature = function() {
objA.component.feature.apply(objA.component, arguments);
};
Is there a shorter (idiomatic) way to do that?
There's a function called "bind" on the Function prototype in newer runtimes:
var newFunc = someFunc.bind(somethingThatShouldBeThis);
will make this
refer to "somethingThatShouldBeThis" when "newFunc" is called.
You can steal code from something like the Functional library to provide a "bind" function in environments that lack a native one.
edit — here's the code from Functional:
Function.prototype.bind = function(object/*, args...*/) {
var fn = this;
var args = Array.slice(arguments, 1);
return function() {
return fn.apply(object, args.concat(Array.slice(arguments, 0)));
}
}
Pretty simple, eh? It just returns a function back to you that, when invoked, will call the first argument as a function, and also pass along whatever arguments you pass in to the result (that is, to "newFunc" in the example above). The main wrinkle is that this one also saves extra arguments passed in originally, which can sometimes be handy.
Here is a great article on scope:
Binding Scope in JavaScript
However, most JavaScript frameworks (MooTools, jQuery) have built in methods for this. jQuery uses "proxy" and MooTools uses "bind", so be sure to check the documentation of whatever framework you're using.
Your best bet is to use a createDelegate-style method like some of the frameworks do. A bare-bones implementation was posted on OdeToCode a few years ago.
精彩评论