Expand description
The theme loader and resolver (VAPP-92), a line-by-line port of
src/theme.ts + src/theme-types.ts. A theme is data, never code: one
JSON file of token VALUES per mode plus component RECIPES.
validate_theme turns a theme file into readable issues (never a
panic), load_theme flattens its extends chain into a
ResolvedTheme and resolve_recipe answers a painter’s question for
one mode with concrete values.
Precedence a painter applies (resolve_node_style): the native’s own
recipe < the node’s style < the macro part’s recipe < the node style’s
AUTHORED keys (VAPP-163: the style written on the macro node, listed in
recipe.authored by the expander).
Source objects are serde_json::Values in SOURCE order (preserve_order),
so issues come out in the TS order.
Round 1 (docs/round-1-contract.md §5): breakpoint (px), ease (cubic
bezier control points) and density (multipliers) token groups, a
high-contrast contrast overlay per mode, recipe keys for per-side
borders, text styling and motion, resolve_mode / apply_density /
apply_contrast for the surface settings, and resolve_condition_key
(a $breakpoint inside a media key resolves to px).
Re-exports§
pub use crate::generated::themes::THEME_SCHEMA_ID;
Structs§
- Font
Spec - How a host registers a family the theme names.
- Modes
- Recipe
Query - The question a painter asks.
- Recipe
Rule - One rule: applies when every
whenentry matches; rules merge in order. - Resolved
Theme - What a painter receives: complete, flat,
extendsgone. - Shadow
- One shadow layer. Numbers serialize in the JS number model (
1, not1.0). - Theme
Error - Every issue of a theme that failed to load.
- Theme
Issue - Theme
Mode - The per-mode values: colours and shadows.
- Theme
Options - The registry an
extendsresolves against and the catalog view recipes are validated against. - Theme
Tokens - Type
Tokens
Enums§
- Density
- The surface density;
default= the tokens as written. - Mode
- Mode
Setting - What a host asks for: a mode, or
system= the platform’s preference. - Theme
Ref - What an
extendsmay name: a theme source or an already resolved theme.
Constants§
- MODES
- The mode names, in resolution order.
Functions§
- apply_
contrast - The theme with its high-contrast overlays merged into the modes (the platform asked for more contrast). A theme without overlays is unchanged.
- apply_
density - The theme a surface of this density runs with:
controlandspacingscaled by the theme’s$density.<name>multiplier and rounded to whole px;default(or a theme without the multiplier) returns it unchanged. Done once per surface, so every resolver and fixture stays density-agnostic. - easing_
css - An easing as CSS
cubic-bezier(…). - is_
theme_ hex #rrggbbor#rrggbbaa, lowercase (color.tsisThemeHex).- load_
theme - A theme file → the flat theme a painter uses, or ONE error listing every issue.
- node_
recipe_ query - The recipe query a NORMALIZED node answers to: its macro part, or the native’s root with its own recipe props.
- recipe_
reacts_ to - Does the query’s recipe change under interaction
state(hover)? True when a rule names the state inwhen.stateand every otherwhenkey matches the query’s props (the rule’s OTHER states are not required: a[hover, checked]rule counts while unchecked). Painters ask it to know which nodes to track the pointer over. - recipe_
style - resolve_
condition_ key - A media key with its
$breakpoint.<name>replaced by the theme’s px (resolveConditionKey); any other key passes. - resolve_
mode system→ what the platform prefers; a mode stays itself.- resolve_
node_ style - What a painter paints a node with: native recipe < node style < macro part recipe < the node style’s authored keys, token references resolved, condition blocks kept nested.
- resolve_
recipe - A part’s concrete visuals for one mode (
theme-recipes.jsonlocks it). - resolve_
style_ values - Every token reference in a style object replaced by its value for the
mode (nested condition blocks, gradients and arrays included, and the
$breakpointtokens inside media keys); other values pass through. - resolve_
token $color.primaryindark→"#e5e5e5";$spacing.md→12;$shadow.sm→ the layers;$type.family.sans→"Inter".Nonewhen not a token (or not one this theme has).- rule_
specificity - The matching rules’ styles merged in order (token refs kept).
How specific a rule is: one point per
whencondition (astatelist counts each state). VAPP-90: rules merge in SPECIFICITY order, like the CSS the web renderer compiles them to — a base rule (nowhen) never shadows achecked/focus/variantrule that sits before it, which is what a child theme’s appended base override used to do under plain source order. Ties keep source order (later wins). MirrorsruleSpecificityinpackages/exponential-ui/src/theme.ts. - shadow_
css - The shadow layers as one CSS
box-shadowstring (for web painters). - try_
load_ theme - Validate + flatten, returning issues instead of failing loudly.
- validate_
theme - Every problem in ONE theme file, each with a path and a readable message. Never panics: a non-object is one issue.
Type Aliases§
- Theme
Recipes - Component → part → rules.