From 8f25346479a95b1ddde39e6ab21a51931b8c80ed Mon Sep 17 00:00:00 2001 From: Eric McDaniel Date: Sun, 15 Feb 2026 18:49:44 -0600 Subject: [PATCH 1/9] Append version number to firmware.bin --- .gitignore | 1 + platformio.ini | 2 +- src/engine/engine.cpp | 2 ++ tools/write_firmware.py | 13 +++++++++++++ 4 files changed, 17 insertions(+), 1 deletion(-) create mode 100644 tools/write_firmware.py diff --git a/.gitignore b/.gitignore index 6d77523..2a99976 100644 --- a/.gitignore +++ b/.gitignore @@ -26,6 +26,7 @@ __pycache__ *.log *.raw *.dat +*.bin *.pro.user *.kicad_pro.user diff --git a/platformio.ini b/platformio.ini index 6bf75eb..2daba9f 100644 --- a/platformio.ini +++ b/platformio.ini @@ -40,10 +40,10 @@ build_flags = -g -DDEBUG -std=gnu++2a platform = espressif32 board = upesy_wroom framework = arduino -lib_ignore = debug-fastled build_type = release build_unflags = -std=gnu++11 build_flags = -Os -DRELEASE -std=gnu++2a +extra_scripts = post:tools/write_firmware.py [env:native] platform = native diff --git a/src/engine/engine.cpp b/src/engine/engine.cpp index d6af5bb..7060430 100644 --- a/src/engine/engine.cpp +++ b/src/engine/engine.cpp @@ -7,6 +7,8 @@ #include "display/menu-navigation.h" #include "logger.h" +// extern "C" const char FW_VERSION[] PROGMEM __attribute__((used, section(".fw_version"))) = "LUMENLAB_FW_VERSION:99.99.99\0"; + namespace Engine { GameEngine::GameEngine() diff --git a/tools/write_firmware.py b/tools/write_firmware.py new file mode 100644 index 0000000..c31b1e1 --- /dev/null +++ b/tools/write_firmware.py @@ -0,0 +1,13 @@ +import os +Import("env") + + +def append_version_to_firmware(source, target, env): + firmware_path = str(target[0]) + version_file = os.path.join(env['PROJECT_DIR'], 'configuration.bin') + with open(firmware_path, 'ab') as f_fw, open(version_file, 'rb') as f_ver: + f_fw.write(f_ver.read()) + print("Appended configuration.bin to firmware") + + +env.AddPostAction("$BUILD_DIR/${PROGNAME}.bin", append_version_to_firmware) From 3f1514ab105a5d1aaf269a476dab6ab03936bc44 Mon Sep 17 00:00:00 2001 From: Eric McDaniel Date: Sun, 15 Feb 2026 23:24:02 -0600 Subject: [PATCH 2/9] Move version number to .data segment --- .github/workflows/release.yaml | 2 +- .gitignore | 1 - include/core/configuration.h | 1 + include/display/display.h | 1 - platformio.ini | 1 - src/display/display.cpp | 9 ++++----- tools/write_firmware.py | 13 ------------- 7 files changed, 6 insertions(+), 22 deletions(-) delete mode 100644 tools/write_firmware.py diff --git a/.github/workflows/release.yaml b/.github/workflows/release.yaml index e50314c..d073009 100644 --- a/.github/workflows/release.yaml +++ b/.github/workflows/release.yaml @@ -60,7 +60,7 @@ jobs: uses: softprops/action-gh-release@v2 with: tag_name: ${{ steps.semver.outputs.tag }} - name: ${{ steps.pr_details.outputs.title }} + name: ${{ steps.semver.outputs.tag }} - ${{ steps.pr_details.outputs.title }} body: ${{ steps.pr_details.outputs.body }} files: | .pio/build/release/firmware.bin diff --git a/.gitignore b/.gitignore index 2a99976..6d77523 100644 --- a/.gitignore +++ b/.gitignore @@ -26,7 +26,6 @@ __pycache__ *.log *.raw *.dat -*.bin *.pro.user *.kicad_pro.user diff --git a/include/core/configuration.h b/include/core/configuration.h index 779a71f..42d1b8f 100644 --- a/include/core/configuration.h +++ b/include/core/configuration.h @@ -7,6 +7,7 @@ namespace SystemCore struct Configuration { // REQUIRED: modify this address to match the mac address of your PS3 controller + static constexpr char version[] = "v0.3.2"; static constexpr char macAddress[] = "00:1b:fb:8e:87:ac"; static constexpr uint16_t numLeds = 327; static constexpr uint32_t serialBaud = 921600; diff --git a/include/display/display.h b/include/display/display.h index e54e38f..4bb703e 100644 --- a/include/display/display.h +++ b/include/display/display.h @@ -38,7 +38,6 @@ namespace Display char selectedOption(uint8_t index, uint8_t selectedOptionIndex) { return index == selectedOptionIndex ? '>' : ' '; }; int16_t calculateCenterText(const char *text); - void drawLogo(); void drawHeader(const char *message); void drawBootScreen(); void drawMainMenu(); diff --git a/platformio.ini b/platformio.ini index 2daba9f..ac865f1 100644 --- a/platformio.ini +++ b/platformio.ini @@ -43,7 +43,6 @@ framework = arduino build_type = release build_unflags = -std=gnu++11 build_flags = -Os -DRELEASE -std=gnu++2a -extra_scripts = post:tools/write_firmware.py [env:native] platform = native diff --git a/src/display/display.cpp b/src/display/display.cpp index caa508a..4423c31 100644 --- a/src/display/display.cpp +++ b/src/display/display.cpp @@ -81,14 +81,13 @@ namespace Display display.print(message); } - void OledDisplay::drawLogo() - { - } - void OledDisplay::drawBootScreen() { display.clearDisplay(); - drawHeader("LumenLab"); + + char versionBuffer[32] = ""; + sprintf(versionBuffer, "LumenLab %s", SystemCore::Configuration::version); + drawHeader(versionBuffer); display.drawBitmap(initLogo.xPos, initLogo.yPos, initLogo.rawValues, initLogo.width, initLogo.height, SSD1306_WHITE); display.display(); diff --git a/tools/write_firmware.py b/tools/write_firmware.py deleted file mode 100644 index c31b1e1..0000000 --- a/tools/write_firmware.py +++ /dev/null @@ -1,13 +0,0 @@ -import os -Import("env") - - -def append_version_to_firmware(source, target, env): - firmware_path = str(target[0]) - version_file = os.path.join(env['PROJECT_DIR'], 'configuration.bin') - with open(firmware_path, 'ab') as f_fw, open(version_file, 'rb') as f_ver: - f_fw.write(f_ver.read()) - print("Appended configuration.bin to firmware") - - -env.AddPostAction("$BUILD_DIR/${PROGNAME}.bin", append_version_to_firmware) From add15af3981c0cc9d3b8cc94509743cee304aafe Mon Sep 17 00:00:00 2001 From: Eric McDaniel Date: Wed, 18 Feb 2026 21:44:11 -0600 Subject: [PATCH 3/9] Set system config from Preferences --- include/core/configuration.h | 30 ++++++++++++++++++++++------ include/games/phase-evasion/driver.h | 2 +- include/games/phase-evasion/gem.h | 2 +- include/games/phase-evasion/state.h | 1 + include/games/recall/driver.h | 2 +- include/games/recall/state.h | 3 ++- include/lights/led-buffer.h | 4 ++-- include/lights/led-strip.h | 2 +- include/player/controller.h | 2 +- include/scenes/canvas/driver.h | 2 +- src/core/configuration.cpp | 9 +++++++++ src/core/context-manager.cpp | 9 ++++++++- src/display/display.cpp | 4 +--- src/display/menu-navigation.cpp | 2 +- src/engine/engine.cpp | 24 ++++++++++------------ src/games/demo/player.cpp | 4 ++-- src/games/phase-evasion/driver.cpp | 24 +++++++++++----------- src/games/phase-evasion/flare.cpp | 4 ++-- src/games/phase-evasion/state.cpp | 6 +++++- src/games/recall/driver.cpp | 12 +++++------ src/games/recall/state.cpp | 13 ++++++------ src/player/controller.cpp | 4 ++-- src/player/player.cpp | 2 +- src/scenes/canvas/driver.cpp | 4 ++-- 24 files changed, 102 insertions(+), 69 deletions(-) create mode 100644 src/core/configuration.cpp diff --git a/include/core/configuration.h b/include/core/configuration.h index 42d1b8f..29aedda 100644 --- a/include/core/configuration.h +++ b/include/core/configuration.h @@ -1,17 +1,35 @@ #pragma once +#include +#include #include namespace SystemCore { - struct Configuration + class Configuration { - // REQUIRED: modify this address to match the mac address of your PS3 controller - static constexpr char version[] = "v0.3.2"; - static constexpr char macAddress[] = "00:1b:fb:8e:87:ac"; - static constexpr uint16_t numLeds = 327; - static constexpr uint32_t serialBaud = 921600; + public: + static const String &version() { return version_; } + static const String &macAddress() { return macAddress_; } + static uint16_t numLeds() { return numLeds_; } + static uint32_t serialBaud() { return serialBaud_; } + + static void load(class Preferences &memory) + { + version_ = memory.getString("version", "v0.0.0"); + macAddress_ = memory.getString("macAddress", "00:1b:fb:8e:87:ac"); + numLeds_ = memory.getUInt("numLeds", 327); + serialBaud_ = memory.getUInt("serialBaud", 921600); + } + + // (in progress) static constexpr uint16_t recallBoundaries[4] = {0, 113, 168, 281}; static constexpr uint8_t ledDimmerGpio = 34; + + private: + static String version_; + static String macAddress_; + static uint16_t numLeds_; + static uint32_t serialBaud_; }; } \ No newline at end of file diff --git a/include/games/phase-evasion/driver.h b/include/games/phase-evasion/driver.h index 0a3f181..4643945 100644 --- a/include/games/phase-evasion/driver.h +++ b/include/games/phase-evasion/driver.h @@ -22,7 +22,7 @@ namespace Games::PhaseEvasion private: SystemCore::ContextManager *contextManager; - GameState &state = contextManager->stateManager.getPhaseEvasionGameState(); + GameState &state; Player player; FlareManager flareManager; diff --git a/include/games/phase-evasion/gem.h b/include/games/phase-evasion/gem.h index 0d60774..96359e4 100644 --- a/include/games/phase-evasion/gem.h +++ b/include/games/phase-evasion/gem.h @@ -22,7 +22,7 @@ namespace Games::PhaseEvasion void spawn(const uint16_t pos) { bool isOutsideLeftRegion = pos < (width - 1); - bool isOutsideRightRegion = pos > SystemCore::Configuration::numLeds + (width - 1); + bool isOutsideRightRegion = pos > SystemCore::Configuration::numLeds() + (width - 1); if (isOutsideLeftRegion || isOutsideRightRegion) return; diff --git a/include/games/phase-evasion/state.h b/include/games/phase-evasion/state.h index 522e581..4427cfe 100644 --- a/include/games/phase-evasion/state.h +++ b/include/games/phase-evasion/state.h @@ -29,6 +29,7 @@ namespace Games::PhaseEvasion static constexpr const char *memoryKeyName = "phase-high"; void reset(); + void loadHighScore(); uint16_t calculateTotalScore() const; void checkHighScore(); void updateHighScore(); diff --git a/include/games/recall/driver.h b/include/games/recall/driver.h index bdf4509..89206af 100644 --- a/include/games/recall/driver.h +++ b/include/games/recall/driver.h @@ -18,7 +18,7 @@ namespace Games::Recall private: SystemCore::ContextManager *contextManager; - GameState &state = contextManager->stateManager.getRecallGameState(); + GameState &state; uint16_t gameplaySpeedIlluminated = 500; uint16_t gameplaySpeedPaused = gameplaySpeedIlluminated / 6; diff --git a/include/games/recall/state.h b/include/games/recall/state.h index 1cbf4b5..c57c0c9 100644 --- a/include/games/recall/state.h +++ b/include/games/recall/state.h @@ -22,13 +22,14 @@ namespace Games::Recall class GameState { public: - GameState(SystemCore::ContextManager *ctx); + GameState(SystemCore::ContextManager *ctx) : contextManager{ctx} {} uint16_t highScore; uint16_t round; Actions current = Actions::Startup; static constexpr const char *memoryKeyName = "recall-high"; void reset(); + void loadHighScore(); void incrementScore(); void updateHighScore(); diff --git a/include/lights/led-buffer.h b/include/lights/led-buffer.h index 67396ef..aee169f 100644 --- a/include/lights/led-buffer.h +++ b/include/lights/led-buffer.h @@ -9,7 +9,7 @@ namespace Lights class LedBuffer { public: - LedBuffer() : leds{new Color[SystemCore::Configuration::numLeds]} {} + LedBuffer() : leds{new Color[SystemCore::Configuration::numLeds()]} {} ~LedBuffer() { delete leds; } LedBuffer(LedBuffer &&other) = delete; LedBuffer &operator=(LedBuffer &&other) = delete; @@ -22,7 +22,7 @@ namespace Lights explicit operator Color *() { return leds; } explicit operator const Color *() const { return leds; } - uint16_t size() { return SystemCore::Configuration::numLeds; } + uint16_t size() { return SystemCore::Configuration::numLeds(); } private: Color *leds; diff --git a/include/lights/led-strip.h b/include/lights/led-strip.h index db2ffe6..4289f18 100644 --- a/include/lights/led-strip.h +++ b/include/lights/led-strip.h @@ -14,7 +14,7 @@ namespace Lights LedBuffer buffer; Color *getRawColors(); - static constexpr uint16_t size() { return SystemCore::Configuration::numLeds; } + static const uint16_t size() { return SystemCore::Configuration::numLeds(); } void reset(); void adjustLuminance(); diff --git a/include/player/controller.h b/include/player/controller.h index 42d7943..a05e0c1 100644 --- a/include/player/controller.h +++ b/include/player/controller.h @@ -36,7 +36,7 @@ namespace Player { public: Controller() { instance = this; } - void begin(const char *macAddress); + void begin(String macAddress); uint8_t cross() { return instance->controller.data.analog.button.cross; } uint8_t circle() { return instance->controller.data.analog.button.circle; } diff --git a/include/scenes/canvas/driver.h b/include/scenes/canvas/driver.h index 5e20db0..a3e2fa1 100644 --- a/include/scenes/canvas/driver.h +++ b/include/scenes/canvas/driver.h @@ -14,7 +14,7 @@ namespace Scenes::Canvas private: SystemCore::ContextManager *contextManager; - SceneState &state = contextManager->stateManager.getCanvasSceneState(); + SceneState &state; Lights::ColorHsl colorHsl; bool hasChange = false; bool controllerWasActive = false; diff --git a/src/core/configuration.cpp b/src/core/configuration.cpp new file mode 100644 index 0000000..119f9ff --- /dev/null +++ b/src/core/configuration.cpp @@ -0,0 +1,9 @@ +#include "core/configuration.h" + +namespace SystemCore +{ + String SystemCore::Configuration::version_; + String SystemCore::Configuration::macAddress_; + uint16_t SystemCore::Configuration::numLeds_; + uint32_t SystemCore::Configuration::serialBaud_; +} \ No newline at end of file diff --git a/src/core/context-manager.cpp b/src/core/context-manager.cpp index 983f5b1..6c416e1 100644 --- a/src/core/context-manager.cpp +++ b/src/core/context-manager.cpp @@ -7,7 +7,14 @@ namespace SystemCore { - ContextManager::ContextManager() : display{this}, stateManager{this}, menuNav{this} {} + ContextManager::ContextManager() : display{this}, stateManager{this}, menuNav{this} + { +#ifdef RELEASE + memory.begin("lumenlab", false); +#else + memory.begin("lumenlab-dev", false); +#endif + } ContextManager::~ContextManager() { diff --git a/src/display/display.cpp b/src/display/display.cpp index 4423c31..000f937 100644 --- a/src/display/display.cpp +++ b/src/display/display.cpp @@ -85,9 +85,7 @@ namespace Display { display.clearDisplay(); - char versionBuffer[32] = ""; - sprintf(versionBuffer, "LumenLab %s", SystemCore::Configuration::version); - drawHeader(versionBuffer); + drawHeader("LumenLab"); display.drawBitmap(initLogo.xPos, initLogo.yPos, initLogo.rawValues, initLogo.width, initLogo.height, SSD1306_WHITE); display.display(); diff --git a/src/display/menu-navigation.cpp b/src/display/menu-navigation.cpp index 03031fa..1188f4c 100644 --- a/src/display/menu-navigation.cpp +++ b/src/display/menu-navigation.cpp @@ -10,7 +10,7 @@ namespace Display Engine::MainMenuSelection modeSelected = contextManager->stateManager.getUserMenuChoice(); Engine::SystemState currentState = contextManager->stateManager.current(); - uint16_t displayIndex = SystemCore::Configuration::numLeds - 1; + uint16_t displayIndex = SystemCore::Configuration::numLeds() - 1; float inactiveSelectionDimmingScale = currentState == Engine::SystemState::MenuHome ? 1.0f : 0.6f; constexpr float center = (menuTileWidth - 1) / 2.0f; constexpr double sigma = 3.0f; diff --git a/src/engine/engine.cpp b/src/engine/engine.cpp index 7060430..f745d47 100644 --- a/src/engine/engine.cpp +++ b/src/engine/engine.cpp @@ -7,8 +7,6 @@ #include "display/menu-navigation.h" #include "logger.h" -// extern "C" const char FW_VERSION[] PROGMEM __attribute__((used, section(".fw_version"))) = "LUMENLAB_FW_VERSION:99.99.99\0"; - namespace Engine { GameEngine::GameEngine() @@ -70,11 +68,15 @@ namespace Engine void GameEngine::initializeEngine() { - contextManager.controller.begin(SystemCore::Configuration::macAddress); + SystemCore::Configuration::load(contextManager.memory); + + contextManager.stateManager.getPhaseEvasionGameState().loadHighScore(); + contextManager.stateManager.getRecallGameState().loadHighScore(); + contextManager.controller.begin(SystemCore::Configuration::macAddress()); // If debugging, ensure serial connection is stable before setting up components #if defined(VIRTUALIZATION) || defined(DEBUG) - Serial.begin(SystemCore::Configuration::serialBaud); + Serial.begin(SystemCore::Configuration::serialBaud()); contextManager.leds.reset(); renderLedStrip(); log("Connecting to computer using a serial connection for debugging."); @@ -112,12 +114,6 @@ namespace Engine log("Startup process completed. Transitioning to Main Menu"); } -#ifdef RELEASE - contextManager.memory.begin("lumenlab", false); -#else - contextManager.memory.begin("lumenlab-dev", false); -#endif - randomSeed(esp_random()); } @@ -135,14 +131,14 @@ namespace Engine return; } - for (uint16_t i = 0; i <= SystemCore::Configuration::numLeds; ++i) + for (uint16_t i = 0; i <= SystemCore::Configuration::numLeds(); ++i) { - float phase = std::cos((2 * M_PI * i / SystemCore::Configuration::numLeds) + (2 * M_PI * disconnectedLedPhaseShift / SystemCore::Configuration::numLeds)) * 127 + 128; + float phase = std::cos((2 * M_PI * i / SystemCore::Configuration::numLeds()) + (2 * M_PI * disconnectedLedPhaseShift / SystemCore::Configuration::numLeds())) * 127 + 128; contextManager.leds.buffer[i] = {static_cast(std::floor(phase)), 0, 0}; } disconnectedLedPhaseShift += 0.5; - if (disconnectedLedPhaseShift > SystemCore::Configuration::numLeds) + if (disconnectedLedPhaseShift > SystemCore::Configuration::numLeds()) disconnectedLedPhaseShift = 0; } @@ -155,7 +151,7 @@ namespace Engine #ifdef VIRTUALIZATION Serial.write(0xAA); // sync bytes Serial.write(0x55); - Serial.write(reinterpret_cast(contextManager.leds.getRawColors()), SystemCore::Configuration::numLeds * sizeof(Lights::Color)); + Serial.write(reinterpret_cast(contextManager.leds.getRawColors()), SystemCore::Configuration::numLeds() * sizeof(Lights::Color)); #endif } diff --git a/src/games/demo/player.cpp b/src/games/demo/player.cpp index bf9c82b..72894b0 100644 --- a/src/games/demo/player.cpp +++ b/src/games/demo/player.cpp @@ -10,7 +10,7 @@ namespace Games::Demo float center = (width + 1) / 2.0f; for (uint16_t i = 0; i <= width; ++i) { - uint16_t index = (getPosition() + i) % SystemCore::Configuration::numLeds; + uint16_t index = (getPosition() + i) % SystemCore::Configuration::numLeds(); float intensity = 1.0f - std::abs(i - center) / center; if (intensity < 0) intensity = 0; @@ -27,7 +27,7 @@ namespace Games::Demo float center = (width + 1) / 2.0f; for (uint16_t i = 0; i <= width; ++i) { - uint16_t index = (getPosition() + i) % SystemCore::Configuration::numLeds; + uint16_t index = (getPosition() + i) % SystemCore::Configuration::numLeds(); float intensity = 1.0f - std::abs(i - center) / center; if (intensity < 0) intensity = 0; diff --git a/src/games/phase-evasion/driver.cpp b/src/games/phase-evasion/driver.cpp index 71e9d68..e26e448 100644 --- a/src/games/phase-evasion/driver.cpp +++ b/src/games/phase-evasion/driver.cpp @@ -6,10 +6,10 @@ namespace Games::PhaseEvasion { Driver::Driver(SystemCore::ContextManager *ctx) : contextManager{ctx}, + state{contextManager->stateManager.getPhaseEvasionGameState()}, player{ctx, playerWidth}, flareManager{ctx} { - state = contextManager->stateManager.getPhaseEvasionGameState(); state.reset(); state.current = Actions::Startup; reset(); @@ -65,7 +65,7 @@ namespace Games::PhaseEvasion { for (uint16_t i = 0; i < player.width; ++i) { - uint16_t index = (player.getPosition() + i) % SystemCore::Configuration::numLeds; + uint16_t index = (player.getPosition() + i) % SystemCore::Configuration::numLeds(); contextManager->leds.buffer[index] = player.getColor(); } } @@ -84,7 +84,7 @@ namespace Games::PhaseEvasion } uint16_t flareHead = std::max(flare.getPosition() - flare.width, 0); - uint16_t flareTail = std::min(flare.getPosition(), SystemCore::Configuration::numLeds); + uint16_t flareTail = std::min(flare.getPosition(), SystemCore::Configuration::numLeds()); for (uint16_t i = flareHead; i < flareTail; ++i) { @@ -102,7 +102,7 @@ namespace Games::PhaseEvasion return; uint16_t gemLeft = std::max(gem.getPosition() - gem.width, 0); - uint16_t gemRight = std::min(gem.getPosition(), SystemCore::Configuration::numLeds); + uint16_t gemRight = std::min(gem.getPosition(), SystemCore::Configuration::numLeds()); for (uint16_t i = gemLeft; i < gemRight; ++i) { @@ -118,7 +118,7 @@ namespace Games::PhaseEvasion continue; uint16_t flareStart = std::max(flare.getPosition() - flare.width, 0); - uint16_t flareEnd = std::min(flare.getPosition(), SystemCore::Configuration::numLeds); + uint16_t flareEnd = std::min(flare.getPosition(), SystemCore::Configuration::numLeds()); bool isUnmatchingColor = player.getColor() != flare.getColor(); bool hasEnteredRegion = flareStart <= player.getPosition() + player.width; @@ -128,7 +128,7 @@ namespace Games::PhaseEvasion { flare.impacted = true; state.current = Actions::MuzzleFlash; - gameOverPhaseShift = static_cast(((SystemCore::Configuration::numLeds / 2) + player.getPosition()) % SystemCore::Configuration::numLeds); + gameOverPhaseShift = static_cast(((SystemCore::Configuration::numLeds() / 2) + player.getPosition()) % SystemCore::Configuration::numLeds()); wait(20); } } @@ -138,7 +138,7 @@ namespace Games::PhaseEvasion { if (!gem.isActive() && gem.isReady()) { - const auto randGemPosition = static_cast((esp_random() % static_cast(SystemCore::Configuration::numLeds)) + gem.width); + const auto randGemPosition = static_cast((esp_random() % static_cast(SystemCore::Configuration::numLeds())) + gem.width); gem.spawn(randGemPosition); gemTimeoutTimer.wait(gemCaptureDelay); } @@ -148,7 +148,7 @@ namespace Games::PhaseEvasion if (!gemTimeoutTimer.isReady()) { uint16_t gemStart = std::max(gem.getPosition() - gem.width, 0); - uint16_t gemEnd = std::min(gem.getPosition(), SystemCore::Configuration::numLeds); + uint16_t gemEnd = std::min(gem.getPosition(), SystemCore::Configuration::numLeds()); bool hasEnteredRegion = gemStart <= player.getPosition() + player.width; bool hasNotExitedRegion = gemEnd >= player.getPosition(); @@ -205,7 +205,7 @@ namespace Games::PhaseEvasion void Driver::muzzleFlash() { - for (uint16_t i = 0; i < SystemCore::Configuration::numLeds; ++i) + for (uint16_t i = 0; i < SystemCore::Configuration::numLeds(); ++i) { contextManager->leds.buffer[i] = Lights::Color::White; } @@ -219,9 +219,9 @@ namespace Games::PhaseEvasion void Driver::gameOver() { - for (uint16_t i = 0; i <= SystemCore::Configuration::numLeds; ++i) + for (uint16_t i = 0; i <= SystemCore::Configuration::numLeds(); ++i) { - float offset = std::cos((2.0f * M_PI * i / SystemCore::Configuration::numLeds) - (2.0f * M_PI * static_cast(gameOverPhaseShift) / SystemCore::Configuration::numLeds)); + float offset = std::cos((2.0f * M_PI * i / SystemCore::Configuration::numLeds()) - (2.0f * M_PI * static_cast(gameOverPhaseShift) / SystemCore::Configuration::numLeds())); float phase = offset * 127.5 + 127.5; contextManager->leds.buffer[i] = {static_cast(std::floor(phase) * 0.95), static_cast(std::floor(phase) * 0.15), @@ -231,7 +231,7 @@ namespace Games::PhaseEvasion gameOverPhaseShift += std::cos(gameOverPhaseOffset) / 16.0f; gameOverPhaseOffset += 1.0 / 32.0f; - if (gameOverPhaseShift > SystemCore::Configuration::numLeds) + if (gameOverPhaseShift > SystemCore::Configuration::numLeds()) gameOverPhaseShift = 0.0; if (contextManager->controller.wasPressed(::Player::ControllerButton::Start)) diff --git a/src/games/phase-evasion/flare.cpp b/src/games/phase-evasion/flare.cpp index 0927093..1234a0f 100644 --- a/src/games/phase-evasion/flare.cpp +++ b/src/games/phase-evasion/flare.cpp @@ -19,7 +19,7 @@ namespace Games::PhaseEvasion completedCycle = false; color = _color; speed = _speed; - positionFloat = static_cast(SystemCore::Configuration::numLeds + width); + positionFloat = static_cast(SystemCore::Configuration::numLeds() + width); } void Flare::deactivate() @@ -33,6 +33,6 @@ namespace Games::PhaseEvasion color = Lights::Color::WhiteSmoke; speed = 0.0f; impacted = false; - positionFloat = static_cast(SystemCore::Configuration::numLeds + width); + positionFloat = static_cast(SystemCore::Configuration::numLeds() + width); } } \ No newline at end of file diff --git a/src/games/phase-evasion/state.cpp b/src/games/phase-evasion/state.cpp index 4862784..f9f3981 100644 --- a/src/games/phase-evasion/state.cpp +++ b/src/games/phase-evasion/state.cpp @@ -7,7 +7,11 @@ namespace Games::PhaseEvasion void GameState::reset() { flaresEvaded = gemsCaptured = 0; - highScore = contextManager->memory.getUInt(memoryKeyName); + } + + void GameState::loadHighScore() + { + highScore = contextManager->memory.getUInt(memoryKeyName, 0); } uint16_t GameState::calculateTotalScore() const diff --git a/src/games/recall/driver.cpp b/src/games/recall/driver.cpp index e39b3cd..e72125d 100644 --- a/src/games/recall/driver.cpp +++ b/src/games/recall/driver.cpp @@ -6,10 +6,10 @@ namespace Games::Recall { - Driver::Driver(SystemCore::ContextManager *ctx) : contextManager{ctx} + Driver::Driver(SystemCore::ContextManager *ctx) : contextManager{ctx}, + state{contextManager->stateManager.getRecallGameState()} { setupGameColors(); - state = contextManager->stateManager.getRecallGameState(); state.reset(); state.current = Actions::Startup; contextManager->stateManager.displayShouldUpdate = true; @@ -207,7 +207,7 @@ namespace Games::Recall case Player::ControllerButton::Cross: return {boundary[2], static_cast(boundary[3] - 1)}; case Player::ControllerButton::Square: - return {boundary[3], static_cast(SystemCore::Configuration::numLeds - 1)}; + return {boundary[3], static_cast(SystemCore::Configuration::numLeds() - 1)}; default: return {0, 0}; } @@ -251,14 +251,14 @@ namespace Games::Recall contextManager->stateManager.displayShouldUpdate = true; } - for (uint16_t i = 0; i <= SystemCore::Configuration::numLeds; ++i) + for (uint16_t i = 0; i <= SystemCore::Configuration::numLeds(); ++i) { - float phase = std::cos((2.0f * M_PI * i / SystemCore::Configuration::numLeds) + (2.0f * M_PI * gameOverLedPhaseShift / SystemCore::Configuration::numLeds)) * 127 + 128; + float phase = std::cos((2.0f * M_PI * i / SystemCore::Configuration::numLeds()) + (2.0f * M_PI * gameOverLedPhaseShift / SystemCore::Configuration::numLeds())) * 127 + 128; contextManager->leds.buffer[i] = {static_cast(std::floor(phase)), 0, 0}; } gameOverLedPhaseShift += 0.5f; - if (gameOverLedPhaseShift > SystemCore::Configuration::numLeds) + if (gameOverLedPhaseShift > SystemCore::Configuration::numLeds()) gameOverLedPhaseShift = 0.0f; } } \ No newline at end of file diff --git a/src/games/recall/state.cpp b/src/games/recall/state.cpp index 4506e43..57f9177 100644 --- a/src/games/recall/state.cpp +++ b/src/games/recall/state.cpp @@ -1,22 +1,21 @@ -#include "games/phase-evasion/state.h" +#include "games/recall/state.h" #include "core/context-manager.h" #include "logger.h" namespace Games::Recall { - GameState::GameState(SystemCore::ContextManager *ctx) : contextManager{ctx} - { - reset(); - } - void GameState::reset() { round = 0; - highScore = contextManager->memory.getUInt(memoryKeyName); contextManager->stateManager.displayShouldUpdate = true; } + void GameState::loadHighScore() + { + highScore = contextManager->memory.getUInt(memoryKeyName, 0); + } + void GameState::updateHighScore() { highScore = round; diff --git a/src/player/controller.cpp b/src/player/controller.cpp index 70e767e..d81336a 100644 --- a/src/player/controller.cpp +++ b/src/player/controller.cpp @@ -10,9 +10,9 @@ namespace Player // Following Singleton pattern. Only one instance of the game controller can exist Controller *Controller::instance = nullptr; - void Controller::begin(const char *macAddress) + void Controller::begin(String macAddress) { - instance->controller.begin(macAddress); + instance->controller.begin(macAddress.c_str()); instance->controller.attachOnConnect(&Controller::onConnect); } diff --git a/src/player/player.cpp b/src/player/player.cpp index 00ccc01..3b1aa3f 100644 --- a/src/player/player.cpp +++ b/src/player/player.cpp @@ -10,7 +10,7 @@ namespace Player float step = analogToSpeed(distance, speed); positionPrecise += step; - const float adjustedLedCount = static_cast(SystemCore::Configuration::numLeds - width); + const float adjustedLedCount = static_cast(SystemCore::Configuration::numLeds() - width); if (shouldWrap) { positionPrecise = std::fmod(positionPrecise, adjustedLedCount); diff --git a/src/scenes/canvas/driver.cpp b/src/scenes/canvas/driver.cpp index b96d55d..f5ffc47 100644 --- a/src/scenes/canvas/driver.cpp +++ b/src/scenes/canvas/driver.cpp @@ -6,7 +6,7 @@ namespace Scenes::Canvas { - Driver::Driver(SystemCore::ContextManager *ctx) : contextManager{ctx} + Driver::Driver(SystemCore::ContextManager *ctx) : contextManager{ctx}, state{contextManager->stateManager.getCanvasSceneState()} { reset(); } @@ -19,7 +19,7 @@ namespace Scenes::Canvas checkChangeOccured(); checkStableControllerForDisplay(); - for (uint16_t i; i < SystemCore::Configuration::numLeds; ++i) + for (uint16_t i; i < SystemCore::Configuration::numLeds(); ++i) { contextManager->leds.buffer[i] = contextManager->stateManager.getCanvasSceneState().currentColor; } From 59e0ed4f3043d73a9b902ab7dc11435ff1940eee Mon Sep 17 00:00:00 2001 From: Eric McDaniel Date: Wed, 18 Feb 2026 23:15:47 -0600 Subject: [PATCH 4/9] Fix bug crashing when pool is at max capacity --- include/games/phase-evasion/flare-manager.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/include/games/phase-evasion/flare-manager.h b/include/games/phase-evasion/flare-manager.h index db986c7..4320333 100644 --- a/include/games/phase-evasion/flare-manager.h +++ b/include/games/phase-evasion/flare-manager.h @@ -28,6 +28,6 @@ namespace Games::PhaseEvasion private: SystemCore::ContextManager *contextManager; - std::array flarePool; + std::array flarePool; }; } \ No newline at end of file From f711f2dab4c6cf9854f15f67cbae6184c2e88c9d Mon Sep 17 00:00:00 2001 From: Eric McDaniel Date: Wed, 18 Feb 2026 23:57:32 -0600 Subject: [PATCH 5/9] Set configuration for boundaries/dimensions --- include/core/configuration.h | 32 ++++++++++++-------------------- src/core/configuration.cpp | 22 ++++++++++++++++++---- 2 files changed, 30 insertions(+), 24 deletions(-) diff --git a/include/core/configuration.h b/include/core/configuration.h index 29aedda..f14dcb7 100644 --- a/include/core/configuration.h +++ b/include/core/configuration.h @@ -1,7 +1,6 @@ #pragma once #include -#include #include namespace SystemCore @@ -9,27 +8,20 @@ namespace SystemCore class Configuration { public: - static const String &version() { return version_; } - static const String &macAddress() { return macAddress_; } - static uint16_t numLeds() { return numLeds_; } - static uint32_t serialBaud() { return serialBaud_; } + static const String &version() { return _version; } + static const String &macAddress() { return _macAddress; } + static uint16_t numLeds() { return _numLeds; } + static uint32_t serialBaud() { return _serialBaud; } + static const std::array &recallBoundaries() { return _recallBoundaries; } + static constexpr uint8_t ledDimmerGpio = 34; // set from PCB design - static void load(class Preferences &memory) - { - version_ = memory.getString("version", "v0.0.0"); - macAddress_ = memory.getString("macAddress", "00:1b:fb:8e:87:ac"); - numLeds_ = memory.getUInt("numLeds", 327); - serialBaud_ = memory.getUInt("serialBaud", 921600); - } - - // (in progress) - static constexpr uint16_t recallBoundaries[4] = {0, 113, 168, 281}; - static constexpr uint8_t ledDimmerGpio = 34; + static void load(class Preferences &memory); private: - static String version_; - static String macAddress_; - static uint16_t numLeds_; - static uint32_t serialBaud_; + static String _version; + static String _macAddress; + static uint16_t _numLeds; + static uint32_t _serialBaud; + static std::array _recallBoundaries; }; } \ No newline at end of file diff --git a/src/core/configuration.cpp b/src/core/configuration.cpp index 119f9ff..31980f4 100644 --- a/src/core/configuration.cpp +++ b/src/core/configuration.cpp @@ -2,8 +2,22 @@ namespace SystemCore { - String SystemCore::Configuration::version_; - String SystemCore::Configuration::macAddress_; - uint16_t SystemCore::Configuration::numLeds_; - uint32_t SystemCore::Configuration::serialBaud_; + String SystemCore::Configuration::_version; + String SystemCore::Configuration::_macAddress; + uint16_t SystemCore::Configuration::_numLeds; + uint32_t SystemCore::Configuration::_serialBaud; + std::array SystemCore::Configuration::_recallBoundaries; + + void Configuration::load(class Preferences &memory) + { + _version = memory.getString("version", "v0.0.0"); + _macAddress = memory.getString("macAddress", "00:1b:fb:8e:87:ac"); + _numLeds = memory.getUInt("numLeds", 327); + _serialBaud = memory.getUInt("serialBaud", 921600); + + _recallBoundaries[0] = memory.getUInt("boundary-0", 0); + _recallBoundaries[1] = memory.getUInt("boundary-1", 113); + _recallBoundaries[2] = memory.getUInt("boundary-2", 168); + _recallBoundaries[3] = memory.getUInt("boundary-3", 281); + } } \ No newline at end of file From 2f20e0a30bb2fe558f58c00971c2d7ffb5ad475f Mon Sep 17 00:00:00 2001 From: Eric McDaniel Date: Thu, 19 Feb 2026 00:17:20 -0600 Subject: [PATCH 6/9] Fix dimensions call --- include/core/configuration.h | 3 ++- src/core/configuration.cpp | 13 +++++++------ src/games/recall/driver.cpp | 8 ++++---- 3 files changed, 13 insertions(+), 11 deletions(-) diff --git a/include/core/configuration.h b/include/core/configuration.h index f14dcb7..b13e232 100644 --- a/include/core/configuration.h +++ b/include/core/configuration.h @@ -1,6 +1,7 @@ #pragma once #include +#include #include namespace SystemCore @@ -15,7 +16,7 @@ namespace SystemCore static const std::array &recallBoundaries() { return _recallBoundaries; } static constexpr uint8_t ledDimmerGpio = 34; // set from PCB design - static void load(class Preferences &memory); + static void load(::Preferences &memory); private: static String _version; diff --git a/src/core/configuration.cpp b/src/core/configuration.cpp index 31980f4..58ac56f 100644 --- a/src/core/configuration.cpp +++ b/src/core/configuration.cpp @@ -1,14 +1,15 @@ #include "core/configuration.h" +#include namespace SystemCore { - String SystemCore::Configuration::_version; - String SystemCore::Configuration::_macAddress; - uint16_t SystemCore::Configuration::_numLeds; - uint32_t SystemCore::Configuration::_serialBaud; - std::array SystemCore::Configuration::_recallBoundaries; + String Configuration::_version; + String Configuration::_macAddress; + uint16_t Configuration::_numLeds; + uint32_t Configuration::_serialBaud; + std::array Configuration::_recallBoundaries; - void Configuration::load(class Preferences &memory) + void Configuration::load(::Preferences &memory) { _version = memory.getString("version", "v0.0.0"); _macAddress = memory.getString("macAddress", "00:1b:fb:8e:87:ac"); diff --git a/src/games/recall/driver.cpp b/src/games/recall/driver.cpp index e72125d..6ec513a 100644 --- a/src/games/recall/driver.cpp +++ b/src/games/recall/driver.cpp @@ -91,12 +91,12 @@ namespace Games::Recall auto boundaries = directionBoundaries(gameplayColors[sequenceIndex]); double mu = (boundaries.first + boundaries.second) / 2.0; - const auto &recallBoundary = SystemCore::Configuration::recallBoundaries; + const auto &boundary = SystemCore::Configuration::recallBoundaries(); double delta = ((gameplayColors[sequenceIndex] == Player::ControllerButton::Circle || gameplayColors[sequenceIndex] == Player::ControllerButton::Square) - ? recallBoundary[2] - recallBoundary[1] - : recallBoundary[1] - recallBoundary[0]) / + ? boundary[2] - boundary[1] + : boundary[1] - boundary[0]) / 5; for (uint16_t i = boundaries.first; i <= boundaries.second; ++i) @@ -196,7 +196,7 @@ namespace Games::Recall std::pair Driver::directionBoundaries(Player::ControllerButton button) { - const auto &boundary = SystemCore::Configuration::recallBoundaries; + const auto &boundary = SystemCore::Configuration::recallBoundaries(); switch (button) { From ee2b183703367f658772d0653d4797d8bdf965e5 Mon Sep 17 00:00:00 2001 From: Eric McDaniel Date: Sat, 21 Feb 2026 10:12:54 -0600 Subject: [PATCH 7/9] Fix data type cast mismatch --- src/core/configuration.cpp | 14 +++++++------- src/engine/engine.cpp | 9 +++++++++ 2 files changed, 16 insertions(+), 7 deletions(-) diff --git a/src/core/configuration.cpp b/src/core/configuration.cpp index 58ac56f..f377d30 100644 --- a/src/core/configuration.cpp +++ b/src/core/configuration.cpp @@ -12,13 +12,13 @@ namespace SystemCore void Configuration::load(::Preferences &memory) { _version = memory.getString("version", "v0.0.0"); - _macAddress = memory.getString("macAddress", "00:1b:fb:8e:87:ac"); - _numLeds = memory.getUInt("numLeds", 327); - _serialBaud = memory.getUInt("serialBaud", 921600); + _macAddress = memory.getString("macAddress", "00:00:00:00:00:00"); + _numLeds = static_cast(memory.getString("numLeds", "300").toInt()); + _serialBaud = static_cast(memory.getString("serialBaud", "921600").toInt()); - _recallBoundaries[0] = memory.getUInt("boundary-0", 0); - _recallBoundaries[1] = memory.getUInt("boundary-1", 113); - _recallBoundaries[2] = memory.getUInt("boundary-2", 168); - _recallBoundaries[3] = memory.getUInt("boundary-3", 281); + _recallBoundaries[0] = static_cast(memory.getString("boundary_0", "0").toInt()); + _recallBoundaries[1] = static_cast(memory.getString("boundary_1", "75").toInt()); + _recallBoundaries[2] = static_cast(memory.getString("boundary_2", "150").toInt()); + _recallBoundaries[3] = static_cast(memory.getString("boundary_3", "225").toInt()); } } \ No newline at end of file diff --git a/src/engine/engine.cpp b/src/engine/engine.cpp index f745d47..eb61cf6 100644 --- a/src/engine/engine.cpp +++ b/src/engine/engine.cpp @@ -86,6 +86,15 @@ namespace Engine delay(100); } log("Serial connection established."); + log("Printing environment variables."); + logf("version = %s", SystemCore::Configuration::version()); + logf("macAddress = %s", SystemCore::Configuration::macAddress().c_str()); + logf("numLeds = %u", SystemCore::Configuration::numLeds()); + logf("serialBaud = %u", SystemCore::Configuration::serialBaud()); + logf("boundary_0 = %u", SystemCore::Configuration::recallBoundaries()[0]); + logf("boundary_1 = %u", SystemCore::Configuration::recallBoundaries()[1]); + logf("boundary_2 = %u", SystemCore::Configuration::recallBoundaries()[2]); + logf("boundary_3 = %u", SystemCore::Configuration::recallBoundaries()[3]); #endif log("Connecting to PS3 controller"); From 022598dcdb13c49baf09d3ec8598ef8ed345b266 Mon Sep 17 00:00:00 2001 From: Eric McDaniel Date: Sun, 22 Feb 2026 10:06:14 -0600 Subject: [PATCH 8/9] Remove unnecessary boundary --- include/core/configuration.h | 6 +++--- src/core/configuration.cpp | 9 ++++----- src/core/context-manager.cpp | 2 +- src/engine/engine.cpp | 9 ++++----- src/games/recall/driver.cpp | 12 ++++++------ 5 files changed, 18 insertions(+), 20 deletions(-) diff --git a/include/core/configuration.h b/include/core/configuration.h index b13e232..ba283ff 100644 --- a/include/core/configuration.h +++ b/include/core/configuration.h @@ -13,8 +13,8 @@ namespace SystemCore static const String &macAddress() { return _macAddress; } static uint16_t numLeds() { return _numLeds; } static uint32_t serialBaud() { return _serialBaud; } - static const std::array &recallBoundaries() { return _recallBoundaries; } - static constexpr uint8_t ledDimmerGpio = 34; // set from PCB design + static const std::array &recallBoundaries() { return _recallBoundaries; } + static constexpr uint8_t ledDimmerGpio = 34; // set from PCB design, should not be configurable static void load(::Preferences &memory); @@ -23,6 +23,6 @@ namespace SystemCore static String _macAddress; static uint16_t _numLeds; static uint32_t _serialBaud; - static std::array _recallBoundaries; + static std::array _recallBoundaries; }; } \ No newline at end of file diff --git a/src/core/configuration.cpp b/src/core/configuration.cpp index f377d30..572b8c7 100644 --- a/src/core/configuration.cpp +++ b/src/core/configuration.cpp @@ -7,7 +7,7 @@ namespace SystemCore String Configuration::_macAddress; uint16_t Configuration::_numLeds; uint32_t Configuration::_serialBaud; - std::array Configuration::_recallBoundaries; + std::array Configuration::_recallBoundaries; void Configuration::load(::Preferences &memory) { @@ -16,9 +16,8 @@ namespace SystemCore _numLeds = static_cast(memory.getString("numLeds", "300").toInt()); _serialBaud = static_cast(memory.getString("serialBaud", "921600").toInt()); - _recallBoundaries[0] = static_cast(memory.getString("boundary_0", "0").toInt()); - _recallBoundaries[1] = static_cast(memory.getString("boundary_1", "75").toInt()); - _recallBoundaries[2] = static_cast(memory.getString("boundary_2", "150").toInt()); - _recallBoundaries[3] = static_cast(memory.getString("boundary_3", "225").toInt()); + _recallBoundaries[0] = static_cast(memory.getString("boundary_1", "75").toInt()); + _recallBoundaries[1] = static_cast(memory.getString("boundary_2", "150").toInt()); + _recallBoundaries[2] = static_cast(memory.getString("boundary_3", "225").toInt()); } } \ No newline at end of file diff --git a/src/core/context-manager.cpp b/src/core/context-manager.cpp index 6c416e1..76823af 100644 --- a/src/core/context-manager.cpp +++ b/src/core/context-manager.cpp @@ -16,7 +16,7 @@ namespace SystemCore #endif } - ContextManager::~ContextManager() + ContextManager::~ContextManager() { if (application) { diff --git a/src/engine/engine.cpp b/src/engine/engine.cpp index eb61cf6..0e0a549 100644 --- a/src/engine/engine.cpp +++ b/src/engine/engine.cpp @@ -88,13 +88,12 @@ namespace Engine log("Serial connection established."); log("Printing environment variables."); logf("version = %s", SystemCore::Configuration::version()); - logf("macAddress = %s", SystemCore::Configuration::macAddress().c_str()); + logf("macAddress = %s", SystemCore::Configuration::macAddress()); logf("numLeds = %u", SystemCore::Configuration::numLeds()); logf("serialBaud = %u", SystemCore::Configuration::serialBaud()); - logf("boundary_0 = %u", SystemCore::Configuration::recallBoundaries()[0]); - logf("boundary_1 = %u", SystemCore::Configuration::recallBoundaries()[1]); - logf("boundary_2 = %u", SystemCore::Configuration::recallBoundaries()[2]); - logf("boundary_3 = %u", SystemCore::Configuration::recallBoundaries()[3]); + logf("boundary_1 = %u", SystemCore::Configuration::recallBoundaries()[0]); + logf("boundary_2 = %u", SystemCore::Configuration::recallBoundaries()[1]); + logf("boundary_3 = %u", SystemCore::Configuration::recallBoundaries()[2]); #endif log("Connecting to PS3 controller"); diff --git a/src/games/recall/driver.cpp b/src/games/recall/driver.cpp index 6ec513a..be2c80c 100644 --- a/src/games/recall/driver.cpp +++ b/src/games/recall/driver.cpp @@ -95,8 +95,8 @@ namespace Games::Recall double delta = ((gameplayColors[sequenceIndex] == Player::ControllerButton::Circle || gameplayColors[sequenceIndex] == Player::ControllerButton::Square) - ? boundary[2] - boundary[1] - : boundary[1] - boundary[0]) / + ? boundary[1] - boundary[0] + : boundary[0] - 0) / 5; for (uint16_t i = boundaries.first; i <= boundaries.second; ++i) @@ -201,13 +201,13 @@ namespace Games::Recall switch (button) { case Player::ControllerButton::Triangle: - return {boundary[0], static_cast(boundary[1] - 1)}; + return {0, static_cast(boundary[0] - 1)}; case Player::ControllerButton::Circle: - return {boundary[1], static_cast(boundary[2] - 1)}; + return {boundary[0], static_cast(boundary[1] - 1)}; case Player::ControllerButton::Cross: - return {boundary[2], static_cast(boundary[3] - 1)}; + return {boundary[1], static_cast(boundary[2] - 1)}; case Player::ControllerButton::Square: - return {boundary[3], static_cast(SystemCore::Configuration::numLeds() - 1)}; + return {boundary[2], static_cast(SystemCore::Configuration::numLeds() - 1)}; default: return {0, 0}; } From 049f9b97bad581f1a0cf58677df2e01619a74205 Mon Sep 17 00:00:00 2001 From: Eric McDaniel Date: Mon, 23 Feb 2026 19:23:09 -0600 Subject: [PATCH 9/9] Combine embedded bindings with NVS memory --- .github/workflows/release.yaml | 14 ++++++++------ .vscode/tasks.json | 10 ++-------- platformio.ini | 6 +++++- src/core/configuration.cpp | 6 +++++- 4 files changed, 20 insertions(+), 16 deletions(-) diff --git a/.github/workflows/release.yaml b/.github/workflows/release.yaml index d073009..4cee09f 100644 --- a/.github/workflows/release.yaml +++ b/.github/workflows/release.yaml @@ -38,12 +38,6 @@ jobs: - name: Install PlatformIO run: pip install --upgrade platformio - - name: Build release - run: pio run -e release - - - name: Run tests - run: pio test --environment native - - name: Determine next SemVer from PR labels id: semver run: bash .github/scripts/compute-semver.sh @@ -56,6 +50,14 @@ jobs: env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} + - name: Build release + run: pio run -e release + env: + LUMENLAB_VERSION: ${{ steps.semver.outputs.tag }} + + - name: Run tests + run: pio test --environment native + - name: Create GitHub Release uses: softprops/action-gh-release@v2 with: diff --git a/.vscode/tasks.json b/.vscode/tasks.json index 342cb4f..70e6ec4 100644 --- a/.vscode/tasks.json +++ b/.vscode/tasks.json @@ -127,14 +127,8 @@ { "label": "LumenLab - Upload (release)", "type": "shell", - "command": "platformio", - "args": [ - "run", - "-e", - "release", - "--target", - "upload" - ], + "command": "export LUMENLAB_VERSION=v999.999.999 && platformio run -e release --target upload", + // Alternative command to align with prod releases: "export LUMENLAB_VERSION=$(git describe --tags --abbrev=0) && platformio run -e release --target upload", "problemMatcher": [ "$platformio" ], diff --git a/platformio.ini b/platformio.ini index ac865f1..3db7412 100644 --- a/platformio.ini +++ b/platformio.ini @@ -42,7 +42,11 @@ board = upesy_wroom framework = arduino build_type = release build_unflags = -std=gnu++11 -build_flags = -Os -DRELEASE -std=gnu++2a +build_flags = + -Os + -DRELEASE + -std=gnu++2a + -DLUMENLAB_VERSION=\"${sysenv.LUMENLAB_VERSION}\" [env:native] platform = native diff --git a/src/core/configuration.cpp b/src/core/configuration.cpp index 572b8c7..36137ac 100644 --- a/src/core/configuration.cpp +++ b/src/core/configuration.cpp @@ -1,6 +1,10 @@ #include "core/configuration.h" #include +#ifndef LUMENLAB_VERSION +#define LUMENLAB_VERSION "v999.999.999" +#endif + namespace SystemCore { String Configuration::_version; @@ -11,7 +15,7 @@ namespace SystemCore void Configuration::load(::Preferences &memory) { - _version = memory.getString("version", "v0.0.0"); + _version = LUMENLAB_VERSION; _macAddress = memory.getString("macAddress", "00:00:00:00:00:00"); _numLeds = static_cast(memory.getString("numLeds", "300").toInt()); _serialBaud = static_cast(memory.getString("serialBaud", "921600").toInt());