New issue
Advanced search Search tips
Note: Color blocks (like or ) mean that a user may not be available. Tooltip shows the reason.

Issue 752838 link

Starred by 1 user

Issue metadata

Status: WontFix
Owner: ----
Closed: Aug 9
Cc:
Components:
EstimatedDays: ----
NextAction: ----
OS: Windows
Pri: 2
Type: Bug



Sign in to add a comment

Smooth Scroll Causes setTimeout to Behave Erratically

Reported by jacklu...@gmail.com, Aug 7 2017

Issue description

UserAgent: Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/60.0.3112.90 Safari/537.36

Steps to reproduce the problem:
1. Go to a major website with a complicated layout (im using cnn.com)
2) Open dev tools and navigate to console
3) Paste the following snippet 

// this snippet logs time for a setTimeout to fire
window.onscroll =  function() {
  if(window.i == undefined) {
    window.i = 0;
  }
  else {
   window.i++;
  }
  var k = i;
  console.time('timer'+k);
  setTimeout(function(){ 
    console.timeEnd('timer'+k);
  }, 50);
};

4) Position mouse over the scroll bar (so to not trigger any dom events) and scroll using your mousewheel

5) Notice that the setTimeout will fire at intervals that can spike many multiples of 100ms. (for me as high as 4000ms)

5) Now try scrolling by left clicking on the scroll bar and dragging it downward

6) Notice that the timer nearly always occurs correctly at 50ms

7) If the issue doesnt occur immediately try leaving the tab stale, minimizing etc, then coming back to the page and trying again

What is the expected behavior?
setTimeout when scrolling using mousewheel should still execute near 50ms from scroll event.

Understandably this can vary, but using mousewheel I've seen it show up as slow as 2000ms for a 50ms timer.

Using the same behavior with a mouse dragging the scrollbar does not have issues.

Other browsers (tested firefox, ie) appear to reproduce the timer more consistently without large spikes.

What went wrong?
This issue with setTimeout occurs for all timers on a page after using mousewheel to scroll, for example if there is a setTimeout in the event handler of a page element it may also be delayed.

I noticed that setTimeout() i use to debounce dropdowns/popups in semantic-ui (semantic-ui.com) in recent versions of Chrome would appear not to function immediately after using mousewheel to scroll. 

I then realized this seems to occur on any setTimeout usage immediately after or during scroll specifically with mousewheel.

Did this work before? N/A 

Does this work in other browsers? Yes

Chrome version: 60.0.3112.90  Channel: stable
OS Version: 10.0
Flash Version: Shockwave Flash 26.0 r0

Example output from nytimes.com

timer0: 293.398193359375ms
VM274:11 timer1: 277.624267578125ms
VM274:11 timer2: 260.62109375ms
VM274:11 timer3: 244.38330078125ms
VM274:11 timer4: 227.494873046875ms
VM274:11 timer5: 211.114990234375ms
VM274:11 timer6: 194.045166015625ms
VM274:11 timer7: 177.667724609375ms
VM274:11 timer8: 161.2470703125ms
VM274:11 timer9: 144.19873046875ms
VM274:11 timer10: 128.044189453125ms
VM274:11 timer11: 111.556884765625ms
VM274:11 timer12: 94.134033203125ms
VM274:11 timer13: 78.60302734375ms
VM274:11 timer14: 61.9140625ms
VM274:11 timer15: 52.564208984375ms
VM274:11 timer16: 52.06201171875ms
VM274:11 timer17: 50.735107421875ms
VM274:11 timer18: 53.10498046875ms
VM274:11 timer19: 51.208984375ms
VM274:11 timer20: 50.52783203125ms
VM274:11 timer21: 50.4677734375ms
VM274:11 timer22: 50.29296875ms
VM274:11 timer23: 269.1669921875ms
VM274:11 timer24: 252.72705078125ms
VM274:11 timer25: 236.729736328125ms
VM274:11 timer26: 220.343994140625ms
VM274:11 timer27: 202.99609375ms
VM274:11 timer28: 186.555908203125ms
VM274:11 timer29: 170.58984375ms
VM274:11 timer30: 136.77783203125ms
VM274:11 timer31: 121.742919921875ms
VM274:11 timer32: 105.121826171875ms
VM274:11 timer33: 88.4970703125ms
VM274:11 timer34: 72.141845703125ms
VM274:11 timer35: 55.921875ms
VM274:11 timer36: 50.281005859375ms
 

Comment 1 by woxxom@gmail.com, Aug 7 2017

The difference you observe is caused by the page's mousewheel event listener, which is not triggered while dragging the scrollbar. You may want to add a passive event listener instead. BTW, on a fast PC here I see ~51ms in both use cases except one spike for the lazily-loaded bottom of the page. 

Comment 2 by woxxom@gmail.com, Aug 7 2017

Correction: the spec-compliant solution in your case would be to use a capturing event listener ("useCapture" parameter should be "true"):
window.addEventListener('scroll',  function() { ..... }, true);
Cc: brajkumar@chromium.org
Components: Blink>Scroll
Labels: Needs-Triage-M60 Needs-Feedback
Unable to reproduce this issue on Windows-10 using chrome latest stable #60.0.3112.90 by following steps mentioned in the original comment, Observed the setTimeout didn't fire more than 70ms while scrolling the CNN page using mouse scroll. 

Attaching screen-cast for reference could you please take a look in to this issue and let me know if anything is missing fro my end.

Thanks!
752838.mp4
12.5 MB View Download
Components: Blink>Scheduling Blink>Input
Status: Available (was: Unconfirmed)
On a page with a potentially blocking wheel event handlers, Chrome may choose to defer timer execution in order to improve animation smoothness. You should see a message about this in the developer console if this is happening in your case.

One way to avoid this is to make your event handlers passive[1] so that the browser knows that main thread responsiveness isn't critical to animation smoothness.

(IIRC we might still be missing some scheduler plumbing related to handler passiveness so we may need to tweak some things here.)

[1] https://github.com/WICG/EventListenerOptions/blob/gh-pages/explainer.md
Project Member

Comment 5 by sheriffbot@chromium.org, Aug 8

Labels: Hotlist-Recharge-Cold
Status: Untriaged (was: Available)
This issue has been Available for over a year. If it's no longer important or seems unlikely to be fixed, please consider closing it out. If it is important, please re-triage the issue.

Sorry for the inconvenience if the bug really should have been left as Available.

For more details visit https://www.chromium.org/issue-tracking/autotriage - Your friendly Sheriffbot
Status: WontFix (was: Untriaged)

Sign in to add a comment