This commit is contained in:
khodowany
2026-09-30 18:23:25 -05:00
parent 896de203b3
commit 2a1aa2c67a
40 changed files with 1197 additions and 610 deletions
+10
View File
@@ -39,6 +39,16 @@ enum class sprite : std::size_t {
ELECTRIC,
VOCAL,
UNAVAILABLE,
MAIN_MENU,
PERFORMANCE,
SETTINGS,
PLAYBACK,
METRONOME,
TEMPO,
BACK,
ON,
OFF,
BPM,
DIGIT_0,
DIGIT_1,
DIGIT_2,
+2 -15
View File
@@ -3,21 +3,11 @@
#include <array>
#include <cstdint>
#include <vamp_pico/artwork.hpp>
#include <vamp_pico/http_client.hpp>
#include <vamp_style.hpp>
#include <vamp_pico/screen.hpp>
namespace vamp_pico {
constexpr auto display_width = std::int32_t{320};
constexpr auto display_height = std::int32_t{240};
enum class link_status { CONNECTING,
OFFLINE,
CONNECTED,
ERROR };
class display {
public:
auto init() -> void;
@@ -32,11 +22,8 @@ private:
title_cache title_{};
std::array<std::bool_t, display_height> dirty_{};
link_status link_{link_status::CONNECTING};
std::bool_t active_{};
std::bool_t busy_{};
sprite part_{sprite::COUNT};
std::uint32_t page_{};
std::uint32_t pages_{};
remote_display_state state_{};
std::uint64_t last_write_ms_{};
std::size_t next_row_{};
};
+8
View File
@@ -19,9 +19,17 @@ struct remote_display_state {
std::char_t title[96]{};
std::char_t part[48]{};
std::char_t mode[24]{};
std::char_t focus[32]{};
std::bool_t playback{};
std::bool_t metronome{};
std::bool_t editing{};
std::uint32_t bpm{120U};
std::array<std::char_t, vamp_protocol::title_id_size + 1U> title_image{};
std::uint32_t page{};
std::uint32_t pages{};
auto operator==(remote_display_state const &other) const -> std::bool_t {
return active == other.active && std::string_view{title} == other.title && std::string_view{part} == other.part && std::string_view{mode} == other.mode && std::string_view{focus} == other.focus && playback == other.playback && metronome == other.metronome && editing == other.editing && bpm == other.bpm && title_image == other.title_image && page == other.page && pages == other.pages;
}
};
auto parse_remote_display_body(std::string_view body, vamp_pico::remote_display_state &state) -> std::bool_t;
+22
View File
@@ -0,0 +1,22 @@
#pragma once
#include <array>
#include <vamp_pico/artwork.hpp>
#include <vamp_pico/http_client.hpp>
#include <vamp_style.hpp>
namespace vamp_pico {
constexpr auto display_width = std::int32_t{320};
constexpr auto display_height = std::int32_t{240};
enum class link_status { CONNECTING,
OFFLINE,
CONNECTED,
ERROR };
auto render_scanline(std::array<std::uint16_t, vamp_pico::display_width> &row, std::size_t y, vamp_pico::remote_display_state const &state, vamp_pico::link_status link, std::bool_t busy, vamp_pico::title_cache const &title, std::string_view atlas) -> void;
}
-2
View File
@@ -8,8 +8,6 @@
namespace vamp_protocol {
constexpr std::char_t root_path[] = "/";
constexpr std::char_t status_path[] = "/api/status";
constexpr std::char_t remote_next_path[] = "/api/remote/next";
constexpr std::char_t remote_previous_path[] = "/api/remote/previous";
constexpr std::char_t remote_select_path[] = "/api/remote/select";
+9 -11
View File
@@ -17,18 +17,16 @@ struct color {
std::uint8_t a{255};
};
constexpr auto background = vamp_style::color{9, 12, 14, 255};
constexpr auto panel = vamp_style::color{21, 27, 30, 255};
constexpr auto ink = vamp_style::color{238, 244, 241, 255};
constexpr auto muted = vamp_style::color{137, 151, 149, 255};
constexpr auto rule = vamp_style::color{66, 78, 78, 255};
constexpr auto paper = vamp_style::color{2, 3, 3, 255};
constexpr auto paper_ink = vamp_style::color{246, 248, 244, 255};
constexpr auto accent = vamp_style::color{232, 190, 70, 255};
constexpr auto selection = vamp_style::color{41, 100, 111, 255};
constexpr auto background = vamp_style::color{255, 255, 255, 255};
constexpr auto panel = vamp_style::color{245, 247, 246, 255};
constexpr auto ink = vamp_style::color{29, 37, 35, 255};
constexpr auto muted = vamp_style::color{92, 104, 100, 255};
constexpr auto rule = vamp_style::color{211, 220, 217, 255};
constexpr auto accent = vamp_style::color{27, 112, 99, 255};
constexpr auto selection = vamp_style::color{230, 241, 237, 255};
constexpr auto connecting = vamp_style::color{45, 111, 185, 255};
constexpr auto retrying = vamp_style::color{229, 171, 37, 255};
constexpr auto connected = vamp_style::color{40, 170, 88, 255};
constexpr auto retrying = vamp_style::color{156, 104, 23, 255};
constexpr auto connected = vamp_style::color{27, 112, 99, 255};
constexpr auto danger = vamp_style::color{190, 63, 58, 255};
auto rgb565(vamp_style::color value) -> std::uint16_t;
@@ -5,12 +5,11 @@
#include <mutex>
#include <optional>
#include <boost/json/value.hpp>
#include <ligo.hpp>
#include <vamp_protocol/page_control.hpp>
#include <vamp_zero/config.hpp>
#include <vamp_zero/menu.hpp>
#include <vamp_zero/types.hpp>
namespace vamp_zero {
@@ -21,6 +20,7 @@ public:
auto config() const -> vamp_zero::config;
auto snapshot() const -> vamp_zero::app_state;
auto apply(vamp_protocol::page_command command) -> vamp_zero::app_state;
auto apply(vamp_zero::menu_action const &action) -> vamp_zero::app_state;
auto heartbeat() -> vamp_zero::app_state;
auto refresh_connection() -> std::optional<vamp_zero::app_state>;
auto set_observer(std::function<void(vamp_zero::app_state)> observer) -> void;
@@ -36,7 +36,6 @@ private:
};
auto make_router(vamp_zero::control_state &state) -> ligo::service_router;
auto portal_status_json(vamp_zero::config const &config, vamp_zero::app_state const &state) -> boost::json::value;
auto validated_title_path(std::string const &assets_path, std::string const &identifier) -> std::expected<std::string, modulus::error>;
}
+34
View File
@@ -0,0 +1,34 @@
#pragma once
#include <string>
#include <vamp_zero/types.hpp>
namespace vamp_zero {
enum class menu_action_kind { ACTIVATE,
PREVIOUS,
NEXT,
TEMPO_DOWN,
TEMPO_UP };
struct menu_action {
vamp_zero::menu_action_kind kind{};
std::size_t row{};
std::uint64_t revision{};
std::shared_ptr<vamp_zero::catalog const> catalog{};
};
struct menu_item {
std::string label{};
std::string detail{};
};
auto menu_count(vamp_zero::app_state const &state) -> std::size_t;
auto menu_selection(vamp_zero::app_state const &state) -> std::size_t;
auto menu_title(vamp_zero::app_state const &state) -> std::string;
auto menu_row(vamp_zero::app_state const &state, std::size_t row) -> vamp_zero::menu_item;
auto apply_menu_action(vamp_zero::app_state state, vamp_zero::menu_action const &action) -> vamp_zero::app_state;
}
+36
View File
@@ -0,0 +1,36 @@
#pragma once
#include <chrono>
#include <optional>
#include <set>
#include <vector>
#include <luma.hpp>
#include <vamp_style.hpp>
#include <vamp_zero/menu.hpp>
namespace vamp_zero {
struct menu_target {
luma::rect bounds{};
vamp_zero::menu_action action{};
};
auto menu_layout(luma::rect bounds, vamp_zero::app_state const &state) -> std::vector<vamp_zero::menu_target>;
auto draw_label(luma::draw_context &context, luma::rect bounds, std::string text, std::float32_t size, vamp_style::color color) -> void;
auto draw_menu(luma::draw_context &context, luma::rect bounds, vamp_zero::app_state const &state) -> void;
auto draw_header(luma::draw_context &context, luma::rect bounds, vamp_zero::app_state const &state) -> void;
class menu_touch {
public:
auto handle(luma::touch_event const &event, luma::rect bounds, vamp_zero::app_state const &state) -> std::optional<vamp_zero::menu_action>;
private:
std::set<std::int32_t> fingers_{};
std::optional<vamp_zero::menu_target> target_{};
luma::point origin_{};
std::chrono::steady_clock::time_point pressed_{};
};
}
-3
View File
@@ -3,8 +3,6 @@
#include <expected>
#include <string>
#include <boost/json/value.hpp>
#include <modulus.hpp>
#include <vamp_protocol/page_control.hpp>
@@ -14,7 +12,6 @@
namespace vamp_zero {
auto apply_app_command(vamp_zero::app_state state, vamp_protocol::page_command command) -> vamp_zero::app_state;
auto app_status_json(vamp_zero::app_state const &state) -> boost::json::value;
auto remote_display_text(vamp_zero::app_state const &state) -> std::string;
auto validate_app_state(vamp_zero::app_state const &state) -> std::expected<void, modulus::error>;
+1
View File
@@ -19,6 +19,7 @@ public:
touch_input(touch_input const &) = delete;
auto operator=(touch_input const &) -> touch_input & = delete;
auto handle(luma::touch_event const &event) -> std::bool_t;
auto reset() -> void;
auto stop() -> void;
private:
struct state;
+4 -5
View File
@@ -62,6 +62,7 @@ struct score_reference {
enum class app_mode {
MAIN_MENU,
SETTINGS_MENU,
PERFORMANCE_SONG_MENU,
PERFORMANCE_PART_MENU,
PERFORMANCE_SCORE,
@@ -83,16 +84,14 @@ struct app_state {
vamp_zero::app_mode mode{vamp_zero::app_mode::MAIN_MENU};
vamp_zero::audio_state audio{};
std::size_t selected_main_menu_index{};
std::size_t selected_settings_index{1U};
std::size_t remembered_settings_index{1U};
std::size_t selected_song_index{};
std::size_t selected_part_index{};
std::string active_part_id{};
std::size_t page_index{};
std::uint64_t score_session{};
std::uint64_t next_count{};
std::uint64_t previous_count{};
std::uint64_t select_count{};
std::uint64_t heartbeat_count{};
std::string last_command{"startup"};
std::uint64_t input_revision{};
std::bool_t pico_connected{false};
};
+3 -12
View File
@@ -14,6 +14,7 @@
#include <vamp_protocol/page_control.hpp>
#include <vamp_zero/config.hpp>
#include <vamp_zero/types.hpp>
#include <vamp_zero/menu.hpp>
namespace vamp_zero {
@@ -21,23 +22,15 @@ struct ui_runtime;
class score_loader;
struct ui_state {
vamp_zero::app_state app{};
std::string ap_ssid{};
std::string zero_ip{};
std::uint16_t port{8080};
};
class zero_ui {
public:
zero_ui(boost::asio::any_io_executor executor, luma::application_config config, vamp_zero::database_config database, std::string assets_path, std::function<void(vamp_protocol::page_command)> command_handler = {});
zero_ui(boost::asio::any_io_executor executor, luma::application_config config, vamp_zero::database_config database, std::string assets_path, std::function<void(vamp_protocol::page_command)> command_handler = {}, std::function<void(vamp_zero::menu_action)> menu_handler = {});
~zero_ui();
zero_ui(zero_ui const &) = delete;
auto operator=(zero_ui const &) -> zero_ui & = delete;
auto run() -> std::expected<void, modulus::error>;
auto stop() -> void;
auto publish(vamp_zero::ui_state state) -> std::expected<void, modulus::error>;
auto snapshot() const -> vamp_zero::ui_state;
auto publish(vamp_zero::app_state state) -> std::expected<void, modulus::error>;
auto selected_score_loader() const -> std::shared_ptr<vamp_zero::score_loader>;
private:
std::shared_ptr<luma::application> application_;
@@ -45,6 +38,4 @@ private:
std::shared_ptr<vamp_zero::score_loader> score_loader_;
};
auto make_ui_state(vamp_zero::config const &config, vamp_zero::app_state app) -> vamp_zero::ui_state;
}