From 80170642ea1d8bfc9703af217993ae29e6ee81d6 Mon Sep 17 00:00:00 2001 From: jacqueline Date: Tue, 4 Jul 2023 13:06:33 +1000 Subject: Add basic browsing and playing ui --- src/ui/ui_fsm.cpp | 71 ++++++++++++++++++++++++++++++++++++++++++++++++++++--- 1 file changed, 68 insertions(+), 3 deletions(-) (limited to 'src/ui/ui_fsm.cpp') diff --git a/src/ui/ui_fsm.cpp b/src/ui/ui_fsm.cpp index 709778c7..58b1f641 100644 --- a/src/ui/ui_fsm.cpp +++ b/src/ui/ui_fsm.cpp @@ -6,23 +6,33 @@ #include "ui_fsm.hpp" #include +#include "audio_events.hpp" #include "core/lv_obj.h" #include "display.hpp" +#include "event_queue.hpp" #include "lvgl_task.hpp" #include "relative_wheel.hpp" #include "screen.hpp" #include "screen_menu.hpp" +#include "screen_playing.hpp" #include "screen_splash.hpp" +#include "screen_track_browser.hpp" #include "system_events.hpp" #include "touchwheel.hpp" namespace ui { +static constexpr char kTag[] = "ui_fsm"; + +static const std::size_t kRecordsPerPage = 10; + drivers::IGpios* UiState::sIGpios; std::shared_ptr UiState::sTouchWheel; std::shared_ptr UiState::sRelativeWheel; std::shared_ptr UiState::sDisplay; +std::weak_ptr UiState::sDb; +std::stack> UiState::sScreens; std::shared_ptr UiState::sCurrentScreen; auto UiState::Init(drivers::IGpios* gpio_expander) -> bool { @@ -52,6 +62,13 @@ auto UiState::Init(drivers::IGpios* gpio_expander) -> bool { return true; } +void UiState::PushScreen(std::shared_ptr screen) { + if (sCurrentScreen) { + sScreens.push(sCurrentScreen); + } + sCurrentScreen = screen; +} + namespace states { void Splash::exit() { @@ -64,14 +81,62 @@ void Splash::react(const system_fsm::BootComplete& ev) { transit(); } -void Interactive::entry() { - sCurrentScreen.reset(new screens::Menu()); -} +void Interactive::entry() {} void Interactive::react(const system_fsm::KeyLockChanged& ev) { sDisplay->SetDisplayOn(ev.falling); } +void Interactive::react(const system_fsm::StorageMounted& ev) { + sDb = ev.db; + auto db = ev.db.lock(); + if (!db) { + // TODO(jacqueline): Hmm. + return; + } + PushScreen(std::make_shared(db->GetIndexes())); +} + +void Interactive::react(const internal::RecordSelected& ev) { + auto db = sDb.lock(); + if (!db) { + return; + } + + if (ev.record.track()) { + ESP_LOGI(kTag, "selected track '%s'", ev.record.text()->c_str()); + // TODO(jacqueline): We should also send some kind of playlist info here. + auto track = ev.record.track().value(); + events::Dispatch(audio::PlayTrack{ + .id = track.data().id(), + .data = track.data(), + }); + PushScreen(std::make_shared(track)); + } else { + ESP_LOGI(kTag, "selected record '%s'", ev.record.text()->c_str()); + auto cont = ev.record.Expand(kRecordsPerPage); + if (!cont) { + return; + } + auto query = db->GetPage(&cont.value()); + std::string title = ev.record.text().value_or("TODO"); + PushScreen( + std::make_shared(sDb, title, std::move(query))); + } +} + +void Interactive::react(const internal::IndexSelected& ev) { + auto db = sDb.lock(); + if (!db) { + return; + } + + ESP_LOGI(kTag, "selected index %s", ev.index.name.c_str()); + auto query = db->GetTracksByIndex(ev.index, kRecordsPerPage); + PushScreen(std::make_shared(sDb, ev.index.name, + std::move(query))); +} + } // namespace states } // namespace ui -- cgit v1.2.3