How Passive Touch Event Listeners Boost Mobile Scrolling Performance in Chrome
This article explains why touch event handlers can degrade mobile scrolling, how Chrome's passive listener option improves performance by default, the implementation details, common pitfalls, and practical fixes using CSS touch-action and proper event handling.
1. Introduction
Scrolling is a crucial interaction for mobile web pages, but touch event handlers often cause serious performance problems. Chrome allows developers to pass
{passive: true}to
addEventListener(), making listeners passive so they no longer block scrolling.
Starting with Chrome 56, touch listeners are passive by default, which greatly improves user experience without significant impact on sites.
In rare cases this can cause unintended scrolling; adding the CSS property
touch-action: noneto the affected element prevents scrolling.
2. Background
If you call
preventDefault()inside
touchstartor
touchmovehandlers, the page scroll is blocked. Browsers must wait for the handler to finish before deciding whether to scroll. By registering listeners with
{passive: true}, the browser assumes
preventDefault()will not be called, allowing smooth scrolling. Example:
element.addEventListener('touchstart', handler, {passive: true});3. Optimization
The goal is to reduce latency after a touch. Observations show about 80% of listeners are already passive but not registered as such. Chrome now defaults
passive: truefor listeners attached to
window,
document, or
body.
Implementation (illustrated in the image) sets
passiveto
truefor these listeners.
Now calls to
preventDefault()inside handlers are ignored.
Performance data collected on Android Chrome shows average latency dropping from over 400 ms to about 250 ms—a 38% reduction—with a target of sub‑50 ms response time.
4. Issues and Fixes
In most cases the optimization does not introduce bugs, but occasional unwanted scrolling or unexpected
clickevents may occur. In Chrome 56+ a DevTools warning is printed if
preventDefault()is called on a passive listener.
You can check the
defaultPreventedproperty to see whether
preventDefault()took effect.
Most problems are easily fixed by using the CSS
touch-actionproperty, e.g.,
touch-action: noneto prevent any scrolling or zooming, or
touch-action: pan-y pinch-zoomto allow only vertical scrolling and pinch‑zoom.
Because Safari and some older browsers do not support
touch-action, you still need to call
preventDefault()in event handlers for those environments.
If
preventDefault()is called in a
touchstartlistener to block a
click, ensure it is also called in the corresponding
touchendlistener.
If you must override the default and need a non‑passive listener, pass
{passive: false}to
addEventListener()and verify that the browser supports EventListenerOptions.
5. Conclusion
After Chrome 56’s passive‑listener optimization, most pages scroll faster, though a few may exhibit unexpected scrolling. Developers should avoid calling
preventDefault()in
touchstartor
touchmovehandlers and instead use the
touch-actionCSS property to control scrolling and zooming, reserving
preventDefault()for
touchendonly when necessary.
Tencent IMWeb Frontend Team
IMWeb Frontend Community gathering frontend development enthusiasts. Follow us for refined live courses by top experts, cutting‑edge technical posts, and to sharpen your frontend skills.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.