---
version: alpha
name: Superwall
description: >
  Superwall's brand design system, spanning two registers that share one DNA:
  Marketing Assets (landing pages, ads, slides, videos, decks, emails) and
  Application Design (apps, dashboards, native product UI). Both are flat,
  square-cornered, structured by hairline borders, with editorial Manrope type,
  italic mono eyebrows and figures, warm-cream / warm-ink surfaces, and a single
  fixed orange accent. Shared foundations are defined once below. Where the two
  registers genuinely diverge - type scale, fonts, dark-mode surfaces, borders,
  layout model, component contracts - the values split under `marketing:` and
  `application:` keys here, and into the "Marketing Assets" and "Application
  Design" sections of the prose.
colors:
  # -- Fixed scale - SHARED, identical in both registers. Does NOT swap by mode.
  #    Eight hue families x five fixed steps (100 lightest -> 500 darkest).
  black-100: "#272522"
  black-200: "#211f1d"
  black-300: "#211f1d"
  black-400: "#191816"
  black-500: "#0c0b0a"

  cream-100: "#fdfef6"
  cream-200: "#fbfde7"
  cream-300: "#fbfde7"
  cream-400: "#e2e4d0"
  cream-500: "#c9cab9"

  blue-100: "#b4c4eb"
  blue-200: "#7c97dd"
  blue-300: "#446bce"
  blue-400: "#29407c"
  blue-500: "#14203e"

  teal-100: "#a4f4f4"
  teal-200: "#67edec"
  teal-300: "#46d7d4"
  teal-400: "#216564"
  teal-500: "#143e3d"

  green-100: "#cfeca3"
  green-200: "#b7e375"
  green-300: "#9fd947"
  green-400: "#5f822b"
  green-500: "#304215"

  amber-100: "#ffdc9b"
  amber-200: "#ffd07a"
  amber-300: "#ffc459"
  amber-400: "#a87635"
  amber-500: "#4a3111"

  orange-100: "#f6af8c"
  orange-200: "#f3996d"
  orange-300: "#ee6d2e"
  orange-400: "#712f1a"
  orange-500: "#441c10"

  gray-100: "#ded9d3"
  gray-200: "#aaaaaa"
  gray-300: "#8b837c"
  gray-400: "#433e38"
  gray-500: "#272522"

  # -- Semantic roles - SHARED (same resolution in both registers).
  #    Only semantic roles swap by mode; the scale above never does.
  fg: "{colors.black-500}" # light; -> cream-100 in dark
  fg-inverse: "{colors.cream-100}" # light; -> black-500 in dark
  bg-inverse: "{colors.black-500}" # light; -> cream-100 in dark
  accent: "{colors.orange-300}" # fixed in BOTH modes - never inverts
  primary: "{colors.orange-300}"
  neutral: "{colors.cream-100}"

  # -- Semantic roles - DIVERGE by register. See Marketing Assets / Application Design.
  bg:
    marketing: "#fdfef6" # cream-100 (light) / #0c0b0a true-ink (dark)
    application: "#fdfef6" # cream-100 (light) / #1c1b19 lighter app canvas (dark)
  border:
    marketing: "{colors.cream-400}" # flat hairline: #e2e4d0 (light) / #211f1d black-300 (dark)
    application: "color-mix(in srgb, var(--fg) 12%, transparent)" # translucent ink 12% (light) / cream 10% (dark)

  # -- Application-only surface layers (three-tier depth; marketing is single-surface).
  application:
    surface: "#f6f7ef" # panels (sidebar/nav, popovers, muted strips); #232220 (dark)
    elevated: "#ffffff" # cards, inputs, dialogs - brightest layer; #2a2926 (dark)
    fg-muted: "color-mix(in srgb, var(--fg) 55%, transparent)" # fg at 55% alpha
