@weasel-js/theme 1.9.4 → 1.10.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.ts CHANGED
@@ -1,6 +1,20 @@
1
- import { n as TokenName, o as ResolvedTheme, a as Theme, S as Selection, p as TokenValue } from './definition-GS7_Kz9D.js';
2
- export { q as AxisDef, A as AxisDefs, r as AxisValue, s as BAKED_THEMES, B as BakedTheme, t as ByAxis, u as ColorContext, v as ColorList, F as FlatTokens, G as GeneratedColors, w as GeneratedTheme, P as PinObject, e as PinValue, x as RampColors, R as RawToken, y as SerializableColorList, z as THEMES, D as THEME_SOURCES, T as ThemeDefinition, E as ThemeInput, V as Varying, H as colorAt, I as colorCount, J as colorCssAt, K as defineTheme, M as enumerateSelections, Q as fullSelection, U as isByAxis, W as rampSteps, X as resolveTheme, Y as selectionKey, Z as themeAxes, _ as themeTones, $ as weaselTheme } from './definition-GS7_Kz9D.js';
1
+ import { o as ColorList, p as ColorSourceContext, q as TokenName, r as ResolvedTheme, a as Theme, S as Selection, s as TokenValue } from './definition-CSeERbSL.js';
2
+ export { t as AxisDef, A as AxisDefs, u as AxisValue, v as BAKED_THEMES, B as BakedTheme, w as ByAxis, x as ColorContext, y as ColorListItem, F as FlatTokens, G as GeneratedColors, z as GeneratedTheme, P as PinObject, e as PinValue, D as RampColors, R as RawToken, E as SerializableColorList, H as THEMES, I as THEME_SOURCES, T as ThemeDefinition, J as ThemeInput, V as Varying, K as colorCount, M as defineTheme, Q as enumerateSelections, U as fullSelection, W as isByAxis, X as rampSteps, Y as resolveTheme, Z as selectionKey, _ as themeAxes, $ as themeTones, a0 as weaselTheme } from './definition-CSeERbSL.js';
3
3
  export { C as ColorMode, a as ColorModePreference, i as isColorModePreference } from './colorMode-CoklZomJ.js';
4
+ import { ColorSource, ColorLiteral } from '@weasel-js/paint';
5
+
6
+ /**
7
+ * The `i`th color of `list`, wrapping. A ramp list reads the resolved theme, so
8
+ * the answer follows its mode; a `ColorSource` item resolves against the
9
+ * context's palette, then its theme. Throws on an item nothing answers.
10
+ */
11
+ declare function colorAt(list: ColorList, i: number, ctx?: ColorSourceContext): string;
12
+ /**
13
+ * As `colorAt`, but a ramp list, and an item that names the theme, answers
14
+ * with its custom property (`var(--wzl-swatch-sky)`), so a color written into
15
+ * CSS follows a mode change without re-rendering, provider or not.
16
+ */
17
+ declare function colorCssAt(list: ColorList, i: number, ctx?: ColorSourceContext): string;
4
18
 
5
19
  /** One row of `TOKEN_MANIFEST`: a token, its DTCG type, the name-prefix
6
20
  * group it belongs to, its value in the default theme and selection, and
@@ -34,6 +48,19 @@ declare const TOKEN_MANIFEST: readonly TokenManifestEntry[];
34
48
  */
35
49
  declare function tokenPx(name: TokenName, resolved?: ResolvedTheme): number;
36
50
 
51
+ /** A weight for each value of each axis a blend is made along. A value left out weighs nothing. */
52
+ type AxisWeights = Readonly<Record<string, Readonly<Record<string, number>>>>;
53
+ /**
54
+ * `theme` partway between values of its axes: resolved at every selection
55
+ * `weights` gives a share to, and each token folded from what it resolved to
56
+ * there. A color mixes in OKLCH and a number with one unit throughout mixes
57
+ * linearly; any other value is the heaviest selection's, the first on a tie.
58
+ * It is the resolved values that mix, never the rules behind them, so a token
59
+ * that is an alias in one mode and a literal in the other blends like any
60
+ * other. An axis `weights` leaves out stays at `selection`.
61
+ */
62
+ declare function blendTheme(theme: Theme, weights: AxisWeights, selection?: Selection): ResolvedTheme;
63
+
37
64
  /**
38
65
  * Apply `theme` at `selection` to `el`'s subtree, and return the release.
39
66
  *
@@ -49,11 +76,17 @@ declare function tokenPx(name: TokenName, resolved?: ResolvedTheme): number;
49
76
  * rule, which leaves the sheet once no element holds it; a release whose
50
77
  * element has since been given something else does nothing.
51
78
  *
79
+ * With `weights`, the rule holds the theme blended along the axes they name
80
+ * (see `blendTheme`), under the same attributes: applying again with the next
81
+ * weights is one step of a transition between two selections.
82
+ *
52
83
  * Two different themes may share a name. The second held at once has its rule
53
84
  * kept to its own elements by a `data-wzl-variant` attribute, matched inside
54
85
  * `:where()` so the rule's specificity is the first's.
55
86
  */
56
- declare function applyTheme(el: HTMLElement, theme: Theme, selection?: Selection): () => void;
87
+ declare function applyTheme(el: HTMLElement, theme: Theme, selection?: Selection, options?: {
88
+ weights?: AxisWeights;
89
+ }): () => void;
57
90
 
58
91
  /**
59
92
  * A resolved token value with `currentColor` taken to be `current`, for a surface drawn without the
@@ -66,6 +99,7 @@ declare function applyTheme(el: HTMLElement, theme: Theme, selection?: Selection
66
99
  */
67
100
  declare function resolveCurrentColor(value: string, current: string): string;
68
101
 
