Theming
A reader whose OS is in dark mode should get a dark page, and one who picks Catppuccin Latte should keep getting Latte on every page after that. chimera handles both with themes. A theme is a class that sets the colors, fonts and spacing every element reads.
Defaults
Each page has one default theme for light mode and one for dark mode. Until the reader picks a theme of their own, the page follows their OS setting:
site
:default_dark_theme(catppuccin.Mocha)
:default_light_theme(catppuccin.Latte)
Without defaults, pages use Light and Dark. A lone Document has the same methods.
Offering more themes
offer_theme adds a theme readers can pick, and a ThemeSwitcher lists it next to the defaults. This site offers six:
site
:offer_theme(catppuccin.Macchiato)
:offer_theme(catppuccin.Frappe)
:offer_theme(Light)
:offer_theme(Dark)
Try a theme:
const picker = Row({ Paragraph("Try a theme:"), ThemeSwitcher() }):align("center")
The browser saves the reader's pick, and links between pages carry it too. That way it sticks even on a site opened straight from disk.
Built-in themes
LightandDark: plain, neutral themes and the fallback defaults.catppuccin.Latte,Frappe,MacchiatoandMocha: the four Catppuccin flavors. Code is colored the way Catppuccin's own editor themes color it.
Your own theme
A theme is a class that implements Theme with a name, a mode and a palette. Any token you leave out of the Palette keeps its Light value:
class Sepia() implements Theme
const name = "sepia"
const mode = "Light"
function palette(self): Palette
return Palette {
background = Color.hex("#f4ecd8"),
text = Color.hex("#5b4636"),
primary = Color.hex("#8b5e3c"),
radius = "2px",
}
end
end
site:offer_theme(Sepia)
The parser finds every theme class by its name. label() sets the name the switcher shows. To restyle the built-in elements themselves, override base_styles().
Every built-in style reads its colors from tokens. Write yours the same way and they'll follow your theme as well (see Styling).