react-proforma
Version:
React Proforma helps you build simple to complex web forms with ease in React. -- Simplicity where you want it. Flexibility where you need it.
67 lines (66 loc) • 3.35 kB
JavaScript
;
var __importDefault = (this && this.__importDefault) || function (mod) {
return (mod && mod.__esModule) ? mod : { "default": mod };
};
Object.defineProperty(exports, "__esModule", { value: true });
var react_1 = __importDefault(require("react"));
var ProformaContext_1 = require("./ProformaContext");
var memoize_one_1 = __importDefault(require("memoize-one"));
function memoCompare(prevProps, nextProps) {
return prevProps.error === nextProps.error;
}
var _FieldError = function (props) {
var Component = props.component, error = props.error;
return react_1.default.createElement(Component, { error: error });
};
var MemoFieldError = react_1.default.memo(_FieldError, memoCompare);
// ==== MEMOIZING THE ARRAY MAPPING ====
var equalityFn = function (newArgs, lastArgs) {
var newErrors = newArgs[0];
var lastErrors = lastArgs[0];
if (newErrors.length !== lastErrors.length)
return false;
for (var i = 0, n = newErrors.length; i < n; i++) {
if (newErrors[i] !== lastErrors[i])
return false;
}
return true;
};
function getErrorMappingFn(component) {
return function errorMappingFn(error, index) {
return react_1.default.createElement(MemoFieldError, { key: index, component: component, error: error });
};
}
function mapErrors(errors, component) {
return errors.map(getErrorMappingFn(component));
}
var memoMapErrors = memoize_one_1.default(mapErrors, equalityFn);
function getContextConsumerProcessor(name, component) {
return function processContextConsumer(_a) {
var touched = _a.touched, errors = _a.errors;
// necessary for type guard to work
var _errors = errors[name];
var _touched = touched[name];
if (_touched === true && _errors !== null) {
return memoMapErrors(_errors, component);
}
return null;
};
}
/**
* Takes a component that you provide and returns an array of your component, each of which has been provided the error message as a prop "error".
* The errors will be displayed only if that field has been touched, and there are errors to display (based on the validationObject you provided).
* This means the component you provide must accept a single prop named "error", which you can use to display the error message however you like inside the component.
*
* @param {string} name - A form element name that corresponds with a property on your "initialValues" object.
* @param {React.ComponentType<{ error: string }>} component - Any component that accepts a single string prop called "error", which you use to display the error message inside your component.
* @returns {JSX.Element} JSX.Element
*/
function fieldError(name, component) {
if (!name)
throw new Error('"fieldError" will not function without a "name" argument passed to it. Please provide a "name" argument that corresponds with one of the properties on your "initialValues" object.');
if (!component)
throw new Error('"fieldError" will not function without a "component" argument passed to it. Please provide one.');
return (react_1.default.createElement(ProformaContext_1.ProformaContextConsumer, null, getContextConsumerProcessor(name, component)));
}
exports.fieldError = fieldError;