UNPKG

@gluestack-ui/core

Version:

Universal UI components for React Native, Expo, and Next.js

102 lines 3.46 kB
import { getItemCount } from '@react-stately/collections'; import { isFocusVisible, useKeyboard } from '@react-aria/interactions'; import { useHover, usePress } from '@gluestack-ui/utils/aria'; import { mapDomPropsToRN } from '@gluestack-ui/utils/aria'; import { mergeProps, useSlotId } from '@react-aria/utils'; import { useSelectableItem } from '@react-aria/selection'; export function useMenuItem(props, state, ref) { let { isSelected, isDisabled, key, onClose, closeOnSelect = true, isVirtualized, onAction, } = props; let role = 'menuitem'; if (state.selectionManager.selectionMode === 'single') { role = 'menuitemradio'; } else if (state.selectionManager.selectionMode === 'multiple') { role = 'menuitemcheckbox'; } let labelId = useSlotId(); let descriptionId = useSlotId(); let keyboardId = useSlotId(); let ariaProps = { 'aria-disabled': isDisabled, role, 'aria-label': props['aria-label'], 'aria-labelledby': labelId, 'aria-describedby': [descriptionId, keyboardId].filter(Boolean).join(' ') || undefined, }; if (state.selectionManager.selectionMode !== 'none') { ariaProps['aria-checked'] = isSelected; } if (isVirtualized) { ariaProps['aria-posinset'] = state.collection.getItem(key).index; ariaProps['aria-setsize'] = getItemCount(state.collection); } let onPressStart = (e) => { if (e.pointerType === 'keyboard' && onAction) { onAction(key); } }; let onPress = () => { if (closeOnSelect && onClose) { onClose(); } }; let onPressUp = (e) => { if (e.pointerType !== 'keyboard') { if (onAction) { onAction(key); } } }; let { itemProps } = useSelectableItem({ selectionManager: state.selectionManager, key, ref, shouldSelectOnPressUp: true, }); let { pressProps } = usePress(mergeProps({ onPressStart, onPressUp, onPress, isDisabled }, mapDomPropsToRN(itemProps))); let { hoverProps } = useHover({ isDisabled, onHoverStart() { if (!isFocusVisible()) { state.selectionManager.setFocused(true); state.selectionManager.setFocusedKey(key); } }, }, ref); const { keyboardProps } = useKeyboard({ onKeyDown: (e) => { if (e.repeat) { e.continuePropagation(); return; } switch (e.key) { case ' ': if (!isDisabled && closeOnSelect && onClose) { onClose(); } break; case 'Enter': if (!isDisabled && closeOnSelect && onClose) { onClose(); } break; default: e.continuePropagation(); break; } }, }); return { menuItemProps: Object.assign(Object.assign({}, mapDomPropsToRN(ariaProps)), mergeProps(pressProps, hoverProps, keyboardProps)), labelProps: { id: labelId, }, descriptionProps: { id: descriptionId, }, keyboardShortcutProps: { id: keyboardId, }, }; } //# sourceMappingURL=useMenuItem.web.js.map