You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
[DRAFT RFC] Component visual recipes: render components to SVG, PNG and Figma
#1568
Spectrum design data describes tokens, components, options, states and anatomy names. It has no geometry, so nothing can draw a component from it. Today, component visuals live in Figma files or in each platform implementation.
We want one source that renders to several outputs (SVG, PNG, Figma), and that isn't tied to Figma, React, or any other platform.
The driving use case is the Spectrum Hub website design. One component has three views fed by the same data:
Usage: a variant × state matrix with option controls.
Anatomy: numbered callouts on each part.
Specs & tokens: measurement annotations labeled with the token behind each value.
2. Proposal: visual recipes
Add a renderer-neutral visual recipe per component, stored at visuals/<component>.json. A recipe is a part tree (box, text, icon, ring) with layout, shape and paint. Every value is bound to a token, so overlays can name the token behind each measurement.
Resolved rects, paths, text and measurements, each with part and token ids
A property value is a literal, a token selected by name-object fields, or a token chosen through the component's relationships. Conditional entries (when.options, states, modes) pick variants; the most specific match wins. The cascade narrows candidates by mode (colorScheme, scale). Unresolvable values produce diagnostics rather than silent fallbacks.
design-data render action-button --state keyboard-focus -o out.svg resolves the pilot recipe against the corpus and writes an SVG. Each part carries data-part and data-tokens attributes. At size m on desktop the container resolves to 32px high, 12px padding and a 6px gap; the mobile scale gives 40px. Not built yet: overlays, matrices, PNG, WASM, Figma.
4. Decisions so far
Playground (Domino): reference only. It models component instances (props, slots), with no geometry, paint, layout or token binding. Its repository is private and its node envelope has no published schema or versioning, so a public spec shouldn't depend on it. Option names align closely with ours, so an adapter between a render request and a Domino instance is possible later.
Text: approximate metrics from Source Sans 3 (OFL). Adobe Clean can't be redistributed. SVG <text> uses the stack Adobe Clean, Source Sans 3, sans-serif.
Layout: a minimal flex implementation first; revisit taffy when text-field is piloted.
Icons: glyph paths keyed by icon name, as literal values.
Figma: a backend consumes the scene graph and emits plugin node JSON bound to Variables by token id. Recipes hold no Figma-specific data.
Location: the renderer lives in the Rust SDK (design_data_core::visual).
5. Open questions
Relationship bindings. Recipes currently bind to relationship context free-text strings, which break if reworded. Should relationships gain structured options and part fields everywhere, so recipes select by option and state?
Stored requests. Should render presets and matrices (what the Hub site shows) live in the dataset, or stay tool input?
Token gaps. Only a handful of tokens set name.component, so most component visuals come from generic tokens plus relationships. What is the policy for components without either?
Deprecated icon sizes.workflow-icon-size-* is deprecated without a replacedBy. Which tokens should icon sizing bind to?
Conditions. Is visibleWhen with a single condition enough, or do we need any/not composition?
Pilot scope. Planned pilots: action-button, button, checkbox, switch, badge, text-field, tag. Is that the right set, and what's the right order?
Token names. The Hub mockups label tokens like corner-radius-500 and component-height-100, while the corpus uses names like corner-radius-medium-size-medium. Which names should overlays display?
6. Feedback wanted
Design: does the recipe model cover what you'd need to draw your components? Engineering: does the scene graph work as a backend contract? Hub site: do the three views map cleanly onto recipes and render requests?
reacted with thumbs up emoji reacted with thumbs down emoji reacted with laugh emoji reacted with hooray emoji reacted with confused emoji reacted with heart emoji reacted with rocket emoji reacted with eyes emoji
Uh oh!
There was an error while loading. Please reload this page.
1. Problem
Spectrum design data describes tokens, components, options, states and anatomy names. It has no geometry, so nothing can draw a component from it. Today, component visuals live in Figma files or in each platform implementation.
We want one source that renders to several outputs (SVG, PNG, Figma), and that isn't tied to Figma, React, or any other platform.
The driving use case is the Spectrum Hub website design. One component has three views fed by the same data:
2. Proposal: visual recipes
Add a renderer-neutral visual recipe per component, stored at
visuals/<component>.json. A recipe is a part tree (box,text,icon,ring) with layout, shape and paint. Every value is bound to a token, so overlays can name the token behind each measurement.A property value is a literal, a token selected by name-object fields, or a token chosen through the component's relationships. Conditional entries (
when.options,states,modes) pick variants; the most specific match wins. The cascade narrows candidates by mode (colorScheme,scale). Unresolvable values produce diagnostics rather than silent fallbacks.3. Prototype
design-data render action-button --state keyboard-focus -o out.svgresolves the pilot recipe against the corpus and writes an SVG. Each part carriesdata-partanddata-tokensattributes. At size m on desktop the container resolves to 32px high, 12px padding and a 6px gap; the mobile scale gives 40px. Not built yet: overlays, matrices, PNG, WASM, Figma.4. Decisions so far
<text>uses the stackAdobe Clean, Source Sans 3, sans-serif.taffywhen text-field is piloted.design_data_core::visual).5. Open questions
contextfree-text strings, which break if reworded. Should relationships gain structuredoptionsandpartfields everywhere, so recipes select by option and state?name.component, so most component visuals come from generic tokens plus relationships. What is the policy for components without either?workflow-icon-size-*is deprecated without areplacedBy. Which tokens should icon sizing bind to?visibleWhenwith a single condition enough, or do we need any/not composition?corner-radius-500andcomponent-height-100, while the corpus uses names likecorner-radius-medium-size-medium. Which names should overlays display?6. Feedback wanted
Design: does the recipe model cover what you'd need to draw your components? Engineering: does the scene graph work as a backend contract? Hub site: do the three views map cleanly onto recipes and render requests?
All reactions