Event listener for Passive

Source: Internet
Author: User

A long time ago, the parameter conventions of AddEventListener () were this:

AddEventListener (type, listener, usecapture)

Later, the last parameter, the usecapture parameter that the control listener executes during the capture phase or during the bubbling phase, becomes an optional parameter (too few for true), which is:

AddEventListener (Type, listener[, Usecapture])

At the end of last year, the DOM specification was revised: the third parameter of AddEventListener () can be an object value, which means that the third parameter can now be two types of values:

AddEventListener (Type, listener[, Usecapture]) AddEventListener (Type, listener[, Options])

This revision is intended to extend the new options to customize more behavior, with three properties available for the options object in the current specification:

AddEventListener (type, listener, {    false    ,false,      False})

All three properties are Boolean-type switches, and the default value is False. Where the Capture property is equivalent to the previous usecapture parameter, the Once property indicates that the listener is a one-time, is automatically removeeventlistener after execution once, and has not been implemented by the browser; The passive attribute is the protagonist of this article. Firefox and chrome have been implemented, first look at the official Chrome video introduction (click Play):

Many mobile pages will listen to Touchstart and other touch events like this:

function (e) {    ...//browser does not know if there will be E.preventdefault ()})

Because the Cancelable property of the Touchstart event object is true, which means that its default behavior can be blocked by the listener through the Preventdefault () method, what is its default behavior, usually scrolling the current page (and possibly scaling the page), If its default behavior is blocked, the page must still stay stationary. But the browser cannot know in advance whether a listener will call Preventdefault (), it can only do when the listener executes the default behavior, and the listener execution is time-consuming, some even time-consuming is obvious, which causes the page to lag. The video also said that even if the listener is an empty function, it will produce a certain lag, after all, the execution of empty functions will be time-consuming.

The video also says that there are 80% of scrolling event listeners that don't block the default behavior, which means that in most cases, the browser is white. So, the passive listener was born, passive meant "submissive," that it would not say no to the default behavior of the event, that the browser knew that a listener was passive, and that it could execute JavaScript in the listener simultaneously in two lines thread The default behavior of the code and the browser.

Here is the comparison video on the Chrome for Android scrolling CNN.com Page, the right side of the Register Touchstart event when the {passive:true} option is not on the left, you can see that the right side is much smoother.

What if the Preventdefault () is executed in a passive listener?

If someone accidentally calls Preventdefault () in the passive listener, it's fine, because Preventdefault () doesn't have any effect. Here I use a custom event to illustrate this situation:

Let event =NewEvent ("foo", {//creates an event object of type Foo that can be blocked by default behavior"Cancelable":true}) Document.addeventlistener ("Foo",function(event) {//The listener function for the Foo event is bound to documentConsole.log (event.defaultprevented)//falseEvent.preventdefault () console.log (event.defaultprevented)//or False,preventdefault () is invalid}, {passive:true}) Document.dispatchevent (event)//send a custom event

Also, the browser's developer tool warns you:

Under Chrome:

Under Firefox:

Support for developer tools

In addition to calling Preventdefault () in the passive listener above, Chrome's developer tools also:

1. Discover a non-passive listener that takes more than 100 milliseconds to warn you to add {passive:true}:

2. Add the passive property to the listener object, the Listener object is not available on the normal page, can be obtained in the Event Listeners panel and by calling the Geteventlisteners () Command line API:

Firefox's developer tools are not yet available.

How do I call RemoveEventListener now?

Previously, when the third parameter was a Boolean value, the listener added by AddEventListener ("foo", listener, true) must be removed with RemoveEventListener ("foo", Listener, true). Because this listener may also be registered in the bubbling phase, the same listener actually corresponds to two listener objects (via Geteventlisteners ()).

So how does the listener that AddEventListener ("foo", Listener, {passive:true}) Add now delete it? The answer is RemoveEventListener ("foo", listener), passive can be omitted, the reason is: inside the browser, the map used to store the listener's key is the event type, listener function, whether the capture of the three components, Passive and once are not in it, the reason is obvious, a listener is passive and non-passive (as well as once and non-once) is not easy to say, if you add both, then added does not count, the browser will think added:

true }) AddEventListener (false//  This sentence does not count AddEventListener (false  }) AddEventListener (True})  //  This sentence does not count

So in RemoveEventListener you never have to write passive and once, but capture may be:

true }) RemoveEventListener (true//  {capture:true} must be added, and of course {Capture:true} can be converted to true
Passive can't guarantee anything.

The only thing the passive listener can guarantee is that the call to Preventdefault () is invalid, as far as the browser's optimization of the default behavior, which is the browser thing, is outside the specification requirements. Given that this new feature was invented to solve the lag of scrolling and touch events, the current types of events supported by Chrome and Firefox are limited to such events, such as Touchstart,touchmove,wheel events, which I cannot provide for a specific list of events, Maybe we should study the source code.

But I can enumerate several types of events that the browser does not optimize, plus a demo:

In addition to these three event types, all event types with cancelable true can theoretically be optimized for this type of UI, you can look at this list of event types, and the list of touch event types, and note the cancelable column.

I consulted with a Chrome engineer and there was no plan to optimize the type of events outside the scrolling and touch event types, and the reply was not currently:

Firefox's APZ optimization

Before the passive specification, Firefox had its own optimization of the rolling touch behavior problem, and one of the key practices was that it did not respect preventdefault (): If Preventdefault () was not called within a certain time, then Firefox It is assumed that you will not prevent the default scrolling, for example, after executing the following sentence, the page will not scroll:

function (e) {    e.preventdefault ()})

But after executing this sentence can still scroll:

function (e) {    sleep (    ) E.preventdefault ()//This sentence is invalid in Firefox})

This blog is about APZ optimization: smoother scrolling in Firefox, with APZ

Feature detection

The following is a copy of the detection script from MODERNIZR:

var false ; Try {  var opts = Object.defineproperty ({}, ' passive ', {    function()} {       true ;    }  });  Window.addeventlistener (nullcatch  (e) {}

This can be used:

if (supportspassiveoption) {    Document.addeventlistener (true// ) The third parameter in the old browser is automatically turned True, not what we want }else  {    document.addeventlistener ("foo", Listener)}
None of the frameworks currently use this feature

https://github.com/facebook/react/issues/6436

https://github.com/angular/angular/issues/8866

https://github.com/emberjs/ember.js/issues/12783

https://github.com/Polymer/polymer/issues/3604

https://github.com/jquery/jquery/issues/2871

Event listener for Passive

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.