The essence of an event is a means of communication between the various components of a program.

DOM event operations (listening and firing) are defined in the EventTarget interface. This interface is deployed on all node objects. The interface mainly provides three instance methods.

  1. addEventListenerAdd a listener function for events
  2. removeEventListener Remove event listener function
  3. dispatchEventTriggering event

Propagation of events

There are three stages of event propagation

  • Stage one. Is transmitted from the Window object to the target node (upper to lower), calledCapture phase(Capture Phase).
  • Phase 2: triggers on the target node, calledThe target stage(Target phase).
  • Stage 3: The target node is transmitted back to the Window object (from the bottom to the top), calledBubbling phase(Bubbling phase).

<div>
  <p>Click on the</p>
</div>
<script>
var phases = {
  1: 'capture'.2: 'target'.3: 'bubble'
};

var div = document.querySelector('div');
var p = document.querySelector('p');

div.addEventListener('click', callback, true);
p.addEventListener('click', callback, true);
div.addEventListener('click', callback, false);
p.addEventListener('click', callback, false);

function callback(event) {
  var tag = event.currentTarget.tagName;
  var phase = phases[event.eventPhase];
  console.log("Tag: '" + tag + "'. EventPhase: '" + phase + "'");
}
<script/>

// Click the next result
// Tag: 'DIV'. EventPhase: 'capture'
// Tag: 'P'. EventPhase: 'target'
// Tag: 'P'. EventPhase: 'target'
// Tag: 'DIV'. EventPhase: 'bubble'

Copy the code

Note: Browsers always assume that the target node for the click event is the node with the deepest nested click location (in this case, the

node within the

node). Therefore, both the capture phase and the bubble phase of the

node are displayed as the target phase. And the third argument of addEventListener is different, indicating that two different listener functions are bound

Add event listener functionEventTarget.addEventListener()

A listener function that defines a specific event on the current node or object. Once this event occurs, the listening function is executed. This method does not return a value. When multiple events are bound to the same node, only one takes effect.

target.addEventListener(type, fn[, useCapture]);
Copy the code
  • Type: indicates the event name, which is case sensitive

  • Fn: specifies the function to be bound

  • UseCapture: whether to call the bound function during the capture phase. Default is false. It can also be a property configuration object. This object has the following properties.

    • capture: A Boolean value indicating whether the event triggers the listening function during the capture phase.
    • once: A Boolean value indicating whether the listener is fired only once and then removed automatically. // It is more elegant to write remove, otherwise you have to write in fnremoveEventListener
    • passive: Boolean, indicating that the listener will not call the event preventDefault method. If the listening function is called, the browser will ignore the request and print a warning on the monitor console.
function hello() {
  console.log('Hello world');
}

var button = document.getElementById('btn');
button.addEventListener('click', hello, false); 

button.addEventListener('click', hello, {once:true});// Listen for events once

Copy the code

Remove event listener functionEventTarget.removeEventListener()

EventTarget. RemoveEventListener method is used to remove the addEventListener method to add events to monitor function. This method does not return a value. It is used the same way as addEventListener

Note that the listener removed by the removeEventListener method must be the same listener added by the addEventListener method, and must be on the same element node. In other words, you can only change add to remove, otherwise it will not work.

div.addEventListener('click'.function (e) {}, false);
div.removeEventListener('click'.function (e) {}, false);
Copy the code

Triggering eventEventTarget.dispatchEvent()

EventTarget. DispatchEvent method triggers the specified event on the current node, which triggers the implementation of monitoring function. This method returns a Boolean value as long as one of the listeners calls event.preventDefault (), and true otherwise. Can Dan

button1.addEventListener('click'.() = >{
  const event = new CustomEvent("outInfo", {"detail": {name:'Jack'.age: 18}})
  button1.dispatchEvent(event)
})

button1.addEventListener('outInfo'.(e) = >{
  console.log('outInfo')
  console.log(e)
})
Copy the code

The event agentEvent Delegation

Since events will propagate upward to the parent node in the bubble phase, the listening function of the child node can be defined on the parent node, and the listening function of the parent node can handle the events of multiple child elements in a unified manner. This method is called delegating events.

var ul = document.querySelector('ul');

ul.addEventListener('click'.function (event) {
  if (event.target.tagName.toLowerCase() === 'li') {
    // some code}});Copy the code

Cancel event propagation

// After the event propagates to the p element, it no longer propagates downward
p.addEventListener('click'.function (event) {
  event.stopPropagation();
}, true);

// After the event bubbles to the p element, it no longer bubbles upwards
p.addEventListener('click'.function (event) {
  event.stopPropagation();
}, false);

Copy the code

In the above code, stopPropagation prevents the propagation of events in the capture and bubble phases, respectively.

However, the stopPropagation method only prevents the propagation of the event and does not prevent the event from triggering the listener for other click events on the

node. That is, not to cancel the click event completely.

p.addEventListener('click'.function (event) {
  event.stopPropagation();
  console.log(1);
});

p.addEventListener('click'.function(event) {
  / / triggers
  console.log(2);
});
/ / 1
/ / 2
Copy the code

If you wanted to completely prevent this event from being propagated and not trigger all of the following click listeners, you could use the stopImmediatePropagation method.

p.addEventListener('click'.function (event) {
  event.stopImmediatePropagation();
  console.log(1);
});

p.addEventListener('click'.function(event) {
  // Will not be triggered
  console.log(2);
});
Copy the code