v3.0 — THE BRAIN · 2026-05-28
v3.0 introduces a 7-axis synthesizer. Every brief becomes seven continuous values. Those values then compile to palette, type ladder, spacing scale, radius scale, and motion timing. Here's what each axis measures, where it comes from, and how it lands as code.
| Axis | 0.0 end | 1.0 end | Compiles to |
|---|---|---|---|
warmth | cold | warm | RGB warmth-shift |
contrast | flat | dramatic | Type scale ratio + weight curve |
density | airy | dense | Spacing base + line-height |
geometry | sharp | soft | Radius scale |
formality | playful | corporate | Tracking + motion dampening |
motion | still | kinetic | Animation timing + curve |
type_personality | geometric | humanist | Display family bias |
Each axis is derived through three steps:
17 documented industries each have a 7-axis seed dictionary. Unknown industries default to neutral 0.5 across the board.
INDUSTRY_SEEDS = {
"fintech-payments": {"warmth": 0.35, "contrast": 0.55, "density": 0.6,
"geometry": 0.4, "formality": 0.75, "motion": 0.45,
"type_personality": 0.4},
"luxury": {"warmth": 0.55, "contrast": 0.7, "density": 0.3,
"geometry": 0.55, "formality": 0.75, "motion": 0.4,
"type_personality": 0.75},
"gaming": {"warmth": 0.5, "contrast": 0.85, "density": 0.7,
"geometry": 0.35, "formality": 0.3, "motion": 0.85,
"type_personality": 0.45},
# ... 14 more
}
35+ documented tone tags push axes by ±0.10 to ±0.30:
TONE_NUDGES = {
"warm": {"warmth": +0.20},
"bold": {"contrast": +0.25, "motion": +0.10},
"minimal": {"density": -0.30, "contrast": -0.10},
"rounded": {"geometry": +0.25, "warmth": +0.10},
"corporate": {"formality": +0.25, "warmth": -0.10},
"kinetic": {"motion": +0.25, "contrast": +0.10},
"editorial": {"type_personality": +0.25, "density": +0.10},
# ... 28 more
}
The brief's forbidden list applies hard clamps to specific axes:
FORBIDDEN_CLAMPS = {
"playful": ("formality", (0.6, 1.0)),
"loud": ("contrast", (0.0, 0.5)),
"dense": ("density", (0.0, 0.55)),
"brutalism": ("geometry", (0.3, 1.0)),
}
So forbidden=["playful"] clamps formality to at minimum 0.6, regardless of what the seed + nudges produced.
The palette synthesizer mixes anchor colors from the chosen brand exemplars, then applies a warmth shift based on the axis value. Distance from 0.5 sets intensity, max ±18 RGB units.
def _warmth_shift(rgb, warmth):
delta = (warmth - 0.5) * 2 # -1.0 .. +1.0
shift = 18 * delta # ±18 max
r, g, b = rgb
return (r + shift, g + shift / 2, b - shift / 2)
So a brief with warmth=0.7 produces palette canvas ~12 R units warmer, ~6 G warmer, ~6 B cooler than the same brief at warmth=0.5.
Pick the type-size ratio from contrast:
contrast >= 0.7 → 1.333 (perfect fourth, loud)contrast >= 0.4 → 1.250 (major third, balanced)contrast < 0.4 → 1.200 (minor third, quiet)So a "minimal/quiet" brief produces tightly-stepped headings (16/19.2/23/27.7/33.2). A "bold/dramatic" brief produces dramatic jumps (16/21.3/28.4/37.9/50.5).
This is where the axis interaction matrix kicks in (we documented density × formality conflict resolution in the launch post):
| density | formality | base px |
|---|---|---|
| > 0.65 | any | 4 (Bloomberg) |
| < 0.4 | > 0.7 | 12 (luxury) |
| < 0.4 | < 0.7 | 8 (airy SaaS) |
| else | any | 6 (mid) |
Sharp + corporate = 2px (NYT). Soft + playful = 18px (Glossier). Otherwise blended target.
High formality tightens display letter-spacing (-0.025em vs -0.015em). Also dampens kinetic motion timings by 25% when motion is also high (the "Bloomberg with hover animations" case).
base_ms = 220 - 80 * motion, so a kinetic brief gets 140ms base timings, a still brief gets 220ms.
Curve picks:
motion > 0.7 → spring overshoot (cubic-bezier(0.34, 1.56, 0.64, 1))motion > 0.4 → ease-cinema (cubic-bezier(0.22, 1, 0.36, 1))Low (geometric) biases the synthesizer toward Inter Tight / Söhne / Grotesque families. High (humanist) biases toward Bricolage Grotesque / IBM Plex / Source families. Body always anchors on Inter.
You ask for: industry=fintech-payments, tone=["bold", "serious"].
The synthesizer compiles this to:
All deterministic. All from a brief with 3 fields. All offline, no LLM call.
pip install uxskill
uxskill synthesize \
--industry fintech-payments \
--tone bold --tone serious
# Outputs: { mode: "pure_synthesis",
# axes: {warmth: 0.35, contrast: 0.80, ...},
# palette: {canvas: "#0a1014", ink: "#f6f8fa", ...},
# type_pair: {display: "Inter Tight", body: "Inter", ...},
# spacing: {base: 4, scale: [4, 8, 12, 20, 32, 52, 84]},
# radius: {base_px: 4, sm: 2, md: 4, lg: 6, xl: 10, pill: 999},
# motion: {base_ms: 245, fast_ms: 147, slow_ms: 441, ... } }