haze-ui 1.30.0 → 1.31.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (124) hide show
  1. package/README.md +35 -1
  2. package/dist/components/ActivityRail/ActivityRail.js +76 -0
  3. package/dist/components/ActivityRail/index.js +3 -0
  4. package/dist/components/BottomSheet/BottomSheet.js +12 -26
  5. package/dist/components/ConversationList/ConversationList.js +16 -7
  6. package/dist/components/List/List.js +14 -10
  7. package/dist/components/LocaleProvider/ar-sa.js +7 -0
  8. package/dist/components/LocaleProvider/de-de.js +7 -0
  9. package/dist/components/LocaleProvider/es-es.js +7 -0
  10. package/dist/components/LocaleProvider/fr-fr.js +7 -0
  11. package/dist/components/LocaleProvider/it-it.js +7 -0
  12. package/dist/components/LocaleProvider/ja-jp.js +7 -0
  13. package/dist/components/LocaleProvider/ko-kr.js +7 -0
  14. package/dist/components/LocaleProvider/locale.js +7 -0
  15. package/dist/components/LocaleProvider/pt-br.js +7 -0
  16. package/dist/components/LocaleProvider/ru-ru.js +7 -0
  17. package/dist/components/LocaleProvider/zh-cn.js +7 -0
  18. package/dist/components/LogViewer/LogViewer.js +45 -38
  19. package/dist/components/OTPInput/OTPInputCore.js +1 -0
  20. package/dist/components/Resizable/Resizable.js +266 -36
  21. package/dist/components/Sparkline/Sparkline.js +45 -0
  22. package/dist/components/Sparkline/index.js +3 -0
  23. package/dist/components/Sparkline/sparkline-styles.js +18 -0
  24. package/dist/components/StatusBar/StatusBar.js +47 -0
  25. package/dist/components/StatusBar/index.js +3 -0
  26. package/dist/components/TabBar/TabBar.js +60 -0
  27. package/dist/components/TabBar/index.js +3 -0
  28. package/dist/components/Tabs/SortableTabList.js +116 -0
  29. package/dist/components/Tabs/Tab.js +83 -16
  30. package/dist/components/Tabs/TabList.js +94 -38
  31. package/dist/components/Tabs/edge-scroll.js +6 -0
  32. package/dist/components/Tabs/index.js +4 -3
  33. package/dist/components/Tabs/tab-metas.js +24 -0
  34. package/dist/components/TagInput/SortableTagInputCore.js +11 -11
  35. package/dist/components/Toast/ToastContainer.js +1 -1
  36. package/dist/components/Toast/index.js +1 -1
  37. package/dist/components/Toast/{toast2.js → toast-channel.js} +1 -1
  38. package/dist/components/Toast/useToast.js +1 -1
  39. package/dist/components/Tree/SortableTree.js +39 -39
  40. package/dist/components/VirtualList/VirtualList.js +133 -121
  41. package/dist/components/Workbench/Workbench.js +144 -0
  42. package/dist/components/Workbench/index.js +3 -0
  43. package/dist/css/activity-rail.css +2 -0
  44. package/dist/css/app-shell.css +1 -1
  45. package/dist/css/breadcrumb.css +1 -1
  46. package/dist/css/checkbox.css +1 -1
  47. package/dist/css/command.css +1 -1
  48. package/dist/css/context-menu.css +1 -1
  49. package/dist/css/date-range-picker.css +1 -1
  50. package/dist/css/drawer.css +1 -1
  51. package/dist/css/dropdown-menu.css +2 -2
  52. package/dist/css/hover-card.css +1 -1
  53. package/dist/css/list.css +1 -1
  54. package/dist/css/menu.css +2 -2
  55. package/dist/css/popover.css +1 -1
  56. package/dist/css/radio.css +1 -1
  57. package/dist/css/resizable.css +1 -1
  58. package/dist/css/segmented.css +1 -1
  59. package/dist/css/sidebar.css +1 -1
  60. package/dist/css/slider.css +1 -1
  61. package/dist/css/sparkline.css +2 -0
  62. package/dist/css/status-bar.css +2 -0
  63. package/dist/css/switch.css +1 -1
  64. package/dist/css/tab-bar.css +2 -0
  65. package/dist/css/tabs.css +3 -2
  66. package/dist/css/tag.css +1 -1
  67. package/dist/css/tree.css +1 -1
  68. package/dist/css/workbench.css +2 -0
  69. package/dist/css-manifest.json +16 -0
  70. package/dist/dates/adapter.js +9 -1
  71. package/dist/dates/buddhist.js +43 -0
  72. package/dist/dates/ethiopic.js +67 -0
  73. package/dist/dates/hebrew.js +95 -0
  74. package/dist/dates/japanese.js +41 -0
  75. package/dist/dates/persian.js +121 -0
  76. package/dist/dates/registry.js +14 -4
  77. package/dist/haze-ui.css +30 -24
  78. package/dist/index.js +253 -241
  79. package/dist/mcp-docs.json +555 -10
  80. package/dist/registry.json +115 -5
  81. package/dist/types/components/ActivityRail/ActivityRail.d.ts +30 -0
  82. package/dist/types/components/ActivityRail/index.d.ts +4 -0
  83. package/dist/types/components/ConversationList/ConversationList.d.ts +10 -1
  84. package/dist/types/components/List/List.d.ts +10 -1
  85. package/dist/types/components/LocaleProvider/locale.d.ts +7 -0
  86. package/dist/types/components/LogViewer/LogViewer.d.ts +10 -1
  87. package/dist/types/components/Resizable/Resizable.d.ts +24 -7
  88. package/dist/types/components/Resizable/index.d.ts +1 -1
  89. package/dist/types/components/Sparkline/Sparkline.d.ts +31 -0
  90. package/dist/types/components/Sparkline/index.d.ts +3 -0
  91. package/dist/types/components/Sparkline/sparkline-styles.d.ts +26 -0
  92. package/dist/types/components/StatusBar/StatusBar.d.ts +18 -0
  93. package/dist/types/components/StatusBar/index.d.ts +3 -0
  94. package/dist/types/components/TabBar/TabBar.d.ts +23 -0
  95. package/dist/types/components/TabBar/index.d.ts +4 -0
  96. package/dist/types/components/Tabs/SortableTabList.d.ts +46 -0
  97. package/dist/types/components/Tabs/Tab.d.ts +54 -3
  98. package/dist/types/components/Tabs/TabList.d.ts +26 -2
  99. package/dist/types/components/Tabs/edge-scroll.d.ts +17 -0
  100. package/dist/types/components/Tabs/index.d.ts +3 -1
  101. package/dist/types/components/Tabs/tab-metas.d.ts +20 -0
  102. package/dist/types/components/Toast/index.d.ts +2 -2
  103. package/dist/types/components/Toast/useToast.d.ts +1 -1
  104. package/dist/types/components/VirtualList/VirtualList.d.ts +20 -1
  105. package/dist/types/components/Workbench/Workbench.d.ts +50 -0
  106. package/dist/types/components/Workbench/index.d.ts +2 -0
  107. package/dist/types/dates/adapter.d.ts +33 -6
  108. package/dist/types/dates/buddhist.d.ts +14 -0
  109. package/dist/types/dates/ethiopic.d.ts +15 -0
  110. package/dist/types/dates/hebrew.d.ts +19 -0
  111. package/dist/types/dates/index.d.ts +5 -0
  112. package/dist/types/dates/japanese.d.ts +16 -0
  113. package/dist/types/dates/persian.d.ts +18 -0
  114. package/dist/types/dates/registry.d.ts +1 -1
  115. package/dist/types/index.d.ts +13 -3
  116. package/dist/types/utils/sortable.d.ts +8 -1
  117. package/dist/types/utils/use-end-reached.d.ts +56 -0
  118. package/dist/types/utils/viewport.d.ts +12 -0
  119. package/dist/utils/sortable-shared.js +3 -3
  120. package/dist/utils/sortable.js +15 -14
  121. package/dist/utils/use-end-reached.js +46 -0
  122. package/dist/utils/viewport.js +20 -0
  123. package/package.json +12 -4
  124. /package/dist/types/components/Toast/{toast.d.ts → toast-channel.d.ts} +0 -0
