0.1.26-alpha release

* refactor: render chat rows from presentation state

* Fix Meshtastic channel sync and add MeshCore CN preset

* Add granular chat notification settings

* Add SD settings backup and restore

* Prepare 0.1.26-alpha release

---------

Co-authored-by: vicliu624 <vicliu@outlook.com>
This commit is contained in:
vicliu authored and GitHub committed 2026-05-19 16:04:42 +08:00
1 parent adf33068d7
commit bf7068b02b
1071 files changed
+78913 -14110

No files matched your search

@@ -0,0 +1,59 @@
#include "linux_sim_app_shell.h"
#include "product_composition/target_ux_binding.h"
#include "ui_lvgl_ux_packs/ux/ux_pack_registry.h"
#include <cstring>
namespace trailmate
{
namespace apps
{
namespace linux_sim_shell
{
LinuxSimAppShell::LinuxSimAppShell(LinuxSimAppShellConfig config)
: config_(config)
{
}
const LinuxSimAppShellConfig& LinuxSimAppShell::config() const
{
return config_;
}
const char* LinuxSimAppShell::targetId() const
{
return config_.product_target_id;
}
const product_composition::TargetProfile* LinuxSimAppShell::targetProfile() const
{
return product_composition::findTargetProfile(targetId());
}
const char* LinuxSimAppShell::activeUxPackId() const
{
const auto* binding = product_composition::findTargetUxBinding(targetId());
return binding != nullptr ? binding->active_ux_pack_id : nullptr;
}
bool LinuxSimAppShell::validate() const
{
const auto& historical_source = linuxSimHistoricalSourceDescriptor();
return config_.target_id != nullptr &&
config_.product_target_id != nullptr &&
targetProfile() != nullptr &&
product_composition::findTargetUxBinding(targetId()) != nullptr &&
config_.ux_pack_id != nullptr &&
std::strcmp(config_.ux_pack_id, activeUxPackId()) == 0 &&
ui_lvgl_ux::findUxPackById(activeUxPackId()) != nullptr &&
config_.historical_source != nullptr &&
historical_source.historical_root_name != nullptr &&
historical_source.historical_role != nullptr &&
historical_source.replacement_owner != nullptr;
}
} // namespace linux_sim_shell
} // namespace apps
} // namespace trailmate
@@ -0,0 +1,41 @@
#pragma once
#include "linux_sim_historical_source_descriptor.h"
#include "product_composition/target_profile.h"
namespace trailmate
{
namespace apps
{
namespace linux_sim_shell
{
struct LinuxSimAppShellConfig
{
const char* target_id = "linux_sim";
const char* product_target_id = "cardputerzero";
const char* ux_pack_id = "simulator_full";
const char* historical_source =
linuxSimHistoricalSourceDescriptor().historical_root_name;
};
class LinuxSimAppShell
{
public:
LinuxSimAppShell() = default;
explicit LinuxSimAppShell(LinuxSimAppShellConfig config);
const LinuxSimAppShellConfig& config() const;
const char* targetId() const;
const product_composition::TargetProfile* targetProfile() const;
const char* activeUxPackId() const;
bool validate() const;
private:
LinuxSimAppShellConfig config_{};
};
} // namespace linux_sim_shell
} // namespace apps
} // namespace trailmate
@@ -0,0 +1,12 @@
#include "linux_sim_historical_source_descriptor.h"
namespace trailmate::apps::linux_sim_shell
{
const LinuxSimHistoricalSourceDescriptor& linuxSimHistoricalSourceDescriptor()
{
static const LinuxSimHistoricalSourceDescriptor descriptor{};
return descriptor;
}
} // namespace trailmate::apps::linux_sim_shell
@@ -0,0 +1,15 @@
#pragma once
namespace trailmate::apps::linux_sim_shell
{
struct LinuxSimHistoricalSourceDescriptor
{
const char* historical_root_name = "removed root linux_sim";
const char* historical_role = "pre-refactor Linux simulator implementation root";
const char* replacement_owner = "apps/linux_sim_shell + modules/ui_ascii_runtime";
};
const LinuxSimHistoricalSourceDescriptor& linuxSimHistoricalSourceDescriptor();
} // namespace trailmate::apps::linux_sim_shell
@@ -0,0 +1,65 @@
#include "linux_sim_runtime_entry.h"
namespace trailmate::apps::linux_sim_shell
{
bool LinuxSimRuntimeEntry::start(const LinuxSimAppShell& shell)
{
ready_ = adoption_probe_.load(shell);
if (ready_)
{
runtime_source_ = LinuxSimRuntimeSource::ScreenGraphAdoption;
fallback_ = false;
return true;
}
runtime_source_ = LinuxSimRuntimeSource::HardcodedFallback;
fallback_ = true;
return startFallback(shell);
}
bool LinuxSimRuntimeEntry::startFallback(const LinuxSimAppShell&)
{
// Phase 10 fallback containment: old simulator routing remains available
// until the renderer fully consumes AsciiRuntimeEntryAdoption descriptors.
return false;
}
bool LinuxSimRuntimeEntry::ready() const
{
return ready_;
}
bool LinuxSimRuntimeEntry::usingPrimaryScreenGraph() const noexcept
{
return runtime_source_ == LinuxSimRuntimeSource::ScreenGraphAdoption &&
ready_ && !fallback_;
}
bool LinuxSimRuntimeEntry::fallbackUsed() const
{
return fallback_;
}
LinuxSimRuntimeSource LinuxSimRuntimeEntry::runtimeSource() const noexcept
{
return runtime_source_;
}
std::size_t LinuxSimRuntimeEntry::menuCount() const
{
return ready_ ? adoption_probe_.menuCount() : 0;
}
std::size_t LinuxSimRuntimeEntry::screenCount() const
{
return ready_ ? adoption_probe_.screenCount() : 0;
}
const trailmate::linux_sim::AsciiRuntimeEntryAdoption&
LinuxSimRuntimeEntry::adoption() const
{
return adoption_probe_.adoption();
}
} // namespace trailmate::apps::linux_sim_shell
@@ -0,0 +1,43 @@
#pragma once
#include "linux_sim_app_shell.h"
#include "linux_sim_runtime_entry_adoption_probe.h"
#include "ui_ascii_runtime/ascii_runtime_entry_adoption.h"
#include <cstddef>
namespace trailmate::apps::linux_sim_shell
{
enum class LinuxSimRuntimeSource
{
ScreenGraphAdoption,
HardcodedFallback,
};
class LinuxSimRuntimeEntry
{
public:
bool start(const LinuxSimAppShell& shell);
bool ready() const;
bool usingPrimaryScreenGraph() const noexcept;
bool fallbackUsed() const;
LinuxSimRuntimeSource runtimeSource() const noexcept;
std::size_t menuCount() const;
std::size_t screenCount() const;
const trailmate::linux_sim::AsciiRuntimeEntryAdoption& adoption() const;
private:
bool startFallback(const LinuxSimAppShell& shell);
private:
LinuxSimRuntimeEntryAdoptionProbe adoption_probe_{};
LinuxSimRuntimeSource runtime_source_ =
LinuxSimRuntimeSource::HardcodedFallback;
bool ready_ = false;
bool fallback_ = true;
};
} // namespace trailmate::apps::linux_sim_shell
@@ -0,0 +1,59 @@
#include "linux_sim_runtime_entry_adoption_probe.h"
#include "ui_lvgl_ux_packs/runtime/compatibility_screen_factory.h"
#include "ui_lvgl_ux_packs/ux/ux_menu_provider.h"
namespace trailmate::apps::linux_sim_shell
{
bool LinuxSimRuntimeEntryAdoptionProbe::load(const LinuxSimAppShell& shell)
{
ready_ = false;
fallback_ = true;
menu_.clear();
screen_bindings_.clear();
presentation_ = {};
if (!shell.validate() ||
!ui_lvgl_ux::buildMenuForUxPack(shell.activeUxPackId(), menu_))
{
return false;
}
ui_lvgl_ux::CompatibilityScreenFactory screen_factory;
screen_factory.buildBindingsForMenu(menu_, screen_bindings_);
presentation_.ux_menu = &menu_;
presentation_.screen_bindings = &screen_bindings_;
ready_ = adoption_.load(presentation_);
fallback_ = !ready_;
return ready_;
}
bool LinuxSimRuntimeEntryAdoptionProbe::ready() const
{
return ready_;
}
bool LinuxSimRuntimeEntryAdoptionProbe::fallbackUsed() const
{
return fallback_;
}
std::size_t LinuxSimRuntimeEntryAdoptionProbe::menuCount() const
{
return ready_ ? adoption_.menuCount() : 0;
}
std::size_t LinuxSimRuntimeEntryAdoptionProbe::screenCount() const
{
return ready_ ? adoption_.screenCount() : 0;
}
const trailmate::linux_sim::AsciiRuntimeEntryAdoption&
LinuxSimRuntimeEntryAdoptionProbe::adoption() const
{
return adoption_;
}
} // namespace trailmate::apps::linux_sim_shell
@@ -0,0 +1,35 @@
#pragma once
#include "linux_sim_app_shell.h"
#include "product_composition/presentation_bundle.h"
#include "ui_ascii_runtime/ascii_runtime_entry_adoption.h"
#include "ui_presentation/menu/menu_model.h"
#include "ui_presentation/screen/screen_binding_registry.h"
#include <cstddef>
namespace trailmate::apps::linux_sim_shell
{
class LinuxSimRuntimeEntryAdoptionProbe
{
public:
bool load(const LinuxSimAppShell& shell);
bool ready() const;
bool fallbackUsed() const;
std::size_t menuCount() const;
std::size_t screenCount() const;
const trailmate::linux_sim::AsciiRuntimeEntryAdoption& adoption() const;
private:
ui::menu::MenuModel menu_{};
ui::screen::ScreenBindingRegistry screen_bindings_{};
product_composition::PresentationBundle presentation_{};
trailmate::linux_sim::AsciiRuntimeEntryAdoption adoption_{};
bool ready_ = false;
bool fallback_ = true;
};
} // namespace trailmate::apps::linux_sim_shell
@@ -0,0 +1,79 @@
#include "linux_sim_runtime_renderer.h"
namespace trailmate::apps::linux_sim_shell
{
bool LinuxSimRuntimeRenderer::render(const LinuxSimRuntimeEntry& entry)
{
ready_ = false;
primary_ = false;
fallback_ = true;
if (entry.usingPrimaryScreenGraph())
{
ready_ = descriptor_renderer_.render(entry.adoption());
primary_ = ready_;
fallback_ = !ready_;
return ready_;
}
if (entry.fallbackUsed())
{
return renderFallback(entry);
}
return false;
}
bool LinuxSimRuntimeRenderer::renderFallback(const LinuxSimRuntimeEntry&)
{
// Phase 11 fallback: old hardcoded ASCII rendering remains available only
// when the runtime entry did not provide primary descriptors.
ready_ = false;
primary_ = false;
fallback_ = true;
return false;
}
bool LinuxSimRuntimeRenderer::ready() const noexcept
{
return ready_;
}
bool LinuxSimRuntimeRenderer::usingPrimaryScreenGraph() const noexcept
{
return primary_;
}
bool LinuxSimRuntimeRenderer::usedPrimaryScreenGraph() const noexcept
{
return primary_;
}
bool LinuxSimRuntimeRenderer::fallbackUsed() const noexcept
{
return fallback_;
}
bool LinuxSimRuntimeRenderer::usedFallback() const noexcept
{
return fallback_;
}
std::size_t LinuxSimRuntimeRenderer::lineCount() const noexcept
{
return ready_ ? descriptor_renderer_.lineCount() : 0;
}
const trailmate::linux_sim::AsciiRenderLine*
LinuxSimRuntimeRenderer::lines() const noexcept
{
return ready_ ? descriptor_renderer_.lines() : nullptr;
}
const char* LinuxSimRuntimeRenderer::line(std::size_t index) const noexcept
{
return ready_ ? descriptor_renderer_.line(index) : nullptr;
}
} // namespace trailmate::apps::linux_sim_shell
@@ -0,0 +1,35 @@
#pragma once
#include "linux_sim_runtime_entry.h"
#include "ui_ascii_runtime/ascii_descriptor_renderer.h"
#include <cstddef>
namespace trailmate::apps::linux_sim_shell
{
class LinuxSimRuntimeRenderer
{
public:
bool render(const LinuxSimRuntimeEntry& entry);
bool ready() const noexcept;
bool usingPrimaryScreenGraph() const noexcept;
bool usedPrimaryScreenGraph() const noexcept;
bool fallbackUsed() const noexcept;
bool usedFallback() const noexcept;
std::size_t lineCount() const noexcept;
const trailmate::linux_sim::AsciiRenderLine* lines() const noexcept;
const char* line(std::size_t index) const noexcept;
private:
bool renderFallback(const LinuxSimRuntimeEntry& entry);
private:
trailmate::linux_sim::AsciiDescriptorRenderer descriptor_renderer_{};
bool ready_ = false;
bool primary_ = false;
bool fallback_ = true;
};
} // namespace trailmate::apps::linux_sim_shell