@unpunnyfuns/swatchbook-blocks 0.60.9 → 0.62.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/README.md CHANGED
@@ -2,9 +2,9 @@
2
2
 
3
3
  React MDX doc blocks for [swatchbook](https://github.com/unpunnyfuns/swatchbook).
4
4
 
5
- Render your DTCG tokens in `.mdx` stories swatch grids, type-specific previews, per-token inspectors. The blocks react to the toolbar's axis flips without any wiring in your story code.
5
+ Render your DTCG tokens in `.mdx` stories: swatch grids, type-specific previews, per-token inspectors. The blocks react to the toolbar's axis flips without any wiring in your story code.
6
6
 
7
- Most consumers pick this up transitively via [`@unpunnyfuns/swatchbook-addon`](../addon); `import { TokenTable } from '@unpunnyfuns/swatchbook-addon'` works out of the box. Install this package directly when you want blocks *without* the Storybook addon unit tests, a standalone React app wrapping tokens in a custom surface.
7
+ Most consumers pick this up transitively via [`@unpunnyfuns/swatchbook-addon`](../addon); `import { TokenTable } from '@unpunnyfuns/swatchbook-addon'` works out of the box. Install this package directly when you want blocks *without* the Storybook addon, such as unit tests or a standalone React app wrapping tokens in a custom surface.
8
8
 
9
9
  ## Install
10
10
 
@@ -39,10 +39,10 @@ Block catalogue, props, and composition patterns live in the [blocks reference](
39
39
 
40
40
  ## Boundaries
41
41
 
42
- - ✅ Compose multiple blocks per page each mounts independently.
42
+ - ✅ Compose multiple blocks per page; each mounts independently.
43
43
  - ✅ Render outside Storybook with a hand-built or loaded `ProjectSnapshot`.
44
- - ❌ Don't import from `virtual:swatchbook/tokens` it's the addon's internal wiring, not a public API. Use `SwatchbookProvider`.
45
- - ❌ Don't use `useGlobals` / `useArgs` from `storybook/preview-api` inside custom blocks those hooks throw in docs context.
44
+ - ❌ Don't import from `virtual:swatchbook/tokens`; it's the addon's internal wiring, not a public API. Use `SwatchbookProvider`.
45
+ - ❌ Don't use `useGlobals` / `useArgs` from `storybook/preview-api` inside custom blocks; those hooks throw in docs context.
46
46
 
47
47
  ## Credits
48
48
 
@@ -50,4 +50,4 @@ Token parsing and resolver evaluation come from [Terrazzo](https://terrazzo.app/
50
50
 
51
51
  ## Documentation
52
52
 
53
- [unpunnyfuns.github.io/swatchbook](https://unpunnyfuns.github.io/swatchbook/) concepts, guides, and full API reference.
53
+ [unpunnyfuns.github.io/swatchbook](https://unpunnyfuns.github.io/swatchbook/): concepts, guides, and full API reference.
package/dist/index.d.mts CHANGED
@@ -1,54 +1,11 @@
1
+ import { COLOR_FORMATS, ColorFormat } from "@unpunnyfuns/swatchbook-core/color-formats";
2
+ import { FormatColorResult, NormalizedColor, formatColor } from "@unpunnyfuns/swatchbook-core/format-color";
1
3
  import * as _$react from "react";
2
4
  import { ReactElement, ReactNode } from "react";
3
5
  import { TokenGraph } from "@unpunnyfuns/swatchbook-core/graph";
4
6
  import { Axis, Diagnostic, Preset } from "@unpunnyfuns/swatchbook-core";
5
7
  import { SlimListedToken } from "@unpunnyfuns/swatchbook-core/snapshot-for-wire";
6
8
 
7
- //#region src/format-color.d.ts
8
- /**
9
- * Color display formats understood by {@link formatColor}.
10
- *
11
- * - `hex` — sRGB hex (`#rrggbb` or `#rrggbbaa`). Out-of-gamut or wide-gamut
12
- * colors fall back to `rgb()` and surface `outOfGamut: true` so callers
13
- * can render a ⚠ glyph.
14
- * - `rgb` / `hsl` — modern CSS Color 4 space-separated syntax, converted
15
- * from the source colorspace. Out-of-gamut values are still stringified
16
- * (the browser will clip when actually rendering) and flagged.
17
- * - `oklch` — perceptual wide-gamut form. Never marks out-of-gamut because
18
- * every color expressible in sRGB/P3 fits in oklch.
19
- * - `raw` — compact JSON of the normalized Terrazzo shape. For DTCG
20
- * authors who want to see what the parser actually stored.
21
- */
22
- type ColorFormat = 'hex' | 'rgb' | 'hsl' | 'oklch' | 'raw';
23
- declare const COLOR_FORMATS: readonly ColorFormat[];
24
- /**
25
- * Terrazzo's `ColorValueNormalized`, copied inline to avoid a hard dep on
26
- * `@terrazzo/token-tools` from blocks. Matches the shape documented at
27
- * https://terrazzo.app/docs/cli/reference/token-tools/ColorValueNormalized.
28
- *
29
- * Some token payloads we see in the wild use the legacy DTCG-ish `channels`
30
- * field in place of `components`; we accept either.
31
- */
32
- interface NormalizedColor {
33
- colorSpace: string;
34
- components?: readonly (number | null)[];
35
- channels?: readonly (number | null)[];
36
- alpha?: number;
37
- hex?: string;
38
- }
39
- interface FormatColorResult {
40
- /** Display string — e.g. `rgb(59 132 246)`, `#3b82f6`. */
41
- value: string;
42
- /** True when the requested format can't losslessly represent the color. */
43
- outOfGamut: boolean;
44
- }
45
- /**
46
- * Convert Terrazzo's normalized color payload into a display string in the
47
- * requested format. Pure function — never throws; returns `{ value: '—' }`
48
- * for unrecognized input so calling blocks don't need try/catch.
49
- */
50
- declare function formatColor(value: unknown, format: ColorFormat, fallback?: string): FormatColorResult;
51
- //#endregion
52
9
  //#region src/contexts.d.ts
53
10
  /**
54
11
  * Typed shape of the addon's `virtual:swatchbook/tokens` module.
@@ -114,9 +71,6 @@ type VirtualTokenGraph = TokenGraph;
114
71
  */
115
72
  interface ProjectSnapshot {
116
73
  axes: readonly VirtualAxisShape[];
117
- /** Axis names suppressed via `config.disabledAxes` — pinned to their defaults, hidden from the toolbar. */
118
- disabledAxes: readonly string[];
119
- presets: readonly VirtualPresetShape[];
120
74
  activeTheme: string;
121
75
  activeAxes: Readonly<Record<string, string>>;
122
76
  cssVarPrefix: string;
@@ -169,7 +123,7 @@ declare function useActiveTheme(): string;
169
123
  * Active axis tuple for the current story/docs render — `Record<axisName,
170
124
  * contextName>`. Derived from the same input as {@link ThemeContext}; split
171
125
  * out so consumers needing per-axis info (toolbar, panel, tuple-aware
172
- * blocks) don't have to reparse the composed permutation ID.
126
+ * blocks) don't have to reparse the composed theme name.
173
127
  */
174
128
  declare const AxesContext: _$react.Context<Readonly<Record<string, string>>>;
175
129
  declare function useActiveAxes(): Readonly<Record<string, string>>;
@@ -314,7 +268,7 @@ interface ColorTableProps {
314
268
  *
315
269
  * Single-member groups render as plain rows (no pill selector). Empty
316
270
  * map (default) disables grouping entirely; each token renders as its
317
- * own row, identical to the pre-grouping behavior.
271
+ * own row.
318
272
  */
319
273
  variants?: Record<string, string>;
320
274
  }
@@ -348,7 +302,7 @@ declare function Diagnostics({
348
302
  }?: DiagnosticsProps): ReactElement;
349
303
  //#endregion
350
304
  //#region src/dimension-scale/DimensionBar.d.ts
351
- type DimensionKind = 'length' | 'radius' | 'size';
305
+ type DimensionVisual = 'length' | 'radius' | 'size';
352
306
  interface DimensionBarProps {
353
307
  /** Full dot-path of the dimension token to preview. */
354
308
  path: string;
@@ -358,11 +312,11 @@ interface DimensionBarProps {
358
312
  * - `'radius'`: 56×56 square with the token applied as `border-radius`.
359
313
  * - `'size'`: a square sized to the token's dimension.
360
314
  */
361
- kind?: DimensionKind;
315
+ visual?: DimensionVisual;
362
316
  }
363
317
  declare function DimensionBar({
364
318
  path,
365
- kind
319
+ visual
366
320
  }: DimensionBarProps): ReactElement;
367
321
  //#endregion
368
322
  //#region src/DimensionScale.d.ts
@@ -378,7 +332,7 @@ interface DimensionScaleProps {
378
332
  * - `'radius'`: 56×56 square with the token applied as `border-radius`.
379
333
  * - `'size'`: a square sized to the token's dimension.
380
334
  */
381
- kind?: DimensionKind;
335
+ visual?: DimensionVisual;
382
336
  /** Override the caption. */
383
337
  caption?: string;
384
338
  /**
@@ -394,14 +348,14 @@ interface DimensionScaleProps {
394
348
  }
395
349
  declare function DimensionScale({
396
350
  filter,
397
- kind,
351
+ visual,
398
352
  caption,
399
353
  sortBy,
400
354
  sortDir
401
355
  }: DimensionScaleProps): ReactElement;
402
356
  //#endregion
403
- //#region src/FontFamilySample.d.ts
404
- interface FontFamilySampleProps {
357
+ //#region src/FontFamilyPreview.d.ts
358
+ interface FontFamilyPreviewProps {
405
359
  /**
406
360
  * Token-path filter. Defaults to every `fontFamily` token. Use e.g.
407
361
  * `"font.family.*"` to scope to the ref layer.
@@ -420,13 +374,13 @@ interface FontFamilySampleProps {
420
374
  /** `'asc'` (default) or `'desc'`. */
421
375
  sortDir?: SortDir;
422
376
  }
423
- declare function FontFamilySample({
377
+ declare function FontFamilyPreview({
424
378
  filter,
425
379
  sample,
426
380
  caption,
427
381
  sortBy,
428
382
  sortDir
429
- }: FontFamilySampleProps): ReactElement;
383
+ }: FontFamilyPreviewProps): ReactElement;
430
384
  //#endregion
431
385
  //#region src/FontWeightScale.d.ts
432
386
  interface FontWeightScaleProps {
@@ -569,6 +523,25 @@ declare function OpacityScale({
569
523
  sortDir
570
524
  }: OpacityScaleProps): ReactElement;
571
525
  //#endregion
526
+ //#region src/internal/channel-globals.d.ts
527
+ /**
528
+ * Shared subscription to Storybook's globals channel, lifted out of React
529
+ * component state so the values survive docs-mode remounts.
530
+ *
531
+ * On MDX docs pages, Storybook force-rerenders the docs container on every
532
+ * `updateGlobals` (see `preview/runtime.js` → `onUpdateGlobals`), which
533
+ * unmounts and remounts any embedded blocks. A `useState(null)` initializer
534
+ * inside the block would reset to null on each remount — the symptom is a
535
+ * one-frame flicker to the correct value, then revert to the defaults.
536
+ * Module-level state persists; React reads it through `useSyncExternalStore`
537
+ * and stays concurrent-safe.
538
+ */
539
+ interface ChannelGlobals {
540
+ axes: Record<string, string> | null;
541
+ format: ColorFormat | null;
542
+ }
543
+ declare function useChannelGlobals(): ChannelGlobals;
544
+ //#endregion
572
545
  //#region src/provider.d.ts
573
546
  interface SwatchbookProviderProps {
574
547
  value: ProjectSnapshot;
@@ -594,6 +567,49 @@ declare function SwatchbookProvider({
594
567
  */
595
568
  declare function useSwatchbookData(): ProjectSnapshot;
596
569
  //#endregion
570
+ //#region src/internal/channel-tokens.d.ts
571
+ /**
572
+ * Live token snapshot backed by the addon's preview dev-time HMR event.
573
+ *
574
+ * The initial snapshot is *injected* by the addon preview via
575
+ * {@link registerTokenSource} rather than imported from the addon's
576
+ * `virtual:swatchbook/tokens` build artifact — so blocks carries no
577
+ * dependency on that module and imports cleanly standalone (outside
578
+ * Storybook, in unit tests, in the docs site). Until something registers
579
+ * a source, blocks render from empty defaults.
580
+ *
581
+ * For dev-time updates this module subscribes to `TOKENS_UPDATED_EVENT`
582
+ * on Storybook's channel (which the addon preview re-broadcasts from its
583
+ * own HMR listener) and exposes the latest snapshot via
584
+ * `useSyncExternalStore`, so hooks re-render in place on each token save.
585
+ */
586
+ declare const TOKENS_UPDATED_EVENT = "swatchbook/tokens-updated";
587
+ interface TokenSnapshot {
588
+ readonly axes: readonly VirtualAxisShape[];
589
+ readonly presets: readonly {
590
+ name: string;
591
+ axes: Partial<Record<string, string>>;
592
+ description?: string;
593
+ }[];
594
+ readonly diagnostics: readonly VirtualDiagnosticShape[];
595
+ readonly css: string;
596
+ readonly cssVarPrefix: string;
597
+ readonly listing: Readonly<Record<string, VirtualTokenListingShape>>;
598
+ readonly tokenGraph: VirtualTokenGraph;
599
+ readonly defaultTuple: Record<string, string>;
600
+ /** Monotonic counter, bumped on each update. Useful as a React key. */
601
+ readonly version: number;
602
+ }
603
+ /**
604
+ * Seed the initial token snapshot. The addon preview calls this once at
605
+ * init with the build-time `virtual:swatchbook/tokens` data. Keeping the
606
+ * virtual-module read on the addon side (the package that owns it) lets
607
+ * blocks import cleanly without it. No-op fields fall back to the current
608
+ * snapshot, so a partial source is safe.
609
+ */
610
+ declare function registerTokenSource(source: Partial<TokenSnapshot>): void;
611
+ declare function useTokenSnapshot(): TokenSnapshot;
612
+ //#endregion
597
613
  //#region src/ShadowPreview.d.ts
598
614
  interface ShadowPreviewProps {
599
615
  /**
@@ -628,8 +644,8 @@ declare function ShadowSample({
628
644
  path
629
645
  }: ShadowSampleProps): ReactElement;
630
646
  //#endregion
631
- //#region src/StrokeStyleSample.d.ts
632
- interface StrokeStyleSampleProps {
647
+ //#region src/StrokeStylePreview.d.ts
648
+ interface StrokeStylePreviewProps {
633
649
  /**
634
650
  * Token-path filter. Defaults to every `strokeStyle` token. Use e.g.
635
651
  * `"stroke.style.*"` to scope to the ref layer.
@@ -646,12 +662,12 @@ interface StrokeStyleSampleProps {
646
662
  /** `'asc'` (default) or `'desc'`. */
647
663
  sortDir?: SortDir;
648
664
  }
649
- declare function StrokeStyleSample({
665
+ declare function StrokeStylePreview({
650
666
  filter,
651
667
  caption,
652
668
  sortBy,
653
669
  sortDir
654
- }: StrokeStyleSampleProps): ReactElement;
670
+ }: StrokeStylePreviewProps): ReactElement;
655
671
  //#endregion
656
672
  //#region src/TokenDetail.d.ts
657
673
  interface TokenDetailProps {
@@ -859,5 +875,5 @@ declare function TypographyScale({
859
875
  sortDir
860
876
  }: TypographyScaleProps): ReactElement;
861
877
  //#endregion
862
- export { AliasChain, type AliasChainProps, AliasedBy, type AliasedByProps, AxesContext, AxisVariance, type AxisVarianceProps, BorderPreview, type BorderPreviewProps, BorderSample, type BorderSampleProps, COLOR_FORMATS, type ColorFormat, ColorFormatContext, ColorPalette, type ColorPaletteProps, ColorTable, type ColorTableProps, CompositeBreakdown, type CompositeBreakdownProps, CompositePreview, type CompositePreviewProps, ConsumerOutput, type ConsumerOutputProps, Diagnostics, type DiagnosticsProps, DimensionBar, type DimensionBarProps, type DimensionKind, DimensionScale, type DimensionScaleProps, FontFamilySample, type FontFamilySampleProps, FontWeightScale, type FontWeightScaleProps, type FormatColorResult, GradientPalette, type GradientPaletteProps, MotionPreview, type MotionPreviewProps, MotionSample, type MotionSampleProps, type MotionSpeed, type NormalizedColor, OpacityScale, type OpacityScaleProps, type ProjectSnapshot, ShadowPreview, type ShadowPreviewProps, ShadowSample, type ShadowSampleProps, StrokeStyleSample, type StrokeStyleSampleProps, SwatchbookContext, SwatchbookProvider, type SwatchbookProviderProps, ThemeContext, TokenDetail, type TokenDetailProps, TokenHeader, type TokenHeaderProps, TokenNavigator, type TokenNavigatorProps, TokenTable, type TokenTableProps, TokenUsageSnippet, type TokenUsageSnippetProps, TypographyScale, type TypographyScaleProps, type VirtualAxisShape as VirtualAxis, type VirtualAxisShape, type VirtualDiagnosticShape as VirtualDiagnostic, type VirtualDiagnosticShape, type VirtualPresetShape as VirtualPreset, type VirtualPresetShape, type VirtualTokenShape as VirtualToken, type VirtualTokenShape, type VirtualTokenGraph, type VirtualTokenListingShape, formatColor, useActiveAxes, useActiveTheme, useColorFormat, useOptionalSwatchbookData, useSwatchbookData };
878
+ export { AliasChain, type AliasChainProps, AliasedBy, type AliasedByProps, AxesContext, AxisVariance, type AxisVarianceProps, BorderPreview, type BorderPreviewProps, BorderSample, type BorderSampleProps, COLOR_FORMATS, type ChannelGlobals, type ColorFormat, ColorFormatContext, ColorPalette, type ColorPaletteProps, ColorTable, type ColorTableProps, CompositeBreakdown, type CompositeBreakdownProps, CompositePreview, type CompositePreviewProps, ConsumerOutput, type ConsumerOutputProps, Diagnostics, type DiagnosticsProps, DimensionBar, type DimensionBarProps, DimensionScale, type DimensionScaleProps, type DimensionVisual, FontFamilyPreview, type FontFamilyPreviewProps, FontWeightScale, type FontWeightScaleProps, type FormatColorResult, GradientPalette, type GradientPaletteProps, MotionPreview, type MotionPreviewProps, MotionSample, type MotionSampleProps, type MotionSpeed, type NormalizedColor, OpacityScale, type OpacityScaleProps, type ProjectSnapshot, ShadowPreview, type ShadowPreviewProps, ShadowSample, type ShadowSampleProps, StrokeStylePreview, type StrokeStylePreviewProps, SwatchbookContext, SwatchbookProvider, type SwatchbookProviderProps, TOKENS_UPDATED_EVENT, ThemeContext, TokenDetail, type TokenDetailProps, TokenHeader, type TokenHeaderProps, TokenNavigator, type TokenNavigatorProps, type TokenSnapshot, TokenTable, type TokenTableProps, TokenUsageSnippet, type TokenUsageSnippetProps, TypographyScale, type TypographyScaleProps, type VirtualAxisShape as VirtualAxis, type VirtualAxisShape, type VirtualDiagnosticShape as VirtualDiagnostic, type VirtualDiagnosticShape, type VirtualPresetShape as VirtualPreset, type VirtualPresetShape, type VirtualTokenShape as VirtualToken, type VirtualTokenShape, type VirtualTokenGraph, type VirtualTokenListingShape, formatColor, registerTokenSource, useActiveAxes, useActiveTheme, useChannelGlobals, useColorFormat, useOptionalSwatchbookData, useSwatchbookData, useTokenSnapshot };
863
879
  //# sourceMappingURL=index.d.mts.map