DEV Community

loading...
DropConfig

Using Browser Custom Events

powerc9000 profile image Clay Murray ・2 min read

A lot of times when writing things you may want want to react to certain events on your page.

We do this all the time with builtin ones like click or keydown

But we can also make our own custom events and have the browser handle all the work for us! Since it's part of the DOM API we get free event code without installing another lib or rolling our own buggy version.

CustomEvent is what we will be using. We'll wrap it a little to make it a bit neater to use as well.

Making a custom event

It's pretty simple

const event = new CustomEvent("myevent", {details: {some: "data"}});

document.dispatchEvent(event);

Notice we had to put our own custom data in the details key of the event. This is just a quirk of how they work.

Listening for a custom event

function eventHandler(event){
    const data = event.details.data;
    console.lo(data);
}
document.addEventListener("myevent", eventHandler)

Stopping listening

document.removeEventListener("myevent", eventHandler);

Pretty easy stuff.

What's great is, we can also dispatch the event on an element so it doesn't bubble up to the dom. Keeping our code event more modularized. Just replace document with another element you have.

A little wrapper.

Because it's a little bit cumbersome to have to write all that everytime you want to use an event. Let's wrap it just a little.

function publish(eventName, data){
    const event = new CustomEvent(eventName, {details: data});
    document.dispatchEvent(event);
}
const events = [];
function subscribe(eventName, cb){
    const wrapper =  function(event){
        cb(event.details);
    }
    document.addEventListener(eventName, wrapper);

    events.push({
        cb, wrapper, eventName
    })
}

function unsubscribe(eventName, cb){
    events.forEach((event)=>{
        if(event.eventName === eventName && cb === event.cb){
            document.removeEventListener(eventName, event.wrapper);
        }
    })

}

export {subscribe, unsubscribe, publish};

Usage

function eventHandler(data){
    console.log(data);
}
subscribe("myEvent", eventHandler))
publish("myEvent", {some: "data"});
unsubscribe("myEvent", eventHandler);

Et voilà

If you like my stuff please check out my site https://dropconfig.com

Discussion (7)

pic
Editor guide
Collapse
graphicbeacon profile image
Jermaine Oppong

Thanks Clay for the refresher. In the example for event listening you have console.lo rather then console.log. I like the pub/sub example and could be packaged into a tiny library.

Collapse
alexparra profile image
Alex Parra

Do you use this as cross components communication? Example trigger a function in a sibling component?

Collapse
powerc9000 profile image
Clay Murray Author

Sure. That's a solid use case.

Collapse
alexparra profile image
Alex Parra

Thanks for your reply Clay.
I try to keep it top-down but I’ve faced a couple of situations where this pub/sub using the native event bubbling would come in real handy. Didn’t reach for it yet though.

Collapse
deciduously profile image
Ben Lovy

This is awesome, I had no idea. Thanks!

Collapse
mynameistakenomg profile image
MyNameIsTakenOMG

Wow, amazing! Never heard of this thing,plz don't tease me, I'm just a little newb 😂 thanks so much for sharing this 🤗

Collapse
mfaghfoory profile image
Meysam Faghfouri

Really cool! I don't know why I haven't seen this before!