From 7d8013380d142f6ae7de53a9441ea4500bd37223 Mon Sep 17 00:00:00 2001 From: Holger Wirtz Date: Wed, 28 Jul 2021 16:28:32 +0200 Subject: [PATCH] Exchanged load/save functions to JSON based ones. Voices are still loaded via SYSEX. --- UI.hpp | 30 ++-- config.h | 7 +- dexed_sd.cpp | 393 +++++++++++++++++++++++++++------------------------ dexed_sd.h | 12 +- 4 files changed, 233 insertions(+), 209 deletions(-) diff --git a/UI.hpp b/UI.hpp index 073629c..42ee64e 100644 --- a/UI.hpp +++ b/UI.hpp @@ -4479,15 +4479,13 @@ void UI_func_load_performance(uint8_t param) lcd.print("Does not exist."); else { - load_sd_voice(configuration.performance.bank[0], configuration.performance.voice[0], 0); - load_sd_voiceconfig(configuration.performance.voiceconfig_number[0], 0); + load_sd_voiceconfig_json(configuration.performance.voiceconfig_number[0], 0); set_voiceconfig_params(0); #if NUM_DEXED > 1 + load_sd_voiceconfig_json(configuration.performance.voiceconfig_number[1], 1); set_voiceconfig_params(1); - load_sd_voice(configuration.performance.bank[0], configuration.performance.voice[1], 1); - load_sd_voiceconfig(configuration.performance.voiceconfig_number[1], 1); #endif - load_sd_fx(configuration.performance.fx_number); + load_sd_fx_json(configuration.performance.fx_number); set_fx_params(); lcd.print("Done. "); @@ -4539,7 +4537,7 @@ void UI_func_save_performance(uint8_t param) sprintf(tmp, "[%2d]", configuration.sys.performance_number); lcd.print(tmp); - sprintf(tmp, "/%s/%s%d.syx", PERFORMANCE_CONFIG_PATH, PERFORMANCE_CONFIG_NAME, configuration.sys.performance_number); + sprintf(tmp, "/%s/%s%d.json", PERFORMANCE_CONFIG_PATH, PERFORMANCE_CONFIG_NAME, configuration.sys.performance_number); if (SD.exists(tmp)) overwrite = true; else @@ -4693,7 +4691,7 @@ void UI_func_load_voiceconfig(uint8_t param) { mode = 0xff; lcd.setCursor(0, 1); - if (load_sd_voiceconfig(configuration.performance.voiceconfig_number[selected_instance_id], selected_instance_id) == false) + if (load_sd_voiceconfig_json(configuration.performance.voiceconfig_number[selected_instance_id], selected_instance_id) == false) lcd.print("Does not exist. "); else lcd.print("Done. "); @@ -4773,7 +4771,7 @@ void UI_func_save_voiceconfig(uint8_t param) sprintf(tmp, "[%2d]", configuration.performance.voiceconfig_number[selected_instance_id]); lcd.print(tmp); - sprintf(tmp, "/%s/%s%d.syx", VOICE_CONFIG_PATH, VOICE_CONFIG_NAME, configuration.performance.voiceconfig_number[selected_instance_id]); + sprintf(tmp, "/%s/%s%d.json", VOICE_CONFIG_PATH, VOICE_CONFIG_NAME, configuration.performance.voiceconfig_number[selected_instance_id]); if (SD.exists(tmp)) overwrite = true; else @@ -4819,10 +4817,10 @@ void UI_func_save_voiceconfig(uint8_t param) if (yesno == true) { char tmp[FILENAME_LEN]; - sprintf(tmp, "/%s/%s%d.syx", VOICE_CONFIG_PATH, VOICE_CONFIG_NAME, configuration.performance.voiceconfig_number[selected_instance_id]); + sprintf(tmp, "/%s/%s%d.json", VOICE_CONFIG_PATH, VOICE_CONFIG_NAME, configuration.performance.voiceconfig_number[selected_instance_id]); SD.remove(tmp); } - save_sd_voiceconfig(configuration.performance.voiceconfig_number[selected_instance_id], selected_instance_id); + save_sd_voiceconfig_json(configuration.performance.voiceconfig_number[selected_instance_id], selected_instance_id); lcd.show(1, 0, 16, "Done."); delay(MESSAGE_WAIT_TIME); LCDML.FUNC_goBackToMenu(); @@ -4848,7 +4846,7 @@ void UI_func_save_voiceconfig(uint8_t param) { char tmp[FILENAME_LEN]; - sprintf(tmp, "/%s/%s%d.syx", VOICE_CONFIG_PATH, VOICE_CONFIG_NAME, configuration.performance.voiceconfig_number[selected_instance_id]); + sprintf(tmp, "/%s/%s%d.json", VOICE_CONFIG_PATH, VOICE_CONFIG_NAME, configuration.performance.voiceconfig_number[selected_instance_id]); if (SD.exists(tmp)) overwrite = true; else @@ -4925,7 +4923,7 @@ void UI_func_load_fx(uint8_t param) mode = 0xff; lcd.setCursor(0, 1); - if (load_sd_fx(configuration.performance.fx_number) == false) + if (load_sd_fx_json(configuration.performance.fx_number) == false) lcd.print("Does not exist. "); else lcd.print("Done. "); @@ -4979,7 +4977,7 @@ void UI_func_save_fx(uint8_t param) sprintf(tmp, "[%2d]", configuration.performance.fx_number); lcd.print(tmp); - sprintf(tmp, "/%s/%s%d.syx", FX_CONFIG_PATH, FX_CONFIG_NAME, configuration.performance.fx_number); + sprintf(tmp, "/%s/%s%d.json", FX_CONFIG_PATH, FX_CONFIG_NAME, configuration.performance.fx_number); if (SD.exists(tmp)) overwrite = true; else @@ -5020,10 +5018,10 @@ void UI_func_save_fx(uint8_t param) if (yesno == true) { char tmp[FILENAME_LEN]; - sprintf(tmp, "/%s/%s%d.syx", FX_CONFIG_PATH, FX_CONFIG_NAME, configuration.performance.fx_number); + sprintf(tmp, "/%s/%s%d.json", FX_CONFIG_PATH, FX_CONFIG_NAME, configuration.performance.fx_number); SD.remove(tmp); } - save_sd_fx(configuration.performance.fx_number); + save_sd_fx_json(configuration.performance.fx_number); lcd.show(1, 0, 16, "Done."); LCDML.FUNC_goBackToMenu(); @@ -5044,7 +5042,7 @@ void UI_func_save_fx(uint8_t param) if (mode == 0) { char tmp[FILENAME_LEN]; - sprintf(tmp, "/%s/%s%d.syx", FX_CONFIG_PATH, FX_CONFIG_NAME, configuration.performance.fx_number); + sprintf(tmp, "/%s/%s%d.json", FX_CONFIG_PATH, FX_CONFIG_NAME, configuration.performance.fx_number); if (SD.exists(tmp)) overwrite = true; else diff --git a/config.h b/config.h index c872f52..8e946f2 100644 --- a/config.h +++ b/config.h @@ -54,7 +54,7 @@ // sed -i.orig 's/^#define USB_MIDI_SYSEX_MAX 290/#define USB_MIDI_SYSEX_MAX 4104/' /usr/local/arduino-teensy/hardware/teensy/avr/cores/teensy4/usb_midi.h //#define USB_MIDI_SYSEX_MAX 4104 -#define VERSION "1.1.0" +#define VERSION "1.1.1" //************************************************************************************************* //* DEVICE SETTINGS @@ -610,7 +610,10 @@ #define EQ_TREBLE_MAX 10 #define EQ_TREBLE_DEFAULT 0 -// +// Buffer for load/save configuration as JSON +#define JSON_BUFFER 1024 + +// Internal configuration structure typedef struct dexed_s { uint8_t lowest_note; uint8_t highest_note; diff --git a/dexed_sd.cpp b/dexed_sd.cpp index 6f2eb04..5ec2cd4 100644 --- a/dexed_sd.cpp +++ b/dexed_sd.cpp @@ -396,19 +396,17 @@ bool save_sd_bank(const char* bank_filename, uint8_t* data) /****************************************************************************** SD VOICECONFIG ******************************************************************************/ -bool load_sd_voiceconfig(int8_t vc, uint8_t instance_id) +bool load_sd_voiceconfig_json(int8_t vc, uint8_t instance_id) { - if (vc < 0) - return (false); + char filename[FILENAME_LEN]; vc = constrain(vc, 0, MAX_VOICECONFIG); if (sd_card > 0) { - File sysex; - char filename[FILENAME_LEN]; + File json; - sprintf(filename, "/%s/%s%d.syx", VOICE_CONFIG_PATH, VOICE_CONFIG_NAME, vc); + sprintf(filename, "/%s/%s%d.json", VOICE_CONFIG_PATH, VOICE_CONFIG_NAME, vc); // first check if file exists... AudioNoInterrupts(); @@ -420,48 +418,87 @@ bool load_sd_voiceconfig(int8_t vc, uint8_t instance_id) Serial.print(filename); Serial.println(F("]... loading...")); #endif - sysex = SD.open(filename); - if (sysex) + json = SD.open(filename); + if (json) { - get_sd_data(sysex, 0x42, (uint8_t*)&configuration.dexed[instance_id]); - set_voiceconfig_params(instance_id); - sysex.close(); + StaticJsonDocument data_json; + + deserializeJson(data_json, json); + + json.close(); AudioInterrupts(); +#ifdef DEBUG + Serial.println(F("Read JSON data:")); + serializeJsonPretty(data_json, Serial); + Serial.println(); +#endif + configuration.dexed[instance_id].lowest_note = data_json["lowest_note"][instance_id]; + configuration.dexed[instance_id].highest_note = data_json["highest_note"][instance_id]; + configuration.dexed[instance_id].transpose = data_json["transpose"][instance_id]; + configuration.dexed[instance_id].tune = data_json["tune"][instance_id]; + configuration.dexed[instance_id].sound_intensity = data_json["sound_intensity"][instance_id]; + configuration.dexed[instance_id].pan = data_json["pan"][instance_id]; + configuration.dexed[instance_id].polyphony = data_json["polyphony"][instance_id]; + configuration.dexed[instance_id].velocity_level = data_json["velocity_level"][instance_id]; + configuration.dexed[instance_id].monopoly = data_json["monopoly"][instance_id]; + configuration.dexed[instance_id].note_refresh = data_json["note_refresh"][instance_id]; + configuration.dexed[instance_id].pb_range = data_json["pb_range"][instance_id]; + configuration.dexed[instance_id].pb_step = data_json["pb_step"][instance_id]; + configuration.dexed[instance_id].mw_range = data_json["mw_range"][instance_id]; + configuration.dexed[instance_id].mw_assign = data_json["mw_assign"][instance_id]; + configuration.dexed[instance_id].mw_mode = data_json["mw_mode"][instance_id]; + configuration.dexed[instance_id].fc_range = data_json["fc_range"][instance_id]; + configuration.dexed[instance_id].fc_assign = data_json["fc_assign"][instance_id]; + configuration.dexed[instance_id].fc_mode = data_json["fc_mode"][instance_id]; + configuration.dexed[instance_id].bc_range = data_json["bc_range"][instance_id]; + configuration.dexed[instance_id].bc_assign = data_json["bc_assign"][instance_id]; + configuration.dexed[instance_id].bc_mode = data_json["bc_mode"][instance_id]; + configuration.dexed[instance_id].at_range = data_json["at_range"][instance_id]; + configuration.dexed[instance_id].at_assign = data_json["at_assign"][instance_id]; + configuration.dexed[instance_id].at_mode = data_json["at_mode"][instance_id]; + configuration.dexed[instance_id].portamento_mode = data_json["portamento_mode"][instance_id]; + configuration.dexed[instance_id].portamento_glissando = data_json["portamento_glissando"][instance_id]; + configuration.dexed[instance_id].portamento_time = data_json["portamento_time"][instance_id]; + configuration.dexed[instance_id].op_enabled = data_json["op_enabled"][instance_id]; + configuration.dexed[instance_id].midi_channel = data_json["midi_channel"][instance_id]; + + set_voiceconfig_params(instance_id); + return (true); } #ifdef DEBUG else { - AudioInterrupts(); Serial.print(F("E : Cannot open ")); Serial.print(filename); Serial.println(F(" on SD.")); } -#endif } else { -#ifdef DEBUG Serial.print(F("No ")); Serial.print(filename); Serial.println(F(" available.")); #endif } } + + AudioInterrupts(); return (false); } -bool save_sd_voiceconfig(uint8_t vc, uint8_t instance_id) +bool save_sd_voiceconfig_json(uint8_t vc, uint8_t instance_id) { + char filename[FILENAME_LEN]; + vc = constrain(vc, 0, MAX_VOICECONFIG); if (sd_card > 0) { - File sysex; - char filename[FILENAME_LEN]; + File json; - sprintf(filename, "/%s/%s%d.syx", VOICE_CONFIG_PATH, VOICE_CONFIG_NAME, vc); + sprintf(filename, "/%s/%s%d.json", VOICE_CONFIG_PATH, VOICE_CONFIG_NAME, vc); #ifdef DEBUG Serial.print(F("Saving voice config ")); @@ -474,35 +511,72 @@ bool save_sd_voiceconfig(uint8_t vc, uint8_t instance_id) #endif AudioNoInterrupts(); - sysex = SD.open(filename, FILE_WRITE); - if (sysex) + json = SD.open(filename, FILE_WRITE); + if (json) { - if (write_sd_data(sysex, 0x42, (uint8_t*)&configuration.dexed[instance_id], sizeof(configuration.dexed[instance_id]))) - { - sysex.close(); - AudioInterrupts(); - return (true); - } - sysex.close(); + StaticJsonDocument data_json; + + data_json["lowest_note"][instance_id] = configuration.dexed[instance_id].lowest_note; + data_json["highest_note"][instance_id] = configuration.dexed[instance_id].highest_note; + data_json["transpose"][instance_id] = configuration.dexed[instance_id].transpose; + data_json["tune"][instance_id] = configuration.dexed[instance_id].tune; + data_json["sound_intensity"][instance_id] = configuration.dexed[instance_id].sound_intensity; + data_json["pan"][instance_id] = configuration.dexed[instance_id].pan; + data_json["polyphony"][instance_id] = configuration.dexed[instance_id].polyphony; + data_json["velocity_level"][instance_id] = configuration.dexed[instance_id].velocity_level; + data_json["monopoly"][instance_id] = configuration.dexed[instance_id].monopoly; + data_json["monopoly"][instance_id] = configuration.dexed[instance_id].monopoly; + data_json["note_refresh"][instance_id] = configuration.dexed[instance_id].note_refresh; + data_json["pb_range"][instance_id] = configuration.dexed[instance_id].pb_range; + data_json["pb_step"][instance_id] = configuration.dexed[instance_id].pb_step; + data_json["mw_range"][instance_id] = configuration.dexed[instance_id].mw_range; + data_json["mw_assign"][instance_id] = configuration.dexed[instance_id].mw_assign; + data_json["mw_mode"][instance_id] = configuration.dexed[instance_id].mw_mode; + data_json["fc_range"][instance_id] = configuration.dexed[instance_id].fc_range; + data_json["fc_assign"][instance_id] = configuration.dexed[instance_id].fc_assign; + data_json["fc_mode"][instance_id] = configuration.dexed[instance_id].fc_mode; + data_json["bc_range"][instance_id] = configuration.dexed[instance_id].bc_range; + data_json["bc_assign"][instance_id] = configuration.dexed[instance_id].bc_assign; + data_json["bc_mode"][instance_id] = configuration.dexed[instance_id].bc_mode; + data_json["at_range"][instance_id] = configuration.dexed[instance_id].at_range; + data_json["at_assign"][instance_id] = configuration.dexed[instance_id].at_assign; + data_json["at_mode"][instance_id] = configuration.dexed[instance_id].at_mode; + data_json["portamento_mode"][instance_id] = configuration.dexed[instance_id].portamento_mode; + data_json["portamento_glissando"][instance_id] = configuration.dexed[instance_id].portamento_glissando; + data_json["portamento_time"][instance_id] = configuration.dexed[instance_id].portamento_time; + data_json["op_enabled"][instance_id] = configuration.dexed[instance_id].op_enabled; + data_json["midi_channel"][instance_id] = configuration.dexed[instance_id].midi_channel; + +#ifdef DEBUG + Serial.println(F("Write JSON data:")); + serializeJsonPretty(data_json, Serial); + Serial.println(); +#endif + serializeJsonPretty(data_json, json); + json.close(); AudioInterrupts(); + + return (true); } - else - { + json.close(); + } + else + { #ifdef DEBUG - Serial.print(F("E : Cannot open ")); - Serial.print(filename); - Serial.println(F(" on SD.")); + Serial.print(F("E : Cannot open ")); + Serial.print(filename); + Serial.println(F(" on SD.")); #endif - } } + AudioInterrupts(); return (false); } /****************************************************************************** SD FX ******************************************************************************/ -bool load_sd_fx(int8_t fx) +bool load_sd_fx_json(int8_t fx) { if (fx < 0) return (false); @@ -511,10 +585,10 @@ bool load_sd_fx(int8_t fx) if (sd_card > 0) { - File sysex; + File json; char filename[FILENAME_LEN]; - sprintf(filename, "/%s/%s%d.syx", FX_CONFIG_PATH, FX_CONFIG_NAME, fx); + sprintf(filename, "/%s/%s%d.json", FX_CONFIG_PATH, FX_CONFIG_NAME, fx); // first check if file exists... AudioNoInterrupts(); @@ -526,29 +600,59 @@ bool load_sd_fx(int8_t fx) Serial.print(filename); Serial.println(F("]... loading...")); #endif - sysex = SD.open(filename); - if (sysex) + json = SD.open(filename); + if (json) { - get_sd_data(sysex, 0x43, (uint8_t*)&configuration.fx); - set_fx_params(); - sysex.close(); + StaticJsonDocument data_json; + + deserializeJson(data_json, json); + + json.close(); AudioInterrupts(); +#ifdef DEBUG + Serial.println(F("Read JSON data:")); + serializeJsonPretty(data_json, Serial); + Serial.println(); +#endif + for (uint8_t i = 0; i < MAX_DEXED; i++) + { + configuration.fx.filter_cutoff[i] = data_json["filter_cutoff"][i]; + configuration.fx.filter_resonance[i] = data_json["filter_resonance"][i]; + configuration.fx.chorus_frequency[i] = data_json["chorus_frequency"][i]; + configuration.fx.chorus_waveform[i] = data_json["chorus_waveform"][i]; + configuration.fx.chorus_depth[i] = data_json["chorus_depth"][i]; + configuration.fx.chorus_level[i] = data_json["chorus_level"][i]; + configuration.fx.delay_time[i] = data_json["delay_time"][i]; + configuration.fx.delay_feedback[i] = data_json["delay_feedback"][i]; + configuration.fx.delay_level[i] = data_json["delay_level"][i]; + configuration.fx.delay_sync[i] = data_json["delay_sync"][i]; + configuration.fx.reverb_send[i] = data_json["reverb_send"][i]; + } + configuration.fx.reverb_roomsize = data_json["reverb_roomsize"]; + configuration.fx.reverb_damping = data_json["reverb_damping"]; + configuration.fx.reverb_lowpass = data_json["reverb_lowpass"]; + configuration.fx.reverb_lodamp = data_json["reverb_lodamp"]; + configuration.fx.reverb_hidamp = data_json["reverb_hidamp"]; + configuration.fx.reverb_diffusion = data_json["reverb_diffusion"]; + configuration.fx.reverb_level = data_json["reverb_level"]; + configuration.fx.eq_bass = data_json["eq_bass"]; + configuration.fx.eq_treble = data_json["eq_treble"]; + + set_fx_params(); + return (true); } #ifdef DEBUG else { - AudioInterrupts(); Serial.print(F("E : Cannot open ")); Serial.print(filename); Serial.println(F(" on SD.")); } -#endif } else { -#ifdef DEBUG Serial.print(F("No ")); Serial.print(filename); Serial.println(F(" available.")); @@ -556,19 +660,21 @@ bool load_sd_fx(int8_t fx) } } + AudioInterrupts(); return (false); } -bool save_sd_fx(uint8_t fx) +bool save_sd_fx_json(uint8_t fx) { + char filename[FILENAME_LEN]; + fx = constrain(fx, 0, MAX_FX); if (sd_card > 0) { - File sysex; - char filename[FILENAME_LEN]; + File json; - sprintf(filename, "/%s/%s%d.syx", FX_CONFIG_PATH, FX_CONFIG_NAME, fx); + sprintf(filename, "/%s/%s%d.json", FX_CONFIG_PATH, FX_CONFIG_NAME, fx); #ifdef DEBUG Serial.print(F("Saving fx config ")); @@ -578,143 +684,63 @@ bool save_sd_fx(uint8_t fx) #endif AudioNoInterrupts(); - sysex = SD.open(filename, FILE_WRITE); - if (sysex) - { - if (write_sd_data(sysex, 0x43, (uint8_t*)&configuration.fx, sizeof(configuration.fx))) - { - sysex.close(); - AudioInterrupts(); - return (true); - } - sysex.close(); - AudioInterrupts(); - } - else - { -#ifdef DEBUG - Serial.print(F("E : Cannot open ")); - Serial.print(filename); - Serial.println(F(" on SD.")); -#endif - return (false); - } - } - - return (false); -} - -/****************************************************************************** - SD PERFORMANCE - ******************************************************************************/ -bool load_sd_performance(int8_t p) -{ - if (p < 0) - return (false); - - p = constrain(p, 0, MAX_PERFORMANCE); - - if (sd_card > 0) - { - File sysex; - char filename[FILENAME_LEN]; - - sprintf(filename, "/%s/%s%d.syx", PERFORMANCE_CONFIG_PATH, PERFORMANCE_CONFIG_NAME, p); - - // first check if file exists... - AudioNoInterrupts(); - if (SD.exists(filename)) + json = SD.open(filename, FILE_WRITE); + if (json) { - // ... and if: load -#ifdef DEBUG - Serial.print(F("Found performance configuration [")); - Serial.print(filename); - Serial.println(F("]... loading...")); -#endif - sysex = SD.open(filename); - if (sysex) - { - get_sd_data(sysex, 0x44, (uint8_t*)&configuration.performance); - sysex.close(); - AudioInterrupts(); - - for (uint8_t instance_id = 0; instance_id < NUM_DEXED; instance_id++) - { - load_sd_voice(configuration.performance.bank[instance_id], configuration.performance.voice[instance_id], instance_id); - load_sd_voiceconfig(configuration.performance.voiceconfig_number[instance_id], instance_id); - - MicroDexed[instance_id]->ControllersRefresh(); - MicroDexed[instance_id]->panic(); - } - load_sd_fx(configuration.performance.fx_number); + StaticJsonDocument data_json; - return (true); - } -#ifdef DEBUG - else + for (uint8_t i = 0; i < MAX_DEXED; i++) { - Serial.print(F("E : Cannot open ")); - Serial.print(filename); - Serial.println(F(" on SD.")); + data_json["filter_cutoff"][i] = configuration.fx.filter_cutoff[i]; + data_json["filter_resonance"][i] = configuration.fx.filter_resonance[i]; + data_json["chorus_frequency"][i] = configuration.fx.chorus_frequency[i]; + data_json["chorus_waveform"][i] = configuration.fx.chorus_waveform[i]; + data_json["chorus_depth"][i] = configuration.fx.chorus_depth[i]; + data_json["chorus_level"][i] = configuration.fx.chorus_level[i]; + data_json["delay_time"][i] = configuration.fx.delay_time[i]; + data_json["delay_feedback"][i] = configuration.fx.delay_feedback[i]; + data_json["delay_level"][i] = configuration.fx.delay_level[i]; + data_json["delay_sync"][i] = configuration.fx.delay_sync[i]; + data_json["reverb_send"][i] = configuration.fx.reverb_send[i]; } -#endif - } - else - { -#ifdef DEBUG - Serial.print(F("No ")); - Serial.print(filename); - Serial.println(F(" available.")); -#endif - } - } - return (false); -} - -bool save_sd_performance(uint8_t p) -{ - p = constrain(p, 0, MAX_PERFORMANCE); - - if (sd_card > 0) - { - File sysex; - char filename[FILENAME_LEN]; - - sprintf(filename, "/%s/%s%d.syx", PERFORMANCE_CONFIG_PATH, PERFORMANCE_CONFIG_NAME, p); + data_json["reverb_roomsize"] = configuration.fx.reverb_roomsize; + data_json["reverb_damping"] = configuration.fx.reverb_damping; + data_json["reverb_lowpass"] = configuration.fx.reverb_lowpass; + data_json["reverb_lodamp"] = configuration.fx.reverb_lodamp; + data_json["reverb_hidamp"] = configuration.fx.reverb_hidamp; + data_json["reverb_diffusion"] = configuration.fx.reverb_diffusion; + data_json["reverb_level"] = configuration.fx.reverb_level; + data_json["eq_bass"] = configuration.fx.eq_bass; + data_json["eq_treble"] = configuration.fx.eq_treble; #ifdef DEBUG - Serial.print(F("Saving performance config ")); - Serial.print(p); - Serial.print(F(" to ")); - Serial.println(filename); + Serial.println(F("Write JSON data:")); + serializeJsonPretty(data_json, Serial); + Serial.println(); #endif - - AudioNoInterrupts(); - sysex = SD.open(filename, FILE_WRITE); - if (sysex) - { - if (write_sd_data(sysex, 0x44, (uint8_t*)&configuration.performance, sizeof(configuration.performance))) - { - sysex.close(); - AudioInterrupts(); - return (true); - } - sysex.close(); + serializeJsonPretty(data_json, json); + json.close(); AudioInterrupts(); + return (true); } - else - { + json.close(); + } + else + { #ifdef DEBUG - Serial.print(F("E : Cannot open ")); - Serial.print(filename); - Serial.println(F(" on SD.")); + Serial.print(F("E : Cannot open ")); + Serial.print(filename); + Serial.println(F(" on SD.")); #endif - return (false); - } } + + AudioInterrupts(); return (false); } +/****************************************************************************** + SD PERFORMANCE + ******************************************************************************/ bool load_sd_performance_json(int8_t p) { if (p < 0) @@ -742,14 +768,15 @@ bool load_sd_performance_json(int8_t p) json = SD.open(filename); if (json) { - StaticJsonDocument<256> data_json; - + StaticJsonDocument data_json; deserializeJson(data_json, json); - + json.close(); + AudioInterrupts(); + #ifdef DEBUG - Serial.println(F("Read JSON data:")); - serializeJsonPretty(data_json, Serial); - Serial.println(); + Serial.println(F("Read JSON data:")); + serializeJsonPretty(data_json, Serial); + Serial.println(); #endif for (uint8_t i = 0; i < MAX_DEXED; i++) { @@ -759,17 +786,15 @@ bool load_sd_performance_json(int8_t p) } configuration.performance.fx_number = data_json["fx_number"]; - json.close(); - AudioInterrupts(); - for (uint8_t instance_id = 0; instance_id < NUM_DEXED; instance_id++) { - load_sd_voiceconfig(configuration.performance.voiceconfig_number[instance_id], instance_id); + load_sd_voice(configuration.performance.bank[instance_id], configuration.performance.voice[instance_id], instance_id); + load_sd_voiceconfig_json(configuration.performance.voiceconfig_number[instance_id], instance_id); MicroDexed[instance_id]->ControllersRefresh(); MicroDexed[instance_id]->panic(); } - load_sd_fx(configuration.performance.fx_number); + load_sd_fx_json(configuration.performance.fx_number); return (true); } @@ -780,17 +805,17 @@ bool load_sd_performance_json(int8_t p) Serial.print(filename); Serial.println(F(" on SD.")); } -#endif } else { -#ifdef DEBUG Serial.print(F("No ")); Serial.print(filename); Serial.println(F(" available.")); #endif } } + + AudioInterrupts(); return (false); } @@ -817,7 +842,7 @@ bool save_sd_performance_json(uint8_t p) json = SD.open(filename, FILE_WRITE); if (json) { - StaticJsonDocument<256> data_json; + StaticJsonDocument data_json; for (uint8_t i = 0; i < MAX_DEXED; i++) { diff --git a/dexed_sd.h b/dexed_sd.h index 563a837..7d4c5aa 100644 --- a/dexed_sd.h +++ b/dexed_sd.h @@ -48,24 +48,22 @@ extern void set_fx_params(void); extern void set_voiceconfig_params(uint8_t instance_id); extern void set_sys_params(void); + bool load_sd_voice(uint8_t b, uint8_t v, uint8_t instance_id); bool save_sd_voice(uint8_t b, uint8_t v, uint8_t instance_id); bool get_sd_voice(File sysex, uint8_t voice_number, uint8_t* data); bool put_sd_voice(File sysex, uint8_t voice_number, uint8_t* data); bool save_sd_bank(const char* bank_filename, uint8_t* data); -bool load_sd_voiceconfig(int8_t vc, uint8_t instance_id); -bool save_sd_voiceconfig(uint8_t vc, uint8_t instance_id); +bool load_sd_voiceconfig_json(int8_t vc, uint8_t instance_id); +bool save_sd_voiceconfig_json(uint8_t vc, uint8_t instance_id); -bool load_sd_fx(int8_t fx); -bool save_sd_fx(uint8_t fx); +bool load_sd_fx_json(int8_t fx); +bool save_sd_fx_json(uint8_t fx); -bool load_sd_performance(int8_t p); -bool save_sd_performance(uint8_t p); bool load_sd_performance_json(int8_t p); bool save_sd_performance_json(uint8_t p); - bool get_sd_data(File sysex, uint8_t format, uint8_t* conf); bool write_sd_data(File sysex, uint8_t format, uint8_t* data, uint16_t len);