@godxjp/ui 33.20.0 → 33.21.0

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.
Files changed (108) hide show
  1. package/README.md +4 -4
  2. package/agent/START-HERE.md +7 -7
  3. package/agent/components/AppSettingPicker.json +0 -1
  4. package/agent/components/AppShell.json +11 -1
  5. package/agent/components/CardShowcase.json +44 -0
  6. package/agent/components/CatalogCard.json +83 -0
  7. package/agent/components/CatalogDetail.json +76 -0
  8. package/agent/components/CatalogDetailSection.json +52 -0
  9. package/agent/components/CatalogDetailTag.json +27 -0
  10. package/agent/components/EditorialArticle.json +53 -0
  11. package/agent/components/EditorialAuth.json +53 -0
  12. package/agent/components/EditorialAuthCard.json +52 -0
  13. package/agent/components/EditorialBanner.json +53 -0
  14. package/agent/components/EditorialBreadcrumb.json +38 -0
  15. package/agent/components/EditorialCard.json +70 -0
  16. package/agent/components/EditorialEmptyPanel.json +57 -0
  17. package/agent/components/EditorialFilterBar.json +51 -0
  18. package/agent/components/EditorialFilterField.json +39 -0
  19. package/agent/components/EditorialFilterPanel.json +46 -0
  20. package/agent/components/EditorialFooter.json +54 -0
  21. package/agent/components/EditorialFootnote.json +36 -0
  22. package/agent/components/EditorialHero.json +52 -0
  23. package/agent/components/EditorialInlineSearch.json +54 -0
  24. package/agent/components/EditorialMasthead.json +52 -0
  25. package/agent/components/EditorialMetaBar.json +37 -0
  26. package/agent/components/EditorialPageHeader.json +73 -0
  27. package/agent/components/EditorialPanel.json +48 -0
  28. package/agent/components/EditorialPillNav.json +41 -0
  29. package/agent/components/EditorialPrompt.json +54 -0
  30. package/agent/components/EditorialSearch.json +112 -0
  31. package/agent/components/EditorialSection.json +68 -0
  32. package/agent/components/EditorialSectionHead.json +62 -0
  33. package/agent/components/EditorialStats.json +32 -0
  34. package/agent/components/EditorialTextButton.json +47 -0
  35. package/agent/components/EditorialToggleGroup.json +52 -0
  36. package/agent/components/EditorialToolbar.json +45 -0
  37. package/agent/components/Eyebrow.json +39 -0
  38. package/agent/components/HoldingCard.json +69 -0
  39. package/agent/components/HoldingCardAction.json +51 -0
  40. package/agent/components/HoldingGrid.json +37 -0
  41. package/agent/components/NumberInput.json +5 -0
  42. package/agent/components/PriceSummary.json +32 -0
  43. package/agent/components/SettingsLayout.json +31 -0
  44. package/agent/components/SettingsPanel.json +53 -0
  45. package/agent/components/ThemePicker.json +54 -0
  46. package/agent/components/TopbarItem.json +5 -0
  47. package/agent/components-index.json +292 -98
  48. package/agent/components.json +2046 -2
  49. package/agent/index.json +7 -7
  50. package/agent/llms.txt +8 -8
  51. package/agent/tokens.json +5637 -135
  52. package/dist/components/data-display/badge.js +4 -2
  53. package/dist/components/data-entry/form-field.js +2 -2
  54. package/dist/components/data-entry/number-input.d.ts +1 -0
  55. package/dist/components/data-entry/number-input.js +8 -0
  56. package/dist/components/data-entry/select.js +24 -2
  57. package/dist/components/general/button.js +7 -0
  58. package/dist/components/general/typography.d.ts +1 -1
  59. package/dist/components/layout/app-shell.d.ts +1 -1
  60. package/dist/components/layout/app-shell.js +28 -2
  61. package/dist/components/layout/centered-shell.js +4 -0
  62. package/dist/components/layout/editorial-account.d.ts +51 -0
  63. package/dist/components/layout/editorial-account.js +466 -0
  64. package/dist/components/layout/editorial-catalog.d.ts +18 -0
  65. package/dist/components/layout/editorial-catalog.js +164 -0
  66. package/dist/components/layout/editorial.d.ts +56 -0
  67. package/dist/components/layout/editorial.js +867 -0
  68. package/dist/components/layout/index.d.ts +6 -0
  69. package/dist/components/layout/index.js +98 -0
  70. package/dist/components/layout/mobile-shell.d.ts +2 -0
  71. package/dist/components/layout/mobile-shell.js +18 -11
  72. package/dist/components/layout/responsive-grid.js +9 -1
  73. package/dist/components/layout/topbar-item.d.ts +1 -0
  74. package/dist/components/layout/topbar-item.js +2 -0
  75. package/dist/contracts/measurement.json +1 -1
  76. package/dist/lib/toast-clearance.js +1 -1
  77. package/dist/props/components/data-entry.prop.d.ts +9 -0
  78. package/dist/props/components/editorial-account.prop.d.ts +249 -0
  79. package/dist/props/components/editorial-account.prop.js +0 -0
  80. package/dist/props/components/general.prop.d.ts +6 -2
  81. package/dist/props/components/layout.prop.d.ts +602 -2
  82. package/dist/props/registry.d.ts +1124 -0
  83. package/dist/props/registry.js +792 -0
  84. package/dist/styles/badge-layout.css +2 -0
  85. package/dist/styles/control.css +58 -12
  86. package/dist/styles/core.css +1 -0
  87. package/dist/styles/data-display-layout.css +9 -3
  88. package/dist/styles/editorial-account-layout.css +1130 -0
  89. package/dist/styles/focus-ring.css +33 -10
  90. package/dist/styles/form-layout.css +8 -1
  91. package/dist/styles/index.css +1 -0
  92. package/dist/styles/layers.json +248 -1
  93. package/dist/styles/layout.css +2022 -0
  94. package/dist/styles/shell-layout.css +100 -2
  95. package/dist/styles/table-layout.css +25 -13
  96. package/dist/styles/text-layout.css +6 -0
  97. package/dist/styles.css +1 -1
  98. package/dist/tokens/base.css +2 -0
  99. package/dist/tokens/components/badge.css +3 -0
  100. package/dist/tokens/components/control.css +9 -0
  101. package/dist/tokens/components/editorial-account.css +393 -0
  102. package/dist/tokens/components/editorial.css +721 -0
  103. package/dist/tokens/components/form.css +4 -0
  104. package/dist/tokens/components/shell.css +23 -0
  105. package/dist/tokens/components/table.css +1 -1
  106. package/docs/TOKENS.md +26 -0
  107. package/package.json +2 -2
  108. package/scripts/ui-audit.mjs +3 -2
