Vue组件间的常用通信方式

116 阅读1分钟

组件之间的常用通信方式一般有六种(props、自定义事件、全局事件总线、pubsub、vuex、插槽)。其中不乏有父传子的、子传父的,还有全局都能够使用的。着重理解props、自定义事件与全局总线$bus。

1.props

适用场景

父传子(使用率高)

示例

现在有两个组件,是父组件与子组件的关系,同样两个组件对应两个不同的人物,他们也是父子关系。如图:

image.png

很显然,需要将父组件中的money(非函数值)传给子组件,具体代码如下:

// 父组件
<template>
<div style="margin:100px 0px 0px 100px">
   <img src="@/assets/老王.jpg" style="width:80px;height:100px;">
   <span>我是老王</span>
  <div>拥有的资产:{{money}}元</div>
   <LaoWangSon :money="money"></LaoWangSon>
</div> 
</template>

<script>
import LaoWangSon from '@/components/LaoWangSon/LaoWangSon.vue';
export default {
  data() {
    return {
    money:10000
  }
  },
  components: {
  LaoWangSon
}
}
</script>
// 子组件
<template>
  <div style="margin-top:100px">
    <img src="@/assets/儿子.jpg" style="width:100px;height:100px">
    <span>我是老王的儿子,我身上的钱与爸爸的一样多</span>
    <div>拥有的资产:{{money}}元</div>
  </div>
</template>

<script>
export default {
// props书写方式有三种
  props: ['money']

// props: {
  //   money: {
  //     type: Number
  //   }
  // }
  
  // props: {
  //   money: {
  //     type: Number,
  //     default:0
  //   }
  // }
}
</script>

2.自定义事件

适用场景

子组件传父组件

示例

刚开始儿子有100元,爸爸有10000元,没有点击按钮前,如图:

image.png

点击按钮后具体实现代码:

// 父组件
<template>
<div style="margin:100px 0px 0px 100px">
   <p>我是老王</p>
   <img src="@/assets/老王.jpg" style="width:80px;height:100px;">
  <div>拥有的资产:{{money}}元</div>
   <LaoWangSon :money="money" @update1="update1"></LaoWangSon>
</div> 
</template>

<script>
import LaoWangSon from '@/components/LaoWangSon/LaoWangSon.vue';
export default {
  data() {
    return {
    money:10000
  }
  },
  methods: {
    update1(i) {
      // console.log(i)
      this.money-=i
    }
  },
  components: {
  LaoWangSon
}
}
</script>
// 子组件
<template>
  <div style="margin-top:100px">
  <p>我是老王的儿子</p>
    <img src="@/assets/儿子.jpg" style="width:100px;height:100px">
    <button @click="update(500)">从爸爸那借500元</button>
    <div>拥有的资产:{{money}}元</div>
  </div>
</template>

<script>
export default {
  data() {
    return {
      money:100
    }
  },
  methods: {
    update(i) {
      this.money += i
      this.$emit('update1',i)
    }
   } 
}
</script>

点击按钮后的效果图:

image.png

啊啊啊!写的好水呀,水我都要给水完😕😕😭😭

3.全局事件总线$bus

使用场景

万能

示例

现在新增一位人物——小红,她向老王的儿子借钱,因为这两个组件之间的关系比较远,故采用全局事件总线。

没有点击按钮前,如图:

image.png

点击按钮后的具体代码实现如下:

需要先在src/main.js中注入

new Vue({
  render: h => h(App),
  // 全局事件总线$bus配置
  beforeCreate() {
    Vue.prototype.$bus = this
  },
}).$mount('#app')

小红组件代码:

<template>
  <div style="margin-left:500px">
   <p>我是小红</p>
     
    <img src="@/assets/girl.jpg" style="width:100px;height:100px">
    <button @click="borrow(100)">向老王的儿子借100元</button>
    <div>拥有的资产:{{money}}元</div>
  </div>
</template>

<script>
export default {
  data() {
    return {
    money:500
  }
  },
  methods: {
    borrow(i) {
      this.money += i
      this.$bus.$emit('take',i)
   }
}
}
</script>

老王儿子代码:

<template>
  <div style="margin-top:100px">
  <p>我是老王的儿子</p>
    <img src="@/assets/儿子.jpg" style="width:100px;height:100px">
    <div>拥有的资产:{{money}}元</div>
  </div>
</template>

<script>
export default {
  data() {
    return {
      money:1000
    }
  },
  mounted() {
    this.$bus.$on('take', (i) => {
      this.money-=i
    })
  } 
}
</script>

最终点击按钮后的结果:

image.png

4.Vuex

在前面的文章介绍过:juejin.cn/post/712822…

结语:水的差不多了,只能说继续加油吧!!!