UNPKG

@ariakit/react-core

Version:

Ariakit React core

133 lines (115 loc) 5.02 kB
"use strict";Object.defineProperty(exports, "__esModule", {value: true}); var _ENNAUHNHcjs = require('./ENNAUHNH.cjs'); var _26P4PLHIcjs = require('./26P4PLHI.cjs'); var _YUGKYIYYcjs = require('./YUGKYIYY.cjs'); var _25BPIGZHcjs = require('./25BPIGZH.cjs'); var _OZM4QA2Vcjs = require('./OZM4QA2V.cjs'); var _7EQBAZ46cjs = require('./7EQBAZ46.cjs'); // src/dialog/utils/use-hide-on-interact-outside.ts var _dom = require('@ariakit/core/utils/dom'); var _events = require('@ariakit/core/utils/events'); var _react = require('react'); function isInDocument(target) { if (target.tagName === "HTML") return true; return _dom.contains.call(void 0, _dom.getDocument.call(void 0, target).body, target); } function isDisclosure(disclosure, target) { if (!disclosure) return false; if (_dom.contains.call(void 0, disclosure, target)) return true; const activeId = target.getAttribute("aria-activedescendant"); if (activeId) { const activeElement = _dom.getDocument.call(void 0, disclosure).getElementById(activeId); if (activeElement) { return _dom.contains.call(void 0, disclosure, activeElement); } } return false; } function isMouseEventOnDialog(event, dialog) { if (!("clientY" in event)) return false; const rect = dialog.getBoundingClientRect(); if (rect.width === 0 || rect.height === 0) return false; return rect.top <= event.clientY && event.clientY <= rect.top + rect.height && rect.left <= event.clientX && event.clientX <= rect.left + rect.width; } function useEventOutside({ store, type, listener, capture, domReady }) { const callListener = _OZM4QA2Vcjs.useEvent.call(void 0, listener); const open = _25BPIGZHcjs.useStoreState.call(void 0, store, "open"); const focusedRef = _react.useRef.call(void 0, false); _OZM4QA2Vcjs.useSafeLayoutEffect.call(void 0, () => { if (!open) return; if (!domReady) return; const { contentElement } = store.getState(); if (!contentElement) return; const onFocus = () => { focusedRef.current = true; }; contentElement.addEventListener("focusin", onFocus, true); return () => contentElement.removeEventListener("focusin", onFocus, true); }, [store, open, domReady]); _react.useEffect.call(void 0, () => { if (!open) return; const onEvent = (event) => { const { contentElement, disclosureElement } = store.getState(); const target = event.target; if (!contentElement) return; if (!target) return; if (!isInDocument(target)) return; if (_dom.contains.call(void 0, contentElement, target)) return; if (isDisclosure(disclosureElement, target)) return; if (target.hasAttribute("data-focus-trap")) return; if (isMouseEventOnDialog(event, contentElement)) return; const focused = focusedRef.current; if (focused && !_26P4PLHIcjs.isElementMarked.call(void 0, target, contentElement.id)) return; if (_YUGKYIYYcjs.isSafariFocusAncestor.call(void 0, target)) return; callListener(event); }; return _events.addGlobalEventListener.call(void 0, type, onEvent, capture); }, [open, capture]); } function shouldHideOnInteractOutside(hideOnInteractOutside, event) { if (typeof hideOnInteractOutside === "function") { return hideOnInteractOutside(event); } return !!hideOnInteractOutside; } function useHideOnInteractOutside(store, hideOnInteractOutside, domReady) { const open = _25BPIGZHcjs.useStoreState.call(void 0, store, "open"); const previousMouseDownRef = _ENNAUHNHcjs.usePreviousMouseDownRef.call(void 0, open); const props = { store, domReady, capture: true }; useEventOutside(_7EQBAZ46cjs.__spreadProps.call(void 0, _7EQBAZ46cjs.__spreadValues.call(void 0, {}, props), { type: "click", listener: (event) => { const { contentElement } = store.getState(); const previousMouseDown = previousMouseDownRef.current; if (!previousMouseDown) return; if (!_dom.isVisible.call(void 0, previousMouseDown)) return; if (!_26P4PLHIcjs.isElementMarked.call(void 0, previousMouseDown, contentElement == null ? void 0 : contentElement.id)) return; if (!shouldHideOnInteractOutside(hideOnInteractOutside, event)) return; store.hide(); } })); useEventOutside(_7EQBAZ46cjs.__spreadProps.call(void 0, _7EQBAZ46cjs.__spreadValues.call(void 0, {}, props), { type: "focusin", listener: (event) => { const { contentElement } = store.getState(); if (!contentElement) return; if (event.target === _dom.getDocument.call(void 0, contentElement)) return; if (!shouldHideOnInteractOutside(hideOnInteractOutside, event)) return; store.hide(); } })); useEventOutside(_7EQBAZ46cjs.__spreadProps.call(void 0, _7EQBAZ46cjs.__spreadValues.call(void 0, {}, props), { type: "contextmenu", listener: (event) => { if (!shouldHideOnInteractOutside(hideOnInteractOutside, event)) return; store.hide(); } })); } exports.useHideOnInteractOutside = useHideOnInteractOutside;