@bysages/solid 0.2.3 → 0.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (154) hide show
  1. package/README.md +16 -2
  2. package/dist/{ai-response-B_586r27.mjs → ai-response-slzE03wh.mjs} +19 -17
  3. package/dist/chevron-D5RzcayK.mjs +9 -0
  4. package/dist/components/affix/index.mjs +15 -17
  5. package/dist/components/ai/index.d.mts +1 -1
  6. package/dist/components/ai/index.mjs +21 -22
  7. package/dist/components/ai-action/index.mjs +2 -2
  8. package/dist/components/ai-attachments/index.mjs +52 -38
  9. package/dist/components/ai-message/index.mjs +11 -13
  10. package/dist/components/ai-prompt-input/index.mjs +81 -55
  11. package/dist/components/ai-reasoning/index.mjs +10 -6
  12. package/dist/components/ai-response/index.mjs +1 -1
  13. package/dist/components/ai-source/index.mjs +23 -23
  14. package/dist/components/ai-suggestion/index.mjs +1 -1
  15. package/dist/components/ai-tool/index.mjs +29 -17
  16. package/dist/components/alert/index.mjs +37 -42
  17. package/dist/components/angle-slider/index.mjs +2 -2
  18. package/dist/components/aspect-ratio/index.mjs +14 -16
  19. package/dist/components/autocomplete/index.mjs +8 -3
  20. package/dist/components/avatar/index.d.mts +3 -0
  21. package/dist/components/avatar/index.mjs +10 -5
  22. package/dist/components/avatar-group/index.mjs +11 -13
  23. package/dist/components/back-top/index.mjs +31 -27
  24. package/dist/components/badge/index.mjs +14 -16
  25. package/dist/components/banner/index.mjs +26 -28
  26. package/dist/components/bento/index.d.mts +24 -0
  27. package/dist/components/bento/index.mjs +51 -0
  28. package/dist/components/block-ui/index.d.mts +12 -0
  29. package/dist/components/block-ui/index.mjs +43 -0
  30. package/dist/components/breadcrumb/index.mjs +12 -10
  31. package/dist/components/browser/index.d.mts +21 -0
  32. package/dist/components/browser/index.mjs +87 -0
  33. package/dist/components/button/index.mjs +27 -29
  34. package/dist/components/button-group/index.mjs +18 -20
  35. package/dist/components/calendar/index.mjs +141 -129
  36. package/dist/components/card/index.mjs +2 -2
  37. package/dist/components/cascade-select/index.mjs +167 -121
  38. package/dist/components/checkbox/index.mjs +2 -2
  39. package/dist/components/checkbox-group/index.mjs +53 -55
  40. package/dist/components/chip/index.mjs +22 -20
  41. package/dist/components/clipboard/index.mjs +2 -2
  42. package/dist/components/color-picker/index.mjs +2 -2
  43. package/dist/components/combobox/index.mjs +2 -2
  44. package/dist/components/command/index.mjs +83 -59
  45. package/dist/components/comment/index.mjs +77 -62
  46. package/dist/components/config-provider/index.d.mts +4 -1
  47. package/dist/components/config-provider/index.mjs +13 -9
  48. package/dist/components/container/index.mjs +14 -16
  49. package/dist/components/data-view/index.d.mts +18 -0
  50. package/dist/components/data-view/index.mjs +116 -0
  51. package/dist/components/date-input/index.mjs +2 -2
  52. package/dist/components/date-picker/index.mjs +2 -2
  53. package/dist/components/deferred-content/index.d.mts +16 -0
  54. package/dist/components/deferred-content/index.mjs +52 -0
  55. package/dist/components/descriptions/index.d.mts +9 -1
  56. package/dist/components/descriptions/index.mjs +43 -16
  57. package/dist/components/dock/index.d.mts +22 -0
  58. package/dist/components/dock/index.mjs +64 -0
  59. package/dist/components/dynamic-input/index.mjs +75 -68
  60. package/dist/components/editable/index.mjs +2 -2
  61. package/dist/components/ellipsis/index.mjs +17 -19
  62. package/dist/components/empty/index.mjs +2 -2
  63. package/dist/components/file-upload/index.d.mts +7 -1
  64. package/dist/components/file-upload/index.mjs +13 -3
  65. package/dist/components/float-button/index.mjs +42 -39
  66. package/dist/components/form/index.d.mts +1 -1
  67. package/dist/components/form/index.mjs +52 -37
  68. package/dist/components/grid/index.mjs +19 -21
  69. package/dist/components/icon/index.d.mts +9 -4
  70. package/dist/components/icon/index.mjs +37 -36
  71. package/dist/components/image/index.d.mts +4 -0
  72. package/dist/components/image/index.mjs +50 -43
  73. package/dist/components/image-viewer/index.d.mts +4 -0
  74. package/dist/components/image-viewer/index.mjs +54 -37
  75. package/dist/components/input/index.d.mts +3 -0
  76. package/dist/components/input/index.mjs +1 -41
  77. package/dist/components/input-group/index.mjs +14 -18
  78. package/dist/components/json-tree-view/index.d.mts +5 -2
  79. package/dist/components/json-tree-view/index.mjs +25 -2
  80. package/dist/components/kbd/index.mjs +8 -10
  81. package/dist/components/layout/index.mjs +81 -77
  82. package/dist/components/link/index.mjs +12 -13
  83. package/dist/components/list/index.d.mts +2 -1
  84. package/dist/components/list/index.mjs +62 -48
  85. package/dist/components/listbox/index.mjs +2 -2
  86. package/dist/components/masonry/index.mjs +15 -17
  87. package/dist/components/mentions/index.mjs +1 -1
  88. package/dist/components/menu/index.mjs +2 -2
  89. package/dist/components/menubar/index.mjs +59 -57
  90. package/dist/components/meter/index.mjs +41 -41
  91. package/dist/components/number-input/index.mjs +2 -2
  92. package/dist/components/order-list/index.d.mts +21 -0
  93. package/dist/components/order-list/index.mjs +168 -0
  94. package/dist/components/page-header/index.mjs +2 -2
  95. package/dist/components/pagination/index.mjs +2 -2
  96. package/dist/components/password-input/index.mjs +2 -2
  97. package/dist/components/pin-input/index.mjs +2 -2
  98. package/dist/components/popconfirm/index.mjs +19 -12
  99. package/dist/components/progress/index.mjs +2 -2
  100. package/dist/components/progress-group/index.mjs +65 -58
  101. package/dist/components/radio-group/index.mjs +2 -2
  102. package/dist/components/rating-group/index.mjs +2 -2
  103. package/dist/components/result/index.d.mts +22 -0
  104. package/dist/components/result/index.mjs +66 -0
  105. package/dist/components/select/index.d.mts +2 -17
  106. package/dist/components/select/index.mjs +2 -18
  107. package/dist/components/separator/index.mjs +17 -19
  108. package/dist/components/skeleton/index.mjs +8 -10
  109. package/dist/components/slider/index.mjs +2 -2
  110. package/dist/components/spinner/index.mjs +17 -17
  111. package/dist/components/split-button/index.mjs +88 -83
  112. package/dist/components/spotlight/index.d.mts +11 -0
  113. package/dist/components/spotlight/index.mjs +38 -0
  114. package/dist/components/stack/index.mjs +20 -22
  115. package/dist/components/stat/index.mjs +12 -14
  116. package/dist/components/steps/index.d.mts +6 -1
  117. package/dist/components/steps/index.mjs +9 -3
  118. package/dist/components/switch/index.mjs +2 -2
  119. package/dist/components/table/index.mjs +323 -214
  120. package/dist/components/tabs/index.d.mts +2 -0
  121. package/dist/components/tabs/index.mjs +10 -5
  122. package/dist/components/tags-input/index.mjs +2 -2
  123. package/dist/components/terminal/index.d.mts +17 -0
  124. package/dist/components/terminal/index.mjs +86 -0
  125. package/dist/components/textarea/index.mjs +8 -8
  126. package/dist/components/timeline/index.d.mts +9 -3
  127. package/dist/components/timeline/index.mjs +18 -3
  128. package/dist/components/toc/index.d.mts +2 -7
  129. package/dist/components/toc/index.mjs +1 -9
  130. package/dist/components/toggle-group/index.mjs +2 -2
  131. package/dist/components/toolbar/index.d.mts +17 -0
  132. package/dist/components/toolbar/index.mjs +46 -0
  133. package/dist/components/transfer/index.mjs +126 -107
  134. package/dist/components/tree-select/index.mjs +36 -25
  135. package/dist/components/tree-view/index.d.mts +8 -1
  136. package/dist/components/tree-view/index.mjs +29 -3
  137. package/dist/components/typography/index.mjs +2 -2
  138. package/dist/components/user/index.d.mts +19 -0
  139. package/dist/components/user/index.mjs +68 -0
  140. package/dist/components/virtual-list/index.d.mts +17 -0
  141. package/dist/components/virtual-list/index.mjs +72 -0
  142. package/dist/components/watermark/index.mjs +19 -13
  143. package/dist/index-DdsnfV4f.d.mts +16 -0
  144. package/dist/{index-B4XS2n2y.d.mts → index-IfofF-SW.d.mts} +718 -3773
  145. package/dist/index-YPUiqD3n.d.mts +42 -0
  146. package/dist/index.d.mts +17 -4
  147. package/dist/index.mjs +22 -9
  148. package/dist/input-DoFQ7RXh.mjs +78 -0
  149. package/dist/{mentions-xbI6vJAP.mjs → mentions-f5Js_2W7.mjs} +76 -70
  150. package/dist/select-CX6OuQlU.mjs +123 -0
  151. package/dist/toc-CZmYEaQR.mjs +21 -0
  152. package/dist/use-component-messages-C4SCVYjD.mjs +17 -0
  153. package/package.json +28 -7
  154. package/dist/chevron-GWEoEYdO.mjs +0 -9
