@santi020k/lumen-react 3.0.1 → 4.1.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 (145) hide show
  1. package/README.md +692 -13
  2. package/dist/ai-surfaces.d.ts +49 -0
  3. package/dist/ai-surfaces.d.ts.map +1 -0
  4. package/dist/ai-surfaces.js +88 -0
  5. package/dist/amount-field.d.ts +11 -0
  6. package/dist/amount-field.d.ts.map +1 -0
  7. package/dist/amount-field.js +37 -0
  8. package/dist/attachments.d.ts +17 -0
  9. package/dist/attachments.d.ts.map +1 -0
  10. package/dist/attachments.js +23 -0
  11. package/dist/bullet-chart.d.ts +14 -0
  12. package/dist/bullet-chart.d.ts.map +1 -0
  13. package/dist/bullet-chart.js +22 -0
  14. package/dist/change-summary.d.ts +14 -0
  15. package/dist/change-summary.d.ts.map +1 -0
  16. package/dist/change-summary.js +4 -0
  17. package/dist/chart-inspection.d.ts +10 -0
  18. package/dist/chart-inspection.d.ts.map +1 -0
  19. package/dist/chart-inspection.js +11 -0
  20. package/dist/chart-interaction.d.ts +17 -0
  21. package/dist/chart-interaction.d.ts.map +1 -0
  22. package/dist/chart-interaction.js +50 -0
  23. package/dist/chart-label.d.ts +3 -0
  24. package/dist/chart-label.d.ts.map +1 -0
  25. package/dist/chart-label.js +1 -0
  26. package/dist/chart-recipes.d.ts +8 -0
  27. package/dist/chart-recipes.d.ts.map +1 -1
  28. package/dist/chart-recipes.js +35 -0
  29. package/dist/combobox.d.ts +9 -0
  30. package/dist/combobox.d.ts.map +1 -0
  31. package/dist/combobox.js +137 -0
  32. package/dist/comparison-chart.d.ts +13 -0
  33. package/dist/comparison-chart.d.ts.map +1 -0
  34. package/dist/comparison-chart.js +18 -0
  35. package/dist/components.d.ts +106 -70
  36. package/dist/components.d.ts.map +1 -1
  37. package/dist/components.js +4 -1949
  38. package/dist/dashboard.d.ts +20 -0
  39. package/dist/dashboard.d.ts.map +1 -0
  40. package/dist/dashboard.js +19 -0
  41. package/dist/data-table-range-model.d.ts +8 -0
  42. package/dist/data-table-range-model.d.ts.map +1 -0
  43. package/dist/data-table-range-model.js +31 -0
  44. package/dist/data-table-range.d.ts +17 -0
  45. package/dist/data-table-range.d.ts.map +1 -0
  46. package/dist/data-table-range.js +8 -0
  47. package/dist/data-table-saved-views.d.ts +30 -0
  48. package/dist/data-table-saved-views.d.ts.map +1 -0
  49. package/dist/data-table-saved-views.js +49 -0
  50. package/dist/data-table-selection-model.d.ts +23 -0
  51. package/dist/data-table-selection-model.d.ts.map +1 -0
  52. package/dist/data-table-selection-model.js +36 -0
  53. package/dist/data-table-selection.d.ts +11 -0
  54. package/dist/data-table-selection.d.ts.map +1 -0
  55. package/dist/data-table-selection.js +10 -0
  56. package/dist/data-table-state.d.ts +6 -0
  57. package/dist/data-table-state.d.ts.map +1 -0
  58. package/dist/data-table-state.js +38 -0
  59. package/dist/data-table-view.d.ts +88 -0
  60. package/dist/data-table-view.d.ts.map +1 -0
  61. package/dist/data-table-view.js +1 -0
  62. package/dist/data-table.d.ts +60 -0
  63. package/dist/data-table.d.ts.map +1 -0
  64. package/dist/data-table.js +1 -0
  65. package/dist/date-range-calendar.d.ts +29 -0
  66. package/dist/date-range-calendar.d.ts.map +1 -0
  67. package/dist/date-range-calendar.js +69 -0
  68. package/dist/date-range-input.d.ts +25 -0
  69. package/dist/date-range-input.d.ts.map +1 -0
  70. package/dist/date-range-input.js +195 -0
  71. package/dist/device-frame.d.ts +13 -0
  72. package/dist/device-frame.d.ts.map +1 -0
  73. package/dist/device-frame.js +23 -0
  74. package/dist/dialog-lifecycle.d.ts +3 -0
  75. package/dist/dialog-lifecycle.d.ts.map +1 -0
  76. package/dist/dialog-lifecycle.js +70 -0
  77. package/dist/expanded-charts.d.ts +26 -0
  78. package/dist/expanded-charts.d.ts.map +1 -0
  79. package/dist/expanded-charts.js +46 -0
  80. package/dist/floating-panel.d.ts +12 -0
  81. package/dist/floating-panel.d.ts.map +1 -0
  82. package/dist/floating-panel.js +1 -0
  83. package/dist/form-workflow.d.ts +77 -0
  84. package/dist/form-workflow.d.ts.map +1 -0
  85. package/dist/form-workflow.js +337 -0
  86. package/dist/hooks.d.ts +24 -21
  87. package/dist/hooks.d.ts.map +1 -1
  88. package/dist/hooks.js +1 -2468
  89. package/dist/image-comparison.d.ts +20 -0
  90. package/dist/image-comparison.d.ts.map +1 -0
  91. package/dist/image-comparison.js +55 -0
  92. package/dist/index.d.ts +25 -1
  93. package/dist/index.d.ts.map +1 -1
  94. package/dist/index.js +24 -0
  95. package/dist/interval-charts.d.ts +21 -0
  96. package/dist/interval-charts.d.ts.map +1 -0
  97. package/dist/interval-charts.js +23 -0
  98. package/dist/media-selection.d.ts +18 -0
  99. package/dist/media-selection.d.ts.map +1 -0
  100. package/dist/media-selection.js +12 -0
  101. package/dist/media-viewport.d.ts +16 -0
  102. package/dist/media-viewport.d.ts.map +1 -0
  103. package/dist/media-viewport.js +37 -0
  104. package/dist/motion.d.ts +597 -0
  105. package/dist/motion.d.ts.map +1 -0
  106. package/dist/motion.js +22 -0
  107. package/dist/review-workflow.d.ts +32 -0
  108. package/dist/review-workflow.d.ts.map +1 -0
  109. package/dist/review-workflow.js +76 -0
  110. package/dist/rich-text-editor.d.ts +21 -0
  111. package/dist/rich-text-editor.d.ts.map +1 -0
  112. package/dist/rich-text-editor.js +143 -0
  113. package/dist/select-form.d.ts +3 -0
  114. package/dist/select-form.d.ts.map +1 -0
  115. package/dist/select-form.js +1 -0
  116. package/dist/server-components.d.ts +33 -6
  117. package/dist/server-components.d.ts.map +1 -1
  118. package/dist/server-components.js +26 -10
  119. package/dist/server.d.ts +1 -0
  120. package/dist/server.d.ts.map +1 -1
  121. package/dist/server.js +1 -0
  122. package/dist/toast-context.d.ts +4 -0
  123. package/dist/toast-context.d.ts.map +1 -0
  124. package/dist/toast-context.js +10 -0
  125. package/dist/toast-provider.d.ts +3 -0
  126. package/dist/toast-provider.d.ts.map +1 -0
  127. package/dist/toast-provider.js +3 -0
  128. package/dist/use-copy-feedback.d.ts +17 -0
  129. package/dist/use-copy-feedback.d.ts.map +1 -0
  130. package/dist/use-copy-feedback.js +54 -0
  131. package/dist/virtual-list-data.d.ts +13 -0
  132. package/dist/virtual-list-data.d.ts.map +1 -0
  133. package/dist/virtual-list-data.js +87 -0
  134. package/dist/virtual-list.d.ts +14 -0
  135. package/dist/virtual-list.d.ts.map +1 -0
  136. package/dist/virtual-list.js +24 -0
  137. package/dist/visual-interactions.d.ts +16 -0
  138. package/dist/visual-interactions.d.ts.map +1 -0
  139. package/dist/visual-interactions.js +30 -0
  140. package/dist/world-map.d.ts +26 -0
  141. package/dist/world-map.d.ts.map +1 -0
  142. package/dist/world-map.js +81 -0
  143. package/package.json +99 -11
  144. package/styles/critical.css +696 -66
  145. package/styles/data-table-view.css +36 -0
