theJuls
theJuls

Reputation: 7470

Is there a way I can add single event listener to cover multiple?

I have something that happens whenever the user moves, so for this I set the three event listeners:

document.addEventListener('mousemove', this.doThing)
document.addEventListener('click', this.doThing)
document.addEventListener('keydown', this.doThing)

Which do also eventually need to be removed:

document.removeEventListener('mousemove', this.doThing)
document.removeEventListener('click', this.doThing)
document.removeEventListener('keydown', this.doThing)

The thing is, they are all doing the exact same thing, so I was wondering if there is a better way to group these into a single add and remove event listener. Or perhaps if there is one that covers any movement/interaction of the user?

Upvotes: 0

Views: 180

Answers (3)

holmicz
holmicz

Reputation: 577

You can possibly do something like:

["mousemove", "click", "keydown"].forEach(evt => document.addEventListener(evt, this.doThing));
["mousemove", "click", "keydown"].forEach(evt => document.removeEventListener(evt, this.doThing));

Simple generic version with lambdas could be:

let addHandlers = (events, handler) => events.forEach(evt => document.addEventListener(evt, handler))
let removeHandlers = (events, handler) => events.forEach(evt => document.addEventListener(evt, handler))
addHandlers(["mousemove", "click"], this.doThing);
removeHandlers(["mousemove", "click"], this.doThing);

Upvotes: 1

zero298
zero298

Reputation: 26909

Yes, create a handleEvent member function and provide this as the event handler:

class Thing {
  constructor(el) {
    this.el = el;
    this.el.addEventListener("mouseover", this);
    this.el.addEventListener("click", this);
  }
  handleEvent(e) {
    switch (e.type) {
      case "mouseover":
        console.log("mouseover");
        break;
      case "click":
        console.log("click");
        break;
    }
  }
};

const thing = new Thing(document.getElementById("foo"));
<button id="foo">Hello</button>

Upvotes: 1

Joseph
Joseph

Reputation: 119867

You can supply a space-separated string of events and loop through each. Most libraries, like jQuery.on(), do something similar.

function setEventsToDocument(events, callback) {
  events.split(' ').forEach(event => {
    document.addEventListener(event, callback)
  })
}

function removeEventsFromDocument(events, callback) {
  events.split(' ').forEach(event => {
    document.removeEventListener(event, callback)
  })
}

setEventsToDocument('mousemove click keydown', callback)

removeEventsFromDocument('mousemove click keydown', callback)

Upvotes: 1

Related Questions