Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
 into SPV-1006/DockerImage
  • Loading branch information
Nazarii-4chain committed Aug 29, 2024
2 parents 4424745 + 68b61bc commit 3f60719
Show file tree
Hide file tree
Showing 4 changed files with 270 additions and 91 deletions.
108 changes: 106 additions & 2 deletions src/components/ui/form/form.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,107 @@
import { FormProvider } from 'react-hook-form';
import { useFormField } from '@/components';
import { Label } from '@/components/ui/label.tsx';

export const Form = FormProvider;
import { cn } from '@/lib/utils.ts';
import * as LabelPrimitive from '@radix-ui/react-label';
import { Slot } from '@radix-ui/react-slot';
import * as React from 'react';
import { Controller, ControllerProps, FieldPath, FieldValues, FormProvider } from 'react-hook-form';

const Form = FormProvider;

type FormFieldContextValue<
TFieldValues extends FieldValues = FieldValues,
TName extends FieldPath<TFieldValues> = FieldPath<TFieldValues>,
> = {
name: TName;
};

export const FormFieldContext = React.createContext<FormFieldContextValue>({} as FormFieldContextValue);

const FormField = <
TFieldValues extends FieldValues = FieldValues,
TName extends FieldPath<TFieldValues> = FieldPath<TFieldValues>,
>({
...props
}: ControllerProps<TFieldValues, TName>) => {
return (
<FormFieldContext.Provider value={{ name: props.name }}>
<Controller {...props} />
</FormFieldContext.Provider>
);
};

type FormItemContextValue = {
id: string;
};

export const FormItemContext = React.createContext<FormItemContextValue>({} as FormItemContextValue);

const FormItem = React.forwardRef<HTMLDivElement, React.HTMLAttributes<HTMLDivElement>>(
({ className, ...props }, ref) => {
const id = React.useId();

return (
<FormItemContext.Provider value={{ id }}>
<div ref={ref} className={cn('space-y-2', className)} {...props} />
</FormItemContext.Provider>
);
},
);
FormItem.displayName = 'FormItem';

const FormLabel = React.forwardRef<
React.ElementRef<typeof LabelPrimitive.Root>,
React.ComponentPropsWithoutRef<typeof LabelPrimitive.Root>
>(({ className, ...props }, ref) => {
const { error, formItemId } = useFormField();

return <Label ref={ref} className={cn(error && 'text-destructive', className)} htmlFor={formItemId} {...props} />;
});
FormLabel.displayName = 'FormLabel';

const FormControl = React.forwardRef<React.ElementRef<typeof Slot>, React.ComponentPropsWithoutRef<typeof Slot>>(
({ ...props }, ref) => {
const { error, formItemId, formDescriptionId, formMessageId } = useFormField();

return (
<Slot
ref={ref}
id={formItemId}
aria-describedby={!error ? `${formDescriptionId}` : `${formDescriptionId} ${formMessageId}`}
aria-invalid={!!error}
{...props}
/>
);
},
);
FormControl.displayName = 'FormControl';

const FormDescription = React.forwardRef<HTMLParagraphElement, React.HTMLAttributes<HTMLParagraphElement>>(
({ className, ...props }, ref) => {
const { formDescriptionId } = useFormField();

return <p ref={ref} id={formDescriptionId} className={cn('text-sm text-muted-foreground', className)} {...props} />;
},
);
FormDescription.displayName = 'FormDescription';

const FormMessage = React.forwardRef<HTMLParagraphElement, React.HTMLAttributes<HTMLParagraphElement>>(
({ className, children, ...props }, ref) => {
const { error, formMessageId } = useFormField();
const body = error ? String(error?.message) : children;

if (!body) {
return null;
}

return (
<p ref={ref} id={formMessageId} className={cn('text-sm font-medium text-destructive', className)} {...props}>
{body}
</p>
);
},
);
FormMessage.displayName = 'FormMessage';

export { Form, FormItem, FormLabel, FormControl, FormDescription, FormMessage, FormField };
8 changes: 0 additions & 8 deletions src/components/ui/form/index.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,2 @@
export * from './form-control.tsx';
export * from './form-description.tsx';
export * from './form-field-context.tsx';
export * from './form-field.tsx';
export * from './form-item.tsx';
export * from './form-item-context.tsx';
export * from './form-label.tsx';
export * from './form-message.tsx';
export * from './form.tsx';
export * from './use-form-field.tsx';
1 change: 1 addition & 0 deletions src/components/ui/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ export * from './calendar.tsx';
export * from './card.tsx';
export * from './dialog.tsx';
export * from './dropdown-menu.tsx';
export * from './form';
export * from './input.tsx';
export * from './label.tsx';
export * from './popover.tsx';
Expand Down
Loading

0 comments on commit 3f60719

Please sign in to comment.