??注册一个 $bus ,使用 全局事件总线 实现任意组件间通信!除了 Vuex ,本文的 全局事件总线 是实现组件间通信的第二种方式。
??欢迎持续关注新系列文章 [Vue 补洞] 系列,用久了 Vue2 总有一些遗漏的知识点,一起通过该系列文章一起查漏补缺!
实现组件间通信的另外两种方式,建议阅读! 【Vue | 补洞 | 01】Vuex 环境搭建及基本使用 【Vue | 补洞 | 02】mapState 一行代码获取 vuex 所有数据 【Vue | 补洞 | 03】Vuex 模块化编码 【Vue补洞 | 05】消息订阅与发布
1. 作用
??用于任意组件间通信
??举个简单的例子:原本不认识的两个小年轻,通过媒婆建立起联系,在还没有互加联系方式的情况下,双方要互通消息 只能借助媒婆。而媒婆之所以能当媒婆,其前提条件是:男女双方都认识媒婆。这在全局事件总线中,也是类似的情况。
2. 适用场景
??非父子组件,跨多级进行数据或事件的传递
3. “媒婆” 所需具备的条件
- 所有组件都能访问到该实例上的方法(因此需要将该"媒婆"挂载到
根实例vm 上,其所有子组件就都能访问了) - 能调用到
$on $off $emit (这些方法都在Vue原型链上,因此"媒婆"得是 Vue的实例对象 ,要么是 vm ,要么是 VueComponent )
4. 使用
1)声明全局事件总线
为何要将 $bus 绑定在 beforeCreated 中?
???beforeCreated 时还未对数据监测、数据代理等进行挂载,
??等到创建组件时,在 mounted 中调用了 this.$bus.$on 绑定事件,这时 $bus 已经存在且可以使用了
import Vue from 'vue'
...
new Vue({
...
beforeCreated() {
Vue.prototype.$bus = this
}
})
2)接收方绑定事件
??假设:A组件想接收数据,而B组件会触发事件 getName 并传递数据给A,则需要在A组件身上使用 $on 绑定自定义事件,如下:
mounted() {
this.$bus.$on('getName', (value)=>{
console.log(value)
})
}
3)发送方触发事件
??在B组件中,通过 $emit 就可以触发在A身上的 getName 事件,并将 name 的值传给A组件
methods: {
xxxx() {
let name = 'Jokerls'
this.$bus.$emit('getName', name)
}
}
4)解绑
??最好在组件销毁时,把组件身上 $on 的事件给解绑。(因为 $bus 会一直存在,若不解绑,则会一直占用着总线上的某个方法,导致别的组件 调用同名方法时,会出现冲突)
??注意 不能使用 this.$off() 全部解绑,会导致别人在 $bus 身上注册的方法失效。
mounted() {
this.$bus.$on('getName', (value)=>{
console.log(value)
})
},
beforeDestroy() {
this.$off('getName')
}
5. 总结
- 通过
$bus 注册全局时间总线 - 通过
$on 注册事件 - 通过
$emit 触发事件并发送数据 - 通过
$off 解绑事件
|