Assumptions:
This article assumes you know about the neat little trick to use Vue as an event bus to communicate between your components. If not, read the article Creating a Global Event Bus with Vue.js by Joshua Bemenderfer.
Why?
I started off using the EventBus in my components and the implementation looked like this,
mounted() {
EventBus.$on('some-event', this.handleEvent)
},
destroyed() {
EventBus.$off('some-event', this.handleEvent)
}
This got a little cluttered as the number of events increased and the worse part? you can forget turning off the events.
Solution
The two solutions the came up to my mind were,
- Mixin to auto destroy events
- A dummy component that handles the
mounted
anddestroyed
logic.
Personally, I don't like mixins which is why I didn't even think twice about the point 1.
The dummy component seemed more fun to write. Additionally, event listeners in html templates looked a lot better than their JS counterpart (and it conforms to the idea behind https://vuejs.org/v2/guide/events.html#Why-Listeners-in-HTML).
This is how the component for EventBus looks like,
import _ from 'lodash'
import { EventBus } from '../common/eventBus.js'
export default {
data() {
return {
events: Object.keys(this.$listeners),
methods: _.mapValues(this.$listeners, (value, key) => this.handleEvent.bind(this, key))
}
},
mounted() {
this.events.forEach(event => {
this.methods[event].SOMETHING = event
EventBus.$on(event, this.methods[event])
})
},
destroyed() {
this.events.forEach(event => {
EventBus.$off(event, this.methods[event])
})
},
methods: {
handleEvent(name, ...args) {
this.$emit(name, ...args)
}
}
}
The demo is up at https://codesandbox.io/s/k5v2owk8v7.
Footnotes
This is my first ever post on any platform so looking forward to your comments.
Top comments (0)