theme config, layout preview, container alignment
Server: ThemeConfig entity + CRUD (GET/PUT /theme), SQLite persistence, ThemeUpdate broadcast to ESP32 on save and initial connect. Client: render engine uses theme colors, full-screen redraw on theme change. SPA: theme page with color pickers + presets, layout preview with TS port of layout engine, justify/align controls on containers. DisplayHint refactored to struct (kind + h_align + v_align).
This commit is contained in:
@@ -1,6 +1,6 @@
|
||||
use domain::{
|
||||
ConfigRepository, DataSource, DataSourceId, Layout, LayoutPreset, LayoutPresetId, User,
|
||||
WidgetConfig, WidgetId,
|
||||
ConfigRepository, DataSource, DataSourceId, Layout, LayoutPreset, LayoutPresetId, ThemeConfig,
|
||||
User, WidgetConfig, WidgetId,
|
||||
};
|
||||
use std::collections::HashMap;
|
||||
use std::sync::RwLock;
|
||||
@@ -15,6 +15,7 @@ pub struct MemoryConfigStore {
|
||||
widgets: RwLock<HashMap<WidgetId, WidgetConfig>>,
|
||||
data_sources: RwLock<HashMap<DataSourceId, DataSource>>,
|
||||
layout: RwLock<Option<Layout>>,
|
||||
theme: RwLock<Option<ThemeConfig>>,
|
||||
presets: RwLock<HashMap<LayoutPresetId, LayoutPreset>>,
|
||||
users: RwLock<Vec<User>>,
|
||||
}
|
||||
@@ -25,6 +26,7 @@ impl Default for MemoryConfigStore {
|
||||
widgets: RwLock::new(HashMap::new()),
|
||||
data_sources: RwLock::new(HashMap::new()),
|
||||
layout: RwLock::new(None),
|
||||
theme: RwLock::new(None),
|
||||
presets: RwLock::new(HashMap::new()),
|
||||
users: RwLock::new(Vec::new()),
|
||||
}
|
||||
@@ -125,6 +127,23 @@ impl ConfigRepository for MemoryConfigStore {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
async fn get_theme(&self) -> Result<Option<ThemeConfig>, Self::Error> {
|
||||
let guard = self
|
||||
.theme
|
||||
.read()
|
||||
.map_err(|_| MemoryConfigError::LockPoisoned)?;
|
||||
Ok(guard.clone())
|
||||
}
|
||||
|
||||
async fn save_theme(&self, theme: &ThemeConfig) -> Result<(), Self::Error> {
|
||||
let mut guard = self
|
||||
.theme
|
||||
.write()
|
||||
.map_err(|_| MemoryConfigError::LockPoisoned)?;
|
||||
*guard = Some(theme.clone());
|
||||
Ok(())
|
||||
}
|
||||
|
||||
async fn get_preset(&self, id: LayoutPresetId) -> Result<Option<LayoutPreset>, Self::Error> {
|
||||
let guard = self
|
||||
.presets
|
||||
|
||||
Reference in New Issue
Block a user