package/README.md CHANGED
@@ -31,7 +31,7 @@ English | [简体中文](./README-zh_CN.md)
31
31
 
32
32
  **`haze-ui/css-manifest.json` is machine-readable data.** The authoritative export → CSS-file mapping (family absorption included) is regenerated on every build, so bundler plugins and codemods read one source of truth instead of re-deriving kebab-case file names. A directory of pasted components has no equivalent — the mapping exists only in your head or your fork, and it drifts.
33
33
 
34
- **The `ControlOrValue<T>` protocol needs a real runtime.** One prop — `checked?: Control<T> | T` — covers controlled *and* uncontrolled usage because `react-use-control` carries the wiring; a published package is the contract that keeps that behavior identical across every component and version. None of this is hostile to the shadcn / Base UI ecosystem: haze-ui tokens are plain CSS custom properties, so they interoperate with a Tailwind v4 `@theme` block, and haze components compose alongside copy-pasted primitives wherever each fits.
34
+ **The `ControlOrValue<T>` protocol needs a real runtime.** One prop — `checked?: Control<T> | T` — covers controlled *and* uncontrolled usage because `react-use-control` carries the wiring; a published package is the contract that keeps that behavior identical across every component and version. None of this is hostile to the shadcn / Base UI ecosystem: haze-ui tokens are plain CSS custom properties, and haze components compose alongside copy-pasted primitives wherever each fits.
35
35
 
