@blibliki/engine 0.1.17 → 0.1.19

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (161) hide show
  1. package/README.md +13 -1
  2. package/{build → dist/build}/Engine.d.ts +14 -22
  3. package/dist/build/core/IO/AudioNode.d.ts +35 -0
  4. package/dist/build/core/IO/Collection.d.ts +13 -0
  5. package/dist/build/core/IO/ForwardNode.d.ts +38 -0
  6. package/dist/build/core/IO/MidiNode.d.ts +30 -0
  7. package/dist/build/core/IO/Node.d.ts +36 -0
  8. package/dist/build/core/IO/index.d.ts +12 -0
  9. package/dist/build/core/Module/MonoModule.d.ts +67 -0
  10. package/dist/build/core/Module/PolyModule.d.ts +57 -0
  11. package/dist/build/core/Module/index.d.ts +6 -0
  12. package/{build → dist/build/core}/Note/index.d.ts +3 -0
  13. package/{build → dist/build/core/midi}/MidiDevice.d.ts +1 -1
  14. package/dist/build/core/midi/MidiEvent.d.ts +21 -0
  15. package/dist/build/core/midi/index.d.ts +5 -0
  16. package/dist/build/index.d.ts +9 -0
  17. package/{build/Module → dist/build/modules}/BitCrusher.d.ts +5 -1
  18. package/{build/Module → dist/build/modules}/Delay.d.ts +5 -1
  19. package/{build/Module → dist/build/modules}/Distortion.d.ts +5 -1
  20. package/{build/Module → dist/build/modules}/Effect.d.ts +7 -2
  21. package/{build/Module → dist/build/modules}/Envelope/AmpEnvelope.d.ts +10 -2
  22. package/{build/Module → dist/build/modules}/Envelope/Base.d.ts +30 -11
  23. package/{build/Module → dist/build/modules}/Envelope/FreqEnvelope.d.ts +10 -3
  24. package/{build/Module → dist/build/modules}/Filter.d.ts +13 -13
  25. package/{build/Module → dist/build/modules}/Master.d.ts +5 -2
  26. package/{build/Module → dist/build/modules}/MidiSelector.d.ts +9 -5
  27. package/{build/Module → dist/build/modules}/Oscillator.d.ts +15 -9
  28. package/{build/Module → dist/build/modules}/Reverb.d.ts +5 -1
  29. package/{build/Module → dist/build/modules}/Sequencer.d.ts +9 -5
  30. package/{build/Module → dist/build/modules}/VirtualMidi.d.ts +12 -8
  31. package/dist/build/modules/VoiceScheduler.d.ts +43 -0
  32. package/dist/build/modules/Volume.d.ts +26 -0
  33. package/dist/build/modules/index.d.ts +16 -0
  34. package/{build → dist/build}/routes.d.ts +6 -5
  35. package/dist/build/types.d.ts +5 -0
  36. package/dist/build/utils.d.ts +1 -0
  37. package/dist/main.cjs.js +33 -0
  38. package/dist/main.cjs.js.map +1 -0
  39. package/dist/main.esm.js +33 -0
  40. package/dist/main.esm.js.map +1 -0
  41. package/package.json +26 -22
  42. package/src/Engine.ts +27 -36
  43. package/src/core/IO/AudioNode.ts +77 -0
  44. package/src/core/IO/Collection.ts +76 -0
  45. package/src/core/IO/ForwardNode.ts +192 -0
  46. package/src/core/IO/MidiNode.ts +67 -0
  47. package/src/core/IO/Node.ts +117 -0
  48. package/src/core/IO/index.ts +47 -0
  49. package/src/core/Module/MonoModule.ts +219 -0
  50. package/src/core/Module/PolyModule.ts +206 -0
  51. package/src/core/Module/index.ts +15 -0
  52. package/src/{Note → core/Note}/index.ts +19 -4
  53. package/src/{MidiDeviceManager.ts → core/midi/MidiDeviceManager.ts} +20 -15
  54. package/src/core/midi/MidiEvent.ts +91 -0
  55. package/src/core/midi/index.ts +5 -0
  56. package/src/index.ts +8 -12
  57. package/src/{Module → modules}/BitCrusher.ts +15 -4
  58. package/src/{Module → modules}/Delay.ts +15 -4
  59. package/src/{Module → modules}/Distortion.ts +15 -4
  60. package/src/{Module → modules}/Effect.ts +10 -6
  61. package/src/modules/Envelope/AmpEnvelope.ts +23 -0
  62. package/src/{Module → modules}/Envelope/Base.ts +50 -31
  63. package/src/{Module → modules}/Envelope/FreqEnvelope.ts +18 -23
  64. package/src/{Module → modules}/Filter.ts +18 -46
  65. package/src/{Module → modules}/Master.ts +8 -2
  66. package/src/{Module → modules}/MidiSelector.ts +18 -14
  67. package/src/{Module → modules}/Oscillator.ts +27 -16
  68. package/src/{Module → modules}/Reverb.ts +15 -4
  69. package/src/{Module → modules}/Sequencer.ts +17 -13
  70. package/src/{Module → modules}/VirtualMidi.ts +16 -12
  71. package/src/modules/VoiceScheduler.ts +145 -0
  72. package/src/{Module → modules}/Volume.ts +23 -15
  73. package/src/{Module → modules}/index.ts +14 -21
  74. package/src/routes.ts +19 -18
  75. package/src/types.ts +3 -0
  76. package/src/utils.ts +18 -0
  77. package/build/Engine.js +0 -165
  78. package/build/Engine.js.map +0 -1
  79. package/build/MidiDevice.js +0 -45
  80. package/build/MidiDevice.js.map +0 -1
  81. package/build/MidiDeviceManager.js +0 -59
  82. package/build/MidiDeviceManager.js.map +0 -1
  83. package/build/MidiEvent.d.ts +0 -18
  84. package/build/MidiEvent.js +0 -64
  85. package/build/MidiEvent.js.map +0 -1
  86. package/build/Module/Base.d.ts +0 -63
  87. package/build/Module/Base.js +0 -138
  88. package/build/Module/Base.js.map +0 -1
  89. package/build/Module/BitCrusher.js +0 -22
  90. package/build/Module/BitCrusher.js.map +0 -1
  91. package/build/Module/DataSequencer.d.ts +0 -26
  92. package/build/Module/DataSequencer.js +0 -91
  93. package/build/Module/DataSequencer.js.map +0 -1
  94. package/build/Module/Delay.js +0 -30
  95. package/build/Module/Delay.js.map +0 -1
  96. package/build/Module/Distortion.js +0 -22
  97. package/build/Module/Distortion.js.map +0 -1
  98. package/build/Module/Effect.js +0 -22
  99. package/build/Module/Effect.js.map +0 -1
  100. package/build/Module/Envelope/AmpEnvelope.js +0 -14
  101. package/build/Module/Envelope/AmpEnvelope.js.map +0 -1
  102. package/build/Module/Envelope/Base.js +0 -106
  103. package/build/Module/Envelope/Base.js.map +0 -1
  104. package/build/Module/Envelope/FreqEnvelope.js +0 -50
  105. package/build/Module/Envelope/FreqEnvelope.js.map +0 -1
  106. package/build/Module/Envelope/index.js +0 -4
  107. package/build/Module/Envelope/index.js.map +0 -1
  108. package/build/Module/Filter.js +0 -100
  109. package/build/Module/Filter.js.map +0 -1
  110. package/build/Module/IO.d.ts +0 -39
  111. package/build/Module/IO.js +0 -59
  112. package/build/Module/IO.js.map +0 -1
  113. package/build/Module/Master.js +0 -12
  114. package/build/Module/Master.js.map +0 -1
  115. package/build/Module/MidiSelector.js +0 -50
  116. package/build/Module/MidiSelector.js.map +0 -1
  117. package/build/Module/Oscillator.js +0 -136
  118. package/build/Module/Oscillator.js.map +0 -1
  119. package/build/Module/PolyModule.d.ts +0 -49
  120. package/build/Module/PolyModule.js +0 -175
  121. package/build/Module/PolyModule.js.map +0 -1
  122. package/build/Module/Reverb.js +0 -30
  123. package/build/Module/Reverb.js.map +0 -1
  124. package/build/Module/Sequencer.js +0 -131
  125. package/build/Module/Sequencer.js.map +0 -1
  126. package/build/Module/VirtualMidi.js +0 -53
  127. package/build/Module/VirtualMidi.js.map +0 -1
  128. package/build/Module/VoiceScheduler.d.ts +0 -38
  129. package/build/Module/VoiceScheduler.js +0 -130
  130. package/build/Module/VoiceScheduler.js.map +0 -1
  131. package/build/Module/Volume.d.ts +0 -20
  132. package/build/Module/Volume.js +0 -48
  133. package/build/Module/Volume.js.map +0 -1
  134. package/build/Module/index.d.ts +0 -14
  135. package/build/Module/index.js +0 -66
  136. package/build/Module/index.js.map +0 -1
  137. package/build/Note/frequencyTable.js +0 -146
  138. package/build/Note/frequencyTable.js.map +0 -1
  139. package/build/Note/index.js +0 -81
  140. package/build/Note/index.js.map +0 -1
  141. package/build/index.d.ts +0 -8
  142. package/build/index.js +0 -5
  143. package/build/index.js.map +0 -1
  144. package/build/routes.js +0 -31
  145. package/build/routes.js.map +0 -1
  146. package/jest.config.js +0 -19
  147. package/src/MidiEvent.ts +0 -93
  148. package/src/Module/Base.ts +0 -223
  149. package/src/Module/DataSequencer.ts +0 -121
  150. package/src/Module/Envelope/AmpEnvelope.ts +0 -17
  151. package/src/Module/IO.ts +0 -85
  152. package/src/Module/PolyModule.ts +0 -234
  153. package/src/Module/VoiceScheduler.ts +0 -161
  154. package/test/Module/Oscillator.test.ts +0 -9
  155. package/tsconfig.json +0 -22
  156. /package/{build → dist/build/core}/Note/frequencyTable.d.ts +0 -0
  157. /package/{build → dist/build/core/midi}/MidiDeviceManager.d.ts +0 -0
  158. /package/{build/Module → dist/build/modules}/Envelope/index.d.ts +0 -0
  159. /package/src/{Note → core/Note}/frequencyTable.ts +0 -0
  160. /package/src/{MidiDevice.ts → core/midi/MidiDevice.ts} +0 -0
  161. /package/src/{Module → modules}/Envelope/index.ts +0 -0
