Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Consider marking event handler as 'passive' to make the page more responsive

People also ask

How do you solve do not use passive listeners to improve scrolling performance?

Currently, browsers can't know if an event listener will prevent scrolling, so they always wait for the listener to finish executing before scrolling the page. Passive event listeners solve this problem by letting you indicate that an event listener will never prevent scrolling.

Can I use passive event listeners?

Event listeners created with the passive: true option cannot cancel ( preventDefault() ) the events they receive. Primarily intended to be used with touch events and wheel events. Since they cannot prevent scrolls, passive event listeners allow the browser to perform optimizations that result in smoother scrolling.

What is passive event listener invocation?

Passive event listeners are an emerging web standard, new feature shipped in Chrome 51 that provide a major potential boost to scroll performance. Chrome Release Notes. It enables developers to opt-in to better scroll performance by eliminating the need for scrolling to block on touch and wheel event listeners.


For those receiving this warning for the first time, it is due to a bleeding edge feature called Passive Event Listeners that has been implemented in browsers fairly recently (summer 2016). From https://github.com/WICG/EventListenerOptions/blob/gh-pages/explainer.md:

Passive event listeners are a new feature in the DOM spec that enable developers to opt-in to better scroll performance by eliminating the need for scrolling to block on touch and wheel event listeners. Developers can annotate touch and wheel listeners with {passive: true} to indicate that they will never invoke preventDefault. This feature shipped in Chrome 51, Firefox 49 and landed in WebKit. For full official explanation read more here.

See also: What are passive event listeners?

You may have to wait for your .js library to implement support.

If you are handling events indirectly via a JavaScript library, you may be at the mercy of that particular library's support for the feature. As of December 2019, it does not look like any of the major libraries have implemented support. Some examples:

  • jQuery.js - ongoing issue: https://github.com/jquery/jquery/issues/2871
  • React.js - ongoing issue: https://github.com/facebook/react/issues/6436
  • Hammer.js - closed due to no follow up: https://github.com/hammerjs/hammer.js/pull/987
  • perfect-scrollbar - closed: https://github.com/noraesae/perfect-scrollbar/issues/560
  • AngularJS - closed due to won't fix: https://github.com/angular/angular.js/issues/15901

This hides the warning message:

jQuery.event.special.touchstart = {
  setup: function( _, ns, handle ) {
      this.addEventListener("touchstart", handle, { passive: !ns.includes("noPreventDefault") });
  }
};

For jquery-ui-dragable with jquery-ui-touch-punch I fixed it similar to Iván Rodríguez, but with one more event override for touchmove:

jQuery.event.special.touchstart = {
    setup: function( _, ns, handle ) {
        this.addEventListener('touchstart', handle, { passive: !ns.includes('noPreventDefault') });
    }
};
jQuery.event.special.touchmove = {
    setup: function( _, ns, handle ) {
        this.addEventListener('touchmove', handle, { passive: !ns.includes('noPreventDefault') });
    }
};

Also encounter this in select2 dropdown plugin in Laravel. Changing the value as suggested by Alfred Wallace from

this.element.addEventListener(t, e, !1)

to

this.element.addEventListener(t, e, { passive: true} )

solves the issue. Why he has a down vote, I don't know but it works for me.


The following library resolved the issue.
Simply add this code to your project.

<script type="text/javascript" src="https://unpkg.com/default-passive-events"></script>

If you need more information visit this library.


For those stuck with legacy issues, find the line throwing the error and add {passive: true} - eg:

this.element.addEventListener(t, e, !1)

becomes

this.element.addEventListener(t, e, { passive: true} )

I think in addition to touch-based events you can add scroll-based fixes so to prevent google page score from flagging it for Desktop vs Mobile:

// Passive event listeners (Tw0 slight variations in setting the flag)

jQuery.event.special.touchstart = {
    setup: function( _, ns, handle ) {
        this.addEventListener("touchstart", handle, { passive: !ns.includes("noPreventDefault") });
    }
};
jQuery.event.special.touchmove = {
    setup: function( _, ns, handle ) {
        this.addEventListener("touchmove", handle, { passive: !ns.includes("noPreventDefault") });
    }
};
jQuery.event.special.wheel = {
    setup: function( _, ns, handle ){
        this.addEventListener("wheel", handle, { passive: true });
    }
};
jQuery.event.special.mousewheel = {
    setup: function( _, ns, handle ){
        this.addEventListener("mousewheel", handle, { passive: true });
    }
};