@@ -369,4 +369,92 @@ describe('<Form />', () => {
369369
370370 expect ( ( ) => getByText ( 'Field is required' ) ) . toThrow ( ) ;
371371 } ) ;
372+
373+ it ( 'should update isTouched when an input is interacted with' , async ( ) => {
374+ const onSubmit = jest . fn ( ( ) => Promise . resolve ( ) ) ;
375+ const { getByRole, formInstance } = renderWithForm (
376+ < >
377+ < Form . Item name = "test" label = "Test" >
378+ < TextInput />
379+ </ Form . Item >
380+ < SubmitButton > Submit</ SubmitButton >
381+ </ > ,
382+ ) ;
383+
384+ // Initially, isTouched should be false
385+ expect ( formInstance . isTouched ) . toBeFalsy ( ) ;
386+
387+ // Simulate user interaction
388+ const input = getByRole ( 'textbox' ) ;
389+ await act ( async ( ) => {
390+ await userEvents . type ( input , 'hello' ) ;
391+ } ) ;
392+
393+ // After typing, isTouched should be true
394+ expect ( formInstance . isTouched ) . toBeTruthy ( ) ;
395+ } ) ;
396+
397+ it ( 'should update isDirty when input value differs from the initial value' , async ( ) => {
398+ const onSubmit = jest . fn ( ( ) => Promise . resolve ( ) ) ;
399+ const defaultValues = { test : 'initial' } ;
400+ const { getByRole, formInstance } = renderWithForm (
401+ < >
402+ < TextInput name = "test" label = "Test" />
403+ < SubmitButton > Submit</ SubmitButton >
404+ </ > ,
405+ { formProps : { onSubmit, defaultValues } } ,
406+ ) ;
407+
408+ // Initially, isDirty should be false because the value is same as initial
409+ expect ( formInstance . isDirty ) . toBeFalsy ( ) ;
410+
411+ // Change the input value
412+ const input = getByRole ( 'textbox' ) ;
413+ await act ( async ( ) => {
414+ await userEvents . clear ( input ) ;
415+ await userEvents . type ( input , 'changed' ) ;
416+ } ) ;
417+
418+ // After change, isDirty should be true
419+ expect ( formInstance . isDirty ) . toBeTruthy ( ) ;
420+ } ) ;
421+
422+ it ( 'should maintain isTouched true but set isDirty false when input value reverts to initial' , async ( ) => {
423+ const onSubmit = jest . fn ( ( ) => Promise . resolve ( ) ) ;
424+ const initialValue = { test : 'initial' } ;
425+ const { getByRole, formInstance } = renderWithForm (
426+ < >
427+ < Form . Item name = "test" label = "Test" >
428+ < TextInput />
429+ </ Form . Item >
430+ < SubmitButton > Submit</ SubmitButton >
431+ </ > ,
432+ { formProps : { onSubmit, defaultValues : initialValue } } ,
433+ ) ;
434+
435+ // Initially, both isTouched and isDirty should be false
436+ expect ( formInstance . isTouched ) . toBeFalsy ( ) ;
437+ expect ( formInstance . isDirty ) . toBeFalsy ( ) ;
438+
439+ // Change the input to a different value
440+ const input = getByRole ( 'textbox' ) ;
441+ await act ( async ( ) => {
442+ await userEvents . clear ( input ) ;
443+ await userEvents . type ( input , 'changed' ) ;
444+ } ) ;
445+
446+ // After change, both isTouched and isDirty should be true
447+ expect ( formInstance . isTouched ) . toBeTruthy ( ) ;
448+ expect ( formInstance . isDirty ) . toBeTruthy ( ) ;
449+
450+ // Revert the input back to its initial value
451+ await act ( async ( ) => {
452+ await userEvents . clear ( input ) ;
453+ await userEvents . type ( input , 'initial' ) ;
454+ } ) ;
455+
456+ // After reverting, isTouched remains true, but isDirty should be false
457+ expect ( formInstance . isTouched ) . toBeTruthy ( ) ;
458+ expect ( formInstance . isDirty ) . toBeFalsy ( ) ;
459+ } ) ;
372460} ) ;
0 commit comments