@@ -0,0 +1,49 @@
1
+ import type { ComponentPropsWithoutRef, ReactNode } from 'react';
2
+ import { type LumenApprovalResponseDetail, type LumenApprovalStatus, type LumenPromptSubmitDetail, type LumenStreamStatus, type LumenToolStatus } from '@santi020k/lumen-core';
3
+ export interface PromptComposerProps extends Omit<ComponentPropsWithoutRef<'form'>, 'defaultValue'> {
4
+ actions?: ReactNode;
5
+ defaultValue?: string;
6
+ disabled?: boolean;
7
+ label?: string;
8
+ maxLength?: number;
9
+ onPromptSubmit?: (detail: LumenPromptSubmitDetail) => void;
10
+ onStop?: () => void;
11
+ onValueChange?: (value: string) => void;
12
+ pending?: boolean;
13
+ sendLabel?: string;
14
+ stopLabel?: string;
15
+ submitOnEnter?: boolean;
16
+ value?: string;
17
+ }
18
+ export declare const PromptComposer: ({ actions, children, className, defaultValue, disabled, id, label, maxLength, onPromptSubmit, onStop, onValueChange, pending, sendLabel, stopLabel, submitOnEnter, value, onReset, ...props }: PromptComposerProps) => import("react").JSX.Element;
19
+ export interface StreamMessageProps extends ComponentPropsWithoutRef<'article'> {
20
+ actions?: ReactNode;
21
+ label?: string;
22
+ sources?: ReactNode;
23
+ status?: LumenStreamStatus;
24
+ statusLabel: string;
25
+ }
26
+ export declare const StreamMessage: ({ actions, children, className, label, sources, status, statusLabel, ...props }: StreamMessageProps) => import("react").JSX.Element;
27
+ export interface SourceCitationProps extends Omit<ComponentPropsWithoutRef<'a'>, 'href'> {
28
+ href: string;
29
+ label: string;
30
+ }
31
+ export declare const SourceCitation: ({ children, className, href, label, ...props }: SourceCitationProps) => import("react").JSX.Element;
32
+ export interface ToolActivityProps extends ComponentPropsWithoutRef<'details'> {
33
+ label: string;
34
+ status?: LumenToolStatus;
35
+ statusLabel: string;
36
+ }
37
+ export declare const ToolActivity: ({ children, className, label, status, statusLabel, ...props }: ToolActivityProps) => import("react").JSX.Element;
38
+ export interface ApprovalCardProps extends ComponentPropsWithoutRef<'div'> {
39
+ approveLabel?: string;
40
+ disabled?: boolean;
41
+ label: string;
42
+ onResponse?: (detail: LumenApprovalResponseDetail) => void;
43
+ rejectLabel?: string;
44
+ requestId: string;
45
+ status?: LumenApprovalStatus;
46
+ statusLabel: string;
47
+ }
48
+ export declare const ApprovalCard: ({ approveLabel, children, className, disabled, label, onResponse, rejectLabel, requestId, status, statusLabel, ...props }: ApprovalCardProps) => import("react").JSX.Element;
49
+ //# sourceMappingURL=ai-surfaces.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"ai-surfaces.d.ts","sourceRoot":"","sources":["../src/ai-surfaces.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,wBAAwB,EAAE,SAAS,EAAE,MAAM,OAAO,CAAA;AAGhE,OAAO,EAKL,KAAK,2BAA2B,EAChC,KAAK,mBAAmB,EAExB,KAAK,uBAAuB,EAC5B,KAAK,iBAAiB,EACtB,KAAK,eAAe,EAKrB,MAAM,uBAAuB,CAAA;AAI9B,MAAM,WAAW,mBAAoB,SAAQ,IAAI,CAAC,wBAAwB,CAAC,MAAM,CAAC,EAAE,cAAc,CAAC;IACjG,OAAO,CAAC,EAAE,SAAS,CAAA;IACnB,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,QAAQ,CAAC,EAAE,OAAO,CAAA;IAClB,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,cAAc,CAAC,EAAE,CAAC,MAAM,EAAE,uBAAuB,KAAK,IAAI,CAAA;IAC1D,MAAM,CAAC,EAAE,MAAM,IAAI,CAAA;IACnB,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,IAAI,CAAA;IACvC,OAAO,CAAC,EAAE,OAAO,CAAA;IACjB,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,aAAa,CAAC,EAAE,OAAO,CAAA;IACvB,KAAK,CAAC,EAAE,MAAM,CAAA;CACf;AAMD,eAAO,MAAM,cAAc,GAAI,+LAI5B,mBAAmB,gCAmGrB,CAAA;AAED,MAAM,WAAW,kBAAmB,SAAQ,wBAAwB,CAAC,SAAS,CAAC;IAC7E,OAAO,CAAC,EAAE,SAAS,CAAA;IACnB,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,OAAO,CAAC,EAAE,SAAS,CAAA;IACnB,MAAM,CAAC,EAAE,iBAAiB,CAAA;IAC1B,WAAW,EAAE,MAAM,CAAA;CACpB;AAED,eAAO,MAAM,aAAa,GAAI,iFAAwG,kBAAkB,gCASvJ,CAAA;AAED,MAAM,WAAW,mBAAoB,SAAQ,IAAI,CAAC,wBAAwB,CAAC,GAAG,CAAC,EAAE,MAAM,CAAC;IAAG,IAAI,EAAE,MAAM,CAAC;IAAC,KAAK,EAAE,MAAM,CAAA;CAAE;AAExH,eAAO,MAAM,cAAc,GAAI,gDAAgD,mBAAmB,gCAgBjG,CAAA;AAED,MAAM,WAAW,iBAAkB,SAAQ,wBAAwB,CAAC,SAAS,CAAC;IAAG,KAAK,EAAE,MAAM,CAAC;IAAC,MAAM,CAAC,EAAE,eAAe,CAAC;IAAC,WAAW,EAAE,MAAM,CAAA;CAAE;AAE/I,eAAO,MAAM,YAAY,GAAI,+DAA0E,iBAAiB,gCAQvH,CAAA;AAED,MAAM,WAAW,iBAAkB,SAAQ,wBAAwB,CAAC,KAAK,CAAC;IACxE,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,QAAQ,CAAC,EAAE,OAAO,CAAA;IAClB,KAAK,EAAE,MAAM,CAAA;IACb,UAAU,CAAC,EAAE,CAAC,MAAM,EAAE,2BAA2B,KAAK,IAAI,CAAA;IAC1D,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,SAAS,EAAE,MAAM,CAAA;IACjB,MAAM,CAAC,EAAE,mBAAmB,CAAA;IAC5B,WAAW,EAAE,MAAM,CAAA;CACpB;AAED,eAAO,MAAM,YAAY,GAAI,2HAAsK,iBAAiB,gCAwCnN,CAAA"}
@@ -0,0 +1,88 @@
1
+ 'use client';
2
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
3
+ import { useEffect, useId, useRef, useState } from 'react';
4
+ import { bindLumenApprovalCard, canSubmitLumenPrompt, composeClassName, createLumenPromptComposerController, normalizeLumenPromptLimit, readLumenApprovalResponseDetail, readLumenPromptSubmitDetail, resolveLumenCitationHref } from '@santi020k/lumen-core';
5
+ import { Button, Card, Collapsible, Form, Label, Link, Message, Prose, Stack, Textarea } from './components.js';
6
+ const promptLabels = (label, sendLabel, stopLabel) => ({
7
+ label: label ?? 'Message', sendLabel: sendLabel ?? 'Send', stopLabel: stopLabel ?? 'Stop'
8
+ });
9
+ export const PromptComposer = ({ actions, children, className, defaultValue = '', disabled = false, id, label, maxLength, onPromptSubmit, onStop, onValueChange, pending = false, sendLabel, stopLabel, submitOnEnter = false, value, onReset, ...props }) => {
10
+ const generatedId = useId();
11
+ const inputId = id === undefined ? generatedId : `${id}-input`;
12
+ const [draft, setDraft] = useState(defaultValue);
13
+ const text = value ?? draft;
14
+ const limit = normalizeLumenPromptLimit(maxLength);
15
+ const formRef = useRef(null);
16
+ const controllerRef = useRef(null);
17
+ const labels = promptLabels(label, sendLabel, stopLabel);
18
+ useEffect(() => {
19
+ const form = formRef.current;
20
+ if (!form)
21
+ return;
22
+ controllerRef.current = createLumenPromptComposerController(form);
23
+ const submit = (event) => {
24
+ if (!('detail' in event))
25
+ return;
26
+ const detail = readLumenPromptSubmitDetail(event.detail);
27
+ if (detail && onPromptSubmit) {
28
+ event.preventDefault();
29
+ onPromptSubmit(detail);
30
+ }
31
+ };
32
+ const stop = () => {
33
+ onStop?.();
34
+ };
35
+ form.addEventListener('ui:prompt-submit', submit);
36
+ form.addEventListener('ui:prompt-stop', stop);
37
+ return () => {
38
+ controllerRef.current?.destroy();
39
+ controllerRef.current = null;
40
+ form.removeEventListener('ui:prompt-submit', submit);
41
+ form.removeEventListener('ui:prompt-stop', stop);
42
+ };
43
+ }, [onPromptSubmit, onStop]);
44
+ useEffect(() => {
45
+ controllerRef.current?.sync();
46
+ }, [text, limit, disabled, pending]);
47
+ return (_jsxs(Form, { ...props, id: id, ref: formRef, className: composeClassName('ui-prompt-composer', className), "data-disabled": String(disabled), "data-pending": String(pending), "data-submit-on-enter": String(submitOnEnter), "data-ui-prompt-composer": true, enhance: false, method: "post", onReset: event => {
48
+ onReset?.(event);
49
+ if (!event.defaultPrevented && value === undefined) {
50
+ setDraft(defaultValue);
51
+ onValueChange?.(defaultValue);
52
+ }
53
+ }, status: pending ? 'submitting' : 'idle', children: [_jsx(Label, { htmlFor: inputId, children: labels.label }), _jsx(Textarea, { id: inputId, "data-ui-prompt-input": true, disabled: disabled, maxLength: limit, name: "prompt", onChange: event => {
54
+ if (value === undefined)
55
+ setDraft(event.currentTarget.value);
56
+ onValueChange?.(event.currentTarget.value);
57
+ }, rows: 3, required: true, value: text }), _jsxs(Stack, { direction: "horizontal", gap: "related", wrap: true, children: [actions, _jsx(Button, { "data-ui-prompt-send": true, disabled: disabled || pending || !canSubmitLumenPrompt(text, limit), type: "submit", children: labels.sendLabel }), _jsx(Button, { "data-ui-prompt-stop": true, disabled: disabled, hidden: !pending, type: "button", variant: "secondary", children: labels.stopLabel })] }), children] }));
58
+ };
59
+ export const StreamMessage = ({ actions, children, className, label = 'Assistant', sources, status = 'idle', statusLabel, ...props }) => (_jsxs(Message, { ...props, "aria-label": label, className: composeClassName('ui-stream-message', className), "data-status": status, from: "assistant", children: [_jsx(Prose, { "aria-busy": status === 'streaming', "aria-live": "off", "data-ui-stream-content": true, children: children }), _jsxs(Stack, { direction: "horizontal", gap: "related", wrap: true, children: [_jsx("span", { "aria-live": "polite", role: "status", children: statusLabel }), actions] }), sources] }));
60
+ export const SourceCitation = ({ children, className, href, label, ...props }) => {
61
+ const safeHref = resolveLumenCitationHref(href);
62
+ return safeHref ?
63
+ (_jsxs(Link, { ...props, className: composeClassName('ui-source-citation', className), href: safeHref, rel: "noopener noreferrer", children: [label, children] })) :
64
+ (_jsxs("span", { className: composeClassName('ui-source-citation', className), children: [label, children] }));
65
+ };
66
+ export const ToolActivity = ({ children, className, label, status = 'queued', statusLabel, ...props }) => (_jsxs(Collapsible, { ...props, className: composeClassName('ui-tool-activity', className), "data-status": status, children: [_jsx("summary", { children: label }), _jsxs(Stack, { gap: "related", children: [_jsx("span", { role: "status", children: statusLabel }), children] })] }));
67
+ export const ApprovalCard = ({ approveLabel = 'Approve', children, className, disabled = false, label, onResponse, rejectLabel = 'Reject', requestId, status = 'pending', statusLabel, ...props }) => {
68
+ const ref = useRef(null);
69
+ useEffect(() => {
70
+ const root = ref.current;
71
+ if (!root)
72
+ return;
73
+ const cleanup = bindLumenApprovalCard(root);
74
+ const respond = (event) => {
75
+ if (!('detail' in event))
76
+ return;
77
+ const detail = readLumenApprovalResponseDetail(event.detail);
78
+ if (detail)
79
+ onResponse?.(detail);
80
+ };
81
+ root.addEventListener('ui:approval-response', respond);
82
+ return () => {
83
+ cleanup();
84
+ root.removeEventListener('ui:approval-response', respond);
85
+ };
86
+ }, [onResponse]);
87
+ return (_jsx(Card, { ...props, ref: ref, "aria-label": label, className: composeClassName('ui-approval-card', className), "data-disabled": String(disabled), "data-request-id": requestId, "data-status": status, "data-ui-approval-card": true, children: _jsxs(Stack, { gap: "group", children: [_jsx("strong", { children: label }), children, _jsx("span", { role: "status", children: statusLabel }), _jsxs(Stack, { direction: "horizontal", gap: "related", wrap: true, children: [_jsx(Button, { "data-ui-approval-response": "approve", disabled: disabled || status !== 'pending', type: "button", children: approveLabel }), _jsx(Button, { "data-ui-approval-response": "reject", disabled: disabled || status !== 'pending', type: "button", variant: "secondary", children: rejectLabel })] })] }) }));
88
+ };
@@ -0,0 +1,11 @@
1
+ import type { ComponentPropsWithRef } from 'react';
2
+ import { type LumenAmountChangeDetail, type LumenAmountOptions } from '@santi020k/lumen-core';
3
+ export interface AmountFieldProps extends Omit<ComponentPropsWithRef<'input'>, 'value' | 'defaultValue' | 'type' | 'min' | 'max' | 'step'>, LumenAmountOptions {
4
+ value?: string;
5
+ defaultValue?: string;
6
+ invalidMessage?: string;
7
+ onValueChange?: (draft: string, detail: LumenAmountChangeDetail) => void;
8
+ }
9
+ /** Formatting owns no currency conversion, rounding or domain validation. */
10
+ export declare const AmountField: ({ value, defaultValue, locale, fractionDigits, allowNegative, invalidMessage, onValueChange, name, form, disabled, readOnly, className, ...props }: AmountFieldProps) => import("react").JSX.Element;
11
+ //# sourceMappingURL=amount-field.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"amount-field.d.ts","sourceRoot":"","sources":["../src/amount-field.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,OAAO,CAAA;AAGlD,OAAO,EAAmG,KAAK,uBAAuB,EAAmC,KAAK,kBAAkB,EAAE,MAAM,uBAAuB,CAAA;AAE/N,MAAM,WAAW,gBAAiB,SAAQ,IAAI,CAAC,qBAAqB,CAAC,OAAO,CAAC,EAAE,OAAO,GAAG,cAAc,GAAG,MAAM,GAAG,KAAK,GAAG,KAAK,GAAG,MAAM,CAAC,EAAE,kBAAkB;IAC5J,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,cAAc,CAAC,EAAE,MAAM,CAAA;IACvB,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,EAAE,MAAM,EAAE,uBAAuB,KAAK,IAAI,CAAA;CACzE;AAED,6EAA6E;AAC7E,eAAO,MAAM,WAAW,GAAI,oJAA+K,gBAAgB,gCA0D1N,CAAA"}
@@ -0,0 +1,37 @@
1
+ 'use client';
2
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
3
+ import { useLayoutEffect, useRef, useState } from 'react';
4
+ import { composeClassName, createLumenAmountFieldController, formatLumenAmountDraft, getLumenAmountValue } from '@santi020k/lumen-core';
5
+ /** Formatting owns no currency conversion, rounding or domain validation. */
6
+ export const AmountField = ({ value, defaultValue = '', locale = 'en-US', fractionDigits = 2, allowNegative = false, invalidMessage, onValueChange, name, form, disabled, readOnly, className, ...props }) => {
7
+ const rootRef = useRef(null);
8
+ const controllerRef = useRef(undefined);
9
+ const latestRef = useRef({ value, onValueChange });
10
+ const options = { locale, fractionDigits, allowNegative };
11
+ const initial = value ?? defaultValue;
12
+ const [draft, setDraft] = useState(initial);
13
+ useLayoutEffect(() => {
14
+ latestRef.current = { value, onValueChange };
15
+ });
16
+ useLayoutEffect(() => {
17
+ const root = rootRef.current;
18
+ if (!root)
19
+ return;
20
+ const controller = createLumenAmountFieldController(root, detail => {
21
+ setDraft(detail.draft);
22
+ latestRef.current.onValueChange?.(detail.draft, detail);
23
+ if (latestRef.current.value !== undefined)
24
+ controller.setValue(latestRef.current.value);
25
+ });
26
+ controllerRef.current = controller;
27
+ return () => {
28
+ controller.destroy();
29
+ controllerRef.current = undefined;
30
+ };
31
+ }, [locale, fractionDigits, allowNegative, form]);
32
+ useLayoutEffect(() => {
33
+ if (value !== undefined)
34
+ controllerRef.current?.setValue(value);
35
+ }, [value]);
36
+ return (_jsxs("span", { ref: rootRef, "data-ui-amount-field": true, locale, 'fraction-digits': String(fractionDigits), 'allow-negative': allowNegative ? '' : undefined, value: value ?? draft, 'default-value': defaultValue, 'invalid-message': invalidMessage, children: [_jsx("input", { ...props, className: composeClassName('ui-input ui-amount-field', className), defaultValue: formatLumenAmountDraft(initial, options), "data-ui-amount-input": true, disabled: disabled, readOnly: readOnly, form: form, type: "text", inputMode: "decimal" }), _jsx("input", { "data-ui-amount-value": true, type: "hidden", name: name, form: form, disabled: disabled, value: getLumenAmountValue(value ?? draft) ?? '' })] }));
37
+ };
@@ -0,0 +1,17 @@
1
+ import type { ComponentPropsWithRef, ReactNode } from 'react';
2
+ import { type LumenAttachmentPreviewLabels, type LumenAttachmentPreviewState } from '@santi020k/lumen-core';
3
+ export interface AttachmentPreviewProps extends ComponentPropsWithRef<'figure'> {
4
+ actions?: ReactNode;
5
+ alt: string;
6
+ caption?: ReactNode;
7
+ contentType?: string;
8
+ labels?: Partial<LumenAttachmentPreviewLabels>;
9
+ onStateChange?: (state: LumenAttachmentPreviewState) => void;
10
+ retryKey?: number | string;
11
+ src?: string;
12
+ state?: LumenAttachmentPreviewState;
13
+ }
14
+ export declare const AttachmentPreview: ({ actions, alt, caption, children, className, contentType, labels, onStateChange, retryKey, src, state: requested, ...props }: AttachmentPreviewProps) => import("react").JSX.Element;
15
+ export type AttachmentListProps = ComponentPropsWithRef<'ul'>;
16
+ export declare const AttachmentList: ({ className, ...props }: AttachmentListProps) => import("react").JSX.Element;
17
+ //# sourceMappingURL=attachments.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"attachments.d.ts","sourceRoot":"","sources":["../src/attachments.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,qBAAqB,EAAE,SAAS,EAAE,MAAM,OAAO,CAAA;AAG7D,OAAO,EAEL,KAAK,4BAA4B,EAEjC,KAAK,2BAA2B,EAEjC,MAAM,uBAAuB,CAAA;AAI9B,MAAM,WAAW,sBAAuB,SAAQ,qBAAqB,CAAC,QAAQ,CAAC;IAC7E,OAAO,CAAC,EAAE,SAAS,CAAA;IACnB,GAAG,EAAE,MAAM,CAAA;IACX,OAAO,CAAC,EAAE,SAAS,CAAA;IACnB,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,MAAM,CAAC,EAAE,OAAO,CAAC,4BAA4B,CAAC,CAAA;IAC9C,aAAa,CAAC,EAAE,CAAC,KAAK,EAAE,2BAA2B,KAAK,IAAI,CAAA;IAC5D,QAAQ,CAAC,EAAE,MAAM,GAAG,MAAM,CAAA;IAC1B,GAAG,CAAC,EAAE,MAAM,CAAA;IACZ,KAAK,CAAC,EAAE,2BAA2B,CAAA;CACpC;AAED,eAAO,MAAM,iBAAiB,GAAI,+HAG/B,sBAAsB,gCAwCxB,CAAA;AAED,MAAM,MAAM,mBAAmB,GAAG,qBAAqB,CAAC,IAAI,CAAC,CAAA;AAC7D,eAAO,MAAM,cAAc,GAAI,yBAAyB,mBAAmB,gCAE1E,CAAA"}
@@ -0,0 +1,23 @@
1
+ 'use client';
2
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
3
+ import { useEffect, useRef, useState } from 'react';
4
+ import { composeClassName, lumenAttachmentPreviewLabels, resolveLumenAttachmentPreviewState } from '@santi020k/lumen-core';
5
+ import { Image } from './components.js';
6
+ export const AttachmentPreview = ({ actions, alt, caption, children, className, contentType, labels, onStateChange, retryKey, src, state: requested, ...props }) => {
7
+ const [failure, setFailure] = useState(null);
8
+ const failed = failure !== null && failure.src === src && failure.key === retryKey;
9
+ const state = resolveLumenAttachmentPreviewState(src, contentType, requested, failed);
10
+ const previousStateRef = useRef(state);
11
+ useEffect(() => {
12
+ if (previousStateRef.current !== state) {
13
+ previousStateRef.current = state;
14
+ onStateChange?.(state);
15
+ }
16
+ }, [onStateChange, state]);
17
+ const canPreview = resolveLumenAttachmentPreviewState(src, contentType) === 'ready';
18
+ const copy = { ...lumenAttachmentPreviewLabels, ...labels };
19
+ return (_jsxs("figure", { ...props, className: composeClassName('ui-attachment-preview', className), "aria-busy": state === 'loading', "data-state": state, children: [_jsx("div", { "data-slot": "attachment-preview-media", hidden: state !== 'ready', children: canPreview && (_jsx(Image, { src: src, alt: alt, fit: "contain", radius: "none", loading: "eager", onError: () => {
20
+ setFailure({ src, key: retryKey });
21
+ } }, `${src ?? ''}:${retryKey ?? ''}`)) }), _jsx("p", { role: "status", "data-slot": "attachment-preview-fallback", hidden: state === 'ready', children: state === 'ready' ? '' : copy[state] }), caption && _jsx("figcaption", { children: caption }), children, actions && _jsx("div", { "data-slot": "attachment-preview-actions", children: actions })] }));
22
+ };
23
+ export const AttachmentList = ({ className, ...props }) => (_jsx("ul", { ...props, className: composeClassName('ui-attachment-list', className), "data-slot": "attachment-list" }));
@@ -0,0 +1,14 @@
1
+ import { type LumenBulletOptions, type LumenChartLabels, type LumenChartTone } from '@santi020k/lumen-core';
2
+ import { type ChartProps } from './components.js';
3
+ export interface BulletChartProps extends Omit<ChartProps, 'children' | 'value'>, LumenBulletOptions {
4
+ formatValue?: (value: number) => string;
5
+ labels?: Partial<LumenChartLabels>;
6
+ showTable?: boolean;
7
+ target: number;
8
+ targetLabel?: string;
9
+ tone?: LumenChartTone;
10
+ value: number | null;
11
+ valueLabel?: string;
12
+ }
13
+ export declare const BulletChart: (props: BulletChartProps) => import("react").JSX.Element;
14
+ //# sourceMappingURL=bullet-chart.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"bullet-chart.d.ts","sourceRoot":"","sources":["../src/bullet-chart.tsx"],"names":[],"mappings":"AAEA,OAAO,EAIL,KAAK,kBAAkB,EACvB,KAAK,gBAAgB,EACrB,KAAK,cAAc,EAEpB,MAAM,uBAAuB,CAAA;AAE9B,OAAO,EAAS,KAAK,UAAU,EAAE,MAAM,iBAAiB,CAAA;AAExD,MAAM,WAAW,gBAAiB,SAAQ,IAAI,CAAC,UAAU,EAAE,UAAU,GAAG,OAAO,CAAC,EAAE,kBAAkB;IAClG,WAAW,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,MAAM,CAAA;IACvC,MAAM,CAAC,EAAE,OAAO,CAAC,gBAAgB,CAAC,CAAA;IAClC,SAAS,CAAC,EAAE,OAAO,CAAA;IACnB,MAAM,EAAE,MAAM,CAAA;IACd,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,IAAI,CAAC,EAAE,cAAc,CAAA;IACrB,KAAK,EAAE,MAAM,GAAG,IAAI,CAAA;IACpB,UAAU,CAAC,EAAE,MAAM,CAAA;CACpB;AAyGD,eAAO,MAAM,WAAW,GAAI,OAAO,gBAAgB,gCAElD,CAAA"}
@@ -0,0 +1,22 @@
1
+ 'use client';
2
+ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
3
+ import { composeClassName, createLumenBulletGeometry, getLumenChartToneClassName, resolveLumenChartLabels } from '@santi020k/lumen-core';
4
+ import { Chart } from './components.js';
5
+ const resolveBulletProps = (props) => ({
6
+ ...props,
7
+ formatValue: props.formatValue ?? String,
8
+ showTable: props.showTable ?? true,
9
+ targetLabel: props.targetLabel ?? 'Target',
10
+ tone: props.tone ?? 'series-1'
11
+ });
12
+ const BulletContent = ({ className, domain, formatValue, labels, ranges, showTable, summary, target, targetLabel, tone, value, valueLabel, ...props }) => {
13
+ const text = resolveLumenChartLabels(labels);
14
+ const model = createLumenBulletGeometry(value, target, { domain, ranges });
15
+ const title = valueLabel ?? text.value;
16
+ const actual = model.valid && value !== null ? formatValue(value) : text.notAvailable;
17
+ const factual = model.valid ? `${title}: ${actual}. ${targetLabel}: ${formatValue(target)}.` : text.invalidData;
18
+ return (_jsx(Chart, { ...props, className: className, summary: summary ?? factual, children: model.valid ?
19
+ (_jsxs(_Fragment, { children: [_jsxs("div", { className: "ui-bullet-chart__values", children: [_jsxs("div", { children: [_jsx("span", { children: title }), _jsx("strong", { children: actual })] }), _jsxs("p", { children: [_jsx("span", { className: "ui-bullet-chart__target-key", "aria-hidden": "true" }), targetLabel, _jsx("strong", { children: formatValue(target) })] })] }), _jsxs("div", { "aria-hidden": "true", className: "ui-bullet-chart__plot", children: [_jsxs("div", { className: "ui-bullet-chart__track", children: [model.ranges.map((range, index) => (_jsx("span", { className: composeClassName('ui-bullet-chart__range', getLumenChartToneClassName(range.tone ?? 'neutral')), style: { left: `${range.startRatio * 100}%`, width: `${(range.endRatio - range.startRatio) * 100}%`, opacity: 0.08 + index / Math.max(1, model.ranges.length - 1) * 0.14 } }, range.end))), value !== null && _jsx("span", { className: composeClassName('ui-bullet-chart__bar', getLumenChartToneClassName(tone)), style: { left: `${model.valueStartRatio * 100}%`, width: `${model.valueWidthRatio * 100}%` } }), _jsx("span", { className: "ui-bullet-chart__target", style: { left: `${model.targetRatio * 100}%` } })] }), _jsx("div", { className: "ui-bullet-chart__ticks", children: model.ticks.map(tick => _jsx("span", { children: formatValue(tick.value) }, tick.position)) })] }), model.ranges.length > 0 && (_jsx("ul", { className: "ui-bullet-chart__ranges", children: model.ranges.map(range => (_jsxs("li", { className: getLumenChartToneClassName(range.tone ?? 'neutral'), children: [_jsx("span", { children: range.label }), _jsxs("span", { children: [formatValue(range.start), "\u2013", formatValue(range.end)] })] }, range.end))) })), showTable && (_jsxs("details", { className: "ui-chart__data", children: [_jsx("summary", { children: text.viewData }), _jsx("div", { role: "group", tabIndex: 0, "aria-label": text.chartData, children: _jsxs("table", { children: [_jsx("thead", { children: _jsxs("tr", { children: [_jsx("th", { scope: "col", children: text.category }), _jsx("th", { scope: "col", children: text.value })] }) }), _jsxs("tbody", { children: [_jsxs("tr", { children: [_jsx("th", { scope: "row", children: title }), _jsx("td", { children: actual })] }), _jsxs("tr", { children: [_jsx("th", { scope: "row", children: targetLabel }), _jsx("td", { children: formatValue(target) })] }), model.ranges.map(range => (_jsxs("tr", { children: [_jsx("th", { scope: "row", children: range.label }), _jsxs("td", { children: [formatValue(range.start), "\u2013", formatValue(range.end)] })] }, range.end)))] })] }) })] }))] })) :
20
+ _jsx("p", { className: "ui-chart__empty", role: "status", children: text.invalidData }) }));
21
+ };
22
+ export const BulletChart = (props) => (_jsx(BulletContent, { ...resolveBulletProps(props), className: composeClassName('ui-bullet-chart', props.className) }));
@@ -0,0 +1,14 @@
1
+ import type { ComponentPropsWithRef } from 'react';
2
+ import { type LumenChangeSummaryItem } from '@santi020k/lumen-core';
3
+ export interface ChangeSummaryProps extends ComponentPropsWithRef<'section'> {
4
+ items?: readonly LumenChangeSummaryItem[];
5
+ label?: string;
6
+ beforeLabel?: string;
7
+ afterLabel?: string;
8
+ changedLabel?: string;
9
+ unchangedLabel?: string;
10
+ /** Localized count text, supplied by the host. */
11
+ summary?: string;
12
+ }
13
+ export declare const ChangeSummary: ({ items, label, beforeLabel, afterLabel, changedLabel, unchangedLabel, summary, className, children, ...props }: ChangeSummaryProps) => import("react").JSX.Element;
14
+ //# sourceMappingURL=change-summary.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"change-summary.d.ts","sourceRoot":"","sources":["../src/change-summary.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,qBAAqB,EAAE,MAAM,OAAO,CAAA;AAElD,OAAO,EAAoB,KAAK,sBAAsB,EAAE,MAAM,uBAAuB,CAAA;AAErF,MAAM,WAAW,kBAAmB,SAAQ,qBAAqB,CAAC,SAAS,CAAC;IAC1E,KAAK,CAAC,EAAE,SAAS,sBAAsB,EAAE,CAAA;IACzC,KAAK,CAAC,EAAE,MAAM,CAAA;IACd,WAAW,CAAC,EAAE,MAAM,CAAA;IACpB,UAAU,CAAC,EAAE,MAAM,CAAA;IACnB,YAAY,CAAC,EAAE,MAAM,CAAA;IACrB,cAAc,CAAC,EAAE,MAAM,CAAA;IACvB,kDAAkD;IAClD,OAAO,CAAC,EAAE,MAAM,CAAA;CACjB;AAID,eAAO,MAAM,aAAa,GAAI,iHAG3B,kBAAkB,gCAwBpB,CAAA"}
@@ -0,0 +1,4 @@
1
+ import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
2
+ import { composeClassName } from '@santi020k/lumen-core';
3
+ const noChanges = [];
4
+ export const ChangeSummary = ({ items = noChanges, label = 'Changes', beforeLabel = 'Before', afterLabel = 'After', changedLabel = 'Changed', unchangedLabel = 'Unchanged', summary, className, children, ...props }) => (_jsxs("section", { className: composeClassName('ui-change-summary', className), "aria-label": label, ...props, children: [_jsx("h3", { className: "ui-change-summary__heading", children: label }), summary && _jsx("p", { className: "ui-change-summary__summary", children: summary }), _jsx("dl", { className: "ui-change-summary__list", children: items.map(item => (_jsxs("div", { className: "ui-change-summary__item", "data-changed": item.changed, children: [_jsxs("dt", { children: [item.label, _jsx("span", { className: "ui-change-summary__state", children: item.changed ? changedLabel : unchangedLabel })] }), _jsxs("dd", { children: [_jsx("span", { className: "ui-change-summary__value-label", children: beforeLabel }), item.before] }), _jsxs("dd", { children: [_jsx("span", { className: "ui-change-summary__value-label", children: afterLabel }), item.after] })] }, item.id))) }), children] }));
@@ -0,0 +1,10 @@
1
+ import { type createLumenLineChartModel, type LumenChartLabels } from '@santi020k/lumen-core';
2
+ interface ChartInspectionProps {
3
+ formatCategory?: (value: number | string) => string;
4
+ formatValue: (value: number) => string;
5
+ labels: Readonly<LumenChartLabels>;
6
+ model: ReturnType<typeof createLumenLineChartModel>;
7
+ }
8
+ export declare const ChartInspection: ({ formatCategory, formatValue, labels, model }: ChartInspectionProps) => import("react").JSX.Element;
9
+ export {};
10
+ //# sourceMappingURL=chart-inspection.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"chart-inspection.d.ts","sourceRoot":"","sources":["../src/chart-inspection.tsx"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,yBAAyB,EAA0D,KAAK,gBAAgB,EAAE,MAAM,uBAAuB,CAAA;AAErJ,UAAU,oBAAoB;IAC5B,cAAc,CAAC,EAAE,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM,KAAK,MAAM,CAAA;IACnD,WAAW,EAAE,CAAC,KAAK,EAAE,MAAM,KAAK,MAAM,CAAA;IACtC,MAAM,EAAE,QAAQ,CAAC,gBAAgB,CAAC,CAAA;IAClC,KAAK,EAAE,UAAU,CAAC,OAAO,yBAAyB,CAAC,CAAA;CACpD;AAED,eAAO,MAAM,eAAe,GAAI,gDAAgD,oBAAoB,gCAmCnG,CAAA"}
@@ -0,0 +1,11 @@
1
+ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
+ import { getLumenChartCategoryLabel, getLumenChartToneClassName } from '@santi020k/lumen-core';
3
+ export const ChartInspection = ({ formatCategory, formatValue, labels, model }) => {
4
+ const lookup = model.series.map(series => new Map(series.data.map(datum => [datum.x, datum])));
5
+ return (_jsxs(_Fragment, { children: [_jsx("div", { className: "ui-chart__inspection", "data-ui-chart-inspection": true, hidden: true, children: model.categories.map((category, index) => (_jsxs("div", { "data-ui-chart-point": JSON.stringify(category), "data-ui-chart-position": model.positions[index], hidden: true, children: [_jsx("strong", { children: getLumenChartCategoryLabel(model.series, category, formatCategory, 'detail') }), model.series.map((series, seriesIndex) => {
6
+ const value = lookup[seriesIndex]?.get(category)?.y;
7
+ return (_jsxs("span", { className: getLumenChartToneClassName(series.tone, seriesIndex), "data-ui-chart-series-value": series.id, children: [_jsx("i", { "aria-hidden": "true" }), series.label, ' ', _jsx("b", { children: value === null || value === undefined || !Number.isFinite(value) ?
8
+ labels.notAvailable :
9
+ formatValue(value) })] }, series.id));
10
+ })] }, `${typeof category}:${category}`))) }), _jsx("p", { "aria-live": "polite", "aria-atomic": "true", className: "ui-sr-only", "data-ui-chart-announcement": true })] }));
11
+ };
@@ -0,0 +1,17 @@
1
+ import { type ReactNode } from 'react';
2
+ import { type createLumenLineChartModel, type LumenChartCursorChangeDetail } from '@santi020k/lumen-core';
3
+ export interface ChartInteractionProps {
4
+ interactive?: boolean;
5
+ onCursorChange?: (detail: LumenChartCursorChangeDetail) => void;
6
+ /** A stable X identity; null clears the cursor. */
7
+ cursor?: number | string | null;
8
+ syncGroup?: string;
9
+ }
10
+ interface ChartInteractionContainerProps extends ChartInteractionProps {
11
+ children: ReactNode;
12
+ showLegend: boolean;
13
+ model: ReturnType<typeof createLumenLineChartModel>;
14
+ }
15
+ export declare const ChartInteraction: ({ children, model, showLegend, syncGroup, ...props }: ChartInteractionContainerProps) => import("react").JSX.Element;
16
+ export {};
17
+ //# sourceMappingURL=chart-interaction.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"chart-interaction.d.ts","sourceRoot":"","sources":["../src/chart-interaction.tsx"],"names":[],"mappings":"AAEA,OAAO,EAAE,KAAK,SAAS,EAAqB,MAAM,OAAO,CAAA;AAEzD,OAAO,EAEL,KAAK,yBAAyB,EAC9B,KAAK,4BAA4B,EAElC,MAAM,uBAAuB,CAAA;AAE9B,MAAM,WAAW,qBAAqB;IACpC,WAAW,CAAC,EAAE,OAAO,CAAA;IACrB,cAAc,CAAC,EAAE,CAAC,MAAM,EAAE,4BAA4B,KAAK,IAAI,CAAA;IAC/D,mDAAmD;IACnD,MAAM,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,IAAI,CAAA;IAC/B,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB;AAyDD,UAAU,8BAA+B,SAAQ,qBAAqB;IACpE,QAAQ,EAAE,SAAS,CAAA;IACnB,UAAU,EAAE,OAAO,CAAA;IACnB,KAAK,EAAE,UAAU,CAAC,OAAO,yBAAyB,CAAC,CAAA;CACpD;AAED,eAAO,MAAM,gBAAgB,GAAI,sDAE9B,8BAA8B,gCAQhC,CAAA"}
@@ -0,0 +1,50 @@
1
+ 'use client';
2
+ import { jsx as _jsx } from "react/jsx-runtime";
3
+ import { useEffect, useRef } from 'react';
4
+ import { createLumenChartInteractionController } from '@santi020k/lumen-core';
5
+ const useChartInteraction = ({ cursor, interactive, onCursorChange }, bindingKey) => {
6
+ const ref = useRef(null);
7
+ const controllerRef = useRef(null);
8
+ useEffect(() => {
9
+ if (!interactive || !ref.current)
10
+ return;
11
+ const root = ref.current;
12
+ const instance = createLumenChartInteractionController(root);
13
+ controllerRef.current = instance;
14
+ return () => {
15
+ instance.destroy();
16
+ controllerRef.current = null;
17
+ };
18
+ }, [interactive, bindingKey]);
19
+ useEffect(() => {
20
+ controllerRef.current?.setControlledCursor(cursor);
21
+ }, [cursor, interactive, bindingKey]);
22
+ useEffect(() => {
23
+ const root = ref.current;
24
+ if (!root || !onCursorChange)
25
+ return;
26
+ const CustomEventType = root.ownerDocument.defaultView?.CustomEvent;
27
+ const listener = (event) => {
28
+ if (!CustomEventType || !(event instanceof CustomEventType))
29
+ return;
30
+ const detail = event.detail;
31
+ if (detail === null || typeof detail !== 'object' || !('x' in detail))
32
+ return;
33
+ const x = detail.x;
34
+ if (x === null || typeof x === 'string' || (typeof x === 'number' && Number.isFinite(x)))
35
+ onCursorChange({ x });
36
+ };
37
+ root.addEventListener('ui:chart-cursor-change', listener);
38
+ return () => {
39
+ root.removeEventListener('ui:chart-cursor-change', listener);
40
+ };
41
+ }, [onCursorChange]);
42
+ return ref;
43
+ };
44
+ export const ChartInteraction = ({ children, model, showLegend, syncGroup, ...props }) => {
45
+ const bindingKey = JSON.stringify([
46
+ model.categories, model.positions, model.series.map(series => series.id), showLegend, syncGroup
47
+ ]);
48
+ const ref = useChartInteraction(props, bindingKey);
49
+ return _jsx("div", { className: "ui-chart__content", "data-ui-chart-sync": syncGroup, ref: ref, children: children });
50
+ };
@@ -0,0 +1,3 @@
1
+ import type { ReactNode } from 'react';
2
+ export declare const getChartPlotLabel: (label: string | undefined, heading: ReactNode, fallback: string) => string;
3
+ //# sourceMappingURL=chart-label.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"chart-label.d.ts","sourceRoot":"","sources":["../src/chart-label.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,SAAS,EAAE,MAAM,OAAO,CAAA;AAEtC,eAAO,MAAM,iBAAiB,GAC5B,OAAO,MAAM,GAAG,SAAS,EAAE,SAAS,SAAS,EAAE,UAAU,MAAM,KAC9D,MAAqE,CAAA"}
@@ -0,0 +1 @@
1
+ export const getChartPlotLabel = (label, heading, fallback) => label ?? (typeof heading === 'string' ? heading : fallback);
@@ -1,2 +1,10 @@
1
+ import { type LumenChartDatumActivationDetail, type LumenChartLabels } from '@santi020k/lumen-core';
2
+ export interface ReactChartDatumAction {
3
+ key: string;
4
+ label: string;
5
+ serialized: string;
6
+ }
7
+ export declare const createReactChartDatumAction: (detail: LumenChartDatumActivationDetail | null, context: string, labels: Readonly<LumenChartLabels>) => ReactChartDatumAction | null;
8
+ export declare const readReactChartDatumActivation: (root: HTMLElement, target: EventTarget | null) => LumenChartDatumActivationDetail | null;
1
9
  export declare const formatReactChartTableValue: (value: number | null | undefined, formatValue: (value: number) => string, notAvailable?: string) => string;
