Xzero UI
Pro library

composition

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.

Xzero components own their internals; your CSS module owns the layout.

Contents

Plan the page

Write three lines before you choose anything:

Job: what the person comes here to do ("change their plan and see what it costs")
Primary action: exactly one ("Upgrade to Team")
Regions: each region and the Xzero item it uses (components.md)

Hierarchy: one h1; section headings describe content; the primary action is the only primary button on screen (button defaults to primary, so set variant on every other one); secondary actions go in split-button or dropdown-menu.

One page container

An app has one page container that sets the max width and the gutters, usually in the app layout. Everything inside fills its column. Blocks and cards never add their own page gutter. A page may narrow its reading column with max-width alone (settings and forms at 640 to 720px), never with extra padding.

/* Correct: one container, children fill it */
.page {
  width: 100%;
  max-width: 1200px;
  margin-inline: auto;
  padding: 32px clamp(16px, 4vw, 32px);
  display: grid;
  gap: 24px;
}
.page > * { min-width: 0; }
// Incorrect: a second container inside the page doubles the gutter
<main className={styles.page}>
  <section style={{ maxWidth: 960, margin: "0 auto", padding: "0 24px" }}>...</section>
</main>

Checks:

Product pages and dashboards

.tableCard { border: 1px solid var(--border); border-radius: var(--radius-surface); overflow: hidden; }
.tableScroll { overflow-x: auto; overscroll-behavior-x: contain; }
// Correct: one group, divided rows
<section aria-labelledby="notifications">
  <h2 id="notifications">Notifications</h2>
  <div className={styles.group}>
    <div className={styles.row}><span id="updates">Product updates</span><Switch aria-labelledby="updates" /></div>
    <div className={styles.row}><span id="summary">Weekly summary</span><Switch aria-labelledby="summary" /></div>
  </div>
</section>

// Incorrect: a card per row, an eyebrow, and a second heading level for nothing
<p className="eyebrow">PREFERENCES</p>
<Card title="Product updates"><Switch /></Card>
<Card title="Weekly summary"><Switch /></Card>

Marketing pages

States

Design every data region for all of them before you finish:

StateTreatment
Loadingskeleton in the final layout, same dimensions, aria-busy on the region
Emptyempty-state with why it is empty and one next step
ErrorInline alert next to the cause, with a retry
SuccessConfirm in place: the button label, the row, the value
DisabledExplain why nearby, or hide the control. A save button disabled until something changes needs no explanation
Long contentWrap or truncate with the full value reachable

React correctness

// Incorrect: differs between server and client
const [theme] = useState(localStorage.getItem("theme") ?? "light");

// Correct: the server snapshot ("light") is also the first client render, then it syncs
const subscribe = (onChange: () => void) => {
  window.addEventListener("storage", onChange);
  return () => window.removeEventListener("storage", onChange);
};
const theme = useSyncExternalStore(subscribe, () => localStorage.getItem("theme") ?? "light", () => "light");

Page recipes

Free items unless marked Pro. Full worked code: example-settings.md, example-pricing.md, example-dashboard.md.

PageBuild it from
Sign in and sign upsign-in or login-centered, then signup-form, otp-input. Pro: login-split, login-immersive
Dashboardh1 and segmented-control for range, metric-card row, line-chart or bar-chart, sortable-data-table. Pro: metrics-dashboard, metric-explorer
SettingsSections of input, select, switch rows, a save button, confirm-morph for deleting. Pro: settings-page, security-settings
Record listfilter-toolbar or search-field, sortable-data-table, pagination, empty-state. Pro: data-grid
Pricingbilling-toggle and BillingPrice, plan cards or radio-cards, comparison-table, faq-section. Pro: pricing-calculator, usage-pricing
Landing pagesite-header, hero-section, logo-marquee, stats-band, comparison-table, faq-section, cta-section, site-footer. Pro: feature-bento, scroll-story
App shellcommand-palette, user-menu, notification-center. Pro: sidebar-rail, workspace-sidebar
Not found, offline, no resultsempty-states block, or empty-state inside a region