Angular组件之间的通信方式。

本来准备写到Angular总结中去的,又怕太长以后自己都找不到,就先写下来再说吧!
不管是Vue,还是Angular,组件之间的通信方式无非是以下3种情况。

1.父组件往子组件传递,(vue中是props down)
2.子组件往父组件传递,(vue中是events up)
3.非父子关系组件传递(vue中使用bus总线)

1.父组件往子组件传递

既然是父组件往子组件传值,那么首先肯定要有2个组件。先创建2个组件

ng g component father
ng g component son

这时两个组件创建好了,但是还没有形成父子关系。
在这里插入图片描述

在father组件中,引入子组件。
在这里插入图片描述

子组件中准备好接受父组件传值的位置:
在这里插入图片描述
将父组件导入根组件中,看看效果。
在这里插入图片描述

还是和vue类似,在父组件引用子组件的位置,写一个自定义属性,不用:也不用[],直接写属性和值即可,这里叫做myName=‘我是父组件传给子组件的值9588’。

在这里插入图片描述


这里需要注意的是,因为这里我传递的是一个写好的字符串,如果传递的是一个变量,或者其他组件传过来的值,那么这里需要用[]将myName括起来,作为绑定属性使用。后面双引号的内容就应该是绑定属性的变量。这个地方有点坑,否则你传递给子组件的只是一个字符串。

在这里插入图片描述

看看效果。

扫描二维码关注公众号,回复: 5039734 查看本文章

在这里插入图片描述


然后子组件需要接受父组件传来的值。因为接受一个值属于输入行为,所以在子组件son的ts文件中,需要添加Input类才能接受输入。这一点和自定义指令中接受参数的设置是一样的。
在这里插入图片描述
上图红框可以看到,使用装饰器@Input绑定myName属性之后,直接使用this.myName已经可以读取到数据了。
在子组件son的html中,直接使用{{myName}}即可读取到父组件传递进来的值。
在这里插入图片描述

最后看下效果,没毛病。
在这里插入图片描述

个人总结:感觉父传子和vue一样,需要通过在引用子组件的位置绑定属性才能传递。只是接受值的方式写法有些不同。

2.子组件向父组件传递,通信

首先复习一下vue中的子组件向父组件通信。
在这里插入图片描述
这里同样的,我们要 在调用子组件时,给子组件绑定一个自定义事件,事件名为myEvent。
Angular中绑定事件是用小圆括号(),这里vue中可以不加函数的括号和参数,但是Angular中一定要加括号,而且参数也要写上$event才行,否则无法接受到子组件传过来的值。
如果子组件只是想调用父组件中的方法而不传值,就可以不写。
在这里插入图片描述

然后回到father.ts,设置一个msg变量用来保存传递过来的值,创建handleEvent方法,用来操作传递过来的值。
在这里插入图片描述
这样步骤1父组件中的操作就结束了。
回到子组件son中的ts文件,由于子组件向父组件传值属于输出事件,所以这里需要引入Output类,而传递事件属于事件发送,所以还需要引入EventEmitter类。

引入之后在下面使用装饰器创建变量,保存事件发送对象。

@Output() myEvent = new EventEmitter()

最后调用事件对象的emit方法,发送信息给父组件。

   this.myEvent.emit('我是子组件发送给父组件的值123')

完整代码如下:
在这里插入图片描述

查看下效果,没问题。
在这里插入图片描述

总结:

步骤1:调用子组件时,给子组件绑定一个自定义事件
handleEvent(msg){}
<son (myEvent)=“handleEvent($event)”></son>
步骤2:触发事件并传值
import {Output,EventEmitter} from ‘@angular/core’
绑定装饰器
@Output() myEvent = new EventEmitter()
调用emit方法
this.myEvent.emit(123)

3.兄弟/父子组件之间的传值

如果是兄弟组件,拥有一个共同的父组件这种,可以通过子传父,父再传给另外一个子来实现。不过这种方法很麻烦,特别是父子组件之间的层级深了以后,每一级都要绑定事件和属性来传递,非常麻烦。例如前面todolist的demo,只是从todo-box——>todo-list——>todo-item,3个层级,纯粹使用事件和绑定属性来传递,就已经很讨人嫌了。
在Vue中的解决方案是创建了一个叫bus的全局组件,将触发的自定义事件和接收的自定义事件都绑定在bus上,来实现组件之间的通信。

但是在Angular中,可以使用服务来实现兄弟/父子组件的通信。
3.2,使用服务在组件之间通信!
前面学习服务的时候,我们知道了一个服务注册完之后可以被任意组件调用。假如两个组件都调用了某一个服务,那么这两个组件就可以通过这个服务来通信。原理是因为Angular中的服务都是单例对象,也就是不管你有一个组件调用服务,其实都是调用的同一个对象。这种方式有点像vue中使用bus

首先我们创造一个服务,名为 my-store,给它创建一个数组list为空。
在这里插入图片描述

然后在一个组件other-son中引入该服务,并且修改该服务类中的list,给它传递一个值进去。
在这里插入图片描述

接下来,在另外一个子组件son中也引入my-store服务
在这里插入图片描述

然后给son组件绑定一个点击事件,用来获取服务类中的list数据,看看是否能获取到other-son填入的数据。
在这里插入图片描述

可以获取到!
在这里插入图片描述
这样就实现了兄弟间组件的通信!不管层级有多深,都能够快速的实现通信,个人感觉类似于Vue中的bus总线,都是搭载一个公用的组件来实现。

3.4 父子组件间通信补充,使用本地变量通信。

首先在父组件引用子组件的地方,给子组件起一个别名,格式为 #+别名,这里我们给子组件的类中创建一个name属性,待会让父组件调用。
在这里插入图片描述
然后直接在父组件的模板中就可以使用双花括号来调用子组件中的属性或者方法了!
在这里插入图片描述

但是这里只能在父组件的模板中使用,也就是只有在html这里使用。如果要想在类中使用,需要再引入其他的类。
在这里插入图片描述

使用ViewChild类使得父组件在组件类中可以使用子组件的属性或者方法。
首先需要再父组件的组件类中,从核心库中引入ViewChild类。
在这里插入图片描述

然后将子组件导入到父组件中。
在这里插入图片描述

接下来使用@ViewChild装饰器,定义要接收的组件类和保存的变量。
在这里插入图片描述

这样就可以在父组件类中直接调用子组件中的方法和变量了!
在这里插入图片描述

猜你喜欢

转载自blog.csdn.net/SilenceJude/article/details/85280506