2
10
  //# sourceMappingURL=chart-recipes.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"chart-recipes.d.ts","sourceRoot":"","sources":["../src/chart-recipes.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,0BAA0B,GACrC,OAAO,MAAM,GAAG,IAAI,GAAG,SAAS,EAChC,aAAa,CAAC,KAAK,EAAE,MAAM,KAAK,MAAM,EACtC,qBAA8B,KAC7B,MAEiB,CAAA"}
1
+ {"version":3,"file":"chart-recipes.d.ts","sourceRoot":"","sources":["../src/chart-recipes.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,KAAK,+BAA+B,EAAE,KAAK,gBAAgB,EAAkC,MAAM,uBAAuB,CAAA;AAEnI,MAAM,WAAW,qBAAqB;IACpC,GAAG,EAAE,MAAM,CAAA;IACX,KAAK,EAAE,MAAM,CAAA;IACb,UAAU,EAAE,MAAM,CAAA;CACnB;AAUD,eAAO,MAAM,2BAA2B,GACtC,QAAQ,+BAA+B,GAAG,IAAI,EAC9C,SAAS,MAAM,EACf,QAAQ,QAAQ,CAAC,gBAAgB,CAAC,KACjC,qBAAqB,GAAG,IAMrB,CAAA;AAEN,eAAO,MAAM,6BAA6B,GACxC,MAAM,WAAW,EACjB,QAAQ,WAAW,GAAG,IAAI,KACzB,+BAA+B,GAAG,IAsBpC,CAAA;AAED,eAAO,MAAM,0BAA0B,GACrC,OAAO,MAAM,GAAG,IAAI,GAAG,SAAS,EAChC,aAAa,CAAC,KAAK,EAAE,MAAM,KAAK,MAAM,EACtC,qBAA8B,KAC7B,MAEiB,CAAA"}
@@ -1,3 +1,38 @@
1
+ import { parseLumenChartDatumActivation } from '@santi020k/lumen-core';
2
+ const datumActionKey = (detail) => {
3
+ if (detail.kind === 'series')
4
+ return JSON.stringify([detail.kind, detail.seriesId, detail.x, detail.datumId]);
5
+ if (detail.kind === 'heatmap')
6
+ return JSON.stringify([detail.kind, detail.x, detail.y, detail.datumId]);
7
+ return JSON.stringify([detail.kind, detail.x, detail.datumId]);
8
+ };
9
+ export const createReactChartDatumAction = (detail, context, labels) => detail ?
10
+ {
11
+ key: datumActionKey(detail),
12
+ label: labels.formatDatumAction(context),
13
+ serialized: JSON.stringify(detail)
14
+ } :
15
+ null;
16
+ export const readReactChartDatumActivation = (root, target) => {
17
+ const ElementType = root.ownerDocument.defaultView?.Element;
18
+ if (!root.isConnected || !ElementType || !(target instanceof ElementType))
19
+ return null;
20
+ const element = target.closest('[data-ui-chart-datum]');
21
+ if (element?.closest('[data-ui-chart-activation]') !== root)
22
+ return null;
23
+ if (element.closest('[inert], [hidden], [disabled], [aria-disabled="true"]'))
24
+ return null;
25
+ const serialized = element.getAttribute('data-ui-chart-datum');
26
+ if (!serialized)
27
+ return null;
28
+ try {
29
+ const input = JSON.parse(serialized);
30
+ return parseLumenChartDatumActivation(input);
31
+ }
32
+ catch {
33
+ return null;
34
+ }
35
+ };
1
36
  export const formatReactChartTableValue = (value, formatValue, notAvailable = 'Not available') => value === null || value === undefined || !Number.isFinite(value) ?
2
37
  notAvailable :
3
38
  formatValue(value);
@@ -0,0 +1,9 @@
1
+ import type { ComponentPropsWithoutRef, ReactNode } from 'react';
2
+ export interface ComboboxProps extends ComponentPropsWithoutRef<'input'> {
3
+ label?: ReactNode;
4
+ list: string;
5
+ options?: string[];
6
+ wrapperClassName?: string;
7
+ }
8
+ export declare const Combobox: ({ className, defaultValue, disabled, readOnly, form, id, label, list, onBlur, onChange, onFocus, onKeyDown, options: rawOptions, type, value: valueProp, wrapperClassName, ...props }: ComboboxProps) => import("react").JSX.Element;
9
+ //# sourceMappingURL=combobox.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"combobox.d.ts","sourceRoot":"","sources":["../src/combobox.tsx"],"names":[],"mappings":"AAEA,OAAO,KAAK,EAAE,wBAAwB,EAAiB,SAAS,EAAE,MAAM,OAAO,CAAA;AA0B/E,MAAM,WAAW,aAAc,SAAQ,wBAAwB,CAAC,OAAO,CAAC;IACtE,KAAK,CAAC,EAAE,SAAS,CAAA;IACjB,IAAI,EAAE,MAAM,CAAA;IACZ,OAAO,CAAC,EAAE,MAAM,EAAE,CAAA;IAClB,gBAAgB,CAAC,EAAE,MAAM,CAAA;CAC1B;AAED,eAAO,MAAM,QAAQ,GAAI,uLAkBtB,aAAa,gCA0Of,CAAA"}