微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

javascript – Node.js EventEmitter:如何将类上下文绑定到事件侦听器,然后删除此侦听器

有没有办法在事件监听器方法中访问类上下文,并有可能删除监听器?

例1:

import {EventEmitter} from "events";

export default class EventsExample1 {
    private emitter: EventEmitter;

    constructor(private text: string) {
        this.emitter = new EventEmitter();

        this.emitter.addListener("test",this.handleTestEvent);
        this.emitter.emit("test");
    }


    public dispose() {
        this.emitter.removeListener("test",this.handleTestEvent);
    }

    private handleTestEvent() {
        console.log(this.text);
    }
}

在此示例中,删除侦听器是可行的,但handleTestEvent()方法无法使用此方法访问类上下文.这指向EventEmitter上下文,因此无法访问this.text.

例2:

import {EventEmitter} from "events";

export default class EventsExample2 {
    private emitter: EventEmitter;

    constructor(private text: string) {
        this.emitter = new EventEmitter();

        this.emitter.addListener("test",this.handleTestEvent.bind(this));
        this.emitter.emit("test");
    }

    public dispose() {
        this.emitter.removeListener("test",this.handleTestEvent);
    }

    private handleTestEvent() {
        console.log(this.text);
    }
}

在这个例子中,我使用bind函数将类的上下文绑定到事件侦听器.现在,handleTestEvent方法可以使用this =>访问类上下文. this.text是可访问的,但是无法使用removeListener删除侦听器 – 似乎bind创建了一个新的匿名函数,因此没有对有界侦听器的引用.

例3:

import {EventEmitter} from "events";

export default class EventsExample3 {
    private emitter: EventEmitter;

    constructor(private text: string) {
        this.emitter = new EventEmitter();

        this.emitter.addListener("test",() => this.handleTestEvent());
        this.emitter.emit("test");
    }

    public dispose() {
        this.emitter.removeListener("test",我使用箭头函数来保留事件监听器中的类的上下文. handleTestEvent方法可以使用它来访问类上下文,但是无法删除侦听器(没有像示例2那样引用有界侦听器).

我已经尝试了另一个事件库 – EventEmitter3,它支持事件的自定义上下文(类上下文可以作为第三个参数传递给addListener函数(this.emitter.addListener(“test”,this.handleTestEvent,this),它工作得很好,但我宁愿使用Node.js中包含的EventEmitter.

解决方法

你可以在构造函数中执行此操作:
this.handleTestEvent = this.handleTestEvent.bind(this);
this.emitter.addListener("test",this.handleTestEvent);

如果要使用前沿,可以使用proposed bind operator作为快捷方式:

this.handleTestEvent = ::this.handleTestEvent;
this.emitter.addListener("test",this.handleTestEvent);

或使用property initializer创建绑定方法

constructor(private text: string) {
  this.emitter = new EventEmitter();

  this.emitter.addListener("test",this.handleTestEvent);
  this.emitter.emit("test");
}

handleTestEvent = () => {
  console.log(this.text);
}

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