36
36
  ## Getting Started
37
37
 
@@ -194,11 +194,43 @@ import 'haze-ui/css/tokens.css';
194
194
  import 'haze-ui/css/button.css';
195
195
  import { Button } from 'haze-ui';
196
196
 
197
+ // …or zero CSS imports at all — the official Vite plugin injects the
198
+ // right per-component CSS for you (see "Automatic CSS with haze-ui-vite"):
199
+ // vite.config.ts → hazeCss() from 'haze-ui-vite'
200
+ import { Button } from 'haze-ui';
201
+
197
202
  export default function MyComponent() {
198
203
  return <Button>Start</Button>;
199
204
  }
200
205
  ```
201
206
 
207
+ #### Automatic CSS with haze-ui-vite
208
+
209
+ [`haze-ui-vite`](https://www.npmjs.com/package/haze-ui-vite) is the
210
+ official companion Vite plugin: it scans each module's named imports from
211
+ `haze-ui` (`import { Button, Select } from 'haze-ui'`), maps them through
212
+ `haze-ui/css-manifest.json`, and prepends the matching
213
+ `haze-ui/css/*.css` side-effect imports — `tokens.css` always first. CSS
214
+ enters the module graph exactly where it's consumed, so code-split views
215
+ carry only their own component CSS and HMR works through Vite's native
216
+ pipeline.
217
+
218
+ ```ts
219
+ // vite.config.ts
220
+ import hazeCss from 'haze-ui-vite';
221
+
222
+ export default {
223
+ plugins: [react(), hazeCss()],
224
+ };
225
+ ```
226
+
227
+ It reads the manifest shipped by your installed haze-ui version (no
228
+ hardcoded name mapping), validates every injected file exists in the
229
+ actual package, and warns on namespace imports it cannot collect. Works
230
+ with Vite 5–8, zero runtime dependencies. Not on Vite? Keep the explicit
231
+ imports above, or read `haze-ui/css-manifest.json` from your own bundler
232
+ tooling — it's the same data the plugin uses.
233
+
202
234
  Component CSS files are kebab-case versions of the component name
203
235
  (`OTPInput` → `haze-ui/css/otp-input.css`). Per-component files only
204
236
  cover that component's rules — tokens (themes, spacing, typography)
@@ -222,6 +254,8 @@ authoritative export → css-file mapping ships as data:
222
254
  included); `noCss` lists pure-logic exports with no css of their own.
223
255
  Bundler plugins and codemods should read this manifest instead of
224
256
  re-deriving file names — the mapping changes in lockstep with the build.
257
+ The official [`haze-ui-vite`](https://www.npmjs.com/package/haze-ui-vite)
258
+ plugin (above) is the reference consumer of this data.
225
259
 
226
260
  ### Server Components (Next.js App Router)
227
261
 
@@ -0,0 +1,76 @@
1
+
2
+ "use client";
3
+ import { classnames as e } from "../../utils/classnames.js";
4
+ import t from "../Badge/Badge.js";
5
+ import n from "../Tooltip/Tooltip.js";
6
+ /* empty css */
7
+ import { Children as r, isValidElement as i } from "react";
8
+ import { jsx as a, jsxs as o } from "react/jsx-runtime";
9
+ //#region src/lib/components/ActivityRail/ActivityRail.tsx
10
+ var s = "haze-ActivityRail__rail", c = "haze-ActivityRail__railHorizontal", l = "haze-ActivityRail__endGroup", u = "haze-ActivityRail__endGroupHorizontal";
11
+ function d({ orientation: t, children: n, className: d, ...f }) {
12
+ let p = [], m = [];
13
+ return r.forEach(n, (e) => {
14
+ i(e) && e.props.slot === "end" ? m.push(e) : p.push(e);
15
+ }), /* @__PURE__ */ o("nav", {
16
+ "data-slot": "activity-rail",
17
+ "data-orientation": t,
18
+ ...f,
19
+ className: e([
20
+ s,
21
+ c,
22
+ d
23
+ ]),
24
+ children: [p, m.length > 0 && /* @__PURE__ */ a("div", {
25
+ "data-slot": "activity-rail-end",
26
+ className: e([l, u]),
27
+ children: m
28
+ })]
29
+ });
30
+ }
31
+ var f = "haze-ActivityRail__item", p = "haze-ActivityRail__itemActive", m = "haze-ActivityRail__indicator", h = "haze-ActivityRail__itemIcon", g = "haze-ActivityRail__itemBadge";
32
+ function _({ icon: r, label: i, badge: s, active: c = !1, onSelect: l, slot: u = "start", className: d, onClick: _, ...v }) {
33
+ let y = /* @__PURE__ */ o("button", {
34
+ type: "button",
35
+ "data-slot": "activity-rail-item",
36
+ "aria-label": i,
37
+ "aria-current": c ? "true" : void 0,
38
+ onClick: (e) => {
39
+ _?.(e), l?.();
40
+ },
41
+ ...v,
42
+ className: e([
43
+ f,
44
+ c && p,
45
+ d
46
+ ]),
47
+ children: [
48
+ /* @__PURE__ */ a("span", {
49
+ "data-slot": "activity-rail-item-icon",
50
+ "aria-hidden": "true",
51
+ className: e(h),
52
+ children: r
53
+ }),
54
+ s != null && /* @__PURE__ */ a("span", {
55
+ "data-slot": "activity-rail-item-badge",
56
+ className: e(g),
57
+ children: /* @__PURE__ */ a(t, {
58
+ size: "sm",
59
+ children: s
60
+ })
61
+ }),
62
+ c && /* @__PURE__ */ a("span", {
63
+ "data-slot": "activity-rail-item-indicator",
64
+ "aria-hidden": "true",
65
+ className: e(m)
66
+ })
67
+ ]
68
+ });
69
+ return /* @__PURE__ */ a(n, {
70
+ content: i,
71
+ position: "right",
72
+ children: y
73
+ });
74
+ }
75
+ //#endregion
76
+ export { _ as ActivityRailItem, d as default };
@@ -0,0 +1,3 @@
1
+ "use client";
2
+ import e, { ActivityRailItem as t } from "./ActivityRail.js";
3
+ export { e as ActivityRail, t as ActivityRailItem };
@@ -4,8 +4,9 @@ import { classnames as e } from "../../utils/classnames.js";
4
4
  import { Presence as t } from "../../utils/presence.js";