package/README.md CHANGED
@@ -4,11 +4,11 @@
4
4
  ![npm downloads](https://img.shields.io/npm/dw/@bysages/solid)
5
5
  ![npm license](https://img.shields.io/npm/l/@bysages/solid)
6
6
 
7
- > By Sages Elements for Solid — 90+ accessible component families, headless by construction, dressed by the paper-and-ink style layer.
7
+ > By Sages Elements for Solid — 140+ accessible component families, headless by construction, dressed by the paper-and-ink style layer.
8
8
 
9
9
  ## Features
10
10
 
11
- - 🧩 **90+ families** — actions, forms, overlays, navigation, data, layout, and an AI conversation family on ai-sdk formats
11
+ - 🧩 **140+ families** — actions, forms, overlays, navigation, data, layout, an AI conversation family on ai-sdk formats, and a full generative vocabulary
12
12
  - 🏛️ **Headless inside** — interaction, state, ARIA, and positioning come from proven headless state machines; wrappers add API narrowing and style injection, no DOM of their own
13
13
  - 🎨 **Token-styled** — every visual value is a CSS custom property from `@bysages/core`; light/dark, accent pigments, contrast and density tiers are data, never hardcoded styles
14
14
  - 📦 **Container-driven** — components respond to `@container`, not the viewport; the same component composes in a sidebar, a card, or a page
@@ -62,6 +62,20 @@ render(
62
62
  );
63
63
  ```
64
64
 
65
+ ## Generative UI
66
+
67
+ Every family carries a generative face — a zod-typed catalog entry that
68
+ lives beside the component. The faces compose into a
69
+ [json-render](https://json-render.dev) catalog and render through the
70
+ same package:
71
+
72
+ ```ts
73
+ import { catalog } from "@bysages/solid/generative";
74
+ ```
75
+
76
+ Point an AI SDK stream at the renderer and a prompt becomes real,
77
+ on-brand components — constrained to the families you registered.
78
+
65
79
  ## Documentation
66
80
 
67
81
  The [documentation site](https://elements.bysages.com) carries every family with live demos and props tables.
@@ -1,5 +1,6 @@
1
+ import { n as useComponentMessages } from "./use-component-messages-C4SCVYjD.mjs";
1
2
  import { injectComponentStyle } from "@bysages/core";
2
- import { mergeProps, spread, template, use } from "solid-js/web";
3
+ import { ref, spread, template } from "@solidjs/web";
3
4
  import { createEffect, createMemo, onMount, splitProps } from "solid-js";
4
5
  import { renderHtml } from "@tanstack/markdown/html";
5
6
  //#region src/components/ai-response/code-copy.ts
@@ -99,7 +100,7 @@ function wrapResponseTables(root) {
99
100
  }
100
101
  //#endregion
101
102
  //#region src/components/ai-response/index.tsx
102
- var _tmpl$ = /*#__PURE__*/ template(`<div>`);
103
+ var _tmpl$ = /* @__PURE__ */ template(`<div>`);
103
104
  /** Markdown set on the paper. Rendering goes through
104
105
  * `@tanstack/markdown`, whose defaults leave raw HTML and executable
105
106
  * links inert — streaming-safe by construction. */
@@ -111,29 +112,30 @@ function Response(props) {
111
112
  "copyLabel",
112
113
  "copiedLabel"
113
114
  ]);
115
+ const messages = useComponentMessages();
114
116
  const html = createMemo(() => renderHtml(own.content, own.highlighter ? { highlighter: own.highlighter } : void 0));
115
117
  let root;
116
118
  onMount(() => createEffect(() => {
117
119
  html();
118
- if (root) decorateCodeCopy(root, own.copyLabel ?? "Copy code");
120
+ if (root) decorateCodeCopy(root, own.copyLabel ?? messages().ai.copyCode);
119
121
  if (root) wrapResponseTables(root);
120
122
  }));
121
123
  const onClick = (event) => {
122
- clickCodeCopy(event, own.copyLabel ?? "Copy code", own.copiedLabel ?? "Copied");
124
+ clickCodeCopy(event, own.copyLabel ?? messages().ai.copyCode, own.copiedLabel ?? messages().ai.copied);
123
125
  };
124
- return (() => {
125
- var _el$ = _tmpl$();
126
- use((el) => root = el, _el$);
127
- spread(_el$, mergeProps(rest, {
128
- "data-scope": "ai",
129
- "data-part": "response",
130
- "onClick": onClick,
131
- get innerHTML() {
132
- return html();
133
- }
134
- }), false, false);
135
- return _el$;
136
- })();
126
+ var _el$ = _tmpl$();
127
+ ref(() => {
128
+ return (el) => root = el;
129
+ }, _el$);
130
+ spread(_el$, [rest, {
131
+ "data-scope": "ai",
132
+ "data-part": "response",
133
+ onClick,
134
+ get innerHTML() {
135
+ return html();
136
+ }
137
+ }], false);
138
+ return _el$;
137
139
  }
138
140
  //#endregion
139
141
  export { Response as t };
@@ -0,0 +1,9 @@
1
+ import { template } from "@solidjs/web";
2
+ //#region src/components/ai/chevron.tsx
3
+ var _tmpl$ = /* @__PURE__ */ template(`<svg viewBox="0 0 16 16"fill=none aria-hidden=true><path d="M6 4l4 4-4 4"stroke=currentColor stroke-width=1.5 stroke-linecap=round stroke-linejoin=round>`);
4
+ /** The folding chevron the shared indicator turns. */
5
+ function chevron() {
6
+ return _tmpl$();
7
+ }
8
+ //#endregion
9
+ export { chevron as t };
@@ -1,8 +1,8 @@
1
1
  import { injectComponentStyle } from "@bysages/core";
2
- import { mergeProps, spread, template } from "solid-js/web";
2
+ import { spread, template } from "@solidjs/web";
3
3
  import { splitProps } from "solid-js";
4
4
  //#region src/components/affix/index.tsx
5
- var _tmpl$ = /*#__PURE__*/ template(`<div>`);
5
+ var _tmpl$ = /* @__PURE__ */ template(`<div>`);
6
6
  /**
7
7
  * A nail: the wrapped content travels with the page until it reaches its
8
8
  * offset, then stays put while the page moves on. The semantics are
@@ -15,21 +15,19 @@ var _tmpl$ = /*#__PURE__*/ template(`<div>`);
15
15
  function Affix(props) {
16
16
  injectComponentStyle("affix");
17
17
  const [own, rest] = splitProps(props, ["offsetTop", "offsetBottom"]);
18
- return (() => {
19
- var _el$ = _tmpl$();
20
- spread(_el$, mergeProps(rest, {
21
- get style() {
22
- return {
23
- ...rest.style,
24
- top: own.offsetTop ?? "0px",
25
- bottom: own.offsetBottom ?? "0px"
26
- };
27
- },
28
- "data-scope": "affix",
29
- "data-part": "root"
30
- }), false, false);
31
- return _el$;
32
- })();
18
+ var _el$ = _tmpl$();
19
+ spread(_el$, [rest, {
20
+ get style() {
21
+ return {
22
+ ...rest.style,
23
+ top: own.offsetTop ?? "0px",
24
+ bottom: own.offsetBottom ?? "0px"
25
+ };
26
+ },
27
+ "data-scope": "affix",
28
+ "data-part": "root"
29
+ }], false);
30
+ return _el$;
33
31
  }
34
32
  //#endregion
35
33
  export { Affix };
@@ -1,2 +1,2 @@
1
- import { a as AiLoader, c as ReasoningUIPart, d as StepStartUIPart, f as TextUIPart, h as UIMessagePart, i as AiConversation, l as SourceDocumentUIPart, m as UIMessage, n as AiActions, o as DataUIPart, p as ToolUIPart, r as AiContent, s as FileUIPart, t as Ai, u as SourceUrlUIPart } from "../../index-B4XS2n2y.mjs";
1
+ import { a as AiLoader, c as ReasoningUIPart, d as StepStartUIPart, f as TextUIPart, h as UIMessagePart, i as AiConversation, l as SourceDocumentUIPart, m as UIMessage, n as AiActions, o as DataUIPart, p as ToolUIPart, r as AiContent, s as FileUIPart, t as Ai, u as SourceUrlUIPart } from "../../index-IfofF-SW.mjs";
2
2
  export { Ai, AiActions, AiContent, AiConversation, AiLoader, type DataUIPart, type FileUIPart, type ReasoningUIPart, type SourceDocumentUIPart, type SourceUrlUIPart, type StepStartUIPart, type TextUIPart, type ToolUIPart, type UIMessage, type UIMessagePart };
@@ -1,52 +1,51 @@
1
1
  import { Action } from "../ai-action/index.mjs";
2
2
  import { AiMessage as Message } from "../ai-message/index.mjs";
3
+ import { n as useComponentMessages } from "../../use-component-messages-C4SCVYjD.mjs";
3
4
  import { AiPromptInput as PromptInput } from "../ai-prompt-input/index.mjs";
4
5
  import { AiReasoning as Reasoning } from "../ai-reasoning/index.mjs";
5
- import { t as Response } from "../../ai-response-B_586r27.mjs";
6
+ import { t as Response } from "../../ai-response-slzE03wh.mjs";
6
7
  import { AiSource as Source, AiSources as Sources } from "../ai-source/index.mjs";
7
8
  import { AiSuggestion as Suggestion } from "../ai-suggestion/index.mjs";
8
9
  import { AiTool as Tool } from "../ai-tool/index.mjs";
9
10
  import { injectComponentStyle } from "@bysages/core";
10
- import { mergeProps, spread, template } from "solid-js/web";
11
+ import { spread, template } from "@solidjs/web";
11
12
  //#region src/components/ai/index.tsx
12
- var _tmpl$ = /*#__PURE__*/ template(`<div>`);
13
- /** A conversation column: Root is the log, Message carries a role, and
14
- * the speaking parts — Response, Reasoning, Tool, Sources — part the
15
- * stream. The interactive folds are the shared Collapsible wearing a
16
- * `data-ai` marker, so the machine work is never ours. Parts stay
17
- * agnostic of any client; consumers map their message format (e.g. the
18
- * `UIMessage` parts re-exported here) onto these primitives. */
13
+ var _tmpl$ = /* @__PURE__ */ template(`<div>`);
19
14
  function part(name, extra = {}) {
20
15
  function Component(props) {
21
- return (() => {
22
- var _el$ = _tmpl$();
23
- spread(_el$, mergeProps(extra, props, {
16
+ const messages = useComponentMessages();
17
+ const partExtra = typeof extra === "function" ? extra(messages()) : extra;
18
+ var _el$ = _tmpl$();
19
+ spread(_el$, [
20
+ partExtra,
21
+ props,
22
+ {
24
23
  "data-scope": "ai",
25
- get ["data-part"]() {
24
+ get "data-part"() {
26
25
  return name.toLowerCase();
27
26
  }
28
- }), false, false);
29
- return _el$;
30
- })();
27
+ }
28
+ ], false);
29
+ return _el$;
31
30
  }
32
31
  return Component;
33
32
  }
34
33
  /** The log itself: the column every stroke lands in, a landmark to
35
34
  * screen readers. */
36
- const AiConversation = part("Conversation", {
35
+ const AiConversation = part("Conversation", (messages) => ({
37
36
  role: "log",
38
- "aria-label": "Conversation"
39
- });
37
+ "aria-label": messages.ai.conversation
38
+ }));
40
39
  /** The bubble's inner measure — content that belongs to neither side
41
40
  * specifically. */
42
41
  const AiContent = part("Content");
43
42
  /** The quiet row under a message — copy, retry, feedback. */
44
43
  const AiActions = part("Actions");
45
44
  /** The while-it-works whisper for the in-flight turns. */
46
- const AiLoader = part("Loader", {
45
+ const AiLoader = part("Loader", (messages) => ({
47
46
  role: "status",
48
- "aria-label": "Loading"
49
- });
47
+ "aria-label": messages.ai.loading
48
+ }));
50
49
  /** The whole family under one handle — `Ai.Conversation`,
51
50
  * `Ai.MessageContent`, and the rest. */
52
51
  const Ai = Object.assign(AiConversation, {
@@ -1,6 +1,6 @@
1
1
  import { Button } from "../button/index.mjs";
2
2
  import { injectComponentStyle } from "@bysages/core";
3
- import { createComponent, mergeProps } from "solid-js/web";
3
+ import { createComponent, mergeProps } from "@solidjs/web";
4
4
  import { splitProps } from "solid-js";
5
5
  //#region src/components/ai-action/index.tsx
6
6
  /** A quiet icon button — copy, retry, thumbs. The label names it to
@@ -13,7 +13,7 @@ function Action(props) {
13
13
  variant: "ghost",
14
14
  size: "sm",
15
15
  square: true,
16
- get ["aria-label"]() {
16
+ get "aria-label"() {
17
17
  return own.label;
18
18
  },
19
19
  get title() {
@@ -1,12 +1,13 @@
1
+ import { n as useComponentMessages, t as formatComponentMessage } from "../../use-component-messages-C4SCVYjD.mjs";
1
2
  import { injectComponentStyle } from "@bysages/core";
2
- import { delegateEvents, effect, insert, memo, mergeProps, setAttribute, spread, template } from "solid-js/web";
3
+ import { delegateEvents, effect, insert, memo, setAttribute, spread, template } from "@solidjs/web";
3
4
  import { splitProps } from "solid-js";
4
5
  //#region src/components/ai-attachments/index.tsx
5
- var _tmpl$ = /*#__PURE__*/ template(`<svg viewBox="0 0 16 16"aria-hidden=true fill=none stroke=currentColor stroke-width=1.5 stroke-linecap=square><rect x=2.5 y=3.5 width=11 height=9></rect><path d="M2.5 10.5 6 7l3 3 2-1.5 2.5 2"></path><circle cx=6 cy=6 r=0.75 fill=currentColor stroke=none>`);
6
- var _tmpl$2 = /*#__PURE__*/ template(`<svg viewBox="0 0 16 16"aria-hidden=true fill=none stroke=currentColor stroke-width=1.5 stroke-linecap=square><path d="M4 2.5h5l3 3V13.5H4z"></path><path d="M9 2.5v3h3">`);
7
- var _tmpl$3 = /*#__PURE__*/ template(`<svg viewBox="0 0 16 16"width=12 height=12 aria-hidden=true fill=none stroke=currentColor stroke-width=1.5 stroke-linecap=square><path d="M4 4l8 8M12 4l-8 8">`);
8
- var _tmpl$4 = /*#__PURE__*/ template(`<span><span></span><button type=button data-remove>`);
9
- var _tmpl$5 = /*#__PURE__*/ template(`<span>`);
6
+ var _tmpl$ = /* @__PURE__ */ template(`<svg viewBox="0 0 16 16"aria-hidden=true fill=none stroke=currentColor stroke-width=1.5 stroke-linecap=square><rect x=2.5 y=3.5 width=11 height=9></rect><path d="M2.5 10.5 6 7l3 3 2-1.5 2.5 2"></path><circle cx=6 cy=6 r=0.75 fill=currentColor stroke=none>`);
7
+ var _tmpl$2 = /* @__PURE__ */ template(`<svg viewBox="0 0 16 16"aria-hidden=true fill=none stroke=currentColor stroke-width=1.5 stroke-linecap=square><path d="M4 2.5h5l3 3V13.5H4z"></path><path d="M9 2.5v3h3">`);
8
+ var _tmpl$3 = /* @__PURE__ */ template(`<svg viewBox="0 0 16 16"width=12 height=12 aria-hidden=true fill=none stroke=currentColor stroke-width=1.5 stroke-linecap=square><path d="M4 4l8 8M12 4l-8 8">`);
9
+ var _tmpl$4 = /* @__PURE__ */ template(`<span><span></span><button type=button data-remove>`);
10
+ var _tmpl$5 = /* @__PURE__ */ template(`<span>`);
10
11
  function imageGlyph() {
11
12
  return _tmpl$();
12
13
  }
@@ -54,44 +55,57 @@ function Attachment(props) {
54
55
  "status",
55
56
  "onRemove"
56
57
  ]);
57
- return (() => {
58
- var _el$4 = _tmpl$4(), _el$5 = _el$4.firstChild, _el$6 = _el$5.nextSibling;
59
- spread(_el$4, mergeProps(rest, {
60
- "data-scope": "ai",
61
- "data-part": "attachment",
62
- get ["data-status"]() {
63
- return own.status ?? "ready";
64
- }
65
- }), false, true);
66
- insert(_el$4, (() => {
67
- var _c$ = memo(() => !!isImage(own.name));
68
- return () => _c$() ? imageGlyph() : fileGlyph();
69
- })(), _el$5);
70
- insert(_el$5, () => own.name);
71
- insert(_el$4, (() => {
72
- var _c$2 = memo(() => own.size !== void 0);
73
- return () => _c$2() ? (() => {
58
+ const messages = useComponentMessages();
59
+ var _el$4 = _tmpl$4();
60
+ var _el$5 = _el$4.firstChild;
61
+ var _el$6 = _el$5.nextSibling;
62
+ spread(_el$4, [rest, {
63
+ "data-scope": "ai",
64
+ "data-part": "attachment",
65
+ get "data-status"() {
66
+ return own.status ?? "ready";
67
+ }
68
+ }], true);
69
+ insert(_el$4, (() => {
70
+ var _c$ = memo(() => {
71
+ return !!isImage(own.name);
72
+ });
73
+ return () => {
74
+ return _c$() ? imageGlyph() : fileGlyph();
75
+ };
76
+ })(), _el$5);
77
+ insert(_el$5, () => {
78
+ return own.name;
79
+ });
80
+ insert(_el$4, (() => {
81
+ var _c$2 = memo(() => {
82
+ return own.size !== void 0;
83
+ });
84
+ return () => {
85
+ return _c$2() ? (() => {
74
86
  var _el$7 = _tmpl$5();
75
- insert(_el$7, () => humanSize(own.size));
87
+ insert(_el$7, () => {
88
+ return humanSize(own.size);
89
+ });
76
90
  return _el$7;
77
91
  })() : null;
78
- })(), _el$6);
79
- _el$6.$$click = () => own.onRemove?.();
80
- insert(_el$6, removeGlyph);
81
- effect(() => setAttribute(_el$6, "aria-label", `Remove ${own.name}`));
82
- return _el$4;
83
- })();
92
+ };
93
+ })(), _el$6);
94
+ _el$6._$$click = () => own.onRemove?.();
95
+ insert(_el$6, removeGlyph);
96
+ effect(() => formatComponentMessage(messages().ai.removeAttachment, { name: own.name }), (_v$) => {
97
+ setAttribute(_el$6, "aria-label", _v$);
98
+ });
99
+ return _el$4;
84
100
  }
85
101
  /** The row the files ride in — a wrapping line of chips. */
86
102
  function Attachments(props) {
87
- return (() => {
88
- var _el$8 = _tmpl$5();
89
- spread(_el$8, mergeProps(props, {
90
- "data-scope": "ai",
91
- "data-part": "attachments"
92
- }), false, false);
93
- return _el$8;
94
- })();
103
+ var _el$8 = _tmpl$5();
104
+ spread(_el$8, [props, {
105
+ "data-scope": "ai",
106
+ "data-part": "attachments"
107
+ }], false);
108
+ return _el$8;
95
109
  }
96
110
  delegateEvents(["click"]);
97
111
  //#endregion
@@ -1,24 +1,22 @@
1
1
  import { injectComponentStyle } from "@bysages/core";
2
- import { mergeProps, spread, template } from "solid-js/web";
2
+ import { spread, template } from "@solidjs/web";
3
3
  import { splitProps } from "solid-js";
4
4
  //#region src/components/ai-message/index.tsx
5
- var _tmpl$ = /*#__PURE__*/ template(`<article>`);
5
+ var _tmpl$ = /* @__PURE__ */ template(`<article>`);
6
6
  /** Whose stroke this is — the user's words sit in a recessed bubble,
7
7
  * the assistant speaks flat on the paper. */
8
8
  function Message(props) {
9
9
  injectComponentStyle("ai");
10
10
  const [own, rest] = splitProps(props, ["role"]);
11
- return (() => {
12
- var _el$ = _tmpl$();
13
- spread(_el$, mergeProps(rest, {
14
- "data-scope": "ai",
15
- "data-part": "message",
16
- get ["data-role"]() {
17
- return own.role ?? "assistant";
18
- }
19
- }), false, false);
20
- return _el$;
21
- })();
11
+ var _el$ = _tmpl$();
12
+ spread(_el$, [rest, {
13
+ "data-scope": "ai",
14
+ "data-part": "message",
15
+ get "data-role"() {
16
+ return own.role ?? "assistant";
17
+ }
18
+ }], false);
19
+ return _el$;
22
20
  }
23
21
  //#endregion
24
22
  export { Message as AiMessage, Message };
@@ -1,14 +1,15 @@
1
1
  import { Button } from "../button/index.mjs";
2
+ import { n as useComponentMessages } from "../../use-component-messages-C4SCVYjD.mjs";
2
3
  import { Field } from "../field/index.mjs";
3
4
  import { injectComponentStyle } from "@bysages/core";
4
- import { createComponent, insert, mergeProps, setAttribute, spread, template } from "solid-js/web";
5
+ import { claimElement, createComponent, insert, setAttribute, spread, template } from "@solidjs/web";
5
6
  import { Show, splitProps } from "solid-js";
6
7
  //#region src/components/ai-prompt-input/index.tsx
7
- var _tmpl$ = /*#__PURE__*/ template(`<svg viewBox="0 0 16 16"width=14 height=14 aria-hidden=true fill=none stroke=currentColor stroke-width=1.5 stroke-linecap=square><path d="M8 13V3M3.5 7.5 8 3l4.5 4.5">`);
8
- var _tmpl$2 = /*#__PURE__*/ template(`<svg viewBox="0 0 16 16"width=14 height=14 aria-hidden=true><rect x=4.5 y=4.5 width=7 height=7 fill=currentColor>`);
9
- var _tmpl$3 = /*#__PURE__*/ template(`<div data-scope=ai>`);
10
- var _tmpl$4 = /*#__PURE__*/ template(`<div data-scope=ai data-part=prompt-footer><div data-scope=ai data-part=prompt-end>`);
11
- var _tmpl$5 = /*#__PURE__*/ template(`<form><div data-scope=ai data-part=prompt-main>`);
8
+ var _tmpl$ = /* @__PURE__ */ template(`<svg viewBox="0 0 16 16"width=14 height=14 aria-hidden=true fill=none stroke=currentColor stroke-width=1.5 stroke-linecap=square><path d="M8 13V3M3.5 7.5 8 3l4.5 4.5">`);
9
+ var _tmpl$2 = /* @__PURE__ */ template(`<svg viewBox="0 0 16 16"width=14 height=14 aria-hidden=true><rect x=4.5 y=4.5 width=7 height=7 fill=currentColor>`);
10
+ var _tmpl$3 = /* @__PURE__ */ template(`<div data-scope=ai>`);
11
+ var _tmpl$4 = /* @__PURE__ */ template(`<div data-scope=ai data-part=prompt-footer><div data-scope=ai data-part=prompt-end><!><!>`);
12
+ var _tmpl$5 = /* @__PURE__ */ template(`<form><div data-scope=ai data-part=prompt-main><!><!><!></div><!>`);
12
13
  function arrowUpGlyph() {
13
14
  return _tmpl$();
14
15
  }
@@ -43,6 +44,7 @@ function PromptInput(props) {
43
44
  "footer",
44
45
  "footerEnd"
45
46
  ]);
47
+ const messages = useComponentMessages();
46
48
  const send = () => {
47
49
  const value = (own.value ?? "").trim();
48
50
  if (!value || own.disabled || own.busy) return;
@@ -60,7 +62,9 @@ function PromptInput(props) {
60
62
  size: "sm",
61
63
  square: true,
62
64
  type: "button",
63
- "aria-label": "Stop",
65
+ get "aria-label"() {
66
+ return messages().ai.stop;
67
+ },
64
68
  get disabled() {
65
69
  return own.disabled;
66
70
  },
@@ -73,7 +77,9 @@ function PromptInput(props) {
73
77
  size: "sm",
74
78
  square: true,
75
79
  type: "submit",
76
- "aria-label": "Send",
80
+ get "aria-label"() {
81
+ return messages().ai.send;
82
+ },
77
83
  get disabled() {
78
84
  return own.disabled || !(own.value ?? "").trim();
79
85
  },
@@ -82,55 +88,75 @@ function PromptInput(props) {
82
88
  }
83
89
  });
84
90
  const trailing = () => own.footer != null ? own.trailing : own.trailing ?? seal();
85
- return (() => {
86
- var _el$4 = _tmpl$5(), _el$5 = _el$4.firstChild;
87
- spread(_el$4, mergeProps(rest, {
88
- "data-scope": "ai",
89
- "data-part": "prompt",
90
- "onSubmit": (event) => {
91
- event.preventDefault();
92
- send();
93
- }
94
- }), false, true);
95
- insert(_el$4, () => row("prompt-header", own.header), _el$5);
96
- insert(_el$5, () => row("prompt-leading", own.leading), null);
97
- insert(_el$5, createComponent(Field.Root, { get children() {
98
- return createComponent(Field.Textarea, {
99
- autoresize: true,
100
- rows: 1,
101
- get value() {
102
- return own.value ?? "";
103
- },
104
- get placeholder() {
105
- return own.placeholder ?? "Send a message";
106
- },
107
- get disabled() {
108
- return own.disabled;
109
- },
110
- onInput: (event) => own.onValueChange?.(event.currentTarget.value),
111
- onKeyDown: (event) => {
112
- if (event.key === "Enter" && !event.shiftKey) {
113
- event.preventDefault();
114
- send();
115
- }
116
- }
117
- });
118
- } }), null);
119
- insert(_el$5, () => row("prompt-trailing", trailing()), null);
120
- insert(_el$4, createComponent(Show, {
121
- get when() {
122
- return own.footer != null;
91
+ var _el$4 = _tmpl$5();
92
+ var _el$5 = _el$4.firstChild;
93
+ var _el$6 = _el$5.firstChild;
94
+ var _el$7 = _el$6.nextSibling;
95
+ var _el$8 = _el$7.nextSibling;
96
+ var _el$13 = _el$5.nextSibling;
97
+ claimElement(_el$4);
98
+ spread(_el$4, [rest, {
99
+ "data-scope": "ai",
100
+ "data-part": "prompt",
101
+ onSubmit: (event) => {
102
+ event.preventDefault();
103
+ send();
104
+ }
105
+ }], true);
106
+ insert(_el$4, () => {
107
+ return row("prompt-header", own.header);
108
+ }, _el$5);
109
+ insert(_el$5, () => {
110
+ return row("prompt-leading", own.leading);
111
+ }, _el$6);
112
+ insert(_el$5, createComponent(Field.Root, { get children() {
113
+ return createComponent(Field.Textarea, {
114
+ autoresize: true,
115
+ rows: 1,
116
+ get value() {
117
+ return own.value ?? "";
118
+ },
119
+ get placeholder() {
120
+ return own.placeholder ?? messages().ai.send;
123
121
  },
124
- get children() {
125
- var _el$6 = _tmpl$4(), _el$7 = _el$6.firstChild;
126
- insert(_el$6, () => own.footer, _el$7);
127
- insert(_el$7, () => own.footerEnd, null);
128
- insert(_el$7, seal, null);
129
- return _el$6;
122
+ get "aria-label"() {
123
+ return messages().ai.conversation;
124
+ },
125
+ get disabled() {
126
+ return own.disabled;
127
+ },
128
+ onInput: (event) => own.onValueChange?.(event.currentTarget.value),
129
+ onKeyDown: (event) => {
130
+ if (event.key === "Enter" && !event.shiftKey) {
131
+ event.preventDefault();
132
+ send();
133
+ }
130
134
  }
131
- }), null);
132
- return _el$4;
133
- })();
135
+ });
136
+ } }), _el$7);
137
+ insert(_el$5, () => {
138
+ return row("prompt-trailing", trailing());
139
+ }, _el$8);
140
+ insert(_el$4, createComponent(Show, {
141
+ get when() {
142
+ return own.footer != null;
143
+ },
144
+ get children() {
145
+ var _el$9 = _tmpl$4();
146
+ var _el$10 = _el$9.firstChild;
147
+ var _el$11 = _el$10.firstChild;
148
+ var _el$12 = _el$11.nextSibling;
149
+ insert(_el$9, () => {
150
+ return own.footer;
151
+ }, _el$10);
152
+ insert(_el$10, () => {
153
+ return own.footerEnd;
154
+ }, _el$11);
155
+ insert(_el$10, seal, _el$12);
156
+ return _el$9;
157
+ }
158
+ }), _el$13);
159
+ return _el$4;
134
160
  }
135
161
  //#endregion
136
162
  export { PromptInput as AiPromptInput, PromptInput };
@@ -1,11 +1,11 @@
1
- import { t as chevron } from "../../chevron-GWEoEYdO.mjs";
1
+ import { t as chevron } from "../../chevron-D5RzcayK.mjs";
2
2
  import { Collapsible } from "../collapsible/index.mjs";
3
3
  import { injectComponentStyle } from "@bysages/core";
4
- import { createComponent, insert, mergeProps, template } from "solid-js/web";
4
+ import { createComponent, insert, mergeProps, template } from "@solidjs/web";
5
5
  import { splitProps } from "solid-js";
6
6
  //#region src/components/ai-reasoning/index.tsx
7
- var _tmpl$ = /*#__PURE__*/ template(`<span>`);
8
- var _tmpl$2 = /*#__PURE__*/ template(`<div data-scope=ai data-part=reasoning-content>`);
7
+ var _tmpl$ = /* @__PURE__ */ template(`<span>`);
8
+ var _tmpl$2 = /* @__PURE__ */ template(`<div data-scope=ai data-part=reasoning-content>`);
9
9
  /** The model's thought, folded by the shared collapsible in its quiet
10
10
  * register: bare ink for a trigger, the thought on one hairline. */
11
11
  function Reasoning(props) {
@@ -17,14 +17,18 @@ function Reasoning(props) {
17
17
  return [createComponent(Collapsible.Trigger, { get children() {
18
18
  return [(() => {
19
19
  var _el$ = _tmpl$();
20
- insert(_el$, () => own.label ?? "Thinking");
20
+ insert(_el$, () => {
21
+ return own.label ?? "Thinking";
22
+ });
21
23
  return _el$;
22
24
  })(), createComponent(Collapsible.Indicator, { get children() {
23
25
  return chevron();
24
26
  } })];
25
27
  } }), createComponent(Collapsible.Content, { get children() {
26
28
  var _el$2 = _tmpl$2();
27
- insert(_el$2, () => own.children);
29
+ insert(_el$2, () => {
30
+ return own.children;
31
+ });
28
32
  return _el$2;
29
33
  } })];
30
34
  }
@@ -1,2 +1,2 @@
1
- import { t as Response } from "../../ai-response-B_586r27.mjs";
1
+ import { t as Response } from "../../ai-response-slzE03wh.mjs";
2
2
  export { Response as AiResponse, Response };