Created
July 28, 2019 11:33
-
-
Save DJanoskova/12e0f5d4669aafd73c16d0b199631424 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
| export function useFormInput ({ | |
| name, | |
| validation = '', | |
| values: formData, | |
| setValues: setFormData, | |
| defaultInvalidAttr, | |
| handleError | |
| }) { | |
| const formValue = dot.pick(name, formData) || ''; | |
| const [value, setValue] = useState(formValue); | |
| const [isValid, setIsValid] = useState(true); | |
| const [isTouched, setIsTouched] = useState(false); | |
| const [isFocused, setIsFocused] = useState(false); | |
| const [validationRules] = useState(validation); | |
| const handleValidation = useCallback(() => { | |
| const isValid = validate(value, validationRules); | |
| setIsValid(isValid); | |
| handleError(name, isValid); | |
| }, [setIsValid, validationRules, name, value, handleError]); | |
| // watch for external parent data changes | |
| useEffect(() => { | |
| if (value !== formValue) { | |
| setValue(formValue); | |
| setIsTouched(false); | |
| setIsFocused(false); | |
| } | |
| }, [formValue, value, setValue, setIsFocused, setIsTouched]); | |
| // validate on value change | |
| useEffect(() => { | |
| handleValidation(); | |
| }, [handleValidation, name]); | |
| // rewrite self and parent's value | |
| const handleChange = useCallback(({ target }) => { | |
| const { value, checked, type } = target; | |
| const newValue = type === 'checkbox' ? checked : value; | |
| // using dot helps us change nested values | |
| let data; | |
| const isNested = name.includes('.'); | |
| if (isNested) { | |
| dot.override = true; | |
| data = dot.str(name, newValue, { ...formData }); | |
| } | |
| else data = { ...formData, [name]: newValue }; | |
| setValue(newValue); | |
| setFormData(data); | |
| }, [setValue, formData, setFormData, name]); | |
| const handleFocus = useCallback(() => { | |
| setIsTouched(true); | |
| setIsFocused(true); | |
| handleValidation(); | |
| }, [setIsTouched, setIsFocused, handleValidation]); | |
| const handleBlur = useCallback(() => { | |
| setIsFocused(false); | |
| }, [setIsFocused]); | |
| const showError = !isValid && isTouched && !isFocused; | |
| const invalidAttr = showError ? defaultInvalidAttr : null; | |
| return { | |
| value, | |
| name, | |
| onChange: handleChange, | |
| onFocus: handleFocus, | |
| onBlur: handleBlur, | |
| ...invalidAttr | |
| }; | |
| } |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment