Small knowledge, big challenge! This paper is participating in theEssentials for programmers”Creative activities.

TIP 👉 Even Homer sometimes nods. A fool’s plans may strike. Shiji Huaiyin Hou Biography

Introduction to the Global Event Bus

Global EventBus (EventBus) is a way of messaging, based on a message center, subscribe and publish message pattern, in Vue can use EventBus as a communication bridge concept, as all components share the same event center, can register to send or receive events to the event center

The event type

There are two types of events: normal events and Ready events

Ordinary events

Common events use the default event processing logic of vUE. Listeners need to be added before starting events. Listeners added after events are triggered cannot be executed

  • 1) Listening events
Vm. $eventBus. $on (' myEvent '() = > {})/vm/add event listeners. $eventBus. $once (' myEvent' () = > {}) / / add event listeners, and the monitor executed only onceCopy the code
  • 2) Trigger monitoring
$eventBus.$emit('myEvent', myArgument) // Can emit events and pass arguments to listenersCopy the code
  • 3) Remove listening
Vm.$eventBus.$off('myEvent') // Remove all listeners for the eventCopy the code

The ready event

The Ready event applies to scenarios where the event firing timing is uncertain, but event listening must be performed. Both listeners added before the event firing and listeners added after the event firing are executed

  • 1) Listening events
Vm. $eventBus. $onReady (' myEvent '() = > {}) / / add event listeners, Vm.$eventBus.$onReady('myEvent', () => {}, true) $onReady('myEvent', () => {}, false) // Add event listeners that can be triggered multiple timesCopy the code
  • 2) Trigger monitoring
Vm. $eventBus.$emitReady('myEvent', myArgument) // Triggers event listeners and can pass arguments to listenersCopy the code
  • 3) Remove listening
Vm. $eventBus.$removeReadyEventListener('myEvent', myEventHandler) // Triggers event listeners and can pass parameters to listenersCopy the code
  • 4) Clear events
Vm.$eventBus.$clearReadyEvent('myEvent') // Clears the specified eventCopy the code

Encapsulate an EventBusPlugin.js


import Vue from 'vue'

export default {
    install () {
        // Event bus
        const eventBus = new Vue()
        /** * ready event listener *@type {Object.<string, Array[Object.<string, any>]>}
        * @desc The primary key is the event name and the value is the event listener array * Listener array: * 1) isOnce: indicates whether the listener handler is executed only once. If it is executed only once, it will be removed from the listener array. * 2) eventHandler: This listener handler * Example: {isOnce: true, eventHandler: function (payload) { ... }} * /

        const readyListeners = {}
        /** * Ready Event status *@type {Object.<string, Object.<string, any>>}
        * @desc State object: * 1) isReady: indicates whether the event is triggered. * 2) Payload: indicates the parameter when the event is triggered. Example: {isReady: true, payload: {id: 12}} * /
        
        const readyStatus = {}
        /** * Add the ready event listening method (execute if the event has already been triggered) *@param EventName eventName *@param Function (payload) {... } *@param IsOnce Specifies whether to execute only once (default: true) */
        function onReady (eventName, eventHandler, isOnce = true) {
            // Event status
            let status = readyStatus[eventName]
            // If the event has already been raised, execute the listener method directly
            if (status && status.isReady) {
                . / / the console log (' # # # # # # # # # # # directly performed to monitor treatment ', eventHandler)
                eventHandler(status.payload)
                if (isOnce) { // If this listener is executed only once, it is no longer added to the listener array
                    return}}/* Adds the listener to the listener array */
            let listeners = readyListeners[eventName]
            if(! listeners) { listeners = [] readyListeners[eventName] = listeners } listeners.push({ isOnce,// Whether to execute only once
                eventHandler // Event handler})}/** * Triggers the ready event *@param EventName eventName *@param Payload Event payload data */
        function emitReady (eventName, payload) {
            // Set the event status
            readyStatus[eventName] = { isReady: true, payload }
            // The listener array for the event
            let listeners = readyListeners[eventName]
            // New listener array (if there is a listener that executes only once, it is removed after execution)
            let newListener = []
            // Execute the listener event in the listener array
            if (listeners && listeners.length > 0) {
                listeners.forEach((listener) = > {
                    try {
                        if(! listener.isOnce) { newListener.push(listener) } listener.eventHandler(payload) }catch (e) {
                        console.error('eventBus ready event:${eventName}Failed to execute listening method! `, e)
                    }
                })
            }
            readyListeners[eventName] = newListener
        }
        /** * Remove one of the listener methods * from the ready event@param EventName eventName *@param Listener Event listener method */
        function removeReadyEventListener (eventName, listener) {
            if (eventName && listener) {
                let eventListeners = readyListeners[eventName]
                if (eventListeners) {
                    let index = -1
                    for (let i = 0; i < eventListeners.length; i++) {
                        let item = eventListeners[i]
                        if (item.eventHandler === listener) {
                            index = i
                            break}}if(index ! = = -1) {
                        eventListeners.splice(index, 1)}}}}/** * Clears the specified ready event *@param EventName eventName */
        function clearReadyEvent (eventName) {
            delete readyListeners[eventName]
            deletereadyStatus[eventName] } eventBus.$readyListeners = readyListeners eventBus.$readyStatus = readyStatus eventBus.$onReady  = onReady eventBus.$emitReady = emitReady eventBus.$removeReadyEventListener = removeReadyEventListener eventBus.$clearReadyEvent = clearReadyEvent Vue.prototype.$eventBus = eventBus } }Copy the code

main.js

import Vue from 'vue'
import eventBusPlugin from 'eventBusPlugin.js'

// Register global event bus
Vue.use(eventBusPlugin)
Copy the code