spessasynth_core 1.0.0

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 (55) hide show
  1. package/.idea/inspectionProfiles/Project_Default.xml +10 -0
  2. package/.idea/jsLibraryMappings.xml +6 -0
  3. package/.idea/modules.xml +8 -0
  4. package/.idea/spessasynth_core.iml +12 -0
  5. package/.idea/vcs.xml +6 -0
  6. package/README.md +376 -0
  7. package/index.js +7 -0
  8. package/package.json +34 -0
  9. package/spessasynth_core/midi_parser/README.md +3 -0
  10. package/spessasynth_core/midi_parser/midi_loader.js +381 -0
  11. package/spessasynth_core/midi_parser/midi_message.js +231 -0
  12. package/spessasynth_core/sequencer/sequencer.js +192 -0
  13. package/spessasynth_core/sequencer/worklet_sequencer/play.js +221 -0
  14. package/spessasynth_core/sequencer/worklet_sequencer/process_event.js +138 -0
  15. package/spessasynth_core/sequencer/worklet_sequencer/process_tick.js +85 -0
  16. package/spessasynth_core/sequencer/worklet_sequencer/song_control.js +90 -0
  17. package/spessasynth_core/soundfont/README.md +4 -0
  18. package/spessasynth_core/soundfont/chunk/generators.js +205 -0
  19. package/spessasynth_core/soundfont/chunk/instruments.js +60 -0
  20. package/spessasynth_core/soundfont/chunk/modulators.js +232 -0
  21. package/spessasynth_core/soundfont/chunk/presets.js +264 -0
  22. package/spessasynth_core/soundfont/chunk/riff_chunk.js +46 -0
  23. package/spessasynth_core/soundfont/chunk/samples.js +250 -0
  24. package/spessasynth_core/soundfont/chunk/zones.js +264 -0
  25. package/spessasynth_core/soundfont/soundfont_parser.js +301 -0
  26. package/spessasynth_core/synthetizer/README.md +6 -0
  27. package/spessasynth_core/synthetizer/synthesizer.js +303 -0
  28. package/spessasynth_core/synthetizer/worklet_system/README.md +3 -0
  29. package/spessasynth_core/synthetizer/worklet_system/worklet_methods/controller_control.js +285 -0
  30. package/spessasynth_core/synthetizer/worklet_system/worklet_methods/data_entry.js +280 -0
  31. package/spessasynth_core/synthetizer/worklet_system/worklet_methods/note_off.js +102 -0
  32. package/spessasynth_core/synthetizer/worklet_system/worklet_methods/note_on.js +75 -0
  33. package/spessasynth_core/synthetizer/worklet_system/worklet_methods/program_control.js +140 -0
  34. package/spessasynth_core/synthetizer/worklet_system/worklet_methods/system_exclusive.js +265 -0
  35. package/spessasynth_core/synthetizer/worklet_system/worklet_methods/tuning_control.js +105 -0
  36. package/spessasynth_core/synthetizer/worklet_system/worklet_methods/vibrato_control.js +29 -0
  37. package/spessasynth_core/synthetizer/worklet_system/worklet_methods/voice_control.js +186 -0
  38. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/lfo.js +23 -0
  39. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/lowpass_filter.js +95 -0
  40. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/modulation_envelope.js +73 -0
  41. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/modulator_curves.js +86 -0
  42. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/stereo_panner.js +76 -0
  43. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/unit_converter.js +66 -0
  44. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/volume_envelope.js +194 -0
  45. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/wavetable_oscillator.js +83 -0
  46. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/worklet_modulator.js +173 -0
  47. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/worklet_processor_channel.js +105 -0
  48. package/spessasynth_core/synthetizer/worklet_system/worklet_utilities/worklet_voice.js +313 -0
  49. package/spessasynth_core/utils/README.md +4 -0
  50. package/spessasynth_core/utils/buffer_to_wav.js +70 -0
  51. package/spessasynth_core/utils/byte_functions.js +141 -0
  52. package/spessasynth_core/utils/loggin.js +79 -0
  53. package/spessasynth_core/utils/other.js +49 -0
  54. package/spessasynth_core/utils/shiftable_array.js +26 -0
  55. package/spessasynth_core/utils/stbvorbis_sync.js +1877 -0