typography:
  # -- Shared faces (the alphabet is shared; the SCALE diverges, below):
  #   Manrope Variable     - headings (weight 500) + body (weight 400) + UI labels
  #   Quadrant Text Mono   - MARKETING italic eyebrows / figures / pull-quotes
  #   Roboto Mono Variable - code everywhere; marketing micro-labels; and the
  #                          Application register's SINGLE mono face (it uses
  #                          Roboto Mono for eyebrows + figures too, not Quadrant)
  marketing:
    # Big editorial display scale. H1 fluid; H2-H6 fixed.
    heading-h1:
      {
        fontFamily: Manrope Variable,
        fontSize: "clamp(2.25rem, 1.6rem + 2vw, 3rem)",
        fontWeight: 500,
        lineHeight: 1.05,
        letterSpacing: -0.05em,
      }
    heading-h2:
      {
        fontFamily: Manrope Variable,
        fontSize: 5rem,
        fontWeight: 500,
        lineHeight: 1,
        letterSpacing: -0.05em,
      }
    heading-h3:
      {
        fontFamily: Manrope Variable,
        fontSize: 3rem,
        fontWeight: 500,
        lineHeight: 1.1,
        letterSpacing: -0.04em,
      }
    heading-h4:
      {
        fontFamily: Manrope Variable,
        fontSize: 2.25rem,
        fontWeight: 500,
        lineHeight: 1.12,
        letterSpacing: -0.035em,
      }
    heading-h5:
      {
        fontFamily: Manrope Variable,
        fontSize: 1.75rem,
        fontWeight: 500,
        lineHeight: 1.16,
        letterSpacing: -0.025em,
      }
    heading-h6:
      {
        fontFamily: Manrope Variable,
        fontSize: 1.25rem,
        fontWeight: 500,
        lineHeight: 1.2,
        letterSpacing: -0.015em,
      }
    body:
      {
        fontFamily: Manrope Variable,
        fontSize: 1.125rem,
        fontWeight: 400,
        lineHeight: 1.45,
        letterSpacing: -0.01em,
      }
    eyebrow:
      {
        fontFamily: Quadrant Text Mono,
        fontSize: 0.95rem,
        fontWeight: 400,
        fontStyle: italic,
        textTransform: uppercase,
        lineHeight: 1.2,
        letterSpacing: 0.1em,
      }
    micro-label:
      {
        fontFamily: Roboto Mono Variable,
        fontSize: 11px,
        fontWeight: 500,
        textTransform: uppercase,
        lineHeight: 1,
        letterSpacing: 0.12em,
      }
    decorative-figure:
      {
        fontFamily: Quadrant Text Mono,
        fontSize: "clamp(1.75rem, 4vw, 3rem)",
        fontWeight: 400,
        fontStyle: italic,
        lineHeight: 1,
        letterSpacing: -0.02em,
      }
    code:
      {
        fontFamily: Roboto Mono Variable,
        fontSize: 0.85rem,
        fontWeight: 400,
        lineHeight: 1.65,
        letterSpacing: 0,
      }
  application:
    # Dense application-UI scale. H1 keeps display impact for empty/front-door
    # states; H2-H6 scale DOWN for app density. Drives --text-h1..h6 in styles.css.
    heading-h1:
      {
        fontFamily: Manrope Variable,
        fontSize: "clamp(3.5rem, 8vw, 8.3rem)",
        fontWeight: 500,
        lineHeight: 0.95,
        letterSpacing: -0.05em,
      }
    heading-h2:
      {
        fontFamily: Manrope Variable,
        fontSize: 2rem,
        fontWeight: 500,
        lineHeight: 1.2,
        letterSpacing: -0.025em,
      }
    heading-h3:
      {
        fontFamily: Manrope Variable,
        fontSize: 1.5rem,
        fontWeight: 500,
        lineHeight: 1.25,
        letterSpacing: -0.02em,
      }
    heading-h4:
      {
        fontFamily: Manrope Variable,
        fontSize: 1.25rem,
        fontWeight: 500,
        lineHeight: 1.3,
        letterSpacing: -0.015em,
      }
    heading-h5:
      {
        fontFamily: Manrope Variable,
        fontSize: 1.0625rem,
        fontWeight: 500,
        lineHeight: 1.35,
        letterSpacing: -0.01em,
      }
    heading-h6:
      {
        fontFamily: Manrope Variable,
        fontSize: 0.9375rem,
        fontWeight: 500,
        lineHeight: 1.4,
        letterSpacing: -0.005em,
      }
    body: {
        fontFamily: Manrope Variable,
        fontSize: 0.9375rem,
        fontWeight: 400,
        letterSpacing: -0.01em,
      } # --text-body (15px); base body element 14px; long-form prose 16px
    eyebrow:
      {
        fontFamily: Roboto Mono Variable,
        fontSize: 0.75rem,
        fontWeight: 400,
        fontStyle: italic,
        textTransform: uppercase,
        lineHeight: 1.2,
        letterSpacing: 0.1em,
      }
    decorative-figure: {
        fontFamily: Roboto Mono Variable,
        fontWeight: 400,
        fontStyle: italic,
        lineHeight: 1,
        letterSpacing: -0.02em,
      } # size applied responsively/inline
    code: { fontFamily: Roboto Mono Variable } # var(--font-mono)
rounded:
  none: 0 # the default everywhere
  full: 9999px # the only non-square geometry (rare, carved-out)
spacing:
  marketing:
    page-inline: 24px # horizontal inset inside the page frame
    page-bleed: -24px # inverse of page-inline; used by edge-to-edge bands
    page-max: 1280px # frame width cap at base
    page-max-xl: 1440px # frame width cap above ~96rem viewport
    section-separator: 64px # height of the dashed inter-section spacer
    card-padding: 24px # default card / grid-cell padding
    card-padding-lg: 28px # card padding above the small breakpoint
    hairline: 1px # the only border thickness in the system
    accent-rail: 2px # left rail on asides / selection-underline thickness
    intro-to-content: 24px # gap between a section intro and its content band
    control-height: 40px # baseline control height (buttons, chips, inputs)
    control-height-hero: 64px # hero CTA height; 48px compact on small viewports
    reading-measure: 44rem # max reading width for long-form prose (~704px)
  application:
    control-height: 32px # h-8 - default button / input height, AND the floor
    control-height-sm: 28px # h-7
    control-height-xs: 24px # h-6
    control-height-lg: 36px # h-9
    card-padding: 16px # typical app card / panel padding
    composer-inset: 16px # padding around the primary input surface
    hairline: 1px
