Theme file
A theme is one JSON file that holds the complete visual system for diagrams: colors, fonts,
strokes and sizes. diago embeds four: default (light), dark (dark neutral), midnight (dark
vibrant) and sketch (hand-drawn). A spec picks one with its top-level theme field, and
-theme on the command line overrides it; without either, the theme is default. Text art takes
no theme.
A theme is self-contained: no inheritance, no imports, no overrides between themes. To make a
custom one, copy a real file such as midnight.json below and edit it.
Loading a custom theme
Section titled “Loading a custom theme”A theme name that is not built in is looked up as <name>.json in the directory named by the
DIAGO_THEME_DIR environment variable. Built-in names always win, so a file called dark.json
there never replaces the built-in dark.
mkdir -p ~/.config/diago-themessed 's/"midnight"/"ocean"/; s/"#0f0f14"/"#0b1d2a"/' midnight.json > ~/.config/diago-themes/ocean.jsonDIAGO_THEME_DIR=~/.config/diago-themes diago render -theme ocean spec.json > out.svgThe file name is what chooses the theme: ocean.json is ocean, whatever its name field says. A theme name is a plain file name: a name with a path, such as ../ocean or a/b, is an error.
The same name works in a spec’s "theme": "ocean", with DIAGO_THEME_DIR set. Without the
directory, -theme ocean fails with error: render flow: theme "ocean" not found (exit 2), and a
theme field that does not load is a validation error on theme (exit 1). The editor schemas
list only the four built-in names for theme, so an editor may flag a custom one even though
diago accepts it.
What validation rejects
Section titled “What validation rejects”A theme that fails validation is an error that names the field, such as
theme "bad2": field "node.font.family": font family "Arial" is not supported; must be one of: Inter, Pangolin.
The rules:
stylemust becleanorsketch. The field is required: it selects the renderer, sosketchis what gives the hand-drawn look.- A font
familymust beInterorPangolin, the two faces embedded in diago. Text is measured from the embedded font files, so sizing is the same on every machine. - Every color must be
#rrggbbor#rrggbbaa: no names, no empty values. - Every size and stroke width marked below as positive must be greater than 0.
colorsmust define all seven named colors.
Unknown keys are ignored without a word. A typo in a key name degrades the theme instead of failing, so check a new file by rendering with it.
Fields
Section titled “Fields”Every section below is required. Sizes and widths are in pixels.
Top level
Section titled “Top level”| Field | Type | Notes |
|---|---|---|
name |
string | A label for the theme. Not used to find it. |
description |
string | Free text. |
style |
string | clean or sketch. Required. |
background |
color | The diagram background. Also decides whether colors derived from a color field are made for a light or a dark ground. |
colors |
object | The palette behind a spec’s named color values. Needs red, green, blue, yellow, orange, purple and gray, each a color. |
diff |
object | Optional. The diff palette, below. |
| Field | Type | Notes |
|---|---|---|
fill |
color | The box fill. |
stroke |
color | The box outline. |
stroke_width |
number | Positive. |
corner_radius |
number | The corner radius of rounded boxes. |
font |
font | The label font. |
padding |
{"x", "y"} |
The blank between a node’s label and its box, each side. At least 0. Screen output only: text art ignores it. Class boxes keep their own padding. |
| Field | Type | Notes |
|---|---|---|
stroke |
color | The wire color. |
stroke_width |
number | Positive. |
arrow_size |
number | The arrowhead size. Positive. |
label_font |
font | The edge label font. |
| Field | Type | Notes |
|---|---|---|
fill |
color | The frame fill. |
stroke |
color | The frame outline. |
stroke_width |
number | Positive. |
stroke_dash |
string | The dash pattern of the outline, such as 6,3. Not validated. |
label_font |
font | The frame label font. |
padding |
number | The blank between a group’s content and its frame, on every side. At least 12, so a group’s own wires keep clear of its border. Screen output only: text art ignores it. |
The sequence diagram’s header boxes and lifelines.
| Field | Type | Notes |
|---|---|---|
fill |
color | The header box fill. |
stroke |
color | The header box outline. |
stroke_width |
number | Positive. |
font |
font | The header label font. |
fragment
Section titled “fragment”The sequence diagram’s alt, opt, loop, par and break boxes.
| Field | Type | Notes |
|---|---|---|
fill |
color | The box background. A translucent value such as #rrggbbaa lets the lifelines show through. |
stroke |
color | The box outline. |
stroke_width |
number | Positive. |
stroke_dash |
string | The dash pattern of the outline. Not validated. |
label_font |
font | The font of the type tag and the section guards. |
activation
Section titled “activation”The activation bars on sequence lifelines.
| Field | Type | Notes |
|---|---|---|
fill |
color | The bar fill. |
stroke |
color | The bar outline. |
stroke_width |
number | Positive. |
width |
number | The bar width in px. Positive. Screen output only: text art draws its own bar. |
| Field | Type | Notes |
|---|---|---|
member_font |
font | The font of the attribute and method lines. |
separator_width |
number | The width of the lines between a class box’s compartments. Positive. Their color is the box’s stroke. |
A font
Section titled “A font”Wherever a table says font, the value is an object:
| Field | Type | Notes |
|---|---|---|
family |
string | Inter or Pangolin. |
size |
number | Positive. |
weight |
integer | The font weight, such as 400 or 600. |
color |
color | The text color. |
An optional block that sets the palette of diago diff: the stroke and text color of added,
changed and removed elements. A key it leaves out falls back to the palette, per key:
| Field | Falls back to |
|---|---|
added |
colors.green |
changed |
colors.blue |
removed |
colors.red |
A theme without a diff block therefore still renders diffs: delete the block from a theme and its
diffs use its green, blue and red. Each of the three must be a color.
A complete theme: midnight
Section titled “A complete theme: midnight”{ "name": "midnight", "description": "Dark theme", "style": "clean", "background": "#0f0f14", "colors": { "red": "#ff6b6b", "green": "#51cf66", "blue": "#74c0fc", "yellow": "#ffd43b", "orange": "#ff922b", "purple": "#cc5de8", "gray": "#9090b0" }, "diff": { "added": "#51cf66", "changed": "#74c0fc", "removed": "#ff6b6b" }, "node": { "fill": "#1a1a2e", "stroke": "#3a3a5c", "stroke_width": 1.5, "corner_radius": 8, "font": { "family": "Inter", "size": 14, "weight": 500, "color": "#e0e0e8" }, "padding": { "x": 20, "y": 12 } }, "edge": { "stroke": "#5a5a7c", "stroke_width": 1.5, "arrow_size": 8, "label_font": { "family": "Inter", "size": 12, "weight": 400, "color": "#a0a0b8" } }, "group": { "fill": "#12121e", "stroke": "#2a2a4c", "stroke_width": 1.5, "stroke_dash": "6,3", "label_font": { "family": "Inter", "size": 12, "weight": 600, "color": "#8080a0" }, "padding": 12 }, "actor": { "fill": "#1a1a2e", "stroke": "#3a3a5c", "stroke_width": 1.5, "font": { "family": "Inter", "size": 14, "weight": 600, "color": "#e0e0e8" } }, "fragment": { "fill": "#14141f", "stroke": "#2a2a4c", "stroke_width": 1.5, "stroke_dash": "6,3", "label_font": { "family": "Inter", "size": 11, "weight": 700, "color": "#a0a0b8" } }, "activation": { "fill": "#22223a", "stroke": "#3a3a5c", "stroke_width": 1.0, "width": 10 }, "class": { "member_font": { "family": "Inter", "size": 12, "weight": 400, "color": "#e0e0e8" }, "separator_width": 1.0 }}