@iwsio/forms
Advanced tools
Comparing version 2.0.1 to 2.1.0
@@ -5,4 +5,13 @@ import { PropsWithChildren } from 'react'; | ||
export type FieldManagerProps = PropsWithChildren & { | ||
/** | ||
* Initial field values to setup the form with. If you want to change these after initialization, use the `setFieldValues` method from the `useFieldManager` hook. | ||
*/ | ||
fields: FieldValues; | ||
/** | ||
* Initial default values to setup the form with. If you want to change these after initialization, use the `setDefaultValues` method from the `useFieldManager` hook. | ||
*/ | ||
defaultValues?: Record<string, string>; | ||
/** | ||
* Callback to be called when form is valid and submitted. Provides current field values. | ||
*/ | ||
onValidSubmit?: (fields: FieldValues) => void; | ||
@@ -19,5 +28,14 @@ } & Omit<ValidatedFormProps, 'onValidSubmit' | 'noValidate'>; | ||
} & { | ||
/** | ||
* Initial field values to setup the form with. If you want to change these after initialization, use the `setFieldValues` method from the `useFieldManager` hook. | ||
*/ | ||
fields: FieldValues; | ||
/** | ||
* Initial default values to setup the form with. If you want to change these after initialization, use the `setDefaultValues` method from the `useFieldManager` hook. | ||
*/ | ||
defaultValues?: Record<string, string>; | ||
/** | ||
* Callback to be called when form is valid and submitted. Provides current field values. | ||
*/ | ||
onValidSubmit?: (fields: FieldValues) => void; | ||
} & Omit<ValidatedFormProps, "onValidSubmit" | "noValidate"> & import("react").RefAttributes<HTMLFormElement>>; |
@@ -5,2 +5,2 @@ import { InputHTMLAttributes } from 'react'; | ||
export declare const Input: import("react").ForwardRefExoticComponent<ValidationProps & InputHTMLAttributes<HTMLInputElement> & import("react").RefAttributes<HTMLInputElement>>; | ||
export declare const InputField: import("react").ForwardRefExoticComponent<ValidationProps & InputHTMLAttributes<HTMLInputElement> & import("react").RefAttributes<HTMLInputElement>>; | ||
export declare const InputField: import("react").ForwardRefExoticComponent<Omit<InputProps, "DefaultValue"> & import("react").RefAttributes<HTMLInputElement>>; |
@@ -7,4 +7,2 @@ import { SelectHTMLAttributes, PropsWithChildren } from 'react'; | ||
} & ValidationProps & SelectHTMLAttributes<HTMLSelectElement> & import("react").RefAttributes<HTMLSelectElement>>; | ||
export declare const SelectField: import("react").ForwardRefExoticComponent<{ | ||
children?: import("react").ReactNode; | ||
} & ValidationProps & SelectHTMLAttributes<HTMLSelectElement> & import("react").RefAttributes<HTMLSelectElement>>; | ||
export declare const SelectField: import("react").ForwardRefExoticComponent<Omit<SelectProps, "DefaultValue"> & import("react").RefAttributes<HTMLSelectElement>>; |
@@ -5,2 +5,2 @@ import { TextareaHTMLAttributes } from 'react'; | ||
export declare const TextArea: import("react").ForwardRefExoticComponent<ValidationProps & TextareaHTMLAttributes<HTMLTextAreaElement> & import("react").RefAttributes<HTMLTextAreaElement>>; | ||
export declare const TextAreaField: import("react").ForwardRefExoticComponent<ValidationProps & TextareaHTMLAttributes<HTMLTextAreaElement> & import("react").RefAttributes<HTMLTextAreaElement>>; | ||
export declare const TextAreaField: import("react").ForwardRefExoticComponent<Omit<TextAreaProps, "DefaultValue"> & import("react").RefAttributes<HTMLTextAreaElement>>; |
@@ -31,2 +31,6 @@ import { ChangeEvent, Dispatch, SetStateAction } from 'react'; | ||
/** | ||
* Set all field values at once. Ignores undefined values. | ||
*/ | ||
setFields: (values: Partial<FieldValues>) => void; | ||
/** | ||
* Current field errors where kesy match input names. | ||
@@ -54,3 +58,3 @@ */ | ||
*/ | ||
handleChange: (e: ChangeEvent<HTMLInputElement | HTMLTextAreaElement | HTMLSelectElement>) => Record<string, string>; | ||
handleChange: (e: ChangeEvent<HTMLInputElement | HTMLTextAreaElement | HTMLSelectElement>) => FieldValues; | ||
/** | ||
@@ -61,3 +65,3 @@ * @deprecated Please use handleChange | ||
*/ | ||
onChange: (e: ChangeEvent<HTMLInputElement | HTMLTextAreaElement | HTMLSelectElement>) => Record<string, string>; | ||
onChange: (e: ChangeEvent<HTMLInputElement | HTMLTextAreaElement | HTMLSelectElement>) => FieldValues; | ||
/** | ||
@@ -68,2 +72,7 @@ * Invokes when submit event triggered and form has been validated and is valid. | ||
onValidSubmit: (fields: FieldValues) => void; | ||
/** | ||
* Use this to change the default values after initialization. | ||
* @param values The new default values to set. | ||
*/ | ||
setDefaultValues: (values: FieldValues) => void; | ||
}; |
import { FieldValues, UseFieldStateResult } from './types'; | ||
/** | ||
* Manages field state via change handler, values and error state. | ||
* @param fields Initial values for all fields; should include blank strings for fields without values. | ||
* @param defaultValues Default values to be set when invoking `reset()`, which falls back to `fields` if undefined. | ||
* @param fields Initial values for all fields; should include blank strings for fields without values. Change these later with the setFieldValues and setFieldValue methods returned from the hook. | ||
* @param defaultValues Initial default values to be set when invoking `reset()`, which falls back to `fields` if undefined. Change these later with the setDefaultValues method returned from the hook. | ||
* @param onValidSubmit Optional callback when form submit event triggered with valid form. Provides current field values as an argument. | ||
*/ | ||
export declare function useFieldState(fields: FieldValues, defaultValues?: FieldValues, onValidSubmit?: (fields: FieldValues) => void): UseFieldStateResult; |
@@ -9,29 +9,40 @@ "use strict"; | ||
* Manages field state via change handler, values and error state. | ||
* @param fields Initial values for all fields; should include blank strings for fields without values. | ||
* @param defaultValues Default values to be set when invoking `reset()`, which falls back to `fields` if undefined. | ||
* @param fields Initial values for all fields; should include blank strings for fields without values. Change these later with the setFieldValues and setFieldValue methods returned from the hook. | ||
* @param defaultValues Initial default values to be set when invoking `reset()`, which falls back to `fields` if undefined. Change these later with the setDefaultValues method returned from the hook. | ||
* @param onValidSubmit Optional callback when form submit event triggered with valid form. Provides current field values as an argument. | ||
*/ | ||
function useFieldState(fields, defaultValues, onValidSubmit) { | ||
const defaultFieldValues = defaultValues != null ? (0, defaults_1.defaults)((0, omitBy_1.omitBy)(fields, (v) => v == null || v === ''), defaultValues) : fields; | ||
const initDefaultFieldValues = defaultValues != null ? (0, defaults_1.defaults)((0, omitBy_1.omitBy)(fields, (v) => v == null || v === ''), defaultValues) : fields; | ||
const [reportValidation, setReportValidation] = (0, react_1.useState)(false); | ||
const [fieldValues, setFieldValues] = (0, react_1.useState)(fields); | ||
const [fieldErrors, setFieldErrors] = (0, react_1.useState)({}); | ||
const [defaultFieldValues, setDefaultFieldValues] = (0, react_1.useState)(initDefaultFieldValues); | ||
const localOnValidSubmit = (0, react_1.useCallback)(onValidSubmit, []); | ||
const setField = (key, value) => { | ||
const setField = (0, react_1.useCallback)((key, value) => { | ||
setFieldValues((oldFields) => (Object.assign(Object.assign({}, oldFields), { [key]: value }))); | ||
}; | ||
const setFieldError = (key, message) => { | ||
}, []); | ||
const setFields = (0, react_1.useCallback)((values) => { | ||
setFieldValues((oldFields) => { | ||
const newFields = Object.assign({}, oldFields); | ||
for (const key in values) { | ||
if (values[key] != null) | ||
newFields[key] = values[key]; // only set fields provided | ||
} | ||
return newFields; | ||
}); | ||
}, []); | ||
const setFieldError = (0, react_1.useCallback)((key, message) => { | ||
setFieldErrors((old) => (Object.assign(Object.assign({}, old), { [key]: message }))); | ||
}; | ||
const checkFieldError = (key) => { | ||
}, []); | ||
const checkFieldError = (0, react_1.useCallback)((key) => { | ||
if (reportValidation && fieldErrors[key] != null && fieldErrors[key] !== '') | ||
return fieldErrors[key]; | ||
return undefined; | ||
}; | ||
function reset() { | ||
setFieldErrors({}); | ||
setFieldValues(defaultFieldValues); | ||
setReportValidation(false); | ||
} | ||
const handleChange = (e) => { | ||
}, [fieldErrors, reportValidation]); | ||
const reset = (0, react_1.useCallback)(() => { | ||
setFieldErrors((_old) => ({})); | ||
setFieldValues((_old) => (Object.assign({}, defaultFieldValues))); | ||
setReportValidation((_old) => false); | ||
}, [defaultFieldValues]); | ||
const handleChange = (0, react_1.useCallback)((e) => { | ||
let value = e.target.value; | ||
@@ -50,3 +61,3 @@ const name = e.target.name; | ||
return updatedFields; | ||
}; | ||
}, []); | ||
return { | ||
@@ -57,3 +68,3 @@ fieldErrors, | ||
handleChange, | ||
onChange: handleChange, | ||
onChange: handleChange, // alias | ||
onValidSubmit: localOnValidSubmit, | ||
@@ -63,7 +74,9 @@ reportValidation, | ||
setField, | ||
setFields, | ||
setFieldError, | ||
setFieldErrors, | ||
setReportValidation | ||
setReportValidation, | ||
setDefaultValues: setDefaultFieldValues | ||
}; | ||
} | ||
exports.useFieldState = useFieldState; |
@@ -50,4 +50,4 @@ "use strict"; | ||
reportValidity: false, | ||
nativeValidation: true, | ||
nativeValidation: true, // NOTE: I think this makes most sense with the documentation. Much more effort is required when disabling this feature. | ||
className: '' | ||
}; |
{ | ||
"name": "@iwsio/forms", | ||
"version": "2.0.1", | ||
"version": "2.1.0", | ||
"description": "Simple library with useful React forms components and browser validation.", | ||
@@ -40,11 +40,10 @@ "main": "dist/index.js", | ||
"@testing-library/jest-dom": "^6.1.4", | ||
"@testing-library/react": "^14.1.0", | ||
"@testing-library/react": "^14.1.2", | ||
"@testing-library/user-event": "^14.5.1", | ||
"@types/node": "^20.9.0", | ||
"@types/react": "^18.2.37", | ||
"@types/react-dom": "^18.2.15", | ||
"@typescript-eslint/eslint-plugin": "^6.10.0", | ||
"@typescript-eslint/parser": "^6.10.0", | ||
"daisyui": "^3.9.4", | ||
"eslint": "^8.53.0", | ||
"@types/node": "^20.10.1", | ||
"@types/react": "^18.2.39", | ||
"@types/react-dom": "^18.2.17", | ||
"@typescript-eslint/eslint-plugin": "^6.13.1", | ||
"@typescript-eslint/parser": "^6.13.1", | ||
"eslint": "^8.54.0", | ||
"eslint-import-resolver-typescript": "^3.6.1", | ||
@@ -55,5 +54,3 @@ "eslint-plugin-import": "^2.29.0", | ||
"eslint-plugin-react": "^7.33.2", | ||
"jsdom": "^22.1.0", | ||
"lodash.defaults": "^4.2.0", | ||
"lodash.omitby": "^4.6.0", | ||
"jsdom": "^23.0.1", | ||
"npm-run-all": "^4.1.5", | ||
@@ -64,3 +61,3 @@ "react": "^18.2.0", | ||
"tslib": "^2.6.2", | ||
"typescript": "^5.2.2", | ||
"typescript": "^5.3.2", | ||
"vitest": "^0.34.6" | ||
@@ -67,0 +64,0 @@ }, |
44979
22
766