components:
  # -- Marketing component contracts (square; fill OR border).
  marketing:
    button-primary:
      {
        backgroundColor: "{colors.bg-inverse}",
        textColor: "{colors.fg-inverse}",
        border: none,
        rounded: "{rounded.none}",
        height: 40px,
        padding: "0 1.25rem",
      }
    button-secondary:
      {
        backgroundColor: transparent,
        textColor: "{colors.fg}",
        border: "1px solid var(--border)",
        rounded: "{rounded.none}",
        height: 40px,
        padding: "0 1.25rem",
      }
    button-icon:
      {
        backgroundColor: transparent,
        textColor: "{colors.fg}",
        border: "1px solid var(--border)",
        rounded: "{rounded.none}",
        size: 40px,
      }
    button-hero-shader:
      {
        rounded: "{rounded.full}",
        height: 64px,
        note: "The single carved-out pill; reserved for the loudest hero CTA, paired with the dithered shader treatment.",
      }
    chip-outline:
      {
        backgroundColor: transparent,
        textColor: "{colors.fg}",
        border: "1px solid var(--border)",
        rounded: "{rounded.none}",
      }
    chip-active:
      {
        backgroundColor: "{colors.bg-inverse}",
        textColor: "{colors.fg-inverse}",
        border: none,
        rounded: "{rounded.none}",
      }
    card:
      {
        backgroundColor: "{colors.bg}",
        border: "1px solid var(--border)",
        rounded: "{rounded.none}",
        padding: 24px,
      }
    card-cell:
      {
        backgroundColor: "{colors.bg}",
        border: none,
        rounded: "{rounded.none}",
        padding: 24px,
        note: "Cells in a deduped-border grid: bg-painted, no per-cell border; dividers come from a 1px gap on a border-colored substrate.",
      }
    input:
      {
        backgroundColor: "{colors.bg}",
        textColor: "{colors.fg}",
        border: "1px solid var(--border)",
        rounded: "{rounded.none}",
        height: 2.75rem,
        padding: "0 0.875rem",
        note: "Square; the lone exception is a composite input wrapping a pill CTA, which becomes a pill so the inner pill nests.",
      }
    section-separator:
      {
        height: 64px,
        note: "Full-bleed band with a 1px dashed rule top and bottom (repeating-linear-gradient in the border token). Owns vertical rhythm between sections.",
      }
    code-surface:
      {
        backgroundColor: "#191816",
        barBackgroundColor: "#211f1d",
        border: "1px solid rgba(255,255,255,0.08)",
        foreground: "#d6deeb",
        muted: "#8b837c",
        note: "Theme-immune dark island; stays dark in both modes.",
      }
  # -- Application component contracts (square; fill OR border, with the
  #    interactive-panel carve-out). Mirrors the real cva components in styles.css.
  application:
    button:
      {
        variants: "default, outline, secondary, ghost, destructive, link",
        sizes: "default(h-8), xs(h-6), sm(h-7), lg(h-9), icon(size-8), icon-xs/-sm/-lg",
        base: "rounded-none border border-transparent text-sm font-medium",
        note: "default = bg-primary/text-primary-foreground (-> bg-inverse/fg-inverse). 32px floor: chromed variants (default/outline/secondary/destructive) at default/lg sizes get min-h-8 min-w-8.",
      }
    badge:
      {
        variants: "default(filled), outline(border), secondary, destructive, ghost, link",
        height: 1.25rem,
        padding: "px-2 py-0.5",
        text: "text-xs font-medium",
        rounded: "{rounded.none}",
      }
    marker:
      {
        note: "Icon + label row: flex w-full items-center gap-2 text-sm text-muted-foreground, size-4 icon. Variants default/separator/border. No background of its own.",
      }
    input:
      {
        backgroundColor: transparent,
        border: "1px solid var(--input)",
        rounded: "{rounded.none}",
        height: 2rem,
        padding: "px-2.5",
        note: "Square hairline. No pill inputs in this register.",
      }
    interactive-panel:
      {
        backgroundColor: "{colors.application.elevated}",
        border: "1px solid var(--border)",
        rounded: "{rounded.none}",
        note: "Rule-3 carve-out: cards/forms/popovers/dialogs/composer/attachment panels carry a hairline EVEN WITH a fill, so they read as defined affordances.",
      }
    sidebar:
      {
        backgroundColor: "{colors.application.surface}",
        note: "Sidebar/nav resolves to surface so it never bleeds through on mobile overlays.",
      }
---

# Superwall - DESIGN.md

## Overview

Superwall surfaces read as **engineered editorial**: editorial Manrope type,
italic mono eyebrows and figures, warm cream paper or warm ink, structured by
**hairline borders** with a **single fixed orange accent** that earns its
rarity. The system is **paper-flat by intent** - no drop shadows, no rounding
(two narrow carve-outs), no gradients on UI surfaces, no second brand voice.
Depth is communicated by 1px borders, contrasting bg/fg pairs, percentage tints
of the foreground, and type - never by elevation.

The vocabulary is small on purpose: a viewer should point at a button, an
eyebrow, a figure, a separator, or a card and recognize it as Superwall without
seeing a logo. Personality: precise, confident, technical-but-readable - every
gridline, every figure, every hairline placed deliberately.

**Two registers, one DNA.** The same brand expresses itself in two registers
that share the foundations below but diverge in scale, layout, and components:

- **Marketing Assets** - landing pages, ads, slides, videos, decks, emails,
  embeds. Big editorial display type, the framed page with dashed section
  separators and edge-to-edge "bento" bands, the hero shader CTA. True-ink dark
  mode. Italic **Quadrant Text Mono** for eyebrows and figures.
- **Application Design** - apps, dashboards, native product UI. Dense,
  legible type; layered three-tier surfaces (`bg` / `surface` / `elevated`);
  app chrome (sidebar, top bar) instead of the marketing frame; a lighter dark
  canvas for long sessions. **Roboto Mono** carries the whole mono role.

