@zvk/ui 0.1.3 → 0.1.6
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.
- package/CHANGELOG.md +41 -0
- package/README.md +5 -5
- package/dist/components/accordion/accordion.js +4 -4
- package/dist/components/alert/alert.d.ts +5 -0
- package/dist/components/alert/alert.js +8 -4
- package/dist/components/alert/index.d.ts +1 -1
- package/dist/components/alert-dialog/alert-dialog.d.ts +8 -5
- package/dist/components/alert-dialog/alert-dialog.js +26 -13
- package/dist/components/avatar/avatar.js +1 -1
- package/dist/components/badge/badge.js +1 -1
- package/dist/components/breadcrumbs/breadcrumbs.js +3 -3
- package/dist/components/button/button.d.ts +3 -2
- package/dist/components/button/button.js +50 -2
- package/dist/components/calendar/calendar.d.ts +40 -5
- package/dist/components/calendar/calendar.js +17 -5
- package/dist/components/calendar/index.d.ts +1 -1
- package/dist/components/card/card.d.ts +5 -0
- package/dist/components/card/card.js +11 -7
- package/dist/components/card/index.d.ts +1 -1
- package/dist/components/carousel/carousel.js +7 -7
- package/dist/components/checkbox/checkbox.js +4 -4
- package/dist/components/code-block/code-block.js +2 -2
- package/dist/components/collapsible/collapsible.d.ts +3 -2
- package/dist/components/collapsible/collapsible.js +8 -4
- package/dist/components/combobox/combobox.js +6 -5
- package/dist/components/command/command-filter.d.ts +0 -1
- package/dist/components/command/command-filter.js +0 -3
- package/dist/components/command/command.d.ts +11 -4
- package/dist/components/command/command.js +28 -17
- package/dist/components/command/index.d.ts +1 -1
- package/dist/components/context-menu/context-menu.d.ts +17 -6
- package/dist/components/context-menu/context-menu.js +142 -39
- package/dist/components/conversation/conversation.js +11 -11
- package/dist/components/copy-button/copy-button.js +2 -2
- package/dist/components/date-picker/date-picker.js +1 -1
- package/dist/components/dialog/dialog.d.ts +6 -4
- package/dist/components/dialog/dialog.js +22 -12
- package/dist/components/dropdown-menu/dropdown-menu.d.ts +13 -7
- package/dist/components/dropdown-menu/dropdown-menu.js +137 -78
- package/dist/components/empty-state/empty-state.js +1 -1
- package/dist/components/error-boundary/error-boundary.js +1 -1
- package/dist/components/field/field.js +4 -4
- package/dist/components/file-upload-input/file-upload-input.js +2 -2
- package/dist/components/form/form.js +6 -6
- package/dist/components/hover-card/hover-card.d.ts +8 -2
- package/dist/components/hover-card/hover-card.js +13 -7
- package/dist/components/icon-button/icon-button.js +19 -1
- package/dist/components/index.d.ts +10 -10
- package/dist/components/index.js +1 -1
- package/dist/components/input/input.js +1 -1
- package/dist/components/label/label.js +1 -1
- package/dist/components/menubar/menubar.d.ts +24 -5
- package/dist/components/menubar/menubar.js +186 -37
- package/dist/components/pagination/pagination.js +12 -12
- package/dist/components/popover/popover.d.ts +8 -3
- package/dist/components/popover/popover.js +40 -8
- package/dist/components/progress/progress.js +3 -3
- package/dist/components/radio-group/radio-group.js +3 -3
- package/dist/components/responsive-container/responsive-container.js +1 -1
- package/dist/components/scroll-area/scroll-area.js +4 -4
- package/dist/components/sectioned-sidebar-nav/sectioned-sidebar-nav.js +7 -7
- package/dist/components/select/select.js +66 -13
- package/dist/components/separator/separator.js +1 -1
- package/dist/components/sheet/sheet.d.ts +6 -4
- package/dist/components/sheet/sheet.js +29 -16
- package/dist/components/sidebar-shell/sidebar-shell.js +6 -6
- package/dist/components/skeleton/skeleton.js +1 -1
- package/dist/components/slider/slider.js +1 -1
- package/dist/components/spinner/spinner.js +1 -1
- package/dist/components/stat/stat.js +1 -1
- package/dist/components/switch/switch.js +3 -3
- package/dist/components/table/index.d.ts +1 -1
- package/dist/components/table/table.d.ts +5 -0
- package/dist/components/table/table.js +12 -8
- package/dist/components/tabs/tabs.js +4 -4
- package/dist/components/tabs-with-sidebar/tabs-with-sidebar.js +3 -3
- package/dist/components/textarea/textarea.js +1 -1
- package/dist/components/toast/index.d.ts +2 -2
- package/dist/components/toast/index.js +1 -1
- package/dist/components/toast/toast.d.ts +16 -2
- package/dist/components/toast/toast.js +49 -7
- package/dist/components/toggle/toggle.js +1 -1
- package/dist/components/toggle-group/toggle-group.js +1 -1
- package/dist/components/tooltip/tooltip.d.ts +8 -2
- package/dist/components/tooltip/tooltip.js +12 -6
- package/dist/hooks/index.d.ts +2 -2
- package/dist/hooks/use-composed-refs.d.ts +2 -2
- package/dist/hooks/use-controllable-state.d.ts +2 -2
- package/dist/internal/floating/compute-position.js +13 -8
- package/dist/internal/floating/floating-types.d.ts +1 -0
- package/dist/internal/floating/index.d.ts +1 -0
- package/dist/internal/floating/placement-aliases.d.ts +7 -0
- package/dist/internal/floating/placement-aliases.js +13 -0
- package/dist/internal/floating/use-floating-position.js +6 -4
- package/dist/internal/overlay-stack/overlay-stack.js +4 -1
- package/dist/internal/slot/index.d.ts +2 -0
- package/dist/internal/slot/index.js +1 -0
- package/dist/internal/slot/slot.d.ts +6 -0
- package/dist/internal/slot/slot.js +53 -0
- package/dist/styles.css +2079 -2015
- package/dist/tokens/index.d.ts +2 -2
- package/dist/tokens/index.js +1 -1
- package/dist/tokens/token-types.d.ts +5 -5
- package/dist/tokens/tokens.d.ts +16 -10
- package/dist/tokens/tokens.js +16 -10
- package/dist/utils/cn.d.ts +2 -2
- package/dist/utils/index.d.ts +1 -1
- package/package.json +13 -12
|
@@ -7,8 +7,11 @@ import { useControllableState } from "../../hooks/use-controllable-state.js";
|
|
|
7
7
|
import { Portal } from "../../internal/portal/index.js";
|
|
8
8
|
import { DismissableLayer } from "../../internal/dismissable-layer/dismissable-layer.js";
|
|
9
9
|
import { useFloatingPosition } from "../../internal/floating/index.js";
|
|
10
|
+
import { placementFromSideAlign, placementParts } from "../../internal/floating/placement-aliases.js";
|
|
11
|
+
import { Slot } from "../../internal/slot/index.js";
|
|
10
12
|
const defaultContentPositioning = {
|
|
11
13
|
sideOffset: 8,
|
|
14
|
+
alignOffset: 0,
|
|
12
15
|
collisionPadding: 0,
|
|
13
16
|
matchTriggerWidth: false
|
|
14
17
|
};
|
|
@@ -35,6 +38,18 @@ function composeRefs(...refs) {
|
|
|
35
38
|
function filterEnabledItems(items) {
|
|
36
39
|
return items.filter((item) => !item.disabled && item.ref !== null);
|
|
37
40
|
}
|
|
41
|
+
function setComposedRef(internalRef, externalRef, node) {
|
|
42
|
+
internalRef.current = node;
|
|
43
|
+
if (typeof externalRef === "function") {
|
|
44
|
+
externalRef(node);
|
|
45
|
+
}
|
|
46
|
+
else if (externalRef !== undefined && externalRef !== null) {
|
|
47
|
+
externalRef.current = node;
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
function isActivationKey(key) {
|
|
51
|
+
return key === " " || key === "Space" || key === "Enter" || key === "Spacebar";
|
|
52
|
+
}
|
|
38
53
|
const DropdownMenuRadioGroupContext = React.createContext(null);
|
|
39
54
|
function DropdownMenuRoot({ children, className, container, defaultOpen = false, onOpenChange, open: openProp, placement = "bottom", sideOffset = 8, collisionPadding = 0, matchTriggerWidth = false, ...props }) {
|
|
40
55
|
const [open, setOpen] = useControllableState({
|
|
@@ -51,14 +66,16 @@ function DropdownMenuRoot({ children, className, container, defaultOpen = false,
|
|
|
51
66
|
const wasOpenRef = React.useRef(false);
|
|
52
67
|
const [contentPositioning, setContentPositioning] = React.useState({
|
|
53
68
|
sideOffset,
|
|
69
|
+
alignOffset: defaultContentPositioning.alignOffset,
|
|
54
70
|
collisionPadding,
|
|
55
71
|
matchTriggerWidth
|
|
56
72
|
});
|
|
57
73
|
const floating = useFloatingPosition({
|
|
58
74
|
open,
|
|
59
|
-
placement,
|
|
75
|
+
placement: contentPositioning.placement ?? placement,
|
|
60
76
|
strategy: "absolute",
|
|
61
77
|
offset: contentPositioning.sideOffset,
|
|
78
|
+
alignmentOffset: contentPositioning.alignOffset,
|
|
62
79
|
collisionPadding: contentPositioning.collisionPadding,
|
|
63
80
|
matchReferenceWidth: contentPositioning.matchTriggerWidth
|
|
64
81
|
});
|
|
@@ -116,32 +133,37 @@ function DropdownMenuRoot({ children, className, container, defaultOpen = false,
|
|
|
116
133
|
triggerRef,
|
|
117
134
|
referenceRef: floating.referenceRef,
|
|
118
135
|
floatingRef: floating.floatingRef,
|
|
136
|
+
floatingPlacement: floating.placement,
|
|
119
137
|
floatingStyle: floating.floatingStyle,
|
|
120
138
|
getEnabledItems,
|
|
121
139
|
registerItem,
|
|
122
140
|
unregisterItem,
|
|
123
141
|
...(container === undefined ? {} : { container })
|
|
124
|
-
}, children: _jsx("div", { ...props, className: cn("
|
|
142
|
+
}, children: _jsx("div", { ...props, className: cn("zvk-ui-dropdown-menu", className), "data-state": open ? "open" : "closed", children: children }) }));
|
|
125
143
|
}
|
|
126
|
-
function DropdownMenuTrigger({ className, disabled, onClick, ref, type = "button", ...props }) {
|
|
144
|
+
function DropdownMenuTrigger({ asChild = false, className, disabled, onClick, ref, type = "button", ...props }) {
|
|
127
145
|
const { contentId, open, setOpen, triggerRef, triggerId, referenceRef, getEnabledItems } = useDropdownMenuContext("DropdownMenu.Trigger");
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
134
|
-
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
146
|
+
const handleClick = () => {
|
|
147
|
+
if (disabled) {
|
|
148
|
+
return;
|
|
149
|
+
}
|
|
150
|
+
const nextOpen = !open;
|
|
151
|
+
setOpen(nextOpen);
|
|
152
|
+
if (!nextOpen) {
|
|
153
|
+
return;
|
|
154
|
+
}
|
|
155
|
+
queueMicrotask(() => {
|
|
156
|
+
const first = getEnabledItems()[0];
|
|
157
|
+
first?.ref?.focus();
|
|
158
|
+
});
|
|
159
|
+
};
|
|
160
|
+
if (asChild) {
|
|
161
|
+
return (_jsx(Slot, { ...props, ref: composeRefs(ref, triggerRef, referenceRef), id: triggerId, "aria-controls": contentId, "aria-disabled": disabled ? true : undefined, "aria-expanded": open ? "true" : "false", "aria-haspopup": "menu", className: cn("zvk-ui-dropdown-menu__trigger", className), "data-disabled": disabled ? "true" : undefined, "data-state": open ? "open" : "closed", onClick: composeEventHandlers(onClick, handleClick), children: props.children }));
|
|
162
|
+
}
|
|
163
|
+
return (_jsx("button", { ...props, ref: composeRefs(ref, triggerRef, referenceRef), type: type, disabled: disabled, id: triggerId, role: "button", "aria-haspopup": "menu", "aria-expanded": open ? "true" : "false", "aria-controls": contentId, className: cn("zvk-ui-dropdown-menu__trigger", className), "data-state": open ? "open" : "closed", onClick: composeEventHandlers(onClick, handleClick) }));
|
|
142
164
|
}
|
|
143
|
-
function DropdownMenuContent({ children, className, forceMount = false, sideOffset = defaultContentPositioning.sideOffset, collisionPadding = defaultContentPositioning.collisionPadding, matchTriggerWidth = defaultContentPositioning.matchTriggerWidth, ref, onKeyDown, ...props }) {
|
|
144
|
-
const { container, contentId, open, setOpen, updateContentPositioning, triggerId, floatingRef, floatingStyle, getEnabledItems } = useDropdownMenuContext("DropdownMenu.Content");
|
|
165
|
+
function DropdownMenuContent({ align, alignOffset = defaultContentPositioning.alignOffset, children, className, forceMount = false, side, sideOffset = defaultContentPositioning.sideOffset, collisionPadding = defaultContentPositioning.collisionPadding, matchTriggerWidth = defaultContentPositioning.matchTriggerWidth, ref, onKeyDown, ...props }) {
|
|
166
|
+
const { container, contentId, open, setOpen, updateContentPositioning, triggerId, floatingRef, floatingPlacement, floatingStyle, getEnabledItems } = useDropdownMenuContext("DropdownMenu.Content");
|
|
145
167
|
const focusItem = React.useCallback((index, items) => {
|
|
146
168
|
if (items.length === 0) {
|
|
147
169
|
return;
|
|
@@ -181,14 +203,16 @@ function DropdownMenuContent({ children, className, forceMount = false, sideOffs
|
|
|
181
203
|
}, [getEnabledItems]);
|
|
182
204
|
React.useEffect(() => {
|
|
183
205
|
updateContentPositioning({
|
|
206
|
+
...(side === undefined ? {} : { placement: placementFromSideAlign(side, align, "bottom") }),
|
|
184
207
|
sideOffset,
|
|
208
|
+
alignOffset,
|
|
185
209
|
collisionPadding,
|
|
186
210
|
matchTriggerWidth
|
|
187
211
|
});
|
|
188
212
|
return () => {
|
|
189
213
|
updateContentPositioning(defaultContentPositioning);
|
|
190
214
|
};
|
|
191
|
-
}, [collisionPadding, matchTriggerWidth, sideOffset, updateContentPositioning]);
|
|
215
|
+
}, [align, alignOffset, collisionPadding, matchTriggerWidth, side, sideOffset, updateContentPositioning]);
|
|
192
216
|
if (!open && !forceMount) {
|
|
193
217
|
return null;
|
|
194
218
|
}
|
|
@@ -200,7 +224,7 @@ function DropdownMenuContent({ children, className, forceMount = false, sideOffs
|
|
|
200
224
|
else if (ref) {
|
|
201
225
|
ref.current = node;
|
|
202
226
|
}
|
|
203
|
-
}, id: contentId, role: "menu", "aria-labelledby": triggerId, className: cn("
|
|
227
|
+
}, id: contentId, role: "menu", "aria-labelledby": triggerId, className: cn("zvk-ui-dropdown-menu__content", className), style: floatingStyle, "data-align": placementParts(floatingPlacement).align, "data-side": placementParts(floatingPlacement).side, "data-state": open ? "open" : "closed", hidden: open ? undefined : true, onKeyDown: composeEventHandlers(onKeyDown, (event) => {
|
|
204
228
|
if (event.key === "ArrowDown") {
|
|
205
229
|
event.preventDefault();
|
|
206
230
|
moveFocus("next");
|
|
@@ -236,7 +260,7 @@ function DropdownMenuContent({ children, className, forceMount = false, sideOffs
|
|
|
236
260
|
setOpen(false);
|
|
237
261
|
}, children: content }) }));
|
|
238
262
|
}
|
|
239
|
-
function DropdownMenuItem({ children, className, disabled, onClick, onSelect, onKeyDown, ref, ...props }) {
|
|
263
|
+
function DropdownMenuItem({ asChild = false, children, className, disabled, onClick, onSelect, onKeyDown, ref, ...props }) {
|
|
240
264
|
const context = useDropdownMenuContext("DropdownMenu.Item");
|
|
241
265
|
const itemRef = React.useRef(null);
|
|
242
266
|
const itemId = React.useId();
|
|
@@ -251,41 +275,50 @@ function DropdownMenuItem({ children, className, disabled, onClick, onSelect, on
|
|
|
251
275
|
context.registerItem(itemRecord);
|
|
252
276
|
return () => context.unregisterItem(itemId);
|
|
253
277
|
}, [context, isDisabled, itemId, onSelect]);
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
ref.current = node;
|
|
261
|
-
}
|
|
262
|
-
}, type: "button", role: "menuitem", disabled: isDisabled, "aria-disabled": isDisabled ? "true" : undefined, className: cn("liano-dropdown-menu__item", className), "data-state": isDisabled ? "disabled" : "enabled", onClick: composeEventHandlers(onClick, (event) => {
|
|
263
|
-
if (isDisabled) {
|
|
264
|
-
return;
|
|
265
|
-
}
|
|
266
|
-
onSelect?.(event);
|
|
278
|
+
const select = (event) => {
|
|
279
|
+
if (isDisabled) {
|
|
280
|
+
return;
|
|
281
|
+
}
|
|
282
|
+
onSelect?.(event);
|
|
283
|
+
if (!event.defaultPrevented) {
|
|
267
284
|
context.setOpen(false);
|
|
268
|
-
}
|
|
269
|
-
|
|
285
|
+
}
|
|
286
|
+
};
|
|
287
|
+
const itemProps = {
|
|
288
|
+
...props,
|
|
289
|
+
ref: (node) => {
|
|
290
|
+
setComposedRef(itemRef, ref, node);
|
|
291
|
+
},
|
|
292
|
+
role: "menuitem",
|
|
293
|
+
"aria-disabled": isDisabled ? true : undefined,
|
|
294
|
+
className: cn("zvk-ui-dropdown-menu__item", className),
|
|
295
|
+
"data-disabled": isDisabled ? "true" : undefined,
|
|
296
|
+
"data-state": isDisabled ? "disabled" : "enabled",
|
|
297
|
+
onClick: composeEventHandlers(onClick, select),
|
|
298
|
+
onKeyDown: composeEventHandlers(onKeyDown, (event) => {
|
|
299
|
+
if (isActivationKey(event.key)) {
|
|
300
|
+
select(event);
|
|
270
301
|
event.preventDefault();
|
|
271
|
-
if (isDisabled) {
|
|
272
|
-
return;
|
|
273
|
-
}
|
|
274
|
-
onSelect?.(event);
|
|
275
|
-
context.setOpen(false);
|
|
276
302
|
}
|
|
277
|
-
})
|
|
303
|
+
})
|
|
304
|
+
};
|
|
305
|
+
if (asChild) {
|
|
306
|
+
return _jsx(Slot, { ...itemProps, children: children });
|
|
307
|
+
}
|
|
308
|
+
return (_jsx("button", { ...props, ref: (node) => {
|
|
309
|
+
setComposedRef(itemRef, ref, node);
|
|
310
|
+
}, type: "button", role: "menuitem", disabled: isDisabled, "aria-disabled": itemProps["aria-disabled"], className: itemProps.className, "data-disabled": itemProps["data-disabled"], "data-state": itemProps["data-state"], onClick: itemProps.onClick, onKeyDown: itemProps.onKeyDown, children: children }));
|
|
278
311
|
}
|
|
279
312
|
function DropdownMenuSeparator({ className, ref, ...props }) {
|
|
280
|
-
return (_jsx("div", { ...props, ref: ref, role: "separator", "aria-hidden": "true", className: cn("
|
|
313
|
+
return (_jsx("div", { ...props, ref: ref, role: "separator", "aria-hidden": "true", className: cn("zvk-ui-dropdown-menu__separator", className) }));
|
|
281
314
|
}
|
|
282
315
|
function DropdownMenuLabel({ className, ref, ...props }) {
|
|
283
|
-
return (_jsx("div", { ...props, ref: ref, className: cn("
|
|
316
|
+
return (_jsx("div", { ...props, ref: ref, className: cn("zvk-ui-dropdown-menu__label", className) }));
|
|
284
317
|
}
|
|
285
318
|
function DropdownMenuShortcut({ className, ref, ...props }) {
|
|
286
|
-
return (_jsx("span", { ...props, ref: ref, className: cn("
|
|
319
|
+
return (_jsx("span", { ...props, ref: ref, className: cn("zvk-ui-dropdown-menu__shortcut", className) }));
|
|
287
320
|
}
|
|
288
|
-
function DropdownMenuCheckboxItem({ checked, children, className, defaultChecked = false, disabled, onCheckedChange, onClick, onKeyDown, onSelect, ref, ...props }) {
|
|
321
|
+
function DropdownMenuCheckboxItem({ asChild = false, checked, children, className, defaultChecked = false, disabled, onCheckedChange, onClick, onKeyDown, onSelect, ref, ...props }) {
|
|
289
322
|
const context = useDropdownMenuContext("DropdownMenu.CheckboxItem");
|
|
290
323
|
const itemRef = React.useRef(null);
|
|
291
324
|
const itemId = React.useId();
|
|
@@ -308,33 +341,46 @@ function DropdownMenuCheckboxItem({ checked, children, className, defaultChecked
|
|
|
308
341
|
if (isDisabled) {
|
|
309
342
|
return;
|
|
310
343
|
}
|
|
311
|
-
setCurrentChecked((value) => !value);
|
|
312
344
|
onSelect?.(event);
|
|
313
|
-
|
|
345
|
+
if (!event.defaultPrevented) {
|
|
346
|
+
setCurrentChecked((value) => !value);
|
|
347
|
+
context.setOpen(false);
|
|
348
|
+
}
|
|
314
349
|
};
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
|
|
318
|
-
|
|
319
|
-
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
323
|
-
|
|
324
|
-
|
|
325
|
-
|
|
350
|
+
const itemProps = {
|
|
351
|
+
...props,
|
|
352
|
+
ref: (node) => {
|
|
353
|
+
setComposedRef(itemRef, ref, node);
|
|
354
|
+
},
|
|
355
|
+
role: "menuitemcheckbox",
|
|
356
|
+
"aria-checked": currentChecked,
|
|
357
|
+
"aria-disabled": isDisabled ? true : undefined,
|
|
358
|
+
className: cn("zvk-ui-dropdown-menu__item", "zvk-ui-dropdown-menu__checkbox-item", className),
|
|
359
|
+
"data-checked": currentChecked ? "true" : undefined,
|
|
360
|
+
"data-disabled": isDisabled ? "true" : undefined,
|
|
361
|
+
onClick: composeEventHandlers(onClick, select),
|
|
362
|
+
onKeyDown: composeEventHandlers(onKeyDown, (event) => {
|
|
363
|
+
if (isActivationKey(event.key)) {
|
|
326
364
|
select(event);
|
|
365
|
+
event.preventDefault();
|
|
327
366
|
}
|
|
328
|
-
})
|
|
367
|
+
})
|
|
368
|
+
};
|
|
369
|
+
if (asChild) {
|
|
370
|
+
return _jsx(Slot, { ...itemProps, children: children });
|
|
371
|
+
}
|
|
372
|
+
return (_jsxs("button", { ...props, ref: (node) => {
|
|
373
|
+
setComposedRef(itemRef, ref, node);
|
|
374
|
+
}, type: "button", role: "menuitemcheckbox", disabled: isDisabled, "aria-checked": itemProps["aria-checked"], "aria-disabled": itemProps["aria-disabled"], className: itemProps.className, "data-checked": itemProps["data-checked"], "data-disabled": itemProps["data-disabled"], onClick: itemProps.onClick, onKeyDown: itemProps.onKeyDown, children: [_jsx("span", { className: "zvk-ui-dropdown-menu__item-indicator", "aria-hidden": "true", children: currentChecked ? "✓" : "" }), _jsx("span", { className: "zvk-ui-dropdown-menu__item-label", children: children })] }));
|
|
329
375
|
}
|
|
330
376
|
function DropdownMenuRadioGroup({ children, className, onValueChange, ref, value, ...props }) {
|
|
331
377
|
const contextValue = React.useMemo(() => ({
|
|
332
378
|
...(value !== undefined ? { value } : {}),
|
|
333
379
|
...(onValueChange ? { onValueChange } : {})
|
|
334
380
|
}), [onValueChange, value]);
|
|
335
|
-
return (_jsx(DropdownMenuRadioGroupContext.Provider, { value: contextValue, children: _jsx("div", { ...props, ref: ref, className: cn("
|
|
381
|
+
return (_jsx(DropdownMenuRadioGroupContext.Provider, { value: contextValue, children: _jsx("div", { ...props, ref: ref, className: cn("zvk-ui-dropdown-menu__radio-group", className), role: "group", children: children }) }));
|
|
336
382
|
}
|
|
337
|
-
function DropdownMenuRadioItem({ children, className, disabled, onClick, onKeyDown, onSelect, ref, value, ...props }) {
|
|
383
|
+
function DropdownMenuRadioItem({ asChild = false, children, className, disabled, onClick, onKeyDown, onSelect, ref, value, ...props }) {
|
|
338
384
|
const context = useDropdownMenuContext("DropdownMenu.RadioItem");
|
|
339
385
|
const radioGroup = React.useContext(DropdownMenuRadioGroupContext);
|
|
340
386
|
const itemRef = React.useRef(null);
|
|
@@ -354,27 +400,40 @@ function DropdownMenuRadioItem({ children, className, disabled, onClick, onKeyDo
|
|
|
354
400
|
if (isDisabled) {
|
|
355
401
|
return;
|
|
356
402
|
}
|
|
357
|
-
radioGroup?.onValueChange?.(value);
|
|
358
403
|
onSelect?.(event);
|
|
359
|
-
|
|
404
|
+
if (!event.defaultPrevented) {
|
|
405
|
+
radioGroup?.onValueChange?.(value);
|
|
406
|
+
context.setOpen(false);
|
|
407
|
+
}
|
|
360
408
|
};
|
|
361
|
-
|
|
362
|
-
|
|
363
|
-
|
|
364
|
-
|
|
365
|
-
|
|
366
|
-
|
|
367
|
-
|
|
368
|
-
|
|
369
|
-
|
|
370
|
-
|
|
371
|
-
|
|
409
|
+
const itemProps = {
|
|
410
|
+
...props,
|
|
411
|
+
ref: (node) => {
|
|
412
|
+
setComposedRef(itemRef, ref, node);
|
|
413
|
+
},
|
|
414
|
+
role: "menuitemradio",
|
|
415
|
+
"aria-checked": checked,
|
|
416
|
+
"aria-disabled": isDisabled ? true : undefined,
|
|
417
|
+
className: cn("zvk-ui-dropdown-menu__item", "zvk-ui-dropdown-menu__radio-item", className),
|
|
418
|
+
"data-checked": checked ? "true" : undefined,
|
|
419
|
+
"data-disabled": isDisabled ? "true" : undefined,
|
|
420
|
+
onClick: composeEventHandlers(onClick, select),
|
|
421
|
+
onKeyDown: composeEventHandlers(onKeyDown, (event) => {
|
|
422
|
+
if (isActivationKey(event.key)) {
|
|
372
423
|
select(event);
|
|
424
|
+
event.preventDefault();
|
|
373
425
|
}
|
|
374
|
-
})
|
|
426
|
+
})
|
|
427
|
+
};
|
|
428
|
+
if (asChild) {
|
|
429
|
+
return _jsx(Slot, { ...itemProps, children: children });
|
|
430
|
+
}
|
|
431
|
+
return (_jsxs("button", { ...props, ref: (node) => {
|
|
432
|
+
setComposedRef(itemRef, ref, node);
|
|
433
|
+
}, type: "button", role: "menuitemradio", disabled: isDisabled, "aria-checked": itemProps["aria-checked"], "aria-disabled": itemProps["aria-disabled"], className: itemProps.className, "data-checked": itemProps["data-checked"], "data-disabled": itemProps["data-disabled"], onClick: itemProps.onClick, onKeyDown: itemProps.onKeyDown, children: [_jsx("span", { className: "zvk-ui-dropdown-menu__item-indicator", "aria-hidden": "true", children: checked ? "●" : "" }), _jsx("span", { className: "zvk-ui-dropdown-menu__item-label", children: children })] }));
|
|
375
434
|
}
|
|
376
435
|
function DropdownMenuSub({ children, className, ref, ...props }) {
|
|
377
|
-
return (_jsx("div", { ...props, ref: ref, className: cn("
|
|
436
|
+
return (_jsx("div", { ...props, ref: ref, className: cn("zvk-ui-dropdown-menu__sub", className), children: children }));
|
|
378
437
|
}
|
|
379
438
|
export const DropdownMenu = Object.assign(DropdownMenuRoot, {
|
|
380
439
|
CheckboxItem: DropdownMenuCheckboxItem,
|
|
@@ -30,5 +30,5 @@ export function EmptyState({ actions, align = "center", children: _children, cla
|
|
|
30
30
|
const hasIcon = hasRenderableNode(icon);
|
|
31
31
|
const showDescription = description !== null && description !== undefined;
|
|
32
32
|
const showActions = actions !== null && actions !== undefined;
|
|
33
|
-
return (_jsxs("div", { ...props, ref: ref, className: cn("
|
|
33
|
+
return (_jsxs("div", { ...props, ref: ref, className: cn("zvk-ui-empty-state", className), "data-align": align, "data-size": size, children: [icon ? _jsx("div", { "aria-hidden": hasIcon ? undefined : true, className: "zvk-ui-empty-state__icon", children: icon }) : null, _jsx("h3", { className: "zvk-ui-empty-state__title", children: title }), showDescription ? _jsx("p", { className: "zvk-ui-empty-state__description", children: description }) : null, showActions ? _jsx("div", { className: "zvk-ui-empty-state__actions", children: actions }) : null] }));
|
|
34
34
|
}
|
|
@@ -39,5 +39,5 @@ export class ErrorBoundary extends React.Component {
|
|
|
39
39
|
}
|
|
40
40
|
}
|
|
41
41
|
export function ErrorFallback({ action, className, error, ref, title = "Something went wrong", ...props }) {
|
|
42
|
-
return (_jsxs("div", { ...props, ref: ref, "aria-label": typeof title === "string" ? title : undefined, className: cn("
|
|
42
|
+
return (_jsxs("div", { ...props, ref: ref, "aria-label": typeof title === "string" ? title : undefined, className: cn("zvk-ui-error-fallback", className), role: "alert", children: [_jsx("h3", { className: "zvk-ui-error-fallback__title", children: title }), error ? _jsx("p", { className: "zvk-ui-error-fallback__message", children: error.message }) : null, action ? _jsx("div", { className: "zvk-ui-error-fallback__action", children: action }) : null] }));
|
|
43
43
|
}
|
|
@@ -2,16 +2,16 @@ import { jsx as _jsx } from "react/jsx-runtime";
|
|
|
2
2
|
import * as React from "react";
|
|
3
3
|
import { cn } from "../../utils/cn.js";
|
|
4
4
|
function FieldRoot({ className, disabled, invalid, ref, required, ...props }) {
|
|
5
|
-
return (_jsx("div", { ...props, ref: ref, className: cn("
|
|
5
|
+
return (_jsx("div", { ...props, ref: ref, className: cn("zvk-ui-field", className), "data-disabled": disabled ? "true" : undefined, "data-invalid": invalid ? "true" : undefined, "data-required": required ? "true" : undefined }));
|
|
6
6
|
}
|
|
7
7
|
function FieldLabel({ className, ref, ...props }) {
|
|
8
|
-
return _jsx("label", { ...props, ref: ref, className: cn("
|
|
8
|
+
return _jsx("label", { ...props, ref: ref, className: cn("zvk-ui-field__label", className) });
|
|
9
9
|
}
|
|
10
10
|
function FieldDescription({ className, ref, ...props }) {
|
|
11
|
-
return _jsx("p", { ...props, ref: ref, className: cn("
|
|
11
|
+
return _jsx("p", { ...props, ref: ref, className: cn("zvk-ui-field__description", className) });
|
|
12
12
|
}
|
|
13
13
|
function FieldError({ className, ref, role = "alert", ...props }) {
|
|
14
|
-
return _jsx("p", { ...props, ref: ref, className: cn("
|
|
14
|
+
return _jsx("p", { ...props, ref: ref, className: cn("zvk-ui-field__error", className), role: role });
|
|
15
15
|
}
|
|
16
16
|
export const Field = Object.assign(FieldRoot, {
|
|
17
17
|
Label: FieldLabel,
|
|
@@ -28,12 +28,12 @@ export function FileUploadInput({ "aria-describedby": ariaDescribedBy, buttonLab
|
|
|
28
28
|
const descriptionId = hasDescription ? `${inputId}-description` : undefined;
|
|
29
29
|
const errorId = hasError ? `${inputId}-error` : undefined;
|
|
30
30
|
const summaryId = `${inputId}-summary`;
|
|
31
|
-
const describedBy = joinIds(ariaDescribedBy, descriptionId, errorId);
|
|
31
|
+
const describedBy = joinIds(ariaDescribedBy, descriptionId, errorId, summaryId);
|
|
32
32
|
function handleChange(event) {
|
|
33
33
|
setFiles(event.currentTarget.files);
|
|
34
34
|
onChange?.(event);
|
|
35
35
|
}
|
|
36
|
-
const input = (_jsxs("div", { className: "
|
|
36
|
+
const input = (_jsxs("div", { className: "zvk-ui-file-upload-input", children: [_jsx("span", { "aria-hidden": "true", className: "zvk-ui-file-upload-input__button", children: buttonLabel }), _jsx("input", { ...props, ref: ref, "aria-describedby": describedBy, "aria-invalid": invalidState ? true : undefined, className: cn("zvk-ui-file-upload-input__control", className), "data-disabled": disabled ? "true" : undefined, "data-invalid": invalidState ? "true" : undefined, "data-required": required ? "true" : undefined, "data-size": size, disabled: disabled, id: inputId, onChange: handleChange, required: required, type: "file" }), _jsx("span", { className: "zvk-ui-file-upload-input__summary", id: summaryId, children: getFileSummary(files, emptyLabel) })] }));
|
|
37
37
|
if (!hasRenderableNode(label) && !hasDescription && !hasError) {
|
|
38
38
|
return input;
|
|
39
39
|
}
|
|
@@ -15,7 +15,7 @@ function joinIds(ids) {
|
|
|
15
15
|
return value.length > 0 ? value : undefined;
|
|
16
16
|
}
|
|
17
17
|
export function Form({ className, ref, ...props }) {
|
|
18
|
-
return _jsx("form", { ...props, ref: ref, className: cn("
|
|
18
|
+
return _jsx("form", { ...props, ref: ref, className: cn("zvk-ui-form", className) });
|
|
19
19
|
}
|
|
20
20
|
export function FormField({ children, className, disabled, id, invalid, required, ...props }) {
|
|
21
21
|
const generatedId = React.useId();
|
|
@@ -36,14 +36,14 @@ export function FormField({ children, className, disabled, id, invalid, required
|
|
|
36
36
|
registerDescription,
|
|
37
37
|
unregisterDescription
|
|
38
38
|
}), [controlId, descriptionIds, disabled, invalid, registerDescription, required, unregisterDescription]);
|
|
39
|
-
return (_jsx(FormFieldContext.Provider, { value: context, children: _jsx("div", { ...props, className: cn("
|
|
39
|
+
return (_jsx(FormFieldContext.Provider, { value: context, children: _jsx("div", { ...props, className: cn("zvk-ui-form-field", className), "data-disabled": disabled ? "true" : undefined, "data-invalid": invalid ? "true" : undefined, "data-required": required ? "true" : undefined, children: children }) }));
|
|
40
40
|
}
|
|
41
41
|
export function FormItem({ className, ref, ...props }) {
|
|
42
|
-
return _jsx("div", { ...props, ref: ref, className: cn("
|
|
42
|
+
return _jsx("div", { ...props, ref: ref, className: cn("zvk-ui-form-item", className) });
|
|
43
43
|
}
|
|
44
44
|
export function FormLabel({ className, htmlFor, ref, ...props }) {
|
|
45
45
|
const context = useFormFieldContext("FormLabel");
|
|
46
|
-
return _jsx("label", { ...props, ref: ref, className: cn("
|
|
46
|
+
return _jsx("label", { ...props, ref: ref, className: cn("zvk-ui-form-label", className), htmlFor: htmlFor ?? context.controlId });
|
|
47
47
|
}
|
|
48
48
|
export function FormControl({ children }) {
|
|
49
49
|
const context = useFormFieldContext("FormControl");
|
|
@@ -81,8 +81,8 @@ function FormText({ className, id, ref, role, textRole, ...props }) {
|
|
|
81
81
|
return _jsx("p", { ...props, ref: ref, id: textId, role: role, className: className });
|
|
82
82
|
}
|
|
83
83
|
export function FormDescription({ className, ...props }) {
|
|
84
|
-
return _jsx(FormText, { ...props, className: cn("
|
|
84
|
+
return _jsx(FormText, { ...props, className: cn("zvk-ui-form-description", className), textRole: "FormDescription" });
|
|
85
85
|
}
|
|
86
86
|
export function FormMessage({ className, role = "alert", ...props }) {
|
|
87
|
-
return _jsx(FormText, { ...props, className: cn("
|
|
87
|
+
return _jsx(FormText, { ...props, className: cn("zvk-ui-form-message", className), role: role, textRole: "FormMessage" });
|
|
88
88
|
}
|
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import * as React from "react";
|
|
2
2
|
import type { FloatingPlacement } from "../../internal/floating/index.js";
|
|
3
|
+
import type { FloatingAlign, FloatingSide } from "../../internal/floating/placement-aliases.js";
|
|
3
4
|
import type { PortalProps } from "../../internal/portal/index.js";
|
|
4
5
|
export interface HoverCardProps {
|
|
5
6
|
children?: React.ReactNode;
|
|
@@ -12,9 +13,14 @@ export interface HoverCardProps {
|
|
|
12
13
|
disabled?: boolean;
|
|
13
14
|
}
|
|
14
15
|
export interface HoverCardTriggerProps {
|
|
16
|
+
asChild?: boolean;
|
|
15
17
|
children: React.ReactElement;
|
|
16
18
|
}
|
|
17
19
|
export interface HoverCardContentProps extends React.HTMLAttributes<HTMLDivElement> {
|
|
20
|
+
placement?: FloatingPlacement;
|
|
21
|
+
side?: FloatingSide;
|
|
22
|
+
align?: FloatingAlign;
|
|
23
|
+
alignOffset?: number;
|
|
18
24
|
sideOffset?: number;
|
|
19
25
|
collisionPadding?: number;
|
|
20
26
|
forceMount?: boolean;
|
|
@@ -22,8 +28,8 @@ export interface HoverCardContentProps extends React.HTMLAttributes<HTMLDivEleme
|
|
|
22
28
|
ref?: React.Ref<HTMLDivElement>;
|
|
23
29
|
}
|
|
24
30
|
declare function HoverCardRoot({ children, closeDelay, defaultOpen, disabled, onOpenChange, open: openProp, openDelay, placement }: HoverCardProps): React.JSX.Element;
|
|
25
|
-
declare function HoverCardTrigger({ children }: HoverCardTriggerProps): React.ReactElement<unknown, string | React.JSXElementConstructor<any>>;
|
|
26
|
-
declare function HoverCardContent({ children, className, collisionPadding, container, forceMount, id, onBlur, onFocus, onMouseEnter, onMouseLeave, onPointerEnter, onPointerLeave, ref, sideOffset, style, ...props }: HoverCardContentProps): React.JSX.Element | null;
|
|
31
|
+
declare function HoverCardTrigger({ children, asChild: _asChild }: HoverCardTriggerProps): React.ReactElement<unknown, string | React.JSXElementConstructor<any>>;
|
|
32
|
+
declare function HoverCardContent({ align, alignOffset, children, className, collisionPadding, container, forceMount, id, onBlur, onFocus, onMouseEnter, onMouseLeave, onPointerEnter, onPointerLeave, placement, ref, side, sideOffset, style, ...props }: HoverCardContentProps): React.JSX.Element | null;
|
|
27
33
|
export declare const HoverCard: typeof HoverCardRoot & {
|
|
28
34
|
Trigger: typeof HoverCardTrigger;
|
|
29
35
|
Content: typeof HoverCardContent;
|
|
@@ -3,12 +3,14 @@ import { jsx as _jsx } from "react/jsx-runtime";
|
|
|
3
3
|
import * as React from "react";
|
|
4
4
|
import { DismissableLayer } from "../../internal/dismissable-layer/index.js";
|
|
5
5
|
import { useFloatingPosition } from "../../internal/floating/index.js";
|
|
6
|
+
import { placementFromSideAlign } from "../../internal/floating/placement-aliases.js";
|
|
6
7
|
import { Portal } from "../../internal/portal/index.js";
|
|
7
8
|
import { useControllableState } from "../../hooks/use-controllable-state.js";
|
|
8
9
|
import { cn } from "../../utils/cn.js";
|
|
9
10
|
import { composeEventHandlers } from "../../utils/compose-event-handlers.js";
|
|
10
11
|
const defaultContentPositioning = {
|
|
11
12
|
sideOffset: 8,
|
|
13
|
+
alignOffset: 0,
|
|
12
14
|
collisionPadding: 0
|
|
13
15
|
};
|
|
14
16
|
const HoverCardContext = React.createContext(null);
|
|
@@ -25,7 +27,7 @@ function composeRefs(...refs) {
|
|
|
25
27
|
if (typeof ref === "function") {
|
|
26
28
|
ref(node);
|
|
27
29
|
}
|
|
28
|
-
else if (ref !== undefined) {
|
|
30
|
+
else if (ref !== undefined && ref !== null) {
|
|
29
31
|
ref.current = node;
|
|
30
32
|
}
|
|
31
33
|
}
|
|
@@ -55,8 +57,9 @@ function HoverCardRoot({ children, closeDelay = 300, defaultOpen = false, disabl
|
|
|
55
57
|
const contentElement = React.useRef(null);
|
|
56
58
|
const { floatingRef, floatingStyle, placement: resolvedPlacement, referenceRef, updatePosition } = useFloatingPosition({
|
|
57
59
|
open,
|
|
58
|
-
placement,
|
|
60
|
+
placement: contentPositioning.placement ?? placement,
|
|
59
61
|
offset: contentPositioning.sideOffset,
|
|
62
|
+
alignmentOffset: contentPositioning.alignOffset,
|
|
60
63
|
collisionPadding: contentPositioning.collisionPadding,
|
|
61
64
|
flip: true,
|
|
62
65
|
shift: true
|
|
@@ -204,7 +207,7 @@ function HoverCardRoot({ children, closeDelay = 300, defaultOpen = false, disabl
|
|
|
204
207
|
]);
|
|
205
208
|
return (_jsx(HoverCardContext.Provider, { value: contextValue, children: children }));
|
|
206
209
|
}
|
|
207
|
-
function HoverCardTrigger({ children }) {
|
|
210
|
+
function HoverCardTrigger({ children, asChild: _asChild = false }) {
|
|
208
211
|
const context = useHoverCardContext("HoverCard.Trigger");
|
|
209
212
|
if (!React.isValidElement(children) || context.disabled) {
|
|
210
213
|
return children;
|
|
@@ -221,7 +224,7 @@ function HoverCardTrigger({ children }) {
|
|
|
221
224
|
"aria-describedby": joinIds(typeof childAriaDescribedBy === "string" ? childAriaDescribedBy : undefined, context.open ? context.contentId : undefined),
|
|
222
225
|
"aria-expanded": context.open,
|
|
223
226
|
"aria-haspopup": "dialog",
|
|
224
|
-
className: cn("
|
|
227
|
+
className: cn("zvk-ui-hover-card__trigger", childClassName),
|
|
225
228
|
"data-state": context.open ? "open" : "closed",
|
|
226
229
|
onBlur: composeEventHandlers(childProps.onBlur, (event) => {
|
|
227
230
|
context.closeAfterFocusLeaves(event.relatedTarget);
|
|
@@ -233,22 +236,25 @@ function HoverCardTrigger({ children }) {
|
|
|
233
236
|
onPointerLeave: composeEventHandlers(childProps.onPointerLeave, context.closeWithDelay)
|
|
234
237
|
});
|
|
235
238
|
}
|
|
236
|
-
function HoverCardContent({ children, className, collisionPadding = defaultContentPositioning.collisionPadding, container, forceMount = false, id, onBlur, onFocus, onMouseEnter, onMouseLeave, onPointerEnter, onPointerLeave, ref, sideOffset = defaultContentPositioning.sideOffset, style, ...props }) {
|
|
239
|
+
function HoverCardContent({ align, alignOffset = defaultContentPositioning.alignOffset, children, className, collisionPadding = defaultContentPositioning.collisionPadding, container, forceMount = false, id, onBlur, onFocus, onMouseEnter, onMouseLeave, onPointerEnter, onPointerLeave, placement, ref, side, sideOffset = defaultContentPositioning.sideOffset, style, ...props }) {
|
|
237
240
|
const context = useHoverCardContext("HoverCard.Content");
|
|
238
241
|
const contentId = id ?? context.contentId;
|
|
239
242
|
const placementParts = getPlacementParts(context.resolvedPlacement);
|
|
240
243
|
const { setContentPositioning } = context;
|
|
241
244
|
React.useEffect(() => {
|
|
245
|
+
const resolvedPlacement = side === undefined ? placement : placementFromSideAlign(side, align, placement ?? "bottom");
|
|
242
246
|
setContentPositioning({
|
|
247
|
+
...(resolvedPlacement === undefined ? {} : { placement: resolvedPlacement }),
|
|
243
248
|
sideOffset,
|
|
249
|
+
alignOffset,
|
|
244
250
|
collisionPadding
|
|
245
251
|
});
|
|
246
252
|
return () => setContentPositioning(defaultContentPositioning);
|
|
247
|
-
}, [collisionPadding, setContentPositioning, sideOffset]);
|
|
253
|
+
}, [align, alignOffset, collisionPadding, placement, setContentPositioning, side, sideOffset]);
|
|
248
254
|
if (!context.open && !forceMount) {
|
|
249
255
|
return null;
|
|
250
256
|
}
|
|
251
|
-
const content = (_jsx("div", { ...props, ref: composeRefs(ref, context.floatingRef), id: contentId, role: "dialog", className: cn("
|
|
257
|
+
const content = (_jsx("div", { ...props, ref: composeRefs(ref, context.floatingRef), id: contentId, role: "dialog", className: cn("zvk-ui-hover-card__content", className), "data-align": placementParts.align, "data-side": placementParts.side, "data-state": context.open ? "open" : "closed", hidden: context.open ? undefined : true, onBlur: composeEventHandlers(onBlur, (event) => {
|
|
252
258
|
context.closeAfterFocusLeaves(event.relatedTarget);
|
|
253
259
|
}), onFocus: composeEventHandlers(onFocus, context.openImmediately), onMouseEnter: composeEventHandlers(onMouseEnter, context.cancelClose), onMouseLeave: composeEventHandlers(onMouseLeave, context.closeWithDelay), onPointerEnter: composeEventHandlers(onPointerEnter, context.cancelClose), onPointerLeave: composeEventHandlers(onPointerLeave, context.closeWithDelay), style: { ...context.floatingStyle, ...style }, children: children }));
|
|
254
260
|
if (!context.open) {
|
|
@@ -2,7 +2,25 @@ import { jsx as _jsx } from "react/jsx-runtime";
|
|
|
2
2
|
import * as React from "react";
|
|
3
3
|
import { Spinner } from "../spinner/spinner.js";
|
|
4
4
|
import { cn } from "../../utils/cn.js";
|
|
5
|
+
function isDevelopmentEnvironment() {
|
|
6
|
+
const runtimeProcess = globalThis.process;
|
|
7
|
+
if (runtimeProcess?.env?.NODE_ENV) {
|
|
8
|
+
return runtimeProcess.env.NODE_ENV !== "production";
|
|
9
|
+
}
|
|
10
|
+
const metaEnv = import.meta.env;
|
|
11
|
+
if (typeof metaEnv?.DEV === "boolean") {
|
|
12
|
+
return metaEnv.DEV;
|
|
13
|
+
}
|
|
14
|
+
if (typeof metaEnv?.PROD === "boolean") {
|
|
15
|
+
return !metaEnv.PROD;
|
|
16
|
+
}
|
|
17
|
+
return typeof metaEnv?.MODE === "string" && metaEnv.MODE !== "production";
|
|
18
|
+
}
|
|
5
19
|
export function IconButton({ children, className, disabled, loading = false, ref, size = "md", type = "button", variant = "secondary", ...props }) {
|
|
6
20
|
const isDisabled = disabled || loading;
|
|
7
|
-
|
|
21
|
+
const hasAccessibleName = props["aria-label"] !== undefined || props["aria-labelledby"] !== undefined;
|
|
22
|
+
if (!hasAccessibleName && isDevelopmentEnvironment()) {
|
|
23
|
+
console.warn("IconButton requires an accessible name. Provide aria-label or aria-labelledby.");
|
|
24
|
+
}
|
|
25
|
+
return (_jsx("button", { ...props, ref: ref, "aria-busy": loading ? true : undefined, className: cn("zvk-ui-icon-button", className), "data-disabled": isDisabled ? "true" : undefined, "data-loading": loading ? "true" : undefined, "data-size": size, "data-variant": variant, disabled: isDisabled, type: type, children: loading ? _jsx(Spinner, { size: "sm" }) : children }));
|
|
8
26
|
}
|