package/src/MidiEvent.ts DELETED
@@ -1,93 +0,0 @@
1
- import { now } from "tone";
2
- import { ISequence } from "./Module/Sequencer";
3
- import { IDataSequence } from "./Module/DataSequencer";
4
- import Note, { INote } from "./Note";
5
-
6
- const EventType: { [key: number]: EType } = {
7
- 8: "noteOff",
8
- 9: "noteOn",
9
- };
10
-
11
- export type EType = "noteOn" | "noteOff";
12
-
13
- export default class MidiEvent {
14
- notes: Note[];
15
- readonly triggeredAt: number;
16
- _type: EType;
17
- private data: Uint8Array;
18
- private event: MIDIMessageEvent;
19
-
20
- static fromDataSequence(sequence: IDataSequence, triggeredAt: number) {
21
- const event = new MidiEvent(
22
- new MIDIMessageEvent("", { data: new Uint8Array([0, 0, 0]) }),
23
- triggeredAt
24
- );
25
- event._type = "noteOn";
26
- const note = new Note(sequence.frequency);
27
- note.velocity = sequence.amplitude;
28
- event.notes = [note];
29
-
30
- return event;
31
- }
32
-
33
- static fromSequence(sequence: ISequence, triggeredAt: number) {
34
- const event = new MidiEvent(
35
- new MIDIMessageEvent("", { data: new Uint8Array([0, 0, 0]) }),
36
- triggeredAt
37
- );
38
- event._type = "noteOn";
39
- event.notes = sequence.notes.map((n) => new Note(n));
40
-
41
- return event;
42
- }
43
-
44
- static fromNote(
45
- noteName: string | Note | INote,
46
- type: EType,
47
- triggeredAt?: number
48
- ) {
49
- const event = new MidiEvent(
50
- new MIDIMessageEvent("", { data: new Uint8Array([0, 0, 0]) }),
51
- triggeredAt
52
- );
53
-
54
- if (noteName instanceof Note) {
55
- event.notes = [noteName];
56
- } else {
57
- event.notes = [new Note(noteName)];
58
- }
59
- event._type = type;
60
-
61
- return event;
62
- }
63
-
64
- constructor(event: MIDIMessageEvent, triggeredAt?: number) {
65
- this.event = event;
66
- this.triggeredAt = triggeredAt || now();
67
- this.data = event.data;
68
- this.defineNotes();
69
- }
70
-
71
- get type() {
72
- if (this._type) return this._type;
73
-
74
- let type = EventType[this.data[0] >> 4];
75
-
76
- if (type === "noteOn" && this.data[2] === 0) {
77
- type = "noteOff";
78
- }
79
-
80
- return (this._type = type);
81
- }
82
-
83
- get isNote() {
84
- return this.type === "noteOn" || this.type === "noteOff";
85
- }
86
-
87
- defineNotes() {
88
- if (!this.isNote) return;
89
- if (this.notes) return;
90
-
91
- this.notes = [new Note(this.event)];
92
- }
93
- }
@@ -1,223 +0,0 @@
1
- import { v4 as uuidv4 } from "uuid";
2
- import { InputNode } from "tone";
3
-
4
- import { Input, Output, IOInterface } from "./IO";
5
- import MidiEvent from "../MidiEvent";
6
- import { AudioModule, PolyModule } from "../Module";
7
- import Note from "../Note";
8
-
9
- export interface Connectable {
10
- connect: (inputNode: InputNode) => void;
11
- disconnect: (inputNode?: InputNode) => void;
12
- dispose: () => void;
13
- }
14
-
15
- export interface Triggerable {
16
- triggerAttack: Function;
17
- triggerRelease: Function;
18
- }
19
-
20
- export interface Voicable {
21
- voiceNo?: number;
22
- }
23
-
24
- export interface ModuleInterface<PropsInterface> {
25
- name: string;
26
- props: PropsInterface;
27
- voiceNo?: number;
28
- }
29
-
30
- export class DummnyInternalModule implements Connectable {
31
- connect(inputNode: InputNode) {
32
- throw Error("This module is not connectable");
33
- }
34
-
35
- disconnect(inputNode?: InputNode) {}
36
-
37
- dispose() {}
38
- }
39
-
40
- class Module<InternalModule extends Connectable, PropsInterface>
41
- implements ModuleInterface<PropsInterface>
42
- {
43
- static readonly moduleName: string;
44
-
45
- readonly id: string;
46
- name: string;
47
- internalModule: InternalModule;
48
- inputs: Input[] = [];
49
- outputs: Output[] = [];
50
- readonly voiceNo?: number;
51
- updatedAt: Date;
52
- _props: PropsInterface = {} as PropsInterface;
53
-
54
- constructor(
55
- internalModule: InternalModule,
56
- props: Partial<ModuleInterface<PropsInterface>>
57
- ) {
58
- this.internalModule = internalModule;
59
- this.id = uuidv4();
60
-
61
- Object.assign(this, props);
62
- }
63
-
64
- set props(value: PropsInterface) {
65
- if (!value) return;
66
-
67
- this.updatedAt = new Date();
68
-
69
- Object.assign(this, value);
70
- }
71
-
72
- get props() {
73
- return this._props;
74
- }
75
-
76
- plug(audioModule: AudioModule, from: string, to: string) {
77
- const output = this.outputs.find((i) => i.name === from);
78
- if (!output) throw Error(`Output ${from} not exist`);
79
-
80
- const input = audioModule.inputs.find((i) => i.name === to);
81
- if (!input)
82
- throw Error(`Input ${to} in module ${audioModule.name} not exist`);
83
-
84
- output.plug(input);
85
- }
86
-
87
- unplugAll() {
88
- this.outputs.forEach((o) => o.unPlugAll());
89
- }
90
-
91
- connect = (
92
- inputAudioModule: AudioModule,
93
- attribute: string = "internalModule"
94
- ) => {
95
- if (inputAudioModule instanceof PolyModule) {
96
- inputAudioModule.audioModules.forEach((m) => {
97
- this.internalModule.connect((m as any)[attribute] as InputNode);
98
- });
99
- return;
100
- }
101
-
102
- this.internalModule.connect(
103
- (inputAudioModule as any)[attribute] as InputNode
104
- );
105
- };
106
-
107
- disconnect = (
108
- inputAudioModule: AudioModule,
109
- attribute: string = "internalModule"
110
- ) => {
111
- if (inputAudioModule instanceof PolyModule) {
112
- inputAudioModule.audioModules.forEach((m) => {
113
- this.internalModule.disconnect((m as any)[attribute] as InputNode);
114
- });
115
- return;
116
- }
117
-
118
- this.internalModule.disconnect(
119
- (inputAudioModule as any)[attribute] as InputNode
120
- );
121
- };
122
-
123
- dispose() {
124
- this.internalModule.dispose();
125
- }
126
-
127
- triggerAttack(note: Note, triggeredAt: number) {
128
- throw Error("triggerAttack not implemented");
129
- }
130
-
131
- triggerRelease(note: Note, triggeredAt: number) {
132
- throw Error("triggerRelease not implemented");
133
- }
134
-
135
- midiTriggered = (midiEvent: MidiEvent, noteIndex?: number) => {
136
- const { notes, triggeredAt } = midiEvent;
137
-
138
- switch (midiEvent.type) {
139
- case "noteOn":
140
- const { duration } = notes[0];
141
-
142
- this.triggerer(this.triggerAttack, notes, triggeredAt, noteIndex);
143
-
144
- if (duration) {
145
- const releaseTriggeredAt =
146
- triggeredAt + (this.internalModule as any).toSeconds(duration);
147
- this.triggerer(
148
- this.triggerRelease,
149
- notes,
150
- releaseTriggeredAt,
151
- noteIndex
152
- );
153
- }
154
- break;
155
- case "noteOff":
156
- this.triggerer(this.triggerRelease, notes, triggeredAt, noteIndex);
157
- break;
158
- default:
159
- throw Error("This type is not a note");
160
- }
161
- };
162
-
163
- private triggerer(
164
- trigger: Function,
165
- notes: Note[],
166
- triggeredAt: number,
167
- noteIndex?: number
168
- ) {
169
- if (noteIndex !== undefined && this.voiceNo !== undefined) {
170
- trigger(notes[noteIndex], triggeredAt);
171
- return;
172
- }
173
-
174
- notes.forEach((note) => trigger(note, triggeredAt));
175
- }
176
-
177
- serialize() {
178
- const klass = this.constructor as typeof Module;
179
-
180
- return {
181
- id: this.id,
182
- name: this.name,
183
- type: klass.moduleName,
184
- props: this.props,
185
- inputs: this.inputs.map((i) => i.serialize()),
186
- outputs: this.outputs.map((i) => i.serialize()),
187
- };
188
- }
189
-
190
- protected registerInput(props: IOInterface): Input {
191
- const input = new Input(this, props);
192
- this.inputs.push(input);
193
-
194
- return input;
195
- }
196
-
197
- protected registerOutput(props: IOInterface): Output {
198
- const output = new Output(this, props);
199
- this.outputs.push(output);
200
-
201
- return output;
202
- }
203
-
204
- protected registerBasicOutputs() {
205
- this.registerOutput({
206
- name: "output",
207
- onPlug: (output: Output) => {
208
- this.connect(output.audioModule);
209
- },
210
- onUnPlug: (output: Output) => {
211
- this.disconnect(output.audioModule);
212
- },
213
- });
214
- }
215
-
216
- protected registerBasicInputs() {
217
- this.registerInput({
218
- name: "input",
219
- });
220
- }
221
- }
222
-
223
- export default Module;
@@ -1,121 +0,0 @@
1
- import { Loop, now } from "tone";
2
-
3
- import Module, { DummnyInternalModule } from "./Base";
4
- import { Output } from "./IO";
5
- import MidiEvent from "../MidiEvent";
6
- import { sortBy, uniq } from "lodash";
7
- import Engine from "../Engine";
8
-
9
- interface IDataSequencer {
10
- sequences: IDataSequence[];
11
- }
12
-
13
- export interface IDataSequence {
14
- voiceNo: number;
15
- time: number;
16
- frequency: number;
17
- amplitude: number;
18
- }
19
-
20
- const InitialProps = () => ({
21
- sequences: [],
22
- });
23
-
24
- export default class DataSequencer extends Module<
25
- DummnyInternalModule,
26
- IDataSequencer
27
- > {
28
- static moduleName = "DataSequencer";
29
- private midiOutput: Output;
30
- private prevNumberOfVoices: number;
31
- private loop: Loop;
32
-
33
- constructor(name: string, props: Partial<IDataSequence>) {
34
- super(new DummnyInternalModule(), {
35
- name,
36
- props: { ...InitialProps(), ...props },
37
- });
38
-
39
- this.start(now());
40
- this.registerOutputs();
41
- }
42
-
43
- get sequences() {
44
- return this._props["sequences"];
45
- }
46
-
47
- set sequences(value: IDataSequence[]) {
48
- const sequences = sortBy(value, (seq) => -seq.time);
49
- this._props = { ...this.props, sequences };
50
- this.updateNumberOfVoices();
51
- this.start(now());
52
- }
53
-
54
- start(time: number) {
55
- if (!Engine.isStarted) return;
56
- Engine.updateRoutes();
57
-
58
- const loopLength = 0.1;
59
- const tempSequences = [...this.sequences];
60
- const iterate = (maxTime: number) => {
61
- const sequence = tempSequences.pop();
62
- if (!sequence) return;
63
-
64
- const seqTime = time + sequence.time;
65
- this.onPartEvent(seqTime, sequence);
66
- if (seqTime > maxTime) return;
67
-
68
- iterate(maxTime);
69
- };
70
-
71
- this.loop = new Loop((t) => {
72
- iterate(time + t + loopLength);
73
- }, loopLength).start(time);
74
- }
75
-
76
- stop() {
77
- if (!this.loop) return;
78
-
79
- this.loop.stop();
80
- this.loop.dispose();
81
- }
82
-
83
- private onPartEvent = (time: number, sequence: IDataSequence) => {
84
- const { voiceNo } = sequence;
85
- const event = MidiEvent.fromDataSequence(sequence, time);
86
-
87
- this.midiOutput.connections.forEach((input) => {
88
- input.pluggable(event, voiceNo);
89
- });
90
- };
91
-
92
- private get numberOfVoices() {
93
- return uniq(this.sequences.map((sequence) => sequence.voiceNo)).length;
94
- }
95
-
96
- private updateNumberOfVoices() {
97
- if (!this.midiOutput) return;
98
-
99
- this.midiOutput.connections.forEach((input) => {
100
- if (input.audioModule instanceof Module) return;
101
-
102
- input.audioModule.numberOfVoices = this.numberOfVoices;
103
- });
104
-
105
- if (this.prevNumberOfVoices !== this.numberOfVoices) {
106
- Engine.updateRoutes();
107
- }
108
- this.prevNumberOfVoices = this.numberOfVoices;
109
- }
110
-
111
- private registerOutputs() {
112
- this.midiOutput = this.registerOutput({
113
- name: "midi out",
114
- onPlug: (input) => {
115
- if (input.audioModule instanceof Module) return;
116
-
117
- input.audioModule.numberOfVoices = this.numberOfVoices;
118
- },
119
- });
120
- }
121
- }
@@ -1,17 +0,0 @@
1
- import { AmplitudeEnvelope } from "tone";
2
-
3
- import Base, { EnvelopeInterface, PolyBase } from "./Base";
4
-
5
- class MonoAmpEnvelope extends Base<AmplitudeEnvelope> {
6
- constructor(name: string, props: EnvelopeInterface) {
7
- super(name, new AmplitudeEnvelope(), props);
8
- }
9
- }
10
-
11
- export default class AmpEnvelope extends PolyBase<MonoAmpEnvelope> {
12
- static moduleName = "AmpEnvelope";
13
-
14
- constructor(name: string, props: Partial<EnvelopeInterface>) {
15
- super(name, MonoAmpEnvelope, props);
16
- }
17
- }
package/src/Module/IO.ts DELETED
@@ -1,85 +0,0 @@
1
- import { v4 as uuidv4 } from "uuid";
2
- import { AudioModule } from "../Module";
3
-
4
- export interface IOInterface {
5
- name: string;
6
- pluggable?: any;
7
- onPlug?: (io: IO) => void;
8
- onUnPlug?: (io: IO) => void;
9
- }
10
-
11
- export interface SerializeInterface {
12
- id: string;
13
- name: string;
14
- moduleId: string;
15
- moduleName: string;
16
- }
17
-
18
- enum IOType {
19
- Input = "input",
20
- Output = "output",
21
- }
22
-
23
- abstract class IO {
24
- id: string;
25
- ioType: IOType;
26
- name: string;
27
- audioModule: AudioModule;
28
- pluggable: any;
29
- onPlug: (io: IO) => void;
30
- onUnPlug: (io: IO) => void;
31
- connections: Input[] | Output[] = [];
32
-
33
- constructor(ioType: IOType, audioModule: AudioModule, props: IOInterface) {
34
- this.id = uuidv4();
35
- this.ioType = ioType;
36
- this.audioModule = audioModule;
37
-
38
- Object.assign(this, props);
39
- }
40
-
41
- plug(io: IO) {
42
- this.connections.push(io);
43
-
44
- if (this.onPlug) this.onPlug(io);
45
-
46
- if (this.ioType === IOType.Output) io.plug(this);
47
- }
48
-
49
- unPlug(io: IO) {
50
- if (this.onUnPlug) this.onUnPlug(io);
51
-
52
- if (this.ioType === IOType.Output) {
53
- io.unPlug(this);
54
- }
55
-
56
- this.connections = this.connections.filter(
57
- (current_io) => current_io.id !== io.id
58
- );
59
- }
60
-
61
- unPlugAll() {
62
- this.connections.forEach((c) => this.unPlug(c));
63
- }
64
-
65
- serialize(): SerializeInterface {
66
- return {
67
- id: this.id,
68
- name: this.name,
69
- moduleId: this.audioModule.id,
70
- moduleName: this.audioModule.name,
71
- };
72
- }
73
- }
74
-
75
- export class Input extends IO {
76
- constructor(audioModule: AudioModule, props: IOInterface) {
77
- super(IOType.Input, audioModule, props);
78
- }
79
- }
80
-
81
- export class Output extends IO {
82
- constructor(audioModule: AudioModule, props: IOInterface) {
83
- super(IOType.Output, audioModule, props);
84
- }
85
- }