Shared foundations (Colors, Typography faces, Shape & depth, the Do's and
Don'ts) come first. The two register-specific sections follow.

## Colors

The palette is a **closed scale of 8 hue families x 5 fixed steps each**
(100 lightest -> 500 darkest), plus a small set of **semantic role tokens**.
The scale is **shared and identical** in both registers; only semantic roles
swap by mode, and a couple of semantic roles differ between the registers.

**Fixed scale (does NOT swap by mode).** Named scale tokens (`orange-300`,
`teal-200`, `cream-400`, ...) are literal in both light and dark mode. Reach for
them when a color decision is _categorical_ (a card-header tint, a check-mark
color, a data-bar fill) or when a surface must stay on-brand regardless of
theme.

**Semantic role tokens (swap by mode).**

- **`fg`** - primary ink. Light `black-500`; dark `cream-100`. _(shared)_
- **`bg-inverse` / `fg-inverse`** - opposite-mode fills, for hard-inverse
  CTAs and inverted sections. _(shared)_
- **`accent`** - `orange-300` (`#ee6d2e`), **fixed in both modes**. The brand's
  only inverting-immune color. _(shared)_
- **`bg`** - page/canvas surface. Light `cream-100` in both registers. Dark
  **diverges**: Marketing uses true-ink `#0c0b0a`; Application uses the lighter
  `#1c1b19` (see each section).
- **`border`** - **diverges**: Marketing uses the flat `cream-400` (`#e2e4d0`)
  light / `black-300` (`#211f1d`) dark; Application uses a translucent
  `color-mix(in srgb, var(--fg) 12%, transparent)` light / 10% dark.

**Muting is opacity-on-foreground, not extra grays.** Use a ladder of
foreground opacity for secondary ink - `fg/85` (default body), `fg/70`,
`fg/55` (standard muted), `fg/50` (caption), `fg/40` (metadata) - via
`color-mix(in srgb, var(--fg) N%, transparent)`. For hover washes use `fg/5`
(subtle) and `fg/3%` (row hover). Application code additionally exposes
`fg-muted` (fg at 55%) and maps `muted-foreground` to `gray-300` (light) /
`gray-200` (dark). Never invent a new gray token.

**Accent is sacred.** Orange-300 is the eyebrow color, the selection ring, the
active-tab underline, the warning rail, the "this is brand-touched" moment. Do
**not** use accent as a large fill background (the carve-out is the brand's own
product mark, whose dark-mode primary fill may lean into accent).

**Marker hue pairings.** When reaching for a categorical hue
(`blue`/`teal`/`green`/`amber`/`orange`): **`-400` surface with `-100` ink** for
filled card headers, **`-200` surface with `-500` ink** for soft promo bands,
**`-300`** as the canonical bar/series fill. Never put a mid-step (`-200`/`-300`)
as ink on a `-500` surface. In Application code these are exposed as
`--color-blue/teal/green/amber/orange` (-> the `-300` steps) plus status tokens
`success`/`warning`/`info`/`danger`.

**Three / four-branch mode swap is mandatory.** Any token that differs between
light and dark mode MUST be defined in **every** theme cascade branch:
`:root.dark` (forced dark via class), the default `:root` (light), and
`@media (prefers-color-scheme: dark) :root:not(.light)` (system-dark for users
who never toggled). The Application stylesheet additionally carries a standalone
`.dark` block (four branches total, paired with `@custom-variant dark`). A
missing branch silently breaks the largest population - system-dark visitors
who never touched a toggle.

**Fixed-palette islands.** Some surfaces are deliberately theme-immune -
code/prompt chrome stays dark in both modes; brand-honoring assets keep their
source palette; dither tiles and color-profile CTAs run on injected
`--fixed-theme-*` variables. These are explicit, not bugs. **Selection
highlight** is `teal-300 @ 50%` in both modes. **Brand monochrome marks**
(customer/partner logos) recolor via a single `--brand-logo-filter`:
`brightness(0)` on light, `brightness(0) invert(1)` on dark.

## Typography

Three faces, each with a strict job. The **faces are shared**; the **scale and
the mono assignment diverge by register** (see Marketing Assets / Application
Design for the exact scales).

- **Manrope Variable** - the workhorse. Every heading, body paragraph, and UI
  label. Headings are **weight 500** (never 700) with negative tracking that
  tightens as size grows. Body is **weight 400** with a gentle `-0.01em`.
- **Quadrant Text Mono** - italic decorative mono. **Marketing-register**
  eyebrows, decorative figures, and pull-quotes: uppercase with **positive
  `0.1em` tracking** - the deliberate inverse of the negatively-tracked
  headings. Never running body prose.
- **Roboto Mono Variable** - utility monospace. Code, hex values, JSON-like
  payloads, terminal output, and micro-uppercase technical chips everywhere. In
  the **Application register it is the _only_ mono face** - it also carries the
  app's eyebrows and decorative figures (there is no Quadrant Text Mono in app
  UI). Loaded via `@fontsource-variable/roboto-mono` (normal + italic).

**Reach for the scale, don't invent sizes.** Each register's scale is fixed
(below). **Negative tracking escalates with size** for headings; **reverse the
sign** (`+0.1em` / `+0.12em`) for eyebrows and micro-labels - that inversion is
what separates structural type from decorative type.

**At most two weights per screen.** Headings 500, body 400; "strong" inline
emphasis is 600, never 700. Anything wanting more emphasis reaches for a
brighter color, a larger size, or a decorative figure - not a heavier weight.

**Italic is reserved** for the decorative mono face (eyebrows, figures,
pull-quotes, oversized quotation glyphs). Never italicize body prose for
emphasis. Long display titles wrap with `text-balance`.

## Shape, borders & depth

**Square is the default. Fully-rounded is the carved-out exception.**
Containers, panels, cards, buttons, chips, inputs, tables, badges, message
bubbles, and media frames are all **square** (`border-radius: 0`). It is
enforced structurally in Application code: `--radius` is `0` and every radius
scale (`--radius-sm` ... `--radius-4xl`) collapses to `0`, so even `rounded-lg`
renders square - only `rounded-full` produces a shape. When something rounds it
rounds **fully** (`9999px`) or uses a source ecosystem's exact ratio; **never a
partial radius** (no 4px, no 12px, no `xl`). The rounded carve-outs differ by
register and are listed in each section.

