Vue —— 进阶脚手架(五)(全局事件总线、消息订阅与发布)

本文详细介绍了Vue2.x中组件间通信的两种方法:全局事件总线和消息订阅发布。通过实例展示了如何在不同组件之间传递数据,包括安装、使用、解绑事件及实际应用场景。对于全局事件总线,讲解了其原理和在组件生命周期中的应用;而对于消息订阅与发布,引入了pubsub-js库,演示了订阅和发布数据的过程,以及在组件销毁前如何正确取消订阅。
摘要由CSDN通过智能技术生成

Vue全家桶 系列文章目录

内容参考链接
Vue2.x - 基础Vue2.x - 基础
Vue2.x - 进阶(零)初始化脚手架
Vue2.x - 进阶(一)refs属性、props配置项
Vue2.x - 进阶(二)混入 mixin、插件 plugins、样式 scoped
Vue2.x - 进阶(三)本地存储
Vue2.x - 进阶(四)组件的自定义事件
Vue2.x - 进阶(五)全局事件总线、消息订阅与发布
Vue2.x - 进阶(六)过渡与动画
Vue2.x - 进阶(七)解决开发环境 Ajax 跨域问题
Vue2.x - 进阶(八)默认插槽、具名插槽和作用域插槽
Vue2.x - 周边(Vuex、Vue-router)Vuex、Vue-router
Vue3.0 - 新增Vue3.0 新增内容
Vue2.x 项目(附源码)Vue + ElementUI 后台管理项目(附源码)
Vue3.0 项目Vue3.0 企业级 App


一、全局事件总线
1. 什么是全局事件总线?

这是一种组件间通信的方式,适用于任意组件间通信。

2. 安装全局事件总线
	new Vue({
		.....
		beforeCreate() {
			Vue.prototype.$bus = this //安装全局事件总线,$bus就是当前应用的 vm
		}
	})
3. 使用事件总线
  1. 接收数据:A组件想接收数据,则在 A组件中给 $bus 绑定自定义事件,事件的回调留在 A组件自身。
	methods: {
		demo(data) {....}
	},
	....
	mounted() {
		this.$bus.$on('xxx', this.demo)
	}
  1. 提供数据
	this.$bus.$emit('xxx', 数据)
4. 解绑事件

最好在 beforeDestroy 钩子中,用 $off 去解绑当前组件所用到的事件。

5. 实例:实现兄弟间的组件通信(全局事件总线)

main.js

  1. 在生命周期钩子 beforeCreate() 中安装全局事件总线
	// 引入 Vue
	import Vue from 'vue'
	// 引入 App
	import App from './App.vue'
	// 关闭 vue 的生产提示
	Vue.config.production = false
	
	//创建 vm
	new Vue({
	    el: '#app',
	    render: h => h(App),
	    beforeCreate() {
	        Vue.prototype.$bus = this //安装全局事件总线
	    }
	})

Student.vue

  1. $emit() 触发自定义事件( hello 事件)
  2. 为 School 组件提供 this.name(即张三) 数据
	<template>
	  <div class="demo">
	    <h2>学生姓名:{{ name }}</h2>
	    <h2>学生性别:{{ sex }}</h2>
	    <button @click="sendStudentName">把学生名给School组件</button>
	  </div>
	</template>
	
	<script>
	export default {
	  name: "StudentName",
	  data() {
	    return {
	      name: "张三",
	      sex: "男",
	    };
	  },
	  methods: {
	    sendStudentName() {
	      this.$bus.$emit("hello", this.name);
	    },
	  },
	};
	</script>

School.vue

  1. 提供数据:School 组件中给 $bus 绑定自定义事件,事件的回调留在 School 组件自身。
  2. 组件被销毁之前,在 beforeDestroy() 中进行自定义事件的解绑。
	<template>
	  <div class="demo">
	    <h2>学校名称:{{ name }}</h2>
	    <h2>学校地址:{{ address }}</h2>
	  </div>
	</template>
	
	<script>
	export default {
	  name: "SchoolName",
	  data() {
	    return {
	      name: "哔哩哔哩",
	      address: "中国",
	    };
	  },
	  methods:{
	      demo(data){
	        console.log("我是School组件,我收到了数据", data);
	      }
	  },
	  mounted() {
	    this.$bus.$on("hello", this.demo);
	  },
	  beforeDestroy() {
	    this.$bus.$off("hello");
	  },
	};
	</script>

App.vue

  1. 配置相关子组件的标签
	<template>
	  <div class="app">
	    <h3>{{ msg }}</h3>
	    <School />
	    <student />
	  </div>
	</template>
	
	<script>
	// 引入组件
	import School from "./components/School.vue";
	import Student from "./components/Student.vue";
	export default {
	  name: "App",
	  components: { School, Student },
	  data() {
	    return {
	      msg: "你好啊",
	    };
	  },
	};
	</script>

在这里插入图片描述

二、消息订阅与发布
1. 什么是消息订阅与发布?

一种组件间通信的方式,适用于任意组件间通信。

2. 使用步骤
  1. 安装 pubsub:npm i pubsub-js
  1. 引入:import pubsub from 'pubsub-js'
  1. 接收数据:A组件想接收数据,则在 A组件中订阅消息,订阅的回调留在 A组件自身。
	methods: {
		demo(data) {....}		
	},
	....
	mounted() {
		this.pubId = pubsub.subscribe('xxx', this.demo) //订阅消息
	}
  1. 提供数据:pubsub.publish('xxx', 数据)
  1. 最好在 beforeDestroy 钩子中,使用 PubSub.unsubscribe(pubid) 去取消订阅。
3. 实例:实现兄弟间的组件通信(消息订阅与发布)

main.js 不需要添加任何内容

App.vue 不需要做改变

Student.vue

  1. 引入 pubsub
  2. 提供订阅数据:pubsub.publish(‘xxx’)
	<template>
	  <div class="demo">
	    <h2>学生姓名:{{ name }}</h2>
	    <h2>学生性别:{{ sex }}</h2>
	    <button @click="sendStudentName">把学生名给School组件</button>
	  </div>
	</template>
	
	<script>
	import pubsub from 'pubsub-js'
	export default {
	  name: "StudentName",
	  data() {
	    return {
	      name: "张三",
	      sex: "男",
	    };
	  },
	  methods: {
	    sendStudentName() {
	      pubsub.publish('hello', this.name)
	    },
	  },
	};
	</script>

School.vue

  1. 引入 pubsub
  2. 接收数据:this.pubId = pubsub.subscribe('xxx', this.demo)
  3. 组件被销毁之前,在 beforeDestroy() 中取消订阅。
	<template>
	  <div class="demo">
	    <h2>学校名称:{{ name }}</h2>
	    <h2>学校地址:{{ address }}</h2>
	  </div>
	</template>
	
	<script>
	import pubsub from 'pubsub-js'
	export default {
	  name: "SchoolName",
	  data() {
	    return {
	      name: "哔哩哔哩",
	      address: "中国",
	    };
	  },
	  methods:{
	    demo(msgName, data) {
	      console.log('有人发布了hello消息,hello消息的回调执行了', msgName, data);
	      console.log(this);
	    }
	  },
	  mounted() {
	    this.pubId = pubsub.subscribe('hello', this.demo)
	  },
	  beforeDestroy() {
	    pubsub.unsubscribe(this.pubId)
	  },
	};
	</script>

不积跬步无以至千里 不积小流无以成江海

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

前端杂货铺

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值