Reputation: 37305
I have a potentially strange question about this
and jQuery plugins
As I understand it, the following is a very basic jQuery plugin:
$.fn.clickclone = function(param){
return this.click(function(){
param.apply(this);
});
};
(pretending that's a plugin that somehow extends click()
.)
So, if I pass a function as an argument, it does what it needs to do and properly accesses this
as a DOM node. Easy.
That's all clear to me.
What's not clear is, is there any way I could pass a non-function argument to the plugin and have it properly access this
from the arguments? ie, could I configure the plugin to do something like this:
$("#foo").pluginname(["foo", $(this).text() ]);
Such that for:
<a href="/bar" id="foo">Bar</a>
It would properly pass an array to the plugin, with the second item in the array returning the value Bar
?
I'm doing this, basically, to provide syntactic sugar for my plugin, where you can pass an array as a shortcut (in addition to using a normal callback function as the main functionality). Except, doing that, I lose access to use of this
. Hence my dilemma.
EDIT: This is evil, but, it seems like one work around is to pass the argument as a string and then eval
it. Not a workable solution for me, but, it illustrates what I'd like to be able to do:
$.fn.clickclone = function(param){
return this.click(function(){
if(typeof param === "function"){
param.apply(this);
}
else if(typeof param[1] === "string"){
console.dir("This is evil: " + eval(param[1]));
}
});
};
Upvotes: 4
Views: 124
Reputation: 112837
There's no general way to do this without a function, since, in the purely mathematical sense, you are asking for a function of the input (that is, a function of this
): something that depends on this
in a certain way.
You could perhaps hack it with strings, like so, but you lose the flexibility of functions:
$.fn.alertMe = function (methodToAlert) {
alert(this[methodToAlert]());
};
// usage:
$("#foo").alertMe("text");
$("#foo").alertMe("width");
And if you find using a function acceptable but the this
syntax confusing, you can simply do the following:
$.fn.alertMe = function (alertGetter) {
alert(alertGetter($(this));
};
// usage:
$("#foo").alertMe(function (x$) { return x$.text(); });
$("#foo").alertMe(function (x$) { return x$.width(); });
And for completeness I guess I should mention you could probably get away with an eval
-based solution, looking something like $("#foo").alertMe("$(this).text()")
, but eval
is evil and I will neither write up nor condone such a solution. EDIT: oh, I see you have done so in an edit to your original post. Good job corrupting future generations ;)
Upvotes: 2