UNPKG

@gluestack-ui-nightly/core

Version:

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

117 lines 4.4 kB
var __rest = (this && this.__rest) || function (s, e) { var t = {}; for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p) && e.indexOf(p) < 0) t[p] = s[p]; if (s != null && typeof Object.getOwnPropertySymbols === "function") for (var i = 0, p = Object.getOwnPropertySymbols(s); i < p.length; i++) { if (e.indexOf(p[i]) < 0 && Object.prototype.propertyIsEnumerable.call(s, p[i])) t[p[i]] = s[p[i]]; } return t; }; import React, { forwardRef } from 'react'; import { useControllableState } from '@gluestack-ui-nightly/utils/hooks'; import { Overlay } from '../../overlay/creator'; import { PopoverProvider } from './PopoverContext'; export const Popover = (StyledPopover) => forwardRef((_a, ref) => { var { onOpen, trigger, onClose, isOpen: isOpenProp, children, defaultIsOpen = false, initialFocusRef, finalFocusRef, useRNModal, focusScope = true, trapFocus = true, placement = 'bottom', shouldOverlapWithTrigger = false, crossOffset, offset, isKeyboardDismissable = true, shouldFlip, _experimentalOverlay = false } = _a, props = __rest(_a, ["onOpen", "trigger", "onClose", "isOpen", "children", "defaultIsOpen", "initialFocusRef", "finalFocusRef", "useRNModal", "focusScope", "trapFocus", "placement", "shouldOverlapWithTrigger", "crossOffset", "offset", "isKeyboardDismissable", "shouldFlip", "_experimentalOverlay"]); const [isOpen, setIsOpen] = useControllableState({ value: isOpenProp, defaultValue: defaultIsOpen, onChange: (value) => { value ? onOpen && onOpen() : onClose && onClose(); }, }); const [bodyMounted, setBodyMounted] = React.useState(false); const [headerMounted, setHeaderMounted] = React.useState(false); var idCounter = 0; function uniqueId(prefix = '') { var id = ++idCounter; return prefix + id; } const id = uniqueId(); const popoverContentId = `${id}-content`; const headerId = `${popoverContentId}-header`; const bodyId = `${popoverContentId}-body`; const handleOpen = React.useCallback(() => { setIsOpen(true); }, [setIsOpen]); const handleClose = React.useCallback(() => { setIsOpen(false); }, [setIsOpen]); const updatedTrigger = (reference) => { return trigger({ 'ref': reference, 'onPress': handleOpen, 'aria-expanded': isOpen ? true : false, 'aria-controls': isOpen ? popoverContentId : undefined, 'aria-haspopup': true, }, { open: isOpen }); }; const targetRef = React.useRef(null); const contextValue = React.useMemo(() => { return { targetRef, strategy: 'absolute', handleClose, initialFocusRef, finalFocusRef, popoverContentId, bodyId, headerId, headerMounted, bodyMounted, setBodyMounted, setHeaderMounted, isOpen, placement, shouldOverlapWithTrigger, crossOffset, offset, focusScope, trapFocus, shouldFlip, }; }, [ targetRef, handleClose, initialFocusRef, finalFocusRef, popoverContentId, bodyId, headerId, headerMounted, bodyMounted, setBodyMounted, setHeaderMounted, isOpen, placement, shouldOverlapWithTrigger, crossOffset, offset, focusScope, trapFocus, shouldFlip, ]); if (_experimentalOverlay) { return (<> {updatedTrigger(targetRef)} <PopoverProvider value={contextValue}> <StyledPopover ref={ref} {...props}> {children} </StyledPopover> </PopoverProvider> </>); } return (<> {updatedTrigger(targetRef)} <Overlay isOpen={isOpen} onRequestClose={handleClose} isKeyboardDismissable={isKeyboardDismissable} useRNModal={useRNModal}> <PopoverProvider value={contextValue}> <StyledPopover ref={ref} {...props}> {children} </StyledPopover> </PopoverProvider> </Overlay> </>); }); //# sourceMappingURL=Popover.jsx.map