UNPKG

@crossed/ui

Version:

A universal & performant styling library for React Native, Next.js & React

147 lines (146 loc) 4.07 kB
import { jsx } from "react/jsx-runtime"; import { forwardRef, memo, useEffect, useRef } from "react"; import { Sheet } from "./Sheet/index"; import { composeRefs, createScope, withStaticProperties } from "@crossed/core"; import { composeStyles, createStyles, inlineStyle, isWeb } from "@crossed/styled"; import { Floating, useFloatingContext } from "./Floating"; import { autoUpdate, offset, useFloating } from "@floating-ui/react"; import { flip } from "@floating-ui/dom"; import { FadeIn, FadeOut } from "react-native-reanimated"; import { useMedia } from "../useMedia"; import { FocusOn } from "react-focus-on"; const [PopoverConfigProvider, usePopoverConfig] = createScope({}); const useFloatinCompat = isWeb ? (placement, offSetValue) => useFloating({ placement, middleware: [flip({ crossAxis: true }), offset(offSetValue)], whileElementsMounted: autoUpdate }) : () => ({ refs: {}, floatingStyles: {} }); const stylesDyn = createStyles(() => ({ dyn: (e) => e })); const [FloatingUiProvider, useFloatingUi] = createScope( {} ); const Root = memo( ({ children, placement = "bottom-end", triggerStrategy = "onPress", offsetValue = 10, ...props }) => { const { refs, floatingStyles } = useFloatinCompat(placement, offsetValue); const { md } = useMedia(); return /* @__PURE__ */ jsx( PopoverConfigProvider, { showSheet: !isWeb || !md, triggerStrategy, children: /* @__PURE__ */ jsx( Floating, { triggerStrategy: !md && triggerStrategy === "onPointerEnter" ? "onPress" : triggerStrategy, removeScroll: false, ...props, children: /* @__PURE__ */ jsx( FloatingUiProvider, { refs, floatingStyles, children } ) } ) } ); } ); const Trigger = memo( forwardRef((props, ref) => { const { refs } = useFloatingUi(); return /* @__PURE__ */ jsx( Floating.Trigger, { ...props, ref: composeRefs(ref, refs.setReference) } ); }) ); const Content = memo( forwardRef(({ children, style }, ref) => { const { showSheet } = usePopoverConfig(); return showSheet ? /* @__PURE__ */ jsx(ContentNative, { children, style }) : /* @__PURE__ */ jsx(ContentWeb, { ref, children, style }); }) ); const ContentWeb = memo( forwardRef(({ children, style }, ref) => { const { refs, floatingStyles } = useFloatingUi(); const { onClose, open } = useFloatingContext(); const { triggerStrategy } = usePopoverConfig(); return /* @__PURE__ */ jsx(Floating.Portal, { children: /* @__PURE__ */ jsx( FocusOn, { onClickOutside: onClose, onEscapeKey: onClose, enabled: open && triggerStrategy === "onPress", children: /* @__PURE__ */ jsx( Floating.Content, { entering: FadeIn, exiting: FadeOut, ref: composeRefs(ref, refs.setFloating), style: composeStyles( inlineStyle(() => ({ base: { position: "absolute" } })), stylesDyn.dyn(floatingStyles), style ), children } ) } ) }); }) ); const ContentNative = ({ children }) => { const { open, onClose } = useFloatingContext(); const refSheet = useRef(null); useEffect(() => { var _a, _b; if (open) { (_a = refSheet.current) == null ? void 0 : _a.show(); } else { (_b = refSheet.current) == null ? void 0 : _b.hide(); } }, [open]); return /* @__PURE__ */ jsx(Sheet, { ref: refSheet, children: /* @__PURE__ */ jsx(Sheet.Content, { onClose, children: /* @__PURE__ */ jsx(Sheet.Padded, { children }) }) }); }; const Popover = withStaticProperties(Root, { Trigger, Content }); export { Content, Popover, PopoverConfigProvider, Root, Trigger, usePopoverConfig }; //# sourceMappingURL=Popover.js.map