Xzero UI
Pro library

design

Use the public xzero-ui MCP server at https://mcp.xzero.co.uk/mcp. The complete Free and Pro library is available through this service. No account, sign-in, token, or upstream fallback is required. If the service is unavailable, retry later; do not use upstream services.

The visual rules for anything built with or next to Xzero components. Every token below is defined in components/xzero/foundation.css.

Contents

Color

Components and pages use semantic roles only. Never the --neutral-* ramp, raw hex, or Tailwind color classes.

RoleTokens
Page and surfaces--background, --surface, --surface-raised, --surface-muted
Text--foreground, --text-secondary, --text-muted
Lines--border (default), --border-subtle (inside a surface), --border-strong (inputs, emphasis)
Accent--accent, --accent-strong, --accent-subtle, --accent-foreground
Status--success, --warning, --danger (and --accent for info)
Selection controls--control-on, --control-glyph, --control-track, --control-thumb, --control-thumb-on
Chart series--series-1 to --series-4

Accent with intent. Most of the screen stays neutral. Spend --accent on: the active nav item, a selected row or option, the one data series that matters, progress, and a few interaction details (a link, a count that just changed). Tint with --accent-subtle behind accent text or icons. Do not color headings, card backgrounds, or every icon with it.

Status means status. --success, --warning, and --danger appear only when something succeeded, needs attention, or failed. badge tone="info" uses the accent and may mark emphasis ("Recommended", "New"); the other tones are for status only. Put most of the color on the icon with a faint tint behind it, and always pair it with a short label. Never use green for "nice" or red for "important".

Selection controls that you build yourself use the --control-* tokens, not --accent with --accent-foreground. They are tuned per accent so a thumb always reads against its track.

Brand, metallic, and logo treatments

.premium {
  --metal-plate: linear-gradient(112deg, oklch(93.4% .003 260), oklch(98.6% .002 260) 24%, oklch(91.2% .004 260) 50%, oklch(96.8% .003 260) 74%, oklch(92.6% .004 260));
  --metal-edge: inset 0 0 0 1px oklch(0% 0 0 / .075), inset 0 1px 0 oklch(100% 0 0 / .95);
  --metal-ink: oklch(26% .012 260);
  background: var(--metal-plate);
  box-shadow: var(--metal-edge);
  color: var(--metal-ink);
}
:root[data-theme="dark"] .premium {
  --metal-plate: linear-gradient(112deg, oklch(24.5% .004 260), oklch(30.5% .005 260) 24%, oklch(22.5% .004 260) 50%, oklch(28.5% .005 260) 74%, oklch(24% .004 260));
  --metal-edge: inset 0 0 0 1px oklch(100% 0 0 / .09), inset 0 1px 0 oklch(100% 0 0 / .06);
  --metal-ink: oklch(95.5% .004 260);
}

Type

FaceTokenUseSettings
Geist--font-displayHeadings 30px and up400 or 500, letter-spacing: var(--tracking-display) (-0.03em), line-height: var(--leading-display) (1.1)
Inter--font-bodyBody, labels, controls, small headings400 or 500, letter-spacing: var(--tracking-body) (-0.01em), line-height: var(--leading-body) (1.4)

Surfaces, borders, and shadows

Radii (concentric corners)

--radius-control 18px (inputs, buttons), --radius-panel 26px (menus, nested panels), --radius-surface 34px (cards, large surfaces), --radius-pill (tags, status marks).

A nested corner is the outer radius minus the padding between them, so the curves stay parallel:

/* Correct: inner = outer - padding */
.card  { border-radius: var(--radius-surface); padding: 8px; }
.inner { border-radius: calc(var(--radius-surface) - 8px); } /* 26px, same as --radius-panel */

.panel { border-radius: var(--radius-surface); padding: 24px; }
.panel > .media { border-radius: calc(var(--radius-surface) - 24px); } /* 10px */
/* Incorrect: the same radius inside and out makes a thick, uneven corner */
.card  { border-radius: 34px; padding: 16px; }
.inner { border-radius: 34px; }

Clamp the result at a small positive value (max(6px, calc(...))) when padding is large.

Spacing and sizing

Icons

Themes and accents