Theming

RenderConfig(theme = …) picks one of 4 palettes (ThemeName). Each is a ThemeColors record turned into a stylesheet: one CSS custom property per ThemeVar on :root, plus the rules that consume them.

Default

themed(ThemeName.Default)
hotcoldSourceRouteCacheCompute

Dark

themed(ThemeName.Dark)
hotcoldSourceRouteCacheCompute

Forest

themed(ThemeName.Forest)
hotcoldSourceRouteCacheCompute

Neutral

themed(ThemeName.Neutral)
hotcoldSourceRouteCacheCompute

The variables

Every colour and font in the output comes from one of these, so overriding one variable in your own stylesheet restyles everything that uses it. The table is ThemeVar: each member carries its CSS name and description.

VariableUsed by
--mermoid-primaryunused by built-in rules; palette slot for custom stylesheets
--mermoid-primary-borderunused by built-in rules; palette slot for custom stylesheets
--mermoid-primary-textunused by built-in rules; palette slot for custom stylesheets
--mermoid-secondaryunused by built-in rules; palette slot for custom stylesheets
--mermoid-secondary-borderunused by built-in rules; palette slot for custom stylesheets
--mermoid-secondary-textunused by built-in rules; palette slot for custom stylesheets
--mermoid-tertiaryunused by built-in rules; palette slot for custom stylesheets
--mermoid-tertiary-borderunused by built-in rules; palette slot for custom stylesheets
--mermoid-tertiary-textunused by built-in rules; palette slot for custom stylesheets
--mermoid-lineedge stroke, arrowheads, [*] markers
--mermoid-textnode, edge and subgraph labels
--mermoid-main-bkgnode fill
--mermoid-node-bordernode stroke, subgraph frame
--mermoid-backgroundavailable for a page/container background
--mermoid-font-familyall text
--mermoid-font-sizenode and subgraph labels
--mermoid-edge-label-bgthe rect behind an edge label
--mermoid-note-bgnote fill
--mermoid-note-bordernote stroke and connector
--mermoid-note-textnote text
--mermoid-selectionhybrid is-selected outline

The primary/secondary/tertiary triples (colour, border, text) are not consumed by the built-in rules; they exist so a custom stylesheet can pick theme-consistent colours without hardcoding hexes.

resolveVariables

RenderConfig.resolveVariables decides whether the rules reference the variables or the substituted values. It defaults to true.

  • truefill: #1f2020. Self-contained: the SVG renders identically wherever it lands, including contexts that strip <style> or don't cascade (some email clients, some image pipelines). The :root block is still emitted.

  • falsefill: var(--mermoid-main-bkg). Overridable: set the variable anywhere up the cascade and the diagram follows. This is what you want when the diagram is inline in a page you control.

/* resolveVariables = true  (Dark) */
.node-shape { fill: #1f2020; }

/* resolveVariables = false */
.node-shape { fill: var(--mermoid-main-bkg); }

Overriding a variable from the page, with resolveVariables = false:

.diagram-container {
  --mermoid-main-bkg: #eef6ff;
  --mermoid-node-border: #2b6cb0;
}

No re-render — the diagram already on the page restyles.

Beyond the four

The built-in themes are a convenience, not a ceiling. Theme.toStylesheet(colors: ThemeColors) accepts a palette you built yourself, and a whole stylesheet can be merged over any theme — see Custom CSS.

{
  import _root_.mermoid.css.*
  val mine = Theme.colors(ThemeName.Neutral).copy(nodeBorder = "#d97706", lineColor = "#92400e")
  // Theme.toStylesheet(ThemeColors) is the whole extension point: a palette in, a stylesheet out,
  // merged over the chosen theme by customStylesheet.
  MermoidAscent.svgDiagram(
    sample,
    RenderConfig(theme = ThemeName.Neutral, customStylesheet = Some(Theme.toStylesheet(mine))),
  )
}
hotcoldSourceRouteCacheCompute