102
+ /** What `loadDTCG` reads: a `toDTCG` export, or a document shaped like one. */
69
103
  interface DtcgDocument {
70
104
  name?: unknown;
71
105
  defaultMode?: unknown;
@@ -96,6 +130,29 @@ declare function serializeTokenValue(type: string, value: TokenValue): string;
96
130
  */
97
131
  declare function parseTokenValue(type: string, text: string): TokenValue;
98
132
 
133
+ /** The name the tone list answers to: `{ ref: 'tone', index: 2 }` is the third tone, wrapping. */
134
+ declare const TONE_REF = "tone";
135
+
136
+ /**
137
+ * Resolve `source` to a literal, for a surface drawn without the cascade. A ref
138
+ * names an entry of the context's palette first, then the theme: `tone` with an
139
+ * index into the tone list, a token by its name without the `--wzl-` prefix, a
140
+ * ramp by its name with the index of a step, or a custom property spelled out.
141
+ * `null` for a name nothing answers, a token that is not a color, and a custom
142
+ * property the theme does not define.
143
+ */
144
+ declare function colorSourceLiteral(source: ColorSource, ctx?: ColorSourceContext): ColorLiteral | null;
145
+ /**
146
+ * `source` as a CSS color, naming what `colorSourceLiteral` resolves. A source
147
+ * that comes down to a ref the theme answers, directly or through palette
148
+ * entries and functions that only name another color, is written as that
149
+ * ref's custom property: it follows the cascade with no re-render, and a
150
+ * property spelled out need not be the theme's. Everything else is written as
151
+ * the literal it resolves to in `ctx`, which includes a function that reads a
152
+ * color through `resolve` to compute its own.
153
+ */
154
+ declare function colorSourceCss(source: ColorSource, ctx?: ColorSourceContext): string | null;
155
+
99
156
  /**
100
157
  * The vocabulary of stances, and the slots a theme styles a stanced surface with.
101
158
  *
@@ -140,4 +197,4 @@ interface StanceLookup<S extends string> {
140
197
  */
141
198
  declare function resolveStanceSlots<S extends string>(tokens: Readonly<Record<string, string>>, base: Readonly<Record<S, string>>, { stance, nested, stanced }?: StanceLookup<S>): Record<S, string>;
142
199
 
143
- export { ResolvedTheme, STANCES, STANCE_SLOTS, Selection, type Stance, type StanceLookup, type StanceSlot, TOKEN_MANIFEST, Theme, type TokenManifestEntry, TokenName, TokenValue, applyTheme, loadDTCG, parseTokenValue, resolveCurrentColor, resolveStanceSlots, serializeTokenValue, stanceSlotNames, tokenPx };
200
+ export { type AxisWeights, ColorList, ColorSourceContext, type DtcgDocument, ResolvedTheme, STANCES, STANCE_SLOTS, Selection, type Stance, type StanceLookup, type StanceSlot, TOKEN_MANIFEST, TONE_REF, Theme, type TokenManifestEntry, TokenName, TokenValue, applyTheme, blendTheme, colorAt, colorCssAt, colorSourceCss, colorSourceLiteral, loadDTCG, parseTokenValue, resolveCurrentColor, resolveStanceSlots, serializeTokenValue, stanceSlotNames, tokenPx };
package/dist/index.js CHANGED
@@ -1,219 +1,17 @@
1
- import { weaselTheme } from './chunk-EFGZ56CE.js';
2
- export { BAKED_THEMES, THEMES, THEME_SOURCES, applyTheme, colorAt, colorCount, colorCssAt, defineTheme, isColorModePreference, rampSteps, themeTones, weaselTheme } from './chunk-EFGZ56CE.js';
1
+ export { TONE_REF, applyTheme, blendTheme, colorAt, colorCount, colorCssAt, colorSourceCss, colorSourceLiteral, isColorModePreference, rampSteps, resolveCurrentColor, themeTones } from './chunk-5PFIA5JU.js';
3
2
  import { AXES_EXT, overrideKey, ALPHA_EXT } from './chunk-Z675UQ26.js';
4
- import { atAlpha, withAlpha, themeAxes, mergeAxes } from './chunk-7LCRXZDY.js';
5
- export { enumerateSelections, fullSelection, isByAxis, parseTokenValue, resolveTheme, selectionKey, serializeTokenValue, themeAxes } from './chunk-7LCRXZDY.js';
3
+ import './chunk-S7MJPFDP.js';
4
+ import { TOKEN_MANIFEST } from './chunk-354G4TUL.js';
5
+ export { TOKEN_MANIFEST } from './chunk-354G4TUL.js';
6
+ import './chunk-M3R5MV7Q.js';
7
+ import { themeAxes } from './chunk-32JKTYS2.js';
8
+ export { parseTokenValue, resolveTheme, serializeTokenValue, themeAxes } from './chunk-32JKTYS2.js';
9
+ import { weaselTheme } from './chunk-JX2OC444.js';
10
+ export { BAKED_THEMES, THEMES, THEME_SOURCES, defineTheme, weaselTheme } from './chunk-JX2OC444.js';
11
+ import { mergeAxes } from './chunk-P5F3GZV6.js';
12
+ export { enumerateSelections, fullSelection, isByAxis, selectionKey } from './chunk-P5F3GZV6.js';
6
13
  import { isPlainObject } from '@weasel-js/registry';
7
14
 
8
- // src/generated/manifest.ts
9
- var TOKEN_MANIFEST = [
10
- { name: "--wzl-gray-50", type: "color", group: "gray", defaultValue: "#f5f5f6", description: "", hook: false },
11
- { name: "--wzl-gray-100", type: "color", group: "gray", defaultValue: "#e6e7e9", description: "", hook: false },
12
- { name: "--wzl-gray-200", type: "color", group: "gray", defaultValue: "#c9cbcf", description: "", hook: false },
13
- { name: "--wzl-gray-300", type: "color", group: "gray", defaultValue: "#9ea1a8", description: "", hook: false },
14
- { name: "--wzl-gray-400", type: "color", group: "gray", defaultValue: "#6f737b", description: "", hook: false },
15
- { name: "--wzl-gray-500", type: "color", group: "gray", defaultValue: "#4d5058", description: "", hook: false },
16
- { name: "--wzl-gray-600", type: "color", group: "gray", defaultValue: "#383b42", description: "", hook: false },
17
- { name: "--wzl-gray-700", type: "color", group: "gray", defaultValue: "#25272c", description: "", hook: false },
18
- { name: "--wzl-gray-800", type: "color", group: "gray", defaultValue: "#181a1e", description: "", hook: false },
19
- { name: "--wzl-gray-900", type: "color", group: "gray", defaultValue: "#0e0f12", description: "", hook: false },
20
- { name: "--wzl-accent-soft", type: "color", group: "accent", defaultValue: "#262a66", description: "", hook: false },
21
- { name: "--wzl-accent-base", type: "color", group: "accent", defaultValue: "#5b63c9", description: "Periwinkle. Anchors primary actions on dark surfaces.", hook: false },
22
- { name: "--wzl-accent-strong", type: "color", group: "accent", defaultValue: "#8c94ee", description: "", hook: false },
23
- { name: "--wzl-secondary-soft", type: "color", group: "secondary", defaultValue: "#704e09", description: "", hook: false },
24
- { name: "--wzl-secondary-base", type: "color", group: "secondary", defaultValue: "#dc9d15", description: "", hook: false },
25
- { name: "--wzl-secondary-strong", type: "color", group: "secondary", defaultValue: "#f1cb8d", description: "", hook: false },
26
- { name: "--wzl-swatch-fuchsia", type: "color", group: "swatch", defaultValue: "#f641f7", description: "First of ten categorical spot colors for plotting, status and data viz. Take them in sequence: the order is farthest-point over hue, so the first N are as separated as N colors can be (first three 87\xB0 apart, all ten 32\xB0). Mode-invariant on purpose \u2014 a series keeps its color when the mode flips, which is why they are tuned for a dark surface and clear only 1.5:1 on a light one.", hook: false },
27
- { name: "--wzl-swatch-green", type: "color", group: "swatch", defaultValue: "#48e628", description: "", hook: false },
28
- { name: "--wzl-swatch-sky", type: "color", group: "swatch", defaultValue: "#36bff2", description: "", hook: false },
29
- { name: "--wzl-swatch-amber", type: "color", group: "swatch", defaultValue: "#e69628", description: "", hook: false },
30
- { name: "--wzl-swatch-teal", type: "color", group: "swatch", defaultValue: "#3ee1cb", description: "", hook: false },
31
- { name: "--wzl-swatch-red", type: "color", group: "swatch", defaultValue: "#f75034", description: "", hook: false },
32
- { name: "--wzl-swatch-blue", type: "color", group: "swatch", defaultValue: "#407ef7", description: "", hook: false },
33
- { name: "--wzl-swatch-citron", type: "color", group: "swatch", defaultValue: "#d5d23a", description: "", hook: false },
34
- { name: "--wzl-swatch-rose", type: "color", group: "swatch", defaultValue: "#fa4590", description: "", hook: false },
35
- { name: "--wzl-swatch-violet", type: "color", group: "swatch", defaultValue: "#955cf9", description: "", hook: false },
36
- { name: "--wzl-font-size-2xs", type: "dimension", group: "font", defaultValue: "10px", description: "Shortcut keys and index badges. The floor for chrome text.", hook: false },
37
- { name: "--wzl-font-size-xs", type: "dimension", group: "font", defaultValue: "12px", description: "Tool-button labels under an icon.", hook: false },
38
- { name: "--wzl-font-size-sm", type: "dimension", group: "font", defaultValue: "13px", description: "Chrome labels, status readouts, section headings.", hook: false },
39
- { name: "--wzl-font-size-md", type: "dimension", group: "font", defaultValue: "15px", description: "Controls and body text.", hook: false },
40
- { name: "--wzl-font-size-lg", type: "dimension", group: "font", defaultValue: "18px", description: "Panel and dialog titles.", hook: false },
41
- { name: "--wzl-font-size-xl", type: "dimension", group: "font", defaultValue: "23px", description: "The largest chrome text \u2014 a lab or app title.", hook: false },
42
- { name: "--wzl-space-1", type: "dimension", group: "space", defaultValue: "2px", description: "", hook: false },
43
- { name: "--wzl-space-2", type: "dimension", group: "space", defaultValue: "4px", description: "", hook: false },
44
- { name: "--wzl-space-3", type: "dimension", group: "space", defaultValue: "6px", description: "", hook: false },
45
- { name: "--wzl-space-4", type: "dimension", group: "space", defaultValue: "8px", description: "", hook: false },
46
- { name: "--wzl-space-5", type: "dimension", group: "space", defaultValue: "10px", description: "", hook: false },
47
- { name: "--wzl-space-6", type: "dimension", group: "space", defaultValue: "12px", description: "", hook: false },
48
- { name: "--wzl-space-7", type: "dimension", group: "space", defaultValue: "14px", description: "", hook: false },
49
- { name: "--wzl-space-8", type: "dimension", group: "space", defaultValue: "16px", description: "", hook: false },
50
- { name: "--wzl-surface", type: "color", group: "surface", defaultValue: "#181a1e", description: "", hook: false },
51
- { name: "--wzl-surface-raised", type: "color", group: "surface", defaultValue: "#25272c", description: "", hook: false },
52
- { name: "--wzl-surface-popover", type: "color", group: "surface", defaultValue: "#25272c", description: "Background of a dropdown, menu or other popover list. Follows surface-raised unless a theme needs floating lists to read differently from the panels beneath them.", hook: false },
53
- { name: "--wzl-surface-sunken", type: "color", group: "surface", defaultValue: "#0e0f12", description: "", hook: false },
54
- { name: "--wzl-fg", type: "color", group: "fg", defaultValue: "#e6e7e9", description: "", hook: false },
55
- { name: "--wzl-fg-muted", type: "color", group: "fg", defaultValue: "rgb(from currentColor r g b / 0.7)", description: "Secondary text: the text color in effect where it is used, at reduced alpha, so it steps down from whatever text it sits beside on any surface. The alpha is absolute, so muted text nested in muted text stays one step down. Under fg it clears WCAG 4.5:1 on surface, surface-raised, and surface-sunken in both modes.", hook: false },
56
- { name: "--wzl-fg-subtle", type: "color", group: "fg", defaultValue: "rgb(from currentColor r g b / 0.54)", description: "Tertiary text: a further step down from the text color in effect, by the same rule as fg-muted. Under fg it clears WCAG 4.5:1 on surface, surface-raised, and surface-sunken in both modes.", hook: false },
57
- { name: "--wzl-fg-muted-on-accent", type: "color", group: "fg", defaultValue: "rgb(from currentColor r g b / 0.98)", description: "Secondary text on an accent fill. Every rule that sets --wzl-fg-on-accent text redirects --wzl-fg-muted here (npm run check:on-accent), because the general step falls below WCAG 4.5:1 on the accent. In dark mode that leaves almost no step to show.", hook: false },
58
- { name: "--wzl-fg-subtle-on-accent", type: "color", group: "fg", defaultValue: "rgb(from currentColor r g b / 0.96)", description: "Tertiary text on an accent fill, redirected from --wzl-fg-subtle by the same rule as fg-muted-on-accent. Clears WCAG 4.5:1 on the accent in both modes.", hook: false },
59
- { name: "--wzl-border", type: "color", group: "border", defaultValue: "#25272c", description: "", hook: false },
60
- { name: "--wzl-border-strong", type: "color", group: "border", defaultValue: "#6f737b", description: "The line that has to be seen: a control's edge, a raised surface's outline. Clears WCAG 1.4.11's 3:1 against every surface in both modes.", hook: false },
61
- { name: "--wzl-accent-fg", type: "color", group: "accent", defaultValue: "#8c94ee", description: "Accent for foreground use \u2014 text, icons, selected labels drawn on a surface. accent is a fill; the midnight base is too dim to read as text on dark surfaces.", hook: false },
62
- { name: "--wzl-secondary-fg", type: "color", group: "secondary", defaultValue: "#dc9d15", description: "Secondary accent for foreground use: a second voice beside the accent, such as a value the panel derived rather than one the user set. Picked from the ramp so it clears 4.5:1 on the surface in both modes.", hook: false },
63
- { name: "--wzl-fg-inverse", type: "color", group: "fg", defaultValue: "#0e0f12", description: "Text drawn on a filled foreground-colored element (e.g. a slider thumb). Flips with the mode, so it is a semantic, not an alias to a primitive.", hook: false },
64
- { name: "--wzl-shadow", type: "color", group: "shadow", defaultValue: "rgba(0, 0, 0, 0.6)", description: "Elevation. Always darker than any surface \u2014 never derived from fg, which is near-white on dark.", hook: false },
65
- { name: "--wzl-code-keyword", type: "color", group: "code", defaultValue: "#955cf9", description: "Keywords in highlighted code.", hook: false },
66
- { name: "--wzl-code-string", type: "color", group: "code", defaultValue: "#48e628", description: "String literals in highlighted code.", hook: false },
67
- { name: "--wzl-code-number", type: "color", group: "code", defaultValue: "#e69628", description: "Numbers in highlighted code.", hook: false },
68
- { name: "--wzl-code-constant", type: "color", group: "code", defaultValue: "#3ee1cb", description: "true, false, null and undefined in highlighted code.", hook: false },
69
- { name: "--wzl-code-property", type: "color", group: "code", defaultValue: "#36bff2", description: "Property keys and attribute names in highlighted code.", hook: false },
70
- { name: "--wzl-code-name", type: "color", group: "code", defaultValue: "#fa4590", description: "Functions, classes and other names in highlighted code.", hook: false },
71
- { name: "--wzl-panel-surface", type: "color", group: "panel", defaultValue: "#25272c", description: "Fill of a PropertyPanel.", hook: false },
72
- { name: "--wzl-panel-border-color", type: "color", group: "panel", defaultValue: "#25272c", description: "", hook: false },
73
- { name: "--wzl-panel-border-style", type: "string", group: "panel", defaultValue: "solid", description: "", hook: false },
74
- { name: "--wzl-panel-border-width", type: "dimension", group: "panel", defaultValue: "1px", description: "", hook: false },
75
- { name: "--wzl-panel-radius", type: "dimension", group: "panel", defaultValue: "14px", description: "", hook: false },
76
- { name: "--wzl-panel-pad", type: "dimension", group: "panel", defaultValue: "14px 16px", description: "A panel\u2019s padding when no density sets one.", hook: false },
77
- { name: "--wzl-panel-blur", type: "dimension", group: "panel", defaultValue: "3px", description: "", hook: false },
78
- { name: "--wzl-panel-tone-mix", type: "number", group: "panel", defaultValue: "14%", description: "How much of a panel\u2019s tone mixes into its surface.", hook: false },
79
- { name: "--wzl-panel-title-font", type: "fontFamily", group: "panel", defaultValue: "Oswald, 'Helvetica Neue Condensed', 'Arial Narrow', system-ui, sans-serif", description: "", hook: false },
80
- { name: "--wzl-panel-title-weight", type: "fontWeight", group: "panel", defaultValue: "200", description: "", hook: false },
81
- { name: "--wzl-panel-title-size", type: "dimension", group: "panel", defaultValue: "18px", description: "", hook: false },
82
- { name: "--wzl-panel-title-case", type: "string", group: "panel", defaultValue: "none", description: "", hook: false },
83
- { name: "--wzl-panel-title-tracking", type: "dimension", group: "panel", defaultValue: "0.01em", description: "", hook: false },
84
- { name: "--wzl-panel-title-color", type: "color", group: "panel", defaultValue: "#e6e7e9", description: "", hook: false },
85
- { name: "--wzl-panel-title-inset", type: "dimension", group: "panel", defaultValue: "0", description: "", hook: false },
86
- { name: "--wzl-stance-scope-border-width", type: "dimension", group: "stance", defaultValue: "0", description: "", hook: false },
87
- { name: "--wzl-stance-scope-radius", type: "dimension", group: "stance", defaultValue: "8px", description: "", hook: false },
88
- { name: "--wzl-stance-scope-tone-mix", type: "number", group: "stance", defaultValue: "22%", description: "", hook: false },
89
- { name: "--wzl-stance-scope-nested-radius", type: "dimension", group: "stance", defaultValue: "6px", description: "", hook: false },
90
- { name: "--wzl-stance-scope-nested-surface", type: "color", group: "stance", defaultValue: "#181a1e", description: "A scope panel inside another sits back into it.", hook: false },
91
- { name: "--wzl-stance-aside-surface", type: "color", group: "stance", defaultValue: "transparent", description: "", hook: false },
92
- { name: "--wzl-stance-aside-border-color", type: "color", group: "stance", defaultValue: "rgba(230, 231, 233, 0.1)", description: "", hook: false },
93
- { name: "--wzl-stance-aside-blur", type: "dimension", group: "stance", defaultValue: "0px", description: "", hook: false },
94
- { name: "--wzl-stance-aside-title-color", type: "color", group: "stance", defaultValue: "rgb(from currentColor r g b / 0.54)", description: "", hook: false },
95
- { name: "--wzl-stance-advanced-title-color", type: "color", group: "stance", defaultValue: "rgb(from currentColor r g b / 0.54)", description: "", hook: false },
96
- { name: "--wzl-stance-debug-border-style", type: "string", group: "stance", defaultValue: "dashed", description: "", hook: false },
97
- { name: "--wzl-stance-debug-title-font", type: "fontFamily", group: "stance", defaultValue: "ui-monospace, SFMono-Regular, Menlo, Consolas, monospace", description: "", hook: false },
98
- { name: "--wzl-stance-debug-title-case", type: "string", group: "stance", defaultValue: "none", description: "", hook: false },
99
- { name: "--wzl-stance-danger-tone", type: "color", group: "stance", defaultValue: "#d94a3f", description: "", hook: false },
100
- { name: "--wzl-stance-danger-border-color", type: "color", group: "stance", defaultValue: "#d94a3f", description: "", hook: false },
101
- { name: "--wzl-stance-danger-title-color", type: "color", group: "stance", defaultValue: "#d94a3f", description: "", hook: false },
102
- { name: "--wzl-stance-notice-tone", type: "color", group: "stance", defaultValue: "#5b63c9", description: "", hook: false },
103
- { name: "--wzl-stance-notice-tone-mix", type: "number", group: "stance", defaultValue: "8%", description: "", hook: false },
104
- { name: "--wzl-stance-important-border-color", type: "color", group: "stance", defaultValue: "#8c94ee", description: "", hook: false },
105
- { name: "--wzl-stance-important-title-color", type: "color", group: "stance", defaultValue: "#8c94ee", description: "", hook: false },
106
- { name: "--wzl-stance-preview-pad", type: "dimension", group: "stance", defaultValue: "0", description: "", hook: false },
107
- { name: "--wzl-stance-preview-title-size", type: "dimension", group: "stance", defaultValue: "12px", description: "", hook: false },
108
- { name: "--wzl-stance-preview-title-case", type: "string", group: "stance", defaultValue: "none", description: "", hook: false },
109
- { name: "--wzl-stance-preview-title-inset", type: "dimension", group: "stance", defaultValue: "6px 10px 0", description: "", hook: false },
110
- { name: "--wzl-danger-base", type: "color", group: "status", defaultValue: "#d94a3f", description: "", hook: false },
111
- { name: "--wzl-warning-base", type: "color", group: "status", defaultValue: "#d99a3f", description: "", hook: false },
112
- { name: "--wzl-success-base", type: "color", group: "status", defaultValue: "#2ec27e", description: "", hook: false },
113
- { name: "--wzl-fg-on-accent", type: "color", group: "fg", defaultValue: "#f5f5f6", description: "", hook: false },
114
- { name: "--wzl-line-subtle", type: "color", group: "line", defaultValue: "rgba(230, 231, 233, 0.1)", description: "Barely-there separators (table rows).", hook: false },
115
- { name: "--wzl-line", type: "color", group: "line", defaultValue: "rgba(230, 231, 233, 0.2)", description: "Primary gridlines on sunken surfaces.", hook: false },
116
- { name: "--wzl-line-strong", type: "color", group: "line", defaultValue: "rgba(230, 231, 233, 0.4)", description: "Axes and emphasized dividers.", hook: false },
117
- { name: "--wzl-curve-color", type: "color", group: "curve", defaultValue: "#8c94ee", description: "Drawn data curves. Routes through the bright accent because accent-base is too dim on sunken surfaces.", hook: false },
118
- { name: "--wzl-accent", type: "color", group: "accent", defaultValue: "#5b63c9", description: "", hook: false },
119
- { name: "--wzl-accent-hover", type: "color", group: "accent", defaultValue: "#8c94ee", description: "", hook: false },
120
- { name: "--wzl-secondary", type: "color", group: "secondary", defaultValue: "#dc9d15", description: "Honey amber in dark mode and teal in light, where a darkened amber reads as brown. A fill; use secondary-fg for text.", hook: false },
121
- { name: "--wzl-danger", type: "color", group: "status", defaultValue: "#d94a3f", description: "", hook: false },
122
- { name: "--wzl-warning", type: "color", group: "status", defaultValue: "#d99a3f", description: "", hook: false },
123
- { name: "--wzl-success", type: "color", group: "status", defaultValue: "#2ec27e", description: "", hook: false },
124
- { name: "--wzl-focus-ring", type: "color", group: "focus", defaultValue: "#8c94ee", description: "", hook: false },
125
- { name: "--wzl-glass-tint", type: "color", group: "glass", defaultValue: "#5b63c9", description: "Frosted-glass tint. Components compose it as color-mix(in srgb, var(--wzl-glass-tint) 78%, transparent) with backdrop-filter: blur(3px).", hook: false },
126
- { name: "--wzl-surface-hover", type: "color", group: "surface", defaultValue: "rgba(230, 231, 233, 0.1)", description: "Hover wash over a raised surface. Same formula as line-subtle, different job \u2014 do not collapse them.", hook: false },
127
- { name: "--wzl-surface-pressed", type: "color", group: "surface", defaultValue: "rgba(230, 231, 233, 0.18)", description: "Pressed wash over a raised surface.", hook: false },
128
- { name: "--wzl-radius-sm", type: "dimension", group: "radius", defaultValue: "3px", description: "", hook: false },
129
- { name: "--wzl-radius-md", type: "dimension", group: "radius", defaultValue: "5px", description: "", hook: false },
130
- { name: "--wzl-radius-lg", type: "dimension", group: "radius", defaultValue: "14px", description: "", hook: false },
131
- { name: "--wzl-radius-pill", type: "dimension", group: "radius", defaultValue: "999px", description: "Fully rounded ends \u2014 segmented controls, progress tracks.", hook: false },
132
- { name: "--wzl-border-w", type: "dimension", group: "border", defaultValue: "1px", description: "", hook: false },
133
- { name: "--wzl-line-width", type: "dimension", group: "line", defaultValue: "2px", description: "Structural lines \u2014 gridlines, dividers, axes.", hook: false },
134
- { name: "--wzl-curve-width", type: "dimension", group: "curve", defaultValue: "3px", description: "Drawn data curves. Heavier than structural lines so data reads as primary content.", hook: false },
135
- { name: "--wzl-tb-height", type: "dimension", group: "tb", defaultValue: "32px", description: "Height of a horizontal toolbar strip (ButtonBar, OptionsBar, ToolOptionsBar). Taller than control-h so the controls inside a strip are not flush with its edges.", hook: false },
136
- { name: "--wzl-control-h-xs", type: "dimension", group: "control", defaultValue: "22px", description: "Height of the smallest interactive control -- a stepper, a keycap, a swatch button in a dense row. The rank below control-h-sm.", hook: false },
137
- { name: "--wzl-control-h-sm", type: "dimension", group: "control", defaultValue: "24px", description: "Height of a control in a dense inspector -- a Properties field, a small Button. The rank below control-h, which sizes a standalone control.", hook: false },
138
- { name: "--wzl-control-h", type: "dimension", group: "control", defaultValue: "28px", description: "Height of an interactive control \u2014 button, input, select, segmented control. Distinct from tb-height, which sizes the strip a row of them sits in.", hook: false },
139
- { name: "--wzl-icon-button-size", type: "dimension", group: "icon", defaultValue: "26px", description: "Side of a square icon button -- a dialog close, a row remove, a field clear. Smaller than control-h because it carries a glyph rather than a label, and square, so it sizes both axes.", hook: false },
140
- { name: "--wzl-slider-track-h", type: "dimension", group: "slider", defaultValue: "4px", description: "Height of a linear range track. The kit's single-thumb ranges all wear this; Slider's default 24px canvas track does not.", hook: false },
141
- { name: "--wzl-slider-thumb-size", type: "dimension", group: "slider", defaultValue: "8px", description: "Diameter of a linear range thumb.", hook: false },
142
- { name: "--wzl-slider-track-slop", type: "dimension", group: "slider", defaultValue: "6px", description: "How far past a range track's edge a press still lands on it. Invisible, and overlaps whatever sits beside the track rather than taking layout space.", hook: false },
143
- { name: "--wzl-slider-thumb-slop", type: "dimension", group: "slider", defaultValue: "6px", description: "How far past a range thumb's edge a press still grabs the thumb rather than landing on the track. Sits over the track's own slop.", hook: false },
144
- { name: "--wzl-slider-track-mix", type: "dimension", group: "slider", defaultValue: "40%", description: "Proportion of accent-fg in a range track, as a color-mix percentage \u2014 not a color. Mixed into a real property, never into another custom property. Higher in dark mode, where a light tint of the accent sinks into the surface.", hook: false },
145
- { name: "--wzl-slider-thumb-mix", type: "dimension", group: "slider", defaultValue: "100%", description: "Proportion of accent-fg in a range thumb, as a color-mix percentage \u2014 not a color. Solid in dark mode.", hook: false },
146
- { name: "--wzl-handle-size", type: "dimension", group: "handle", defaultValue: "9px", description: "Edge of a draggable handle on a plot or timeline \u2014 a keyframe diamond, a timeline key, an event mark. The default rank; -sm and -lg are the two deliberate departures from it.", hook: false },
147
- { name: "--wzl-handle-size-sm", type: "dimension", group: "handle", defaultValue: "7px", description: "A handle that is drawn but not draggable \u2014 a locked or pinned point. Smaller so it reads as inert next to a live one.", hook: false },
148
- { name: "--wzl-handle-size-lg", type: "dimension", group: "handle", defaultValue: "10px", description: "A handle that is a category of its own rather than one of a row \u2014 a curve's endpoint. Larger so it separates from the handles it sits in line with.", hook: false },
149
- { name: "--wzl-checker-a", type: "color", group: "checker", defaultValue: "#25272c", description: "One square of the transparency checker drawn under a paint that is empty, mixed or translucent. Paint it as repeating-conic-gradient(var(--wzl-checker-a) 0% 25%, var(--wzl-checker-b) 0% 50%) 50% / var(--wzl-checker-size) var(--wzl-checker-size).", hook: false },
150
- { name: "--wzl-checker-b", type: "color", group: "checker", defaultValue: "#181a1e", description: "The other square of the transparency checker.", hook: false },
151
- { name: "--wzl-checker-size", type: "dimension", group: "checker", defaultValue: "8px", description: "Edge of one repeat of the transparency checker: two squares by two.", hook: false },
152
- { name: "--wzl-workspace-surface", type: "color", group: "workspace", defaultValue: "#0e0f12", description: "Ground of a canvas app's workspace \u2014 the area around the document page.", hook: false },
153
- { name: "--wzl-workspace-line", type: "color", group: "workspace", defaultValue: "rgba(230, 231, 233, 0.1)", description: "Marks drawn over workspace-surface, such as its diagonal stripes, so the page reads as the thing on top.", hook: false },
154
- { name: "--wzl-field-pad-x", type: "dimension", group: "field", defaultValue: "8px", description: "Horizontal padding inside a boxed field. Pairs with --wzl-field-h, which is a container override and has no :root default.", hook: false },
155
- { name: "--wzl-glass-blur", type: "dimension", group: "glass", defaultValue: "3px", description: "Backdrop blur radius for frosted surfaces. Pairs with glass-tint.", hook: false },
156
- { name: "--wzl-font-size", type: "dimension", group: "font", defaultValue: "15px", description: "Controls and body text.", hook: false },
157
- { name: "--wzl-tracking-none", type: "dimension", group: "tracking", defaultValue: "0", description: "", hook: false },
158
- { name: "--wzl-tracking-wide", type: "dimension", group: "tracking", defaultValue: "0.06em", description: "Uppercase section headings.", hook: false },
159
- { name: "--wzl-tracking-wider", type: "dimension", group: "tracking", defaultValue: "0.08em", description: "Uppercase at 11px and below.", hook: false },
160
- { name: "--wzl-z-toolbar", type: "number", group: "z", defaultValue: "10", description: "", hook: false },
161
- { name: "--wzl-z-overlay", type: "number", group: "z", defaultValue: "20", description: "", hook: false },
162
- { name: "--wzl-z-modal", type: "number", group: "z", defaultValue: "30", description: "", hook: false },
163
- { name: "--wzl-leading-tight", type: "number", group: "leading", defaultValue: "1", description: "Single-line controls; the box sets the height.", hook: false },
164
- { name: "--wzl-leading-snug", type: "number", group: "leading", defaultValue: "1.2", description: "Headings and two-line labels.", hook: false },
165
- { name: "--wzl-leading", type: "number", group: "leading", defaultValue: "1.4", description: "Body and anything that wraps.", hook: false },
166
- { name: "--wzl-backdrop", type: "gradient", group: "backdrop", defaultValue: "none", description: "Layered backdrop fill for a page or lab root. `none` here; a theme with a signature background sets it.", hook: false },
167
- { name: "--wzl-motion-fast", type: "duration", group: "motion", defaultValue: "120ms", description: "Micro-interactions \u2014 hover, focus, pressed.", hook: false },
168
- { name: "--wzl-motion-medium", type: "duration", group: "motion", defaultValue: "240ms", description: "Entrances and exits \u2014 toasts, popovers, panels.", hook: false },
169
- { name: "--wzl-ease-in-cubic", type: "cubicBezier", group: "ease", defaultValue: "cubic-bezier(0.32, 0, 0.67, 0)", description: "", hook: false },
170
- { name: "--wzl-ease-out-cubic", type: "cubicBezier", group: "ease", defaultValue: "cubic-bezier(0.33, 1, 0.68, 1)", description: "", hook: false },
171
- { name: "--wzl-ease-in-out-cubic", type: "cubicBezier", group: "ease", defaultValue: "cubic-bezier(0.65, 0, 0.35, 1)", description: "", hook: false },
172
- { name: "--wzl-ease-out-back", type: "cubicBezier", group: "ease", defaultValue: "cubic-bezier(0.34, 1.56, 0.64, 1)", description: "", hook: false },
173
- { name: "--wzl-font-ui", type: "fontFamily", group: "font", defaultValue: "Oswald, 'Helvetica Neue Condensed', 'Arial Narrow', system-ui, sans-serif", description: "Condensed UI/display face. The heavier cuts get blocky at any size, so the weight tokens stay in the 200-400 range.", hook: false },
174
- { name: "--wzl-font-numeric", type: "fontFamily", group: "font", defaultValue: "'Oswald Tabular', var(--wzl-font-ui)", description: "The UI face with equal-width digits, for numbers read down a column or updated in place. Oswald Tabular carries only 0-9 and the figure space (U+2007); every other character falls through to the UI face.", hook: false },
175
- { name: "--wzl-font-display", type: "fontFamily", group: "font", defaultValue: "Oswald, 'Helvetica Neue Condensed', 'Arial Narrow', system-ui, sans-serif", description: "", hook: false },
176
- { name: "--wzl-font-body", type: "fontFamily", group: "font", defaultValue: "Inter, system-ui, -apple-system, 'Segoe UI', sans-serif", description: "", hook: false },
177
- { name: "--wzl-font-mono", type: "fontFamily", group: "font", defaultValue: "ui-monospace, SFMono-Regular, Menlo, Consolas, monospace", description: "", hook: false },
178
- { name: "--wzl-font-weight-light", type: "fontWeight", group: "font", defaultValue: "200", description: "", hook: false },
179
- { name: "--wzl-font-weight-normal", type: "fontWeight", group: "font", defaultValue: "300", description: "", hook: false },
180
- { name: "--wzl-font-weight-medium", type: "fontWeight", group: "font", defaultValue: "350", description: "", hook: false },
181
- { name: "--wzl-font-weight-bold", type: "fontWeight", group: "font", defaultValue: "400", description: "", hook: false },
182
- { name: "--wzl-space-xs", type: "dimension", group: "space", defaultValue: "4px", description: "Alias for space-2. The t-shirt names name every other rung of the ladder.", hook: false },
183
- { name: "--wzl-space-sm", type: "dimension", group: "space", defaultValue: "8px", description: "Alias for space-4. The t-shirt names name every other rung of the ladder.", hook: false },
184
- { name: "--wzl-space-md", type: "dimension", group: "space", defaultValue: "12px", description: "Alias for space-6. The t-shirt names name every other rung of the ladder.", hook: false },
185
- { name: "--wzl-space-lg", type: "dimension", group: "space", defaultValue: "16px", description: "Alias for space-8. The t-shirt names name every other rung of the ladder.", hook: false },
186
- { name: "--wzl-detail-figure-min-width", type: "dimension", group: "detail", defaultValue: "8ch", description: 'Least width of a value cell in a `values="figures"` DetailList.', hook: true },
187
- { name: "--wzl-dialog-max-width", type: "dimension", group: "dialog", defaultValue: "900px", description: "Widest a Dialog grows, modal or inline, before its contents wrap or scroll.", hook: true },
188
- { name: "--wzl-disclosure-fill", type: "color", group: "disclosure", defaultValue: "var(--wzl-accent-fg)", description: "Fill of a Disclosure\u2019s fold mark.", hook: true },
189
- { name: "--wzl-disclosure-gap", type: "dimension", group: "disclosure", defaultValue: "4px", description: "Gap between a Disclosure\u2019s twisty and its label.", hook: true },
190
- { name: "--wzl-disclosure-target", type: "dimension", group: "disclosure", defaultValue: "20px", description: "Hit-target square of a Disclosure twisty, and the twisty column of a LayerList row.", hook: true },
191
- { name: "--wzl-input-surface", type: "color", group: "input", defaultValue: "var(--wzl-surface-sunken)", description: "Surface a field\u2019s frame sits on \u2014 Input, NumberField, ComboBox, Select, MenuButton, ListEditor and the property rows. Set it on any container whose own background is the default \u2014 a sunken rail or panel \u2014 where an unset field is the same color as what is behind it.", hook: true },
192
- { name: "--wzl-number-field-width", type: "dimension", group: "number", defaultValue: "9ch", description: "Width of a NumberField\u2019s input.", hook: true },
193
- { name: "--wzl-params-label-align", type: "string", group: "params", defaultValue: "start", description: "Text alignment of row labels in PropertyPanel, Prefs and labkit\u2019s ControlPanel.", hook: true },
194
- { name: "--wzl-params-label-case", type: "string", group: "params", defaultValue: "uppercase", description: "text-transform of every label and title in PropertyPanel, Prefs and labkit\u2019s ControlPanel.", hook: true },
195
- { name: "--wzl-params-label-tracking", type: "dimension", group: "params", defaultValue: "var(--wzl-tracking-wide)", description: "Letter spacing of every label and title in PropertyPanel, Prefs and labkit\u2019s ControlPanel. Unset, rows take --wzl-tracking-wide and titles --wzl-tracking-wider.", hook: true },
196
- { name: "--wzl-params-label-width", type: "dimension", group: "params", defaultValue: "auto", description: "Inline size of row labels in PropertyPanel, Prefs and labkit\u2019s ControlPanel.", hook: true },
197
- { name: "--wzl-prefs-across-gap", type: "dimension", group: "prefs", defaultValue: "28px", description: "Gap between the two columns of rows a PrefsForm pane sets side by side.", hook: true },
198
- { name: "--wzl-prefs-column-width", type: "dimension", group: "prefs", defaultValue: "300px", description: "Width of the Prefs category column.", hook: true },
199
- { name: "--wzl-prefs-control-min", type: "dimension", group: "prefs", defaultValue: "80px", description: "Narrowest a PrefsForm row\u2019s control gets in a two-across pane before the row wraps it under its label.", hook: true },
200
- { name: "--wzl-prefs-rail-width", type: "dimension", group: "prefs", defaultValue: "216px", description: "Width of the Prefs navigation rail.", hook: true },
201
- { name: "--wzl-prop-number-width", type: "dimension", group: "prop", defaultValue: "9ch", description: "Width of a numeric field in the Properties panel.", hook: true },
202
- { name: "--wzl-prop-panel-actions-basis", type: "dimension", group: "prop", defaultValue: "auto", description: "Width a PropertyPanel\u2019s title row gives its actions. Set, it holds that width whatever the actions are.", hook: true },
203
- { name: "--wzl-prop-row-h", type: "dimension", group: "prop", defaultValue: "20px", description: "Floor under every Properties row, whatever control it holds. Unset, it is the panel\u2019s own field height, so it follows density \u2014 20px at the default one.", hook: true },
204
- { name: "--wzl-prop-text-width", type: "dimension", group: "prop", defaultValue: "16ch", description: "Width of a text field in the Properties panel.", hook: true },
205
- { name: "--wzl-property-readout-w", type: "dimension", group: "property", defaultValue: "calc(4.5ch + 2px)", description: "Width of a Properties row\u2019s value readout \u2014 four digits, so the controls beside a column of readouts end on one line. A range whose widest value needs more widens its own readout.", hook: true },
206
- { name: "--wzl-select-border", type: "border", group: "select", defaultValue: "1px solid var(--wzl-border)", description: "Border of a Select\u2019s trigger. Unset, a boxed trigger draws --wzl-border and a bare one a transparent border of the same width.", hook: true },
207
- { name: "--wzl-select-fg", type: "color", group: "select", defaultValue: "var(--wzl-fg)", description: "Text color of a Select\u2019s trigger.", hook: true },
208
- { name: "--wzl-swatch-size", type: "dimension", group: "swatch", defaultValue: "28px", description: "Minimum cell of a swatch grid \u2014 PatternPicker, and any panel laying swatches out the same way.", hook: true },
209
- { name: "--wzl-timeline-label-w", type: "dimension", group: "timeline", defaultValue: "120px", description: "Width of the Timeline\u2019s track-label gutter.", hook: true },
210
- { name: "--wzl-timeline-value-axis-w", type: "dimension", group: "timeline", defaultValue: "32px", description: "Width reserved for the Timeline\u2019s value axis.", hook: true },
211
- { name: "--wzl-tree-fold-size", type: "dimension", group: "tree", defaultValue: "16px", description: "Size of the leading glyph a Tree folds a branch by, where its branches fold by their glyphs.", hook: true },
212
- { name: "--wzl-tree-font-size", type: "dimension", group: "tree", defaultValue: "var(--wzl-font-size-sm)", description: "Size of a Tree row\u2019s text.", hook: true },
213
- { name: "--wzl-tree-guide", type: "color", group: "tree", defaultValue: "var(--wzl-fg-subtle)", description: "Color of the bracket a Tree draws down a branch.", hook: true },
214
- { name: "--wzl-tree-indent", type: "dimension", group: "tree", defaultValue: "calc(var(--wzl-control-h-xs) + var(--wzl-space-2))", description: "Indent of each Tree level. Unset, it is one twisty and one gap, so a child\u2019s twisty sits under its parent\u2019s label.", hook: true }
215
- ];
216
-
217
15
  // src/tokenPx.ts
218
16
  var DEFAULTS = new Map(TOKEN_MANIFEST.map((t) => [t.name, t.defaultValue]));
219
17
  function tokenPx(name, resolved) {
@@ -223,22 +21,6 @@ function tokenPx(name, resolved) {
223
21
  return Number(m[1]);
224
22
  }
225
23
 
226
- // src/currentColor.ts
227
- var NUMBER = String.raw`(\d*\.?\d+)(%?)`;
228
- var RELATIVE = new RegExp(String.raw`^rgb\(\s*from\s+currentcolor\s+r\s+g\s+b\s*/\s*${NUMBER}\s*\)$`, "i");
229
- var MIX = new RegExp(String.raw`^color-mix\(\s*in\s+[\w-]+\s*,\s*currentcolor\s+${NUMBER}\s*,\s*transparent\s*\)$`, "i");
230
- var fraction = (n, pct) => Number(n) / (pct ? 100 : 1);
231
- function resolveCurrentColor(value, current) {
232
- const v = value.trim();
233
- if (!/currentcolor/i.test(v)) return value;
234
- if (/^currentcolor$/i.test(v)) return current;
235
- const rel = RELATIVE.exec(v);
236
- if (rel) return atAlpha(current, fraction(rel[1], rel[2]));
237
- const mix = MIX.exec(v);
238
- if (mix && mix[2] === "%") return withAlpha(current, fraction(mix[1], mix[2]));
239
- throw new Error(`resolveCurrentColor: cannot flatten "${value}"`);
240
- }
241
-
242
24
  // src/dtcg/flatten.ts
243
25
  var isToken = (v) => typeof v === "object" && v !== null && "$value" in v;
244
26
  function flattenTokens(doc) {
@@ -388,6 +170,6 @@ function resolveStanceSlots(tokens, base, { stance, nested, stanced } = {}) {
388
170
  return out;
389
171
  }
390
172
 
391
- export { STANCES, STANCE_SLOTS, TOKEN_MANIFEST, loadDTCG, resolveCurrentColor, resolveStanceSlots, stanceSlotNames, tokenPx };
173
+ export { STANCES, STANCE_SLOTS, loadDTCG, resolveStanceSlots, stanceSlotNames, tokenPx };
392
174
  //# sourceMappingURL=index.js.map
393
175
  //# sourceMappingURL=index.js.map