**Borders are single hairlines, shared, never doubled.** A single 1px line is
the only structural seam. Where regions meet (grid cells, stacked panels, a
header above a body) draw **one** shared line; never stack two borders where one
suffices, and never wrap an element in a full border box when its neighbors
already draw the shared edge.

**There is no elevation.** No `box-shadow`, no `drop-shadow`, no blur (the one
marketing carve-out: a small backdrop blur on the translucent top-nav fill).
Depth comes only from: hairline borders, background/surface contrast, percentage
tints (`color-mix` of `fg` at 3-10% for hover/press washes), and type weight /
size / italic-mono. The single allowed "shadow" is a **2px accent ring** used
strictly as a selection/focus indicator, never as a lift.

**Pixel-perfect decorative geometry.** Pixel-grid icons sit on a **7x7 SVG
matrix** rendered with `image-rendering: pixelated` and
`shape-rendering: crispEdges`; decorative SVG patterns use 1px rects with
`crispEdges`. Corners stay perfectly square at any size.

---

# Marketing Assets

Landing pages, ads, slides, videos, decks, emails, and embeds. The big
editorial register: the framed page, dashed section separators, edge-to-edge
bento bands, the hero shader CTA, and true-ink dark mode.

## Type scale (Marketing)

Big display scale. **H1** is fluid `clamp(2.25rem, 1.6rem + 2vw, 3rem)`. **H2-H6
are fixed**: `5rem / 3rem / 2.25rem / 1.75rem / 1.25rem`. **Body** is `1.125rem`
line-height `1.45`. **Eyebrow** is Quadrant Text Mono italic `0.95rem` uppercase
`+0.1em`. **Micro-label** is Roboto Mono `11px` `500` uppercase `+0.12em`.
Negative tracking runs roughly `-0.015em` at h6 -> `-0.05em` at h2/display.

## Surfaces & color (Marketing)

Single-surface, paper-flat. **`bg`** is `cream-100` (light) / true-ink
`#0c0b0a` (dark). **`border`** is the flat `cream-400` (light) / `black-300`
(dark), always 1px. There is no `surface`/`elevated` layering - depth is the
frame, the dashed separators, deduped grid gaps, and contrast.

## Layout (Marketing)

**The framed page.** Content sits inside a bordered container - `min(90%,
1280px)` wide, widening to `1440px` at very-large viewports, centered with a
24px top margin and `1px solid var(--border)` on the left and right. **Below
~640px the frame dismantles**: side borders drop, top inset disappears, content
goes edge-to-edge, and form controls force `16px` font-size to defeat iOS Safari
focus-zoom.

**Section padding is global.** Every top-level section carries a constant **24px
inline padding** owned by the global stylesheet - section components must NOT
set their own horizontal padding (it would double the frame inset).

**Dashed separators own vertical rhythm.** Sections are separated **only** by a
**64px full-bleed band with a 1px dashed rule** top and bottom (a
`repeating-linear-gradient` in the border token, ~`6px on / 4px off`). No
inter-section `margin-top` exists anywhere else - hairlines for cells, dashes
for sections. A breadcrumb may double as a separator via a matching `::after`.

**Edge-to-edge bento bands.** Content alternates between inset prose and
edge-to-edge grids that touch the frame's inner borders. Bleed by cancelling the
section inline padding with **`-mx-6`**; the frame's own borders become the
band's edges. **Deduped grid dividers** come from a 1px gap on a border-colored
substrate with `bg`-painted cells - the shared gap _is_ the divider; never
per-cell borders. A full-bleed band may NOT carry a four-sided border (its
left/right would double the frame): use `border-t`, `border-y`, or `border-b`
only. Stacked bands sit flush and share one divider. Section vertical padding
follows the band edges (default 24px; `0` bottom when a band is flush at the
bottom; `0` top+bottom for a full-height bleed row).

**Long-form prose** clamps to a **44rem reading measure** (~704px), centered,
opting out of the 24px frame inset. **Responsive pivot** is ~1024px (stacked ->
side-by-side; shared dividers rotate `border-t` -> `border-l`); index tables
collapse to stacked blocks below ~768px.

## Components (Marketing)

**Buttons** - three square variants, **fill OR border, never both**:

- **Primary (filled)** - `bg-inverse` fill, `fg-inverse` ink, **no border**.
  Hover mixes 90% toward transparent.
- **Secondary (outline)** - transparent, `fg` ink, 1px border. Hover `fg/5`.
- **Icon (outline, square)** - `40px x 40px`, transparent, 1px border.
- **Hero shader CTA** - the carved-out **pill** (`9999px`), `64px` tall (`48px`
  compact), dithered shader background + 15% glass overlay. One per screen.
- Baseline `40px` tall, `1.25rem` horizontal padding (`0` for icon). Label voice
  is uppercase **semibold 600**, `0.875rem`, `+0.12em`, leading 1. Press is
  **`transform: scale(0.98)`**. Color-profile buttons inject a `background` /
  `text` / `accent` triple and compute hover as
  `color-mix(in srgb, var(--background) 82%, var(--accent))`.

**Chips** - `outline` (transparent + 1px border), `active` (filled `bg-inverse`,
no border), `eyebrow` (type-only). Always square.

**Cards** - standalone (`bg` + 1px border, `24/28px` padding) or cell-in-grid
(`bg`, no per-cell border). Card headers are **filled** (marker `-400` surface /
`-100` ink, borderless) or **plain** (single `border-b`).

**Inputs** - square, 1px border, `bg` fill, `2.75rem` tall, `0.875rem` padding;
focus darkens the border to `fg/40`, never a glow. Composite inputs that wrap a
pill CTA become a pill so the inner pill nests; all others stay square. Force
`16px` on mobile; defeat UA autofill paint with an inset `1000px` bg box-shadow