@@ -55,5 +55,11 @@ export { AspectRatio } from "./aspect-ratio.js";
55
55
  export { ServiceRolePanel } from "./service-role-panel.js";
56
56
  export type { ServiceRoleItemProp, ServiceRolePanelProp, ServiceRolePanelProps, } from "./service-role-panel.js";
57
57
  export { useAppShellNavigationMode } from "./app-shell.js";
58
+ export { EditorialAuth, EditorialAuthCard, EditorialEmptyPanel, EditorialFootnote, EditorialMetaBar, EditorialStats, EditorialTextButton, EditorialToggleGroup, EditorialToolbar, HoldingCard, HoldingCardAction, HoldingGrid, SettingsLayout, SettingsPanel, ThemePicker, } from "./editorial-account.js";
59
+ export type { EditorialAuthCardProp, EditorialAuthCardProps, EditorialAuthProp, EditorialAuthProps, EditorialEmptyPanelProp, EditorialEmptyPanelProps, EditorialFootnoteProp, EditorialFootnoteProps, EditorialMetaBarProp, EditorialMetaBarProps, EditorialStatsItemProp, EditorialStatsProp, EditorialStatsProps, EditorialTextButtonProp, EditorialTextButtonProps, EditorialToggleGroupItemProp, EditorialToggleGroupProp, EditorialToggleGroupProps, EditorialToolbarProp, EditorialToolbarProps, HoldingCardActionProp, HoldingCardProp, HoldingCardProps, HoldingGridProp, HoldingGridProps, HoldingViewProp, SettingsLayoutProp, SettingsLayoutProps, SettingsPanelProp, SettingsPanelProps, ThemePickerOptionProp, ThemePickerPreviewProp, ThemePickerProp, ThemePickerProps, } from "./editorial-account.js";
58
60
  export { Affix } from "./affix.js";
59
61
  export type { AffixProp, AffixProps, AffixTargetProp } from "./affix.js";
