Vue——组件间常用通信方式详解
文章目录
- 前言
- 一、props
- 二、自定义事件
- 三、全局事件总线
- 四、订阅与发布
- 总结
一、props
1.应用场景
用于父组件给子组件传递数据。
2.使用用法
在父组件内已注册并使用的子组件 School
<School :sex="女" :age="age"></School>
注意:
- 可引用表达式,否则就是字符串。
- 在子组件中写所要传递的值
3.注意
Vue规定prop都使得其父子 prop 之间形成了一个单向下行绑定:父级 prop 的更新会向下流动到子组件中,但是反过来则不行。这样会防止从子组件意外变更父级组件的状态,从而导致你的应用的数据流向难以理解。如果需要添加值需用$set方法
4.声明形式
在子组件 School 中使用 props 接收数据
4.1 简单声明
props: ['realname','sex','age'],//第一种:简单声明
4.2 指定名称与类型
props: {
realname: String,
sex:String,
age:Number
}
4.3 类型+必填+默认值
props: {
realname: {
type: String,
default: '无姓名',
required:true
},:用于父组件给子组件传递数据
sex: {
type: String,
default: '男'
},
age: {
type: Number,
required:true,
default:30,
}
}
二、自定义事件
1.应用场景
可利用自定义事件实现子组件给父组件传递数据。
2.使用用法
在父组件中给子组件绑定一个自定义事件,事件的回调停留在父组件中,在子组件使用this.$emit调用,触发该事件回调。
2.1 绑定事件
在父组件中给子组件绑定一个自定义事件
<!--Student是子组件,sendName:事件名称,getName:回调函数-->
<Student @sendName="getName"/>
事件的回调停留在父组件中
methods:{ getName(value){ this.name = value; } }
在子组件使用this.$emit调用,触发该事件回调。
第一个参数为:事件名称,
第二个参数:传递的数据不传参数就是单纯的触发父组件对应的函数。
School组件代码
methods: { pressBtn() { // 调用自定义事件 this.$emit('sendName',this.name); } },
3.为子组件添加ref
3.1 添加ref 的原因
访问子组件实例或子元素,尽管存在 prop 和事件,有的时候你仍可能需要在 JavaScript 里直接访问一个子组件。为了达到这个目的,你可以通过 ref 特性为这个子组件赋予一个 ID 引用。
3.2 传递数据的格式
给子组件添加ref=”student”,用$on的方式添加,第一个参数:名称,第二个参数:回调函数。
mounted() {
this.$refs.student.$on("sendName",this.getName);
}
3.3 注意
1: 如果子组件调用原生事件 需要添加native,否则会当成自定义组件,
如:@click.native="show"
2:$once,只执行一次。
4. 事件解绑
4.1 解绑一个事件
this.$off(‘xxxx’ ) xxxx:事件名称
4.2 解绑多个事件
this.$off([‘x1’,’x2’]) 使用数组的形式。
4.3 解绑所有事件
this.$off()
4.4 销毁组件实例
this.$destroy() //销毁了当前Student组件的实例,销毁后所有Student实例的自定义事件全都不奏效。
三、全局事件总线
1.应用场景
适用于任意组件通信
2.使用方法
2.1 安装全局事件总线
在入口文件main.js中,给VM添加$bus,任意组件都可以在原型中调用。
beforeCreate(){ Vue.prototype.$bus = this }
2.2 组件间的使用方法
发送数据的组件: 使用 this.$bus.$emit('事件名',所要传递的值)
例如:在点击某一按钮时将数据发送给另一组件
methods:{ addShopCar( ){ if(this.goodsInfo.goodsName !='' && this.goodsInfo.goodsPrice !=''){ this.$bus.$emit('sendtomain',this.goodsInfo); }else{ alert('添加购物车失败!'); } this.goodsInfo.goodsName = ''; this.goodsInfo.goodsPrice = ''; } }
接收数据的组件: 使用 this.$bus.$on('发送数据组件中的事件名',(data)=>{
// 此处的data为所传递的值
})
mounted( ){ this.$bus.$on('sendtomain',(data)=>{ this.goodsList.unshift({ id: new Date( ).getTime( )+Math.round(Math.random()*10), title: data.goodsName, price: data.goodsPrice, num: 1, checked: false }) }); }
组件销毁之前卸载自定义事件
beforeDestroy() { this.$bus.$off('getName') }
四、订阅与发布
1.应用场景
一种组件间通信的方式,适用于任意组件间通信,如今有很多消息订阅与发布的包,在这里只介绍一种,pubsub-js。
2.使用方法
2.1 安装插件 pubsub-js
安装pubsub:npm i pubsub-js
在入口文件main.js中,给VM添加$bus,任意组件都可以在原型中调用。
beforeCreate(){ Vue.prototype.$bus = this }
2.2 发布消息
在所要使用的组件中引入pubsub:
import pubsub from 'pubsub-js'
发布消息
pubsub.publish('hello','hello-world') hello:发布消息的名称,第二个参数:为发布内容
methods:{ addShopCar( ){ pubsub.publish('sendName',this.name); } }
2.3 接收消息
在所要使用的组件中引入pubsub:
import pubsub from 'pubsub-js'
每次接收消息的时,会生成一个订阅的ID
Mounted( ) { this.pubId = pubsub.subscribe('hello',(msgName,data)=>{ console.log(this) // console.log('有人发布了hello消息,hello消息的回调执行了',msgName,data) }) }
2.4 取消订阅
beforeDestroy() { // this.$bus.$off('hello') pubsub.unsubscribe(this.pubId) },
总结
以上就是今日所要分享的内容,关于组件间的通信方式除了本文分享还有其他方式,在这里就不一一赘述,任意组件通信的方式还有一种常见的方式 Vuex,因为这一部分的内容比较重要,我会单独整理写一篇讲解,感兴趣的朋友可以关注一下。
好了,就此停笔,最后依旧诚挚祝福看到这篇文章的你健康幸福、平安喜乐。