react-bfm
Version:
A basic field / form manager for React using hooks
83 lines • 4.14 kB
JavaScript
import _extends from "@babel/runtime/helpers/esm/extends";
import _objectWithoutPropertiesLoose from "@babel/runtime/helpers/esm/objectWithoutPropertiesLoose";
var _excluded = ["validator", "dirtyCheck", "transformValueToInput", "transformEventToValue", "onChange", "onFocus", "onBlur"],
_excluded2 = ["namespace", "fieldName", "initialValue"];
import { useCallback, useContext, useEffect, useRef } from 'react';
import { BFMHooksContext } from './context';
import { defaultEventToValue, defaultValueToInput } from './helpers';
import { useFieldValue } from './field/hooks';
export var useConnectField = function useConnectField(props) {
var _useContext = useContext(BFMHooksContext),
blurField = _useContext.blurField,
changeField = _useContext.changeField,
initialValueField = _useContext.initialValueField,
focusField = _useContext.focusField,
initField = _useContext.initField,
removeField = _useContext.removeField;
var validator = props.validator,
dirtyCheck = props.dirtyCheck,
_props$transformValue = props.transformValueToInput,
transformValueToInput = _props$transformValue === void 0 ? defaultValueToInput : _props$transformValue,
transformEventToValue = props.transformEventToValue,
onChange = props.onChange,
onFocus = props.onFocus,
onBlur = props.onBlur,
staticProps = _objectWithoutPropertiesLoose(props, _excluded);
// For storing static props see bellow.
var propsRef = useRef({});
// Hook specific props.
var namespace = staticProps.namespace,
fieldName = staticProps.fieldName,
initialValue = staticProps.initialValue,
otherProps = _objectWithoutPropertiesLoose(staticProps, _excluded2);
// Throw an error if namespace and/or fieldName changes after first rendering, because it's not supported
// Dynamically changing these values can result in strange side effects. It's better to render a new component.
var namesRef = useRef({
namespace: namespace,
fieldName: fieldName
});
useEffect(function () {
if (namesRef.current.namespace !== namespace || namesRef.current.fieldName !== fieldName) {
throw new Error('Changing the namespace and/or fieldName of an already rendered component is not supported.');
}
}, [namespace, fieldName]);
// Store static props for use in the validator callback.
// This way you can (re-)use for example: required, minlength, maxlength, etc. in the validator
propsRef.current = staticProps;
var getError = useCallback(function (_value) {
return validator && validator(_value, propsRef.current);
}, [validator]);
var value = useFieldValue(namespace, fieldName);
useEffect(function () {
// init field on mount
initField(namespace, fieldName, initialValue, getError(initialValue));
// remove field on unmount
return function () {
removeField(namespace, fieldName);
};
}, []); // eslint-disable-line react-hooks/exhaustive-deps
// update initialValue on change, see `initialValueField` function for more info
useEffect(function () {
initialValueField(namespace, fieldName, initialValue, getError(initialValue));
}, [initialValueField, fieldName, getError, initialValue, namespace]);
var handleFocus = useCallback(function (event) {
focusField(namespace, fieldName);
onFocus && onFocus(event);
}, [fieldName, namespace, onFocus, focusField]);
var handleChange = useCallback(function (arg1, arg2, arg3, arg4, arg5) {
var value = transformEventToValue ? transformEventToValue(arg1, arg2, arg3, arg4, arg5) : defaultEventToValue(arg1);
var error = getError(value);
changeField(namespace, fieldName, value, error, dirtyCheck);
onChange && onChange(arg1, arg2, arg3, arg4, arg5);
}, [transformEventToValue, getError, changeField, namespace, fieldName, dirtyCheck, onChange]);
var handleBlur = useCallback(function (event) {
blurField(namespace, fieldName);
onBlur && onBlur(event);
}, [fieldName, namespace, onBlur, blurField]);
return _extends({}, otherProps, {
value: transformValueToInput(value),
onFocus: handleFocus,
onChange: handleChange,
onBlur: handleBlur
});
};