62
+ export { CatalogDetail, CatalogDetailSection, CatalogDetailTag, EditorialFilterField, EditorialFilterPanel, EditorialPrompt, PriceSummary, } from "./editorial-catalog.js";
63
+ export type { CatalogDetailProp, CatalogDetailProps, CatalogDetailSectionProp, CatalogDetailSectionProps, CatalogDetailTagProp, EditorialPromptProp, EditorialPromptProps, PriceSummaryProp, PriceSummaryProps, EditorialFilterFieldProp, EditorialFilterFieldProps, EditorialFilterPanelProp, EditorialFilterPanelProps, } from "./editorial-catalog.js";
64
+ export { CardShowcase, CatalogCard, CatalogCardTag, EditorialArticle, EditorialArticleSection, EditorialBanner, EditorialBreadcrumb, EditorialCard, EditorialFilterBar, EditorialFooter, EditorialHero, EditorialMasthead, EditorialMastheadAction, EditorialMastheadLink, EditorialNote, EditorialPageHeader, EditorialPanel, EditorialPillNav, EditorialPillNavItem, EditorialSearch, EditorialSection, EditorialSectionHead, EditorialTextLink, Eyebrow, } from "./editorial.js";
65
+ export type { CardShowcaseProp, CardShowcaseProps, CatalogCardProp, CatalogCardProps, CatalogCardTagProp, EditorialBannerProp, EditorialBannerProps, EditorialArticleProp, EditorialArticleProps, EditorialArticleSectionProp, EditorialNoteProp, EditorialPanelProp, EditorialPanelProps, EditorialBreadcrumbProp, EditorialBreadcrumbProps, EditorialCardProp, EditorialCardProps, EditorialHeroProp, EditorialHeroProps, EditorialPageHeaderProp, EditorialPageHeaderProps, EditorialPillNavItemProp, EditorialPillNavProp, EditorialPillNavProps, EditorialSearchProp, EditorialSearchProps, EditorialSearchSuggestionFooterProp, EditorialSearchSuggestionGroupProp, EditorialSearchSuggestionProp, EditorialSectionHeadProp, EditorialSectionHeadProps, EditorialSectionProp, EditorialSectionProps, EditorialTextLinkProp, EyebrowProp, EyebrowProps, EditorialFilterBarProp, EditorialFooterProp, EditorialMastheadActionProp, EditorialMastheadLinkProp, EditorialMastheadProp, } from "./editorial.js";
@@ -26,7 +26,59 @@ import { Separator } from "./separator.js";
26
26
  import { AspectRatio } from "./aspect-ratio.js";
27
27
  import { ServiceRolePanel } from "./service-role-panel.js";
28
28
  import { useAppShellNavigationMode } from "./app-shell.js";
29
+ import {
30
+ EditorialAuth,
31
+ EditorialAuthCard,
32
+ EditorialEmptyPanel,
33
+ EditorialFootnote,
34
+ EditorialMetaBar,
35
+ EditorialStats,
36
+ EditorialTextButton,
37
+ EditorialToggleGroup,
38
+ EditorialToolbar,
39
+ HoldingCard,
40
+ HoldingCardAction,
41
+ HoldingGrid,
42
+ SettingsLayout,
43
+ SettingsPanel,
44
+ ThemePicker
45
+ } from "./editorial-account.js";
29
46
  import { Affix } from "./affix.js";
47
+ import {
48
+ CatalogDetail,
49
+ CatalogDetailSection,
50
+ CatalogDetailTag,
51
+ EditorialFilterField,
52
+ EditorialFilterPanel,
53
+ EditorialPrompt,
54
+ PriceSummary
55
+ } from "./editorial-catalog.js";
56
+ import {
57
+ CardShowcase,
58
+ CatalogCard,
59
+ CatalogCardTag,
60
+ EditorialArticle,
61
+ EditorialArticleSection,
62
+ EditorialBanner,
63
+ EditorialBreadcrumb,
64
+ EditorialCard,
65
+ EditorialFilterBar,
66
+ EditorialFooter,
67
+ EditorialHero,
68
+ EditorialMasthead,
69
+ EditorialMastheadAction,
70
+ EditorialMastheadLink,
71
+ EditorialNote,
72
+ EditorialPageHeader,
73
+ EditorialPanel,
74
+ EditorialPillNav,
75
+ EditorialPillNavItem,
76
+ EditorialSearch,
77
+ EditorialSection,
78
+ EditorialSectionHead,
79
+ EditorialTextLink,
80
+ Eyebrow
81
+ } from "./editorial.js";
30
82
  export {
31
83
  AccountChip,
32
84
  Affix,
@@ -39,25 +91,71 @@ export {
39
91
  AuthIdentity,
40
92
  AuthStack,
41
93
  Breadcrumb,
94
+ CardShowcase,
95
+ CatalogCard,
96
+ CatalogCardTag,
97
+ CatalogDetail,
98
+ CatalogDetailSection,
99
+ CatalogDetailTag,
42
100
  CenteredShell,
101
+ EditorialArticle,
102
+ EditorialArticleSection,
103
+ EditorialAuth,
104
+ EditorialAuthCard,
105
+ EditorialBanner,
106
+ EditorialBreadcrumb,
107
+ EditorialCard,
108
+ EditorialEmptyPanel,
109
+ EditorialFilterBar,
110
+ EditorialFilterField,
111
+ EditorialFilterPanel,
112
+ EditorialFooter,
113
+ EditorialFootnote,
114
+ EditorialHero,
115
+ EditorialMasthead,
116
+ EditorialMastheadAction,
117
+ EditorialMastheadLink,
118
+ EditorialMetaBar,
119
+ EditorialNote,
120
+ EditorialPageHeader,
121
+ EditorialPanel,
122
+ EditorialPillNav,
123
+ EditorialPillNavItem,
124
+ EditorialPrompt,
125
+ EditorialSearch,
126
+ EditorialSection,
127
+ EditorialSectionHead,
128
+ EditorialStats,
129
+ EditorialTextButton,
130
+ EditorialTextLink,
131
+ EditorialToggleGroup,
132
+ EditorialToolbar,
43
133
  ErrorSurface,
134
+ Eyebrow,
44
135
  Flex,
136
+ HoldingCard,
137
+ HoldingCardAction,
138
+ HoldingGrid,
45
139
  MasterDetail,
46
140
  MobileShell,
47
141
  NavList,
48
142
  OrgSwitcher,
49
143
  PageContainer,
144
+ PriceSummary,
50
145
  ResizableHandle,
51
146
  ResizablePanel,
52
147
  ResizablePanelGroup,
53
148
  ResponsiveGrid,
54
149
  Separator,
55
150
  ServiceRolePanel,
151
+ SettingsLayout,
152
+ SettingsPanel,
56
153
  Sidebar,
57
154
  SidebarHeader,
58
155
  SidebarItem,
59
156
  SidebarSection,
60
157
  SplitPane,
158
+ ThemePicker,
61
159
  Topbar,
62
160
  TopbarItem,
63
161
  TopbarSearch,
@@ -1,5 +1,7 @@
1
1
  import type { MobileShellProp } from "../../props/components/layout.prop.js";
2
2
  export type { MobileShellProp, MobileShellProp as MobileShellProps, } from "../../props/components/layout.prop.js";
3
+ /** Shared internal navigation surface; both shells use the same tiling and current-page styles. */
4
+ export declare const ShellTabBar: import("react").ForwardRefExoticComponent<Omit<import("react").DetailedHTMLProps<import("react").HTMLAttributes<HTMLElement>, HTMLElement>, "ref"> & import("react").RefAttributes<HTMLElement>>;
3
5
  /**
4
6
  * MobileShell — the HANDHELD app shell: a status band, an app bar, ONE scroll region,
5
7
  * a sticky action bar and a bottom tab bar, in that fixed order.
@@ -1,9 +1,23 @@
1
1
  "use client";
2
2
  import { jsx, jsxs } from "react/jsx-runtime";
3
- import { useRef } from "react";
3
+ import { forwardRef, useRef } from "react";
4
4
  import { useTranslation } from "../../i18n/use-translation.js";
5
5
  import { useToastStickyBarClearance } from "../../lib/toast-clearance.js";
6
6
  import { cn } from "../../lib/utils.js";
7
+ const ShellTabBar = forwardRef(
8
+ function ShellTabBar2({ className, "aria-label": label, ...props }, ref) {
9
+ const { t } = useTranslation();
10
+ return /* @__PURE__ */ jsx(
11
+ "nav",
12
+ {
13
+ ...props,
14
+ ref,
15
+ className: cn("ui-mobile-shell-tabbar", className),
16
+ "aria-label": label ?? t("layout.sidebar.ariaLabel")
17
+ }
18
+ );
19
+ }
20
+ );
7
21
  function MobileShell({
8
22
  statusBar,
9
23
  header,
@@ -44,19 +58,12 @@ function MobileShell({
44
58
  }
45
59
  ),
46
60
  actions !== void 0 && /* @__PURE__ */ jsx("footer", { ref: actionsRef, className: "ui-mobile-shell-actions", children: actions }),
47
- tabBar !== void 0 && /* @__PURE__ */ jsx(
48
- "nav",
49
- {
50
- ref: tabBarRef,
51
- className: "ui-mobile-shell-tabbar",
52
- "aria-label": t("layout.sidebar.ariaLabel"),
53
- children: tabBar
54
- }
55
- )
61
+ tabBar !== void 0 && /* @__PURE__ */ jsx(ShellTabBar, { ref: tabBarRef, children: tabBar })
56
62
  ]
57
63
  }
