Vue中的组件通信方式有哪些
组件通信分类
- 父子组件通信
- 兄弟组件通信
- 祖先与后代组件通信
- 非关系组件通信
组件间通信方案
- 通过props传递
- 子组件设置props,定义接受父组件传递过来的参数,父组件在使用子组件时在子组件标签中通过字面量的形式传递数据
let props:{ // 字符串形式 name:String // 接收的类型参数 // 对象形式 age:{ type:Number, // 接收的类型为数值 defaule:18, // 默认值为18 require:true // age属性必须传递 } } // 父组件使用子组件 <Children name="jack" age=18 />
- 子组件设置props,定义接受父组件传递过来的参数,父组件在使用子组件时在子组件标签中通过字面量的形式传递数据
- 通过$emit触发自定义事件
- 子组件通过 e m i t 触发自定义事件, emit触发自定义事件, emit触发自定义事件,emit第二个参数为传递的数据,父组件绑定监听器获取子组件传递的数据
this.$emit('add' , data) <Children @add="cartAdd($event)" />
- 使用ref
- 父组件在使用子组件的时候设置 ref 从而获取子组件实例获取相应的数据
<Children ref="foo" /> this.$refs.foo // 获取子组件实例,通过子组件实例我们就能拿到对应的数据
- EventBus
- 创建一个中央事件总线,兄弟组件通过 e m i t 触发自定义事件, emit触发自定义事件, emit触发自定义事件,emit第二个参数为传递的数据,另一个组件通过$on监听自定义事件
// 创建一个中央时间总线类 class Bus { constructor() { this.callbacks = {}; // 存放事件的名字 } $on(name, fn) { this.callbacks[name] = this.callbacks[name] || []; this.callbacks[name].push(fn); } $emit(name, args) { if (this.callbacks[name]) { this.callbacks[name].forEach((cb) => cb(args)); } } } // main.js Vue.prototype.$bus = new Bus() // 将$bus挂载到vue实例的原型上 // 另一种方式 Vue.prototype.$bus = new Vue() // Vue已经实现了Bus的功能 // Children1.vue this.$bus.$emit('foo') //Children2.vue this.$bus.$on('foo', this.handle)
- $parent 或 $root
- 通过公共祖先$parent 或者 $root 搭建通信桥梁
//兄弟组件 this.$parent.on('add',this.add) //另一个兄弟组件 this.$parent.emit('add')
- attrs 与 listeners
- $attrs 包括组件props property中未包含的所有属性,也就是说,该属性包含了除去props声明的属性的所有属性,当我们需要给多层嵌套父子组件传值时,可以直接使用它
- l i s t e n e r s 接收除去带有 . n a t i v e 事件修饰符的所有事件监听器,作用和 listeners 接收除去带有.native事件修饰符的所有事件监听器,作用和 listeners接收除去带有.native事件修饰符的所有事件监听器,作用和attrs类似,但是有一点不同的是,如果遇到了同名事件,不会覆盖,而是都会触发,以冒泡的形式从子组件到父组件
- provide 与 inject
- Vue3中的祖先组件给子孙组件传递数据的一种方法;在祖先中定义provide属性,返回传递的值,在后代中通过inject接受组件传递过来的数据(注意这里是祖先传后代,意思是不管哪一代都能拿到祖先的数据)
//祖先组件 provide(){ return { foo:'foo' } } // 后代组件 let inject:['foo'] // 获取到祖先组件传递过来的值
- Vuex
- 相当于一个用来存储共享数据的容器,详细的使用方式这里就不细说了,可以去官网看,不难
小结
- 父子组件通信,可以用props,自定义事件$emit,也可以使用ref
- 兄弟组件通信,可以用全局事件总线 b u s , 其次可以选择 bus,其次可以选择 bus,其次可以选择parent
- 祖孙组件通信,可以用$attrs $listeners,provide inject
- 复杂关系的组件,可以用状态集成管理(数据共享)Vuex