Home > Software design >  EventListeners, which are defined in another EventListeners in JavaScript
EventListeners, which are defined in another EventListeners in JavaScript

Time:01-12

I want to define an EventListener after clicking on a button.

I set EventListener in another EventListener and want the child EventListener to be listening to click event only after the parent event was triggered.

Code snippet:

const btn = document.querySelector(".btn")
btn.onclick = function() {
  console.log("PARENT")
  document.onclick = function() {
    console.log("CHILD")
  }
}
<button >Click</button>

Current behavior:

Parent and child events trigger together, even on the first click on the button.

So, even on the first click on the button I see "PARENT" "CHILD" in console, but I want to see only "PARENT".

Desired behavior:

Child EventListener should be listening to click event only after clicking on the button element. Thus, I want to see on the first click on the button only "PARENT" in console and after on subsequent clicks: "PARENT" "CHILD".

Why it works in such way? Why does the event, defined in child EventListener, trigger with the event, defined in parent EventListener, though child EventListener should only start listening to click event when the parent event is triggered?

CodePudding user response:

The event is handled for the button - where the new listener is assigned, then it bubbles up and handles the newly registered handler.

Anyway, it may be easier and more clear to use event delegation and a data-attribute to save the click state of the button. for example:

document.addEventListener(`click`, handle);

function handle(evt) {
  console.clear();
  if (evt.target.classList.contains(`btn`)) {
    evt.target.dataset.clicked = 1;
    return console.log(`.btn clicked`);
  }
  
  if (evt.target === document.documentElement) {
    if (!document.querySelector(`.btn`).dataset.clicked) {
      return true;
    }
     
    return console.log(`document clicked`);
  }
}
<button >Click</button>

CodePudding user response:

const btn = document.querySelector(".btn")
btn.onclick = function() {
  console.log("PARENT");
  setTimeout(() => (
    document.onclick = function() {
      console.log("CHILD")
    }
  ), 0);      
}
<button >Click</button>

more content: Why is setTimeout(fn, 0) sometimes useful?

  • Related