58
64
  );
59
65
  }
60
66
  export {
61
- MobileShell
67
+ MobileShell,
68
+ ShellTabBar
62
69
  };
@@ -4,6 +4,12 @@ import { cn } from "../../lib/utils.js";
4
4
  const RESPONSIVE_GRID_PRESET_COLUMNS = {
5
5
  "pricing-plans": { base: 1, sm: 3, md: 3, lg: 3 }
6
6
  };
7
+ const TOKEN_PRESETS = /* @__PURE__ */ new Set([
8
+ "catalog",
9
+ "trio",
10
+ "lead",
11
+ "panels"
12
+ ]);
7
13
  function resolveColumns(columns) {
8
14
  if (typeof columns === "number") {
9
15
  return {
@@ -40,12 +46,14 @@ function ResponsiveGrid({
40
46
  className,
41
47
  children
42
48
  }) {
43
- const resolved = preset ? RESPONSIVE_GRID_PRESET_COLUMNS[preset] : resolveColumns(columns);
49
+ const tokenPreset = preset !== void 0 && TOKEN_PRESETS.has(preset) ? preset : void 0;
50
+ const resolved = (preset && RESPONSIVE_GRID_PRESET_COLUMNS[preset]) ?? resolveColumns(columns);
44
51
  return /* @__PURE__ */ jsx("div", { className: "ui-responsive-grid-scope", children: /* @__PURE__ */ jsx(
45
52
  "div",
46
53
  {
47
54
  className: cn("ui-responsive-grid", className),
48
55
  "data-gap": gap,
56
+ "data-preset": tokenPreset,
49
57
  "data-flow": flow === "columns" ? "columns" : void 0,
50
58
  "data-align": align,
51
59
  "data-dense": dense && flow !== "columns" ? "" : void 0,
@@ -12,6 +12,7 @@ export type { TopbarItemProp, TopbarItemProp as TopbarItemProps, } from "../../p
12
12
  */
13
13
  export declare const TopbarItem: React.ForwardRefExoticComponent<Omit<React.ButtonHTMLAttributes<HTMLButtonElement>, "children"> & {
14
14
  hideBelow?: import("../../props/index.js").BreakpointProp;
15
+ hideFrom?: import("../../props/index.js").BreakpointProp;
15
16
  icon?: React.ReactNode;
16
17
  iconHideFrom?: import("../../props/index.js").BreakpointProp;
17
18
  labelHideBelow?: import("../../props/index.js").BreakpointProp;
@@ -7,6 +7,7 @@ const TopbarItem = React.forwardRef(function TopbarItem2({
7
7
  className,
8
8
  type,
9
9
  hideBelow,
10
+ hideFrom,
10
11
  icon,
11
12
  iconHideFrom,
12
13
  labelHideBelow,
@@ -62,6 +63,7 @@ const TopbarItem = React.forwardRef(function TopbarItem2({
62
63
  "data-truncate": truncate ? "true" : void 0,
63
64
  title: truncate && typeof label === "string" ? label : void 0,
64
65
  "data-hide-below": hideBelow,
66
+ "data-hide-from": hideFrom,
65
67
  className: cn("ui-topbar-item ui-focus-ring", className),
66
68
  type: asChild ? void 0 : type ?? "button",
67
69
  ...props,
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "$comment": "AUTO-GENERATED by scripts/gen-measurement-contract.mjs — do not edit. Read this instead of guessing: docs/MEASUREMENT-CONTRACT.md.",
3
- "version": "33.20.0",
3
+ "version": "33.21.0",
4
4
  "targetSize": {
5
5
  "standard": "WCAG 2.2 SC 2.5.8 Target Size (Minimum), level AA — 24×24 CSS px",
6
6
  "min": 24,
@@ -14,7 +14,7 @@ function useToastStickyBarClearance(refs, enabled) {
14
14
  };
15
15
  publish();
16
16
  const observer = new ResizeObserver(publish);
17
- for (const el of elements) observer.observe(el);
17
+ for (const el of elements) observer.observe(el, { box: "border-box" });
18
18
  return () => {
19
19
  observer.disconnect();
20
20
  html.style.removeProperty(TOAST_STICKY_BAR_PROPERTY);
@@ -360,6 +360,15 @@ export type NumberInputProp = FieldA11yProps & {
360
360
  prefix?: React.ReactNode;
361
361
  /** Trailing affix inside the field (e.g. `%`). */
362
362
  suffix?: React.ReactNode;
363
+ /**
364
+ * How the field takes its inline space, as `Select` and the pickers mean it (gh#1448).
365
+ * `full` (default) fills the line; `auto` is sized to the widest value the bounds allow (the
366
+ * formatted `min` / `max`, 6 characters when unbounded) plus the steppers — a quantity stepper in
367
+ * a `ListRow` trailing slot, outside any `FormField` `controlWidth`; `bounded` holds
368
+ * `--control-bounded-width`. Measured in a consumer deck builder: a 0–99 stepper took 215px at
369
+ * 1440px and, at 390px, pushed every row's trailing cluster onto its own line.
370
+ */
371
+ width?: ControlWidthProp;
363
372
  /** Form field name — the visible input submits its value natively. */
364
373
  name?: NameProp;
365
374
  id?: IdProp;
@@ -0,0 +1,249 @@
1
+ /** Editorial account family prop types (gh#1439) — @see components/layout/editorial-account.tsx */
2
+ import type { ReactNode } from "react";
3
+ import type { ClassNameProp } from "../vocabulary/index.js";
4
+ /** One choice of an EditorialToggleGroup. `label` is the visible text (text variant) and the
5
+ * accessible name of the button in both variants. */
6
+ export type EditorialToggleGroupItemProp = {
7
+ value: string;
8
+ label: string;
9
+ icon?: ReactNode;
10
+ };
11
+ /**
12
+ * @see EditorialToggleGroup — a named `role="group"` of `aria-pressed` buttons, one pressed at a
13
+ * time: `variant="text"` for a filter ("All · Cards · Sealed"), `variant="icon"` for a framed
14
+ * icon-only switch (grid / list view). Geometry: `--editorial-toggle-group-*`.
15
+ */
16
+ export type EditorialToggleGroupProp = {
17
+ "aria-label": string;
18
+ items: EditorialToggleGroupItemProp[];
19
+ value: string;
20
+ onValueChange: (value: string) => void;
21
+ /** `text` (default) shows the labels; `icon` shows only the icons, the label is the name. */
22
+ variant?: "text" | "icon";
23
+ className?: ClassNameProp;
24
+ };
25
+ /**
26
+ * @see EditorialMetaBar — a hairline-ruled strip under a page header: a start cluster (a glyph and
27
+ * a line, e.g. "Your private collection") and an end slot (a badge). Stacks on a phone (tokens).
28
+ */
29
+ export type EditorialMetaBarProp = {
30
+ /** Leading glyph, drawn in the primary tone. */
31
+ icon?: ReactNode;
32
+ start: ReactNode;
33
+ end?: ReactNode;
34
+ className?: ClassNameProp;
35
+ };
36
+ /**
37
+ * @see EditorialEmptyPanel — a centred panel for a signed-out or an empty state. `variant="guest"`
38
+ * draws a decorative three-card stack above the copy; `variant="empty"` is dashed, with a round
39
+ * icon medallion.
40
+ */
41
+ export type EditorialEmptyPanelProp = {
42
+ variant?: "guest" | "empty";
43
+ /** A kicker (an `Eyebrow`) above the title. */
44
+ eyebrow?: ReactNode;
45
+ title: ReactNode;
46
+ /** Heading level of the title. Default `2`. */
47
+ level?: 2 | 3;
48
+ description?: ReactNode;
49
+ /** Buttons, centred in a wrapping row. */
50
+ actions?: ReactNode;
51
+ /** The medallion glyph of `variant="empty"`. */
52
+ icon?: ReactNode;
53
+ className?: ClassNameProp;
54
+ };
55
+ /** One tile of an EditorialStats strip. */
56
+ export type EditorialStatsItemProp = {
57
+ label: ReactNode;
58
+ value: ReactNode;
59
+ /** A small unit after the figure ("items"). */
60
+ unit?: ReactNode;
61
+ /** A short line under the figure. */
62
+ note?: ReactNode;
63
+ };
64
+ /**
65
+ * @see EditorialStats — a strip of figure tiles on unequal tracks; the first tile is the lead
66
+ * (emphasised; on a phone it spans the row with its figure beside the label).
67
+ */
68
+ export type EditorialStatsProp = {
69
+ items: EditorialStatsItemProp[];
70
+ /** Accessible name of the strip (a list). */
71
+ "aria-label"?: string;
72
+ className?: ClassNameProp;
73
+ };
74
+ /**
75
+ * @see EditorialToolbar — the row above a collection (gh#1438, gh#1439): an optional `summary`
76
+ * (result count as a polite live region + a short note), a `start` cluster (filters) and an `end`
77
+ * cluster (order `Select`, view switch, primary action), optionally over a hairline (`divider`).
78
+ * With a `summary` it is a listing row: one line whose summary shrinks, the
79
+ * `--editorial-toolbar-summary-*` spacing, never stacked. Without one it is a wrapping bar whose
80
+ * clusters stack when a theme sets `--editorial-toolbar-display: block`. Selects in `end` read the
81
+ * toolbar's control scale (`--editorial-toolbar-control-*`).
82
+ */
83
+ export type EditorialToolbarProp = {
84
+ /** The listing summary: `count` ("396 results", announced politely) and a `note` under it. */
85
+ summary?: {
86
+ count?: ReactNode;
87
+ note?: ReactNode;
88
+ };
89
+ /** Start cluster — filters. */
90
+ start?: ReactNode;
91
+ /** End cluster — the order `Select`, a view switch, the primary action. */
92
+ end?: ReactNode;
93
+ /** A hairline under the row (`--editorial-toolbar-divider-padding-block-end` above it). */
94
+ divider?: boolean;
95
+ className?: ClassNameProp;
96
+ };
97
+ /** `grid` = tiles; `list` = the same cards as wide rows. */
98
+ export type HoldingViewProp = "grid" | "list";
99
+ /** @see HoldingGrid — the track of HoldingCards in grid or list view. */
100
+ export type HoldingGridProp = {
101
+ view?: HoldingViewProp;
102
+ /** Accessible name of the list. */
103
+ "aria-label"?: string;
104
+ children?: ReactNode;
105
+ className?: ClassNameProp;
106
+ };
107
+ /**
108
+ * @see HoldingCard — one owned item: a picture ground (the consumer's link around an image), then
109
+ * overline, title, meta, tags, the purchase line, a date and actions. Its geometry follows the
110
+ * enclosing HoldingGrid's view.
111
+ */
112
+ export type HoldingCardProp = {
113
+ /** The picture ground: a link (router Link or `<a>`) whose child is the image. */
114
+ media: ReactNode;
115
+ /** Small line above the title (kind, badges). */
116
+ overline?: ReactNode;
117
+ title: ReactNode;
118
+ /** Heading level of the title. Default `2`. */
119
+ level?: 2 | 3;
120
+ meta?: ReactNode;
121
+ /** Outlined tags (condition, grade, quantity); the last one is set apart. */
122
+ tags?: ReactNode[];
123
+ /** The owner's purchase line: a label and a figure. */
124
+ purchase?: {
125
+ label: ReactNode;
126
+ value: ReactNode;
127
+ };
128
+ /** A date line ("Purchased: 2026-10-01"). */
129
+ date?: ReactNode;
130
+ /** HoldingCardAction elements. */
131
+ actions?: ReactNode;
132
+ className?: ClassNameProp;
133
+ };
134
+ /**
135
+ * @see HoldingCardAction — a quiet glyph + label action of a HoldingCard (edit, remove). A
136
+ * `<button>` by default; `asChild` turns the consumer's link into the action.
137
+ */
138
+ export type HoldingCardActionProp = {
139
+ icon?: ReactNode;
140
+ children?: ReactNode;
141
+ asChild?: boolean;
142
+ onClick?: () => void;
143
+ disabled?: boolean;
144
+ "aria-label"?: string;
145
+ className?: ClassNameProp;
146
+ };
147
+ /**
148
+ * @see SettingsLayout — a settings page: a sticky rail (`aside`) beside the panels. The rail hides
149
+ * on narrow screens through tokens.
150
+ */
151
+ export type SettingsLayoutProp = {
152
+ aside?: ReactNode;
153
+ children?: ReactNode;
154
+ className?: ClassNameProp;
155
+ };
156
+ /**
157
+ * @see SettingsPanel — one bordered settings section: a number and a title with a description,
158
+ * then its fields.
159
+ */
160
+ export type SettingsPanelProp = {
161
+ /** The section number ("01"), set in the figure face. */
162
+ number?: ReactNode;
163
+ title: ReactNode;
164
+ /** Heading level of the title. Default `2`. */
165
+ level?: 2 | 3;
166
+ description?: ReactNode;
167
+ children?: ReactNode;
168
+ /** id of the title, so a group inside can be named by it. */
169
+ titleId?: string;
170
+ className?: ClassNameProp;
171
+ };
172
+ /** A painted preview of the interface in a ThemePicker choice. */
173
+ export type ThemePickerPreviewProp = "light" | "dark" | "system";
174
+ /** One choice of a ThemePicker. */
175
+ export type ThemePickerOptionProp = {
176
+ value: string;
177
+ label: string;
178
+ icon?: ReactNode;
179
+ preview: ThemePickerPreviewProp;
180
+ };
181
+ /**
182
+ * @see ThemePicker — an illustrated radio group for the colour theme: each choice is a painted
183
+ * preview of the interface (light / dark / split system) with a glyph and its label.
184
+ */
185
+ export type ThemePickerProp = {
186
+ /** Accessible name of the radio group (a visually hidden legend). */
187
+ legend: string;
188
+ options: ThemePickerOptionProp[];
189
+ value?: string;
190
+ defaultValue?: string;
191
+ onValueChange?: (value: string) => void;
192
+ /** Name of the radio inputs. */
193
+ name?: string;
194
+ className?: ClassNameProp;
195
+ };
196
+ /**
197
+ * @see EditorialAuth — a sign-in / sign-up page: a story column (kicker, display title, copy,
198
+ * decorative art, benefits) beside the form card (`children`).
199
+ */
200
+ export type EditorialAuthProp = {
201
+ eyebrow?: ReactNode;
202
+ title: ReactNode;
203
+ description?: ReactNode;
204
+ /** The picture on the front card of the decorative card pair (e.g. the brand mark). */
205
+ art?: ReactNode;
206
+ /** Short benefit lines, each led by a check glyph. */
207
+ benefits?: ReactNode[];
208
+ children?: ReactNode;
209
+ className?: ClassNameProp;
210
+ };
211
+ /**
212
+ * @see EditorialAuthCard — the form card of EditorialAuth: badge, title, copy, the form
213
+ * (`children`) and a ruled footer line ("New here? Create an account").
214
+ */
215
+ export type EditorialAuthCardProp = {
216
+ badge?: ReactNode;
217
+ title: ReactNode;
218
+ /** Heading level of the title. Default `2`. */
219
+ level?: 2 | 3;
220
+ description?: ReactNode;
221
+ children?: ReactNode;
222
+ footer?: ReactNode;
223
+ className?: ClassNameProp;
224
+ };
225
+ /**
226
+ * @see EditorialTextButton — an underlined text action in the primary tone ("Reset display
227
+ * preferences", "Your collection →"). A `<button>` by default; `asChild` turns the consumer's link
228
+ * into it. `icon` trails the label.
229
+ */
230
+ export type EditorialTextButtonProp = {
231
+ children?: ReactNode;
232
+ icon?: ReactNode;
233
+ asChild?: boolean;
234
+ onClick?: () => void;
235
+ disabled?: boolean;
236
+ className?: ClassNameProp;
237
+ };
238
+ /**
239
+ * @see EditorialFootnote — a quiet closing line under a collection or a settings form: a note at the
240
+ * start and an optional action (an EditorialTextButton) at the end. Geometry:
241
+ * `--editorial-footnote-*`.
242
+ */
243
+ export type EditorialFootnoteProp = {
244
+ children?: ReactNode;
245
+ action?: ReactNode;
246
+ /** Cross-axis alignment of note and action: `start` (default, a multi-line note) or `center`. */
247
+ align?: "start" | "center";
248
+ className?: ClassNameProp;
249
+ };
@@ -29,8 +29,12 @@ export type TextProp = Omit<React.HTMLAttributes<HTMLElement>, "color"> & Omit<T
29
29
  * so in a table cell it cannot wrap and cannot share the cell's line height.
30
30
  */
31
31
  link?: boolean;
32
- /** Size from the type scale — never an arbitrary px. Default `sm` (base). */
33
- size?: TextSizeProp;
32
+ /**
33
+ * Size from the type scale — never an arbitrary px. Default `sm` (base). `"inherit"` (gh#1434)
34
+ * takes the parent's size, leading and tracking: an emphasised run INSIDE a `Heading` (a hero's
35
+ * second line in the brand tone) keeps the heading's step at every breakpoint.
36
+ */
37
+ size?: TextSizeProp | "inherit";
34
38
  /** Semantic colour intent. Default `default` (foreground). */
35
39
  tone?: TextToneProp;
36
40
  /** Weight (system 2-weight: 400/500). Default `regular`. */