vue原始方式:通过emit事件、父组件props进行中转
一、父组件下属两个子组件
parent.vue
<template>
<div class="flex">
<childEVue @post="receive"></childEVue>
<childFVue :num = "receiveNum"></childFVue>
</div>
</template>
<script setup lang='ts'>
import childEVue from '../example/childE.vue';
import childFVue from '../example/childF.vue';
import {ref} from 'vue';
let receiveNum = ref(0)
const receive = (param:any)=>{
console.log(param.value)
receiveNum.value = param.value
}
</script>
<style scoped>
.flex {
display: flex;
}
</style>
子组件childEVue
<template>
<div class="ce-box">
<button @click="postMessage">
子组件 发射部分 {{count}}
</button>
</div>
</template>
<script setup lang='ts'>
import {ref} from 'vue'
const emit = defineEmits([ 'post'])
const count = ref(0)
const postMessage = () =>{
count.value = count.value + 1
emit('post',count)
console.log("子组件发射部分触发")
}
</script>
<style scoped>
.ce-box {
width: 200px;
height: 200px;
background-color: aqua;
}
</style>
子组件childFVue
<template>
<div class="ce-box">
<button>
子组件 被改变部分{{num}}
</button>
</div>
</template>
<script setup lang='ts'>
defineProps({
num: Number
})
</script>
<style scoped>
.ce-box {
width: 200px;
height: 200px;
background-color: aqua;
margin-left: 200px;
}
</style>
效果:
mitt方式
官方推荐的vue3事件总线方式:mitt
实现方式:
- 安装
npm install mitt -S
main.ts中全局挂载
import { createApp } from 'vue'
import App from './App.vue'
import mitt from 'mitt'
const Mit = mitt()
//TypeScript注册
// 由于必须要拓展ComponentCustomProperties类型才能获得类型提示
declare module "vue" {
export interface ComponentCustomProperties {
$Bus: typeof Mit
}
}
const app = createApp(App)
app.config.globalProperties.$Bus = Mit
app.mount('#app')
- 两个子组件
childE.vue
<template>
<div class="ce-box">
<button @click="postMessage">
子组件 发射部分 {{count}}
</button>
<div class="mittp">
<button @click="mittEmit">mitt发射子组件{{newCount}}</button>
</div>
</div>
</template>
<script setup lang='ts'>
import {ref} from 'vue'
import { getCurrentInstance } from 'vue'
const emit = defineEmits([ 'post'])
const count = ref(0)
const newCount = ref(0)
const postMessage = () =>{
count.value = count.value + 1
emit('post',count)
console.log("子组件发射部分触发")
}
const instance = getCurrentInstance();
const mittEmit = ()=>{
newCount.value += 10
instance?.proxy?.$Bus.emit('on-num', newCount)
}
</script>
<style scoped>
.ce-box {
width: 200px;
height: 200px;
background-color: aqua;
}
.mittp{
font-size: 30px;
}
</style>
childF.vue
<template>
<div class="ce-box">
<button>
子组件 被改变部分{{num}}
</button>
<div class="mittr">
<button>
子组件 mitt 被改变部分{{showNum}}
</button>
</div>
</div>
</template>
<script setup lang='ts'>
import { getCurrentInstance, ref } from 'vue'
const instance = getCurrentInstance()
const showNum:any = ref("")
instance?.proxy?.$Bus.on('on-num', (num) => {
console.log(num,'===========>B')
showNum.value = num
})
defineProps({
num: Number
})
</script>
<style scoped>
.ce-box {
width: 200px;
height: 200px;
background-color: aqua;
margin-left: 200px;
}
.mittr{
margin-top: 20px;
}
</style>
效果: