什么是EventEmitter的正确使用?

我已经阅读了CustomHttp中的Access EventEmitter Service这样的问题,用户在他的服务中使用了EventEmitter,但是在这个评论中他被build议不要使用它,而是直接在他的服务中使用Observable。

我也在解决schemebuild议将EventEmitter传递给孩子并订阅的情况下阅读这个问题 。

我的问题是:我应该或者不应该手动订阅EventEmitter? 我应该如何使用它?

不,你不应该手动订阅它。

EventEmitter是一个angular2抽象,它的唯一目的是在组件中发射事件。 引用Rob Wormald的评论

EventEmitter实际上是一个有angular度的抽象,应该仅用于在组件中发出自定义事件。 否则,就像使用其他库一样使用Rx。

这在EventEmitter的文档中说得很清楚。

使用指令和组件来发出自定义事件。

使用它有什么问题?

Angular2永远不会保证EventEmitter将继续成为Observable。 所以这意味着如果它改变了我们的代码就会重构。 我们必须访问的唯一API是其emit()方法。 我们不应该手动订阅EventEmitter。

上述所有内容在本病房贝尔的评论中都更加清楚(build议阅读文章以及对该评论的回答 )。 引用以供参考

不要指望EventEmitter继续成为Observable!

不要指望那些将来在那里的可观察运营商!

这些将很快被弃用,并可能在发布之前被删除。

使用EventEmitter仅用于子组件和父组件之间的事件绑定。 不要订阅它。 不要调用任何这些方法。 只调用eve.emit()

他的评论很早就符合罗布的评论。

那么,如何正确使用它?

只需使用它从组件发出事件。 看看下面的例子。

 @Component({ selector : 'child', template : ` <button (click)="sendNotification()">Notify my parent!</button> ` }) class Child { @Output() notifyParent: EventEmitter<any> = new EventEmitter(); sendNotification() { this.notifyParent.emit('Some value to send to the parent'); } } @Component({ selector : 'parent', template : ` <child (notifyParent)="getNotification($event)"></child> ` }) class Parent { getNotification(evt) { // Do something with the notification (evt) sent by the child! } } 

怎么不使用它?

 class MyService { @Output() myServiceEvent : EventEmitter<any> = new EventEmitter(); } 

停在那里你已经错了

希望这两个简单的例子将阐明EventEmitter的正确用法。

TL; DR回答:

不,不要手动订阅,不要在服务中使用它们。 如文档中所示,仅使用它们来发出组件中的事件。 不要打败angular度的抽象。

是的,继续使用它。

EventEmitter是最终的Angular Core API中的一个公开的loggingtypes 。 它是否基于Observable是无关的; 如果它的文档emitsubscribe方法适合你所需要的,那就继续使用它。

正如文件中所述:

使用Rx.Observable,但提供了一个适配器,使其工作在这里指定: https : //github.com/jhusain/observable-spec

一旦规范的参考实现可用,切换到它。

所以他们想要一个像对象一样的Observable对象,以某种方式performance出来,然后将它们实现并公之于众。 如果仅仅是一个不应该使用的内部的angular度抽象,他们不会公开的。

有很多时候有一个发射器发送特定types的事件是有用的。 如果这是你的用例,那就去做吧。 如果/当他们链接的规范的参考实现可用,它应该是一个插入式replace,就像任何其他polyfill一样。

只要确保您传递给subscribe()函数的生成器遵循链接的规范。 返回的对象保证有一个unsubscribe方法,应该调用这个方法来释放对生成器的任何引用(这是一个RxJs Subscription对象,但这确实是一个不应该依赖的实现细节)。

 export class MyServiceEvent { message: string; eventId: number; } export class MyService { public onChange: EventEmitter<MyServiceEvent> = new EventEmitter<MyServiceEvent>(); public doSomething(message: string) { // do something, then... this.onChange.emit({message: message, eventId: 42}); } } export class MyConsumer { private _serviceSubscription; constructor(private service: MyService) { this._serviceSubscription = this.service.onChange.subscribe({ next: (event: MyServiceEvent) => { console.log(`Received message #${event.eventId}: ${event.message}`); } }) } public consume() { // do some stuff, then later... this.cleanup(); } private cleanup() { this._serviceSubscription.unsubscribe(); } } 

所有强烈措辞的厄运和黯淡的预测似乎都是来自单个开发者在Angular 2的预发行版本上的单个Stack Overflow评论。