@marmooo/midy 0.4.0 → 0.4.1

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.
@@ -1 +1 @@
1
- {"version":3,"file":"midy-GM1.d.ts","sourceRoot":"","sources":["../src/midy-GM1.js"],"names":[],"mappings":"AA6FA;IA0BE;;;;;;;;;;;MAWE;IAEF,+BAeC;IArDD,aAAa;IACb,oBAAiB;IACjB,qBAAmB;IACnB,kBAAc;IACd,0BAAwB;IACxB,kBAAc;IACd,mBAAiB;IACjB,kBAAc;IACd,mBAAe;IACf,kBAAgB;IAChB,0BAAuD;IACvD,4BAAyB;IACzB,0BAAuB;IACvB,kCAA+B;IAC/B,mBAAkB;IAClB,mBAAkB;IAClB,kBAAiB;IACjB,oBAAmB;IACnB,mBAAkB;IAClB,iBAAY;IACZ,gBAAc;IACd,oBAAkB;IAClB,sBAAwB;IACxB,2BAAqC;IAgBnC,kBAAgC;IAChC,kBAA8C;IAC9C,eAAwD;IACxD,qBAGE;IACF,uBAAmD;IACnD;;;;;;;;;;;MAA2D;IAC3D,6BAA+D;IAC/D,gBAAiD;IAMnD,mCASC;IAED,2DAYC;IAED,yCAmBC;IAED,oCASC;IAED,sBAoCC;IAED,8DAWC;IAED;;;;MAeC;IAED,yCAaC;IAED,kDAUC;IAED,4DASC;IAED,yEAqDC;IAED,mCAOC;IAED,uBASC;IAED,yDA2BC;IAED,2BAwCC;IAED,uDAEC;IAED,wDAEC;IAED,qCAKC;IAED;;;MAwDC;IAED,kGAeC;IAED,mGAeC;IAED,wEAMC;IAED,uBAMC;IAED,sBAKC;IAED,uBAQC;IAED,wBAKC;IAED,0BAKC;IAED,wBAOC;IAED,sBAIC;IAED,yDAQC;IAED,yEASC;IAED,2BAEC;IAED,8BAEC;IAED,8BAEC;IAED,4BAEC;IAED,qCAMC;IAED,2DAIC;IAED,+DAIC;IAED,sDAeC;IAED,qDAoBC;IAED,6CAIC;IAED,sDAsBC;IAED,kEAoBC;IAED,4GAkCC;IAED,uEAmCC;IAED,0EAiBC;IAED,oEASC;IAED,0FAwBC;IAED,gCASC;IAED,iEAqBC;IAED,4FAmBC;IAED,6CAUC;IAED,qDAUC;IAED,sFAeC;IAED,+BAmBC;IAED,kDAOC;IAED,uGA2BC;IAED,mFAGC;IAED,wFAGC;IAED,sEAUC;IAED,mEAWC;IAED,wDAKC;IAED,sDAOC;IAED,mDAMC;IAED,kDAKC;IAED;;;;;;;;;;;MAiCC;IAED,oFAMC;IAED,6EA2BC;IAED,qCAeC;IAED,+FAWC;IAED,wDASC;IAED,iFAKC;IAED,oEAKC;IAED;;;MAMC;IAED,8DAKC;IAED,4EAKC;IAED,sEAGC;IAED,2DAUC;IAED,yEAWC;IAED,kFAeC;IAED,2DAMC;IAED,uDAkBC;IAED,gDAEC;IAED,gDAEC;IAED,sEAGC;IAED,qEAKC;IAED,2EAUC;IAED,iEAMC;IAED,uEAQC;IAED,mEAKC;IAED,yEAQC;IAED,gFAGC;IAED,6CAqBC;IAGD,8EAgCC;IAED,gFAGC;IAED,+EAgBC;IAED,qCASC;IAED,4EAaC;IAED,4DAGC;IAED,qDAKC;IAED,gDAYC;IAGD,6DAgBC;CACF"}
1
+ {"version":3,"file":"midy-GM1.d.ts","sourceRoot":"","sources":["../src/midy-GM1.js"],"names":[],"mappings":"AA6FA;IA0BE;;;;;;;;;;;MAWE;IAEF,+BAeC;IArDD,aAAa;IACb,oBAAiB;IACjB,qBAAmB;IACnB,kBAAc;IACd,0BAAwB;IACxB,kBAAc;IACd,mBAAiB;IACjB,kBAAc;IACd,mBAAe;IACf,kBAAgB;IAChB,0BAAuD;IACvD,4BAAyB;IACzB,0BAAuB;IACvB,kCAA+B;IAC/B,mBAAkB;IAClB,mBAAkB;IAClB,kBAAiB;IACjB,oBAAmB;IACnB,mBAAkB;IAClB,iBAAY;IACZ,gBAAc;IACd,oBAAkB;IAClB,sBAAwB;IACxB,2BAAqC;IAgBnC,kBAAgC;IAChC,kBAA8C;IAC9C,eAAwD;IACxD,qBAGE;IACF,uBAAmD;IACnD;;;;;;;;;;;MAA2D;IAC3D,6BAA+D;IAC/D,gBAAiD;IAMnD,mCASC;IAED,2DAYC;IAED,yCAmBC;IAED,oCASC;IAED,sBAoCC;IAED,8DAWC;IAED;;;;MAeC;IAED,yCAaC;IAED,kDASC;IAED,4DASC;IAED,yEAoDC;IAED,mCAOC;IAED,uBASC;IAED,yDA2BC;IAED,2BA8CC;IAED,uDAEC;IAED,wDAEC;IAED,qCAKC;IAED;;;MAwDC;IAED,kGAeC;IAED,mGAeC;IAED,wEAMC;IAED,uBAMC;IAED,sBAKC;IAED,uBAQC;IAED,wBAKC;IAED,0BAKC;IAED,wBAOC;IAED,sBAIC;IAED,yDAQC;IAED,yEASC;IAED,2BAEC;IAED,8BAEC;IAED,8BAEC;IAED,4BAEC;IAED,qCAMC;IAED,2DAIC;IAED,+DAIC;IAED,sDAeC;IAED,qDAoBC;IAED,6CAIC;IAED,sDAsBC;IAED,kEAoBC;IAED,4GAkCC;IAED,uEAwCC;IAED,0EAiBC;IAED,oEASC;IAED,0FAwBC;IAED,gCASC;IAED,iEAqBC;IAED,gHAqBC;IAED,6CAUC;IAED,qDAUC;IAED,4GAeC;IAED,+BAmBC;IAED,kDAOC;IAED,sGA2BC;IAED,mFAGC;IAED,wFAGC;IAED,sEAUC;IAED,mEAYC;IAED,wDAKC;IAED,sDAOC;IAED,mDAMC;IAED,kDAKC;IAED;;;;;;;;;;;MAiCC;IAED,oFAMC;IAED,6EA2BC;IAED,qCAeC;IAED,+FAWC;IAED,wDAUC;IAED,iFAKC;IAED,oEAKC;IAED;;;MAMC;IAED,8DAKC;IAED,4EAKC;IAED,sEAGC;IAED,2DAUC;IAED,yEAWC;IAED,kFAeC;IAED,2DAMC;IAED,uDAkBC;IAED,gDAEC;IAED,gDAEC;IAED,sEAGC;IAED,qEAKC;IAED,2EAUC;IAED,iEAMC;IAED,uEAQC;IAED,mEAKC;IAED,yEAQC;IAED,gFAGC;IAED,6CAqBC;IAGD,8EAgCC;IAED,gFAGC;IAED,+EAgBC;IAED,qCASC;IAED,4EAaC;IAED,4DAGC;IAED,qDAKC;IAED,gDAYC;IAGD,6DAgBC;CACF"}
@@ -89,11 +89,11 @@ const defaultControllerState = {
89
89
  pitchWheel: { type: 14, defaultValue: 8192 / 16383 },
90
90
  pitchWheelSensitivity: { type: 16, defaultValue: 2 / 128 },
91
91
  link: { type: 127, defaultValue: 0 },
92
- modulationDepth: { type: 128 + 1, defaultValue: 0 },
92
+ modulationDepthMSB: { type: 128 + 1, defaultValue: 0 },
93
93
  // dataMSB: { type: 128 + 6, defaultValue: 0, },
94
- volume: { type: 128 + 7, defaultValue: 100 / 127 },
95
- pan: { type: 128 + 10, defaultValue: 64 / 127 },
96
- expression: { type: 128 + 11, defaultValue: 1 },
94
+ volumeMSB: { type: 128 + 7, defaultValue: 100 / 127 },
95
+ panMSB: { type: 128 + 10, defaultValue: 64 / 127 },
96
+ expressionMSB: { type: 128 + 11, defaultValue: 1 },
97
97
  // dataLSB: { type: 128 + 38, defaultValue: 0, },
98
98
  sustainPedal: { type: 128 + 64, defaultValue: 0 },
99
99
  // rpnLSB: { type: 128 + 100, defaultValue: 127 },
@@ -413,7 +413,7 @@ class MidyGM1 {
413
413
  return soundFontIndex * (2 ** 32) + (instrument << 16) + sampleID;
414
414
  }
415
415
  createChannelAudioNodes(audioContext) {
416
- const { gainLeft, gainRight } = this.panToGain(defaultControllerState.pan.defaultValue);
416
+ const { gainLeft, gainRight } = this.panToGain(defaultControllerState.panMSB.defaultValue);
417
417
  const gainL = new GainNode(audioContext, { gain: gainLeft });
418
418
  const gainR = new GainNode(audioContext, { gain: gainRight });
419
419
  const merger = new ChannelMergerNode(audioContext, { numberOfInputs: 2 });
@@ -441,10 +441,9 @@ class MidyGM1 {
441
441
  return channels;
442
442
  }
443
443
  async createAudioBuffer(voiceParams) {
444
- const sample = voiceParams.sample;
445
- const sampleStart = voiceParams.start;
446
- const sampleEnd = sample.data.length + voiceParams.end;
447
- const audioBuffer = await sample.toAudioBuffer(this.audioContext, sampleStart, sampleEnd);
444
+ const { sample, start, end } = voiceParams;
445
+ const sampleEnd = sample.data.length + end;
446
+ const audioBuffer = await sample.toAudioBuffer(this.audioContext, start, sampleEnd);
448
447
  return audioBuffer;
449
448
  }
450
449
  createBufferSource(voiceParams, audioBuffer) {
@@ -472,9 +471,7 @@ class MidyGM1 {
472
471
  await this.noteOn(event.channel, event.noteNumber, event.velocity, startTime);
473
472
  break;
474
473
  case "noteOff": {
475
- const notePromise = this.noteOff(event.channel, event.noteNumber, event.velocity, startTime, false);
476
- if (notePromise)
477
- this.notePromises.push(notePromise);
474
+ this.noteOff(event.channel, event.noteNumber, event.velocity, startTime, false);
478
475
  break;
479
476
  }
480
477
  case "controller":
@@ -568,6 +565,12 @@ class MidyGM1 {
568
565
  const waitTime = now + this.noteCheckInterval;
569
566
  await this.scheduleTask(() => { }, waitTime);
570
567
  }
568
+ if (this.timeline.length <= queueIndex) {
569
+ const now = this.audioContext.currentTime;
570
+ await this.stopNotes(0, true, now);
571
+ await this.audioContext.suspend();
572
+ finished = true;
573
+ }
571
574
  if (finished) {
572
575
  this.notePromises = [];
573
576
  this.resetAllStates();
@@ -907,7 +910,13 @@ class MidyGM1 {
907
910
  }
908
911
  note.bufferSource.connect(note.filterNode);
909
912
  note.filterNode.connect(note.volumeEnvelopeNode);
910
- note.bufferSource.start(startTime);
913
+ if (voiceParams.sample.type === "compressed") {
914
+ const offset = voiceParams.start / audioBuffer.sampleRate;
915
+ note.bufferSource.start(startTime, offset);
916
+ }
917
+ else {
918
+ note.bufferSource.start(startTime);
919
+ }
911
920
  return note;
912
921
  }
913
922
  handleExclusiveClass(note, channelNumber, startTime) {
@@ -1009,7 +1018,9 @@ class MidyGM1 {
1009
1018
  }
1010
1019
  note.ending = true;
1011
1020
  this.setNoteIndex(channel, index);
1012
- this.releaseNote(channel, note, endTime);
1021
+ const promise = this.releaseNote(channel, note, endTime);
1022
+ this.notePromises.push(promise);
1023
+ return promise;
1013
1024
  }
1014
1025
  setNoteIndex(channel, index) {
1015
1026
  let allEnds = true;
@@ -1107,11 +1118,12 @@ class MidyGM1 {
1107
1118
  setModLfoToPitch(channel, note, scheduleTime) {
1108
1119
  if (note.modulationDepth) {
1109
1120
  const modLfoToPitch = note.voiceParams.modLfoToPitch;
1110
- const baseDepth = Math.abs(modLfoToPitch) + channel.state.modulationDepth;
1111
- const modulationDepth = baseDepth * Math.sign(modLfoToPitch);
1121
+ const baseDepth = Math.abs(modLfoToPitch) +
1122
+ channel.state.modulationDepthMSB;
1123
+ const depth = baseDepth * Math.sign(modLfoToPitch);
1112
1124
  note.modulationDepth.gain
1113
1125
  .cancelScheduledValues(scheduleTime)
1114
- .setValueAtTime(modulationDepth, scheduleTime);
1126
+ .setValueAtTime(depth, scheduleTime);
1115
1127
  }
1116
1128
  else {
1117
1129
  this.startModulation(channel, note, scheduleTime);
@@ -1148,18 +1160,18 @@ class MidyGM1 {
1148
1160
  createVoiceParamsHandlers() {
1149
1161
  return {
1150
1162
  modLfoToPitch: (channel, note, scheduleTime) => {
1151
- if (0 < channel.state.modulationDepth) {
1163
+ if (0 < channel.state.modulationDepthMSB) {
1152
1164
  this.setModLfoToPitch(channel, note, scheduleTime);
1153
1165
  }
1154
1166
  },
1155
1167
  vibLfoToPitch: (_channel, _note, _scheduleTime) => { },
1156
1168
  modLfoToFilterFc: (channel, note, scheduleTime) => {
1157
- if (0 < channel.state.modulationDepth) {
1169
+ if (0 < channel.state.modulationDepthMSB) {
1158
1170
  this.setModLfoToFilterFc(note, scheduleTime);
1159
1171
  }
1160
1172
  },
1161
1173
  modLfoToVolume: (channel, note, scheduleTime) => {
1162
- if (0 < channel.state.modulationDepth) {
1174
+ if (0 < channel.state.modulationDepthMSB) {
1163
1175
  this.setModLfoToVolume(note, scheduleTime);
1164
1176
  }
1165
1177
  },
@@ -1171,7 +1183,7 @@ class MidyGM1 {
1171
1183
  }
1172
1184
  },
1173
1185
  freqModLFO: (_channel, note, scheduleTime) => {
1174
- if (0 < channel.state.modulationDepth) {
1186
+ if (0 < channel.state.modulationDepthMSB) {
1175
1187
  this.setFreqModLFO(note, scheduleTime);
1176
1188
  }
1177
1189
  },
@@ -1246,7 +1258,8 @@ class MidyGM1 {
1246
1258
  }
1247
1259
  }
1248
1260
  updateModulation(channel, scheduleTime) {
1249
- const depth = channel.state.modulationDepth * channel.modulationDepthRange;
1261
+ const depth = channel.state.modulationDepthMSB *
1262
+ channel.modulationDepthRange;
1250
1263
  this.processScheduledNotes(channel, (note) => {
1251
1264
  if (note.modulationDepth) {
1252
1265
  note.modulationDepth.gain.setValueAtTime(depth, scheduleTime);
@@ -1259,13 +1272,13 @@ class MidyGM1 {
1259
1272
  setModulationDepth(channelNumber, modulation, scheduleTime) {
1260
1273
  const channel = this.channels[channelNumber];
1261
1274
  scheduleTime ??= this.audioContext.currentTime;
1262
- channel.state.modulationDepth = modulation / 127;
1275
+ channel.state.modulationDepthMSB = modulation / 127;
1263
1276
  this.updateModulation(channel, scheduleTime);
1264
1277
  }
1265
1278
  setVolume(channelNumber, volume, scheduleTime) {
1266
1279
  scheduleTime ??= this.audioContext.currentTime;
1267
1280
  const channel = this.channels[channelNumber];
1268
- channel.state.volume = volume / 127;
1281
+ channel.state.volumeMSB = volume / 127;
1269
1282
  this.updateChannelVolume(channel, scheduleTime);
1270
1283
  }
1271
1284
  panToGain(pan) {
@@ -1278,13 +1291,13 @@ class MidyGM1 {
1278
1291
  setPan(channelNumber, pan, scheduleTime) {
1279
1292
  scheduleTime ??= this.audioContext.currentTime;
1280
1293
  const channel = this.channels[channelNumber];
1281
- channel.state.pan = pan / 127;
1294
+ channel.state.panMSB = pan / 127;
1282
1295
  this.updateChannelVolume(channel, scheduleTime);
1283
1296
  }
1284
1297
  setExpression(channelNumber, expression, scheduleTime) {
1285
1298
  scheduleTime ??= this.audioContext.currentTime;
1286
1299
  const channel = this.channels[channelNumber];
1287
- channel.state.expression = expression / 127;
1300
+ channel.state.expressionMSB = expression / 127;
1288
1301
  this.updateChannelVolume(channel, scheduleTime);
1289
1302
  }
1290
1303
  dataEntryLSB(channelNumber, value, scheduleTime) {
@@ -1293,8 +1306,8 @@ class MidyGM1 {
1293
1306
  }
1294
1307
  updateChannelVolume(channel, scheduleTime) {
1295
1308
  const state = channel.state;
1296
- const volume = state.volume * state.expression;
1297
- const { gainLeft, gainRight } = this.panToGain(state.pan);
1309
+ const volume = state.volumeMSB * state.expressionMSB;
1310
+ const { gainLeft, gainRight } = this.panToGain(state.panMSB);
1298
1311
  channel.gainL.gain
1299
1312
  .cancelScheduledValues(scheduleTime)
1300
1313
  .setValueAtTime(volume * gainLeft, scheduleTime);
@@ -1442,8 +1455,8 @@ class MidyGM1 {
1442
1455
  resetAllControllers(channelNumber, _value, scheduleTime) {
1443
1456
  const keys = [
1444
1457
  "pitchWheel",
1445
- "expression",
1446
- "modulationDepth",
1458
+ "expressionMSB",
1459
+ "modulationDepthMSB",
1447
1460
  "sustainPedal",
1448
1461
  ];
1449
1462
  const channel = this.channels[channelNumber];
@@ -182,11 +182,11 @@ export class MidyGM2 {
182
182
  noteOn(channelNumber: any, noteNumber: any, velocity: any, startTime: any): Promise<void>;
183
183
  disconnectNote(note: any): void;
184
184
  releaseNote(channel: any, note: any, endTime: any): Promise<any>;
185
- noteOff(channelNumber: any, noteNumber: any, velocity: any, endTime: any, force: any): void;
185
+ noteOff(channelNumber: any, noteNumber: any, velocity: any, endTime: any, force: any): Promise<any> | undefined;
186
186
  setNoteIndex(channel: any, index: any): void;
187
187
  findNoteOffIndex(channel: any, noteNumber: any): any;
188
- releaseSustainPedal(channelNumber: any, halfVelocity: any, scheduleTime: any): void[];
189
- releaseSostenutoPedal(channelNumber: any, halfVelocity: any, scheduleTime: any): void[];
188
+ releaseSustainPedal(channelNumber: any, halfVelocity: any, scheduleTime: any): (Promise<any> | undefined)[];
189
+ releaseSostenutoPedal(channelNumber: any, halfVelocity: any, scheduleTime: any): (Promise<any> | undefined)[];
190
190
  createMessageHandlers(): any[];
191
191
  handleMessage(data: any, scheduleTime: any): void;
192
192
  activeSensing(): void;
@@ -1 +1 @@
1
- {"version":3,"file":"midy-GM2.d.ts","sourceRoot":"","sources":["../src/midy-GM2.js"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"midy-GM2.d.ts","sourceRoot":"","sources":["../src/midy-GM2.js"],"names":[],"mappings":"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"}
@@ -154,12 +154,12 @@ const defaultControllerState = {
154
154
  pitchWheelSensitivity: { type: 16, defaultValue: 2 / 128 },
155
155
  link: { type: 127, defaultValue: 0 },
156
156
  // bankMSB: { type: 128 + 0, defaultValue: 121, },
157
- modulationDepth: { type: 128 + 1, defaultValue: 0 },
158
- portamentoTime: { type: 128 + 5, defaultValue: 0 },
157
+ modulationDepthMSB: { type: 128 + 1, defaultValue: 0 },
158
+ portamentoTimeMSB: { type: 128 + 5, defaultValue: 0 },
159
159
  // dataMSB: { type: 128 + 6, defaultValue: 0, },
160
- volume: { type: 128 + 7, defaultValue: 100 / 127 },
161
- pan: { type: 128 + 10, defaultValue: 64 / 127 },
162
- expression: { type: 128 + 11, defaultValue: 1 },
160
+ volumeMSB: { type: 128 + 7, defaultValue: 100 / 127 },
161
+ panMSB: { type: 128 + 10, defaultValue: 64 / 127 },
162
+ expressionMSB: { type: 128 + 11, defaultValue: 1 },
163
163
  // bankLSB: { type: 128 + 32, defaultValue: 0, },
164
164
  // dataLSB: { type: 128 + 38, defaultValue: 0, },
165
165
  sustainPedal: { type: 128 + 64, defaultValue: 0 },
@@ -549,7 +549,7 @@ class MidyGM2 {
549
549
  return soundFontIndex * (2 ** 32) + (instrument << 16) + sampleID;
550
550
  }
551
551
  createChannelAudioNodes(audioContext) {
552
- const { gainLeft, gainRight } = this.panToGain(defaultControllerState.pan.defaultValue);
552
+ const { gainLeft, gainRight } = this.panToGain(defaultControllerState.panMSB.defaultValue);
553
553
  const gainL = new GainNode(audioContext, { gain: gainLeft });
554
554
  const gainR = new GainNode(audioContext, { gain: gainRight });
555
555
  const merger = new ChannelMergerNode(audioContext, { numberOfInputs: 2 });
@@ -590,10 +590,9 @@ class MidyGM2 {
590
590
  return channels;
591
591
  }
592
592
  async createAudioBuffer(voiceParams) {
593
- const sample = voiceParams.sample;
594
- const sampleStart = voiceParams.start;
595
- const sampleEnd = sample.data.length + voiceParams.end;
596
- const audioBuffer = await sample.toAudioBuffer(this.audioContext, sampleStart, sampleEnd);
593
+ const { sample, start, end } = voiceParams;
594
+ const sampleEnd = sample.data.length + end;
595
+ const audioBuffer = await sample.toAudioBuffer(this.audioContext, start, sampleEnd);
597
596
  return audioBuffer;
598
597
  }
599
598
  isLoopDrum(channel, noteNumber) {
@@ -628,9 +627,7 @@ class MidyGM2 {
628
627
  await this.noteOn(event.channel, event.noteNumber, event.velocity, startTime);
629
628
  break;
630
629
  case "noteOff": {
631
- const notePromise = this.noteOff(event.channel, event.noteNumber, event.velocity, startTime, false);
632
- if (notePromise)
633
- this.notePromises.push(notePromise);
630
+ this.noteOff(event.channel, event.noteNumber, event.velocity, startTime, false);
634
631
  break;
635
632
  }
636
633
  case "controller":
@@ -734,6 +731,12 @@ class MidyGM2 {
734
731
  const waitTime = now + this.noteCheckInterval;
735
732
  await this.scheduleTask(() => { }, waitTime);
736
733
  }
734
+ if (this.timeline.length <= queueIndex) {
735
+ const now = this.audioContext.currentTime;
736
+ await this.stopNotes(0, true, now);
737
+ await this.audioContext.suspend();
738
+ finished = true;
739
+ }
737
740
  if (finished) {
738
741
  this.notePromises = [];
739
742
  this.resetAllStates();
@@ -1142,7 +1145,7 @@ class MidyGM2 {
1142
1145
  }
1143
1146
  getPortamentoTime(channel, note) {
1144
1147
  const deltaSemitone = Math.abs(note.noteNumber - note.portamentoNoteNumber);
1145
- const value = Math.ceil(channel.state.portamentoTime * 127);
1148
+ const value = Math.ceil(channel.state.portamentoTimeMSB * 127);
1146
1149
  return deltaSemitone / this.getPitchIncrementSpeed(value) / 10;
1147
1150
  }
1148
1151
  getPitchIncrementSpeed(value) {
@@ -1401,7 +1404,7 @@ class MidyGM2 {
1401
1404
  if (0 < state.vibratoDepth) {
1402
1405
  this.startVibrato(channel, note, now);
1403
1406
  }
1404
- if (0 < state.modulationDepth) {
1407
+ if (0 < state.modulationDepthMSB) {
1405
1408
  this.startModulation(channel, note, now);
1406
1409
  }
1407
1410
  if (channel.mono && channel.currentBufferSource) {
@@ -1412,7 +1415,13 @@ class MidyGM2 {
1412
1415
  note.filterNode.connect(note.volumeEnvelopeNode);
1413
1416
  this.setChorusSend(channel, note, now);
1414
1417
  this.setReverbSend(channel, note, now);
1415
- note.bufferSource.start(startTime);
1418
+ if (voiceParams.sample.type === "compressed") {
1419
+ const offset = voiceParams.start / audioBuffer.sampleRate;
1420
+ note.bufferSource.start(startTime, offset);
1421
+ }
1422
+ else {
1423
+ note.bufferSource.start(startTime);
1424
+ }
1416
1425
  return note;
1417
1426
  }
1418
1427
  handleExclusiveClass(note, channelNumber, startTime) {
@@ -1570,7 +1579,9 @@ class MidyGM2 {
1570
1579
  }
1571
1580
  note.ending = true;
1572
1581
  this.setNoteIndex(channel, index);
1573
- this.releaseNote(channel, note, endTime);
1582
+ const promise = this.releaseNote(channel, note, endTime);
1583
+ this.notePromises.push(promise);
1584
+ return promise;
1574
1585
  }
1575
1586
  setNoteIndex(channel, index) {
1576
1587
  let allEnds = true;
@@ -1702,7 +1713,8 @@ class MidyGM2 {
1702
1713
  if (note.modulationDepth) {
1703
1714
  const modLfoToPitch = note.voiceParams.modLfoToPitch +
1704
1715
  this.getLFOPitchDepth(channel, note);
1705
- const baseDepth = Math.abs(modLfoToPitch) + channel.state.modulationDepth;
1716
+ const baseDepth = Math.abs(modLfoToPitch) +
1717
+ channel.state.modulationDepthMSB;
1706
1718
  const depth = baseDepth * Math.sign(modLfoToPitch);
1707
1719
  note.modulationDepth.gain
1708
1720
  .cancelScheduledValues(scheduleTime)
@@ -1834,7 +1846,7 @@ class MidyGM2 {
1834
1846
  createVoiceParamsHandlers() {
1835
1847
  return {
1836
1848
  modLfoToPitch: (channel, note, scheduleTime) => {
1837
- if (0 < channel.state.modulationDepth) {
1849
+ if (0 < channel.state.modulationDepthMSB) {
1838
1850
  this.setModLfoToPitch(channel, note, scheduleTime);
1839
1851
  }
1840
1852
  },
@@ -1844,12 +1856,12 @@ class MidyGM2 {
1844
1856
  }
1845
1857
  },
1846
1858
  modLfoToFilterFc: (channel, note, scheduleTime) => {
1847
- if (0 < channel.state.modulationDepth) {
1859
+ if (0 < channel.state.modulationDepthMSB) {
1848
1860
  this.setModLfoToFilterFc(channel, note, scheduleTime);
1849
1861
  }
1850
1862
  },
1851
1863
  modLfoToVolume: (channel, note, scheduleTime) => {
1852
- if (0 < channel.state.modulationDepth) {
1864
+ if (0 < channel.state.modulationDepthMSB) {
1853
1865
  this.setModLfoToVolume(channel, note, scheduleTime);
1854
1866
  }
1855
1867
  },
@@ -1860,12 +1872,12 @@ class MidyGM2 {
1860
1872
  this.setReverbSend(channel, note, scheduleTime);
1861
1873
  },
1862
1874
  delayModLFO: (_channel, note, _scheduleTime) => {
1863
- if (0 < channel.state.modulationDepth) {
1875
+ if (0 < channel.state.modulationDepthMSB) {
1864
1876
  this.setDelayModLFO(note);
1865
1877
  }
1866
1878
  },
1867
1879
  freqModLFO: (_channel, note, scheduleTime) => {
1868
- if (0 < channel.state.modulationDepth) {
1880
+ if (0 < channel.state.modulationDepthMSB) {
1869
1881
  this.setFreqModLFO(note, scheduleTime);
1870
1882
  }
1871
1883
  },
@@ -1967,7 +1979,8 @@ class MidyGM2 {
1967
1979
  this.channels[channelNumber].bankMSB = msb;
1968
1980
  }
1969
1981
  updateModulation(channel, scheduleTime) {
1970
- const depth = channel.state.modulationDepth * channel.modulationDepthRange;
1982
+ const depth = channel.state.modulationDepthMSB *
1983
+ channel.modulationDepthRange;
1971
1984
  this.processScheduledNotes(channel, (note) => {
1972
1985
  if (note.modulationDepth) {
1973
1986
  note.modulationDepth.gain.setValueAtTime(depth, scheduleTime);
@@ -1982,7 +1995,7 @@ class MidyGM2 {
1982
1995
  if (channel.isDrum)
1983
1996
  return;
1984
1997
  scheduleTime ??= this.audioContext.currentTime;
1985
- channel.state.modulationDepth = modulation / 127;
1998
+ channel.state.modulationDepthMSB = modulation / 127;
1986
1999
  this.updateModulation(channel, scheduleTime);
1987
2000
  }
1988
2001
  updatePortamento(channel, scheduleTime) {
@@ -2004,9 +2017,9 @@ class MidyGM2 {
2004
2017
  });
2005
2018
  }
2006
2019
  setPortamentoTime(channelNumber, portamentoTime, scheduleTime) {
2007
- const channel = this.channels[channelNumber];
2008
2020
  scheduleTime ??= this.audioContext.currentTime;
2009
- channel.state.portamentoTime = portamentoTime / 127;
2021
+ const channel = this.channels[channelNumber];
2022
+ channel.state.portamentoTimeMSB = portamentoTime / 127;
2010
2023
  if (channel.isDrum)
2011
2024
  return;
2012
2025
  this.updatePortamento(channel, scheduleTime);
@@ -2014,7 +2027,7 @@ class MidyGM2 {
2014
2027
  setVolume(channelNumber, volume, scheduleTime) {
2015
2028
  scheduleTime ??= this.audioContext.currentTime;
2016
2029
  const channel = this.channels[channelNumber];
2017
- channel.state.volume = volume / 127;
2030
+ channel.state.volumeMSB = volume / 127;
2018
2031
  if (channel.isDrum) {
2019
2032
  for (let i = 0; i < 128; i++) {
2020
2033
  this.updateKeyBasedVolume(channel, i, scheduleTime);
@@ -2034,7 +2047,7 @@ class MidyGM2 {
2034
2047
  setPan(channelNumber, pan, scheduleTime) {
2035
2048
  scheduleTime ??= this.audioContext.currentTime;
2036
2049
  const channel = this.channels[channelNumber];
2037
- channel.state.pan = pan / 127;
2050
+ channel.state.panMSB = pan / 127;
2038
2051
  if (channel.isDrum) {
2039
2052
  for (let i = 0; i < 128; i++) {
2040
2053
  this.updateKeyBasedVolume(channel, i, scheduleTime);
@@ -2047,7 +2060,7 @@ class MidyGM2 {
2047
2060
  setExpression(channelNumber, expression, scheduleTime) {
2048
2061
  scheduleTime ??= this.audioContext.currentTime;
2049
2062
  const channel = this.channels[channelNumber];
2050
- channel.state.expression = expression / 127;
2063
+ channel.state.expressionMSB = expression / 127;
2051
2064
  this.updateChannelVolume(channel, scheduleTime);
2052
2065
  }
2053
2066
  setBankLSB(channelNumber, lsb) {
@@ -2059,8 +2072,8 @@ class MidyGM2 {
2059
2072
  }
2060
2073
  updateChannelVolume(channel, scheduleTime) {
2061
2074
  const state = channel.state;
2062
- const volume = state.volume * state.expression;
2063
- const { gainLeft, gainRight } = this.panToGain(state.pan);
2075
+ const volume = state.volumeMSB * state.expressionMSB;
2076
+ const { gainLeft, gainRight } = this.panToGain(state.panMSB);
2064
2077
  channel.gainL.gain
2065
2078
  .cancelScheduledValues(scheduleTime)
2066
2079
  .setValueAtTime(volume * gainLeft, scheduleTime);
@@ -2074,8 +2087,8 @@ class MidyGM2 {
2074
2087
  return;
2075
2088
  const gainR = channel.keyBasedGainRs[keyNumber];
2076
2089
  const state = channel.state;
2077
- const defaultVolume = state.volume * state.expression;
2078
- const defaultPan = state.pan;
2090
+ const defaultVolume = state.volumeMSB * state.expressionMSB;
2091
+ const defaultPan = state.panMSB;
2079
2092
  const keyBasedVolume = this.getKeyBasedValue(channel, keyNumber, 7);
2080
2093
  const volume = (0 <= keyBasedVolume)
2081
2094
  ? defaultVolume * keyBasedVolume / 64
@@ -2326,8 +2339,8 @@ class MidyGM2 {
2326
2339
  const keys = [
2327
2340
  "channelPressure",
2328
2341
  "pitchWheel",
2329
- "expression",
2330
- "modulationDepth",
2342
+ "expressionMSB",
2343
+ "modulationDepthMSB",
2331
2344
  "sustainPedal",
2332
2345
  "portamento",
2333
2346
  "sostenutoPedal",
@@ -112,13 +112,13 @@ export class MidyGMLite {
112
112
  noteOn(channelNumber: any, noteNumber: any, velocity: any, startTime: any): Promise<void>;
113
113
  disconnectNote(note: any): void;
114
114
  releaseNote(channel: any, note: any, endTime: any): Promise<any>;
115
- noteOff(channelNumber: any, noteNumber: any, velocity: any, endTime: any, force: any): void;
115
+ noteOff(channelNumber: any, noteNumber: any, velocity: any, endTime: any, force: any): Promise<any> | undefined;
116
116
  setNoteIndex(channel: any, index: any): void;
117
117
  findNoteOffIndex(channel: any, noteNumber: any): any;
118
- releaseSustainPedal(channelNumber: any, halfVelocity: any, scheduleTime: any): void[];
118
+ releaseSustainPedal(channelNumber: any, halfVelocity: any, scheduleTime: any): (Promise<any> | undefined)[];
119
119
  createMessageHandlers(): any[];
120
120
  handleMessage(data: any, scheduleTime: any): void;
121
- handleChannelMessage(statusByte: any, data1: any, data2: any, scheduleTime: any): void | Promise<void>;
121
+ handleChannelMessage(statusByte: any, data1: any, data2: any, scheduleTime: any): void | Promise<any>;
122
122
  setProgramChange(channelNumber: any, programNumber: any, _scheduleTime: any): void;
123
123
  handlePitchBendMessage(channelNumber: any, lsb: any, msb: any, scheduleTime: any): void;
124
124
  setPitchBend(channelNumber: any, value: any, scheduleTime: any): void;
@@ -1 +1 @@
1
- {"version":3,"file":"midy-GMLite.d.ts","sourceRoot":"","sources":["../src/midy-GMLite.js"],"names":[],"mappings":"AA2GA;IA6BE;;;;;;;;;MASE;IAEF,+BAeC;IAtDD,aAAa;IACb,oBAAiB;IACjB,qBAAmB;IACnB,kBAAc;IACd,0BAAwB;IACxB,kBAAc;IACd,mBAAiB;IACjB,kBAAc;IACd,mBAAe;IACf,kBAAgB;IAChB,0BAAuD;IACvD,4BAAyB;IACzB,0BAAuB;IACvB,kCAA+B;IAC/B,mBAAkB;IAClB,mBAAkB;IAClB,kBAAiB;IACjB,oBAAmB;IACnB,mBAAkB;IAClB,iBAAY;IACZ,gBAAc;IACd,oBAAkB;IAClB,sBAAwB;IACxB,2BAAqC;IACrC,+BAEE;IAcA,kBAAgC;IAChC,kBAA8C;IAC9C,eAAwD;IACxD,qBAGE;IACF,uBAAmD;IACnD;;;;;;;;;;;MAA2D;IAC3D,6BAA+D;IAC/D,gBAAiD;IAMnD,mCASC;IAED,2DAYC;IAED,yCAmBC;IAED,oCASC;IAED,sBAoCC;IAED,8DAWC;IAED;;;;MAeC;IAED,yCAaC;IAED,kDAUC;IAED,0EAUC;IAED,yEAqDC;IAED,mCAOC;IAED,uBASC;IAED,yDA2BC;IAED,2BAwCC;IAED,uDAEC;IAED,wDAEC;IAED,qCAKC;IAED;;;MAwDC;IAED,kGAeC;IAED,mGAeC;IAED,wEAMC;IAED,uBAMC;IAED,sBAKC;IAED,uBAQC;IAED,wBAKC;IAED,0BAKC;IAED,wBAOC;IAED,sBAIC;IAED,yDAQC;IAED,yEASC;IAED,2BAEC;IAED,8BAEC;IAED,8BAEC;IAED,4BAEC;IAED,wCAIC;IAED,2DAIC;IAED,+DAIC;IAED,sDAeC;IAED,qDAoBC;IAED,6CAIC;IAED,sDAsBC;IAED,kEAoBC;IAED,4GAkCC;IAED,uEAuCC;IAED,0EAiBC;IAED,8EAiBC;IAED,oEAUC;IAED,0FAwBC;IAED,gCASC;IAED,iEAqBC;IAED,4FAsBC;IAED,6CAUC;IAED,qDAUC;IAED,sFAeC;IAED,+BAmBC;IAED,kDAOC;IAED,uGA2BC;IAED,mFAGC;IAED,wFAGC;IAED,sEAUC;IAED,mEAWC;IAED,wDAKC;IAED,sDAOC;IAED,mDAMC;IAED,kDAKC;IAED;;;;;;;;;;;MAiCC;IAED,oFAMC;IAED,6EA2BC;IAED,qCAeC;IAED,+FAWC;IAED,wDASC;IAED,iFAKC;IAED,oEAKC;IAED;;;MAMC;IAED,8DAKC;IAED,4EAKC;IAED,sEAGC;IAED,2DAUC;IAED,yEAWC;IAED,kFAeC;IAED,uDAYC;IAED,gDAEC;IAED,gDAEC;IAED,sEAGC;IAED,qEAKC;IAED,2EAUC;IAED,gFAGC;IAED,6CAqBC;IAGD,8EAgCC;IAED,gFAGC;IAED,+EAgBC;IAED,qCASC;IAED,4EAaC;IAED,4DAGC;IAED,qDAKC;IAED,gDAYC;IAGD,6DAgBC;CACF"}
1
+ {"version":3,"file":"midy-GMLite.d.ts","sourceRoot":"","sources":["../src/midy-GMLite.js"],"names":[],"mappings":"AA2GA;IA6BE;;;;;;;;;MASE;IAEF,+BAeC;IAtDD,aAAa;IACb,oBAAiB;IACjB,qBAAmB;IACnB,kBAAc;IACd,0BAAwB;IACxB,kBAAc;IACd,mBAAiB;IACjB,kBAAc;IACd,mBAAe;IACf,kBAAgB;IAChB,0BAAuD;IACvD,4BAAyB;IACzB,0BAAuB;IACvB,kCAA+B;IAC/B,mBAAkB;IAClB,mBAAkB;IAClB,kBAAiB;IACjB,oBAAmB;IACnB,mBAAkB;IAClB,iBAAY;IACZ,gBAAc;IACd,oBAAkB;IAClB,sBAAwB;IACxB,2BAAqC;IACrC,+BAEE;IAcA,kBAAgC;IAChC,kBAA8C;IAC9C,eAAwD;IACxD,qBAGE;IACF,uBAAmD;IACnD;;;;;;;;;;;MAA2D;IAC3D,6BAA+D;IAC/D,gBAAiD;IAMnD,mCASC;IAED,2DAYC;IAED,yCAmBC;IAED,oCASC;IAED,sBAoCC;IAED,8DAWC;IAED;;;;MAeC;IAED,yCAaC;IAED,kDASC;IAED,0EAUC;IAED,yEAoDC;IAED,mCAOC;IAED,uBASC;IAED,yDA2BC;IAED,2BA8CC;IAED,uDAEC;IAED,wDAEC;IAED,qCAKC;IAED;;;MAwDC;IAED,kGAeC;IAED,mGAeC;IAED,wEAMC;IAED,uBAMC;IAED,sBAKC;IAED,uBAQC;IAED,wBAKC;IAED,0BAKC;IAED,wBAOC;IAED,sBAIC;IAED,yDAQC;IAED,yEASC;IAED,2BAEC;IAED,8BAEC;IAED,8BAEC;IAED,4BAEC;IAED,wCAIC;IAED,2DAIC;IAED,+DAIC;IAED,sDAeC;IAED,qDAoBC;IAED,6CAIC;IAED,sDAsBC;IAED,kEAoBC;IAED,4GAkCC;IAED,uEA4CC;IAED,0EAiBC;IAED,8EAiBC;IAED,oEAUC;IAED,0FAwBC;IAED,gCASC;IAED,iEAqBC;IAED,gHAwBC;IAED,6CAUC;IAED,qDAUC;IAED,4GAeC;IAED,+BAmBC;IAED,kDAOC;IAED,sGA2BC;IAED,mFAGC;IAED,wFAGC;IAED,sEAUC;IAED,mEAYC;IAED,wDAKC;IAED,sDAOC;IAED,mDAMC;IAED,kDAKC;IAED;;;;;;;;;;;MAiCC;IAED,oFAMC;IAED,6EA2BC;IAED,qCAeC;IAED,+FAWC;IAED,wDASC;IAED,iFAKC;IAED,oEAKC;IAED;;;MAMC;IAED,8DAKC;IAED,4EAKC;IAED,sEAGC;IAED,2DAUC;IAED,yEAWC;IAED,kFAeC;IAED,uDAYC;IAED,gDAEC;IAED,gDAEC;IAED,sEAGC;IAED,qEAKC;IAED,2EAUC;IAED,gFAGC;IAED,6CAqBC;IAGD,8EAgCC;IAED,gFAGC;IAED,+EAgBC;IAED,qCASC;IAED,4EAaC;IAED,4DAGC;IAED,qDAKC;IAED,gDAYC;IAGD,6DAgBC;CACF"}
@@ -102,11 +102,11 @@ const defaultControllerState = {
102
102
  pitchWheel: { type: 14, defaultValue: 8192 / 16383 },
103
103
  pitchWheelSensitivity: { type: 16, defaultValue: 2 / 128 },
104
104
  link: { type: 127, defaultValue: 0 },
105
- modulationDepth: { type: 128 + 1, defaultValue: 0 },
105
+ modulationDepthMSB: { type: 128 + 1, defaultValue: 0 },
106
106
  // dataMSB: { type: 128 + 6, defaultValue: 0, },
107
- volume: { type: 128 + 7, defaultValue: 100 / 127 },
108
- pan: { type: 128 + 10, defaultValue: 64 / 127 },
109
- expression: { type: 128 + 11, defaultValue: 1 },
107
+ volumeMSB: { type: 128 + 7, defaultValue: 100 / 127 },
108
+ panMSB: { type: 128 + 10, defaultValue: 64 / 127 },
109
+ expressionMSB: { type: 128 + 11, defaultValue: 1 },
110
110
  // dataLSB: { type: 128 + 38, defaultValue: 0, },
111
111
  sustainPedal: { type: 128 + 64, defaultValue: 0 },
112
112
  // rpnLSB: { type: 128 + 100, defaultValue: 127 },
@@ -432,7 +432,7 @@ class MidyGMLite {
432
432
  return soundFontIndex * (2 ** 32) + (instrument << 16) + sampleID;
433
433
  }
434
434
  createChannelAudioNodes(audioContext) {
435
- const { gainLeft, gainRight } = this.panToGain(defaultControllerState.pan.defaultValue);
435
+ const { gainLeft, gainRight } = this.panToGain(defaultControllerState.panMSB.defaultValue);
436
436
  const gainL = new GainNode(audioContext, { gain: gainLeft });
437
437
  const gainR = new GainNode(audioContext, { gain: gainRight });
438
438
  const merger = new ChannelMergerNode(audioContext, { numberOfInputs: 2 });
@@ -460,10 +460,9 @@ class MidyGMLite {
460
460
  return channels;
461
461
  }
462
462
  async createAudioBuffer(voiceParams) {
463
- const sample = voiceParams.sample;
464
- const sampleStart = voiceParams.start;
465
- const sampleEnd = sample.data.length + voiceParams.end;
466
- const audioBuffer = await sample.toAudioBuffer(this.audioContext, sampleStart, sampleEnd);
463
+ const { sample, start, end } = voiceParams;
464
+ const sampleEnd = sample.data.length + end;
465
+ const audioBuffer = await sample.toAudioBuffer(this.audioContext, start, sampleEnd);
467
466
  return audioBuffer;
468
467
  }
469
468
  createBufferSource(channel, voiceParams, audioBuffer) {
@@ -493,9 +492,7 @@ class MidyGMLite {
493
492
  await this.noteOn(event.channel, event.noteNumber, event.velocity, startTime);
494
493
  break;
495
494
  case "noteOff": {
496
- const notePromise = this.noteOff(event.channel, event.noteNumber, event.velocity, startTime, false);
497
- if (notePromise)
498
- this.notePromises.push(notePromise);
495
+ this.noteOff(event.channel, event.noteNumber, event.velocity, startTime, false);
499
496
  break;
500
497
  }
501
498
  case "controller":
@@ -589,6 +586,12 @@ class MidyGMLite {
589
586
  const waitTime = now + this.noteCheckInterval;
590
587
  await this.scheduleTask(() => { }, waitTime);
591
588
  }
589
+ if (this.timeline.length <= queueIndex) {
590
+ const now = this.audioContext.currentTime;
591
+ await this.stopNotes(0, true, now);
592
+ await this.audioContext.suspend();
593
+ finished = true;
594
+ }
592
595
  if (finished) {
593
596
  this.notePromises = [];
594
597
  this.resetAllStates();
@@ -921,12 +924,18 @@ class MidyGMLite {
921
924
  this.setFilterEnvelope(note, now);
922
925
  this.setPitchEnvelope(note, now);
923
926
  this.updateDetune(channel, note, now);
924
- if (0 < state.modulationDepth) {
927
+ if (0 < state.modulationDepthMSB) {
925
928
  this.startModulation(channel, note, now);
926
929
  }
927
930
  note.bufferSource.connect(note.filterNode);
928
931
  note.filterNode.connect(note.volumeEnvelopeNode);
929
- note.bufferSource.start(startTime);
932
+ if (voiceParams.sample.type === "compressed") {
933
+ const offset = voiceParams.start / audioBuffer.sampleRate;
934
+ note.bufferSource.start(startTime, offset);
935
+ }
936
+ else {
937
+ note.bufferSource.start(startTime);
938
+ }
930
939
  return note;
931
940
  }
932
941
  handleExclusiveClass(note, channelNumber, startTime) {
@@ -1048,7 +1057,9 @@ class MidyGMLite {
1048
1057
  }
1049
1058
  note.ending = true;
1050
1059
  this.setNoteIndex(channel, index);
1051
- this.releaseNote(channel, note, endTime);
1060
+ const promise = this.releaseNote(channel, note, endTime);
1061
+ this.notePromises.push(promise);
1062
+ return promise;
1052
1063
  }
1053
1064
  setNoteIndex(channel, index) {
1054
1065
  let allEnds = true;
@@ -1146,11 +1157,12 @@ class MidyGMLite {
1146
1157
  setModLfoToPitch(channel, note, scheduleTime) {
1147
1158
  if (note.modulationDepth) {
1148
1159
  const modLfoToPitch = note.voiceParams.modLfoToPitch;
1149
- const baseDepth = Math.abs(modLfoToPitch) + channel.state.modulationDepth;
1150
- const modulationDepth = baseDepth * Math.sign(modLfoToPitch);
1160
+ const baseDepth = Math.abs(modLfoToPitch) +
1161
+ channel.state.modulationDepthMSB;
1162
+ const depth = baseDepth * Math.sign(modLfoToPitch);
1151
1163
  note.modulationDepth.gain
1152
1164
  .cancelScheduledValues(scheduleTime)
1153
- .setValueAtTime(modulationDepth, scheduleTime);
1165
+ .setValueAtTime(depth, scheduleTime);
1154
1166
  }
1155
1167
  else {
1156
1168
  this.startModulation(channel, note, scheduleTime);
@@ -1187,18 +1199,18 @@ class MidyGMLite {
1187
1199
  createVoiceParamsHandlers() {
1188
1200
  return {
1189
1201
  modLfoToPitch: (channel, note, scheduleTime) => {
1190
- if (0 < channel.state.modulationDepth) {
1202
+ if (0 < channel.state.modulationDepthMSB) {
1191
1203
  this.setModLfoToPitch(channel, note, scheduleTime);
1192
1204
  }
1193
1205
  },
1194
1206
  vibLfoToPitch: (_channel, _note, _scheduleTime) => { },
1195
1207
  modLfoToFilterFc: (channel, note, scheduleTime) => {
1196
- if (0 < channel.state.modulationDepth) {
1208
+ if (0 < channel.state.modulationDepthMSB) {
1197
1209
  this.setModLfoToFilterFc(note, scheduleTime);
1198
1210
  }
1199
1211
  },
1200
1212
  modLfoToVolume: (channel, note, scheduleTime) => {
1201
- if (0 < channel.state.modulationDepth) {
1213
+ if (0 < channel.state.modulationDepthMSB) {
1202
1214
  this.setModLfoToVolume(note, scheduleTime);
1203
1215
  }
1204
1216
  },
@@ -1436,8 +1448,8 @@ class MidyGMLite {
1436
1448
  resetAllControllers(channelNumber, _value, scheduleTime) {
1437
1449
  const keys = [
1438
1450
  "pitchWheel",
1439
- "expression",
1440
- "modulationDepth",
1451
+ "expressionMSB",
1452
+ "modulationDepthMSB",
1441
1453
  "sustainPedal",
1442
1454
  ];
1443
1455
  const channel = this.channels[channelNumber];