export interface Event { type : string ; detail ? : any ; } export type Listener = ( ( e : Event ) => void ) | { handle : ( e : Event ) => void ; } ; export interface EventTarget { addEventListener ( eventName , listener ) : any ; removeEventListener ( eventName , listener ) : any ; } export class EventEmitter implements EventTarget { private _listeners = new Map < string , Set < Listener > > ( ) ; addEventListener ( eventName , listener ) { if ( ! this . _listeners . has ( eventName ) ) { this . _listeners . set ( eventName , new Set < Listener > ( ) ) ; } this . _listeners . get ( eventName ) ! . add ( listener ) ; } removeEventListener ( eventName , listener ) { const listeners = this . _listeners . get ( eventName ) ; if ( listeners ) { listeners . delete ( listener ) ; } } dispatchEvent ( e ) { const listeners = this . _listeners . get ( e . type ) ; if ( listeners ) { for ( const listener of listeners ) { if ( typeof listener === "function" ) { listener ( e ) ; } else { listener . handle ( e ) ; } } } } dispatch ( type , detail ? ) { this . dispatchEvent ( { type , detail } ) ; } }