1.为什么要进行组件通信?
组件可以说是一个具有独立功能的整体,但是当我们要将这些组件拼接在一起时,这些组件相互之间要建立联系,这个联系我们就称之为通信
2.组件通信的方式有以下几种
- 父子组件通信 (使用props来实现)
- 子父组件通信 (自定义事件)
- 非父子组件通信 ( ref链 或 bus事件总线)
- 多组件状态共享 ( 多个组件共用同一数据 vuex)
父子组件通信
<div id="app">
<Father></Father>
</div>
<template id="father">
<div>
<h3> 这里是父组件 </h3>
<hr>
<Son :aa = "money" :mask-flag = "maskFlag"/>
</div>
</template>
<template id="son">
<div>
<h3> 这里是son组件 </h3>
<p> 父亲给了我 {{ aa }} 钱 </p>
<p> {{ maskFlag }} </p>
</div>
</template>
<script>
Vue.component('Father',{
template: '#father',
data () {
return {
money: 2000,
maskFlag: 10000000000
}
}
})
Vue.component('Son',{
template: '#son',
props: ['aa','maskFlag']
})
new Vue({
}).$mount('#app')
</script>
非父子组件通信
ref
ref链: 可以实现非父子组件的通信,但是如果层级太多,就比较繁琐了
<div id="app">
<Father></Father>
</div>
<template id="father">
<!-- 组件中根元素必须唯一 -->
<div>
<h3> 这里是father </h3>
<button @click = "look"> 点击查看father的this </button>
<p> father的 n: {{ n }} </p>
<hr>
<Son ref = "son"></Son>
<Girl ref = "girl" :n = "n"></Girl>
</div>
</template>
<template id="son">
<div>
<h3> 这里是 son 1 </h3>
</div>
</template>
<template id="girl">
<div>
<h3> 这里是girl </h3>
<button @click = "out"> 输出girl的this </button>
</div>
</template>
<script>
/*
通过ref绑定组件后,我们发现在他们的共同父组件的 $refs里面可以找到子组件
*/
Vue.component('Father',{
template: '#father',
data () {
return {
n: 0
}
},
methods: {
look () {
this.n = this.$refs.son.money
}
}
})
Vue.component('Son',{
template: '#son',
data () {
return {
money: 1000
}
}
})
Vue.component('Girl',{
template: '#girl',
data () {
return {
num: 0
}
},
methods: {
out () {
console.log( this )
console.log( this.$attrs )
}
}
})
new Vue({
el: '#app'
})
</script>
bus事件总线
<div id="app">
<Bro></Bro>
<Sma></Sma>
</div>
<template id="big">
<div>
<h3> 这里是哥哥组件 </h3>
<button @click = "hick"> 揍 </button>
</div>
</template>
<template id="small">
<div>
<h3> 这里是弟弟组件 </h3>
<p v-show = "flag"> 呜呜呜呜呜呜呜呜呜uwuwuwuwu </p>
</div>
</template>
<script>
var bus = new Vue()
Vue.component('Bro',{
template: '#big',
methods: {
hick () {
bus.$emit('aa')
}
}
})
Vue.component('Sma',{
template: '#small',
data () {
return {
flag: false
}
},
mounted () { //当前组件挂载结束,也就是我们可以在页面当中看到真实dom
// mounted这个钩子函数的触发条件是组件创建时会自动触发
// 事件的声明
var _this = this
bus.$on( 'aa',function () {
_this.flag = true
console.log( this )//这里是this指的是bus, 但是我们需要的this应该是Sma这个组件
})
}
})
new Vue({
el: '#app'
})
</script>