5
5
  import { useFocusScope as n } from "../../utils/focus-scope.js";
6
6
  import { useViewTransitionFlip as r } from "../../utils/view-transition.js";
7
+ import { useVisualViewportInset as i } from "../../utils/viewport.js";
7
8
  /* empty css */
8
- import { useCallback as i, useEffect as a, useImperativeHandle as o, useRef as s, useState as c } from "react";
9
+ import { useCallback as a, useEffect as o, useImperativeHandle as s, useRef as c } from "react";
9
10
  import { jsx as l, jsxs as u } from "react/jsx-runtime";
10
11
  import { useControl as d } from "react-use-control";
11
12
  //#region src/lib/components/BottomSheet/BottomSheet.tsx
@@ -19,24 +20,9 @@ function v(e, t) {
19
20
  }
20
21
  return !0;
21
22
  }
22
- function y(e, t) {
23
- let [n, r] = c(0);
24
- return a(() => {
25
- if (!e || !t) return;
26
- let n = window.visualViewport;
27
- if (!n) return;
28
- let i = () => {
29
- let e = Math.max(0, Math.round(window.innerHeight - n.height - n.offsetTop));
30
- r((t) => t === e ? t : e);
31
- };
32
- return i(), n.addEventListener("resize", i), n.addEventListener("scroll", i), () => {
33
- n.removeEventListener("resize", i), n.removeEventListener("scroll", i);
34
- };
35
- }, [e, t]), n;
36
- }
37
- function b({ open: c, onClose: b, viewTransition: x = !1, swipeToDismiss: S = !1, virtualKeyboard: C = !1, children: w, className: T, style: E, ref: D, ...O }) {
38
- let [k, A] = d(c, !1), j = r(x, A), M = s(null);
39
- a(() => {
23
+ function y({ open: y, onClose: b, viewTransition: x = !1, swipeToDismiss: S = !1, virtualKeyboard: C = !1, children: w, className: T, style: E, ref: D, ...O }) {
24
+ let [k, A] = d(y, !1), j = r(x, A), M = c(null);
25
+ o(() => {
40
26
  if (!k) return;
41
27
  let e = document.activeElement;
42
28
  M.current = e instanceof HTMLElement ? e : null;
@@ -44,10 +30,10 @@ function b({ open: c, onClose: b, viewTransition: x = !1, swipeToDismiss: S = !1
44
30
  let N = n({
45
31
  enabled: k,
46
32
  trapped: !0
47
- }), P = i(() => {
33
+ }), P = a(() => {
48
34
  j(!1), b?.();
49
35
  }, [j, b]);
50
- o(D, () => ({
36
+ s(D, () => ({
51
37
  open: () => {
52
38
  j(!0);
53
39
  },
@@ -57,13 +43,13 @@ function b({ open: c, onClose: b, viewTransition: x = !1, swipeToDismiss: S = !1
57
43
  e?.isConnected && e.focus();
58
44
  }
59
45
  }), [j, P]);
60
- let F = y(C, k), I = C ? {
46
+ let F = i(C && k), I = C ? {
61
47
  "--haze-sheet-kb-inset": `${F}px`,
62
48
  maxHeight: `min(80dvh, calc(100dvh - ${F}px))`,
63
49
  ...F > 0 ? { transform: `translateY(${-F}px)` } : null
64
- } : void 0, L = s(null), R = i((e) => {
50
+ } : void 0, L = c(null), R = a((e) => {
65
51
  N(e), L.current = e;
66
- }, [N]), z = s(null), B = i((e) => {
52
+ }, [N]), z = c(null), B = a((e) => {
67
53
  let t = z.current, n = L.current;
68
54
  if (!t || !n || e.touches.length !== 1 || e.defaultPrevented) return;
69
55
  let [r] = e.touches;
@@ -111,7 +97,7 @@ function b({ open: c, onClose: b, viewTransition: x = !1, swipeToDismiss: S = !1
111
97
  let t = z.current, n = L.current;
112
98
  t && n && t.pointerId === e.pointerId && (z.current = null, H(n), t.dragging && U(n));
113
99
  };
114
- return a(() => {
100
+ return o(() => {
115
101
  if (k) return;
116
102
  z.current = null;
117
103
  let e = L.current;
@@ -154,4 +140,4 @@ function b({ open: c, onClose: b, viewTransition: x = !1, swipeToDismiss: S = !1
154
140
  });
155
141
  }
156
142
  //#endregion
157
- export { b as default };
143
+ export { y as default };
@@ -1,16 +1,25 @@
1
1
 
2
2
  "use client";
3
3
  import { classnames as e } from "../../utils/classnames.js";
4
+ import { useEndReached as t } from "../../utils/use-end-reached.js";
4
5
  /* empty css */
5
- import { jsx as t } from "react/jsx-runtime";
6
+ import { Children as n, useRef as r } from "react";
7
+ import { jsx as i } from "react/jsx-runtime";
6
8
  //#region src/lib/components/ConversationList/ConversationList.tsx
7
- var n = "haze-ConversationList__list";
8
- function r({ children: r, className: i }) {
9
- return /* @__PURE__ */ t("div", {
9
+ var a = "haze-ConversationList__list";
10
+ function o({ children: o, onLoadMore: s, className: c }) {
11
+ let l = r(null);
12
+ return t({
13
+ ref: l,
14
+ onEndReached: s,
15
+ threshold: 200,
16
+ contentUnits: n.count(o)
17
+ }), /* @__PURE__ */ i("div", {
18
+ ref: l,
10
19
  "data-slot": "conversation-list",
11
- className: e([n, i]),
12
- children: r
20
+ className: e([a, c]),
21
+ children: o
13
22
  });
14
23
  }
15
24
  //#endregion
16
- export { r as default };
25
+ export { o as default };
@@ -2,23 +2,27 @@
2
2
  "use client";
3
3
  import { classnames as e } from "../../utils/classnames.js";
4
4
  /* empty css */
5
- import { jsx as t } from "react/jsx-runtime";
5
+ import { jsx as t, jsxs as n } from "react/jsx-runtime";
6
6
  //#region src/lib/components/List/List.tsx
7
- var n = "haze-List__base", r = {
7
+ var r = "haze-List__base", i = {
8
8
  unordered: "haze-List__unordered",
9
9
  ordered: "haze-List__ordered",
10
10
  none: "haze-List__none"
11
- };
12
- function i({ variant: i = "unordered", className: a, children: o }) {
13
- return /* @__PURE__ */ t(i === "ordered" ? "ol" : "ul", {
11
+ }, a = "haze-List__loadMoreSlot";
12
+ function o({ variant: o = "unordered", className: s, children: c, loadMore: l }) {
13
+ return /* @__PURE__ */ n(o === "ordered" ? "ol" : "ul", {
14
14
  "data-slot": "list",
15
15
  className: e([
16
- n,
17
- r[i],
18
- a
16
+ r,
17
+ i[o],
18
+ s
19
19
  ]),
20
- children: o
20
+ children: [c, l && /* @__PURE__ */ t("li", {
21
+ "data-slot": "load-more",
22
+ className: e([a]),
23
+ children: l
24
+ })]
21
25
  });
22
26
  }
23
27
  //#endregion
24
- export { i as default };
28
+ export { o as default };
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "إخفاء المقتطف"
187
187
  },
188
188
  streamingText: { generating: "جارٍ الإنشاء" },
189
+ tabs: {
190
+ close: "إغلاق",
191
+ moreTabs: "المزيد من علامات التبويب",
192
+ statusDirty: "تغييرات غير محفوظة",
193
+ statusError: "خطأ",
194
+ statusSyncing: "جارٍ المزامنة"
195
+ },
189
196
  tag: { remove: "إزالة" },
190
197
  tagGroup: { remove: "إزالة" },
191
198
  tagInput: {
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "Auszug ausblenden"
187
187
  },
188
188
  streamingText: { generating: "Wird generiert" },
189
+ tabs: {
190
+ close: "Schließen",
191
+ moreTabs: "Weitere Tabs",
192
+ statusDirty: "Ungespeicherte Änderungen",
193
+ statusError: "Fehler",
194
+ statusSyncing: "Synchronisiert"
195
+ },
189
196
  tag: { remove: "Entfernen" },
190
197
  tagGroup: { remove: "Entfernen" },
191
198
  tagInput: {
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "Ocultar extracto"
187
187
  },
188
188
  streamingText: { generating: "Generando" },
189
+ tabs: {
190
+ close: "Cerrar",
191
+ moreTabs: "Más pestañas",
192
+ statusDirty: "Cambios sin guardar",
193
+ statusError: "Error",
194
+ statusSyncing: "Sincronizando"
195
+ },
189
196
  tag: { remove: "Quitar" },
190
197
  tagGroup: { remove: "Quitar" },
191
198
  tagInput: {
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "Masquer l’extrait"
187
187
  },
188
188
  streamingText: { generating: "Génération en cours" },
189
+ tabs: {
190
+ close: "Fermer",
191
+ moreTabs: "Plus d'onglets",
192
+ statusDirty: "Modifications non enregistrées",
193
+ statusError: "Erreur",
194
+ statusSyncing: "Synchronisation"
195
+ },
189
196
  tag: { remove: "Retirer" },
190
197
  tagGroup: { remove: "Retirer" },
191
198
  tagInput: {
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "Nascondi stralcio"
187
187
  },
188
188
  streamingText: { generating: "Generazione in corso" },
189
+ tabs: {
190
+ close: "Chiudi",
191
+ moreTabs: "Più schede",
192
+ statusDirty: "Modifiche non salvate",
193
+ statusError: "Errore",
194
+ statusSyncing: "Sincronizzazione"
195
+ },
189
196
  tag: { remove: "Rimuovi" },
190
197
  tagGroup: { remove: "Rimuovi" },
191
198
  tagInput: {
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "抜粋を非表示"
187
187
  },
188
188
  streamingText: { generating: "生成中" },
189
+ tabs: {
190
+ close: "閉じる",
191
+ moreTabs: "その他のタブ",
192
+ statusDirty: "未保存の変更",
193
+ statusError: "エラー",
194
+ statusSyncing: "同期中"
195
+ },
189
196
  tag: { remove: "削除" },
190
197
  tagGroup: { remove: "削除" },
191
198
  tagInput: {
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "발췌 접기"
187
187
  },
188
188
  streamingText: { generating: "생성 중" },
189
+ tabs: {
190
+ close: "닫기",
191
+ moreTabs: "탭 더 보기",
192
+ statusDirty: "저장되지 않은 변경 사항",
193
+ statusError: "오류",
194
+ statusSyncing: "동기화 중"
195
+ },
189
196
  tag: { remove: "제거" },
190
197
  tagGroup: { remove: "제거" },
191
198
  tagInput: {
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "Hide excerpt"
187
187
  },
188
188
  streamingText: { generating: "Generating" },
189
+ tabs: {
190
+ close: "Close",
191
+ moreTabs: "More tabs",
192
+ statusDirty: "Unsaved changes",
193
+ statusError: "Error",
194
+ statusSyncing: "Syncing"
195
+ },
189
196
  tag: { remove: "Remove" },
190
197
  tagGroup: { remove: "Remove" },
191
198
  tagInput: {
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "Ocultar trecho"
187
187
  },
188
188
  streamingText: { generating: "Gerando" },
189
+ tabs: {
190
+ close: "Fechar",
191
+ moreTabs: "Mais abas",
192
+ statusDirty: "Alterações não salvas",
193
+ statusError: "Erro",
194
+ statusSyncing: "Sincronizando"
195
+ },
189
196
  tag: { remove: "Remover" },
190
197
  tagGroup: { remove: "Remover" },
191
198
  tagInput: {
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "Скрыть отрывок"
187
187
  },
188
188
  streamingText: { generating: "Генерация" },
189
+ tabs: {
190
+ close: "Закрыть",
191
+ moreTabs: "Ещё вкладки",
192
+ statusDirty: "Несохранённые изменения",
193
+ statusError: "Ошибка",
194
+ statusSyncing: "Синхронизация"
195
+ },
189
196
  tag: { remove: "Удалить" },
190
197
  tagGroup: { remove: "Удалить" },
191
198
  tagInput: {
@@ -186,6 +186,13 @@ var e = {
186
186
  collapse: "收起摘录"
187
187
  },
188
188
  streamingText: { generating: "生成中" },
189
+ tabs: {
190
+ close: "关闭",
191
+ moreTabs: "更多标签页",
192
+ statusDirty: "未保存",
193
+ statusError: "错误",
194
+ statusSyncing: "同步中"
195
+ },
189
196
  tag: { remove: "移除" },
190
197
  tagGroup: { remove: "移除" },
191
198
  tagInput: {
@@ -2,78 +2,85 @@
2
2
  "use client";
3
3
  import { classnames as e } from "../../utils/classnames.js";
4
4
  import { useStrings as t } from "../LocaleProvider/useStrings.js";
5
+ import { useEndReached as n } from "../../utils/use-end-reached.js";
5
6
  /* empty css */
6
- import { useMemo as n } from "react";
7
- import { jsx as r, jsxs as i } from "react/jsx-runtime";
8
- import { useControl as a } from "react-use-control";
7
+ import { useMemo as r, useRef as i } from "react";
8
+ import { jsx as a, jsxs as o } from "react/jsx-runtime";
9
+ import { useControl as s } from "react-use-control";
9
10
  //#region src/lib/components/LogViewer/LogViewer.tsx
10
- var o = "haze-LogViewer__wrapper", s = "haze-LogViewer__toolbar", c = "haze-LogViewer__filterBtn", l = "haze-LogViewer__filterActive", u = "haze-LogViewer__body", d = "haze-LogViewer__entry", f = "haze-LogViewer__timestamp", p = "haze-LogViewer__levelBadge", m = "haze-LogViewer__levelDebug", h = "haze-LogViewer__levelInfo", g = "haze-LogViewer__levelWarn", _ = "haze-LogViewer__levelError", v = "haze-LogViewer__messageStyle", y = {
11
- debug: m,
12
- info: h,
13
- warn: g,
14
- error: _
15
- }, b = [
11
+ var c = "haze-LogViewer__wrapper", l = "haze-LogViewer__toolbar", u = "haze-LogViewer__filterBtn", d = "haze-LogViewer__filterActive", f = "haze-LogViewer__body", p = "haze-LogViewer__entry", m = "haze-LogViewer__timestamp", h = "haze-LogViewer__levelBadge", g = "haze-LogViewer__levelDebug", _ = "haze-LogViewer__levelInfo", v = "haze-LogViewer__levelWarn", y = "haze-LogViewer__levelError", b = "haze-LogViewer__messageStyle", x = {
12
+ debug: g,
13
+ info: _,
14
+ warn: v,
15
+ error: y
16
+ }, S = [
16
17
  "debug",
17
18
  "info",
18
19
  "warn",
19
20
  "error"
20
21
  ];
21
- function x({ logs: m, filter: h, className: g }) {
22
- let [_, x] = a(h, null), S = t("logViewer"), C = n(() => _ ? m.filter((e) => e.level === _) : m, [m, _]);
23
- return /* @__PURE__ */ i("div", {
22
+ function C({ logs: g, filter: _, onLoadMore: v, className: y }) {
23
+ let [C, w] = s(_, null), T = t("logViewer"), E = i(null), D = r(() => C ? g.filter((e) => e.level === C) : g, [g, C]);
24
+ return n({
25
+ ref: E,
26
+ onEndReached: v,
27
+ threshold: 200,
28
+ contentUnits: D.length
29
+ }), /* @__PURE__ */ o("div", {
24
30
  "data-slot": "log-viewer",
25
- className: e([o, g]),
26
- children: [/* @__PURE__ */ i("div", {
31
+ className: e([c, y]),
32
+ children: [/* @__PURE__ */ o("div", {
27
33
  "data-slot": "toolbar",
28
- className: e([s]),
29
- children: [/* @__PURE__ */ r("button", {
34
+ className: e([l]),
35
+ children: [/* @__PURE__ */ a("button", {
30
36
  "data-slot": "filter-button",
31
37
  type: "button",
32
- onClick: () => x(null),
33
- className: e([c, !_ && l]),
34
- children: S.all
35
- }), b.map((t) => /* @__PURE__ */ r("button", {
38
+ onClick: () => w(null),
39
+ className: e([u, !C && d]),
40
+ children: T.all
41
+ }), S.map((t) => /* @__PURE__ */ a("button", {
36
42
  "data-slot": "filter-button",
37
43
  type: "button",
38
- onClick: () => x(t),
39
- className: e([c, _ === t && l]),
44
+ onClick: () => w(t),
45
+ className: e([u, C === t && d]),
40
46
  children: t
41
47
  }, t))]
42
- }), /* @__PURE__ */ i("div", {
48
+ }), /* @__PURE__ */ o("div", {
49
+ ref: E,
43
50
  "data-slot": "body",
44
- className: e([u]),
45
- children: [C.map((t, n) => /* @__PURE__ */ i("div", {
51
+ className: e([f]),
52
+ children: [D.map((t, n) => /* @__PURE__ */ o("div", {
46
53
  "data-slot": "entry",
47
- className: e([d]),
54
+ className: e([p]),
48
55
  children: [
49
- t.timestamp && /* @__PURE__ */ r("span", {
56
+ t.timestamp && /* @__PURE__ */ a("span", {
50
57
  "data-slot": "time",
51
- className: e([f]),
58
+ className: e([m]),
52
59
  children: t.timestamp
53
60
  }),
54
- /* @__PURE__ */ r("span", {
61
+ /* @__PURE__ */ a("span", {
55
62
  "data-slot": "level",
56
- className: e([p, y[t.level]]),
63
+ className: e([h, x[t.level]]),
57
64
  children: t.level
58
65
  }),
59
- /* @__PURE__ */ r("span", {
66
+ /* @__PURE__ */ a("span", {
60
67
  "data-slot": "message",
61
- className: e([v]),
68
+ className: e([b]),
62
69
  children: t.message
63
70
  })
64
71
  ]
65
- }, n)), C.length === 0 && /* @__PURE__ */ r("div", {
72
+ }, n)), D.length === 0 && /* @__PURE__ */ a("div", {
66
73
  "data-slot": "entry",
67
- className: e([d]),
68
- children: /* @__PURE__ */ r("span", {
74
+ className: e([p]),
75
+ children: /* @__PURE__ */ a("span", {
69
76
  "data-slot": "message",
70
77
  style: { color: "var(--haze-color-text-muted)" },
71
- className: e([v]),
72
- children: S.noLogs
78
+ className: e([b]),
79
+ children: T.noLogs
73
80
  })
74
81
  })]
75
82
  })]
76
83
  });
77
84
  }
78
85
  //#endregion
79
- export { x as default };
86
+ export { C as default };
@@ -36,6 +36,7 @@ function l({ length: l = 6, value: u, onChange: d, className: f, ref: p }) {
36
36
  },
37
37
  type: "text",
38
38
  inputMode: "numeric",
39
+ autoComplete: "one-time-code",
39
40
  maxLength: 1,
40
41
  "aria-label": n(h.digitLabel, {
41
42
  index: r + 1,