@cloudgrid-io/ui 0.15.0 → 0.17.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.
@@ -32,6 +32,79 @@
32
32
  * identity card is `aria-hidden` whenever a title sits beside it, because
33
33
  * announcing a decorative preview after the title reads the card twice.
34
34
  *
35
+ * ## The kind badge says WHAT the thing is
36
+ *
37
+ * `kind` is agent, inspiration or app, and it paints a circular badge on the
38
+ * preview's top-right corner — and beside the title when there is no preview to
39
+ * put it on. Founder request 2026-09-08 (#165): the console once carried it, a
40
+ * build dropped it, and every thumbnail had been showing the same badge
41
+ * regardless of what the entity was.
42
+ *
43
+ * Three deliberate choices in it.
44
+ *
45
+ * The glyphs come from `@/registry/ui/icons` under CloudGrid names, so the marks
46
+ * can be swapped for the founder's Figma set without touching this file or any
47
+ * consumer. `ENTITY_KIND_ICON` and `ENTITY_KIND_LABEL` are the whole mapping and
48
+ * nothing else here branches on a kind, the same arrangement `EntityStatus` uses
49
+ * for its ten statuses.
50
+ *
51
+ * The badge does NOT flip per surface, which is the identity tile's rule applied
52
+ * to a mark. Its ground is `--cg-surface-raised` and its glyph is
53
+ * `--cg-text-on-accent`, both declared at `:root` only, so a light disc with an
54
+ * ink glyph is what renders on white, on the purple panel and on ink alike. The
55
+ * alternative — a badge painted with `--cg-surface-card` and `--cg-text-primary`
56
+ * — inverts to white-on-white the moment the card sits inside
57
+ * `data-cg-surface="ink"`, because half of what it reads flips and the picture
58
+ * under it does not. Its hairline is mixed from `--cg-ink` for the same reason:
59
+ * `--cg-border-hairline` is a white wash on both dark surfaces and would leave
60
+ * the badge with no edge at all.
61
+ *
62
+ * The kind is announced. The glyph is `aria-hidden` and the word rides along in
63
+ * an `sr-only` span, because "agent" is information and a decorative mark is not
64
+ * a way to convey it.
65
+ *
66
+ * ## The hover reveal, and the rule it supersedes
67
+ *
68
+ * `reveal` puts a panel over the preview carrying the title, one line of
69
+ * description, the creator, the status and two real links: Open and Settings.
70
+ * It shows on hover and on `:focus-within`, and it respects
71
+ * `prefers-reduced-motion` by arriving without the fade rather than not at all.
72
+ *
73
+ * **This supersedes the "cards are visually static" rule of the console's
74
+ * 2026-08-16 card spec, for the media variant only.** Founder direction
75
+ * 2026-09-08 (#165). The rest of that rule stands and is unchanged: no lift, no
76
+ * shadow, no scale, no colour change on the card itself, on either variant. What
77
+ * moves is a panel that was always there, not the card.
78
+ *
79
+ * Four things about it that are not obvious:
80
+ *
81
+ * **A revealed card is not a whole-card link.** `href` still names where the
82
+ * entity lives, but with `reveal` set it is spent on the panel's Open action
83
+ * instead of on a wrapper, because an `<a>` inside an `<a>` is invalid HTML and
84
+ * browsers repair it by closing the outer one — which silently unlinks the card
85
+ * and leaves the actions where the parser decides to put them. The panel is the
86
+ * link surface instead: Open stretches across the whole panel with an
87
+ * `::after`, so a click anywhere on the thumbnail opens the entity, and Settings
88
+ * sits above it. Every existing caller is unaffected — `reveal` defaults off and
89
+ * the wrapper behaves exactly as it did.
90
+ *
91
+ * **The panel stays clickable while it is invisible.** `opacity-0` is a paint
92
+ * state, not a pointer state, so a touch user with no hover at all still gets
93
+ * Open by tapping the thumbnail. Gating pointer events on hover would make the
94
+ * card do nothing on a phone.
95
+ *
96
+ * **It is an ink surface, declared.** The panel carries
97
+ * `data-cg-surface="ink"`, so the status chip, the hairlines and the two links
98
+ * inside it resolve to their on-dark values without this file knowing what any
99
+ * of them are. It also declares `text-ink` itself, because text is the one thing
100
+ * that does not flip by inheritance.
101
+ *
102
+ * **The radii cannot disagree.** The preview carries `rounded-t-xl` — the same
103
+ * `--cg-radius-xl` the card rounds to — and the panel is `inset-0` inside it
104
+ * with no radius of its own, so there is no inner corner to mismatch when the
105
+ * panel appears. An e2e assertion compares the two computed radii rather than
106
+ * trusting that.
107
+ *
35
108
  * ## Status is a slot
36
109
  *
37
110
  * `status` takes a node, not a status name. `EntityStatus` is a separate
@@ -44,8 +117,8 @@
44
117
  *
45
118
  * The chrome flips: ground, hairlines, title, body text and the stat rule all
46
119
  * come from tokens, so `data-cg-surface="panel"` on any ancestor moves them
47
- * together. The identity tile deliberately does not flip — see its own note; it
48
- * is a picture, and a picture does not flip.
120
+ * together. The identity tile and the kind badge deliberately do not flip — see
121
+ * their notes; they are pictures, and a picture does not flip.
49
122
  */
50
123
  export interface EntityCardStat {
51
124
  /**
@@ -57,7 +130,45 @@ export interface EntityCardStat {
57
130
  /** Names the stat, e.g. "Views". Rendered for assistive tech. */
58
131
  label: string;
59
132
  }
60
- declare function EntityCard({ title, slug, description, titleLines, descriptionLines, status, stats, seed, previewUrl, href, ariaLabel, meta, footer, className, children, ...props }: Omit<React.ComponentProps<"div">, "ref" | "title"> & {
133
+ /**
134
+ * What an entity IS. Three kinds, and they are the product's, not this file's:
135
+ * an agent, an inspiration someone can pick up, and a runnable app.
136
+ *
137
+ * The array is the source and the type is derived from it, the arrangement
138
+ * `ENTITY_STATUS_ORDER` uses: a kind added here is immediately missing from both
139
+ * tables below and typecheck says so, so a half-added kind cannot ship.
140
+ */
141
+ export declare const ENTITY_KIND_ORDER: readonly ["agent", "inspiration", "app"];
142
+ export type EntityKind = (typeof ENTITY_KIND_ORDER)[number];
143
+ /**
144
+ * THE MARKS. Edit this to change what a kind looks like.
145
+ *
146
+ * Every entry points at a name from `@/registry/ui/icons` rather than at a
147
+ * lucide import, which is what makes the founder's Figma marks a one-file swap
148
+ * over there instead of an edit here and in every consumer.
149
+ */
150
+ export declare const ENTITY_KIND_ICON: Record<EntityKind, React.ComponentType<{
151
+ className?: string;
152
+ }>>;
153
+ /**
154
+ * THE WORDS. What a screen reader hears where a sighted reader sees the mark.
155
+ *
156
+ * Plain nouns, no adjective: this names a thing, it does not sell it.
157
+ */
158
+ export declare const ENTITY_KIND_LABEL: Record<EntityKind, string>;
159
+ /**
160
+ * The kind badge on its own, exported because a listing header, a detail page or
161
+ * a row may want the same mark without a card around it.
162
+ *
163
+ * `size` is the only variant: `md` is the 28px disc that sits on a preview,
164
+ * `sm` the 20px one that sits beside a title. Both render a 16px-class glyph,
165
+ * which is what the marks were picked to survive.
166
+ */
167
+ declare function EntityKindBadge({ kind, size, className, ...props }: Omit<React.ComponentProps<"span">, "children"> & {
168
+ kind: EntityKind;
169
+ size?: "sm" | "md";
170
+ }): import("react").JSX.Element;
171
+ declare function EntityCard({ title, slug, description, titleLines, descriptionLines, status, stats, seed, previewUrl, kind, reveal, settingsHref, creator, href, ariaLabel, meta, footer, className, children, ...props }: Omit<React.ComponentProps<"div">, "ref" | "title"> & {
61
172
  title: string;
62
173
  /** The entity's address, in the mono utility face. */
63
174
  slug?: string;
@@ -74,6 +185,30 @@ declare function EntityCard({ title, slug, description, titleLines, descriptionL
74
185
  seed?: string;
75
186
  /** A real capture, painted over the identity tile. A miss falls back to it. */
76
187
  previewUrl?: string;
188
+ /**
189
+ * What the entity IS. Paints the badge on the preview's top-right corner, or
190
+ * beside the title when there is no preview.
191
+ */
192
+ kind?: EntityKind;
193
+ /**
194
+ * Turns the hover reveal on. Needs `seed`, since the panel covers the preview.
195
+ *
196
+ * Off by default, and it changes what `href` does: a revealed card is NOT
197
+ * wrapped in a whole-card link, because the panel's own actions are anchors
198
+ * and an anchor inside an anchor is invalid HTML. See the note above.
199
+ */
200
+ reveal?: boolean;
201
+ /** The Settings action's target. Only read when `reveal` is on. */
202
+ settingsHref?: string;
203
+ /**
204
+ * Who made it, shown on the reveal panel. `avatar` is a node so a consumer can
205
+ * pass its own image, initials tile or `EntityIdentity`; this card does not
206
+ * fetch one and does not know where an avatar lives.
207
+ */
208
+ creator?: {
209
+ name: string;
210
+ avatar?: React.ReactNode;
211
+ };
77
212
  /** When set, the whole card is the target. A plain anchor: routing is yours. */
78
213
  href?: string;
79
214
  /** Accessible name for the whole-card link. Defaults to `title`. */
@@ -85,5 +220,5 @@ declare function EntityCard({ title, slug, description, titleLines, descriptionL
85
220
  /** Replaces the whole body. The preview and the card chrome still render. */
86
221
  children?: React.ReactNode;
87
222
  }): import("react").JSX.Element;
88
- export { EntityCard };
223
+ export { EntityCard, EntityKindBadge };
89
224
  //# sourceMappingURL=entity-card.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"entity-card.d.ts","sourceRoot":"","sources":["../../src/blocks/entity-card.tsx"],"names":[],"mappings":"AAIA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GAgDG;AAEH,MAAM,WAAW,cAAc;IAC7B;;;OAGG;IACH,IAAI,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;IACtB,KAAK,EAAE,KAAK,CAAC,SAAS,CAAA;IACtB,iEAAiE;IACjE,KAAK,EAAE,MAAM,CAAA;CACd;AAED,iBAAS,UAAU,CAAC,EAClB,KAAK,EACL,IAAI,EACJ,WAAW,EACX,UAAc,EACd,gBAAoB,EACpB,MAAM,EACN,KAAK,EACL,IAAI,EACJ,UAAU,EACV,IAAI,EACJ,SAAS,EACT,IAAI,EACJ,MAAM,EACN,SAAS,EACT,QAAQ,EACR,GAAG,KAAK,EACT,EAAE,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,KAAK,CAAC,EAAE,KAAK,GAAG,OAAO,CAAC,GAAG;IACtD,KAAK,EAAE,MAAM,CAAA;IACb,sDAAsD;IACtD,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,UAAU,CAAC,EAAE,CAAC,GAAG,CAAC,CAAA;IAClB,gBAAgB,CAAC,EAAE,CAAC,GAAG,CAAC,CAAA;IACxB,8DAA8D;IAC9D,MAAM,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;IACxB,KAAK,CAAC,EAAE,cAAc,EAAE,CAAA;IACxB;;;OAGG;IACH,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,+EAA+E;IAC/E,UAAU,CAAC,EAAE,MAAM,CAAA;IACnB,gFAAgF;IAChF,IAAI,CAAC,EAAE,MAAM,CAAA;IACb,oEAAoE;IACpE,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,uFAAuF;IACvF,IAAI,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;IACtB,kDAAkD;IAClD,MAAM,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;IACxB,6EAA6E;IAC7E,QAAQ,CAAC,EAAE,KAAK,CAAC,SAAS,CAAA;CAC3B,+BAwIA;AAED,OAAO,EAAE,UAAU,EAAE,CAAA"}
1
+ {"version":3,"file":"entity-card.d.ts","sourceRoot":"","sources":["../../src/blocks/entity-card.tsx"],"names":[],"mappings":"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"}
@@ -1,10 +1,68 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
2
  import { Card } from "../ui/card.js";
3
3
  import { EntityIdentity } from "./entity-identity.js";
4
+ import { KindAgentIcon, KindAppIcon, KindInspirationIcon, OpenLiveIcon, SettingsIcon, } from "./icons.js";
4
5
  import { cn } from "../lib/cloudgrid-cn.js";
5
- function EntityCard({ title, slug, description, titleLines = 2, descriptionLines = 1, status, stats, seed, previewUrl, href, ariaLabel, meta, footer, className, children, ...props }) {
6
+ /**
7
+ * What an entity IS. Three kinds, and they are the product's, not this file's:
8
+ * an agent, an inspiration someone can pick up, and a runnable app.
9
+ *
10
+ * The array is the source and the type is derived from it, the arrangement
11
+ * `ENTITY_STATUS_ORDER` uses: a kind added here is immediately missing from both
12
+ * tables below and typecheck says so, so a half-added kind cannot ship.
13
+ */
14
+ export const ENTITY_KIND_ORDER = ["agent", "inspiration", "app"];
15
+ /**
16
+ * THE MARKS. Edit this to change what a kind looks like.
17
+ *
18
+ * Every entry points at a name from `@/registry/ui/icons` rather than at a
19
+ * lucide import, which is what makes the founder's Figma marks a one-file swap
20
+ * over there instead of an edit here and in every consumer.
21
+ */
22
+ export const ENTITY_KIND_ICON = {
23
+ agent: KindAgentIcon,
24
+ inspiration: KindInspirationIcon,
25
+ app: KindAppIcon,
26
+ };
27
+ /**
28
+ * THE WORDS. What a screen reader hears where a sighted reader sees the mark.
29
+ *
30
+ * Plain nouns, no adjective: this names a thing, it does not sell it.
31
+ */
32
+ export const ENTITY_KIND_LABEL = {
33
+ agent: "Agent",
34
+ inspiration: "Inspiration",
35
+ app: "App",
36
+ };
37
+ /**
38
+ * The kind badge on its own, exported because a listing header, a detail page or
39
+ * a row may want the same mark without a card around it.
40
+ *
41
+ * `size` is the only variant: `md` is the 28px disc that sits on a preview,
42
+ * `sm` the 20px one that sits beside a title. Both render a 16px-class glyph,
43
+ * which is what the marks were picked to survive.
44
+ */
45
+ function EntityKindBadge({ kind, size = "md", className, ...props }) {
46
+ const Icon = ENTITY_KIND_ICON[kind];
47
+ return (_jsxs("span", { "data-slot": "entity-card-kind", "data-kind": kind, className: cn("inline-flex shrink-0 items-center justify-center rounded-pill bg-raised text-on-accent", size === "md" ? "size-7" : "size-5", className), style: {
48
+ // Mixed from --cg-ink rather than taken from --cg-border-hairline, and
49
+ // for the same reason the ground and the glyph are pinned: the hairline
50
+ // is a white wash on both dark surfaces, so a badge inside
51
+ // data-cg-surface="ink" would lose its edge while the disc under it
52
+ // stayed light. The mesh in EntityIdentity mixes its own line the same
53
+ // way, at 8%.
54
+ border: "1px solid color-mix(in srgb, var(--cg-ink) 12%, transparent)",
55
+ }, ...props, children: [_jsx(Icon, { className: size === "md" ? "size-4" : "size-3.5" }), _jsx("span", { className: "sr-only", children: ENTITY_KIND_LABEL[kind] })] }));
56
+ }
57
+ function EntityCard({ title, slug, description, titleLines = 2, descriptionLines = 1, status, stats, seed, previewUrl, kind, reveal = false, settingsHref, creator, href, ariaLabel, meta, footer, className, children, ...props }) {
58
+ // The reveal owns the preview and spends the `href`, so it only exists when
59
+ // both are there. Asked for without a `seed` it would be a panel over nothing;
60
+ // asked for without an `href` its Open action would be an anchor with no
61
+ // target, which renders as a link, is not focusable, and does nothing when
62
+ // clicked. Silently off in both cases rather than half-built.
63
+ const revealed = reveal && Boolean(seed) && Boolean(href);
6
64
  const body = children ??
7
- (_jsxs(_Fragment, { children: [_jsxs("div", { className: "flex items-start justify-between gap-3", children: [_jsxs("div", { className: "min-w-0 flex-1", children: [_jsx("span", { dir: "auto", "data-slot": "entity-card-title", title: title, className: cn("block text-body-sm font-medium break-words text-ink", titleLines === 1 ? "truncate" : "line-clamp-2"), children: title }), slug ? (_jsx("span", { dir: "auto", "data-slot": "entity-card-slug", title: slug, className: "mt-0.5 block truncate font-mono text-caption text-faint", children: slug })) : null] }), status ? _jsx("div", { className: "shrink-0", children: status }) : null] }), description ? (_jsx("p", { dir: "auto", "data-slot": "entity-card-description", title: description, className: cn("m-0 text-body-sm text-body", descriptionLines === 1 ? "truncate" : "line-clamp-2"), children: description })) : null, meta, _jsx("div", { "aria-hidden": "true", className: "grow" }), stats && stats.length > 0 ? (_jsx("div", { "data-slot": "entity-card-stats", className: "flex flex-wrap items-center gap-4 border-t border-hairline pt-3 text-caption text-body", children: stats.map((stat) => (_jsxs("span", { className: "inline-flex items-center gap-1.5", children: [stat.icon ? (_jsx("span", { "aria-hidden": "true", className: "inline-flex [&>svg]:size-4", children: stat.icon })) : null, stat.value, _jsx("span", { className: "sr-only", children: stat.label })] }, stat.label))) })) : null, footer] }));
65
+ (_jsxs(_Fragment, { children: [_jsxs("div", { className: "flex items-start justify-between gap-3", children: [_jsxs("div", { className: "min-w-0 flex-1", children: [_jsxs("span", { dir: "auto", "data-slot": "entity-card-title", title: title, className: cn("block text-body-sm font-medium break-words text-ink", titleLines === 1 ? "truncate" : "line-clamp-2"), children: [kind && !seed ? (_jsx(EntityKindBadge, { kind: kind, size: "sm", className: "mr-1.5 align-[-0.2em]" })) : null, title] }), slug ? (_jsx("span", { dir: "auto", "data-slot": "entity-card-slug", title: slug, className: "mt-0.5 block truncate font-mono text-caption text-faint", children: slug })) : null] }), status ? _jsx("div", { className: "shrink-0", children: status }) : null] }), description ? (_jsx("p", { dir: "auto", "data-slot": "entity-card-description", title: description, className: cn("m-0 text-body-sm text-body", descriptionLines === 1 ? "truncate" : "line-clamp-2"), children: description })) : null, meta, _jsx("div", { "aria-hidden": "true", className: "grow" }), stats && stats.length > 0 ? (_jsx("div", { "data-slot": "entity-card-stats", className: "flex flex-wrap items-center gap-4 border-t border-hairline pt-3 text-caption text-body", children: stats.map((stat) => (_jsxs("span", { className: "inline-flex items-center gap-1.5", children: [stat.icon ? (_jsx("span", { "aria-hidden": "true", className: "inline-flex [&>svg]:size-4", children: stat.icon })) : null, stat.value, _jsx("span", { className: "sr-only", children: stat.label })] }, stat.label))) })) : null, footer] }));
8
66
  const card = (_jsxs(Card, { "data-slot": "entity-card",
9
67
  // gap-0 py-0: `Card` pads itself for a header/content/footer stack, and
10
68
  // this card's preview is full bleed to the top edge. The padding moves
@@ -12,18 +70,53 @@ function EntityCard({ title, slug, description, titleLines = 2, descriptionLines
12
70
  // No hover lift, shadow, scale or colour change, even when the whole card
13
71
  // is a link. That is the console's founder card spec (2026-08-16) carried
14
72
  // across rather than re-decided here, and it matches this system's own
15
- // canon: containment is a hairline, not elevation.
73
+ // canon: containment is a hairline, not elevation. The reveal panel is
74
+ // this rule's one exception, and only on the media variant: see the note
75
+ // at the top of this file.
16
76
  // `h-full` only inside the link wrapper, where the card has to fill the
17
77
  // anchor. As a direct grid item it must NOT be h-full: a grid area has a
18
78
  // definite height, so height:100% pins the card to the tallest card in the
19
79
  // row even when the grid was told `items-start`.
20
- className: cn("gap-0 py-0", href && "h-full", className), ...props, children: [seed ? (_jsxs("div", { "data-slot": "entity-card-preview", className: "relative shrink-0 border-b border-hairline", children: [_jsx(EntityIdentity, { seed: seed, name: title }), previewUrl ? (_jsx("div", { "data-slot": "entity-card-capture", "aria-hidden": "true", className: "absolute inset-0 bg-cover bg-center",
80
+ className: cn("gap-0 py-0", href && !revealed && "h-full", className), ...props, children: [seed ? (_jsxs("div", { "data-slot": "entity-card-preview",
81
+ // rounded-t-xl is the same --cg-radius-xl the card rounds to, and
82
+ // overflow-hidden is what keeps the reveal panel inside it. The card
83
+ // already clips; stating it here means the panel can never paint a
84
+ // corner the card does not have.
85
+ className: "relative shrink-0 overflow-hidden rounded-t-xl border-b border-hairline", children: [_jsx(EntityIdentity, { seed: seed, name: title }), previewUrl ? (_jsx("div", { "data-slot": "entity-card-capture", "aria-hidden": "true", className: "absolute inset-0 bg-cover bg-center",
21
86
  // A background image, not an <img>: a URL that 404s paints
22
87
  // nothing and the identity tile below shows through, with no
23
88
  // state and no client boundary. encodeURI escapes the quote that
24
89
  // would otherwise break out of url("...").
25
- style: { backgroundImage: `url("${encodeURI(previewUrl)}")` } })) : null] })) : null, _jsx("div", { className: "flex min-h-0 flex-1 flex-col gap-3 p-(--card-spacing)", children: body })] }));
26
- if (!href)
90
+ style: { backgroundImage: `url("${encodeURI(previewUrl)}")` } })) : null, revealed ? (_jsxs("div", { "data-slot": "entity-card-reveal", "data-cg-surface": "ink", className: cn("absolute inset-0 flex flex-col justify-end gap-1.5 bg-scrim-strong p-3 text-ink",
91
+ // opacity-0, not hidden: the panel is in the tab order at all
92
+ // times, so tabbing into Open is what reveals it, and a touch
93
+ // user with no hover still has a live tap target.
94
+ "opacity-0 transition-opacity duration-[var(--cg-duration)] ease-out", "group-hover/card:opacity-100 group-focus-within/card:opacity-100",
95
+ // Reduced motion removes the FADE, not the panel. Someone who
96
+ // has asked for less movement still needs the actions.
97
+ "motion-reduce:transition-none"), children: [_jsx("span", { "data-slot": "entity-card-reveal-title", dir: "auto", className: "truncate text-body-sm font-medium", children: title }), description ? (_jsx("p", { "data-slot": "entity-card-reveal-description", dir: "auto",
98
+ // text-body, never text-faint. The secondary measures 6.18:1
99
+ // on this scrim and the guardrail holds it there; the muted
100
+ // rung measures 4.06:1, under AA, and is deliberately outside
101
+ // that assertion because it is documented as non-essential
102
+ // text. So there is no muted tier available on this panel.
103
+ className: "m-0 truncate text-caption text-body", children: description })) : null, creator || status ? (_jsxs("div", { className: "flex min-w-0 items-center justify-between gap-2", children: [creator ? (_jsxs("span", { "data-slot": "entity-card-reveal-creator", className: "flex min-w-0 items-center gap-1.5 text-caption text-body", children: [creator.avatar ? (_jsx("span", { "aria-hidden": "true", className: "inline-flex size-4 shrink-0 overflow-hidden rounded-pill [&>*]:size-full", children: creator.avatar })) : null, _jsx("span", { className: "truncate", children: creator.name })] })) : (_jsx("span", {})), status ? _jsx("span", { className: "shrink-0", children: status }) : null] })) : null, _jsxs("div", { className: "flex items-center gap-2 pt-0.5", children: [_jsxs("a", { href: href, "data-slot": "entity-card-open",
104
+ // after:inset-0 makes this link the whole panel, so a click
105
+ // anywhere on the thumbnail opens the entity. The anchor
106
+ // itself must NOT be positioned or the stretched layer sizes
107
+ // to the anchor instead of to the panel — the panel is already
108
+ // absolute, so it is the containing block. Settings comes
109
+ // later in the DOM and IS positioned, so it stacks above the
110
+ // stretched layer rather than under it.
111
+ className: "inline-flex items-center gap-1 rounded-pill border border-hairline px-2 py-1 text-caption no-underline after:absolute after:inset-0 after:content-[''] focus-visible:ring-3 focus-visible:ring-ring focus-visible:outline-none", children: [_jsx(OpenLiveIcon, { className: "size-3.5" }), "Open"] }), settingsHref ? (_jsxs("a", { href: settingsHref, "data-slot": "entity-card-settings",
112
+ // relative, and that is load-bearing: it lifts this link
113
+ // above Open's stretched ::after, which otherwise covers the
114
+ // whole panel and would swallow every click meant for here.
115
+ className: "relative inline-flex items-center gap-1 rounded-pill border border-hairline px-2 py-1 text-caption no-underline focus-visible:ring-3 focus-visible:ring-ring focus-visible:outline-none", children: [_jsx(SettingsIcon, { className: "size-3.5" }), "Settings"] })) : null] })] })) : null, kind ? (_jsx(EntityKindBadge, { kind: kind, className: "pointer-events-none absolute top-2 right-2" })) : null] })) : null, _jsx("div", { className: "flex min-h-0 flex-1 flex-col gap-3 p-(--card-spacing)", children: body })] }));
116
+ // A revealed card is never wrapped: the panel's Open action is already an
117
+ // anchor, and an anchor inside an anchor is invalid HTML that browsers repair
118
+ // by closing the outer one.
119
+ if (!href || revealed)
27
120
  return card;
28
121
  return (_jsx("a", { href: href, "aria-label": ariaLabel ?? title,
29
122
  // The focus ring is the same token every control uses, so it flips with
@@ -31,5 +124,5 @@ function EntityCard({ title, slug, description, titleLines = 2, descriptionLines
31
124
  // by keyboard, and that failure never shows up in a screenshot.
32
125
  className: "group block rounded-xl no-underline focus-visible:ring-3 focus-visible:ring-ring focus-visible:outline-none", children: card }));
33
126
  }
34
- export { EntityCard };
127
+ export { EntityCard, EntityKindBadge };
35
128
  //# sourceMappingURL=entity-card.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"entity-card.js","sourceRoot":"","sources":["../../src/blocks/entity-card.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"entity-card.js","sourceRoot":"","sources":["../../src/blocks/entity-card.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,104 @@
1
+ /**
2
+ * The curated icon surface: every glyph a CloudGrid surface is allowed to reach
3
+ * for, under a CloudGrid name.
4
+ *
5
+ * ## Why the library owns the names
6
+ *
7
+ * Before this, a consumer that wanted the "open it live" arrow imported an icon
8
+ * from whatever family was nearest. That is a second design system entering the
9
+ * app through the side door: nothing stops two surfaces picking two different
10
+ * arrows for the same idea, nothing records which glyph means what, and swapping
11
+ * a family later means editing every call site in every repo. This repo's own
12
+ * gallery was doing it, for nine glyphs.
13
+ *
14
+ * So the rule is the one the colour layer already has: a consumer names the
15
+ * ROLE, the library decides what it looks like.
16
+ *
17
+ * ## Phosphor, because that is what the designs are drawn with
18
+ *
19
+ * Founder confirmed 2026-09-08: Phosphor (phosphoricons.com) is CloudGrid's icon
20
+ * library, and #167 is the standing rule — Phosphor is the ONLY one. The marks
21
+ * below are Phosphor's, inlined by `scripts/generate-phosphor-marks.mjs` into
22
+ * `blocks/phosphor-marks.tsx` and re-exported here under role names.
23
+ *
24
+ * This module is #167's first slice. lucide is still imported by fourteen
25
+ * components in this package and by the gallery; removing it there, and gating
26
+ * against its return, is that issue's remaining work and deliberately not this
27
+ * file's.
28
+ *
29
+ * This module shipped its first draft as lucide re-exports, which was wrong for
30
+ * the reason `phosphor-marks.tsx` already had written down: the Figma frames
31
+ * name Phosphor glyphs directly, so a lucide equivalent is an approximation of
32
+ * one the designer actually picked. `Bot`, `Sparkles` and `AppWindow` were
33
+ * approximations of `robot`, `lightbulb` and `app-window`.
34
+ *
35
+ * ## THE SWAP POINT
36
+ *
37
+ * Changing what a role looks like is **one slug in `ICON_MARKS`** in
38
+ * `scripts/generate-phosphor-marks.mjs`, followed by
39
+ * `node scripts/generate-phosphor-marks.mjs`. Nothing here changes, nothing in
40
+ * `EntityCard` changes, and no consumer changes a line — the names below are the
41
+ * contract and the glyphs are not.
42
+ *
43
+ * That is also why this file re-exports rather than telling consumers to import
44
+ * the `*Mark` names themselves. A rename at the call site is a rename that then
45
+ * has to happen in every repo at once.
46
+ *
47
+ * ## Re-exports, not wrappers
48
+ *
49
+ * A wrapper would let this file pin a size, and it would also add a component
50
+ * layer between a caller and a mark for nothing: the marks already take
51
+ * `className` and nothing else, already carry `aria-hidden` themselves, and
52
+ * already paint `currentColor`. Sizing is the caller's, through `size-4` and
53
+ * friends, which is how every existing component in this library sizes a glyph.
54
+ *
55
+ * **Every call site must size the mark.** A Phosphor mark carries a `viewBox`
56
+ * and no width or height, so an unsized one falls back to the SVG default box
57
+ * rather than to something plausible.
58
+ *
59
+ * ## No icon package reaches a consumer
60
+ *
61
+ * `@phosphor-icons/core` is a devDependency and ships raw SVG with no React. The
62
+ * path data is read at generation time and inlined, so `shadcn add
63
+ * @cloudgrid/icons` installs no icon dependency at all — the property
64
+ * `tool-marks.tsx` and `phosphor-marks.tsx` already have.
65
+ *
66
+ * ## The picks, and why each survives 16px inside a circle
67
+ *
68
+ * The kind marks render at 16px inside a 28px badge on an entity card, so a
69
+ * glyph with fine interior detail turns to mush there. Each was chosen against
70
+ * that constraint rather than in a 24px rail.
71
+ *
72
+ * KindAgentIcon Phosphor `robot`. A head, two eyes, an antenna: heavy
73
+ * shapes, no interior hairlines. The same mark the
74
+ * onboarding build question already uses for "AI apps",
75
+ * shared rather than inlined twice.
76
+ * KindInspirationIcon Phosphor `lightbulb`. Continuity, not invention: it is
77
+ * the badge the console shows for an inspiration today,
78
+ * so nothing a user already recognises changes meaning.
79
+ * KindAppIcon Phosphor `app-window`. A window with a title bar: a
80
+ * thing that runs and has a screen, which separates it
81
+ * from the agent (no screen) and the inspiration (not
82
+ * running yet).
83
+ * OpenLiveIcon Phosphor `arrow-up-right`. Named by the issue. One
84
+ * stroke, and it means "leaves this surface" everywhere.
85
+ * SettingsIcon Phosphor `gear-six`. The six-tooth gear, which is
86
+ * Phosphor's own settings mark and reads cleaner at 14px
87
+ * than the eight-tooth `gear` the build question uses.
88
+ * ViewsIcon Phosphor `eye`, for a count in a card's stat row.
89
+ * CommentsIcon Phosphor `chat-circle`, for the count beside it.
90
+ *
91
+ * No comments inside the export block below, deliberately. The barrel's
92
+ * collision test reads exported names with a regex that splits the braces on
93
+ * commas, so a sentence in there is parsed as an export name.
94
+ */
95
+ export { RobotMark as KindAgentIcon, LightbulbMark as KindInspirationIcon, AppWindowMark as KindAppIcon, ArrowUpRightMark as OpenLiveIcon, GearSixMark as SettingsIcon, EyeMark as ViewsIcon, ChatCircleMark as CommentsIcon, } from "./phosphor-marks.js";
96
+ /**
97
+ * The props every icon above takes, and all it takes.
98
+ *
99
+ * Re-exported from the generated module rather than restated here as
100
+ * `{ className?: string }`, so the two cannot drift apart when the mark
101
+ * signature changes.
102
+ */
103
+ export type { PhosphorMarkProps as CloudGridIconProps } from "./phosphor-marks.js";
104
+ //# sourceMappingURL=icons.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"icons.d.ts","sourceRoot":"","sources":["../../src/blocks/icons.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6FG;AAEH,OAAO,EACL,SAAS,IAAI,aAAa,EAC1B,aAAa,IAAI,mBAAmB,EACpC,aAAa,IAAI,WAAW,EAC5B,gBAAgB,IAAI,YAAY,EAChC,WAAW,IAAI,YAAY,EAC3B,OAAO,IAAI,SAAS,EACpB,cAAc,IAAI,YAAY,GAC/B,MAAM,8BAA8B,CAAA;AAErC;;;;;;GAMG;AACH,YAAY,EAAE,iBAAiB,IAAI,kBAAkB,EAAE,MAAM,8BAA8B,CAAA"}
@@ -0,0 +1,96 @@
1
+ /**
2
+ * The curated icon surface: every glyph a CloudGrid surface is allowed to reach
3
+ * for, under a CloudGrid name.
4
+ *
5
+ * ## Why the library owns the names
6
+ *
7
+ * Before this, a consumer that wanted the "open it live" arrow imported an icon
8
+ * from whatever family was nearest. That is a second design system entering the
9
+ * app through the side door: nothing stops two surfaces picking two different
10
+ * arrows for the same idea, nothing records which glyph means what, and swapping
11
+ * a family later means editing every call site in every repo. This repo's own
12
+ * gallery was doing it, for nine glyphs.
13
+ *
14
+ * So the rule is the one the colour layer already has: a consumer names the
15
+ * ROLE, the library decides what it looks like.
16
+ *
17
+ * ## Phosphor, because that is what the designs are drawn with
18
+ *
19
+ * Founder confirmed 2026-09-08: Phosphor (phosphoricons.com) is CloudGrid's icon
20
+ * library, and #167 is the standing rule — Phosphor is the ONLY one. The marks
21
+ * below are Phosphor's, inlined by `scripts/generate-phosphor-marks.mjs` into
22
+ * `blocks/phosphor-marks.tsx` and re-exported here under role names.
23
+ *
24
+ * This module is #167's first slice. lucide is still imported by fourteen
25
+ * components in this package and by the gallery; removing it there, and gating
26
+ * against its return, is that issue's remaining work and deliberately not this
27
+ * file's.
28
+ *
29
+ * This module shipped its first draft as lucide re-exports, which was wrong for
30
+ * the reason `phosphor-marks.tsx` already had written down: the Figma frames
31
+ * name Phosphor glyphs directly, so a lucide equivalent is an approximation of
32
+ * one the designer actually picked. `Bot`, `Sparkles` and `AppWindow` were
33
+ * approximations of `robot`, `lightbulb` and `app-window`.
34
+ *
35
+ * ## THE SWAP POINT
36
+ *
37
+ * Changing what a role looks like is **one slug in `ICON_MARKS`** in
38
+ * `scripts/generate-phosphor-marks.mjs`, followed by
39
+ * `node scripts/generate-phosphor-marks.mjs`. Nothing here changes, nothing in
40
+ * `EntityCard` changes, and no consumer changes a line — the names below are the
41
+ * contract and the glyphs are not.
42
+ *
43
+ * That is also why this file re-exports rather than telling consumers to import
44
+ * the `*Mark` names themselves. A rename at the call site is a rename that then
45
+ * has to happen in every repo at once.
46
+ *
47
+ * ## Re-exports, not wrappers
48
+ *
49
+ * A wrapper would let this file pin a size, and it would also add a component
50
+ * layer between a caller and a mark for nothing: the marks already take
51
+ * `className` and nothing else, already carry `aria-hidden` themselves, and
52
+ * already paint `currentColor`. Sizing is the caller's, through `size-4` and
53
+ * friends, which is how every existing component in this library sizes a glyph.
54
+ *
55
+ * **Every call site must size the mark.** A Phosphor mark carries a `viewBox`
56
+ * and no width or height, so an unsized one falls back to the SVG default box
57
+ * rather than to something plausible.
58
+ *
59
+ * ## No icon package reaches a consumer
60
+ *
61
+ * `@phosphor-icons/core` is a devDependency and ships raw SVG with no React. The
62
+ * path data is read at generation time and inlined, so `shadcn add
63
+ * @cloudgrid/icons` installs no icon dependency at all — the property
64
+ * `tool-marks.tsx` and `phosphor-marks.tsx` already have.
65
+ *
66
+ * ## The picks, and why each survives 16px inside a circle
67
+ *
68
+ * The kind marks render at 16px inside a 28px badge on an entity card, so a
69
+ * glyph with fine interior detail turns to mush there. Each was chosen against
70
+ * that constraint rather than in a 24px rail.
71
+ *
72
+ * KindAgentIcon Phosphor `robot`. A head, two eyes, an antenna: heavy
73
+ * shapes, no interior hairlines. The same mark the
74
+ * onboarding build question already uses for "AI apps",
75
+ * shared rather than inlined twice.
76
+ * KindInspirationIcon Phosphor `lightbulb`. Continuity, not invention: it is
77
+ * the badge the console shows for an inspiration today,
78
+ * so nothing a user already recognises changes meaning.
79
+ * KindAppIcon Phosphor `app-window`. A window with a title bar: a
80
+ * thing that runs and has a screen, which separates it
81
+ * from the agent (no screen) and the inspiration (not
82
+ * running yet).
83
+ * OpenLiveIcon Phosphor `arrow-up-right`. Named by the issue. One
84
+ * stroke, and it means "leaves this surface" everywhere.
85
+ * SettingsIcon Phosphor `gear-six`. The six-tooth gear, which is
86
+ * Phosphor's own settings mark and reads cleaner at 14px
87
+ * than the eight-tooth `gear` the build question uses.
88
+ * ViewsIcon Phosphor `eye`, for a count in a card's stat row.
89
+ * CommentsIcon Phosphor `chat-circle`, for the count beside it.
90
+ *
91
+ * No comments inside the export block below, deliberately. The barrel's
92
+ * collision test reads exported names with a regex that splits the braces on
93
+ * commas, so a sentence in there is parsed as an export name.
94
+ */
95
+ export { RobotMark as KindAgentIcon, LightbulbMark as KindInspirationIcon, AppWindowMark as KindAppIcon, ArrowUpRightMark as OpenLiveIcon, GearSixMark as SettingsIcon, EyeMark as ViewsIcon, ChatCircleMark as CommentsIcon, } from "./phosphor-marks.js";
96
+ //# sourceMappingURL=icons.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"icons.js","sourceRoot":"","sources":["../../src/blocks/icons.tsx"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;GA6FG;AAEH,OAAO,EACL,SAAS,IAAI,aAAa,EAC1B,aAAa,IAAI,mBAAmB,EACpC,aAAa,IAAI,WAAW,EAC5B,gBAAgB,IAAI,YAAY,EAChC,WAAW,IAAI,YAAY,EAC3B,OAAO,IAAI,SAAS,EACpB,cAAc,IAAI,YAAY,GAC/B,MAAM,8BAA8B,CAAA"}
@@ -1,58 +1,80 @@
1
1
  import * as React from "react";
2
- type MarkProps = {
2
+ /**
3
+ * What every mark in this file takes, and all it takes.
4
+ *
5
+ * Exported so a module that re-exports these under other names can re-export the
6
+ * TYPE too rather than restating `{ className?: string }` and letting the two
7
+ * drift. `blocks/icons.tsx` does exactly that, as `CloudGridIconProps`.
8
+ *
9
+ * Sizing is the caller's, through `size-4` and friends. A mark carries no
10
+ * width or height of its own, so an unsized one falls back to the SVG default
11
+ * box rather than to something plausible — size it at every call site.
12
+ */
13
+ export type PhosphorMarkProps = {
3
14
  className?: string;
4
15
  };
5
16
  /** A friend. Phosphor `user`. */
6
- export declare const UserMark: ({ className }: MarkProps) => React.JSX.Element;
17
+ export declare const UserMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
7
18
  /** X. Phosphor `x-logo`. */
8
- export declare const XLogoMark: ({ className }: MarkProps) => React.JSX.Element;
19
+ export declare const XLogoMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
9
20
  /** LinkedIn. Phosphor `linkedin-logo`. */
10
- export declare const LinkedinLogoMark: ({ className }: MarkProps) => React.JSX.Element;
21
+ export declare const LinkedinLogoMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
11
22
  /** YouTube. Phosphor `youtube-logo`. */
12
- export declare const YoutubeLogoMark: ({ className }: MarkProps) => React.JSX.Element;
23
+ export declare const YoutubeLogoMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
13
24
  /** A podcast. Phosphor `apple-podcasts-logo`. */
14
- export declare const ApplePodcastsLogoMark: ({ className }: MarkProps) => React.JSX.Element;
25
+ export declare const ApplePodcastsLogoMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
15
26
  /** Google Search. Phosphor `google-logo`. */
16
- export declare const GoogleLogoMark: ({ className }: MarkProps) => React.JSX.Element;
27
+ export declare const GoogleLogoMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
17
28
  /** My AI tool said so. Phosphor `star-four`. */
18
- export declare const StarFourMark: ({ className }: MarkProps) => React.JSX.Element;
29
+ export declare const StarFourMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
19
30
  /** Somewhere else. Phosphor `dots-three-outline`. */
20
- export declare const DotsThreeOutlineMark: ({ className }: MarkProps) => React.JSX.Element;
31
+ export declare const DotsThreeOutlineMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
21
32
  /** Dashboards. Phosphor `chart-pie-slice`. */
22
- export declare const ChartPieSliceMark: ({ className }: MarkProps) => React.JSX.Element;
33
+ export declare const ChartPieSliceMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
23
34
  /** Web apps. Phosphor `browsers`. */
24
- export declare const BrowsersMark: ({ className }: MarkProps) => React.JSX.Element;
35
+ export declare const BrowsersMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
25
36
  /** Sites and landing pages. Phosphor `devices`. */
26
- export declare const DevicesMark: ({ className }: MarkProps) => React.JSX.Element;
37
+ export declare const DevicesMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
27
38
  /** Games. Phosphor `ghost`. */
28
- export declare const GhostMark: ({ className }: MarkProps) => React.JSX.Element;
39
+ export declare const GhostMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
29
40
  /** Internal tools. Phosphor `code-block`. */
30
- export declare const CodeBlockMark: ({ className }: MarkProps) => React.JSX.Element;
41
+ export declare const CodeBlockMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
31
42
  /** APIs and backends. Phosphor `database`. */
32
- export declare const DatabaseMark: ({ className }: MarkProps) => React.JSX.Element;
43
+ export declare const DatabaseMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
33
44
  /** Automations. Phosphor `gear`. */
34
- export declare const GearMark: ({ className }: MarkProps) => React.JSX.Element;
45
+ export declare const GearMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
35
46
  /** AI apps. Phosphor `robot`. */
36
- export declare const RobotMark: ({ className }: MarkProps) => React.JSX.Element;
47
+ export declare const RobotMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
48
+ /** An inspiration. Phosphor `lightbulb`. */
49
+ export declare const LightbulbMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
50
+ /** A runnable app. Phosphor `app-window`. */
51
+ export declare const AppWindowMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
52
+ /** Open it live. Phosphor `arrow-up-right`. */
53
+ export declare const ArrowUpRightMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
54
+ /** Settings. Phosphor `gear-six`. */
55
+ export declare const GearSixMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
56
+ /** Views. Phosphor `eye`. */
57
+ export declare const EyeMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
58
+ /** Comments. Phosphor `chat-circle`. */
59
+ export declare const ChatCircleMark: ({ className }: PhosphorMarkProps) => React.JSX.Element;
37
60
  /** Keyed by the label a caller shows, the same shape as TOOL_MARKS. */
38
61
  export declare const PHOSPHOR_MARKS: {
39
- readonly "A friend": ({ className }: MarkProps) => React.JSX.Element;
40
- readonly X: ({ className }: MarkProps) => React.JSX.Element;
41
- readonly LinkedIn: ({ className }: MarkProps) => React.JSX.Element;
42
- readonly YouTube: ({ className }: MarkProps) => React.JSX.Element;
43
- readonly "A podcast": ({ className }: MarkProps) => React.JSX.Element;
44
- readonly "Google Search": ({ className }: MarkProps) => React.JSX.Element;
45
- readonly "My AI tool said so": ({ className }: MarkProps) => React.JSX.Element;
46
- readonly "Somewhere else": ({ className }: MarkProps) => React.JSX.Element;
47
- readonly Dashboards: ({ className }: MarkProps) => React.JSX.Element;
48
- readonly "Web apps": ({ className }: MarkProps) => React.JSX.Element;
49
- readonly "Sites and landing pages": ({ className }: MarkProps) => React.JSX.Element;
50
- readonly Games: ({ className }: MarkProps) => React.JSX.Element;
51
- readonly "Internal tools": ({ className }: MarkProps) => React.JSX.Element;
52
- readonly "APIs and backends": ({ className }: MarkProps) => React.JSX.Element;
53
- readonly Automations: ({ className }: MarkProps) => React.JSX.Element;
54
- readonly "AI apps": ({ className }: MarkProps) => React.JSX.Element;
62
+ readonly "A friend": ({ className }: PhosphorMarkProps) => React.JSX.Element;
63
+ readonly X: ({ className }: PhosphorMarkProps) => React.JSX.Element;
64
+ readonly LinkedIn: ({ className }: PhosphorMarkProps) => React.JSX.Element;
65
+ readonly YouTube: ({ className }: PhosphorMarkProps) => React.JSX.Element;
66
+ readonly "A podcast": ({ className }: PhosphorMarkProps) => React.JSX.Element;
67
+ readonly "Google Search": ({ className }: PhosphorMarkProps) => React.JSX.Element;
68
+ readonly "My AI tool said so": ({ className }: PhosphorMarkProps) => React.JSX.Element;
69
+ readonly "Somewhere else": ({ className }: PhosphorMarkProps) => React.JSX.Element;
70
+ readonly Dashboards: ({ className }: PhosphorMarkProps) => React.JSX.Element;
71
+ readonly "Web apps": ({ className }: PhosphorMarkProps) => React.JSX.Element;
72
+ readonly "Sites and landing pages": ({ className }: PhosphorMarkProps) => React.JSX.Element;
73
+ readonly Games: ({ className }: PhosphorMarkProps) => React.JSX.Element;
74
+ readonly "Internal tools": ({ className }: PhosphorMarkProps) => React.JSX.Element;
75
+ readonly "APIs and backends": ({ className }: PhosphorMarkProps) => React.JSX.Element;
76
+ readonly Automations: ({ className }: PhosphorMarkProps) => React.JSX.Element;
77
+ readonly "AI apps": ({ className }: PhosphorMarkProps) => React.JSX.Element;
55
78
  };
56
79
  export type PhosphorMarkName = keyof typeof PHOSPHOR_MARKS;
57
- export {};
58
80
  //# sourceMappingURL=phosphor-marks.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"phosphor-marks.d.ts","sourceRoot":"","sources":["../../src/blocks/phosphor-marks.tsx"],"names":[],"mappings":"AAoCA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAA;AAE9B,KAAK,SAAS,GAAG;IAAE,SAAS,CAAC,EAAE,MAAM,CAAA;CAAE,CAAA;AAevC,iCAAiC;AACjC,eAAO,MAAM,QAAQ,kBAZiB,SAAS,sBAc5C,CAAA;AAEH,4BAA4B;AAC5B,eAAO,MAAM,SAAS,kBAjBgB,SAAS,sBAmB5C,CAAA;AAEH,0CAA0C;AAC1C,eAAO,MAAM,gBAAgB,kBAtBS,SAAS,sBAwB5C,CAAA;AAEH,wCAAwC;AACxC,eAAO,MAAM,eAAe,kBA3BU,SAAS,sBA6B5C,CAAA;AAEH,iDAAiD;AACjD,eAAO,MAAM,qBAAqB,kBAhCI,SAAS,sBAkC5C,CAAA;AAEH,6CAA6C;AAC7C,eAAO,MAAM,cAAc,kBArCW,SAAS,sBAuC5C,CAAA;AAEH,gDAAgD;AAChD,eAAO,MAAM,YAAY,kBA1Ca,SAAS,sBA4C5C,CAAA;AAEH,qDAAqD;AACrD,eAAO,MAAM,oBAAoB,kBA/CK,SAAS,sBAiD5C,CAAA;AAEH,8CAA8C;AAC9C,eAAO,MAAM,iBAAiB,kBApDQ,SAAS,sBAsD5C,CAAA;AAEH,qCAAqC;AACrC,eAAO,MAAM,YAAY,kBAzDa,SAAS,sBA2D5C,CAAA;AAEH,mDAAmD;AACnD,eAAO,MAAM,WAAW,kBA9Dc,SAAS,sBAgE5C,CAAA;AAEH,+BAA+B;AAC/B,eAAO,MAAM,SAAS,kBAnEgB,SAAS,sBAqE5C,CAAA;AAEH,6CAA6C;AAC7C,eAAO,MAAM,aAAa,kBAxEY,SAAS,sBA0E5C,CAAA;AAEH,8CAA8C;AAC9C,eAAO,MAAM,YAAY,kBA7Ea,SAAS,sBA+E5C,CAAA;AAEH,oCAAoC;AACpC,eAAO,MAAM,QAAQ,kBAlFiB,SAAS,sBAoF5C,CAAA;AAEH,iCAAiC;AACjC,eAAO,MAAM,SAAS,kBAvFgB,SAAS,sBAyF5C,CAAA;AAEH,uEAAuE;AACvE,eAAO,MAAM,cAAc;yCA5FW,SAAS;gCAAT,SAAS;uCAAT,SAAS;sCAAT,SAAS;0CAAT,SAAS;8CAAT,SAAS;mDAAT,SAAS;+CAAT,SAAS;yCAAT,SAAS;yCAAT,SAAS;wDAAT,SAAS;oCAAT,SAAS;+CAAT,SAAS;kDAAT,SAAS;0CAAT,SAAS;wCAAT,SAAS;CA6GrC,CAAA;AAEV,MAAM,MAAM,gBAAgB,GAAG,MAAM,OAAO,cAAc,CAAA"}
1
+ {"version":3,"file":"phosphor-marks.d.ts","sourceRoot":"","sources":["../../src/blocks/phosphor-marks.tsx"],"names":[],"mappings":"AAoCA,OAAO,KAAK,KAAK,MAAM,OAAO,CAAA;AAE9B;;;;;;;;;;GAUG;AACH,MAAM,MAAM,iBAAiB,GAAG;IAAE,SAAS,CAAC,EAAE,MAAM,CAAA;CAAE,CAAA;AAetD,iCAAiC;AACjC,eAAO,MAAM,QAAQ,kBAZiB,iBAAiB,sBAcpD,CAAA;AAEH,4BAA4B;AAC5B,eAAO,MAAM,SAAS,kBAjBgB,iBAAiB,sBAmBpD,CAAA;AAEH,0CAA0C;AAC1C,eAAO,MAAM,gBAAgB,kBAtBS,iBAAiB,sBAwBpD,CAAA;AAEH,wCAAwC;AACxC,eAAO,MAAM,eAAe,kBA3BU,iBAAiB,sBA6BpD,CAAA;AAEH,iDAAiD;AACjD,eAAO,MAAM,qBAAqB,kBAhCI,iBAAiB,sBAkCpD,CAAA;AAEH,6CAA6C;AAC7C,eAAO,MAAM,cAAc,kBArCW,iBAAiB,sBAuCpD,CAAA;AAEH,gDAAgD;AAChD,eAAO,MAAM,YAAY,kBA1Ca,iBAAiB,sBA4CpD,CAAA;AAEH,qDAAqD;AACrD,eAAO,MAAM,oBAAoB,kBA/CK,iBAAiB,sBAiDpD,CAAA;AAEH,8CAA8C;AAC9C,eAAO,MAAM,iBAAiB,kBApDQ,iBAAiB,sBAsDpD,CAAA;AAEH,qCAAqC;AACrC,eAAO,MAAM,YAAY,kBAzDa,iBAAiB,sBA2DpD,CAAA;AAEH,mDAAmD;AACnD,eAAO,MAAM,WAAW,kBA9Dc,iBAAiB,sBAgEpD,CAAA;AAEH,+BAA+B;AAC/B,eAAO,MAAM,SAAS,kBAnEgB,iBAAiB,sBAqEpD,CAAA;AAEH,6CAA6C;AAC7C,eAAO,MAAM,aAAa,kBAxEY,iBAAiB,sBA0EpD,CAAA;AAEH,8CAA8C;AAC9C,eAAO,MAAM,YAAY,kBA7Ea,iBAAiB,sBA+EpD,CAAA;AAEH,oCAAoC;AACpC,eAAO,MAAM,QAAQ,kBAlFiB,iBAAiB,sBAoFpD,CAAA;AAEH,iCAAiC;AACjC,eAAO,MAAM,SAAS,kBAvFgB,iBAAiB,sBAyFpD,CAAA;AAUH,4CAA4C;AAC5C,eAAO,MAAM,aAAa,kBApGY,iBAAiB,sBAsGpD,CAAA;AAEH,6CAA6C;AAC7C,eAAO,MAAM,aAAa,kBAzGY,iBAAiB,sBA2GpD,CAAA;AAEH,+CAA+C;AAC/C,eAAO,MAAM,gBAAgB,kBA9GS,iBAAiB,sBAgHpD,CAAA;AAEH,qCAAqC;AACrC,eAAO,MAAM,WAAW,kBAnHc,iBAAiB,sBAqHpD,CAAA;AAEH,6BAA6B;AAC7B,eAAO,MAAM,OAAO,kBAxHkB,iBAAiB,sBA0HpD,CAAA;AAEH,wCAAwC;AACxC,eAAO,MAAM,cAAc,kBA7HW,iBAAiB,sBA+HpD,CAAA;AAEH,uEAAuE;AACvE,eAAO,MAAM,cAAc;yCAlIW,iBAAiB;gCAAjB,iBAAiB;uCAAjB,iBAAiB;sCAAjB,iBAAiB;0CAAjB,iBAAiB;8CAAjB,iBAAiB;mDAAjB,iBAAiB;+CAAjB,iBAAiB;yCAAjB,iBAAiB;yCAAjB,iBAAiB;wDAAjB,iBAAiB;oCAAjB,iBAAiB;+CAAjB,iBAAiB;kDAAjB,iBAAiB;0CAAjB,iBAAiB;wCAAjB,iBAAiB;CAmJ7C,CAAA;AAEV,MAAM,MAAM,gBAAgB,GAAG,MAAM,OAAO,cAAc,CAAA"}
@@ -73,6 +73,25 @@ export const DatabaseMark = mark("M128,24C74.17,24,32,48.6,32,80v96c0,31.4,42.17
73
73
  export const GearMark = mark("M128,80a48,48,0,1,0,48,48A48.05,48.05,0,0,0,128,80Zm0,80a32,32,0,1,1,32-32A32,32,0,0,1,128,160Zm88-29.84q.06-2.16,0-4.32l14.92-18.64a8,8,0,0,0,1.48-7.06,107.21,107.21,0,0,0-10.88-26.25,8,8,0,0,0-6-3.93l-23.72-2.64q-1.48-1.56-3-3L186,40.54a8,8,0,0,0-3.94-6,107.71,107.71,0,0,0-26.25-10.87,8,8,0,0,0-7.06,1.49L130.16,40Q128,40,125.84,40L107.2,25.11a8,8,0,0,0-7.06-1.48A107.6,107.6,0,0,0,73.89,34.51a8,8,0,0,0-3.93,6L67.32,64.27q-1.56,1.49-3,3L40.54,70a8,8,0,0,0-6,3.94,107.71,107.71,0,0,0-10.87,26.25,8,8,0,0,0,1.49,7.06L40,125.84Q40,128,40,130.16L25.11,148.8a8,8,0,0,0-1.48,7.06,107.21,107.21,0,0,0,10.88,26.25,8,8,0,0,0,6,3.93l23.72,2.64q1.49,1.56,3,3L70,215.46a8,8,0,0,0,3.94,6,107.71,107.71,0,0,0,26.25,10.87,8,8,0,0,0,7.06-1.49L125.84,216q2.16.06,4.32,0l18.64,14.92a8,8,0,0,0,7.06,1.48,107.21,107.21,0,0,0,26.25-10.88,8,8,0,0,0,3.93-6l2.64-23.72q1.56-1.48,3-3L215.46,186a8,8,0,0,0,6-3.94,107.71,107.71,0,0,0,10.87-26.25,8,8,0,0,0-1.49-7.06Zm-16.1-6.5a73.93,73.93,0,0,1,0,8.68,8,8,0,0,0,1.74,5.48l14.19,17.73a91.57,91.57,0,0,1-6.23,15L187,173.11a8,8,0,0,0-5.1,2.64,74.11,74.11,0,0,1-6.14,6.14,8,8,0,0,0-2.64,5.1l-2.51,22.58a91.32,91.32,0,0,1-15,6.23l-17.74-14.19a8,8,0,0,0-5-1.75h-.48a73.93,73.93,0,0,1-8.68,0,8,8,0,0,0-5.48,1.74L100.45,215.8a91.57,91.57,0,0,1-15-6.23L82.89,187a8,8,0,0,0-2.64-5.1,74.11,74.11,0,0,1-6.14-6.14,8,8,0,0,0-5.1-2.64L46.43,170.6a91.32,91.32,0,0,1-6.23-15l14.19-17.74a8,8,0,0,0,1.74-5.48,73.93,73.93,0,0,1,0-8.68,8,8,0,0,0-1.74-5.48L40.2,100.45a91.57,91.57,0,0,1,6.23-15L69,82.89a8,8,0,0,0,5.1-2.64,74.11,74.11,0,0,1,6.14-6.14A8,8,0,0,0,82.89,69L85.4,46.43a91.32,91.32,0,0,1,15-6.23l17.74,14.19a8,8,0,0,0,5.48,1.74,73.93,73.93,0,0,1,8.68,0,8,8,0,0,0,5.48-1.74L155.55,40.2a91.57,91.57,0,0,1,15,6.23L173.11,69a8,8,0,0,0,2.64,5.1,74.11,74.11,0,0,1,6.14,6.14,8,8,0,0,0,5.1,2.64l22.58,2.51a91.32,91.32,0,0,1,6.23,15l-14.19,17.74A8,8,0,0,0,199.87,123.66Z");
74
74
  /** AI apps. Phosphor `robot`. */
75
75
  export const RobotMark = mark("M200,48H136V16a8,8,0,0,0-16,0V48H56A32,32,0,0,0,24,80V192a32,32,0,0,0,32,32H200a32,32,0,0,0,32-32V80A32,32,0,0,0,200,48Zm16,144a16,16,0,0,1-16,16H56a16,16,0,0,1-16-16V80A16,16,0,0,1,56,64H200a16,16,0,0,1,16,16Zm-52-56H92a28,28,0,0,0,0,56h72a28,28,0,0,0,0-56Zm-24,16v24H116V152ZM80,164a12,12,0,0,1,12-12h8v24H92A12,12,0,0,1,80,164Zm84,12h-8V152h8a12,12,0,0,1,0,24ZM72,108a12,12,0,1,1,12,12A12,12,0,0,1,72,108Zm88,0a12,12,0,1,1,12,12A12,12,0,0,1,160,108Z");
76
+ // ---- The curated icon surface's marks (#165) -------------------------------
77
+ //
78
+ // Components only. They are deliberately absent from PHOSPHOR_MARKS below,
79
+ // which is keyed by the label an onboarding QUESTION shows; see ICON_MARKS in
80
+ // the generator for why the two sets stay apart. blocks/icons.tsx re-exports
81
+ // these under stable CloudGrid names, and RobotMark above serves as the agent
82
+ // mark rather than being inlined a second time.
83
+ /** An inspiration. Phosphor `lightbulb`. */
84
+ export const LightbulbMark = mark("M176,232a8,8,0,0,1-8,8H88a8,8,0,0,1,0-16h80A8,8,0,0,1,176,232Zm40-128a87.55,87.55,0,0,1-33.64,69.21A16.24,16.24,0,0,0,176,186v6a16,16,0,0,1-16,16H96a16,16,0,0,1-16-16v-6a16,16,0,0,0-6.23-12.66A87.59,87.59,0,0,1,40,104.49C39.74,56.83,78.26,17.14,125.88,16A88,88,0,0,1,216,104Zm-16,0a72,72,0,0,0-73.74-72c-39,.92-70.47,33.39-70.26,72.39a71.65,71.65,0,0,0,27.64,56.3A32,32,0,0,1,96,186v6h64v-6a32.15,32.15,0,0,1,12.47-25.35A71.65,71.65,0,0,0,200,104Zm-16.11-9.34a57.6,57.6,0,0,0-46.56-46.55,8,8,0,0,0-2.66,15.78c16.57,2.79,30.63,16.85,33.44,33.45A8,8,0,0,0,176,104a9,9,0,0,0,1.35-.11A8,8,0,0,0,183.89,94.66Z");
85
+ /** A runnable app. Phosphor `app-window`. */
86
+ export const AppWindowMark = mark("M216,40H40A16,16,0,0,0,24,56V200a16,16,0,0,0,16,16H216a16,16,0,0,0,16-16V56A16,16,0,0,0,216,40Zm0,160H40V56H216V200ZM80,84A12,12,0,1,1,68,72,12,12,0,0,1,80,84Zm40,0a12,12,0,1,1-12-12A12,12,0,0,1,120,84Z");
87
+ /** Open it live. Phosphor `arrow-up-right`. */
88
+ export const ArrowUpRightMark = mark("M200,64V168a8,8,0,0,1-16,0V83.31L69.66,197.66a8,8,0,0,1-11.32-11.32L172.69,72H88a8,8,0,0,1,0-16H192A8,8,0,0,1,200,64Z");
89
+ /** Settings. Phosphor `gear-six`. */
90
+ export const GearSixMark = mark("M128,80a48,48,0,1,0,48,48A48.05,48.05,0,0,0,128,80Zm0,80a32,32,0,1,1,32-32A32,32,0,0,1,128,160Zm109.94-52.79a8,8,0,0,0-3.89-5.4l-29.83-17-.12-33.62a8,8,0,0,0-2.83-6.08,111.91,111.91,0,0,0-36.72-20.67,8,8,0,0,0-6.46.59L128,41.85,97.88,25a8,8,0,0,0-6.47-.6A112.1,112.1,0,0,0,54.73,45.15a8,8,0,0,0-2.83,6.07l-.15,33.65-29.83,17a8,8,0,0,0-3.89,5.4,106.47,106.47,0,0,0,0,41.56,8,8,0,0,0,3.89,5.4l29.83,17,.12,33.62a8,8,0,0,0,2.83,6.08,111.91,111.91,0,0,0,36.72,20.67,8,8,0,0,0,6.46-.59L128,214.15,158.12,231a7.91,7.91,0,0,0,3.9,1,8.09,8.09,0,0,0,2.57-.42,112.1,112.1,0,0,0,36.68-20.73,8,8,0,0,0,2.83-6.07l.15-33.65,29.83-17a8,8,0,0,0,3.89-5.4A106.47,106.47,0,0,0,237.94,107.21Zm-15,34.91-28.57,16.25a8,8,0,0,0-3,3c-.58,1-1.19,2.06-1.81,3.06a7.94,7.94,0,0,0-1.22,4.21l-.15,32.25a95.89,95.89,0,0,1-25.37,14.3L134,199.13a8,8,0,0,0-3.91-1h-.19c-1.21,0-2.43,0-3.64,0a8.08,8.08,0,0,0-4.1,1l-28.84,16.1A96,96,0,0,1,67.88,201l-.11-32.2a8,8,0,0,0-1.22-4.22c-.62-1-1.23-2-1.8-3.06a8.09,8.09,0,0,0-3-3.06l-28.6-16.29a90.49,90.49,0,0,1,0-28.26L61.67,97.63a8,8,0,0,0,3-3c.58-1,1.19-2.06,1.81-3.06a7.94,7.94,0,0,0,1.22-4.21l.15-32.25a95.89,95.89,0,0,1,25.37-14.3L122,56.87a8,8,0,0,0,4.1,1c1.21,0,2.43,0,3.64,0a8.08,8.08,0,0,0,4.1-1l28.84-16.1A96,96,0,0,1,188.12,55l.11,32.2a8,8,0,0,0,1.22,4.22c.62,1,1.23,2,1.8,3.06a8.09,8.09,0,0,0,3,3.06l28.6,16.29A90.49,90.49,0,0,1,222.9,142.12Z");
91
+ /** Views. Phosphor `eye`. */
92
+ export const EyeMark = mark("M247.31,124.76c-.35-.79-8.82-19.58-27.65-38.41C194.57,61.26,162.88,48,128,48S61.43,61.26,36.34,86.35C17.51,105.18,9,124,8.69,124.76a8,8,0,0,0,0,6.5c.35.79,8.82,19.57,27.65,38.4C61.43,194.74,93.12,208,128,208s66.57-13.26,91.66-38.34c18.83-18.83,27.3-37.61,27.65-38.4A8,8,0,0,0,247.31,124.76ZM128,192c-30.78,0-57.67-11.19-79.93-33.25A133.47,133.47,0,0,1,25,128,133.33,133.33,0,0,1,48.07,97.25C70.33,75.19,97.22,64,128,64s57.67,11.19,79.93,33.25A133.46,133.46,0,0,1,231.05,128C223.84,141.46,192.43,192,128,192Zm0-112a48,48,0,1,0,48,48A48.05,48.05,0,0,0,128,80Zm0,80a32,32,0,1,1,32-32A32,32,0,0,1,128,160Z");
93
+ /** Comments. Phosphor `chat-circle`. */
94
+ export const ChatCircleMark = mark("M128,24A104,104,0,0,0,36.18,176.88L24.83,210.93a16,16,0,0,0,20.24,20.24l34.05-11.35A104,104,0,1,0,128,24Zm0,192a87.87,87.87,0,0,1-44.06-11.81,8,8,0,0,0-6.54-.67L40,216,52.47,178.6a8,8,0,0,0-.66-6.54A88,88,0,1,1,128,216Z");
76
95
  /** Keyed by the label a caller shows, the same shape as TOOL_MARKS. */
77
96
  export const PHOSPHOR_MARKS = {
78
97
  "A friend": UserMark,
@@ -1 +1 @@
1
- {"version":3,"file":"phosphor-marks.js","sourceRoot":"","sources":["../../src/blocks/phosphor-marks.tsx"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"phosphor-marks.js","sourceRoot":"","sources":["../../src/blocks/phosphor-marks.tsx"],"names":[],"mappings":"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"}
package/dist/index.d.ts CHANGED
@@ -33,6 +33,7 @@ export * from "./blocks/entity-identity.js";
33
33
  export * from "./blocks/entity-status.js";
34
34
  export * from "./blocks/feature-cells.js";
35
35
  export * from "./blocks/hub-index.js";
36
+ export * from "./blocks/icons.js";
36
37
  export * from "./blocks/logo.js";
37
38
  export * from "./blocks/onboarding-question.js";
38
39
  export * from "./blocks/option-card.js";
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAiBA,cAAc,mBAAmB,CAAA;AACjC,cAAc,eAAe,CAAA;AAC7B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,cAAc,CAAA;AAC5B,cAAc,kBAAkB,CAAA;AAChC,cAAc,kBAAkB,CAAA;AAChC,cAAc,oBAAoB,CAAA;AAClC,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,uBAAuB,CAAA;AACrC,cAAc,qBAAqB,CAAA;AACnC,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,eAAe,CAAA;AAC7B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,mBAAmB,CAAA;AACjC,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,eAAe,CAAA;AAC7B,cAAc,cAAc,CAAA;AAC5B,cAAc,kBAAkB,CAAA;AAChC,cAAc,iBAAiB,CAAA;AAG/B,cAAc,0BAA0B,CAAA;AACxC,cAAc,uBAAuB,CAAA;AACrC,cAAc,yBAAyB,CAAA;AACvC,cAAc,2BAA2B,CAAA;AACzC,cAAc,2BAA2B,CAAA;AACzC,cAAc,wBAAwB,CAAA;AACtC,cAAc,uBAAuB,CAAA;AACrC,cAAc,yBAAyB,CAAA;AACvC,cAAc,6BAA6B,CAAA;AAC3C,cAAc,2BAA2B,CAAA;AACzC,cAAc,2BAA2B,CAAA;AACzC,cAAc,uBAAuB,CAAA;AACrC,cAAc,kBAAkB,CAAA;AAChC,cAAc,iCAAiC,CAAA;AAC/C,cAAc,yBAAyB,CAAA;AACvC,cAAc,0BAA0B,CAAA;AACxC,cAAc,4BAA4B,CAAA;AAC1C,cAAc,yBAAyB,CAAA;AACvC,cAAc,gCAAgC,CAAA;AAC9C,cAAc,2BAA2B,CAAA;AACzC,cAAc,mBAAmB,CAAA;AACjC,cAAc,uBAAuB,CAAA;AACrC,cAAc,6BAA6B,CAAA;AAC3C,cAAc,yBAAyB,CAAA;AACvC,cAAc,uBAAuB,CAAA;AACrC,cAAc,uBAAuB,CAAA;AACrC,cAAc,wBAAwB,CAAA;AACtC,cAAc,wBAAwB,CAAA;AAGtC,cAAc,uBAAuB,CAAA"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAiBA,cAAc,mBAAmB,CAAA;AACjC,cAAc,eAAe,CAAA;AAC7B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,cAAc,CAAA;AAC5B,cAAc,kBAAkB,CAAA;AAChC,cAAc,kBAAkB,CAAA;AAChC,cAAc,oBAAoB,CAAA;AAClC,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,uBAAuB,CAAA;AACrC,cAAc,qBAAqB,CAAA;AACnC,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,eAAe,CAAA;AAC7B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,mBAAmB,CAAA;AACjC,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,eAAe,CAAA;AAC7B,cAAc,cAAc,CAAA;AAC5B,cAAc,kBAAkB,CAAA;AAChC,cAAc,iBAAiB,CAAA;AAG/B,cAAc,0BAA0B,CAAA;AACxC,cAAc,uBAAuB,CAAA;AACrC,cAAc,yBAAyB,CAAA;AACvC,cAAc,2BAA2B,CAAA;AACzC,cAAc,2BAA2B,CAAA;AACzC,cAAc,wBAAwB,CAAA;AACtC,cAAc,uBAAuB,CAAA;AACrC,cAAc,yBAAyB,CAAA;AACvC,cAAc,6BAA6B,CAAA;AAC3C,cAAc,2BAA2B,CAAA;AACzC,cAAc,2BAA2B,CAAA;AACzC,cAAc,uBAAuB,CAAA;AACrC,cAAc,mBAAmB,CAAA;AACjC,cAAc,kBAAkB,CAAA;AAChC,cAAc,iCAAiC,CAAA;AAC/C,cAAc,yBAAyB,CAAA;AACvC,cAAc,0BAA0B,CAAA;AACxC,cAAc,4BAA4B,CAAA;AAC1C,cAAc,yBAAyB,CAAA;AACvC,cAAc,gCAAgC,CAAA;AAC9C,cAAc,2BAA2B,CAAA;AACzC,cAAc,mBAAmB,CAAA;AACjC,cAAc,uBAAuB,CAAA;AACrC,cAAc,6BAA6B,CAAA;AAC3C,cAAc,yBAAyB,CAAA;AACvC,cAAc,uBAAuB,CAAA;AACrC,cAAc,uBAAuB,CAAA;AACrC,cAAc,wBAAwB,CAAA;AACtC,cAAc,wBAAwB,CAAA;AAGtC,cAAc,uBAAuB,CAAA"}
package/dist/index.js CHANGED
@@ -50,6 +50,7 @@ export * from "./blocks/entity-identity.js";
50
50
  export * from "./blocks/entity-status.js";
51
51
  export * from "./blocks/feature-cells.js";
52
52
  export * from "./blocks/hub-index.js";
53
+ export * from "./blocks/icons.js";
53
54
  export * from "./blocks/logo.js";
54
55
  export * from "./blocks/onboarding-question.js";
55
56
  export * from "./blocks/option-card.js";
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,0CAA0C;AAC1C,EAAE;AACF,gFAAgF;AAChF,8EAA8E;AAC9E,oEAAoE;AACpE,EAAE;AACF,gFAAgF;AAChF,+EAA+E;AAC/E,yEAAyE;AACzE,gFAAgF;AAChF,4EAA4E;AAC5E,EAAE;AACF,kEAAkE;AAClE,8EAA8E;AAC9E,uEAAuE;AAEvE,cAAc;AACd,cAAc,mBAAmB,CAAA;AACjC,cAAc,eAAe,CAAA;AAC7B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,cAAc,CAAA;AAC5B,cAAc,kBAAkB,CAAA;AAChC,cAAc,kBAAkB,CAAA;AAChC,cAAc,oBAAoB,CAAA;AAClC,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,uBAAuB,CAAA;AACrC,cAAc,qBAAqB,CAAA;AACnC,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,eAAe,CAAA;AAC7B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,mBAAmB,CAAA;AACjC,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,eAAe,CAAA;AAC7B,cAAc,cAAc,CAAA;AAC5B,cAAc,kBAAkB,CAAA;AAChC,cAAc,iBAAiB,CAAA;AAE/B,mBAAmB;AACnB,cAAc,0BAA0B,CAAA;AACxC,cAAc,uBAAuB,CAAA;AACrC,cAAc,yBAAyB,CAAA;AACvC,cAAc,2BAA2B,CAAA;AACzC,cAAc,2BAA2B,CAAA;AACzC,cAAc,wBAAwB,CAAA;AACtC,cAAc,uBAAuB,CAAA;AACrC,cAAc,yBAAyB,CAAA;AACvC,cAAc,6BAA6B,CAAA;AAC3C,cAAc,2BAA2B,CAAA;AACzC,cAAc,2BAA2B,CAAA;AACzC,cAAc,uBAAuB,CAAA;AACrC,cAAc,kBAAkB,CAAA;AAChC,cAAc,iCAAiC,CAAA;AAC/C,cAAc,yBAAyB,CAAA;AACvC,cAAc,0BAA0B,CAAA;AACxC,cAAc,4BAA4B,CAAA;AAC1C,cAAc,yBAAyB,CAAA;AACvC,cAAc,gCAAgC,CAAA;AAC9C,cAAc,2BAA2B,CAAA;AACzC,cAAc,mBAAmB,CAAA;AACjC,cAAc,uBAAuB,CAAA;AACrC,cAAc,6BAA6B,CAAA;AAC3C,cAAc,yBAAyB,CAAA;AACvC,cAAc,uBAAuB,CAAA;AACrC,cAAc,uBAAuB,CAAA;AACrC,cAAc,wBAAwB,CAAA;AACtC,cAAc,wBAAwB,CAAA;AAEtC,0EAA0E;AAC1E,cAAc,uBAAuB,CAAA"}
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,0CAA0C;AAC1C,EAAE;AACF,gFAAgF;AAChF,8EAA8E;AAC9E,oEAAoE;AACpE,EAAE;AACF,gFAAgF;AAChF,+EAA+E;AAC/E,yEAAyE;AACzE,gFAAgF;AAChF,4EAA4E;AAC5E,EAAE;AACF,kEAAkE;AAClE,8EAA8E;AAC9E,uEAAuE;AAEvE,cAAc;AACd,cAAc,mBAAmB,CAAA;AACjC,cAAc,eAAe,CAAA;AAC7B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,cAAc,CAAA;AAC5B,cAAc,kBAAkB,CAAA;AAChC,cAAc,kBAAkB,CAAA;AAChC,cAAc,oBAAoB,CAAA;AAClC,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,uBAAuB,CAAA;AACrC,cAAc,qBAAqB,CAAA;AACnC,cAAc,eAAe,CAAA;AAC7B,cAAc,sBAAsB,CAAA;AACpC,cAAc,eAAe,CAAA;AAC7B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,mBAAmB,CAAA;AACjC,cAAc,kBAAkB,CAAA;AAChC,cAAc,gBAAgB,CAAA;AAC9B,cAAc,gBAAgB,CAAA;AAC9B,cAAc,eAAe,CAAA;AAC7B,cAAc,cAAc,CAAA;AAC5B,cAAc,kBAAkB,CAAA;AAChC,cAAc,iBAAiB,CAAA;AAE/B,mBAAmB;AACnB,cAAc,0BAA0B,CAAA;AACxC,cAAc,uBAAuB,CAAA;AACrC,cAAc,yBAAyB,CAAA;AACvC,cAAc,2BAA2B,CAAA;AACzC,cAAc,2BAA2B,CAAA;AACzC,cAAc,wBAAwB,CAAA;AACtC,cAAc,uBAAuB,CAAA;AACrC,cAAc,yBAAyB,CAAA;AACvC,cAAc,6BAA6B,CAAA;AAC3C,cAAc,2BAA2B,CAAA;AACzC,cAAc,2BAA2B,CAAA;AACzC,cAAc,uBAAuB,CAAA;AACrC,cAAc,mBAAmB,CAAA;AACjC,cAAc,kBAAkB,CAAA;AAChC,cAAc,iCAAiC,CAAA;AAC/C,cAAc,yBAAyB,CAAA;AACvC,cAAc,0BAA0B,CAAA;AACxC,cAAc,4BAA4B,CAAA;AAC1C,cAAc,yBAAyB,CAAA;AACvC,cAAc,gCAAgC,CAAA;AAC9C,cAAc,2BAA2B,CAAA;AACzC,cAAc,mBAAmB,CAAA;AACjC,cAAc,uBAAuB,CAAA;AACrC,cAAc,6BAA6B,CAAA;AAC3C,cAAc,yBAAyB,CAAA;AACvC,cAAc,uBAAuB,CAAA;AACrC,cAAc,uBAAuB,CAAA;AACrC,cAAc,wBAAwB,CAAA;AACtC,cAAc,wBAAwB,CAAA;AAEtC,0EAA0E;AAC1E,cAAc,uBAAuB,CAAA"}
package/dist/theme.css CHANGED
@@ -167,6 +167,19 @@
167
167
  --color-line-strong: var(--cg-border-strong);
168
168
  --color-line-accent: var(--cg-border-accent);
169
169
 
170
+ /* ---- washes ----
171
+ The two scrims, so a component that lays one over a picture writes
172
+ bg-scrim-strong rather than an arbitrary value or an inline style. Both are
173
+ declared at :root only and neither flips: a scrim composites over whatever
174
+ is beneath it, which is why a surface-scoped override would darken a wash
175
+ that is already dark.
176
+
177
+ --cg-hover deliberately gets no utility. `bg-hover` would sit one character
178
+ away from Tailwind's own `hover:` variant, and a name that reads as a
179
+ variant is a name someone writes by accident. */
180
+ --color-scrim: var(--cg-scrim);
181
+ --color-scrim-strong: var(--cg-scrim-strong);
182
+
170
183
  /* ---- type families ----
171
184
  --font-sans points at the body face so the stock font-sans utility is
172
185
  correct rather than something to remember not to use. */
@@ -1328,6 +1328,16 @@
1328
1328
  }
1329
1329
  }
1330
1330
  },
1331
+ "scrim-strong": {
1332
+ "$value": "rgba(34, 34, 34, 0.82)",
1333
+ "$type": "color",
1334
+ "$description": "The wash under TEXT laid over a picture, e.g. the entity card's hover reveal.\n\nA second scrim rather than a heavier --cg-scrim, because the two carry different\nobligations. --cg-scrim sits behind a modal and only has to separate two layers,\nso 0.4 is a mood. This one has words on it, and the picture underneath is an\narbitrary screenshot: the worst case is a white capture, where the composite is\nthe lightest this token ever gets and every foreground on it is at its least\nreadable.\n\nMEASURED against that worst case, over --cg-neutral-0: 8.89:1 for the ink\nsurface's own #ffffff and 6.18:1 for its rgba(255,255,255,0.78) secondary, both\nclear of the 4.5:1 AA floor for normal text. At 0.6 the white would measure\n4.26:1 and fail, which is why this is not a rounder number. Asserted in\ntest/contrast-guardrail.test.mjs, so lightening it goes red rather than shipping\na caption nobody can read.\n\nDoes NOT flip per surface, for the same reason --cg-scrim does not: it\ncomposites over whatever is beneath it, and what is beneath it is a picture that\ndoes not flip either.",
1335
+ "$extensions": {
1336
+ "io.cloudgrid": {
1337
+ "css": "--cg-scrim-strong"
1338
+ }
1339
+ }
1340
+ },
1331
1341
  "hover": {
1332
1342
  "$value": "rgba(34, 34, 34, 0.045)",
1333
1343
  "$type": "color",
package/dist/tokens.css CHANGED
@@ -637,6 +637,27 @@
637
637
  Does NOT flip per surface, deliberately: it composites over whatever is beneath
638
638
  it, so a panel-scoped override would darken a scrim that is already dark. */
639
639
  --cg-scrim: rgba(34, 34, 34, 0.4);
640
+ /*
641
+ The wash under TEXT laid over a picture, e.g. the entity card's hover reveal.
642
+
643
+ A second scrim rather than a heavier --cg-scrim, because the two carry different
644
+ obligations. --cg-scrim sits behind a modal and only has to separate two layers,
645
+ so 0.4 is a mood. This one has words on it, and the picture underneath is an
646
+ arbitrary screenshot: the worst case is a white capture, where the composite is
647
+ the lightest this token ever gets and every foreground on it is at its least
648
+ readable.
649
+
650
+ MEASURED against that worst case, over --cg-neutral-0: 8.89:1 for the ink
651
+ surface's own #ffffff and 6.18:1 for its rgba(255,255,255,0.78) secondary, both
652
+ clear of the 4.5:1 AA floor for normal text. At 0.6 the white would measure
653
+ 4.26:1 and fail, which is why this is not a rounder number. Asserted in
654
+ test/contrast-guardrail.test.mjs, so lightening it goes red rather than shipping
655
+ a caption nobody can read.
656
+
657
+ Does NOT flip per surface, for the same reason --cg-scrim does not: it
658
+ composites over whatever is beneath it, and what is beneath it is a picture that
659
+ does not flip either. */
660
+ --cg-scrim-strong: rgba(34, 34, 34, 0.82);
640
661
  /*
641
662
  The wash under a hovered row or control. The system had no hover token; components were each inventing one. */
642
663
  --cg-hover: rgba(34, 34, 34, 0.045);
package/dist/tokens.json CHANGED
@@ -143,6 +143,7 @@
143
143
  "--cg-volt-ink": "#243d00",
144
144
  "--cg-live-halo": "color-mix(in srgb, var(--cg-volt) 32%, transparent)",
145
145
  "--cg-scrim": "rgba(34, 34, 34, 0.4)",
146
+ "--cg-scrim-strong": "rgba(34, 34, 34, 0.82)",
146
147
  "--cg-hover": "rgba(34, 34, 34, 0.045)"
147
148
  },
148
149
  "panel": {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@cloudgrid-io/ui",
3
- "version": "0.15.0",
3
+ "version": "0.17.0",
4
4
  "description": "CloudGrid design system: React components, brand design tokens, Tailwind theme, self-hosted fonts.",
5
5
  "publishConfig": {
6
6
  "registry": "https://registry.npmjs.org/",