mirror of
https://github.com/hanzoai/sign.git
synced 2026-10-21 01:21:51 +00:00
fix(editor): keep the editor's fields in a form without a resolver
useEditorFields keeps the envelope editor's fields in a react-hook-form
field array. Under @hookform/resolvers 5 its zod resolver types the form as
the schema's input, where field meta may be `{}`, while every function the
hook returns takes and gives parsed fields. Spelled as the output, the
resolver does not fit the form; left to the resolver, the fields do not fit
the functions.
The resolver never ran. The form is private to the hook, which only reads
it with getValues, rewrites it with reset and edits it through the field
array. Nothing calls handleSubmit or trigger or reads formState; with the
default onSubmit mode a field array validates only after a submit, and
validity is computed only when something subscribes to isValid. So the form
drops the resolver and is typed as what it holds: parsed fields, which is
what the defaults and every write already put in it.
Co-authored-by: Hanzo Dev <[email protected]>
This commit is contained in:
@@ -1,6 +1,5 @@
|
||||
import { useCallback, useEffect, useMemo, useState } from 'react';
|
||||
|
||||
import { zodResolver } from '@hookform/resolvers/zod';
|
||||
import type { Field, Recipient } from '@prisma/client';
|
||||
import { FieldType } from '@prisma/client';
|
||||
import { useFieldArray, useForm } from 'react-hook-form';
|
||||
@@ -30,11 +29,12 @@ export const ZLocalFieldSchema = z.object({
|
||||
|
||||
export type TLocalField = z.infer<typeof ZLocalFieldSchema>;
|
||||
|
||||
const ZEditorFieldsFormSchema = z.object({
|
||||
fields: z.array(ZLocalFieldSchema),
|
||||
});
|
||||
|
||||
export type TEditorFieldsFormSchema = z.infer<typeof ZEditorFieldsFormSchema>;
|
||||
// The form only stores the editor's fields. Nothing submits it or asks whether it is valid,
|
||||
// so it has no resolver, and every write goes through the functions below, which take
|
||||
// parsed fields.
|
||||
type TEditorFieldsForm = {
|
||||
fields: TLocalField[];
|
||||
};
|
||||
|
||||
type EditorFieldsProps = {
|
||||
envelope: TEditorEnvelope;
|
||||
@@ -75,30 +75,27 @@ export const useEditorFields = ({
|
||||
const [selectedRecipientId, setSelectedRecipientId] = useState<number | null>(null);
|
||||
|
||||
const generateDefaultValues = (fields?: Field[]) => {
|
||||
const formFields = (fields || envelope.fields).map(
|
||||
(field): TLocalField => ({
|
||||
id: field.id,
|
||||
formId: nanoid(),
|
||||
envelopeItemId: field.envelopeItemId,
|
||||
page: field.page,
|
||||
type: field.type,
|
||||
positionX: Number(field.positionX),
|
||||
positionY: Number(field.positionY),
|
||||
width: Number(field.width),
|
||||
height: Number(field.height),
|
||||
recipientId: field.recipientId,
|
||||
fieldMeta: field.fieldMeta ? ZFieldMetaSchema.parse(field.fieldMeta) : undefined,
|
||||
}),
|
||||
);
|
||||
const formFields = (fields || envelope.fields).map((field): TLocalField => ({
|
||||
id: field.id,
|
||||
formId: nanoid(),
|
||||
envelopeItemId: field.envelopeItemId,
|
||||
page: field.page,
|
||||
type: field.type,
|
||||
positionX: Number(field.positionX),
|
||||
positionY: Number(field.positionY),
|
||||
width: Number(field.width),
|
||||
height: Number(field.height),
|
||||
recipientId: field.recipientId,
|
||||
fieldMeta: field.fieldMeta ? ZFieldMetaSchema.parse(field.fieldMeta) : undefined,
|
||||
}));
|
||||
|
||||
return {
|
||||
fields: formFields,
|
||||
};
|
||||
};
|
||||
|
||||
const form = useForm<TEditorFieldsFormSchema>({
|
||||
const form = useForm<TEditorFieldsForm>({
|
||||
defaultValues: generateDefaultValues(),
|
||||
resolver: zodResolver(ZEditorFieldsFormSchema),
|
||||
});
|
||||
|
||||
const {
|
||||
|
||||
Reference in New Issue
Block a user