I'm not using eval, and I'm not sure what the problem is that Crockford has with the following. Is there a better approach to solve the following problem or is this just something I need to ignore (I prefer to perfect/improve my solutions if there is areas for improvement).
I'm using some pixel tracking stuff and in this case a client has bound a JS function to the onclick
property of an HTML image tag which redirects off the site. I need to track the clicks reliably without running into race conditions with multiples of event listeners on the image. The strategy is to override the event at run time, copying and running it in my own function. Note this is being applied to a site I do not control and cannot change. So the solution looks something like:
...
func = Function(img.attr('onclick'));
...
img.attr('onclick', '');
... //some custom tracking code
func.call(this);
and the JSLint checker throws the eval is evil
error.
Is there a better way to avoid race conditions for multiple events around href
actions?
You're implicitly using eval
because you're asking for the callback function as it was specified as an attribute in the HTML as a string and then constructing a Function
with it.
Just use the img.onclick
property instead, and you will directly obtain the function that the browser built from the attribute that you can then .call
:
var func = img.onclick; // access already compiled function
img.onclick = null; // property change updates the attribute too
... // some custom tracking code
func.call(img, ev); // call the original function
or better yet:
(function(el) {
var old = el.onclick;
el.onclick = function() {
// do my stuff
..
// invoke the old handler with the same parameters
old.apply(this, arguments);
}
})(img);
The advantage of this latter method are two fold:
var oldClick = myImg.onclick;
myImg.onclick = function(evt){
// Put you own code here
return oldClick.call( this, evt );
};
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With