import React , { useEffect } from "react" ; import { useFormikContext } from "formik" ; export const ErrorFocus = ( { containerRef } ) => { const { isSubmitting , isValidating , errors } = useFormikContext ( ) ; useEffect ( ( ) => { const keys = Object . keys ( errors ) ; if ( keys . length > 0 && isSubmitting && ! isValidating ) { const errorElement = containerRef ?. current ?. querySelector < HTMLDivElement > ( `#form_field_${ keys [ 0 ] }` ) ; if ( errorElement && containerRef ?. current ) { const scrollableParent = getScrollableParent ( containerRef . current ) ; if ( scrollableParent ) { const top = errorElement . getBoundingClientRect ( ) . top ; scrollableParent . scrollTo ( { top : scrollableParent . scrollTop + top - 64 , behavior : "smooth" } ) ; } const input = errorElement . querySelector ( "input" ) ; if ( input ) input . focus ( ) ; } } } , [ isSubmitting , isValidating , errors , containerRef ] ) ; return null ; } ; const isScrollable = ( ele ) => { const hasScrollableContent = ele && ele . scrollHeight > ele . clientHeight ; const overflowYStyle = ele ? window . getComputedStyle ( ele ) . overflowY : null ; const isOverflowHidden = overflowYStyle && overflowYStyle . indexOf ( "hidden" ) !== - 1 ; return hasScrollableContent && ! isOverflowHidden ; } ; const getScrollableParent = ( ele ) : HTMLElement | null => { return ( ! ele || ele === document . body ) ? document . body : ( isScrollable ( ele ) ? ele : getScrollableParent ( ele . parentNode as HTMLElement ) ) ; } ;