Files
MontaukOS/template/sysroot/include/gui/mtk/theme.hpp
T

134 lines
3.7 KiB
C++

/*
* theme.hpp
* Montauk Toolkit theme tokens and color helpers
* Copyright (c) 2026 Daniel Hammer
*/
#pragma once
#include "gui/gui.hpp"
#include "gui/mtk/settings.hpp"
namespace gui::mtk {
inline Color mix(Color base, Color tint, uint8_t tint_alpha) {
auto blend = [tint_alpha](uint8_t a, uint8_t b) -> uint8_t {
return (uint8_t)((((uint16_t)a * (255 - tint_alpha)) +
((uint16_t)b * tint_alpha) + 127) / 255);
};
return Color::from_rgb(blend(base.r, tint.r),
blend(base.g, tint.g),
blend(base.b, tint.b));
}
inline Color lighten(Color c, uint8_t amount) {
return mix(c, colors::WHITE, amount);
}
inline Color darken(Color c, uint8_t amount) {
return mix(c, colors::BLACK, amount);
}
// Light selection/hover tint derived from the desktop accent. Returns the
// canonical MENU_HOVER for the default blue accent so existing visuals are
// preserved exactly; otherwise tints white with ~11% of the accent.
inline Color accent_hover_tint(Color accent) {
if (accent.r == colors::ACCENT.r && accent.g == colors::ACCENT.g
&& accent.b == colors::ACCENT.b)
return colors::MENU_HOVER;
return mix(colors::WHITE, accent, 28);
}
struct Theme {
Color window_bg;
Color surface;
Color surface_alt;
Color surface_hover;
Color border;
Color text;
Color text_muted;
Color text_subtle;
Color text_inverse;
Color accent;
Color accent_hover;
Color accent_soft;
Color accent_fg;
Color selection;
Color text_selection;
Color danger;
Color danger_hover;
Color danger_soft;
Color danger_fg;
Color disabled_bg;
Color disabled_fg;
Color badge_admin_bg;
Color badge_admin_fg;
Color badge_user_bg;
Color badge_user_fg;
int radius_sm;
int radius_md;
int control_h;
int tab_h;
int gap_xs;
int gap_sm;
int gap_md;
int gap_lg;
};
inline Theme make_theme(Color accent) {
Theme theme {};
theme.window_bg = colors::WINDOW_BG;
theme.surface = Color::from_rgb(0xF5, 0xF5, 0xF5);
theme.surface_alt = Color::from_rgb(0xF8, 0xF8, 0xF8);
theme.surface_hover = mix(theme.surface, accent, 18);
theme.border = colors::BORDER;
theme.text = colors::TEXT_COLOR;
theme.text_muted = Color::from_rgb(0x88, 0x88, 0x88);
theme.text_subtle = Color::from_rgb(0x66, 0x66, 0x66);
theme.text_inverse = colors::WHITE;
theme.accent = accent;
theme.accent_hover = darken(accent, 32);
theme.accent_soft = lighten(accent, 214);
theme.accent_fg = colors::WHITE;
theme.selection = accent;
theme.text_selection = Color::from_rgb(0xB0, 0xD0, 0xF0);
theme.danger = Color::from_rgb(0xD0, 0x3E, 0x3E);
theme.danger_hover = Color::from_rgb(0xDD, 0x44, 0x44);
theme.danger_soft = Color::from_rgb(0xF7, 0xDF, 0xDF);
theme.danger_fg = colors::WHITE;
theme.disabled_bg = Color::from_rgb(0xCC, 0xCC, 0xCC);
theme.disabled_fg = colors::WHITE;
theme.badge_admin_bg = Color::from_rgb(0xE8, 0xD8, 0xF0);
theme.badge_admin_fg = Color::from_rgb(0x7B, 0x3E, 0xB8);
theme.badge_user_bg = Color::from_rgb(0xE0, 0xE8, 0xF0);
theme.badge_user_fg = Color::from_rgb(0x36, 0x7B, 0xF0);
theme.radius_sm = 3;
theme.radius_md = 4;
theme.control_h = 30;
theme.tab_h = 36;
theme.gap_xs = 2;
theme.gap_sm = 6;
theme.gap_md = 10;
theme.gap_lg = 16;
return theme;
}
// Zero-arg overload pulls the accent from the desktop appearance settings, so
// MTK widgets (buttons, menus, etc.) automatically pick up the user's chosen
// accent without each caller having to plumb it through.
inline Theme make_theme() {
return make_theme(load_system_accent());
}
} // namespace gui::mtk