完整总结请看下面的链接:
Vue组件通信方式居然有这么多?你了解几种
1、什么是组件通信
组件间如何通信,也就成为了vue中重点知识,组件通信,涉及到组件之间数据的传递、类似NET POST/GET参数传递。
Vue基本的三种传递方式** (props、ref、ref、emit)** 组件是 vue.js 最强大的功能之一,而组件实例的作用域是相互独立的,这就意味着不同组件之间的数据无法相互引用。那么组件间如何通信,也就成为了vue中重点知识了。这篇文章将会通过props、ref和ref和emit 这几个知识点,来讲解如何实现父子组件间通信。
2、父子通信 (props、ref、emit) 区别
prop 着重于数据的传递,它并不能调用子组件里的属性data和方法methods。适合的场景是从父亲给孩子,给了之后就是给了,最适合使用prop,。
$ref 着重于索引,主要用来调用子组件里的属性和方法,其实并不擅长数据传递,但是也是可以传递参数的。
详细的讲解请参考:【Vue组件通信】props、$ref、$emit,组件传值 - 家秋 - 博客园
具体实现方法:
一、子组件把数据传给父组件:this.$emit()
步骤如下:compChart.vue为子组件,sdCompare.vue为父级页面。
1、在子组件中声明变量sericesArr
2、在子组件用$emit()传值给父页面。
3、在父页面中使用子组件<comp-chart></comp-chart>的地方,使用@方法名="子组件方法名"
4、在父页面的method里定义方法childValue(ev),ev就是子组件传递的值。
注意:父组件传值给子组件分为传引用和传值两种方式,传引用的时候改变引用关系,则子组件的也会变化(改变父组件中数组的引用时可以看到子组件的props数组随之改变)。传值则不会。
二、父组件把数据传给子组件:
方法一:子组件通过props来接收数据
1、简易写法:
props: ['childMsg']
2、给要传递的参数指定传入的类型,如果类型不对,会警告。
props: {
childMsg: Array
}
3、给参数指定默认值
props: {
childMsg: {
type: Array,
default: [0,0,0]
}
}
具体用法:
1、在父组件的data声明参数变量:
data() {
return {
//图表数据
cSource:[],
}
},
2、给变量赋值
mounted(){
_this.cSource = [
['product', '10:00', '11:00', '12:00', '13:00', '14:00', '15:00', '16:00'],
['洁美家初体验公众号', 41.1, 99.7, 165.1, 53.3, 103.8, 298.7 , 125 ],
['洁美家一元拼团', 86.5, 119, 243,109, 73.4, 255 , 225 ],
['好厨娘初体验公众号', 24.1, 99.5, 156.4, 288.2, 108.5 ,225 ],
['洁美家包年Q3公众号', 155.2, 267.1, 369.2, 472.4, 503.9, 139.1 ,99.2 ],
['洁美家包年Q6公众号', 100, 83, 99, 109, 250, 150 ,225 ,88],
['洁美家包年Q9公众号', 210, 309, 450, 324, 250, 150 , 109],
['洁美家包年Q10公众号', 101, 196, 293, 102, 199, 277 , 159],
['洁美家包年Q11公众号', 213, 432, 124, 543, 341, 231 , 123],
];
},
3、
4、子组件用props接收参数,在子组件的data中声明一个变量来接收父组件的参数,
props: {
chartSource:Array,
},
data() {
return {
sourceData:[],
}
},
mounted(){
_this.sourceData=_this.chartSource;
},
5、如果父组件中的cSource参数值发生改变,子组件接收到的参数值相应改变的话,还需要在子组件的watch中监听参数的变化。
watch:{
chartSource(e){
_this.sourceData=_this.chartSource;
},
}
方法二:父组件把参数放在路由上,子组件通过 $route 获取。
//方法一:
this.$router.push({
name: '/modifyUser',//这里是你要跳转的路由name
params: {
userID:999
})
//方法二:
this.$router.push({
path: '/modifyUser',//这里是你要跳转的路由path
query:{
userID:999
}
})
获取参数的方法:
this.$route.query.userID
方法三:$ref
$ref 着重于索引,主要用来调用子组件里的属性和方法,其实并不擅长数据传递,但是也是可以传递参数的。
1、父页面
<base-input ref="usernameInput"></base-input>
可以在父页面任意的使用,可以调用子页面的 methods
this.$refs.usernameInput.focus()
this.$refs.usernameInput.demo('我是参数,任意的那种')
2、子页面
methods: {
// 用来从父级组件聚焦输入框
focus: function () {
this.$refs.input.focus()
},
demo(data){
console.log(data)
}
}
三、兄弟组件或者多层级组件之间传参
方法1:通过vuex来传值。
方法2:通过eventBus实现兄弟组件传值。这里有2种写法,均可使用。
(2.1)main.js
new Vue({
el: '#app',
router,
store,
data:{
eventHub:new Vue(),//新建一个名为eventHub的空对象,可以在任意一个组件内调用事件、触发方法。
},
render: h => h(App),
})
(2.2)在组件a里
this.$root.eventHub.$emit("function1","parame");
//参数1:方法名
//参数2:携带的参数
(2.3)在组件b的creatd()或者mounted()钩子函数里
created(){
this.$root.eventHub.$on(function1,(params)=>{
//...
});
},
mounted(){
this.$root.eventHub.$on(function1,(params)=>{
//...
});
},
参考: