Reputation: 366
I have a function that accepts an anonymous function as an argument and sets it to a variable (scoped) for reference. I then try to execute another function with that reference but it obviously fails since that function is out of scope.
I was wondering if anyone knew of a simple way of passing the anonymous function straight through as an anonymous function, avoiding the scoping issue?
EDIT: To clarify, the el element is defined after the function is isolated from the arguments list. Additionally, the el element is a part of the arguments list as well. Were this code to be used by only me, I would likely have used a two argument list with the second argument being an array or hash object but unfortunately this code is going to be used by some folks who are less familiar with JS or even coding for that matter.
Thanks for the help!
Here is the relevant portion of my code:
locate : function(){
if ((!arguments)||(!arguments.length)) return;
arguments = [].splice.call(arguments,0); //This just converts arguments into an array
for (var i=0;i<arguments.length;i++){
if (typeof(arguments[i])=='function'){
var tf = arguments.splice(i,1);
break;
};
};
if (!tf) return;
JAS.Globals.eventListen('click',el,tf);
}
This is abbreviated so just trust that el is defined. JAS.Globals.eventListen is just an intelligent addEventListener.
Upvotes: 1
Views: 1823
Reputation: 61558
I am not a JS expert, not sure if this will help in your case.
But since you are asking for a way to pass a function "by value"... you can re-compose the function so it becomes anonymous again, like this:
JAS.Globals.eventListen('click', el,
new Function(tf.toString() + tf.name + "();")
What that last part do is that it creates a new function from the original source obtained from tf.toString()
which will prints out the function's definition code with the same function name, but in the scope of the about-to-be-created function.
And then you immediately calls that very function with tf.name + "();"
.
Note that if the function doesn't have a name, then you can wraps it in as an inline function call, i.e.:
new Function("(" + tf.toString() + ")();");
Wrapping it up:
new Function(tf.name
? (tf.toString() + tf.name + "();") // func has a name, call by name
: ("(" + tf.toString() + ")();") // func don't have a name, call inline
Try it out in Firebug to see what I mean.
Upvotes: 0
Reputation: 189505
var tf = arguments.splice(i,1)
This returns an array into tf. Is eventListen expecting an array? If not use:-
var tf = arguments.splice(i,1)[0]
Since you don't seem to have any other uses for your other arguments why are you using splice anyway?
Upvotes: 3
Reputation: 85194
You can do:
for (var i=0;i<arguments.length;i++){
if (typeof(arguments[i])=='function'){
JAS.Globals.eventListen('click',el,arguments[i]);
break;
}
}
or if you need to assign the event after the loop for some reason:
var tf;
for (var i=0;i<arguments.length;i++){
if (typeof(arguments[i])=='function'){
tf = arguments[i];
break;
}
}
if (!tf) return;
JAS.Globals.eventListen('click',el,tf);
Upvotes: 0