Vue2组件通信方式有哪些?

256 阅读1分钟

父子组件

使用props和事件进行通信

props

父向子传值:props只可以从上一级组件传递到下一级组件(父子组件)。并且props只读,不可被修改。

// 父组件传递
<template>
  <child :message="hello world" />
</template>
// 子组件接受
<template>
  <div>{message}</div>
</template>
<script>
export default {
  props:{
    message: string
  }
}
</script>

$emit + v-on

子向父派发通过$emit发送一个自定义事件,父组件通过v-on(@)监听事件并处理数据。

// 子组件派发
<template>
  <div>
    <button @click="handleClick">Click me</button>
  </div>
</template>
<script>
export default {
  methods: {
    handleClick() {
      const data = 'Hello from child'
      this.$emit('child-event', data)
    }
  }
}
// 父组件响应
<template>
  <child @child-event="handleChild">
</template>
<script>
export default {
  methods: {
    handleChild(data) {
      console.log(data)
    }
  }
}
</script>

爷孙组件

使用两次父子组件通信来实现

使用两次v-on通过爷爷爸爸通信,爸爸儿子通信来实现爷孙通信。

provide + inject

跨组件通信,不论子组件嵌套有多深,只要调用了inject就可以访问provide中的数据。 注意:provide 和 inject 不是响应式的,也不会做出任何响应式的数据处理。因此,提供的数据如果发生变化,需要借助其他方式来通知子组件进行更新。

// 祖先组件
export default{
    provide(){
        return {
        message:'hello world'
        }
    }
}
// 后代组件
export default{
    inject:['message']
    created(){
        console.log(this.message)
    }
}

任意组件

使用eventBus = new Vue()来通信

eventBus 是一种简单的事件总线,用于在不同组件之间进行通信。它是基于 Vue 实例创建的,并使用 $on 和 $emit 方法来实现事件的监听和触发。

主要api是eventBus.$oneventBus.$emit
缺点是事件多了就很乱,难以维护。下面是示例:

  1. 定义一个单独的文件如eventBus,在需要的组件只引入
    // eventBus.js
    import Vue from 'vue'
    // 创建并导出一个事件总线
    export const eventBus = new Vue()
    
  2. 在发送组件中,使用$emit方法来触发一个名为message的事件,并传递字符串'hello world'。
    // SenderComponent.vue
    import eventBus from './eventBus'
    
    export default {
      methods: {
        sendMessage() {
          eventBus.$emit('message', 'Hello from sender')
        }
      }
    }
    
  3. 在接受组件中,使用$on方法来监听message事件
    // ReceiverComponent.vue
    import eventBus from './eventBus'
    export default {
      mounted() {
        eventBus.$on('message', (message) => {
          console.log(message)
        })
      },
      beforeDestroy(){ 
          // 取消监听 eventBus.$off("sendMsg") 
      }
    }
    

任意组件

使用Vuex通信(Vue3 可用Pinia代替Vuex)