{"version":3,"file":"index.mjs","sources":[""],"sourcesContent":["import \"./style.pcss\";\r\nimport { bubble } from \"@web3r/flowerkit/evt\";\r\nimport { getDebouncedFn } from \"@web3r/flowerkit/fn\";\r\nimport { isObjEmpty } from \"@web3r/flowerkit/obj\";\r\nimport type {\r\n  FC,\r\n  FormEvent, FormEventHandler,\r\n  Ref,\r\n  ReactElement,\r\n} from \"react\";\r\nimport {\r\n  useCallback,\r\n  useMemo,\r\n  useRef,\r\n  useState,\r\n  useImperativeHandle,\r\n} from \"react\";\r\nimport { FormRow } from \"./components/formRow\";\r\nimport type {\r\n  IForm, IFormRef, IFormCfg, TFormValues, \r\n} from \"./config/types\";\r\nimport { FormContext } from \"./context\";\r\nimport { isStateIncludesOtherState, getFormInitialValues, getCustomisationForCols } from \"./lib\";\r\nimport type { IComponentBaseProps } from \"../../types/components\";\r\nimport { getUserControlledFields } from \"../../utils/getUserControlledFields\";\r\nimport { useCN } from \"../../utils/react/useCN\";\r\nimport { Input } from \"../input\";\r\n\r\n/**\r\n * Компонент формы\r\n * @returns {ReactElement}\r\n */\r\nconst Form: FC<IForm & IComponentBaseProps> = ({\r\n  id = null,\r\n  rows = [],\r\n  cfg = {},\r\n  onSubmit = (e: FormEvent) => e.preventDefault(),\r\n  onReset = null,\r\n  baseClass = \"form\",\r\n  children = null,\r\n  setCustomComponent = null,\r\n  setInputProps = null,\r\n  setVisibility = null,\r\n  extraClasses = {},\r\n  extraAttrs = {},\r\n  isCustomWrapper = false,\r\n  isUseValuesCompare = false,\r\n  initialValues = {},\r\n  auxParams = {},\r\n  isHidden = false,\r\n  headerSlot = null,\r\n  footerSlot = null,\r\n  ref = null,\r\n}): ReactElement => {\r\n\r\n  const { getCN } = useCN(baseClass);\r\n\r\n  const formRef = useRef<HTMLFormElement | null>(null);\r\n\r\n  const [ formValues, setFormValues ] = useState<TFormValues>(\r\n    () => (rows?.length ? getFormInitialValues({ formRows: rows }) : initialValues || {})\r\n  );\r\n\r\n  const stateActions = useMemo(() => ({ setFormValues }), []);\r\n\r\n  const onChange = useCallback(({\r\n    target,\r\n    detail,\r\n  }: {\r\n    target: { name: string; value: unknown; };\r\n    detail?: { name?: string; value?: unknown; } | unknown;\r\n  }) => {\r\n    const hasDetailName = typeof detail === \"object\" && detail !== null && \"name\" in detail;\r\n    const source = hasDetailName ? (detail as { name?: string; value?: unknown; }) : target;\r\n    const { name, value } = source;\r\n    name && setFormValues((state) => ({ ...state, [name]: value as TFormValues[string] }));\r\n  }, []);\r\n\r\n  const handleReset = useCallback((event: FormEvent) => {\r\n    if (typeof onReset === \"function\") {\r\n      onReset({ event, data: { formValues }, stateActions });\r\n    } else {\r\n      getUserControlledFields(formRef.current)?.forEach((node) => bubble(node, \"reset\", { bubbles: false }));\r\n    }\r\n  }, [ onReset, formValues, stateActions ]);\r\n\r\n  const isFormElementVisible = useMemo(() => {\r\n    return isUseValuesCompare\r\n      ? ({ isShowForValues }: { isShowForValues?: Record<string, unknown>; }) =>\r\n        isShowForValues ? isStateIncludesOtherState({\r\n          firstState: isShowForValues,\r\n          secondState: formValues,\r\n        }) : true\r\n      : setVisibility;\r\n  }, [ formValues, isUseValuesCompare, setVisibility ]);\r\n\r\n  const formRows = useMemo(() => {\n    if (!setCustomComponent && !setInputProps && !isUseValuesCompare) {\n      return rows;\n    } else {\n      return rows?.map((row) => {\n        const nextRow = {\n          ...row,\n          cols: row.cols?.map((col) => ({\n            ...col,\n            field: col.field ? {\n              ...col.field,\n              input: col.field.input ? { ...col.field.input } : col.field.input,\n            } : col.field,\n          })),\n        };\n\n        if (typeof isFormElementVisible === \"function\") {\n          nextRow.isVisible = isFormElementVisible(nextRow);\n        }\n\n        getCustomisationForCols({\n          cols: nextRow.cols,\n          setCustomComponent,\n          setInputProps,\n          isFormElementVisible,\n        });\n\n        return nextRow;\n      });\n    }\n  }, [ rows, setCustomComponent, setInputProps, isFormElementVisible, isUseValuesCompare ]);\n\r\n  const visibleRows = useMemo(() => {\r\n    const keyCounter = new Map<string, number>();\r\n    return formRows?.filter(({ isVisible = true }) => isVisible).map((row) => {\r\n      const keyBase = JSON.stringify({\r\n        columns: row.columns,\r\n        colsCount: row.cols?.length ?? 0,\r\n        isShowForValues: row.isShowForValues,\r\n      });\r\n      const keyOrder = (keyCounter.get(keyBase) ?? 0) + 1;\r\n      keyCounter.set(keyBase, keyOrder);\r\n      return <FormRow key={`${keyBase}_${keyOrder}`} {...row} />;\r\n    });\r\n  }, [ formRows ]);\r\n\r\n  const formBody = useMemo(() => (\r\n    <div className={getCN(\"body\")}>\r\n      {children || visibleRows}\r\n    </div>\r\n  ), [ getCN, children, visibleRows ]);\r\n\r\n  const formHeader = useMemo(() => (\r\n    (!!headerSlot || (!!auxParams && !isObjEmpty(auxParams))) && (\r\n      <div className={getCN(\"header\", { isHidden: !headerSlot })}>\r\n        {Object.entries(auxParams || {}).map(([ name, value ]) => (\r\n          <Input key={`auxParam_${name}`} type={\"hidden\"} name={name} value={value?.toString()} />\r\n        ))}\r\n        {headerSlot}\r\n      </div>\r\n    )\r\n  ), [ headerSlot, auxParams, getCN ]);\r\n\r\n  const formFooter = useMemo(() => (\r\n    !!footerSlot && <div className={getCN(\"footer\")}>{footerSlot}</div>\r\n  ), [ footerSlot, getCN ]);\r\n\r\n  const formExtraClasses = { ...extraClasses, isHidden };\r\n\r\n  useImperativeHandle(ref, (): IFormRef => ({\r\n    el: formRef.current,\r\n    ref: null,\r\n    utils: null,\r\n    getData: () => ({ value: formValues }),\r\n    stateActions,\r\n  }), [ formValues, stateActions ]);\r\n\r\n  const debouncedChangeHandler: Function = getDebouncedFn(onChange);\r\n  const debouncedResetHandler: Function = getDebouncedFn(handleReset, 300, true);\r\n\r\n  const ctx = useMemo(() => ({\r\n    getCN, baseClass, formValues, setFormValues,\r\n  }), [ getCN, baseClass, formValues, setFormValues ]);\r\n\r\n  return (\r\n    <FormContext value={ctx}>\r\n      {isCustomWrapper ? (\r\n        <div role={\"form\"} id={id || undefined} ref={formRef as Ref<HTMLDivElement>} className={getCN(\"\", formExtraClasses)} {...extraAttrs}>\r\n          {formHeader}\r\n          {formBody}\r\n          {formFooter}\r\n        </div>\r\n      ) : (\r\n        <form\r\n          onChange={debouncedChangeHandler as FormEventHandler<HTMLFormElement>}\r\n          hidden={isHidden}\r\n          id={id || undefined}\r\n          ref={formRef}\r\n          onReset={debouncedResetHandler as FormEventHandler<HTMLFormElement>}\r\n          onSubmit={onSubmit}\r\n          autoComplete={\"off\"}\r\n          className={getCN(\"\", formExtraClasses)}\r\n          data-js-form={JSON.stringify(cfg)}\r\n          noValidate\r\n          {...extraAttrs}\r\n        >\r\n          {formHeader}\r\n          {formBody}\r\n          {formFooter}\r\n        </form>\r\n      )}\r\n    </FormContext>\r\n  );\r\n};\r\n\r\nexport type { IForm, IFormCfg, IFormRef };\r\n\r\nexport { Form };\r\n"],"names":["Form","id","rows","cfg","onSubmit","e","preventDefault","onReset","baseClass","children","setCustomComponent","setInputProps","setVisibility","extraClasses","extraAttrs","isCustomWrapper","isUseValuesCompare","initialValues","auxParams","isHidden","headerSlot","footerSlot","ref","getCN","useCN","formRef","useRef","formValues","setFormValues","useState","length","getFormInitialValues","formRows","stateActions","useMemo","onChange","useCallback","target","detail","hasDetailName","source","name","value","state","handleReset","event","data","getUserControlledFields","current","forEach","node","bubble","bubbles","isFormElementVisible","isShowForValues","isStateIncludesOtherState","firstState","secondState","map","row","nextRow","cols","col","field","input","isVisible","getCustomisationForCols","visibleRows","keyCounter","Map","filter","keyBase","JSON","stringify","columns","colsCount","keyOrder","get","set","_jsx","FormRow","formBody","className","formHeader","isObjEmpty","_jsxs","Object","entries","Input","type","toString","formFooter","formExtraClasses","useImperativeHandle","el","utils","getData","debouncedChangeHandler","getDebouncedFn","debouncedResetHandler","ctx","FormContext","role","undefined","hidden","autoComplete","noValidate"],"mappings":"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"}