首页IT科技vue的组件通信有哪些(vue组件间通信全面讲解)

vue的组件通信有哪些(vue组件间通信全面讲解)

时间2025-05-01 12:12:44分类IT科技浏览6183
导读:前言 本章我们将介绍组件间是如何实现数据通信的。包括父组件向子组件、子组件向父组件、兄弟组件、非关系组件之间的数据通信。...

前言

本章我们将介绍组件间是如何实现数据通信的                。包括父组件向子组件                、子组件向父组件                   、兄弟组件      、非关系组件之间的数据通信                   。

组件通信是组件式开发中非常重要的一部分            ,也是组件式开发中的难点      。

组件介绍

组件是 vue 最强大的功能之一                      ,而组件实例的作用域是相互独立的       ,这就意味着不同组件之间的数据无法相互引用            。

我们需要使用特定的方式来实现组件间的数据通信         ,接下来让我们一个个介绍这几种类别的组件通信是如何实现的                    。

一            、父传子

1. 父组件通过 props 传递数据给子组件

父组件通过 props 属性向子组件传递数据         。

子组件利用组件实例的 props 属性定义组件需要接收的参数                     ,在使用组件时通过 attribute的方式传入参数        。

// 在子组件内定义组件接收一个参数 name {   props: [name] } // 父组件使用组件时传递参数 name <child :name="name"></child>

接下来我们看一个具体示例:

