import { IDisposable } from './Types' interface IListener { (arg: T): void } export interface IEvent { (listener: IListener): IDisposable } export interface IEventEmitter { onEvent: IEvent fire(arg: T): void dispose(): void } export class EventEmitter implements IEventEmitter { private _listeners: IListener[] = [] private _event?: IEvent private _disposed: boolean = false public get onEvent(): IEvent { if (!this._event) { this._event = (listener: IListener) => { this._listeners.push(listener) const disposable = { dispose: () => { if (!this._disposed) { for (let i = 0; i < this._listeners.length; i++) { if (this._listeners[i] === listener) { this._listeners.splice(i, 1) return } } } } } return disposable } } return this._event } public fire(arg: T): void { for (let i = 0; i < this._listeners.length; i++) { this._listeners[i](arg) } } public dispose(): void { if (this._listeners) { this._listeners.length = 0 } this._disposed = true } }