- `-webkit-text-fill-color`.

**Decorative figures** - a first-class primitive for every stat, price, rank,
and oversized quotation glyph: **italic Quadrant Text Mono**, weight 400,
line-height 1, `-0.02em`, responsive `clamp(1.75rem, 4vw, 3rem)` (heroes scale to
`clamp(2.5rem, 7vw, 7rem)`). A **sans tabular alternate** (Manrope medium,
`-0.03em`) lines up prices. Quotation glyphs tint to `border`, not `fg`.

**Eyebrows** - the universal section opener: italic Quadrant Text Mono,
uppercase, `0.95rem`, `+0.1em`, color `accent`. One per section, above the
heading. **Eyebrow -> heading -> muted body** is the canonical section intro.

**Asides** - **fill OR rail, never a full border**: a 2px left rail in an accent
color + a ~8% tinted fill of the same accent, with a matching eyebrow label.
Closed vocabulary: TL;DR `teal-300`, Note `blue-300`, Tip `green-300`, Related
`accent`, Warning `orange-300`. Pull-quotes use the same 2px rail with the
decorative italic face at `1.375rem`.

**Index tables** - one canonical design for every long-form listing: column
headers in italic Quadrant Text Mono uppercase `+0.1em` `fg/40`; 1px row
hairlines; `~3% fg` row-hover wash; whole-row click via a real inner `<a>`;
stack below ~768px.

**Section separators** - the 64px dashed-rule band described in Layout; nothing
else may add inter-section margin.

**Code surfaces** - theme-immune **dark islands**: bg `#191816`, bar `#211f1d`,
border `rgba(255,255,255,0.08)`, fg `#d6deeb`, muted `#8b837c`. Tab bars use a
2px transparent bottom border that swaps to accent when active. Copy buttons are
borderless until hover and swap to "Copied" for 1500ms.

**Media** - images / video / iframes wear a 1px hairline frame, square, no
shadow, `bg-inverse` placeholder; captions centered `text-sm` `fg/50`, `mt-3`.
Media block rhythm `32px` (`my-8`); code blocks `24px` (`my-6`). **Dither tiles**
are duotone halftone surfaces on a six-slot `--fixed-theme-*` profile.
**Theme-paired rasters** ship `-light` / `-dark` variants, enforced at build.

**Decorative patterns** - four full-bleed motifs (vertical-tile, square,
stripes, brick), all 1px SVG rects with `crispEdges`, two-variable color, line
clamped to ~50% alpha; randomized def IDs. **Corner brackets** are four 20x20px
L-shapes, 2px borders, `currentColor`, never rounded.

**Brand marks** - transparent assets, no border/fill/shadow/radius. Customer
marks recolor via `--brand-logo-filter`; sized by a closed scale of named
modifiers (default/wide/large/tall/medium/emphasis/boost/hero), never inline
pixel heights. The product mark is inline SVG with token-driven multi-fill.

**Iconography** - **line icons** (24-unit viewBox, stroke `1.6`, round caps,
`fill:none`, `stroke:currentColor`) for UI affordances; **pixel-grid icons** on
a 7x7 matrix with `crispEdges`, five sizes (`14/21/28/42/56px`). Decorative
icons are `aria-hidden`; meaningful ones get `role="img"` + `aria-label`. The
full pixel-grid icon library is published as base36 codes at `<host>/icons.md`
(decode/render instructions included); build or edit icons at `<host>/icons`.

**Rounded carve-outs (Marketing):** hero shader CTA (full pill), composite
inputs wrapping a pill CTA, brand-honoring app-icon squircles at hero size
(source ratio, e.g. `rounded-[22%]`), and utilitarian micro-shapes (scrollbar
thumbs, status dots). **Press feedback: `scale(0.98)`.**

---

# Application Design

Apps, dashboards, and native product UI. The dense register: layered three-tier
surfaces, app chrome (sidebar / top bar) instead of the marketing frame, a
lighter dark canvas for long sessions, and Roboto Mono as the sole mono face.
This register is the reference implementation in `src/client/styles.css` and the
shadcn/cva components - its values are validated against that code.

## Type scale (Application)

Dense application-UI scale, driving `--text-h1..h6` / `--text-body` /
`--text-eyebrow`. **H1** keeps display impact for empty/front-door states:
`clamp(3.5rem, 8vw, 8.3rem)`, line-height `0.95`. **H2-H6** scale down for app
density: `2rem / 1.5rem / 1.25rem / 1.0625rem / 0.9375rem`, with the
letter-spacing ladder `-0.025 / -0.02 / -0.015 / -0.01 / -0.005em`. **Body**:
`--text-body` is `0.9375rem` (15px), the base body element is `14px`, and
long-form prose & content surfaces (rendered markdown, transcripts) run at
`16px` - there is no 1.125rem body size here. **Eyebrow** (`.type-eyebrow`):
**Roboto Mono** italic uppercase `0.75rem` `+0.1em`, colored `accent`.

## Surfaces & color (Application)

**Layered, not flat - the layering is the depth.** Three tiers, read through
subtle hue contrast plus a single hairline border, never a shadow:

- **`bg`** - canvas / main content. Light warm cream `#fdfef6`; dark `#1c1b19`
  (deliberately lighter than true ink so long sessions stay comfortable and
  `elevated` reads as elevated without glare).
- **`surface`** - panels (sidebar / primary nav, popover bodies, muted strips).
  Light `#f6f7ef`; dark `#232220`. `--muted` / `--secondary` / `--sidebar`
  resolve here.
