diff --git a/packages/dataviews/src/normalize-form-fields.ts b/packages/dataviews/src/normalize-form-fields.ts index 3cd5f67564d7ce..945293c8c3d8d6 100644 --- a/packages/dataviews/src/normalize-form-fields.ts +++ b/packages/dataviews/src/normalize-form-fields.ts @@ -1,13 +1,13 @@ /** * Internal dependencies */ -import type { Form } from './types'; +import type { Form, FormFieldValidation } from './types'; -interface NormalizedFormField { +export type NormalizedFormField = { id: string; layout: 'regular' | 'panel'; labelPosition: 'side' | 'top' | 'none'; -} +} & { validation: FormFieldValidation }; export default function normalizeFormFields( form: Form @@ -20,12 +20,19 @@ export default function normalizeFormFields( const labelPosition = form.labelPosition ?? ( layout === 'regular' ? 'top' : 'side' ); - return ( form.fields ?? [] ).map( ( field ) => { + return Object.entries( form.fields ?? {} ).map( ( [ id, field ] ) => { if ( typeof field === 'string' ) { return { - id: field, + id, layout, labelPosition, + validation: { + callback: () => ( { + isValid: true, + errorMessage: '', + } ), + showErrorOnlyWhenDirty: true, + }, }; } @@ -35,8 +42,12 @@ export default function normalizeFormFields( ( fieldLayout === 'regular' ? 'top' : 'side' ); return { ...field, + id, layout: fieldLayout, labelPosition: fieldLabelPosition, + validation: { + ...field.validation, + }, }; } ); } diff --git a/packages/dataviews/src/types.ts b/packages/dataviews/src/types.ts index 036b57c426e2ef..e6d2c831d242ef 100644 --- a/packages/dataviews/src/types.ts +++ b/packages/dataviews/src/types.ts @@ -549,7 +549,7 @@ export type SimpleFormField = { id: string; layout?: 'regular' | 'panel'; labelPosition?: 'side' | 'top' | 'none'; -}; +} & { validation: FormFieldValidation }; export type CombinedFormField = { id: string; @@ -557,10 +557,25 @@ export type CombinedFormField = { layout?: 'regular' | 'panel'; labelPosition?: 'side' | 'top' | 'none'; children: Array< FormField | string >; +} & { validation: FormFieldValidation }; + +export type ValidationResult = { + isValid: boolean; + errorMessage: string | undefined; }; -export type FormField = SimpleFormField | CombinedFormField; +export type FormFieldValidation = { + /** + * The validation should be triggered only when the field is dirty. + */ + showErrorOnlyWhenDirty: boolean; + /** + * The validation function. + */ + callback: ( data: any ) => ValidationResult; +}; +export type FormField = SimpleFormField | CombinedFormField; /** * The form configuration. */ @@ -568,6 +583,11 @@ export type Form = { type?: 'regular' | 'panel'; fields?: Array< FormField | string >; labelPosition?: 'side' | 'top' | 'none'; + touchedFields: string[]; + messageErrors: Record< string, string | undefined >; + setTouchedFields: ( touchedFields: string[] ) => void; + setErrors: ( field: string, error: string | undefined ) => void; + isFormValid: ( data: Record< string, any > ) => boolean; }; export interface DataFormProps< Item > { diff --git a/packages/fields/src/actions/duplicate-post.tsx b/packages/fields/src/actions/duplicate-post.tsx index fd7e0ae9de4ad1..b66fba37500379 100644 --- a/packages/fields/src/actions/duplicate-post.tsx +++ b/packages/fields/src/actions/duplicate-post.tsx @@ -23,9 +23,6 @@ import type { BasePost, CoreDataError } from '../types'; import { getItemTitle } from './utils'; const fields = [ titleField ]; -const formDuplicateAction = { - fields: [ 'title' ], -}; const duplicatePost: Action< BasePost > = { id: 'duplicate-post', @@ -139,7 +136,8 @@ const duplicatePost: Action< BasePost > = { setItem( ( prev ) => ( { ...prev, diff --git a/packages/fields/src/actions/reorder-page.tsx b/packages/fields/src/actions/reorder-page.tsx index 1820884d8d8c73..068793d1ed8b83 100644 --- a/packages/fields/src/actions/reorder-page.tsx +++ b/packages/fields/src/actions/reorder-page.tsx @@ -39,7 +39,7 @@ function ReorderModal( { async function onOrder( event: React.FormEvent ) { event.preventDefault(); - + // @ts-ignore if ( ! isItemValid( item, fields, formOrderAction ) ) { return; } @@ -68,6 +68,7 @@ function ReorderModal( { } ); } } + // @ts-ignore const isSaveDisabled = ! isItemValid( item, fields, formOrderAction ); return (
@@ -80,6 +81,7 @@ function ReorderModal( { setItem( {