import React, { forwardRef, useCallback, useImperativeHandle, useRef, useState, type ReactElement, type Ref, } from 'react' import { IconX } from '@tabler/icons-react' import type { FieldValues } from 'react-hook-form' import { ActionIcon, Drawer } from '@mantine/core' import type { SuperFormDrawerProps, SuperFormDrawerRef, SuperFormRef } from '../../types' import SuperForm from '../../components/SuperForm' import { openConfirmModal } from '../../utils/openConfirmModal' const SuperFormDrawer = ( { drawerProps, noCloseOnSubmit, ...formProps }: SuperFormDrawerProps, ref: Ref> ) => { // Component Refs const formRef = useRef>(null) const drawerRef = useRef(null) // Component store State // Tell drawer that form layout mounted to fix refs const [layoutMounted, setLayoutMounted] = useState(false) // Component Callback Functions const onSubmit = (data: T, request, formData, form, closeForm: boolean = true) => { formProps?.onSubmit?.(data, request, formData, form, closeForm) if (request === 'delete') { drawerProps?.onClose() } if (!noCloseOnSubmit) { if (closeForm) { drawerProps?.onClose() } } } const onCancel = (request) => { if (formRef?.current?.getFormState().isDirty) { openConfirmModal(() => { drawerProps?.onClose() formProps?.onCancel?.(request) }) } else { drawerProps?.onClose() formProps?.onCancel?.(request) } } const onLayoutMounted = useCallback(() => { setLayoutMounted(true) formProps?.onLayoutMounted?.() }, [formProps?.onLayoutMounted]) const onLayoutUnMounted = useCallback(() => { setLayoutMounted(false) formProps?.onLayoutUnMounted?.() }, [formProps?.onLayoutUnMounted]) // Component use Effects useImperativeHandle, SuperFormDrawerRef>( ref, () => ({ ...formRef.current, drawer: drawerRef.current, } as SuperFormDrawerRef), [layoutMounted] ) return ( { if (e.key === 'Escape' && drawerProps.closeOnEscape !== false) { e.stopPropagation() onCancel(formProps.request) } }} overlayProps={{ backgroundOpacity: 0.5, blur: 0.5 }} padding={6} position='right' transitionProps={{ transition: 'slide-left', duration: 150, timingFunction: 'linear', }} size={500} styles={{ content: { display: 'flex', flexDirection: 'column', justifyContent: 'stretch', }, body: { minHeight: '100px', flexGrow: 1, }, }} keepMounted={false} {...drawerProps} closeOnEscape={false} withCloseButton={false} title={null} > {...formProps} onCancel={onCancel} onSubmit={onSubmit} onLayoutMounted={onLayoutMounted} onLayoutUnMounted={onLayoutUnMounted} ref={formRef} layoutProps={{ ...formProps?.layoutProps, rightSection: ( { onCancel(formProps?.request) }} > ), title: (drawerProps.title as string) ?? formProps?.layoutProps?.title ?? (formProps?.request as string), }} /> ) } const FRSuperFormDrawer = forwardRef(SuperFormDrawer) as ( props: SuperFormDrawerProps & { ref?: Ref> } ) => ReactElement export default FRSuperFormDrawer