I'm trying to bind event handlers within a loop such as:
var tabs = ['one', 'two', 'three', 'four']
for(var i = 0; i < tabs.length; i++) {
alert(tabs[i]);
var id = i;
$('#' + tabs[i]).bind('click', function() {
loadTabs(id, tabs);
});
}
Which only keeps the last one bound (value 'four').
I'm trying to consolidate this code which currently does work:
$('#one').click(function() {
loadTabs(0, tabs);
});
$('#two').click(function() {
loadTabs(1, tabs);
});
$('#three').click(function() {
loadTabs(2, tabs);
});
$('#four').click(function() {
loadTabs(3, tabs);
});
Thought I might need a closure due to this post.
You are right about what you read in the other post. You need to make a closure to bind the arguments to each single onclick handler:
$('#' + tabs[i]).bind(
'click',
(function(id) {
return function()
{
loadTabs(id, tabs);
};
})(id)
);
You might also want to look into currying. In this example you might create a small helper function, which binds the first argument to a passed function and returns the new function.
function curry(func, arg1)
{
return function()
{
func(arg);
};
}
And then put it together like this:
$('#' + tabs[i]).bind(
'click',
curry(function(id) { loadTabs(id); }, id)
);
Note that my curry function does not match the definition of currying, because it ignores any other argument. But it should work for your case.
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