From e02e7232f522ea0eb01fddade3db3c485a1eceff Mon Sep 17 00:00:00 2001 From: "[poww10s]" <[theironminer@gmail.com]> Date: Wed, 9 Sep 2020 04:04:52 -0400 Subject: [PATCH] create parse function --- src/App.js | 179 ++++++++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 172 insertions(+), 7 deletions(-) diff --git a/src/App.js b/src/App.js index 7428747..b79cfca 100644 --- a/src/App.js +++ b/src/App.js @@ -4,13 +4,178 @@ import "./App.css"; import FileIOComponent from "./components/FileIOComponent"; import MidiComponent from "./components/MidiComponent"; -import EditorComponent from "./components/EditorComponent"; +//import EditorComponent from "./components/EditorComponent"; + +import Parser from "binary-parser"; + +// converts SYSEX file to the dump format the system uses (and the implementation refers to) +function parse(binary) { + // check if the binary is a valid KORG-produced SYSEX file + if (binary.length !== 297) { + throw new Error("incorrect file length"); + } + if (binary[0] !== 0xf0) { + throw new Error("first byte is not SYSEX byte"); + } + if (binary[1] !== 0x42) { + throw new Error("manufacturer code is not KORG"); + } + if (binary[4] !== 0x40) { + throw new Error("not a program dump"); + } + if (binary[5] !== 0x00) { + // in all files found in the wild it's always zero + throw new Error("sixth byte is not zero"); + } + if (binary[binary.length - 1] !== 0xf7) { + throw new Error("last byte is does not end SYSEX message"); + } + + const trimmedBinary = binary.slice(5, -1); + // every eigth byte is padding, so we remove it + const unpaddedBinary = trimmedBinary.filter((el, idx) => idx % 8); + + const timbre = new Parser() + .uint8("midiChannel") + .bit2("assignMode") + .bit1("eg2Reset") + .bit1("eg1Reset") + .bit1("triggerMode") + .bit2("keyPriority") + .uint8("unisonDetune") + .uint8("pitchTune") + .uint8("pitchBendRange") + .uint8("pitchTranspose") + .uint8("pitchVibratoInt") + .uint8("osc1Wave") + .uint8("osc1WaveCtrl1") + .uint8("osc1WaveCtrl2") + .uint8("osc1DWGSWave") + .seek(1) + .bit2("ignore") + .bit2("osc2ModSelect") + .bit2("ignore") + .bit2("osc2Wave") + .uint8("osc2Semitone") + .uint8("osc2Tune") + .bit1("ignore") + .bit7("portamentoTime") + .uint8("osc1Level") + .uint8("osc2Level") + .uint8("noiseLevel") + .uint8("filterType") + .uint8("filterCutoff") + .uint8("filterResonance") + .uint8("filterEG1Intensity") + .uint8("filterVelocitySense") + .uint8("filterKeyboardTrack") + .uint8("ampLevel") + .uint8("ampPanpot") + .bit1("ignore") + .bit1("ampSW") + .bit6("ignore") + .bit1("ampDistortion") + .uint8("ampVelocitySense") + .uint8("ampKeyboardTrack") + .uint8("eg1Attack") + .uint8("eg1Decay") + .uint8("eg1Sustain") + .uint8("eg1Release") + .uint8("eg2Attack") + .uint8("eg2Decay") + .uint8("eg2Sustain") + .uint8("eg2Release") + .bit2("ignore") + .bit2("lfo1KeySync") + .bit2("ignore") + .bit2("lfo1Wave") + .uint8("lfo1Freq") + .bit1("lfo1TempoSync") + .bit2("ignore") + .bit5("lfo1SyncNote") + .bit2("ignore") + .bit2("lfo2KeySync") + .bit2("ignore") + .bit2("lfo2Wave") + .uint8("lfo2Freq") + .bit1("lfo2TempoSync") + .bit2("ignore") + .bit5("lfo2SyncNote") + .bit4("patch1Dest") + .bit4("patch1Src") + .uint8("patch1Intensity") + .bit4("patch2Dest") + .bit4("patch2Src") + .uint8("patch2Intensity") + .bit4("patch3Dest") + .bit4("patch3Src") + .uint8("patch3Intensity") + .bit4("patch4Dest") + .bit4("patch4Src") + .uint8("patch4Intensity"); + + const parser = new Parser() + .endianness("big") + .string("name", ["ASCII", 12]) + .seek(3) + .bit5("ignore") + .bit3("arpTriggerLength") + .bit8("arpTriggerPattern") + .bit2("ignore") + .bit2("voiceMode") + .bit4("ignore") + .bit4("scaleKey") + .bit4("scaleType") + .seek(1) + .bit1("delayFxSync") + .bit3("ignore") + .bit4("delayFXTimeBase") + .uint8("delayFXDelayTime") + .uint8("delayFXDepth") + .uint8("delayFXType") + .uint8("modFXLFOSpeed") + .uint8("modFXDepth") + .uint8("modFXType") + .uint8("eqHiFreq") + .uint8("eqHiGain") + .uint8("eqLowFreq") + .uint8("eqLowGain") + .uint8be("arpTempo") + .uint8le("arpSeqTempo") + .bit1("arpOnOff") + .bit1("arpLatchOnOff") + .bit2("arpTarget") + .bit1("ignore") + .bit1("arpKeySync") + .bit4("arpRange") + .bit4("arpType") + .uint8("arpGateTime") + .uint8("arpResolution") + .uint8("arpSwing") + .uint8("kbdOctave") + .nest("timbre1", { type: timbre }) + .seek(56) + .nest("timbre2", { type: timbre }) + .seek(56); +} function PatchEditor() { const defaultPatch = { name: "", arpeggio: { length: 8, pattern: [0, 0, 0, 0, 0, 0, 0, 0] }, - arpeggio2: {}, + arpeggio2: { + tempo: 20, + seq: 0, + on: false, + latch: false, + target: 0, + keySync: false, + type: 0, // 0 - 5 + range: 0, // 0 - 4 + gate: 0, // 0 - 100 + resolution: 0, + swing: 0, + }, voiceMode: 0, scaleKey: 0, // C scaleType: 0, // Equal Temperment @@ -23,13 +188,13 @@ function PatchEditor() { synthParameter3: {}, // this is for vocoder mode }; - const [patch, updatePatch] = useState(defaultPatch); + const [patch, setPatch] = useState(defaultPatch); return (
- - - + + {/* + */}
); } @@ -40,7 +205,7 @@ function App() {
logo
- +