This is something with Javascript that tripped me up recently:
I had a geographical US map, with the different states highlighted - I used a jquery plugin called maphilight to get the highlights working, and needed to respond to the click event on the southern US states, I had a code along these lines:
var south=["VA", "WV", "KY", "TN", "NC", "SC", "GA", "AL", "MS", "FL", "LA", "AR"]; for (var i=0;i<south.length;i++){ $("[title=" + south[i] + "]").click(function(){ alert(south[i] + " clicked"); }); }
This however does not work - if I click on any of the southern states, the result is actually "undefined clicked".
The reason for this behavior is the closure defined as the click handler - it has a reference to variable "i" and NOT it's value at the point of defining the function, and is resolved only at the point of calling it, which is as a response to the click event. Since it is defined within a loop, i's value at the end of the loop is 12 at the end of the loop, and is resolved as south[12] in the function, and a southern state at this index does not exist
The fix is interesting, I got it from the book - Secrets of the Javascript Ninja and is to use something called an immediate function which looks something like this:
(function(){ ..... })()
Using the immediate function, the fixed code looks like this:
var south=["VA", "WV", "KY", "TN", "NC", "SC", "GA", "AL", "MS", "FL", "LA", "AR"]; for (var i=0;i<south.length;i++){ (function(index){ $("[title=" + south[index] + "]").click(function(){ alert(south[index] + " clicked"); }); })(i);
No comments:
Post a Comment