Memory improvements in bootsplash and StateManager
This commit is contained in:
@ -203,13 +203,13 @@ void HandleEncoderPressed() {
|
|||||||
gravity.encoder.SetReverseDirection(app.encoder_reversed);
|
gravity.encoder.SetReverseDirection(app.encoder_reversed);
|
||||||
}
|
}
|
||||||
if (app.selected_param == PARAM_MAIN_SAVE_DATA) {
|
if (app.selected_param == PARAM_MAIN_SAVE_DATA) {
|
||||||
if (app.selected_sub_param < MAX_SAVE_SLOTS) {
|
if (app.selected_sub_param < StateManager::MAX_SAVE_SLOTS) {
|
||||||
app.selected_save_slot = app.selected_sub_param;
|
app.selected_save_slot = app.selected_sub_param;
|
||||||
stateManager.saveData(app);
|
stateManager.saveData(app);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (app.selected_param == PARAM_MAIN_LOAD_DATA) {
|
if (app.selected_param == PARAM_MAIN_LOAD_DATA) {
|
||||||
if (app.selected_sub_param < MAX_SAVE_SLOTS) {
|
if (app.selected_sub_param < StateManager::MAX_SAVE_SLOTS) {
|
||||||
app.selected_save_slot = app.selected_sub_param;
|
app.selected_save_slot = app.selected_sub_param;
|
||||||
stateManager.loadData(app, app.selected_save_slot);
|
stateManager.loadData(app, app.selected_save_slot);
|
||||||
InitGravity(app);
|
InitGravity(app);
|
||||||
@ -223,6 +223,7 @@ void HandleEncoderPressed() {
|
|||||||
}
|
}
|
||||||
if (app.selected_param == PARAM_MAIN_FACTORY_RESET) {
|
if (app.selected_param == PARAM_MAIN_FACTORY_RESET) {
|
||||||
if (app.selected_sub_param == 0) { // Erase
|
if (app.selected_sub_param == 0) { // Erase
|
||||||
|
// Show bootsplash during slow erase operation.
|
||||||
Bootsplash();
|
Bootsplash();
|
||||||
stateManager.factoryReset(app);
|
stateManager.factoryReset(app);
|
||||||
InitGravity(app);
|
InitGravity(app);
|
||||||
@ -297,7 +298,7 @@ void editMainParameter(int val) {
|
|||||||
break;
|
break;
|
||||||
case PARAM_MAIN_SAVE_DATA:
|
case PARAM_MAIN_SAVE_DATA:
|
||||||
case PARAM_MAIN_LOAD_DATA:
|
case PARAM_MAIN_LOAD_DATA:
|
||||||
updateSelection(app.selected_sub_param, val, MAX_SAVE_SLOTS + 1);
|
updateSelection(app.selected_sub_param, val, StateManager::MAX_SAVE_SLOTS + 1);
|
||||||
break;
|
break;
|
||||||
case PARAM_MAIN_RESET_STATE:
|
case PARAM_MAIN_RESET_STATE:
|
||||||
updateSelection(app.selected_sub_param, val, 2);
|
updateSelection(app.selected_sub_param, val, 2);
|
||||||
|
|||||||
@ -19,9 +19,7 @@
|
|||||||
// Global state for settings and app behavior.
|
// Global state for settings and app behavior.
|
||||||
struct AppState {
|
struct AppState {
|
||||||
int tempo = Clock::DEFAULT_TEMPO;
|
int tempo = Clock::DEFAULT_TEMPO;
|
||||||
bool encoder_reversed = false;
|
Channel channel[Gravity::OUTPUT_COUNT];
|
||||||
bool refresh_screen = true;
|
|
||||||
bool editing_param = false;
|
|
||||||
byte selected_param = 0;
|
byte selected_param = 0;
|
||||||
byte selected_sub_param = 0; // Temporary value for editing params.
|
byte selected_sub_param = 0; // Temporary value for editing params.
|
||||||
byte selected_channel = 0; // 0=tempo, 1-6=output channel
|
byte selected_channel = 0; // 0=tempo, 1-6=output channel
|
||||||
@ -29,7 +27,9 @@ struct AppState {
|
|||||||
byte selected_save_slot = 0; // The currently active save slot.
|
byte selected_save_slot = 0; // The currently active save slot.
|
||||||
Clock::Source selected_source = Clock::SOURCE_INTERNAL;
|
Clock::Source selected_source = Clock::SOURCE_INTERNAL;
|
||||||
Clock::Pulse selected_pulse = Clock::PULSE_PPQN_24;
|
Clock::Pulse selected_pulse = Clock::PULSE_PPQN_24;
|
||||||
Channel channel[Gravity::OUTPUT_COUNT];
|
bool editing_param = false;
|
||||||
|
bool encoder_reversed = false;
|
||||||
|
bool refresh_screen = true;
|
||||||
};
|
};
|
||||||
|
|
||||||
extern AppState app;
|
extern AppState app;
|
||||||
|
|||||||
@ -214,10 +214,10 @@ void swingDivisionMark() {
|
|||||||
|
|
||||||
// Human friendly display value for save slot.
|
// Human friendly display value for save slot.
|
||||||
String displaySaveSlot(int slot) {
|
String displaySaveSlot(int slot) {
|
||||||
if (slot >= 0 && slot < MAX_SAVE_SLOTS / 2) {
|
if (slot >= 0 && slot < StateManager::MAX_SAVE_SLOTS / 2) {
|
||||||
return String("A") + String(slot + 1);
|
return String("A") + String(slot + 1);
|
||||||
} else if (slot >= MAX_SAVE_SLOTS / 2 && slot <= MAX_SAVE_SLOTS) {
|
} else if (slot >= StateManager::MAX_SAVE_SLOTS / 2 && slot <= StateManager::MAX_SAVE_SLOTS) {
|
||||||
return String("B") + String(slot - (MAX_SAVE_SLOTS / 2) + 1);
|
return String("B") + String(slot - (StateManager::MAX_SAVE_SLOTS / 2) + 1);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -283,7 +283,7 @@ void DisplayMainPage() {
|
|||||||
break;
|
break;
|
||||||
case PARAM_MAIN_SAVE_DATA:
|
case PARAM_MAIN_SAVE_DATA:
|
||||||
case PARAM_MAIN_LOAD_DATA:
|
case PARAM_MAIN_LOAD_DATA:
|
||||||
if (app.selected_sub_param == MAX_SAVE_SLOTS) {
|
if (app.selected_sub_param == StateManager::MAX_SAVE_SLOTS) {
|
||||||
mainText = F("x");
|
mainText = F("x");
|
||||||
subText = F("BACK TO MAIN");
|
subText = F("BACK TO MAIN");
|
||||||
} else {
|
} else {
|
||||||
@ -465,7 +465,7 @@ void UpdateDisplay() {
|
|||||||
DisplayChannelPage();
|
DisplayChannelPage();
|
||||||
}
|
}
|
||||||
// Global channel select UI.
|
// Global channel select UI.
|
||||||
DisplaySelectedChannel();
|
DisplaySelectedChannel();
|
||||||
} while (gravity.display.nextPage());
|
} while (gravity.display.nextPage());
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -473,16 +473,17 @@ void Bootsplash() {
|
|||||||
gravity.display.firstPage();
|
gravity.display.firstPage();
|
||||||
do {
|
do {
|
||||||
int textWidth;
|
int textWidth;
|
||||||
|
String loadingText = F("LOADING....");
|
||||||
gravity.display.setFont(TEXT_FONT);
|
gravity.display.setFont(TEXT_FONT);
|
||||||
|
|
||||||
textWidth = gravity.display.getStrWidth(SKETCH_NAME);
|
textWidth = gravity.display.getStrWidth(StateManager::SKETCH_NAME);
|
||||||
gravity.display.drawStr(16 + (textWidth / 2), 20, SKETCH_NAME);
|
gravity.display.drawStr(16 + (textWidth / 2), 20, StateManager::SKETCH_NAME);
|
||||||
|
|
||||||
textWidth = gravity.display.getStrWidth(SEMANTIC_VERSION);
|
textWidth = gravity.display.getStrWidth(StateManager::SEMANTIC_VERSION);
|
||||||
gravity.display.drawStr(16 + (textWidth / 2), 32, SEMANTIC_VERSION);
|
gravity.display.drawStr(16 + (textWidth / 2), 32, StateManager::SEMANTIC_VERSION);
|
||||||
|
|
||||||
textWidth = gravity.display.getStrWidth("LOADING....");
|
textWidth = gravity.display.getStrWidth(loadingText.c_str());
|
||||||
gravity.display.drawStr(26 + (textWidth / 2), 44, "LOADING....");
|
gravity.display.drawStr(26 + (textWidth / 2), 44, loadingText.c_str());
|
||||||
} while (gravity.display.nextPage());
|
} while (gravity.display.nextPage());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -15,9 +15,20 @@
|
|||||||
|
|
||||||
#include "app_state.h"
|
#include "app_state.h"
|
||||||
|
|
||||||
|
// Define the constants for the current firmware.
|
||||||
|
const char StateManager::SKETCH_NAME[] = "ALT GRAVITY";
|
||||||
|
const char StateManager::SEMANTIC_VERSION[] = "V2.0.0BETA2";
|
||||||
|
|
||||||
|
// Number of available save slots.
|
||||||
|
const byte StateManager::MAX_SAVE_SLOTS = 10;
|
||||||
|
const byte StateManager::TRANSIENT_SLOT = 10;
|
||||||
|
|
||||||
|
// Define the minimum amount of time between EEPROM writes.
|
||||||
|
const unsigned long StateManager::SAVE_DELAY_MS = 2000;
|
||||||
|
|
||||||
// Calculate the starting address for EepromData, leaving space for metadata.
|
// Calculate the starting address for EepromData, leaving space for metadata.
|
||||||
static const int METADATA_START_ADDR = 0;
|
const int StateManager::METADATA_START_ADDR = 0;
|
||||||
static const int EEPROM_DATA_START_ADDR = sizeof(StateManager::Metadata);
|
const int StateManager::EEPROM_DATA_START_ADDR = sizeof(StateManager::Metadata);
|
||||||
|
|
||||||
StateManager::StateManager() : _isDirty(false), _lastChangeTime(0) {}
|
StateManager::StateManager() : _isDirty(false), _lastChangeTime(0) {}
|
||||||
|
|
||||||
|
|||||||
@ -18,17 +18,6 @@
|
|||||||
// Forward-declare AppState to avoid circular dependencies.
|
// Forward-declare AppState to avoid circular dependencies.
|
||||||
struct AppState;
|
struct AppState;
|
||||||
|
|
||||||
// Define the constants for the current firmware.
|
|
||||||
const char SKETCH_NAME[] = "ALT GRAVITY";
|
|
||||||
const char SEMANTIC_VERSION[] = "V2.0.0BETA2";
|
|
||||||
|
|
||||||
// Number of available save slots.
|
|
||||||
const byte MAX_SAVE_SLOTS = 10; // Count of save slots 0 - 9 to save/load presets.
|
|
||||||
const byte TRANSIENT_SLOT = 10; // Transient slot index to persist state when powered off.
|
|
||||||
|
|
||||||
// Define the minimum amount of time between EEPROM writes.
|
|
||||||
static const unsigned long SAVE_DELAY_MS = 2000;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Manages saving and loading of the application state to and from EEPROM.
|
* @brief Manages saving and loading of the application state to and from EEPROM.
|
||||||
* The number of user slots is defined by MAX_SAVE_SLOTS, and one additional slot
|
* The number of user slots is defined by MAX_SAVE_SLOTS, and one additional slot
|
||||||
@ -39,6 +28,11 @@ static const unsigned long SAVE_DELAY_MS = 2000;
|
|||||||
*/
|
*/
|
||||||
class StateManager {
|
class StateManager {
|
||||||
public:
|
public:
|
||||||
|
static const char SKETCH_NAME[];
|
||||||
|
static const char SEMANTIC_VERSION[];
|
||||||
|
static const byte MAX_SAVE_SLOTS;
|
||||||
|
static const byte TRANSIENT_SLOT;
|
||||||
|
|
||||||
StateManager();
|
StateManager();
|
||||||
|
|
||||||
// Populate the AppState instance with values from EEPROM if they exist.
|
// Populate the AppState instance with values from EEPROM if they exist.
|
||||||
@ -92,6 +86,10 @@ class StateManager {
|
|||||||
void _saveState(const AppState& app, byte slot_index);
|
void _saveState(const AppState& app, byte slot_index);
|
||||||
void _loadState(AppState& app, byte slot_index);
|
void _loadState(AppState& app, byte slot_index);
|
||||||
|
|
||||||
|
static const unsigned long SAVE_DELAY_MS;
|
||||||
|
static const int METADATA_START_ADDR;
|
||||||
|
static const int EEPROM_DATA_START_ADDR;
|
||||||
|
|
||||||
bool _isDirty;
|
bool _isDirty;
|
||||||
unsigned long _lastChangeTime;
|
unsigned long _lastChangeTime;
|
||||||
};
|
};
|
||||||
|
|||||||
Reference in New Issue
Block a user