import { EventEmitter as BaseEventEmitter } from "eventemitter3"; export class EventEmitter extends BaseEventEmitter { subscribe>( event: T, fn: EventListener, destroy?: () => void, ): { unsubscribe: () => void; } { this.addListener(event, fn); return { unsubscribe: () => { this.removeListener(event, fn); if (destroy) { destroy(); } }, }; } } /* |-------------------------------------------------------------------------------- | Types |-------------------------------------------------------------------------------- */ type EventListener> = T extends string | symbol ? (...args: any[]) => void : (...args: ArgumentMap>[Extract]) => void; type EventNames = T extends string | symbol ? T : keyof T; type ValidEventTypes = string | symbol | Record; type ArgumentMap> = { [K in keyof T]: T[K] extends (...args: any[]) => void ? Parameters : T[K] extends any[] ? T[K] : any[]; };