<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> </head> <body> <div id="app"> <parent></parent> </div> </body> <script src="https://unpkg.com/vue/dist/vue.js"></script> <script type="text/javascript"> Vue.component(parent, { template: <child :name="name"></child>, data() { return { name: 句号 } } }) Vue.component(child, { template: <div>{{name}}</div>, props: [name] }) var vm = new Vue({ el: #app, data() { return {} } }) </script> </html>

代码解释

JS 代码第 14-18 行:定义了组件 child           ,并用 props 接收一个参数 name                     。

JS 代码第 4-12 行:定义了组件 parent      ,在组件中使用 <child></child> 引用组件                    ,并用 attribute 的方式将 name 传递给组件 child            。

在上面的例子中               ,组件 Child 接收参数 name   ,name 可以是字符串                    、数组         、布尔值        、对象等类型    。但有时候我们需要给接收的参数指定一个特殊的类型和默认值                   ,接下来我们就来介绍一下如何指定 props 的类型和默认值                      。

2. 定义props的类型和默认值

在上面的例子中                   ,props 接收一个组件参数数组               。

实际上,props 也可以接收一个对象               ,对象key为组件接收参数的参数名                      ,其值是一个对象   ,属性 type 用来指定参数的类型            ,属性 default 用来指定参数的默认值:

{ props: { name: { type: String, default: 句号 } } }

接下来我们看一个具体示例:

<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> </head> <body> <div id="app"> <parent></parent> </div> </body> <script src="https://unpkg.com/vue/dist/vue.js"></script> <script type="text/javascript"> Vue.component(parent, { template: <div><child :name="name" /> <child/></div>, data() { return { name: 慕课网 } } }) Vue.component(child, { template: <div>{{name}}</div>, props: { name: { type: String, default: 句号 } } }) var vm = new Vue({ el: #app, data() { return {} } }) </script> </html>

JS 代码第 11-19 行:定义了组件 child                      ,并用 props 接收一个字符串类型的参数 name       ,其默认值是:句号。

JS 代码第 3-10 行:定义了组件 parent         ,在组件中使用<child></child>两次引用组件                     ,<child :name="name" /> 的方式传递 name 值           ,<child/> 使用默认的 name 值                   。

TIPS: 注意      ,给数组和对象类型的 props设置默认值的时候                    ,需要按照以下的写法:

props: { detail: { type: Object, default: () => { return { name: 句号 } } }, loves: { type: Array, default: () => { return [] } } }

二                     、子传父

子组件通过 $emit 传递数据给父组件

介绍完父组件传递数据给子组件的方式               ,我们再来看看子组件是如何传递数据给父组件的                  。

子组件通过 $emit 传递事件给父组件   ,父组件通过$on监听事件:

// 子组件定义事件 this.$emit(事件名称, 传递的参数) //例: this.$emit(add, 111) // 父组件监听事件的触发 <child  @事件名称="事件触发的方法"/>

具体示例:

<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> </head> <body> <div id="app"> <parent></parent> </div> </body> <script src="https://unpkg.com/vue/dist/vue.js"></script> <script type="text/javascript"> Vue.component(parent, { template: <div><child :name="name" :count="count" @add="add"/></div>, data() { return { name: 句号, count: 18 } }, methods: { // 父组件通过 @事件名 监听 // count 表示事件触发传递的参数 add(count) { this.count = count } } }) Vue.component(child, { template: <div>我是:{{name}}                   , 我今年 {{count}}岁   。<button @click="add">加一岁</button></div>, props: { name: { type: String, default: 句号 }, count: { type: Number, default: 18 } }, methods: { add(){ // add -> 触发的事件名 // this.count + 1 -> 触发事件时传递的参数 this.$emit(add, this.count + 1) } } }) var vm = new Vue({ el: #app, data() { return {} } }) </script> </html>

代码解释

JS 代码第 19-38 行:定义了组件 child                   ,该组件接收两个参数:1. 字符串类型的 name,默认值为:句号                。2. 数字类型的 age               ,默认值为 18                   。组件模版中                      ,通过按钮点击事件触发 add 方法   ,该方法内部通过$emit触发事件 add            ,并将 age + 1 的值作为参数传递      。

JS 代码第 3-18 行:定义了组件 parent                      ,在组件中使用<child :name="name" :age="age" @add="add"/>引用组件       ,并绑定 add 事件         ,当事件 add 触发时调用 methods 中的 add 函数            。

三            、非父子组件间数据传递

前面我们介绍了具有父子关系的组件是如何进行数据传递的                    。但实际上                     ,并不是所有的组件都是父子关系           ,组件间还有兄弟组件    、子孙组件                      、无关系组件      ,那么这些组件间是如何进行通信的呢?

相信在学完本章前面的内容之后这个问题并不能难倒大家         。

对于兄弟组件的数据通信:它们有共同的父组件                    ,我们可以通过父组件传递的方式实现数据通信        。 对于子孙组件的数据通信:可以通过 props 的方式向下逐层传递下去               ,也可以通过 $emit 将事件向上逐层传递                     。 对于非关系组件的数据通信:通过使用一个空的Vue实例作为中央事件总线            。

1.通过公有的父组件进行非父子组件间的通信

假设现在有三个组件分别是<Parent>               、<ChildA>、<ChildB>   ,其中组件<Parent>是<ChildA>和<ChildB>的父组件                   ,<ChildA>和<ChildB>为兄弟组件                   ,<ChildA>和<ChildB>组件间的通信可以借助<Parent>来间接传递    。它的流程大致是这样:

<ChildA>通过$emit将数据传递给<Parent>,<Parent>再通过props将数据传递给<ChildB>                       。

具体示例:

<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> </head> <body> <div id="app"> <person @modify="modify"></person> <detail :name="name" :count="count"/> </div> </body> <script src="https://unpkg.com/vue/dist/vue.js"></script> <script type="text/javascript"> Vue.component(person, { template: <div><div>姓名:<input type="text" v-model="name"/></div><div>年龄:<input type="text" v-model="count"/></div><button @click="modify">修改</button></div>, data() { return { name: 句号, count: 18 } }, methods: { modify() { this.$emit(modify, {name: this.name, count: this.count}) } } }) Vue.component(detail, { template: <div>我是:{{name}}               , 我今年 {{count}}岁               。</div>, props: { name: { type: String, default: 句号 }, count: { type: Number, default: 18 } }, methods: { } }) var vm = new Vue({ el: #app, data() { return { name: 句号, count: 18 } }, methods: { modify(detail) { this.name = detail.name this.count = parseInt(detail.count) } } }) </script> </html>

代码解释

JS 代码第 18-30 行:定义了组件 detail                      ,它从父组件接收 name 和 age 两个参数。

JS 代码第 3-17 行:定义了组件 person   ,它通过 $emit 将组件内输入的 name 和 age 传递给父组件                   。

JS 代码第 38-41 行:接收了组件 person 传递过来的事件            ,并修改 name 和 age                  。

HTML 代码第 3 行:将 name 和 age 传递给组件 detail   。

2. 通过使用一个空的 Vue 实例作为中央事件总线

在Vue中可以使用 EventBus 来作为沟通桥梁的概念                      ,就像是所有组件共用相同的事件中心       ,可以向该中心注册发送事件或接收事件         ,所以组件都可以上下平行地通知其他组件                。

首先我们需要做的是创建事件总线                     ,并将它挂载到Vue原型上           ,在实例中通过this.bus.$emit发送事件      ,通过this.bus.$on接收事件

// 定义事件总线 let bus = new Vue() Vue.prototype.bus = bus // 定义发送事件 this.bus.$emit(事件名称, data) // 定义接收事件 并在回调中接收参数 this.bus.$on(事件名称, (data) => { })

接下来我们看一段具体示例代码:

<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta http-equiv="X-UA-Compatible" content="ie=edge"> <title>Document</title> </head> <body> <div id="app"> <person></person> <detail /> </div> </body> <script src="https://unpkg.com/vue/dist/vue.js"></script> <script type="text/javascript"> let bus = new Vue() Vue.prototype.bus = bus Vue.component(person, { template: <div><div>姓名:<input type="text" v-model="name"/></div><div>年龄:<input type="text" v-model="count"/></div><button @click="modify">修改</button></div>, data() { return { name: 句号, count: 18 } }, methods: { modify() { this.bus.$emit(modify, {name: this.name, count: this.count}) } } }) Vue.component(detail, { template: <div>我是:{{name}}                    , 我今年 {{count}}岁                   。</div>, data() { return { name: 句号, count: 18 } }, mounted() { this.bus.$on(modify, (detail) => { this.name = detail.name this.count = detail.count }) } }) var vm = new Vue({ el: #app, methods: { } }) </script> </html>

代码解释

JS 代码第 3-4 行:通过 new Vue() 创建一个 vue 实例               ,并将它挂载在 Vue 的原型上      。这样   ,在 vue 组件中可以通过 this.bus 访问到这个实例对象            。

JS 代码第 5-18 行:定义了组件 person                   ,当点击修改按钮的时候通过 this.bus.$emit 发送一个名为 modify 的事件                   ,并将组件内输入的 name 和 age 作为参数传递                    。

JS 代码第 19-33 行:定义组件 detail,在组件内部通过this.bus.$on监听名为 modify 的事件               ,当事件触发时执行修改操作         。

小结

在本章                      ,我们介绍了组件间的通信方式   ,主要有以下知识点:

父组件通过 props 向子组件传递参数进行数据通信; 子组件通过 $emit 向父组件传递事件进行数据通信; 兄弟组件通过共同父组件进行数据通信; 通过使用一个空的 Vue 实例作为中央事件总线进行非关系层组件的数据通信        。

以上为个人经验            ,希望能给大家一个参考                      ,也希望大家多多支持本站                     。

声明:本站所有文章       ,如无特殊说明或标注         ,均为本站原创发布            。任何个人或组织                     ,在未征得本站同意时           ,禁止复制                   、盗用                  、采集   、发布本站内容到任何网站                、书籍等各类媒体平台    。如若本站内容侵犯了原著者的合法权益      ,可联系我们进行处理                      。

创心域SEO版权声明:以上内容作者已申请原创保护,未经允许不得转载,侵权必究!授权事宜、对本内容有异议或投诉,敬请联系网站管理员,我们将尽快回复您,谢谢合作!

展开全文READ MORE
php递归算法经典题目(php递增和递减运算符的介绍) uniapp下拉框(【uniapp】页面下拉刷新)