"use client"; import { AnimatePresence, type HTMLMotionProps, motion } from "motion/react"; import { Dialog as DialogPrimitive } from "radix-ui"; import type * as React from "react"; import { useTranslation } from "react-i18next"; import { RxCross2 } from "react-icons/rx"; import { useControlledState } from "@/hooks/use-controlled-state"; import { getStrictContext } from "@/lib/get-strict-context"; import { cn } from "@/lib/utils"; import { WindowDragArea } from "../window-drag-area"; type DialogContextType = { isOpen: boolean; setIsOpen: DialogProps["onOpenChange"]; subPage: boolean; container: HTMLElement | null | undefined; }; const [DialogProvider, useDialog] = getStrictContext("DialogContext"); type DialogProps = React.ComponentProps & { /** Render in a portal container as an in-flow sub-page instead of a centered modal. */ subPage?: boolean; /** Portal container target. Required when subPage=true; ignored otherwise. */ container?: HTMLElement | null; }; function Dialog({ subPage, container, children, ...props }: DialogProps) { const [isOpen, setIsOpen] = useControlledState({ value: props?.open, defaultValue: props?.defaultOpen, onChange: props?.onOpenChange, }); return ( {/* In sub-page mode the Dialog isn't a modal — it's an in-flow page. Forcing `modal={false}` prevents Radix from locking pointer-events and aria-hiding everything outside the dialog. Children are passed explicitly (not via spread) so React doesn't have to guess where the JSX subtree should mount. */} {children} ); } type DialogTriggerProps = React.ComponentProps; function DialogTrigger(props: DialogTriggerProps) { return ; } type DialogPortalProps = Omit< React.ComponentProps, "forceMount" >; function DialogPortal(props: DialogPortalProps) { const { isOpen, container } = useDialog(); return ( {isOpen && ( )} ); } type DialogOverlayProps = Omit< React.ComponentProps, "forceMount" | "asChild" > & HTMLMotionProps<"div">; function DialogOverlay({ className, transition = { duration: 0.2, ease: "easeInOut" }, ...props }: DialogOverlayProps) { return ( {/* Keep the OS title-bar zone draggable while a modal is open — the overlay otherwise covers the native drag region. `data-window-drag-area` stops Radix from treating a drag here as an outside-click dismiss. */}