use crate::tokens::*;
use std::sync::Arc;
#[derive(Clone, Copy, Debug, Default, PartialEq, Eq, Hash)]
pub enum ColorScheme {
#[default]
Light,
Dark,
}
impl ColorScheme {
pub fn toggle(self) -> Self {
match self {
ColorScheme::Light => ColorScheme::Dark,
ColorScheme::Dark => ColorScheme::Light,
}
}
}
pub trait Theme: Send + Sync + std::fmt::Debug {
fn name(&self) -> &str;
fn color_scheme(&self) -> ColorScheme;
fn colors(&self) -> &ColorTokens;
fn typography(&self) -> &TypographyTokens;
fn spacing(&self) -> &SpacingTokens;
fn radii(&self) -> &RadiusTokens;
fn shadows(&self) -> &ShadowTokens;
fn animations(&self) -> &AnimationTokens;
}
#[derive(Clone)]
pub struct ThemeBundle {
pub name: String,
pub light: Arc<dyn Theme>,
pub dark: Arc<dyn Theme>,
}
impl ThemeBundle {
pub fn new(
name: impl Into<String>,
light: impl Theme + 'static,
dark: impl Theme + 'static,
) -> Self {
Self {
name: name.into(),
light: Arc::new(light),
dark: Arc::new(dark),
}
}
pub fn for_scheme(&self, scheme: ColorScheme) -> Arc<dyn Theme> {
match scheme {
ColorScheme::Light => Arc::clone(&self.light),
ColorScheme::Dark => Arc::clone(&self.dark),
}
}
}
impl std::fmt::Debug for ThemeBundle {
fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
f.debug_struct("ThemeBundle")
.field("name", &self.name)
.finish()
}
}