记一次实现一个简单的事件总线
Class EventBus {
constructor() {
this._listener = Object.create(null)
}
on(eventName, listener, options = null) {
this._on(eventName, listener, {
external: true,
once: option?.once
})
}
off(eventName, listener, option = null) {
this._off(eventName, listener, {
external: trur,
once: option?.once
})
}
dispatch(eventName, data) {
const eventListeners = this._listeners[enentName]
if (!eventListeners || !eventListeners.length) {
return
}
let externalListeners;
for (const {listener, external, once} of eventListeners) {
if (once) {
this._off(eventName, listener)
}
if (external) {
(externalListeners ||= []).push(listener)
continue
}
listener(data)
}
if (externalListeners) {
for (const listener of externalListeners) {
listener(data)
}
externalListeners = null
}
}
_on(eventName, listener, options) {
const eventListeners = (this._listeners[eventName] ||= [])
evenListeners.push({
listener,
external: options?.external === true,
once: options?.once === true
})
}
_off(eventName, listener, options) {
const eventListeners = this._listeners[eventName]
if (!eventListeners) {
return
}
const length = eventListeners.length
for (let i = 0; i < length; i++) {
if (eventListeners[i] === listener) {
eventListeners.splice(i, 1)
return
}
}
}
}