73 lines
2.6 kB
1
import { MoonlightEventEmitter } from "@moonlight-mod/types/core/event";
2
3
export function createEventEmitter<
4
EventId extends string = string,
5
EventData = Record<EventId, any>
6
>(): MoonlightEventEmitter<EventId, EventData> {
7
webTarget: {
8
const eventEmitter = new EventTarget();
9
const listeners = new Map<(data: EventData) => void, (e: Event) => void>();
10
11
return {
12
dispatchEvent: <Id extends keyof EventData>(id: Id, data: EventData[Id]) => {
13
eventEmitter.dispatchEvent(new CustomEvent(id as string, { detail: data }));
14
},
15
16
addEventListener: <Id extends keyof EventData>(id: Id, cb: (data: EventData[Id]) => void) => {
17
const untyped = cb as (data: EventData) => void;
18
if (listeners.has(untyped)) return;
19
20
function listener(e: Event) {
21
const event = e as CustomEvent<string>;
22
cb(event.detail as EventData[Id]);
23
}
24
25
listeners.set(untyped, listener);
26
eventEmitter.addEventListener(id as string, listener);
27
},
28
29
removeEventListener: <Id extends keyof EventData>(id: Id, cb: (data: EventData[Id]) => void) => {
30
const untyped = cb as (data: EventData) => void;
31
const listener = listeners.get(untyped);
32
if (listener == null) return;
33
listeners.delete(untyped);
34
eventEmitter.removeEventListener(id as string, listener);
35
}
36
};
37
}
38
39
nodeTarget: {
40
const EventEmitter = require("events");
41
const eventEmitter = new EventEmitter();
42
const listeners = new Map<(data: EventData) => void, (e: Event) => void>();
43
44
return {
45
dispatchEvent: <Id extends keyof EventData>(id: Id, data: EventData[Id]) => {
46
eventEmitter.emit(id as string, data);
47
},
48
49
addEventListener: <Id extends keyof EventData>(id: Id, cb: (data: EventData[Id]) => void) => {
50
const untyped = cb as (data: EventData) => void;
51
if (listeners.has(untyped)) return;
52
53
function listener(e: Event) {
54
const event = e as CustomEvent<string>;
55
cb(event as EventData[Id]);
56
}
57
58
listeners.set(untyped, listener);
59
eventEmitter.on(id as string, listener);
60
},
61
62
removeEventListener: <Id extends keyof EventData>(id: Id, cb: (data: EventData[Id]) => void) => {
63
const untyped = cb as (data: EventData) => void;
64
const listener = listeners.get(untyped);
65
if (listener == null) return;
66
listeners.delete(untyped);
67
eventEmitter.off(id as string, listener);
68
}
69
};
70
}
71
72
throw new Error("Called createEventEmitter() in an impossible environment");
73
}
74