{
  "$schema": "https://ui.shadcn.com/schema/registry-item.json",
  "name": "form",
  "title": "Form",
  "description": "react-hook-form bindings (`Form`, `FormField`, `FormItem`, `FormMessage`) with accessible labels and errors.",
  "dependencies": [
    "@base-ui/react@^1.8.0",
    "react-hook-form@^7.62.0"
  ],
  "registryDependencies": [
    "https://rdf.dev.360online.com/r/label.json"
  ],
  "files": [
    {
      "path": "registry/rapid/ui/form/form.tsx",
      "content": "'use client'\n\nimport { mergeProps } from '@base-ui/react/merge-props'\nimport { useRender } from '@base-ui/react/use-render'\nimport * as React from 'react'\nimport {\n\tController,\n\ttype ControllerProps,\n\ttype FieldPath,\n\ttype FieldValues,\n\tFormProvider,\n\tuseFormContext,\n\tuseFormState,\n} from 'react-hook-form'\nimport { Label } from '@/components/ui/label'\nimport { cn } from '@/lib/utils'\n\nconst Form = FormProvider\n\ntype FormFieldContextValue<\n\tTFieldValues extends FieldValues = FieldValues,\n\tTName extends FieldPath<TFieldValues> = FieldPath<TFieldValues>,\n> = {\n\tname: TName\n}\n\nconst FormFieldContext = React.createContext<FormFieldContextValue>({} as FormFieldContextValue)\n\nconst FormField = <\n\tTFieldValues extends FieldValues = FieldValues,\n\tTName extends FieldPath<TFieldValues> = FieldPath<TFieldValues>,\n>({\n\t...props\n}: ControllerProps<TFieldValues, TName>) => {\n\treturn (\n\t\t<FormFieldContext.Provider value={{ name: props.name }}>\n\t\t\t<Controller {...props} />\n\t\t</FormFieldContext.Provider>\n\t)\n}\n\nconst useFormField = () => {\n\tconst fieldContext = React.useContext(FormFieldContext)\n\tconst itemContext = React.useContext(FormItemContext)\n\tconst { getFieldState } = useFormContext()\n\tconst formState = useFormState({ name: fieldContext.name })\n\tconst fieldState = getFieldState(fieldContext.name, formState)\n\n\tif (!fieldContext) {\n\t\tthrow new Error('useFormField should be used within <FormField>')\n\t}\n\n\tconst { id } = itemContext\n\n\treturn {\n\t\tid,\n\t\tname: fieldContext.name,\n\t\tformItemId: `${id}-form-item`,\n\t\tformDescriptionId: `${id}-form-item-description`,\n\t\tformMessageId: `${id}-form-item-message`,\n\t\t...fieldState,\n\t}\n}\n\ntype FormItemContextValue = {\n\tid: string\n}\n\nconst FormItemContext = React.createContext<FormItemContextValue>({} as FormItemContextValue)\n\nfunction FormItem({ className, ...props }: React.ComponentProps<'div'>) {\n\tconst id = React.useId()\n\n\treturn (\n\t\t<FormItemContext.Provider value={{ id }}>\n\t\t\t<div data-slot=\"form-item\" className={cn('grid gap-2', className)} {...props} />\n\t\t</FormItemContext.Provider>\n\t)\n}\n\nfunction FormLabel({ className, ...props }: React.ComponentProps<typeof Label>) {\n\tconst { error, formItemId } = useFormField()\n\n\treturn (\n\t\t<Label\n\t\t\tdata-slot=\"form-label\"\n\t\t\tdata-error={!!error}\n\t\t\tclassName={cn('data-[error=true]:text-destructive break-words', className)}\n\t\t\thtmlFor={formItemId}\n\t\t\t{...props}\n\t\t/>\n\t)\n}\n\ntype FormControlProps = React.HTMLAttributes<HTMLElement> & {\n\tref?: React.Ref<HTMLElement>\n}\n\n// Passes the field's id, aria-describedby and aria-invalid on to its only child (the form control)\nfunction FormControl({ children, ref, ...props }: FormControlProps) {\n\tconst { error, formItemId, formDescriptionId, formMessageId } = useFormField()\n\tconst child = React.isValidElement(children) ? children : undefined\n\n\treturn useRender({\n\t\tdefaultTagName: 'div',\n\t\trender: child,\n\t\tref,\n\t\tprops: mergeProps<'div'>(\n\t\t\t{\n\t\t\t\t'data-slot': 'form-control',\n\t\t\t\tid: formItemId,\n\t\t\t\t'aria-describedby': error ? `${formDescriptionId} ${formMessageId}` : `${formDescriptionId}`,\n\t\t\t\t'aria-invalid': !!error,\n\t\t\t\tchildren: child ? undefined : children,\n\t\t\t} as React.ComponentProps<'div'>,\n\t\t\tprops as React.ComponentProps<'div'>,\n\t\t),\n\t})\n}\n\nfunction FormDescription({ className, ...props }: React.ComponentProps<'p'>) {\n\tconst { formDescriptionId } = useFormField()\n\n\treturn (\n\t\t<p\n\t\t\tdata-slot=\"form-description\"\n\t\t\tid={formDescriptionId}\n\t\t\tclassName={cn('text-muted-foreground text-sm break-words', className)}\n\t\t\t{...props}\n\t\t/>\n\t)\n}\n\nfunction FormMessage({ className, ...props }: React.ComponentProps<'p'>) {\n\tconst { error, formMessageId } = useFormField()\n\tconst body = error ? String(error?.message ?? '') : props.children\n\n\tif (!body) {\n\t\treturn null\n\t}\n\n\treturn (\n\t\t<p data-slot=\"form-message\" id={formMessageId} className={cn('text-destructive text-sm', className)} {...props}>\n\t\t\t{body}\n\t\t</p>\n\t)\n}\n\nexport { useFormField, Form, FormItem, FormLabel, FormControl, FormDescription, FormMessage, FormField }\n",
      "type": "registry:ui",
      "target": "components/ui/form.tsx"
    }
  ],
  "type": "registry:ui"
}