more interaction
Signed-off-by: Peter Siegmund <developer@mars3142.org>
This commit is contained in:
@@ -119,114 +119,103 @@ protected:
|
|||||||
// Base implementation intentionally empty - override in derived classes as needed
|
// Base implementation intentionally empty - override in derived classes as needed
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Retrieves a menu item by its index position
|
||||||
|
* @param index Zero-based index of the menu item to retrieve
|
||||||
|
* @return MenuItem object at the specified index
|
||||||
|
*
|
||||||
|
* @pre index must be within valid range [0, getItemCount()-1]
|
||||||
|
* @post Returns a copy of the menu item at the specified position
|
||||||
|
*
|
||||||
|
* @throws std::out_of_range if index is invalid
|
||||||
|
*
|
||||||
|
* @note This method returns a copy of the menu item, not a reference
|
||||||
|
*/
|
||||||
MenuItem getItem(int index);
|
MenuItem getItem(int index);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Gets the total number of menu items in the menu
|
||||||
|
* @return Size of the menu items collection
|
||||||
|
*
|
||||||
|
* @post Returns current count of menu items (>= 0)
|
||||||
|
*
|
||||||
|
* @note This count includes all types of menu items (text, selection, toggle)
|
||||||
|
*/
|
||||||
[[nodiscard]] size_t getItemCount() const;
|
[[nodiscard]] size_t getItemCount() const;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Dynamically adjusts the number of menu items to the specified size
|
||||||
|
* @param size Target number of menu items the menu should contain
|
||||||
|
*
|
||||||
|
* @details If the target size is larger than current item count, new selection
|
||||||
|
* items are added using the first item's values as template. If the
|
||||||
|
* target size is smaller, excess items are removed from the end.
|
||||||
|
*
|
||||||
|
* @pre size must be > 0 and at least one menu item must exist as template
|
||||||
|
* @post Menu contains exactly 'size' number of items
|
||||||
|
*
|
||||||
|
* @note New items are created as selection items with auto-generated names
|
||||||
|
* in the format "Section X" where X is the item number
|
||||||
|
*/
|
||||||
void setItemSize(size_t size);
|
void setItemSize(size_t size);
|
||||||
|
|
||||||
void replaceItem(int index, const MenuItem &item);
|
/**
|
||||||
|
* @brief Toggles the boolean state of a toggle menu item
|
||||||
|
* @param menuItem The toggle menu item whose state should be flipped
|
||||||
|
*
|
||||||
|
* @pre menuItem must be of type TOGGLE
|
||||||
|
* @post The menu item's value is switched between "true" and "false"
|
||||||
|
*
|
||||||
|
* @details Changes "true" to "false" and "false" to "true" for toggle items.
|
||||||
|
* The modified item replaces the original in the menu's item collection.
|
||||||
|
*
|
||||||
|
* @note This method directly modifies the menu's internal state
|
||||||
|
*/
|
||||||
|
void toggle(const MenuItem &menuItem);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @brief Changes the selected value of a selection menu item based on button input
|
||||||
|
* @param menuItem The selection menu item to modify
|
||||||
|
* @param button The directional button pressed (LEFT or RIGHT)
|
||||||
|
*
|
||||||
|
* @pre menuItem must be of type SELECTION with valid values array
|
||||||
|
* @post The menu item's selected index is adjusted based on button direction
|
||||||
|
*
|
||||||
|
* @details LEFT button moves to previous option (wraps to end if at beginning),
|
||||||
|
* RIGHT button moves to next option (wraps to beginning if at end).
|
||||||
|
* Other button types are ignored.
|
||||||
|
*
|
||||||
|
* @note The modified item replaces the original in the menu's item collection
|
||||||
|
*/
|
||||||
|
void switchValue(const MenuItem &menuItem, ButtonType button);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
/**
|
void replaceItem(int index, const MenuItem &item);
|
||||||
* @brief Renders the entire menu on screen
|
|
||||||
* @details Override from Widget base class. Handles the complete rendering process
|
|
||||||
* including menu items, selection highlighting, and scroll indicators.
|
|
||||||
*
|
|
||||||
* @note This method is called during each frame's render cycle
|
|
||||||
*/
|
|
||||||
void render() override;
|
void render() override;
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Handles button press events from the input system
|
|
||||||
* @param button The button that was pressed
|
|
||||||
* @details Override from Widget base class. Processes user input and delegates
|
|
||||||
* to appropriate handler methods based on button type.
|
|
||||||
*
|
|
||||||
* @see ButtonType for available button types
|
|
||||||
*/
|
|
||||||
void onButtonClicked(ButtonType button) override;
|
void onButtonClicked(ButtonType button) override;
|
||||||
|
|
||||||
// Navigation event handlers
|
|
||||||
/**
|
|
||||||
* @brief Handles down arrow/stick input - moves selection down in the menu
|
|
||||||
* @details Moves the current selection to the next menu item, wrapping to the
|
|
||||||
* beginning if at the end of the list.
|
|
||||||
*/
|
|
||||||
void onPressedDown();
|
void onPressedDown();
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Handles up arrow/stick input - moves selection up in the menu
|
|
||||||
* @details Moves the current selection to the previous menu item, wrapping to the
|
|
||||||
* end if at the beginning of the list.
|
|
||||||
*/
|
|
||||||
void onPressedUp();
|
void onPressedUp();
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Handles left arrow/stick input - decreases value for current item
|
|
||||||
* @details For selection items: moves to previous option in the list
|
|
||||||
* For number items: decreases the numeric value
|
|
||||||
* For other items: no action
|
|
||||||
*/
|
|
||||||
void onPressedLeft() const;
|
void onPressedLeft() const;
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Handles right arrow/stick input - increases value for current item
|
|
||||||
* @details For selection items: moves to next option in the list
|
|
||||||
* For number items: increases the numeric value
|
|
||||||
* For other items: no action
|
|
||||||
*/
|
|
||||||
void onPressedRight() const;
|
void onPressedRight() const;
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Handles select/confirm button press
|
|
||||||
* @details Activates the currently selected menu item:
|
|
||||||
* - Text items: triggers selection event
|
|
||||||
* - Toggle items: toggles the boolean state
|
|
||||||
* - Other items: context-dependent behavior
|
|
||||||
*/
|
|
||||||
void onPressedSelect() const;
|
void onPressedSelect() const;
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Handles back/cancel button press
|
|
||||||
* @details Typically used to exit the menu or return to a previous screen.
|
|
||||||
* The specific behavior depends on the menu configuration.
|
|
||||||
*/
|
|
||||||
void onPressedBack() const;
|
void onPressedBack() const;
|
||||||
|
|
||||||
// Rendering helper methods
|
|
||||||
/**
|
|
||||||
* @brief Draws the scroll bar indicating position in long menus
|
|
||||||
* @details Renders a visual scroll indicator when the menu contains more items
|
|
||||||
* than can be displayed on screen simultaneously.
|
|
||||||
*/
|
|
||||||
void drawScrollBar() const;
|
void drawScrollBar() const;
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Draws the selection highlight box around current menu item
|
|
||||||
* @details Renders visual feedback showing which menu item is currently selected
|
|
||||||
* and will respond to user input.
|
|
||||||
*/
|
|
||||||
void drawSelectionBox() const;
|
void drawSelectionBox() const;
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Renders an individual menu item widget
|
|
||||||
* @param item Pointer to the menu item to render (must not be nullptr)
|
|
||||||
* @param font Font to use for rendering text
|
|
||||||
* @param x X coordinate for rendering position
|
|
||||||
* @param y Y coordinate for rendering position
|
|
||||||
*
|
|
||||||
* @pre item must not be nullptr
|
|
||||||
* @pre font must be a valid u8g2 font
|
|
||||||
* @pre x and y must be valid screen coordinates
|
|
||||||
*
|
|
||||||
* @details Handles the rendering of a single menu item based on its type,
|
|
||||||
* including text, current values, and any type-specific visual elements.
|
|
||||||
*/
|
|
||||||
void renderWidget(const MenuItem *item, const uint8_t *font, int x, int y) const;
|
void renderWidget(const MenuItem *item, const uint8_t *font, int x, int y) const;
|
||||||
|
|
||||||
// Member variables
|
// Member variables
|
||||||
size_t m_selected_item = 0; ///< Index of currently selected menu item (0-based)
|
size_t m_selected_item = 0;
|
||||||
std::vector<MenuItem> m_items; ///< Collection of all menu items in display order
|
std::vector<MenuItem> m_items;
|
||||||
menu_options_t *m_options; ///< Pointer to menu configuration options (not owned)
|
menu_options_t *m_options;
|
||||||
};
|
};
|
@@ -142,35 +142,6 @@ public:
|
|||||||
MenuItem(uint8_t id, uint8_t type, std::string text, std::vector<std::string> values, int index,
|
MenuItem(uint8_t id, uint8_t type, std::string text, std::vector<std::string> values, int index,
|
||||||
ButtonCallback callback);
|
ButtonCallback callback);
|
||||||
|
|
||||||
/**
|
|
||||||
* @brief Constructs a boolean/toggle menu item with on/off state
|
|
||||||
* @param id Unique identifier for this menu item within its parent menu
|
|
||||||
* @param type Type identifier defining the item's behavior and visual appearance
|
|
||||||
* @param text Display text shown to the user for this menu item
|
|
||||||
* @param selected Whether this item is currently selected/enabled/checked
|
|
||||||
* @param callback Function to call when the item is activated
|
|
||||||
*
|
|
||||||
* @pre id must be unique within the parent menu context
|
|
||||||
* @pre text should not be empty for proper user interface display
|
|
||||||
* @pre callback should be a valid callable object
|
|
||||||
* @post MenuItem is initialized as a boolean toggle item
|
|
||||||
*
|
|
||||||
* @details Creates a menu item that represents a boolean state (on/off, enabled/disabled,
|
|
||||||
* checked/unchecked). This type is ideal for settings that have binary states
|
|
||||||
* and need to show their current status visually.
|
|
||||||
*
|
|
||||||
* Typical use cases include:
|
|
||||||
* - Feature toggles (e.g., "Auto-save: ON")
|
|
||||||
* - Enable/disable settings (e.g., "Sound: ENABLED")
|
|
||||||
* - Checkbox-style options (e.g., "Show notifications: ✓")
|
|
||||||
* - Boolean configurations (e.g., "Dark mode: OFF")
|
|
||||||
*
|
|
||||||
* @note The selected state is converted to a string value internally for
|
|
||||||
* consistent value handling across all menu item types.
|
|
||||||
* @note The callback typically implements toggle logic to switch between states.
|
|
||||||
*/
|
|
||||||
MenuItem(uint8_t id, uint8_t type, std::string text, bool selected, ButtonCallback callback);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @brief Gets the unique identifier of this menu item
|
* @brief Gets the unique identifier of this menu item
|
||||||
* @return The menu item's unique ID as assigned during construction
|
* @return The menu item's unique ID as assigned during construction
|
||||||
@@ -282,10 +253,12 @@ public:
|
|||||||
|
|
||||||
[[nodiscard]] int getIndex() const;
|
[[nodiscard]] int getIndex() const;
|
||||||
|
|
||||||
std::vector<std::string> getValues() const;
|
[[nodiscard]] std::vector<std::string> getValues() const;
|
||||||
|
|
||||||
[[nodiscard]] size_t getItemCount() const;
|
[[nodiscard]] size_t getItemCount() const;
|
||||||
|
|
||||||
|
[[nodiscard]] MenuItem copyWith(const std::string &value) const;
|
||||||
|
|
||||||
[[nodiscard]] MenuItem copyWith(size_t index) const;
|
[[nodiscard]] MenuItem copyWith(size_t index) const;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
@@ -2,13 +2,32 @@
|
|||||||
|
|
||||||
#include "common/Menu.h"
|
#include "common/Menu.h"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @class LightSettingsMenu
|
||||||
|
* @brief Menu for configuring light system settings including sections and LED parameters
|
||||||
|
* @details This menu extends the base Menu class to provide specialized functionality
|
||||||
|
* for managing light system configurations. It handles dynamic section management
|
||||||
|
* and provides persistence for user settings.
|
||||||
|
*/
|
||||||
class LightSettingsMenu final : public Menu
|
class LightSettingsMenu final : public Menu
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
/**
|
||||||
|
* @brief Constructs a LightSettingsMenu with the specified options
|
||||||
|
* @param options Pointer to menu configuration options structure
|
||||||
|
* @details Initializes the menu with section counter and default section settings
|
||||||
|
*/
|
||||||
explicit LightSettingsMenu(menu_options_t *options);
|
explicit LightSettingsMenu(menu_options_t *options);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
/**
|
||||||
|
* @brief Handles button press events for light settings menu items
|
||||||
|
* @param menuItem The menu item that received the button press
|
||||||
|
* @param button The type of button that was pressed
|
||||||
|
* @details Manages value switching, dynamic section list updates, and
|
||||||
|
* persistence of section values when settings are modified
|
||||||
|
*/
|
||||||
void onButtonPressed(const MenuItem& menuItem, ButtonType button) override;
|
void onButtonPressed(const MenuItem& menuItem, ButtonType button) override;
|
||||||
|
|
||||||
menu_options_t *m_options;
|
menu_options_t *m_options; ///< Pointer to menu configuration options
|
||||||
};
|
};
|
@@ -67,6 +67,47 @@ void Menu::setItemSize(const size_t size)
|
|||||||
m_items.erase(m_items.begin() + static_cast<int>(size + 1), m_items.end());
|
m_items.erase(m_items.begin() + static_cast<int>(size + 1), m_items.end());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
void Menu::toggle(const MenuItem &menuItem)
|
||||||
|
{
|
||||||
|
const auto item =
|
||||||
|
menuItem.copyWith(menuItem.getValue() == std::to_string(true) ? std::to_string(false) : std::to_string(true));
|
||||||
|
replaceItem(menuItem.getId(), item);
|
||||||
|
}
|
||||||
|
|
||||||
|
void Menu::switchValue(const MenuItem& menuItem, ButtonType button)
|
||||||
|
{
|
||||||
|
switch (button)
|
||||||
|
{
|
||||||
|
case ButtonType::LEFT:
|
||||||
|
if (menuItem.getIndex() > 0)
|
||||||
|
{
|
||||||
|
const auto item = menuItem.copyWith(menuItem.getIndex() - 1);
|
||||||
|
replaceItem(menuItem.getId(), item);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
const auto item = menuItem.copyWith(menuItem.getItemCount() - 1);
|
||||||
|
replaceItem(menuItem.getId(), item);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case ButtonType::RIGHT:
|
||||||
|
if (menuItem.getIndex() < menuItem.getItemCount() - 1)
|
||||||
|
{
|
||||||
|
const auto item = menuItem.copyWith(menuItem.getIndex() + 1);
|
||||||
|
replaceItem(menuItem.getId(), item);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
const auto item = menuItem.copyWith(0);
|
||||||
|
replaceItem(menuItem.getId(), item);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
default:
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
void Menu::replaceItem(const int index, const MenuItem &item)
|
void Menu::replaceItem(const int index, const MenuItem &item)
|
||||||
{
|
{
|
||||||
@@ -145,7 +186,7 @@ void Menu::renderWidget(const MenuItem *item, const uint8_t *font, const int x,
|
|||||||
u8g2_DrawFrame(u8g2, frameX, frameY, UIConstants::FRAME_BOX_SIZE, UIConstants::FRAME_BOX_SIZE);
|
u8g2_DrawFrame(u8g2, frameX, frameY, UIConstants::FRAME_BOX_SIZE, UIConstants::FRAME_BOX_SIZE);
|
||||||
|
|
||||||
// Draw checkmark (X) if toggle is true
|
// Draw checkmark (X) if toggle is true
|
||||||
if (item->getValue() == "true")
|
if (item->getValue() == std::to_string(true))
|
||||||
{
|
{
|
||||||
const int checkX1 = frameX + 2;
|
const int checkX1 = frameX + 2;
|
||||||
const int checkY1 = frameY + 2;
|
const int checkY1 = frameY + 2;
|
||||||
@@ -276,7 +317,7 @@ void Menu::addToggle(uint8_t id, const std::string &text, bool selected)
|
|||||||
auto callback = [this](const MenuItem &menuItem, const ButtonType button) -> void {
|
auto callback = [this](const MenuItem &menuItem, const ButtonType button) -> void {
|
||||||
onButtonPressed(menuItem, button);
|
onButtonPressed(menuItem, button);
|
||||||
};
|
};
|
||||||
m_items.emplace_back(id, MenuItemTypes::TOGGLE, text, selected, callback);
|
m_items.emplace_back(id, MenuItemTypes::TOGGLE, text, std::to_string(selected), callback);
|
||||||
}
|
}
|
||||||
|
|
||||||
void Menu::drawScrollBar() const
|
void Menu::drawScrollBar() const
|
||||||
|
@@ -1,16 +1,19 @@
|
|||||||
#include "data/MenuItem.h"
|
#include "data/MenuItem.h"
|
||||||
|
|
||||||
|
// Constructor for basic menu items (text buttons)
|
||||||
MenuItem::MenuItem(const uint8_t id, const uint8_t type, std::string text, ButtonCallback callback)
|
MenuItem::MenuItem(const uint8_t id, const uint8_t type, std::string text, ButtonCallback callback)
|
||||||
: m_id(id), m_type(type), m_text(std::move(text)), m_callback(std::move(callback))
|
: m_id(id), m_type(type), m_text(std::move(text)), m_callback(std::move(callback))
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Constructor for menu items with a single value (toggles)
|
||||||
MenuItem::MenuItem(const uint8_t id, const uint8_t type, std::string text, std::string value,
|
MenuItem::MenuItem(const uint8_t id, const uint8_t type, std::string text, std::string value,
|
||||||
ButtonCallback callback)
|
ButtonCallback callback)
|
||||||
: m_id(id), m_type(type), m_text(std::move(text)), m_value(std::move(value)), m_callback(std::move(callback))
|
: m_id(id), m_type(type), m_text(std::move(text)), m_value(std::move(value)), m_callback(std::move(callback))
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Constructor for menu items with multiple values (selections)
|
||||||
MenuItem::MenuItem(const uint8_t id, const uint8_t type, std::string text, std::vector<std::string> values, int index,
|
MenuItem::MenuItem(const uint8_t id, const uint8_t type, std::string text, std::vector<std::string> values, int index,
|
||||||
ButtonCallback callback)
|
ButtonCallback callback)
|
||||||
: m_id(id), m_type(type), m_text(std::move(text)), m_values(std::move(values)), m_index(index),
|
: m_id(id), m_type(type), m_text(std::move(text)), m_values(std::move(values)), m_index(index),
|
||||||
@@ -18,13 +21,6 @@ MenuItem::MenuItem(const uint8_t id, const uint8_t type, std::string text, std::
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
MenuItem::MenuItem(const uint8_t id, const uint8_t type, std::string text, const bool selected,
|
|
||||||
ButtonCallback callback)
|
|
||||||
: m_id(id), m_type(type), m_text(std::move(text)), m_value(selected ? "true" : "false"),
|
|
||||||
m_callback(std::move(callback))
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
uint8_t MenuItem::getId() const
|
uint8_t MenuItem::getId() const
|
||||||
{
|
{
|
||||||
return m_id;
|
return m_id;
|
||||||
@@ -42,10 +38,12 @@ const std::string &MenuItem::getText() const
|
|||||||
|
|
||||||
const std::string &MenuItem::getValue() const
|
const std::string &MenuItem::getValue() const
|
||||||
{
|
{
|
||||||
|
// Return the selected value from values array if available and index is valid
|
||||||
if (!m_values.empty() && m_index >= 0 && m_index < m_values.size())
|
if (!m_values.empty() && m_index >= 0 && m_index < m_values.size())
|
||||||
{
|
{
|
||||||
return m_values.at(m_index);
|
return m_values.at(m_index);
|
||||||
}
|
}
|
||||||
|
// Otherwise return the direct value
|
||||||
return m_value;
|
return m_value;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -56,6 +54,7 @@ void MenuItem::setValue(const std::string &value)
|
|||||||
|
|
||||||
void MenuItem::onButtonPressed(const ButtonType button) const
|
void MenuItem::onButtonPressed(const ButtonType button) const
|
||||||
{
|
{
|
||||||
|
// Execute the callback function if one is registered
|
||||||
if (m_callback)
|
if (m_callback)
|
||||||
{
|
{
|
||||||
m_callback(*this, button);
|
m_callback(*this, button);
|
||||||
@@ -82,9 +81,20 @@ size_t MenuItem::getItemCount() const
|
|||||||
return m_values.size();
|
return m_values.size();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
MenuItem MenuItem::copyWith(const std::string &value) const
|
||||||
|
{
|
||||||
|
// Create a copy of this menu item with a new value
|
||||||
|
MenuItem copy = *this;
|
||||||
|
copy.m_value = value;
|
||||||
|
return copy;
|
||||||
|
}
|
||||||
|
|
||||||
MenuItem MenuItem::copyWith(const size_t index) const
|
MenuItem MenuItem::copyWith(const size_t index) const
|
||||||
{
|
{
|
||||||
|
// Create a copy of this menu item with a new selected index
|
||||||
MenuItem copy = *this;
|
MenuItem copy = *this;
|
||||||
|
|
||||||
|
// Check for potential overflow when converting size_t to int
|
||||||
if (index > std::numeric_limits<int>::max())
|
if (index > std::numeric_limits<int>::max())
|
||||||
{
|
{
|
||||||
throw std::overflow_error("index is too large");
|
throw std::overflow_error("index is too large");
|
||||||
|
@@ -2,36 +2,69 @@
|
|||||||
|
|
||||||
#include "ui/LightSettingsMenu.h"
|
#include "ui/LightSettingsMenu.h"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @namespace LightMenuItem
|
||||||
|
* @brief Constants for light menu item identifiers
|
||||||
|
*/
|
||||||
namespace LightMenuItem
|
namespace LightMenuItem
|
||||||
{
|
{
|
||||||
constexpr uint8_t MODE = 1;
|
constexpr uint8_t ACTIVATE = 0; ///< ID for the light activation toggle
|
||||||
constexpr uint8_t TOGGLE = 2;
|
constexpr uint8_t MODE = 1; ///< ID for the light mode selection
|
||||||
constexpr uint8_t LED_SETTINGS = 3;
|
constexpr uint8_t LED_SETTINGS = 2; ///< ID for the LED settings menu item
|
||||||
}
|
} // namespace LightMenuItem
|
||||||
|
|
||||||
LightMenu::LightMenu(menu_options_t *options) : Menu(options), m_options(options)
|
LightMenu::LightMenu(menu_options_t *options) : Menu(options), m_options(options)
|
||||||
{
|
{
|
||||||
|
// Add toggle for enabling/disabling the light system
|
||||||
|
addToggle(LightMenuItem::ACTIVATE, "Einschalten", true);
|
||||||
|
|
||||||
|
// Create mode selection options (Day/Night modes)
|
||||||
std::vector<std::string> values;
|
std::vector<std::string> values;
|
||||||
values.emplace_back("Tag");
|
values.emplace_back("Tag"); // Day mode
|
||||||
values.emplace_back("Nacht");
|
values.emplace_back("Nacht"); // Night mode
|
||||||
addSelection(LightMenuItem::MODE, "Modus", values, 0);
|
addSelection(LightMenuItem::MODE, "Modus", values, 0);
|
||||||
|
|
||||||
|
// Add menu item for accessing LED settings submenu
|
||||||
addText(LightMenuItem::LED_SETTINGS, "LED Einstellungen");
|
addText(LightMenuItem::LED_SETTINGS, "LED Einstellungen");
|
||||||
}
|
}
|
||||||
|
|
||||||
void LightMenu::onButtonPressed(const MenuItem &menuItem, const ButtonType button)
|
void LightMenu::onButtonPressed(const MenuItem &menuItem, const ButtonType button)
|
||||||
{
|
{
|
||||||
std::shared_ptr<Widget> widget;
|
std::shared_ptr<Widget> widget;
|
||||||
|
|
||||||
|
// Handle different menu items based on their ID
|
||||||
switch (menuItem.getId())
|
switch (menuItem.getId())
|
||||||
{
|
{
|
||||||
case LightMenuItem::LED_SETTINGS:
|
case LightMenuItem::ACTIVATE: {
|
||||||
widget = std::make_shared<LightSettingsMenu>(m_options);
|
// Toggle the light activation state when SELECT is pressed
|
||||||
break;
|
if (button == ButtonType::SELECT)
|
||||||
|
{
|
||||||
default:
|
toggle(menuItem);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
case LightMenuItem::MODE: {
|
||||||
|
// Switch between day/night modes using left/right buttons
|
||||||
|
switchValue(menuItem, button);
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
case LightMenuItem::LED_SETTINGS: {
|
||||||
|
// Open the LED settings submenu when SELECT is pressed
|
||||||
|
if (button == ButtonType::SELECT)
|
||||||
|
{
|
||||||
|
widget = std::make_shared<LightSettingsMenu>(m_options);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
default:
|
||||||
|
// Handle unknown menu items (no action required)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Push the new widget to the screen stack if one was created
|
||||||
if (m_options && m_options->pushScreen)
|
if (m_options && m_options->pushScreen)
|
||||||
{
|
{
|
||||||
m_options->pushScreen(widget);
|
m_options->pushScreen(widget);
|
||||||
|
@@ -1,61 +1,39 @@
|
|||||||
#include "ui/LightSettingsMenu.h"
|
#include "ui/LightSettingsMenu.h"
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @namespace LightSettingsMenuItem
|
||||||
|
* @brief Constants for light settings menu item identifiers
|
||||||
|
*/
|
||||||
namespace LightSettingsMenuItem
|
namespace LightSettingsMenuItem
|
||||||
{
|
{
|
||||||
constexpr uint8_t SECTION_COUNTER = 0;
|
constexpr uint8_t SECTION_COUNTER = 0; ///< ID for the section counter menu item
|
||||||
}
|
}
|
||||||
|
|
||||||
LightSettingsMenu::LightSettingsMenu(menu_options_t *options) : Menu(options), m_options(options)
|
LightSettingsMenu::LightSettingsMenu(menu_options_t *options) : Menu(options), m_options(options)
|
||||||
{
|
{
|
||||||
|
// Create values vector for section counts (1-99)
|
||||||
std::vector<std::string> values;
|
std::vector<std::string> values;
|
||||||
for (size_t i = 1; i <= 99; i++)
|
for (size_t i = 1; i <= 99; i++)
|
||||||
{
|
{
|
||||||
values.emplace_back(std::to_string(i));
|
values.emplace_back(std::to_string(i));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Add section counter selection (allows choosing number of sections)
|
||||||
addSelection(LightSettingsMenuItem::SECTION_COUNTER, "Sektionen", values, 0);
|
addSelection(LightSettingsMenuItem::SECTION_COUNTER, "Sektionen", values, 0);
|
||||||
|
|
||||||
|
// Add first section configuration item
|
||||||
addSelection(1, "Sektion 1", values, 0);
|
addSelection(1, "Sektion 1", values, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
void LightSettingsMenu::onButtonPressed(const MenuItem &menuItem, const ButtonType button)
|
void LightSettingsMenu::onButtonPressed(const MenuItem &menuItem, const ButtonType button)
|
||||||
{
|
{
|
||||||
/// change visible counter
|
// Handle value switching for the current menu item
|
||||||
switch (button)
|
switchValue(menuItem, button);
|
||||||
{
|
|
||||||
case ButtonType::LEFT:
|
|
||||||
if (menuItem.getIndex() > 0)
|
|
||||||
{
|
|
||||||
const auto item = menuItem.copyWith(menuItem.getIndex() - 1);
|
|
||||||
replaceItem(menuItem.getId(), item);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
const auto item = menuItem.copyWith(menuItem.getItemCount() - 1);
|
|
||||||
replaceItem(menuItem.getId(), item);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
case ButtonType::RIGHT:
|
// Update the section list size based on the section counter value
|
||||||
if (menuItem.getIndex() < menuItem.getItemCount() - 1)
|
|
||||||
{
|
|
||||||
const auto item = menuItem.copyWith(menuItem.getIndex() + 1);
|
|
||||||
replaceItem(menuItem.getId(), item);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
const auto item = menuItem.copyWith(0);
|
|
||||||
replaceItem(menuItem.getId(), item);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
/// change section list
|
|
||||||
setItemSize(std::stoull(getItem(0).getValue()));
|
setItemSize(std::stoull(getItem(0).getValue()));
|
||||||
|
|
||||||
/// persist section values
|
// Persist the changed section values if persistence is available
|
||||||
if (m_options && m_options->persistence && m_options->persistence->save)
|
if (m_options && m_options->persistence && m_options->persistence->save)
|
||||||
{
|
{
|
||||||
const auto key = "section_" + std::to_string(menuItem.getId());
|
const auto key = "section_" + std::to_string(menuItem.getId());
|
||||||
|
Reference in New Issue
Block a user