@@ -0,0 +1,141 @@
1
+ import { ShiftableByteArray } from './shiftable_array.js'
2
+
3
+ /**
4
+ * byte_functions.js
5
+ * purpose: contains various useful functions for bit manipulation and reading
6
+ */
7
+
8
+ /**
9
+ * Reads as little endian
10
+ * @param dataArray {ShiftableByteArray}
11
+ * @param bytesAmount {number}
12
+ * @returns {number}
13
+ */
14
+ export function readBytesAsUintLittleEndian(dataArray, bytesAmount){
15
+ let out = 0;
16
+ for(let i = 0; i < bytesAmount; i++)
17
+ {
18
+ out |= (readByte(dataArray) << i * 8);
19
+ }
20
+ // make sure it stays unsigned
21
+ return out >>> 0;
22
+ }
23
+
24
+ /**
25
+ * Reads as Big endian
26
+ * @param dataArray {ShiftableByteArray}
27
+ * @param bytesAmount {number}
28
+ * @returns {number}
29
+ */
30
+ export function readBytesAsUintBigEndian(dataArray, bytesAmount){
31
+ let out = 0;
32
+ for (let i = 8 * (bytesAmount - 1); i >= 0; i -= 8) {
33
+ out |= (readByte(dataArray) << i);
34
+ }
35
+ return out >>> 0;
36
+ }
37
+
38
+ /**
39
+ * @param dataArray {ShiftableByteArray}
40
+ * @returns {number}
41
+ */
42
+ export function readByte(dataArray){
43
+ if(!dataArray.shift)
44
+ {
45
+ dataArray.currentIndex = 0;
46
+ dataArray.shift = function () {
47
+ this.currentIndex++;
48
+ return this[this.currentIndex - 1];
49
+ }
50
+ }
51
+ return dataArray.shift();
52
+
53
+ }
54
+
55
+ /**
56
+ * @param dataArray {ShiftableByteArray}
57
+ * @param bytes {number}
58
+ * @param encoding {string} the textElement encoding
59
+ * @param trimEnd {boolean} if we should trim once we reach an invalid byte
60
+ * @returns {string}
61
+ */
62
+ export function readBytesAsString(dataArray, bytes, encoding=undefined, trimEnd=true){
63
+ if(!encoding) {
64
+ let finished = false;
65
+ let string = "";
66
+ for (let i = 0; i < bytes; i++) {
67
+ let byte = readByte(dataArray);
68
+ if(byte < 32 || byte > 127 || finished)
69
+ {
70
+ if(trimEnd) {
71
+ finished = true;
72
+ continue;
73
+ }
74
+ else
75
+ {
76
+ if(byte === 0)
77
+ {
78
+ finished = true;
79
+ continue;
80
+ }
81
+ }
82
+ }
83
+ string += String.fromCharCode(byte);
84
+ }
85
+ return string;
86
+ }
87
+ else {
88
+ let byteBuffer = dataArray.slice(dataArray.currentIndex, dataArray.currentIndex + bytes)
89
+ dataArray.currentIndex += bytes;
90
+ let decoder = new TextDecoder(encoding);
91
+ return decoder.decode(byteBuffer.buffer);
92
+ }
93
+ }
94
+
95
+ /**
96
+ * @param byte1 {number}
97
+ * @param byte2 {number}
98
+ * @returns {number}
99
+ */
100
+ export function signedInt16(byte1, byte2){
101
+ let val = (byte2 << 8) | byte1;
102
+ if(val > 32767)
103
+ {
104
+ return val - 65536;
105
+ }
106
+ return val;
107
+ }
108
+
109
+ /**
110
+ * @param byte {number}
111
+ * @returns {number}
112
+ */
113
+ export function signedInt8(byte) {
114
+ if(byte > 127)
115
+ {
116
+ return byte - 256;
117
+ }
118
+ return byte;
119
+ }
120
+
121
+ /**
122
+ * Reads VLQ From a MIDI byte array
123
+ * @param MIDIbyteArray {ShiftableByteArray}
124
+ * @returns {number}
125
+ */
126
+ export function readVariableLengthQuantity(MIDIbyteArray){
127
+ let out = 0;
128
+ while(MIDIbyteArray)
129
+ {
130
+ const byte = readByte(MIDIbyteArray);
131
+ // extract the first 7 bytes
132
+ out = (out << 7) | (byte & 127);
133
+
134
+ // if the last byte isn't 1, stop reading
135
+ if((byte >> 7) !== 1)
136
+ {
137
+ break;
138
+ }
139
+ }
140
+ return out;
141
+ }
@@ -0,0 +1,79 @@
1
+ let ENABLE_INFO = true;
2
+ let ENABLE_WARN = true;
3
+ let ENABLE_GROUP = true;
4
+ let ENABLE_TABLE = true;
5
+
6
+ /**
7
+ * Enables or disables looging
8
+ * @param enableInfo {boolean} - enables info
9
+ * @param enableWarn {boolean} - enables warning
10
+ * @param enableGroup {boolean} - enables groups
11
+ * @param enableTable {boolean} - enables tables
12
+ */
13
+ export function SpessaSynthLogging(enableInfo, enableWarn, enableGroup, enableTable)
14
+ {
15
+ ENABLE_INFO = enableInfo;
16
+ ENABLE_WARN = enableWarn;
17
+ ENABLE_GROUP = enableGroup;
18
+ ENABLE_TABLE = enableTable;
19
+ }
20
+
21
+ /**
22
+ * @param message {...any}
23
+ */
24
+ export function SpessaSynthInfo(...message)
25
+ {
26
+ if(ENABLE_INFO)
27
+ {
28
+ console.info(...message);
29
+ }
30
+ }
31
+
32
+ /**
33
+ * @param message {...any}
34
+ */
35
+ export function SpessaSynthWarn(...message)
36
+ {
37
+ if(ENABLE_WARN)
38
+ {
39
+ console.warn(...message);
40
+ }
41
+ }
42
+
43
+ export function SpessaSynthTable(...args)
44
+ {
45
+ if(ENABLE_TABLE)
46
+ {
47
+ console.table(...args);
48
+ }
49
+ }
50
+
51
+ /**
52
+ * @param message {...any} the message
53
+ */
54
+ export function SpessaSynthGroup(...message)
55
+ {
56
+ if(ENABLE_GROUP)
57
+ {
58
+ console.group(...message);
59
+ }
60
+ }
61
+
62
+ /**
63
+ * @param message {...any} the message
64
+ */
65
+ export function SpessaSynthGroupCollapsed(...message)
66
+ {
67
+ if(ENABLE_GROUP)
68
+ {
69
+ console.groupCollapsed(...message);
70
+ }
71
+ }
72
+
73
+ export function SpessaSynthGroupEnd()
74
+ {
75
+ if(ENABLE_GROUP)
76
+ {
77
+ console.groupEnd();
78
+ }
79
+ }
@@ -0,0 +1,49 @@
1
+ /**
2
+ * other.js
3
+ * purpose: contains some useful functions that don't belong in any specific category
4
+ */
5
+
6
+ /**
7
+ * Formats the given seconds to nice readable time
8
+ * @param totalSeconds {number} time in seconds
9
+ * @return {{seconds: number, minutes: number, time: string}}
10
+ */
11
+ export function formatTime(totalSeconds) {
12
+ let minutes = Math.floor(totalSeconds / 60);
13
+ let seconds = Math.round(totalSeconds - (minutes * 60));
14
+ return {"minutes": minutes, "seconds": seconds, "time": `${minutes.toString().padStart(2, '0')}:${seconds.toString().padStart(2, '0')}`}
15
+ }
16
+
17
+ /**
18
+ * @param fileName {string}
19
+ * @returns {string}
20
+ */
21
+ export function formatTitle(fileName)
22
+ {
23
+ return fileName.replaceAll(".mid", "").replaceAll("_", " ");
24
+ }
25
+
26
+ /**
27
+ * Does what it says
28
+ * @param arr {number[]}
29
+ * @returns {string}
30
+ */
31
+ export function arrayToHexString(arr) {
32
+ let hexString = '';
33
+
34
+ for (let i = 0; i < arr.length; i++) {
35
+ const hex = arr[i].toString(16).padStart(2, '0').toUpperCase();
36
+ hexString += hex;
37
+ hexString += ' ';
38
+ }
39
+
40
+ return hexString;
41
+ }
42
+
43
+ export const consoleColors = {
44
+ warn: "color: orange;",
45
+ unrecognized: "color: red;",
46
+ info: "color: aqua;",
47
+ recognized: "color: lime",
48
+ value: "color: yellow; background-color: black;"
49
+ }
@@ -0,0 +1,26 @@
1
+ /**
2
+ * shiftable_array.js
3
+ * purpose: exteds Uint8Array with the Array.shift() function
4
+ */
5
+
6
+ export class ShiftableByteArray extends Uint8Array
7
+ {
8
+ /**
9
+ * Creates a new instance of an Uint8Array with Array.shift() function
10
+ * @param args {any} same as for Uint8Array
11
+ */
12
+ constructor(args) {
13
+ super(args);
14
+ this.currentIndex = 0;
15
+ }
16
+
17
+ /**
18
+ * @param amount {number} - Amount of bytes to shift
19
+ * @returns {number} - The shifted byte
20
+ */
21
+ shift = (amount = 1) =>
22
+ {
23
+ this.currentIndex += amount;
24
+ return this[this.currentIndex - amount];
25
+ };
26
+ }