This is a demo announcement, dismissible and configured in site.json.

Themes

How color themes work, and how to add your own using Material Theme Builder.

The example site ships four themes: Light and Dark (the defaults, a cool blue that matches the Bora logo), plus Green Light and Green Dark. Switch the active family with the toggle in the topbar, and pick any specific theme from the settings drawer. Your choice persists across visits and carries from the homepage into the docs.

How it works

  • Each theme is one CSS file at static/docs/css/theme-<id>.css. It holds the Material color variables, scoped under [data-theme="<id>"].
  • site.json registers each theme. Switching themes only changes the data-theme attribute on the <html> element, and the matching file supplies the colors.
  • Only the default theme in each family loads up front (one light, one dark). Other variants load the first time someone picks them. A returning visitor’s saved choice is applied before the first paint, so there is no flash and nothing extra is downloaded.
site.jsonjson
"themes": [
  { "id": "light",       "label": "Light",      "dark": false, "default": true  },
  { "id": "dark",        "label": "Dark",       "dark": true,  "default": true  },
  { "id": "light-green", "label": "Green Light", "dark": false, "default": false },
  { "id": "dark-green",  "label": "Green Dark",  "dark": true,  "default": false }
]

The dark field groups a theme into the light or dark family. The topbar toggle switches between the two families’ defaults. The settings drawer lists every registered theme.

Important

A dark theme’s id must start with dark. The dark code-block palette and the dark treatments of UI elements (admonitions, badges, version banners) apply to any [data-theme^="dark"], so name dark themes like dark, dark-ocean or dark-green. Light themes have no prefix requirement. The dark: true flag and the dark id prefix do two different jobs: the flag groups the theme for the toggle, and the prefix switches the code and component styling to their dark form.

Adding your own theme

  1. Generate the palette with Material Theme Builder. Pick your brand color and export as Web (CSS). The export gives you a light block and a dark block, each wrapped in a class such as .light or .dark.

  2. Re-scope each block to the attribute the theme reads. Replace the exported class selector with [data-theme="<id>"], and give the dark block an id that starts with dark. The variables themselves do not change.

    static/docs/css/theme-ocean.csscss
    [data-theme="ocean"] {
      --md-sys-color-primary: rgb(0 101 142);
      --md-sys-color-on-primary: rgb(255 255 255);
      /* the rest of the exported variables, unchanged */
    }
  3. Save each block as its own file at static/docs/css/theme-<id>.css, for example theme-ocean.css and theme-dark-ocean.css. Your site’s static/ folder merges with the theme’s, so you do not need to fork anything.

  4. Register the themes in site.json:

    site.jsonjson
    { "id": "ocean",      "label": "Ocean",      "dark": false, "default": false },
    { "id": "dark-ocean", "label": "Ocean Dark", "dark": true,  "default": false }

Each theme then appears in the settings drawer and loads the first time it is picked. To make one the family default, set "default": true on it and remove that flag from the theme it replaces.

Tip

High-contrast and brand variants work the same way. Material Theme Builder can export them all at once. Each one is a single file plus a single line in the registry.

  • themeColor in site.json tints the browser UI per scheme (reference).
  • Code block colors come from theme-syntax.css (Chroma classes). Override it from your site’s static/ the same way.
  • Warning accents (admonitions, banners) default to amber. Override with --nti-color-warning inside your theme file.