import * as Ariakit from '@ariakit/react'; import { getClassNames } from '@websolutespa/bom-core'; import { useContext } from 'react'; import styled from 'styled-components'; import { getVariantKey } from '../../variants'; import { getCssResponsive } from '../utils'; import { ModalDialogContext, ModalDialogProvider, ModalForceMountProvider } from './modal-dialog.context'; import { ModalContext } from './modal.context'; import { IModalVariants, modalVariants } from './modal.variants'; const StyledModalPortal = styled(Ariakit.Portal) ` ${props => getVariantKey('portal', props.variant, props.variants)} ${props => getCssResponsive(props)} `; export type ModalPortalExtraProps = { open?: boolean; defaultOpen?: boolean; onOpenChange?: (open: boolean) => void; modal?: boolean; }; export type ModalPortalProps = { open?: boolean; defaultOpen?: boolean; onOpenChange?: (open: boolean) => void; modal?: boolean; } & { forceMount?: boolean; container?: HTMLElement | null; children?: React.ReactNode; } & { className?: string; variant?: keyof typeof modalVariants | (string & {}); variants?: IModalVariants; }; export function ModalPortal({ forceMount = false, container, children, className, variant, variants, // ...props }: ModalPortalProps) { const store_ = Ariakit.useDialogStore({ open: props.open, defaultOpen: props.defaultOpen, setOpen: props.onOpenChange, }); const modal_ = props.modal ?? true; const contextValue = { store: store_, modal: modal_ }; const context = useContext(ModalDialogContext); const { store } = context ? context : contextValue; const portalContext = useContext(Ariakit.PortalContext); const mounted = Ariakit.useStoreState(store, (state) => forceMount || state.mounted); const classNames = getClassNames('modal__portal', className); const variantContext = useContext(ModalContext); if (!mounted) { return null; } return context ? ( {children} ) : ( {children} ); }