Skip to content

Instantly share code, notes, and snippets.

@composite
Created October 16, 2022 12:19
Show Gist options
  • Save composite/ed7381f79aa8768fb3829d2f4246d39a to your computer and use it in GitHub Desktop.
Save composite/ed7381f79aa8768fb3829d2f4246d39a to your computer and use it in GitHub Desktop.
Legacy event bus pattern for Vue 3 Composition API
import {ref, watch} from "vue";
/**
* Event Bus
* @typedef {Object} EventBus
*/
/**
* add event listener
* @method
* @name EventBus#on
* @param {string} name
* @param {Function} callback
* @returns {EventBus}
*/
/**
* remove event listener
* @method
* @name EventBus#off
* @param {string} name
* @param {Function?} callback
* @returns {EventBus}
*/
/**
* fire event listener
* @method
* @name EventBus#emit
* @param {string} name
* @param {...any} args
* @returns {EventBus}
*/
/**
* @type {{[name: string]: { callbacks: Function[], trigger: UnwrapRef<any[]>, stopper: import('vue').WatchStopHandle } }}
*/
const bus = {}
/**
* Composition API Event Bus
* @return {EventBus}
*/
export default function useEventBus() {
return {
on(name, callback) {
if (!bus[name]) {
bus[name] = {
callbacks: [],
trigger: ref([])
}
bus[name].stopper = watch(bus[name].trigger, (params) => {
bus[name].callbacks.forEach(cb => cb.apply(undefined, params))
})
}
bus[name].callbacks.push(callback)
return this
},
off(name, callback = undefined) {
if(bus[name]) {
if (callback) {
const idx = bus[name].callbacks.findIndex(f => f === callback)
if (idx > -1) bus[name].callbacks.splice(idx, 1)
}
if (!bus[name].callbacks.length || !callback) {
bus[name].stopper()
delete bus[name]
}
}
return this
},
emit(name, ...args) {
if(bus[name]) {
bus[name].trigger.value = args
}
return this
}
}
}
<script setup>
import useEventBus from './lib/event-bus'
const bus = useEventBus()
bus
.on('session-change', (...args) => {
// TODO Session Change
console.log('session change event fired', args)
})
const handleClick = e => {
bus.emit('session-change', ['old session', 'new session'])
}
</script>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment