@versini/ui-menu 5.1.3 → 5.3.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.
- package/dist/index.d.ts +83 -81
- package/dist/index.js +458 -15
- package/package.json +9 -9
- package/dist/chunks/index.Benv90bx.js +0 -61
- package/dist/components/Menu/Menu.js +0 -258
- package/dist/components/Menu/MenuContext.js +0 -16
- package/dist/components/Menu/MenuItem.js +0 -136
package/dist/index.d.ts
CHANGED
|
@@ -1,81 +1,83 @@
|
|
|
1
|
-
import
|
|
2
|
-
import
|
|
3
|
-
import {
|
|
4
|
-
import * as
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
declare const
|
|
80
|
-
|
|
81
|
-
|
|
1
|
+
import { JSX } from 'react/jsx-runtime';
|
|
2
|
+
import type { Placement } from '@floating-ui/react';
|
|
3
|
+
import { default as React_2 } from 'react';
|
|
4
|
+
import * as React_3 from 'react';
|
|
5
|
+
|
|
6
|
+
export declare const Menu: React_2.ForwardRefExoticComponent<Omit<MenuProps & React_2.HTMLProps<HTMLButtonElement>, "ref"> & React_2.RefAttributes<HTMLButtonElement>>;
|
|
7
|
+
|
|
8
|
+
export declare const MenuGroupLabel: ({ className, ...props }: React_3.HTMLAttributes<HTMLDivElement>) => JSX.Element;
|
|
9
|
+
|
|
10
|
+
export declare const MenuItem: React_3.ForwardRefExoticComponent<MenuItemProps & React_3.ButtonHTMLAttributes<HTMLButtonElement> & React_3.RefAttributes<HTMLButtonElement>>;
|
|
11
|
+
|
|
12
|
+
declare type MenuItemProps = {
|
|
13
|
+
/**
|
|
14
|
+
* The label to use for the menu item.
|
|
15
|
+
*/
|
|
16
|
+
label?: string;
|
|
17
|
+
/**
|
|
18
|
+
* Whether or not the menu item is disabled.
|
|
19
|
+
* @default false
|
|
20
|
+
*/
|
|
21
|
+
disabled?: boolean;
|
|
22
|
+
/**
|
|
23
|
+
* A React component of type Icon to be placed on the left of the label.
|
|
24
|
+
*/
|
|
25
|
+
icon?: React_2.ReactNode;
|
|
26
|
+
/**
|
|
27
|
+
* Disable internal menu item behavior (click, focus, etc.).
|
|
28
|
+
* @default false
|
|
29
|
+
*/
|
|
30
|
+
raw?: boolean;
|
|
31
|
+
/**
|
|
32
|
+
* Whether or not the menu should close when the menu item is selected.
|
|
33
|
+
* @default false
|
|
34
|
+
*/
|
|
35
|
+
ignoreClick?: boolean;
|
|
36
|
+
/**
|
|
37
|
+
* Whether or not the menu item is selected.
|
|
38
|
+
* @default false
|
|
39
|
+
*/
|
|
40
|
+
selected?: boolean;
|
|
41
|
+
};
|
|
42
|
+
|
|
43
|
+
declare type MenuProps = {
|
|
44
|
+
/**
|
|
45
|
+
* The component to use to open the menu, e.g. a ButtonIcon, a Button, etc.
|
|
46
|
+
* Required for root menus, omit for nested sub-menus (use label instead).
|
|
47
|
+
*/
|
|
48
|
+
trigger?: React_2.ReactNode;
|
|
49
|
+
/**
|
|
50
|
+
* The children to render.
|
|
51
|
+
*/
|
|
52
|
+
children?: React_2.ReactNode;
|
|
53
|
+
/**
|
|
54
|
+
* The default location of the popup.
|
|
55
|
+
* @default "bottom-start"
|
|
56
|
+
*/
|
|
57
|
+
defaultPlacement?: Placement;
|
|
58
|
+
/**
|
|
59
|
+
* The type of focus for the Button. This will change the color
|
|
60
|
+
* of the focus ring around the Button.
|
|
61
|
+
*/
|
|
62
|
+
focusMode?: "dark" | "light" | "system" | "alt-system";
|
|
63
|
+
/**
|
|
64
|
+
* The type of Button trigger. This will change the color of the Button.
|
|
65
|
+
*/
|
|
66
|
+
mode?: "dark" | "light" | "system" | "alt-system";
|
|
67
|
+
/**
|
|
68
|
+
* The label to use for the menu button (root menu) or the sub-menu trigger text (nested menu).
|
|
69
|
+
* When used without a trigger, this creates a nested sub-menu.
|
|
70
|
+
*/
|
|
71
|
+
label?: string;
|
|
72
|
+
/**
|
|
73
|
+
* Callback fired when the component is opened or closed.
|
|
74
|
+
* @param open whether or not the menu is open
|
|
75
|
+
*/
|
|
76
|
+
onOpenChange?: (open: boolean) => void;
|
|
77
|
+
};
|
|
78
|
+
|
|
79
|
+
export declare const MenuSeparator: ({ className, ...props }: MenuSeparatorProps) => JSX.Element;
|
|
80
|
+
|
|
81
|
+
declare type MenuSeparatorProps = React_2.HTMLAttributes<HTMLDivElement>;
|
|
82
|
+
|
|
83
|
+
export { }
|
package/dist/index.js
CHANGED
|
@@ -1,21 +1,464 @@
|
|
|
1
|
-
import { Menu as _ } from "./components/Menu/Menu.js";
|
|
2
|
-
import { MenuGroupLabel as n, MenuItem as t, MenuSeparator as u } from "./components/Menu/MenuItem.js";
|
|
3
1
|
/*!
|
|
4
|
-
@versini/ui-menu v5.
|
|
2
|
+
@versini/ui-menu v5.3.0
|
|
5
3
|
© 2025 gizmette.com
|
|
6
4
|
*/
|
|
7
5
|
try {
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
}
|
|
6
|
+
if (!window.__VERSINI_UI_MENU__) {
|
|
7
|
+
window.__VERSINI_UI_MENU__ = {
|
|
8
|
+
version: "5.3.0",
|
|
9
|
+
buildTime: "11/04/2025 03:44 PM EST",
|
|
10
|
+
homepage: "https://github.com/aversini/ui-components",
|
|
11
|
+
license: "MIT",
|
|
12
|
+
};
|
|
13
|
+
}
|
|
14
|
+
} catch (error) {
|
|
15
|
+
// nothing to declare officer
|
|
15
16
|
}
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
17
|
+
|
|
18
|
+
import { jsx, jsxs } from "react/jsx-runtime";
|
|
19
|
+
import { FloatingFocusManager, FloatingList, FloatingNode, FloatingPortal, FloatingTree, autoUpdate, flip, offset, safePolygon, shift, useClick, useDismiss, useFloating, useFloatingNodeId, useFloatingParentNodeId, useFloatingTree, useHover, useInteractions, useListItem, useListNavigation, useMergeRefs, useRole, useTypeahead } from "@floating-ui/react";
|
|
20
|
+
import { IconNext, IconSelected, IconUnSelected } from "@versini/ui-icons";
|
|
21
|
+
import clsx from "clsx";
|
|
22
|
+
import react, { createContext, forwardRef, useContext, useEffect, useRef, useState } from "react";
|
|
23
|
+
|
|
24
|
+
;// CONCATENATED MODULE: external "react/jsx-runtime"
|
|
25
|
+
|
|
26
|
+
;// CONCATENATED MODULE: external "@floating-ui/react"
|
|
27
|
+
|
|
28
|
+
;// CONCATENATED MODULE: external "@versini/ui-icons"
|
|
29
|
+
|
|
30
|
+
;// CONCATENATED MODULE: external "clsx"
|
|
31
|
+
|
|
32
|
+
;// CONCATENATED MODULE: external "react"
|
|
33
|
+
|
|
34
|
+
;// CONCATENATED MODULE: ./src/components/Menu/MenuContext.tsx
|
|
35
|
+
|
|
36
|
+
const MenuContext = /*#__PURE__*/ createContext({
|
|
37
|
+
getItemProps: ()=>({}),
|
|
38
|
+
activeIndex: null,
|
|
39
|
+
/* v8 ignore next 2 */ setActiveIndex: ()=>{},
|
|
40
|
+
setHasFocusInside: ()=>{},
|
|
41
|
+
isOpen: false,
|
|
42
|
+
allowHover: false,
|
|
43
|
+
parent: null
|
|
44
|
+
});
|
|
45
|
+
|
|
46
|
+
;// CONCATENATED MODULE: ./src/components/Menu/utilities.ts
|
|
47
|
+
const getDisplayName = (element)=>{
|
|
48
|
+
if (typeof element === "string") {
|
|
49
|
+
return element;
|
|
50
|
+
}
|
|
51
|
+
if (typeof element === "function") {
|
|
52
|
+
return element.displayName || element.name || "Component";
|
|
53
|
+
}
|
|
54
|
+
if (typeof element === "object" && element !== null && "type" in element) {
|
|
55
|
+
const type = element.type;
|
|
56
|
+
if (typeof type === "function" || typeof type === "object") {
|
|
57
|
+
return type.displayName || type.name || "Component";
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
return "Element";
|
|
21
61
|
};
|
|
62
|
+
|
|
63
|
+
;// CONCATENATED MODULE: ./src/components/Menu/Menu.tsx
|
|
64
|
+
|
|
65
|
+
|
|
66
|
+
|
|
67
|
+
|
|
68
|
+
|
|
69
|
+
|
|
70
|
+
|
|
71
|
+
const MenuComponent = /*#__PURE__*/ forwardRef(({ trigger, children, label = "Open menu", defaultPlacement = "bottom-start", onOpenChange, mode = "system", focusMode = "system", ...props }, forwardedRef)=>{
|
|
72
|
+
const [isOpen, setIsOpen] = useState(false);
|
|
73
|
+
const [hasFocusInside, setHasFocusInside] = useState(false);
|
|
74
|
+
const [activeIndex, setActiveIndex] = useState(null);
|
|
75
|
+
const [allowHover, setAllowHover] = useState(false);
|
|
76
|
+
const elementsRef = useRef([]);
|
|
77
|
+
const labelsRef = useRef([]);
|
|
78
|
+
const parent = useContext(MenuContext);
|
|
79
|
+
const tree = useFloatingTree();
|
|
80
|
+
const nodeId = useFloatingNodeId();
|
|
81
|
+
const parentId = useFloatingParentNodeId();
|
|
82
|
+
const item = useListItem({
|
|
83
|
+
label: label !== "Open menu" ? label : null
|
|
84
|
+
});
|
|
85
|
+
const isNested = parentId != null;
|
|
86
|
+
const { floatingStyles, refs, context } = useFloating({
|
|
87
|
+
nodeId,
|
|
88
|
+
open: isOpen,
|
|
89
|
+
onOpenChange: (args)=>{
|
|
90
|
+
setIsOpen(args);
|
|
91
|
+
onOpenChange?.(args);
|
|
92
|
+
},
|
|
93
|
+
placement: isNested ? "right-start" : defaultPlacement,
|
|
94
|
+
strategy: "fixed",
|
|
95
|
+
middleware: [
|
|
96
|
+
offset(()=>{
|
|
97
|
+
/**
|
|
98
|
+
* For nested menus, account for responsive padding differences.
|
|
99
|
+
* The menu has p-4 (16px) on mobile and p-2 (8px) on sm+ breakpoints.
|
|
100
|
+
* At 640px (Tailwind's sm breakpoint), padding changes from 16px to 8px.
|
|
101
|
+
* We increase the offset at mobile sizes to compensate for the larger padding.
|
|
102
|
+
*/ if (isNested) {
|
|
103
|
+
const isMobile = window.innerWidth < 640;
|
|
104
|
+
return {
|
|
105
|
+
mainAxis: isMobile ? 22 : 14,
|
|
106
|
+
alignmentAxis: -4
|
|
107
|
+
};
|
|
108
|
+
}
|
|
109
|
+
return {
|
|
110
|
+
mainAxis: 10,
|
|
111
|
+
alignmentAxis: 0
|
|
112
|
+
};
|
|
113
|
+
}),
|
|
114
|
+
flip(),
|
|
115
|
+
shift()
|
|
116
|
+
],
|
|
117
|
+
whileElementsMounted: autoUpdate
|
|
118
|
+
});
|
|
119
|
+
const hover = useHover(context, {
|
|
120
|
+
enabled: isNested && allowHover,
|
|
121
|
+
delay: {
|
|
122
|
+
open: 75
|
|
123
|
+
},
|
|
124
|
+
handleClose: safePolygon({
|
|
125
|
+
blockPointerEvents: true
|
|
126
|
+
})
|
|
127
|
+
});
|
|
128
|
+
const click = useClick(context, {
|
|
129
|
+
event: "mousedown",
|
|
130
|
+
toggle: !isNested || !allowHover,
|
|
131
|
+
ignoreMouse: isNested && allowHover
|
|
132
|
+
});
|
|
133
|
+
const role = useRole(context, {
|
|
134
|
+
role: "menu"
|
|
135
|
+
});
|
|
136
|
+
const dismiss = useDismiss(context, {
|
|
137
|
+
bubbles: true
|
|
138
|
+
});
|
|
139
|
+
const listNavigation = useListNavigation(context, {
|
|
140
|
+
listRef: elementsRef,
|
|
141
|
+
activeIndex,
|
|
142
|
+
nested: isNested,
|
|
143
|
+
onNavigate: setActiveIndex,
|
|
144
|
+
loop: true
|
|
145
|
+
});
|
|
146
|
+
const typeahead = useTypeahead(context, {
|
|
147
|
+
listRef: labelsRef,
|
|
148
|
+
onMatch: isOpen ? setActiveIndex : undefined,
|
|
149
|
+
activeIndex
|
|
150
|
+
});
|
|
151
|
+
const { getReferenceProps, getFloatingProps, getItemProps } = useInteractions([
|
|
152
|
+
hover,
|
|
153
|
+
click,
|
|
154
|
+
role,
|
|
155
|
+
dismiss,
|
|
156
|
+
listNavigation,
|
|
157
|
+
typeahead
|
|
158
|
+
]);
|
|
159
|
+
const mergedRef = useMergeRefs([
|
|
160
|
+
refs.setReference,
|
|
161
|
+
item.ref,
|
|
162
|
+
forwardedRef
|
|
163
|
+
]);
|
|
164
|
+
// Event emitter allows you to communicate across tree components.
|
|
165
|
+
// This effect closes all menus when an item gets clicked anywhere in the tree.
|
|
166
|
+
useEffect(()=>{
|
|
167
|
+
/* v8 ignore next 3 */ if (!tree) {
|
|
168
|
+
return;
|
|
169
|
+
}
|
|
170
|
+
function handleTreeClick() {
|
|
171
|
+
setIsOpen(false);
|
|
172
|
+
onOpenChange?.(false);
|
|
173
|
+
}
|
|
174
|
+
function onSubMenuOpen(event) {
|
|
175
|
+
if (event.nodeId !== nodeId && event.parentId === parentId) {
|
|
176
|
+
setIsOpen(false);
|
|
177
|
+
}
|
|
178
|
+
}
|
|
179
|
+
tree.events.on("click", handleTreeClick);
|
|
180
|
+
tree.events.on("menuopen", onSubMenuOpen);
|
|
181
|
+
return ()=>{
|
|
182
|
+
tree.events.off("click", handleTreeClick);
|
|
183
|
+
tree.events.off("menuopen", onSubMenuOpen);
|
|
184
|
+
};
|
|
185
|
+
}, [
|
|
186
|
+
tree,
|
|
187
|
+
nodeId,
|
|
188
|
+
parentId,
|
|
189
|
+
onOpenChange
|
|
190
|
+
]);
|
|
191
|
+
useEffect(()=>{
|
|
192
|
+
if (isOpen && tree) {
|
|
193
|
+
tree.events.emit("menuopen", {
|
|
194
|
+
parentId,
|
|
195
|
+
nodeId
|
|
196
|
+
});
|
|
197
|
+
}
|
|
198
|
+
}, [
|
|
199
|
+
tree,
|
|
200
|
+
isOpen,
|
|
201
|
+
nodeId,
|
|
202
|
+
parentId
|
|
203
|
+
]);
|
|
204
|
+
// Determine if "hover" logic can run based on input modality.
|
|
205
|
+
// This prevents unwanted focus sync as menus open/close with keyboard nav.
|
|
206
|
+
useEffect(()=>{
|
|
207
|
+
function onPointerMove({ pointerType }) {
|
|
208
|
+
if (pointerType !== "touch") {
|
|
209
|
+
setAllowHover(true);
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
function onKeyDown() {
|
|
213
|
+
setAllowHover(false);
|
|
214
|
+
}
|
|
215
|
+
window.addEventListener("pointermove", onPointerMove, {
|
|
216
|
+
once: true,
|
|
217
|
+
capture: true
|
|
218
|
+
});
|
|
219
|
+
window.addEventListener("keydown", onKeyDown, true);
|
|
220
|
+
return ()=>{
|
|
221
|
+
window.removeEventListener("pointermove", onPointerMove, {
|
|
222
|
+
capture: true
|
|
223
|
+
});
|
|
224
|
+
window.removeEventListener("keydown", onKeyDown, true);
|
|
225
|
+
};
|
|
226
|
+
}, []);
|
|
227
|
+
const noInternalClick = getDisplayName(trigger) === "Button" || getDisplayName(trigger) === "ButtonIcon";
|
|
228
|
+
const uiButtonsExtraProps = noInternalClick ? {
|
|
229
|
+
noInternalClick,
|
|
230
|
+
focusMode,
|
|
231
|
+
mode
|
|
232
|
+
} : {};
|
|
233
|
+
// For nested menus (sub-menus), render as a menu item trigger
|
|
234
|
+
if (isNested && !trigger) {
|
|
235
|
+
const buttonClass = clsx("flex items-center flex-row justify-between", "w-full", "m-0 first:mt-0 mt-2 sm:mt-1 px-2 py-1", "rounded-md border border-transparent", "text-left text-base", "outline-hidden focus:border focus:border-border-medium focus:bg-surface-lighter focus:underline", "disabled:cursor-not-allowed disabled:text-copy-medium", {
|
|
236
|
+
"bg-surface-lighter": isOpen && !hasFocusInside
|
|
237
|
+
});
|
|
238
|
+
return /*#__PURE__*/ jsxs(FloatingNode, {
|
|
239
|
+
id: nodeId,
|
|
240
|
+
children: [
|
|
241
|
+
/*#__PURE__*/ jsxs("button", {
|
|
242
|
+
ref: mergedRef,
|
|
243
|
+
"data-open": isOpen ? "" : undefined,
|
|
244
|
+
...getReferenceProps(parent.getItemProps({
|
|
245
|
+
...props,
|
|
246
|
+
className: buttonClass,
|
|
247
|
+
onFocus (event) {
|
|
248
|
+
props.onFocus?.(event);
|
|
249
|
+
setHasFocusInside(false);
|
|
250
|
+
parent.setHasFocusInside(true);
|
|
251
|
+
},
|
|
252
|
+
onMouseEnter (event) {
|
|
253
|
+
props.onMouseEnter?.(event);
|
|
254
|
+
if (parent.allowHover && parent.isOpen) {
|
|
255
|
+
parent.setActiveIndex(item.index);
|
|
256
|
+
}
|
|
257
|
+
}
|
|
258
|
+
})),
|
|
259
|
+
children: [
|
|
260
|
+
/*#__PURE__*/ jsx("span", {
|
|
261
|
+
children: label
|
|
262
|
+
}),
|
|
263
|
+
/*#__PURE__*/ jsx(IconNext, {
|
|
264
|
+
className: "ml-2",
|
|
265
|
+
size: "size-3",
|
|
266
|
+
monotone: true
|
|
267
|
+
})
|
|
268
|
+
]
|
|
269
|
+
}),
|
|
270
|
+
/*#__PURE__*/ jsx(MenuContext.Provider, {
|
|
271
|
+
value: {
|
|
272
|
+
activeIndex,
|
|
273
|
+
setActiveIndex,
|
|
274
|
+
getItemProps,
|
|
275
|
+
setHasFocusInside,
|
|
276
|
+
isOpen,
|
|
277
|
+
allowHover,
|
|
278
|
+
parent
|
|
279
|
+
},
|
|
280
|
+
children: /*#__PURE__*/ jsx(FloatingList, {
|
|
281
|
+
elementsRef: elementsRef,
|
|
282
|
+
labelsRef: labelsRef,
|
|
283
|
+
children: isOpen && /*#__PURE__*/ jsx(FloatingPortal, {
|
|
284
|
+
children: /*#__PURE__*/ jsx(FloatingFocusManager, {
|
|
285
|
+
context: context,
|
|
286
|
+
modal: false,
|
|
287
|
+
initialFocus: -1,
|
|
288
|
+
returnFocus: false,
|
|
289
|
+
children: /*#__PURE__*/ jsx("div", {
|
|
290
|
+
ref: refs.setFloating,
|
|
291
|
+
className: "rounded-md bg-surface-light shadow-sm shadow-border-dark outline-hidden p-3 sm:p-2",
|
|
292
|
+
style: floatingStyles,
|
|
293
|
+
...getFloatingProps(),
|
|
294
|
+
children: children
|
|
295
|
+
})
|
|
296
|
+
})
|
|
297
|
+
})
|
|
298
|
+
})
|
|
299
|
+
})
|
|
300
|
+
]
|
|
301
|
+
});
|
|
302
|
+
}
|
|
303
|
+
const triggerElement = /*#__PURE__*/ react.cloneElement(trigger, {
|
|
304
|
+
...uiButtonsExtraProps,
|
|
305
|
+
"aria-label": label,
|
|
306
|
+
"data-open": isOpen ? "" : undefined,
|
|
307
|
+
"data-focus-inside": hasFocusInside ? "" : undefined,
|
|
308
|
+
ref: mergedRef,
|
|
309
|
+
...getReferenceProps(parent.getItemProps({
|
|
310
|
+
...props
|
|
311
|
+
}))
|
|
312
|
+
});
|
|
313
|
+
return /*#__PURE__*/ jsxs(FloatingNode, {
|
|
314
|
+
id: nodeId,
|
|
315
|
+
children: [
|
|
316
|
+
triggerElement,
|
|
317
|
+
/*#__PURE__*/ jsx(MenuContext.Provider, {
|
|
318
|
+
value: {
|
|
319
|
+
activeIndex,
|
|
320
|
+
setActiveIndex,
|
|
321
|
+
getItemProps,
|
|
322
|
+
setHasFocusInside,
|
|
323
|
+
isOpen,
|
|
324
|
+
allowHover,
|
|
325
|
+
parent
|
|
326
|
+
},
|
|
327
|
+
children: /*#__PURE__*/ jsx(FloatingList, {
|
|
328
|
+
elementsRef: elementsRef,
|
|
329
|
+
labelsRef: labelsRef,
|
|
330
|
+
children: isOpen && /*#__PURE__*/ jsx(FloatingPortal, {
|
|
331
|
+
children: /*#__PURE__*/ jsx(FloatingFocusManager, {
|
|
332
|
+
context: context,
|
|
333
|
+
modal: false,
|
|
334
|
+
initialFocus: 0,
|
|
335
|
+
returnFocus: true,
|
|
336
|
+
children: /*#__PURE__*/ jsx("div", {
|
|
337
|
+
ref: refs.setFloating,
|
|
338
|
+
className: "rounded-md bg-surface-light shadow-sm shadow-border-dark outline-hidden p-3 sm:p-2",
|
|
339
|
+
style: floatingStyles,
|
|
340
|
+
...getFloatingProps(),
|
|
341
|
+
children: children
|
|
342
|
+
})
|
|
343
|
+
})
|
|
344
|
+
})
|
|
345
|
+
})
|
|
346
|
+
})
|
|
347
|
+
]
|
|
348
|
+
});
|
|
349
|
+
});
|
|
350
|
+
const Menu = /*#__PURE__*/ forwardRef((props, ref)=>{
|
|
351
|
+
const parentId = useFloatingParentNodeId();
|
|
352
|
+
// If parentId is null, this is a root menu - wrap in FloatingTree
|
|
353
|
+
if (parentId === null) {
|
|
354
|
+
return /*#__PURE__*/ jsx(FloatingTree, {
|
|
355
|
+
children: /*#__PURE__*/ jsx(MenuComponent, {
|
|
356
|
+
...props,
|
|
357
|
+
ref: ref
|
|
358
|
+
})
|
|
359
|
+
});
|
|
360
|
+
}
|
|
361
|
+
// This is a nested sub-menu - don't wrap in FloatingTree
|
|
362
|
+
return /*#__PURE__*/ jsx(MenuComponent, {
|
|
363
|
+
...props,
|
|
364
|
+
ref: ref
|
|
365
|
+
});
|
|
366
|
+
});
|
|
367
|
+
Menu.displayName = "Menu";
|
|
368
|
+
MenuComponent.displayName = "MenuComponent";
|
|
369
|
+
|
|
370
|
+
;// CONCATENATED MODULE: ./src/components/Menu/MenuItem.tsx
|
|
371
|
+
|
|
372
|
+
|
|
373
|
+
|
|
374
|
+
|
|
375
|
+
|
|
376
|
+
|
|
377
|
+
const MenuItem = /*#__PURE__*/ forwardRef(({ label, disabled, icon, raw = false, children, ignoreClick = false, selected, ...props }, forwardedRef)=>{
|
|
378
|
+
let buttonSpanClass = "";
|
|
379
|
+
const menu = useContext(MenuContext);
|
|
380
|
+
const item = useListItem({
|
|
381
|
+
label: disabled ? null : label
|
|
382
|
+
});
|
|
383
|
+
const tree = useFloatingTree();
|
|
384
|
+
const mergedRef = useMergeRefs([
|
|
385
|
+
item.ref,
|
|
386
|
+
forwardedRef
|
|
387
|
+
]);
|
|
388
|
+
if (raw && children) {
|
|
389
|
+
return /*#__PURE__*/ jsx("div", {
|
|
390
|
+
role: "menuitem",
|
|
391
|
+
...menu.getItemProps({
|
|
392
|
+
onClick (event) {
|
|
393
|
+
if (!ignoreClick) {
|
|
394
|
+
props.onClick?.(event);
|
|
395
|
+
tree?.events.emit("click");
|
|
396
|
+
}
|
|
397
|
+
}
|
|
398
|
+
}),
|
|
399
|
+
children: children
|
|
400
|
+
});
|
|
401
|
+
}
|
|
402
|
+
if (icon) {
|
|
403
|
+
buttonSpanClass = "pl-2";
|
|
404
|
+
}
|
|
405
|
+
const buttonClass = clsx("flex flex-row items-center", "w-full", "m-0 first:mt-0 mt-2 sm:mt-1 px-2 py-1", "rounded-md border border-transparent", "text-left text-base", "outline-hidden focus:border focus:border-border-medium focus:bg-surface-lighter focus:underline", "disabled:cursor-not-allowed disabled:text-copy-medium", {
|
|
406
|
+
"bg-none": !disabled && !selected
|
|
407
|
+
});
|
|
408
|
+
return /*#__PURE__*/ jsxs("button", {
|
|
409
|
+
...props,
|
|
410
|
+
ref: mergedRef,
|
|
411
|
+
role: "menuitem",
|
|
412
|
+
className: buttonClass,
|
|
413
|
+
tabIndex: 0,
|
|
414
|
+
disabled: disabled,
|
|
415
|
+
...menu.getItemProps({
|
|
416
|
+
onClick (event) {
|
|
417
|
+
if (!ignoreClick) {
|
|
418
|
+
props.onClick?.(event);
|
|
419
|
+
tree?.events.emit("click");
|
|
420
|
+
}
|
|
421
|
+
},
|
|
422
|
+
onFocus (event) {
|
|
423
|
+
props.onFocus?.(event);
|
|
424
|
+
menu.setHasFocusInside(true);
|
|
425
|
+
}
|
|
426
|
+
}),
|
|
427
|
+
children: [
|
|
428
|
+
selected === true && /*#__PURE__*/ jsx(IconSelected, {
|
|
429
|
+
className: "text-copy-success mr-2",
|
|
430
|
+
size: "size-4"
|
|
431
|
+
}),
|
|
432
|
+
selected === false && /*#__PURE__*/ jsx(IconUnSelected, {
|
|
433
|
+
className: "text-copy-medium mr-2",
|
|
434
|
+
size: "size-4"
|
|
435
|
+
}),
|
|
436
|
+
icon,
|
|
437
|
+
label && /*#__PURE__*/ jsx("span", {
|
|
438
|
+
className: buttonSpanClass,
|
|
439
|
+
children: label
|
|
440
|
+
})
|
|
441
|
+
]
|
|
442
|
+
});
|
|
443
|
+
});
|
|
444
|
+
MenuItem.displayName = "MenuItem";
|
|
445
|
+
const MenuSeparator = ({ className, ...props })=>{
|
|
446
|
+
const separatorClass = clsx(className, "my-1 border-t border-border-medium");
|
|
447
|
+
return /*#__PURE__*/ jsx("div", {
|
|
448
|
+
className: separatorClass,
|
|
449
|
+
...props
|
|
450
|
+
});
|
|
451
|
+
};
|
|
452
|
+
const MenuGroupLabel = ({ className, ...props })=>{
|
|
453
|
+
const groupLabelClass = clsx(className, "pt-1 mb-2", "text-sm text-copy-dark font-bold", "border-b border-border-medium");
|
|
454
|
+
return /*#__PURE__*/ jsx("div", {
|
|
455
|
+
className: groupLabelClass,
|
|
456
|
+
...props
|
|
457
|
+
});
|
|
458
|
+
};
|
|
459
|
+
|
|
460
|
+
;// CONCATENATED MODULE: ./src/components/index.ts
|
|
461
|
+
|
|
462
|
+
|
|
463
|
+
|
|
464
|
+
export { Menu, MenuGroupLabel, MenuItem, MenuSeparator };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@versini/ui-menu",
|
|
3
|
-
"version": "5.
|
|
3
|
+
"version": "5.3.0",
|
|
4
4
|
"license": "MIT",
|
|
5
5
|
"author": "Arno Versini",
|
|
6
6
|
"publishConfig": {
|
|
@@ -20,13 +20,13 @@
|
|
|
20
20
|
],
|
|
21
21
|
"scripts": {
|
|
22
22
|
"build:check": "tsc",
|
|
23
|
-
"build:js": "
|
|
24
|
-
"build:types": "
|
|
25
|
-
"build": "npm-run-all --serial clean build:check build:js
|
|
23
|
+
"build:js": "rslib build",
|
|
24
|
+
"build:types": "echo 'Types now built with rslib'",
|
|
25
|
+
"build": "npm-run-all --serial clean build:check build:js",
|
|
26
26
|
"clean": "rimraf dist tmp",
|
|
27
|
-
"dev:js": "
|
|
28
|
-
"dev:types": "
|
|
29
|
-
"dev": "
|
|
27
|
+
"dev:js": "rslib build --watch",
|
|
28
|
+
"dev:types": "echo 'Types now watched with rslib'",
|
|
29
|
+
"dev": "rslib build --watch",
|
|
30
30
|
"lint": "biome lint src",
|
|
31
31
|
"lint:fix": "biome check src --write --no-errors-on-unmatched",
|
|
32
32
|
"prettier": "biome check --write --no-errors-on-unmatched",
|
|
@@ -43,12 +43,12 @@
|
|
|
43
43
|
"dependencies": {
|
|
44
44
|
"@floating-ui/react": "0.27.16",
|
|
45
45
|
"@tailwindcss/typography": "0.5.19",
|
|
46
|
-
"@versini/ui-icons": "4.
|
|
46
|
+
"@versini/ui-icons": "4.15.1",
|
|
47
47
|
"clsx": "2.1.1",
|
|
48
48
|
"tailwindcss": "4.1.16"
|
|
49
49
|
},
|
|
50
50
|
"sideEffects": [
|
|
51
51
|
"**/*.css"
|
|
52
52
|
],
|
|
53
|
-
"gitHead": "
|
|
53
|
+
"gitHead": "7484ad443b77ef31e52ae3a7d88b8129bc6cdf1d"
|
|
54
54
|
}
|
|
@@ -1,61 +0,0 @@
|
|
|
1
|
-
import { jsxs as I, jsx as a } from "react/jsx-runtime";
|
|
2
|
-
import m from "clsx";
|
|
3
|
-
const d = ({
|
|
4
|
-
children: o,
|
|
5
|
-
fill: s,
|
|
6
|
-
viewBox: t,
|
|
7
|
-
className: n,
|
|
8
|
-
defaultViewBox: _,
|
|
9
|
-
size: l,
|
|
10
|
-
title: e,
|
|
11
|
-
semantic: i = !1,
|
|
12
|
-
...r
|
|
13
|
-
}) => {
|
|
14
|
-
const c = m(l, n);
|
|
15
|
-
return /* @__PURE__ */ I(
|
|
16
|
-
"svg",
|
|
17
|
-
{
|
|
18
|
-
xmlns: "http://www.w3.org/2000/svg",
|
|
19
|
-
className: c,
|
|
20
|
-
viewBox: t || _,
|
|
21
|
-
fill: s || "currentColor",
|
|
22
|
-
role: "img",
|
|
23
|
-
"aria-hidden": !i,
|
|
24
|
-
focusable: !1,
|
|
25
|
-
...r,
|
|
26
|
-
children: [
|
|
27
|
-
e && i && /* @__PURE__ */ a("title", { children: e }),
|
|
28
|
-
o
|
|
29
|
-
]
|
|
30
|
-
}
|
|
31
|
-
);
|
|
32
|
-
};
|
|
33
|
-
/*!
|
|
34
|
-
@versini/ui-svgicon v4.2.2
|
|
35
|
-
© 2025 gizmette.com
|
|
36
|
-
*/
|
|
37
|
-
try {
|
|
38
|
-
window.__VERSINI_UI_SVGICON__ || (window.__VERSINI_UI_SVGICON__ = {
|
|
39
|
-
version: "4.2.2",
|
|
40
|
-
buildTime: "10/24/2025 06:42 PM EDT",
|
|
41
|
-
homepage: "https://github.com/aversini/ui-components",
|
|
42
|
-
license: "MIT"
|
|
43
|
-
});
|
|
44
|
-
} catch {
|
|
45
|
-
}
|
|
46
|
-
/*!
|
|
47
|
-
@versini/ui-icons v4.14.1
|
|
48
|
-
© 2025 gizmette.com
|
|
49
|
-
*/
|
|
50
|
-
try {
|
|
51
|
-
window.__VERSINI_UI_ICONS__ || (window.__VERSINI_UI_ICONS__ = {
|
|
52
|
-
version: "4.14.1",
|
|
53
|
-
buildTime: "10/24/2025 06:42 PM EDT",
|
|
54
|
-
homepage: "https://github.com/aversini/ui-components",
|
|
55
|
-
license: "MIT"
|
|
56
|
-
});
|
|
57
|
-
} catch {
|
|
58
|
-
}
|
|
59
|
-
export {
|
|
60
|
-
d as I
|
|
61
|
-
};
|
|
@@ -1,258 +0,0 @@
|
|
|
1
|
-
import { jsxs as b, jsx as t } from "react/jsx-runtime";
|
|
2
|
-
import { useFloatingTree as se, useFloatingNodeId as ie, useFloatingParentNodeId as W, useListItem as re, useFloating as ae, autoUpdate as le, offset as de, flip as ue, shift as ce, useHover as fe, safePolygon as me, useClick as pe, useRole as he, useDismiss as ve, useListNavigation as ge, useTypeahead as we, useInteractions as ye, useMergeRefs as be, FloatingNode as D, FloatingList as S, FloatingPortal as _, FloatingFocusManager as K, FloatingTree as xe } from "@floating-ui/react";
|
|
3
|
-
import { I as Ie } from "../../chunks/index.Benv90bx.js";
|
|
4
|
-
import Fe from "clsx";
|
|
5
|
-
import Ne, { forwardRef as q, useState as y, useRef as U, useContext as Me, useEffect as P } from "react";
|
|
6
|
-
import { MenuContext as R } from "./MenuContext.js";
|
|
7
|
-
const Ee = ({
|
|
8
|
-
className: e,
|
|
9
|
-
viewBox: n,
|
|
10
|
-
title: d,
|
|
11
|
-
monotone: x,
|
|
12
|
-
...f
|
|
13
|
-
}) => /* @__PURE__ */ b(
|
|
14
|
-
Ie,
|
|
15
|
-
{
|
|
16
|
-
defaultViewBox: "0 0 448 512",
|
|
17
|
-
size: "size-5",
|
|
18
|
-
viewBox: n,
|
|
19
|
-
className: e,
|
|
20
|
-
title: d || "Next",
|
|
21
|
-
...f,
|
|
22
|
-
children: [
|
|
23
|
-
/* @__PURE__ */ t(
|
|
24
|
-
"path",
|
|
25
|
-
{
|
|
26
|
-
d: "M0 256c0 17.7 14.3 32 32 32h306.7l32-32-32-32H32c-17.7 0-32 14.3-32 32",
|
|
27
|
-
opacity: x ? "1" : "0.4"
|
|
28
|
-
}
|
|
29
|
-
),
|
|
30
|
-
/* @__PURE__ */ t("path", { d: "M438.6 233.4c12.5 12.5 12.5 32.8 0 45.3l-160 160c-12.5 12.5-32.8 12.5-45.3 0s-12.5-32.8 0-45.3L370.7 256 233.4 118.6c-12.5-12.5-12.5-32.8 0-45.3s32.8-12.5 45.3 0l160 160z" })
|
|
31
|
-
]
|
|
32
|
-
}
|
|
33
|
-
), V = (e) => {
|
|
34
|
-
if (typeof e == "string")
|
|
35
|
-
return e;
|
|
36
|
-
if (typeof e == "function")
|
|
37
|
-
return e.displayName || e.name || "Component";
|
|
38
|
-
if (typeof e == "object" && e !== null && "type" in e) {
|
|
39
|
-
const n = e.type;
|
|
40
|
-
if (typeof n == "function" || typeof n == "object")
|
|
41
|
-
return n.displayName || n.name || "Component";
|
|
42
|
-
}
|
|
43
|
-
return "Element";
|
|
44
|
-
}, k = q(
|
|
45
|
-
({
|
|
46
|
-
trigger: e,
|
|
47
|
-
children: n,
|
|
48
|
-
label: d = "Open menu",
|
|
49
|
-
defaultPlacement: x = "bottom-start",
|
|
50
|
-
onOpenChange: f,
|
|
51
|
-
mode: G = "system",
|
|
52
|
-
focusMode: J = "system",
|
|
53
|
-
...h
|
|
54
|
-
}, Q) => {
|
|
55
|
-
const [o, I] = y(!1), [C, F] = y(!1), [v, g] = y(null), [m, L] = y(!1), N = U([]), M = U([]), a = Me(R), i = se(), u = ie(), p = W(), A = re({ label: d !== "Open menu" ? d : null }), c = p != null, { floatingStyles: H, refs: E, context: l } = ae({
|
|
56
|
-
nodeId: u,
|
|
57
|
-
open: o,
|
|
58
|
-
onOpenChange: (s) => {
|
|
59
|
-
I(s), f?.(s);
|
|
60
|
-
},
|
|
61
|
-
placement: c ? "right-start" : x,
|
|
62
|
-
strategy: "fixed",
|
|
63
|
-
middleware: [
|
|
64
|
-
de(() => c ? {
|
|
65
|
-
mainAxis: window.innerWidth < 640 ? 22 : 14,
|
|
66
|
-
alignmentAxis: -4
|
|
67
|
-
} : {
|
|
68
|
-
mainAxis: 10,
|
|
69
|
-
alignmentAxis: 0
|
|
70
|
-
}),
|
|
71
|
-
ue(),
|
|
72
|
-
ce()
|
|
73
|
-
],
|
|
74
|
-
whileElementsMounted: le
|
|
75
|
-
}), X = fe(l, {
|
|
76
|
-
enabled: c && m,
|
|
77
|
-
delay: { open: 75 },
|
|
78
|
-
handleClose: me({ blockPointerEvents: !0 })
|
|
79
|
-
}), Y = pe(l, {
|
|
80
|
-
event: "mousedown",
|
|
81
|
-
toggle: !c || !m,
|
|
82
|
-
ignoreMouse: c && m
|
|
83
|
-
}), Z = he(l, { role: "menu" }), $ = ve(l, { bubbles: !0 }), ee = ge(l, {
|
|
84
|
-
listRef: N,
|
|
85
|
-
activeIndex: v,
|
|
86
|
-
nested: c,
|
|
87
|
-
onNavigate: g,
|
|
88
|
-
loop: !0
|
|
89
|
-
}), te = we(l, {
|
|
90
|
-
listRef: M,
|
|
91
|
-
onMatch: o ? g : void 0,
|
|
92
|
-
activeIndex: v
|
|
93
|
-
}), { getReferenceProps: B, getFloatingProps: j, getItemProps: z } = ye([X, Y, Z, $, ee, te]), O = be([E.setReference, A.ref, Q]);
|
|
94
|
-
P(() => {
|
|
95
|
-
if (!i)
|
|
96
|
-
return;
|
|
97
|
-
function s() {
|
|
98
|
-
I(!1), f?.(!1);
|
|
99
|
-
}
|
|
100
|
-
function r(w) {
|
|
101
|
-
w.nodeId !== u && w.parentId === p && I(!1);
|
|
102
|
-
}
|
|
103
|
-
return i.events.on("click", s), i.events.on("menuopen", r), () => {
|
|
104
|
-
i.events.off("click", s), i.events.off("menuopen", r);
|
|
105
|
-
};
|
|
106
|
-
}, [i, u, p, f]), P(() => {
|
|
107
|
-
o && i && i.events.emit("menuopen", { parentId: p, nodeId: u });
|
|
108
|
-
}, [i, o, u, p]), P(() => {
|
|
109
|
-
function s({ pointerType: w }) {
|
|
110
|
-
w !== "touch" && L(!0);
|
|
111
|
-
}
|
|
112
|
-
function r() {
|
|
113
|
-
L(!1);
|
|
114
|
-
}
|
|
115
|
-
return window.addEventListener("pointermove", s, {
|
|
116
|
-
once: !0,
|
|
117
|
-
capture: !0
|
|
118
|
-
}), window.addEventListener("keydown", r, !0), () => {
|
|
119
|
-
window.removeEventListener("pointermove", s, {
|
|
120
|
-
capture: !0
|
|
121
|
-
}), window.removeEventListener("keydown", r, !0);
|
|
122
|
-
};
|
|
123
|
-
}, []);
|
|
124
|
-
const T = V(e) === "Button" || V(e) === "ButtonIcon", ne = T ? {
|
|
125
|
-
noInternalClick: T,
|
|
126
|
-
focusMode: J,
|
|
127
|
-
mode: G
|
|
128
|
-
} : {};
|
|
129
|
-
if (c && !e) {
|
|
130
|
-
const s = Fe(
|
|
131
|
-
"flex items-center flex-row justify-between",
|
|
132
|
-
"w-full",
|
|
133
|
-
"m-0 first:mt-0 mt-2 sm:mt-1 px-2 py-1",
|
|
134
|
-
"rounded-md border border-transparent",
|
|
135
|
-
"text-left text-base",
|
|
136
|
-
"outline-hidden focus:border focus:border-border-medium focus:bg-surface-lighter focus:underline",
|
|
137
|
-
"disabled:cursor-not-allowed disabled:text-copy-medium",
|
|
138
|
-
{
|
|
139
|
-
"bg-surface-lighter": o && !C
|
|
140
|
-
}
|
|
141
|
-
);
|
|
142
|
-
return /* @__PURE__ */ b(D, { id: u, children: [
|
|
143
|
-
/* @__PURE__ */ b(
|
|
144
|
-
"button",
|
|
145
|
-
{
|
|
146
|
-
ref: O,
|
|
147
|
-
"data-open": o ? "" : void 0,
|
|
148
|
-
...B(
|
|
149
|
-
a.getItemProps({
|
|
150
|
-
...h,
|
|
151
|
-
className: s,
|
|
152
|
-
onFocus(r) {
|
|
153
|
-
h.onFocus?.(r), F(!1), a.setHasFocusInside(!0);
|
|
154
|
-
},
|
|
155
|
-
onMouseEnter(r) {
|
|
156
|
-
h.onMouseEnter?.(r), a.allowHover && a.isOpen && a.setActiveIndex(A.index);
|
|
157
|
-
}
|
|
158
|
-
})
|
|
159
|
-
),
|
|
160
|
-
children: [
|
|
161
|
-
/* @__PURE__ */ t("span", { children: d }),
|
|
162
|
-
/* @__PURE__ */ t(Ee, { className: "ml-2", size: "size-3", monotone: !0 })
|
|
163
|
-
]
|
|
164
|
-
}
|
|
165
|
-
),
|
|
166
|
-
/* @__PURE__ */ t(
|
|
167
|
-
R.Provider,
|
|
168
|
-
{
|
|
169
|
-
value: {
|
|
170
|
-
activeIndex: v,
|
|
171
|
-
setActiveIndex: g,
|
|
172
|
-
getItemProps: z,
|
|
173
|
-
setHasFocusInside: F,
|
|
174
|
-
isOpen: o,
|
|
175
|
-
allowHover: m,
|
|
176
|
-
parent: a
|
|
177
|
-
},
|
|
178
|
-
children: /* @__PURE__ */ t(S, { elementsRef: N, labelsRef: M, children: o && /* @__PURE__ */ t(_, { children: /* @__PURE__ */ t(
|
|
179
|
-
K,
|
|
180
|
-
{
|
|
181
|
-
context: l,
|
|
182
|
-
modal: !1,
|
|
183
|
-
initialFocus: -1,
|
|
184
|
-
returnFocus: !1,
|
|
185
|
-
children: /* @__PURE__ */ t(
|
|
186
|
-
"div",
|
|
187
|
-
{
|
|
188
|
-
ref: E.setFloating,
|
|
189
|
-
className: "rounded-md bg-surface-light shadow-sm shadow-border-dark outline-hidden p-3 sm:p-2",
|
|
190
|
-
style: H,
|
|
191
|
-
...j(),
|
|
192
|
-
children: n
|
|
193
|
-
}
|
|
194
|
-
)
|
|
195
|
-
}
|
|
196
|
-
) }) })
|
|
197
|
-
}
|
|
198
|
-
)
|
|
199
|
-
] });
|
|
200
|
-
}
|
|
201
|
-
const oe = Ne.cloneElement(
|
|
202
|
-
e,
|
|
203
|
-
{
|
|
204
|
-
...ne,
|
|
205
|
-
"aria-label": d,
|
|
206
|
-
"data-open": o ? "" : void 0,
|
|
207
|
-
"data-focus-inside": C ? "" : void 0,
|
|
208
|
-
ref: O,
|
|
209
|
-
...B(
|
|
210
|
-
a.getItemProps({
|
|
211
|
-
...h
|
|
212
|
-
})
|
|
213
|
-
)
|
|
214
|
-
}
|
|
215
|
-
);
|
|
216
|
-
return /* @__PURE__ */ b(D, { id: u, children: [
|
|
217
|
-
oe,
|
|
218
|
-
/* @__PURE__ */ t(
|
|
219
|
-
R.Provider,
|
|
220
|
-
{
|
|
221
|
-
value: {
|
|
222
|
-
activeIndex: v,
|
|
223
|
-
setActiveIndex: g,
|
|
224
|
-
getItemProps: z,
|
|
225
|
-
setHasFocusInside: F,
|
|
226
|
-
isOpen: o,
|
|
227
|
-
allowHover: m,
|
|
228
|
-
parent: a
|
|
229
|
-
},
|
|
230
|
-
children: /* @__PURE__ */ t(S, { elementsRef: N, labelsRef: M, children: o && /* @__PURE__ */ t(_, { children: /* @__PURE__ */ t(
|
|
231
|
-
K,
|
|
232
|
-
{
|
|
233
|
-
context: l,
|
|
234
|
-
modal: !1,
|
|
235
|
-
initialFocus: 0,
|
|
236
|
-
returnFocus: !0,
|
|
237
|
-
children: /* @__PURE__ */ t(
|
|
238
|
-
"div",
|
|
239
|
-
{
|
|
240
|
-
ref: E.setFloating,
|
|
241
|
-
className: "rounded-md bg-surface-light shadow-sm shadow-border-dark outline-hidden p-3 sm:p-2",
|
|
242
|
-
style: H,
|
|
243
|
-
...j(),
|
|
244
|
-
children: n
|
|
245
|
-
}
|
|
246
|
-
)
|
|
247
|
-
}
|
|
248
|
-
) }) })
|
|
249
|
-
}
|
|
250
|
-
)
|
|
251
|
-
] });
|
|
252
|
-
}
|
|
253
|
-
), Pe = q((e, n) => W() === null ? /* @__PURE__ */ t(xe, { children: /* @__PURE__ */ t(k, { ...e, ref: n }) }) : /* @__PURE__ */ t(k, { ...e, ref: n }));
|
|
254
|
-
Pe.displayName = "Menu";
|
|
255
|
-
k.displayName = "MenuComponent";
|
|
256
|
-
export {
|
|
257
|
-
Pe as Menu
|
|
258
|
-
};
|
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
import * as e from "react";
|
|
2
|
-
const t = e.createContext({
|
|
3
|
-
getItemProps: () => ({}),
|
|
4
|
-
activeIndex: null,
|
|
5
|
-
/* v8 ignore next 2 */
|
|
6
|
-
setActiveIndex: () => {
|
|
7
|
-
},
|
|
8
|
-
setHasFocusInside: () => {
|
|
9
|
-
},
|
|
10
|
-
isOpen: !1,
|
|
11
|
-
allowHover: !1,
|
|
12
|
-
parent: null
|
|
13
|
-
});
|
|
14
|
-
export {
|
|
15
|
-
t as MenuContext
|
|
16
|
-
};
|
|
@@ -1,136 +0,0 @@
|
|
|
1
|
-
import { jsxs as x, jsx as s } from "react/jsx-runtime";
|
|
2
|
-
import { useListItem as C, useFloatingTree as M, useMergeRefs as g } from "@floating-ui/react";
|
|
3
|
-
import { I as b } from "../../chunks/index.Benv90bx.js";
|
|
4
|
-
import l from "clsx";
|
|
5
|
-
import * as p from "react";
|
|
6
|
-
import { MenuContext as h } from "./MenuContext.js";
|
|
7
|
-
const z = ({
|
|
8
|
-
className: e,
|
|
9
|
-
viewBox: t,
|
|
10
|
-
title: o,
|
|
11
|
-
monotone: a,
|
|
12
|
-
...r
|
|
13
|
-
}) => /* @__PURE__ */ x(
|
|
14
|
-
b,
|
|
15
|
-
{
|
|
16
|
-
defaultViewBox: "0 0 512 512",
|
|
17
|
-
size: "size-5",
|
|
18
|
-
viewBox: t,
|
|
19
|
-
className: e,
|
|
20
|
-
title: o || "Selected",
|
|
21
|
-
...r,
|
|
22
|
-
children: [
|
|
23
|
-
/* @__PURE__ */ s(
|
|
24
|
-
"path",
|
|
25
|
-
{
|
|
26
|
-
d: "M0 256a256 256 0 1 0 512 0 256 256 0 1 0-512 0m352 0a96 96 0 1 1-192 0 96 96 0 1 1 192 0",
|
|
27
|
-
opacity: ".4"
|
|
28
|
-
}
|
|
29
|
-
),
|
|
30
|
-
/* @__PURE__ */ s("path", { d: "M256 160a96 96 0 1 0 0 192 96 96 0 1 0 0-192" })
|
|
31
|
-
]
|
|
32
|
-
}
|
|
33
|
-
), I = ({
|
|
34
|
-
className: e,
|
|
35
|
-
viewBox: t,
|
|
36
|
-
title: o,
|
|
37
|
-
monotone: a,
|
|
38
|
-
...r
|
|
39
|
-
}) => /* @__PURE__ */ s(
|
|
40
|
-
b,
|
|
41
|
-
{
|
|
42
|
-
defaultViewBox: "0 0 512 512",
|
|
43
|
-
size: "size-5",
|
|
44
|
-
viewBox: t,
|
|
45
|
-
className: e,
|
|
46
|
-
title: o || "UnSelected",
|
|
47
|
-
...r,
|
|
48
|
-
children: /* @__PURE__ */ s("path", { d: "M256 512a256 256 0 1 0 0-512 256 256 0 1 0 0 512", opacity: ".4" })
|
|
49
|
-
}
|
|
50
|
-
), k = p.forwardRef(
|
|
51
|
-
({
|
|
52
|
-
label: e,
|
|
53
|
-
disabled: t,
|
|
54
|
-
icon: o,
|
|
55
|
-
raw: a = !1,
|
|
56
|
-
children: r,
|
|
57
|
-
ignoreClick: u = !1,
|
|
58
|
-
selected: i,
|
|
59
|
-
...n
|
|
60
|
-
}, N) => {
|
|
61
|
-
let d = "";
|
|
62
|
-
const c = p.useContext(h), w = C({ label: t ? null : e }), f = M(), v = g([w.ref, N]);
|
|
63
|
-
if (a && r)
|
|
64
|
-
return /* @__PURE__ */ s(
|
|
65
|
-
"div",
|
|
66
|
-
{
|
|
67
|
-
role: "menuitem",
|
|
68
|
-
...c.getItemProps({
|
|
69
|
-
onClick(m) {
|
|
70
|
-
u || (n.onClick?.(m), f?.events.emit("click"));
|
|
71
|
-
}
|
|
72
|
-
}),
|
|
73
|
-
children: r
|
|
74
|
-
}
|
|
75
|
-
);
|
|
76
|
-
o && (d = "pl-2");
|
|
77
|
-
const y = l(
|
|
78
|
-
"flex flex-row items-center",
|
|
79
|
-
"w-full",
|
|
80
|
-
"m-0 first:mt-0 mt-2 sm:mt-1 px-2 py-1",
|
|
81
|
-
"rounded-md border border-transparent",
|
|
82
|
-
"text-left text-base",
|
|
83
|
-
"outline-hidden focus:border focus:border-border-medium focus:bg-surface-lighter focus:underline",
|
|
84
|
-
"disabled:cursor-not-allowed disabled:text-copy-medium",
|
|
85
|
-
{
|
|
86
|
-
"bg-none": !t && !i
|
|
87
|
-
}
|
|
88
|
-
);
|
|
89
|
-
return /* @__PURE__ */ x(
|
|
90
|
-
"button",
|
|
91
|
-
{
|
|
92
|
-
...n,
|
|
93
|
-
ref: v,
|
|
94
|
-
role: "menuitem",
|
|
95
|
-
className: y,
|
|
96
|
-
tabIndex: 0,
|
|
97
|
-
disabled: t,
|
|
98
|
-
...c.getItemProps({
|
|
99
|
-
onClick(m) {
|
|
100
|
-
u || (n.onClick?.(m), f?.events.emit("click"));
|
|
101
|
-
},
|
|
102
|
-
onFocus(m) {
|
|
103
|
-
n.onFocus?.(m), c.setHasFocusInside(!0);
|
|
104
|
-
}
|
|
105
|
-
}),
|
|
106
|
-
children: [
|
|
107
|
-
i === !0 && /* @__PURE__ */ s(z, { className: "text-copy-success mr-2", size: "size-4" }),
|
|
108
|
-
i === !1 && /* @__PURE__ */ s(I, { className: "text-copy-medium mr-2", size: "size-4" }),
|
|
109
|
-
o,
|
|
110
|
-
e && /* @__PURE__ */ s("span", { className: d, children: e })
|
|
111
|
-
]
|
|
112
|
-
}
|
|
113
|
-
);
|
|
114
|
-
}
|
|
115
|
-
);
|
|
116
|
-
k.displayName = "MenuItem";
|
|
117
|
-
const j = ({ className: e, ...t }) => {
|
|
118
|
-
const o = l(e, "my-1 border-t border-border-medium");
|
|
119
|
-
return /* @__PURE__ */ s("div", { className: o, ...t });
|
|
120
|
-
}, P = ({
|
|
121
|
-
className: e,
|
|
122
|
-
...t
|
|
123
|
-
}) => {
|
|
124
|
-
const o = l(
|
|
125
|
-
e,
|
|
126
|
-
"pt-1 mb-2",
|
|
127
|
-
"text-sm text-copy-dark font-bold",
|
|
128
|
-
"border-b border-border-medium"
|
|
129
|
-
);
|
|
130
|
-
return /* @__PURE__ */ s("div", { className: o, ...t });
|
|
131
|
-
};
|
|
132
|
-
export {
|
|
133
|
-
P as MenuGroupLabel,
|
|
134
|
-
k as MenuItem,
|
|
135
|
-
j as MenuSeparator
|
|
136
|
-
};
|