Reputation: 888
I have two pages: parent.html and child.html. child.html is included in parent.html with an iframe.
The child.html page bind a scroll event on its parent.window in order to detect when a scroll event is triggered at the top level. The child page set a property on the parent.window in order to display and update an increment each time the scroll event is triggered.
Here is the code of the two pages:
Page parent.html:
<html>
<body>
<iframe border="1" src="child.html"></iframe>
<div style="height:1600px; width:300px; background:gray;">
A div just here to activate the scrollbar
</div>
</body>
</html>
Page child:
<html>
<body>
<a target="_self" href="">Reload this page</a>
<div class="test"></div>
<script type="text/javascript">
parent.window.increment = 1;
var onScroll = function (event) {
parent.window.increment++;
$('.test').html(parent.window.increment);
};
$(parent.window).off('scroll');
$(parent.window).on('scroll', onScroll);
</script>
</body>
</html>
On Chrome (it works on Firefox), if you load the page for the first time the parent.window.increment is correctly incremented by 1 each time a scroll event is detected (when the parent page scrollbar is moved). But if you press on the "Reload" link the parent.window.increment is no more incremented by one when a scroll event is triggered but by two. If you press again on the Reload link the increment property is incremented by 3, etc.
A working example can be found here : http://jsfiddle.net/cm0s/ngZkq/16/.
I'm not really looking for a solution (the code I posted is just an example of a problem I'm facing in another project). I'd rather like to understand what's happening. If I'm making a rookie mistake?
Here are two things I really don't understand :
1. parent.window.increment not reset
I don't understand why the increment property is not always reset to 1. When we press on the "Reload" link the following line is always executed :
parent.window.increment = 1;
2. Works on Firefox but not on Chrome
What I also don't understand is why it doesn't work on Chrome but works fine on Firefox. With Firefox if you try the fiddle demo and click multiple times on the Reload link the parent.window.increment is always incremented by 1 when you move the scroll bar.
I also created a fiddle to show the same problem with a click event : http://jsfiddle.net/cm0s/WYy6U/3/
And another one which use the onscroll javascript function (as explained by @hex494D49) and thus works perfectly in all browsers : http://jsfiddle.net/cm0s/D6j5G/1/
I posted a ticket on the jquery bug tracker: http://bugs.jquery.com/ticket/15204.
The ticket has been closed. The bug has been described as "an unusual browser behavior".
Upvotes: 1
Views: 1822
Reputation: 9235
You just might found a bug in jQuery :) or at least a weird behavior of jQuery's onscroll
event implementation. Perhaps, this could be a shorter answer on your both questions but let's analyze this behavior in more details.
If you add this console.log(parent.window.increment);
in your code, you will see that at the first time Chrome is increasing the value of increment
value just fine; but at the second time, the amount of the scroll is increasing by two as following 1-2, 3-4, 5-6, ...
and that's way the increment
value within the div
seem disordered (like 2, 4, 6, ...); at the third time Chrome starts skipping steps like this 2-3, 5-6, 8-9, 11-12, ...
and the values within the div
came in as 3, 6, 9, 12, ...; at the fourth time values goes like this 3-4, 7-8, 11-12, 15-16, ...
which makes the increment
value within the div
even more fuzzy.
On the other hand, the snippet above works fine in Firefox but the amount of scroll isn't increasing by 1 but at least by 5 and this could be seen only observing the console. Maybe this could be adjusted - I tried to change a few values related to scroll
in Firefox about:config
section but without success so far.
Then I just thought I could change your snippet a bit (excluding jQuery) and here we are - the snippet below works just as expected in all browsers. The scroll amount on Firefox is still about 5 but you'll see that the increment
value on reload is always resetting to 0
and there are no skippings as mentioned in case with jQuery snippet.
// Modified code of child.html (iframe) file
// HTML
<a target="_self" href="">Reload this page</a>
<div id="test"></div>
// JavaScript
parent.window.increment = 0;
parent.window.onscroll = function(){
parent.window.increment++;
document.getElementById('test').innerHTML = parent.window.increment;
console.log(parent.window.increment);
};
Working jsFiddle (Tested on IE, Firefox, Chrome and Opera)
EDIT:
As @NicolasForney (the OP) says in the meantime in his edit section, the same weird behavior is experienced using onclick
event. I'd like to add that the same would be avoided not using jQuery, just as shown in the previous case with onscroll
event.
<!-- HTML -->
<a target="_self" href="">Reload this page</a>
<div id="counter"></div>
// JavaScript
parent.window.counter = 0;
parent.window.onclick = function(){
parent.window.counter++;
document.getElementById('counter').innerHTML = parent.window.counter;
console.log(parent.window.counter);
};
Working jsFiddle (Tested as above)
This definitely leads to a bug which should be explored in more details in the meantime...
Upvotes: 2