Ticket #3906 (closed bug: wontfix)
Live() generates duplicate click events if it's contained within an each() callback and the selector is scoped to a context
| Reported by: | jsdalton | Owned by: | brandon |
|---|---|---|---|
| Priority: | major | Milestone: | 1.3.1 |
| Component: | event | Version: | 1.3 |
| Keywords: | live() | Cc: | |
| Blocking: | Blocked by: |
Description
My apologies if this is a duplicate or invalid ticket, of if I'm just doing something wrong, but I believe this is a bug related to the new live() method.
I have discovered that, within the scope of an each() callback, if a click event is bound to a selector that contains a contex pointing to the this DOM element from the each loop, the event starts firing duplicate times, as though more than one object were clicked.
This is a bit hard to explain, it's best seen by example.
The following code works as one would expect it would, using the regular click() event handler:
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>Live</title>
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3/jquery.min.js"></script>
<script type="text/javascript">
(function($) {
$(document).ready(function() {
$(".foo").each(function() {
$("a", this).click(function() {
alert( $(this).text() );
return false;
})
});
});
})(jQuery);
</script>
</head>
<body>
<p class="foo"><a href="#">here's a click</a></p>
<p class="foo"><a href="#">there's a click</a></p>
</body>
</html>
Now, observe, the only change I am making is changing .click(function() {...}) to .live("click", function() {...}):
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN"
"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" xml:lang="en" lang="en">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8"/>
<title>Live</title>
<script type="text/javascript" src="http://ajax.googleapis.com/ajax/libs/jquery/1.3/jquery.min.js"></script>
<script type="text/javascript">
(function($) {
$(document).ready(function() {
$(".foo").each(function() {
$("a", this).live("click", function() {
alert( $(this).text() );
return false;
})
});
});
})(jQuery);
</script>
</head>
<body>
<p class="foo"><a href="#">here's a click</a></p>
<p class="foo"><a href="#">there's a click</a></p>
</body>
</html>
Observe that the alert window appears twice, as though the element were clicked twice.
I reduced this bug down to it's simplest form I could get it to. If you have more hyperlinks on the page the problem gets even worse.
Note that if you remove the each() scope, it functions as normal.
I have tested this in both Firefox 3.0.5 for Mac and Safari 3.1.2 for Mac and I get the same result in each.
I hope this is helpful. Thanks.
(Loving 1.3 btw, thanks for all the hard work you guys put into it.)
Change History
Please follow the bug reporting guidlines and use jsFiddle when providing test cases and demonstrations instead of pasting the code in the ticket.

That's correct. As of right now .live() doesn't support contexts passed in - only normal selectors. Without knowing more about your specific case you can get away with doing:
$(".foo a").live("click", function() { alert( $(this).text() ); return false; });I'll make a note of this in the documentation.