← All reusables
withFormAutoFocusOnError
extensionInstallation
npx jsrepo add github/reatom/reusables withFormAutoFocusOnError Copy the source code below and save it to the specified file path in your project.
with-form-auto-focus-on-error.ts
import { withCallHook, type Form } from '@reatom/core'
/**
* Form extension that focuses the first field with a validation error after a
* failed submit.
*/
export const withFormAutoFocusOnError =
() =>
<T extends Form<any>>(form: T): T => {
form.submit.onReject.extend(
withCallHook(() => {
const errorField = form
.fieldsList()
.find((field) => !!field.validation().error)
errorField?.elementRef()?.focus()
}),
)
return form
} Documentation
withFormAutoFocusOnError
Focuses the first field with a validation error after a failed submit.
withFormAutoFocusOnError()
Creates a form extension that:
- listens to
form.submit.onReject - finds the first field with
field.validation().error - calls
field.elementRef()?.focus()
Returns
Form extension that can be used with .extend() and returns the original form.
Example
import { reatomForm } from '@reatom/core'
import { withFormAutoFocusOnError } from '#reatom/extension/with-form-auto-focus-on-error'
const form = reatomForm(
{
name: {
initState: '',
validate: ({ value }) => (!value ? 'Required' : ''),
},
email: {
initState: '',
validate: ({ value }) => (!value ? 'Required' : ''),
},
},
{
onSubmit: async (state) => {
await api.save(state)
},
},
).extend(withFormAutoFocusOnError())
// Connect refs (example with DOM elements)
form.fields.name.elementRef.set({ focus: () => nameInput.focus() })
form.fields.email.elementRef.set({ focus: () => emailInput.focus() })
Example
import { reatomForm } from '@reatom/core'
import { withFormAutoFocusOnError } from './with-form-auto-focus-on-error'
const form = reatomForm(
{
name: {
initState: '',
validate: ({ value }) => (!value ? 'Required' : ''),
},
email: {
initState: '',
validate: ({ value }) => (!value ? 'Required' : ''),
},
},
{
onSubmit: async (state) => {
console.log('Submitted', state)
},
},
).extend(withFormAutoFocusOnError())
// Example: attach element refs to drive focus on error
const nameInput = { focus: () => console.log('focus name') }
const emailInput = { focus: () => console.log('focus email') }
form.fields.name.elementRef.set(nameInput)
form.fields.email.elementRef.set(emailInput)
// Trigger submit (will reject and focus name)
form.submit().catch(() => {})