- **`elevated`** - cards, inputs, dialogs: the **brightest** layer. Light pure
  white `#ffffff`; dark `#2a2926`. `--card` / `--popover` resolve here.

**Border** is the translucent `color-mix(in srgb, var(--fg) 12%, transparent)`
(light) / 10% (dark) - a low-alpha foreground tint, not a flat scale value.
`fg-muted` is `fg` at 55%. The fixed `cream-400` / `black-300` hexes serve as the
`-inverse` border tokens here, not the live border.

## Layout (Application)

**App chrome owns layout - there is no marketing frame, no dashed separators, no
bento bleed.** A sidebar / primary nav panel (filled with `surface` so it never
bleeds through on mobile overlays) and a top bar define the box; content fills
the remaining column with no inner `max-w-*` / `mx-auto` constraints on
full-bleed panels. Width is unconstrained inside the chrome. The primary input
surface (composer) is one bordered `elevated` container with a uniform `16px`
inset. Long-form content (rendered prose, transcripts) is the one place that may
carry its own comfortable measure.

## Components (Application)

These mirror the real shadcn/cva components.

**Buttons** - a `cva` button. **Variants:** `default`, `outline`, `secondary`,
`ghost`, `destructive`, `link`. **Sizes:** `default`, `xs`, `sm`, `lg`, `icon`,
`icon-xs`, `icon-sm`, `icon-lg` (`icon` is a size, not a variant). Base is
`rounded-none border border-transparent text-sm font-medium`.

- `default` = filled `bg-primary text-primary-foreground` (-> `bg-inverse` /
  `fg-inverse`), no visible border, hover `bg-primary/80`. `outline` =
  `border-border bg-background`. `secondary` = `bg-secondary` (-> surface).
  `ghost` = transparent/borderless.
- **Sizing:** `default` `h-8` (32px) `px-2.5`; `xs` `h-6`, `sm` `h-7`, `lg`
  `h-9`; `icon` `size-8`, `icon-lg` `size-9`.
- **32px floor:** chromed text variants (`default`/`outline`/`secondary`/
  `destructive`) at the `default`/`lg` sizes carry `min-h-8 min-w-8`, so a short
  label never collapses below the icon button. Excludes `ghost`/`link` and the
  compact `xs`/`sm` sizes.

**Badges** - the square inline label: `h-5`, `px-2 py-0.5`, `text-xs
font-medium`, `rounded-none`. Variants `default` (filled, no border),
`outline` (`border border-border`), `secondary`, `destructive`, `ghost`, `link`.
There is no separate "chip" - the eyebrow is a type style, not a chip.

**Marker** - the icon-plus-label row (`flex w-full items-center gap-2 text-sm
text-muted-foreground`, `size-4` icon, variants `default`/`separator`/`border`).
Introduces no background; the icon color is set per-grouping.

**Inputs** - square, hairline-bordered, transparent-fill: `h-8`, `rounded-none
border border-input bg-transparent`, `px-2.5`. Textarea matches with `py-2`;
the select trigger uses the same shell. No pill inputs in this register.

**Cards & interactive panels** - a plain filled card (`bg-card`, `rounded-none`)
carries **no** border (Rule 3). **Carve-out:** any **interactive in-content
panel** - one that collects input, displays a discrete object, or asks the user
to act - gets a hairline `border border-border` **even with its fill**, because
the border is what makes it read as a defined affordance. Covers the question /
form tool shells, attachment / file cards, the pending/queued item card (dashed),
the primary input / composer surface, and all popover surfaces
(`PopoverContent`, `DialogContent`, `DropdownMenuContent`, `SelectContent`).

**Charts & data** - series use the marker palette in order: `--chart-1`
orange-300, `--chart-2` teal-300, `--chart-3` blue-300, `--chart-4` green-300,
`--chart-5` amber-300; cursor is a 6%-alpha foreground mix. No shadow, no rounded
container. The brand **stat pair** `--stats-value` (orange-300 light / orange-200
dark) + `--stats-label` (orange-500 light / `fg` dark) renders a prominent
figure + label as a unit and swaps as a pair.

**Sidebar / primary nav** - resolves to `surface` (`--sidebar` -> `--surface`),
with `--sidebar-accent` a 6% foreground-over-surface mix for hover/active rows
and `--sidebar-ring` the accent. Carries a fill + hairline; owns its own layout.

**Code in prose** - unlike the marketing dark island, Application code in
rendered markdown uses the **themed muted surface**: `var(--muted)` background
with a 1px border, Roboto Mono, swapping with the theme.

**Rounded carve-outs (Application):** only circular controls round - avatars,
switch tracks/thumbs, radio controls and dots, scrollbar thumbs, small status /
count pills, and the spinner. Everything else is square.

---

# Do's and Don'ts

The **non-negotiable rules**. Universal unless tagged _(Marketing)_ or
_(Application)_.

### 1. No shadows. Ever.

Never `box-shadow`, `drop-shadow`, or shadow-based elevation. Communicate
layering through hairline borders, background/surface contrast, percentage
tints, and z-index. The only allowed "shadow" is the **2px accent ring** as a
selection/focus indicator. _(Marketing exception: a small backdrop blur on the
translucent top-nav fill.)_

### 2. Square by default; only the carve-outs round.

Containers, panels, cards, buttons, chips, inputs, tables, badges, bubbles, and
media frames have **square corners**. When rounding is allowed it is **fully
rounded** (`9999px`) or a source ecosystem's exact ratio - never a partial
radius. _(Marketing)_ carve-outs: hero shader CTA, pill-composite inputs,
app-icon squircles, utilitarian micro-shapes. _(Application)_ carve-outs:
circular controls only (avatars, switches, radio, scrollbar thumbs, status
pills, spinner).

