@ariakit/react-core
Version:
Ariakit React core
170 lines (167 loc) • 5.32 kB
JavaScript
"use client";
import {
MenuScopedContextProvider,
useMenuProviderContext
} from "./VIIRIBF3.js";
import {
useCompositeTypeahead
} from "./T7VMP3TM.js";
import {
isHidden
} from "./KFH4SEIX.js";
import {
useComposite
} from "./5JTVDSTH.js";
import {
useStoreState
} from "./YV4JVR4I.js";
import {
createElement,
createHook,
forwardRef
} from "./LMDWO4NN.js";
import {
useEvent,
useId,
useMergeRefs,
useWrapElement
} from "./ABQUS43J.js";
import {
__objRest,
__spreadProps,
__spreadValues
} from "./3YLGPPWQ.js";
// src/menu/menu-list.tsx
import { invariant } from "@ariakit/core/utils/misc";
import { useEffect, useState } from "react";
import { jsx } from "react/jsx-runtime";
var TagName = "div";
function useAriaLabelledBy(_a) {
var _b = _a, { store } = _b, props = __objRest(_b, ["store"]);
const [id, setId] = useState(void 0);
const label = props["aria-label"];
const disclosureElement = useStoreState(store, "disclosureElement");
const contentElement = useStoreState(store, "contentElement");
useEffect(() => {
const disclosure = disclosureElement;
if (!disclosure) return;
const menu = contentElement;
if (!menu) return;
const menuLabel = label || menu.hasAttribute("aria-label");
if (menuLabel) {
setId(void 0);
} else if (disclosure.id) {
setId(disclosure.id);
}
}, [label, disclosureElement, contentElement]);
return id;
}
var useMenuList = createHook(
function useMenuList2(_a) {
var _b = _a, { store, alwaysVisible, composite } = _b, props = __objRest(_b, ["store", "alwaysVisible", "composite"]);
const context = useMenuProviderContext();
store = store || context;
invariant(
store,
process.env.NODE_ENV !== "production" && "MenuList must receive a `store` prop or be wrapped in a MenuProvider component."
);
const parentMenu = store.parent;
const parentMenubar = store.menubar;
const hasParentMenu = !!parentMenu;
const id = useId(props.id);
const onKeyDownProp = props.onKeyDown;
const dir = store.useState(
(state) => state.placement.split("-")[0]
);
const orientation = store.useState(
(state) => state.orientation === "both" ? void 0 : state.orientation
);
const isHorizontal = orientation !== "vertical";
const isMenubarHorizontal = useStoreState(
parentMenubar,
(state) => !!state && state.orientation !== "vertical"
);
const onKeyDown = useEvent((event) => {
onKeyDownProp == null ? void 0 : onKeyDownProp(event);
if (event.defaultPrevented) return;
if (hasParentMenu || parentMenubar && !isHorizontal) {
const hideMap = {
ArrowRight: () => dir === "left" && !isHorizontal,
ArrowLeft: () => dir === "right" && !isHorizontal,
ArrowUp: () => dir === "bottom" && isHorizontal,
ArrowDown: () => dir === "top" && isHorizontal
};
const action = hideMap[event.key];
if (action == null ? void 0 : action()) {
event.stopPropagation();
event.preventDefault();
return store == null ? void 0 : store.hide();
}
}
if (parentMenubar) {
const keyMap = {
ArrowRight: () => {
if (!isMenubarHorizontal) return;
return parentMenubar.next();
},
ArrowLeft: () => {
if (!isMenubarHorizontal) return;
return parentMenubar.previous();
},
ArrowDown: () => {
if (isMenubarHorizontal) return;
return parentMenubar.next();
},
ArrowUp: () => {
if (isMenubarHorizontal) return;
return parentMenubar.previous();
}
};
const action = keyMap[event.key];
const id2 = action == null ? void 0 : action();
if (id2 !== void 0) {
event.stopPropagation();
event.preventDefault();
parentMenubar.move(id2);
}
}
});
props = useWrapElement(
props,
(element) => /* @__PURE__ */ jsx(MenuScopedContextProvider, { value: store, children: element }),
[store]
);
const ariaLabelledBy = useAriaLabelledBy(__spreadValues({ store }, props));
const mounted = store.useState("mounted");
const hidden = isHidden(mounted, props.hidden, alwaysVisible);
const style = hidden ? __spreadProps(__spreadValues({}, props.style), { display: "none" }) : props.style;
props = __spreadProps(__spreadValues({
id,
"aria-labelledby": ariaLabelledBy,
hidden
}, props), {
ref: useMergeRefs(id ? store.setContentElement : null, props.ref),
style,
onKeyDown
});
const hasCombobox = !!store.combobox;
composite = composite != null ? composite : !hasCombobox;
if (composite) {
props = __spreadValues({
role: "menu",
"aria-orientation": orientation
}, props);
}
props = useComposite(__spreadValues({ store, composite }, props));
props = useCompositeTypeahead(__spreadValues({ store, typeahead: !hasCombobox }, props));
return props;
}
);
var MenuList = forwardRef(function MenuList2(props) {
const htmlProps = useMenuList(props);
return createElement(TagName, htmlProps);
});
export {
useMenuList,
MenuList
};