您的位置:

Vue Bus总线详解

Vue bus总线,一个轻量级的事件中心,常用于跨组件通信,是Vue.js官方推荐的一种应用程序架构方式。Vue Bus总线提供了想不到的灵活性,可以被用于很多不同场景,在这篇文章中,我会从几个方面详细讲解Vue Bus总线的用法和原理。

一、Vue Bus总线简介

Vue Bus总线就是一个事件系统,用于组件之间的通信,值得一提的是,Vue Bus总线既可以当做事件系统使用,也可以当做数据或消息的传递中心。Vue Bus总线发起事件的组件成为发送组件,监听并响应事件的组件成为接收组件

二、Vue Bus总线实现

Vue Bus总线的实现有很多种,这一节中我们将介绍两种主要方式。

1. Event Bus

Vue Bus总线的最简单的实现是通过Event Bus。Event Bus是一个Vue实例,有自己的属性、方法和生命周期函数,它可以被注册,也可以被注销。

    
        const EventBus = new Vue()
        // 声明
        EventBus.$on('eventName', (arg) => {
            console.log(arg)
        })
        // 触发
        EventBus.$emit('eventName', 'Hello World!')
    

2. Provide/Inject

另一种实现方式是使用Vue提供的Provide/Inject,这种方式与Event Bus类似,但是Provide/Inject是使用了Vue自带的provide和inject选项,可自动化继承。provide选项是一个函数,返回一个对象作为注册变量。inject选项可以在嵌套层级即可使用。

    
        const EventBus = {
            install(Vue) {
                Vue.prototype.$bus = new Vue()
            }
        }
        export default EventBus

        // 在发送组件中
        methods: {
            handleClick() {
                this.$bus.$emit('eventName', 'Hello World!')
            }
        }

        // 在接收组件中
        inject: ['$bus'],
        created() {
            this.$bus.$on('eventName', (arg) => {
                console.log(arg)
            })
        }
    

三、Vue Bus总线应用

1. 父子组件之间的通信

父子组件间通信一般通过props和事件调用实现,但是当嵌套的组件层次很多的时候,这种方式会变得很繁琐,这时候使用Vue Bus总线会很方便。

    
        // 父组件
        
   
        <script>
            import EventBus from './EventBus.js'
            export default {
              name: 'ParentComponent',
              mounted() {
                EventBus.$on('eventName', payload => {
                  console.log(payload)
                })
              }
            }
        </script>
        // 子组件
        
   
        <script>
            import EventBus from './EventBus.js'
            export default {
              name: 'ChildComponent',
              methods: {
                handleClick() {
                  EventBus.$emit('eventName', 'Hello World!')
                }
              }
            }
        </script>
    

2. 非父子组件之间的通信

非父子组件之间的通信可以使用Vue Bus总线来实现。我们可以定义一个公共的Vue实例作为事件总线,并在各个组件中使用。在Vue实例中注册$on()方法,监听事件;在组件中,使用$emit()向Vue总线中触发事件,这些事件可以被其它组件监听。

    
        // EventBus.js
        import Vue from 'vue'
        export const EventBus = new Vue()

        // 发送组件
        <script>
            import { EventBus } from './EventBus.js'
            export default {
                methods: {
                    handleClick() {
                        EventBus.$emit('eventName', { a: 'messageA', b: 'messageB' })
                    }
                }
            }
        </script>

        // 接收组件
        <script>
            import { EventBus } from './EventBus.js'
            export default {
                created() {
                  EventBus.$on('eventName', payload => { console.log(payload)})
                }
            }
        </script>
    

四、Vue Bus总线的局限性

Vue Bus总线不能进行vuex的store中状态管理。为解决这个问题,可以通过使用Vuex或其他状态管理库解决。