### 3. Fill OR border, never both.

A surface that **fills** with color carries **no** border; a surface that
**borders** carries no contrasting fill. Active/selected = flip to inverse
bg + inverse fg with the border going transparent. _(Application carve-out:
interactive in-content panels - cards/forms/popovers/composer/attachments - keep
a hairline even with a fill, so they read as defined affordances. The rule still
holds for buttons, badges, status dots, and filled tiles where the fill is the
identity.)_

### 4. One shared seam - never double a border.

Where regions meet, draw a **single shared 1px hairline**. Internal grid
dividers come from a 1px gap on a border-colored substrate with `bg`-painted
cells; per-cell borders are forbidden. _(Marketing)_ a full-bleed band may not
carry a four-sided border (it would double the frame): use `border-t`,
`border-y`, or `border-b` only; stacked bands sit flush and share one divider.

### 5. The frame & separator model. _(Marketing)_

Every page sits inside the bordered container at `min(90%, 1280px)`, side
hairlines, edge-to-edge below ~640px. Sections carry a global 24px inline
padding (components never set their own) and are separated **only** by the 64px
dashed band - no inter-section margin elsewhere. Section intros stay inset;
headings never bleed. Edge-to-edge bento bands bleed via `-mx-6`; section
vertical padding follows the band edges.

### 6. App chrome owns layout. _(Application)_

There is no marketing frame, dashed separator, or bento bleed in product UI. A
filled sidebar/nav (resolving to `surface`) and top bar define the box; content
fills the remaining column. Use the three-tier `bg`/`surface`/`elevated` model
for depth; don't constrain full-bleed panels with inner `max-w-*`/`mx-auto`.

### 7. Three / four-branch theme swaps, or it didn't happen.

Any token, asset, or rule that differs by mode MUST be defined in **every**
cascade branch: default `:root` (light), `:root.dark`, and
`@media (prefers-color-scheme: dark) :root:not(.light)` - plus the standalone
`.dark` block in the Application stylesheet. A missing branch silently breaks
system-dark users who never toggled. Applies to semantic role tokens,
brand-logo filters, theme-paired rasters, the stat value/label pair, and any
component-scoped CSS variable that swaps.

### 8. Don't break dynamic class contracts. _(Marketing)_

When edge workers / SSR rewriters emit branded markup, their class names must
match the component's render exactly. Keep branded-mark and customer-logo
styling in the global stylesheet (not component-scoped or inline utilities) so
injected nodes stay styled.

### 9. One accent. Two marker hues. One figure per moment.

Use the orange `accent` only for the single most important brand beat per
surface - the eyebrow, an active-tab underline, a selection ring, or one
decorative figure. Don't mix more than two marker hues on one beat (a card
header and its check-items must agree, e.g. `infra -> blue`, `paywall -> teal`).
Use accent as a **rail or ring**, not a large fill (carve-out: the product
mark's dark-mode primary).

### 10. Two weights, max.

Headings 500, body 400, inline `<strong>` 600 - never 700. More emphasis ->
brighter color, larger size, or a decorative figure, never a heavier weight.

### 11. Italic is reserved.

Italic only for the decorative mono face (eyebrows, figures, pull-quotes,
quotation glyphs). Never italicize body prose; use weight 600 for emphasis.

### 12. Motion is uniform, short, and for affordance.

Standard transition is **150ms ease** on `background-color`, `border-color`,
`color` (and `transform` for icon buttons). Press feedback _(Marketing)_ is
`transform: scale(0.98)`; Application buttons carry no press transform. No hover
transforms on cards/rows (color/wash only). No spring or bounce easings. Reserve longer motion (300-450ms, auto-cycles, shader
flourishes) for a single hero/decorative layer.

### 13. Honor reduced-motion. Always.

Any continuous animation (auto-cycling tabs, marching dashes, WebGL/shader
layers) MUST honor `prefers-reduced-motion: reduce` and clamp to zero or a
static end state. Gate heavy decorative layers on `deviceMemory < 4` and
required GPU features, failing gracefully to a static raster.

### 14. Hover affordance: color, not motion.

Link hover is `underline + underline-offset` (1px -> 2px thickness), not a color
change. Row/cell hover is a `~3% fg` wash; chip/control hover `~5% fg`. Nav
open/selected is a color swap to accent on hover-capable devices; on coarse
pointers add a soft surface chip so the state is discoverable.

### 15. Decorative interest comes from primitive geometry. _(Marketing-leaning)_

Replace shadow/material/gradient vocabulary with corner brackets, repeating-
gradient patterns (vertical-tile, square, stripes, brick), pixel/dither rasters
on a 7-unit grid, and dashed hairlines. Pattern overlays clamp the line color to
~50% alpha; pattern def IDs are randomized.

### 16. Brand marks are sacred and transparent.

Every brand mark is a transparent asset with no border/fill/shadow/radius.
Customer marks recolor via the single `--brand-logo-filter` (`brightness(0)`
light / `brightness(0) invert(1)` dark). Logo size comes from a closed scale of
named modifiers, never inline pixel heights.

### 17. Accessibility is part of the visual contract.

WCAG AA contrast: `4.5:1` body, `3:1` for headings >= 18pt (or >= 14pt bold).
Decorative SVGs, watermark figures, pattern overlays, and brand-mark filters are
`aria-hidden` + `pointer-events: none`. Icon-only buttons require an
`aria-label`; identity-bearing marks get `role="img"` + `aria-label`.
Whole-row clickable tables keep a real inner `<a>`. Honeypot fields are
off-screen with proper labeling.
