@antmjs/vantui
Version:
一套适用于Taro3及React的vantui组件库
597 lines (592 loc) • 22.3 kB
JavaScript
"use strict";
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault");
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.default = void 0;
var _regenerator = _interopRequireDefault(require("@babel/runtime/regenerator"));
var _asyncToGenerator2 = _interopRequireDefault(require("@babel/runtime/helpers/asyncToGenerator"));
var _defineProperty2 = _interopRequireDefault(require("@babel/runtime/helpers/defineProperty"));
var _typeof2 = _interopRequireDefault(require("@babel/runtime/helpers/typeof"));
var _classCallCheck2 = _interopRequireDefault(require("@babel/runtime/helpers/classCallCheck"));
var _createClass2 = _interopRequireDefault(require("@babel/runtime/helpers/createClass"));
var _reactDom = require("react-dom");
var _validator = require("../../common/validator");
/* eslint-disable @typescript-eslint/ban-ts-comment */
/* 对外接口 */
var formInstanceApi = ['setCallback', 'dispatch', 'registerValidateFields', 'resetFields', 'setFields', 'setFieldsValue', 'getFieldsValue', 'getFieldValue', 'validateFields', 'submit', 'unRegisterValidate', 'registerRequiredMessageCallback', 'validateFieldValue', 'setErrorMessage'];
var isReg = function isReg(value) {
return value instanceof RegExp;
};
var FormStore = /*#__PURE__*/function () {
function FormStore(forceUpdate, defaultFormValue) {
(0, _classCallCheck2.default)(this, FormStore);
this.FormUpdate = forceUpdate;
this.model = {};
this.control = {};
this.isSchedule = false;
this.callback = {};
this.penddingValidateQueue = [];
this.defaultFormValue = defaultFormValue || {};
this.requiredMessageCallback = undefined;
this.multiLevelKeys = [];
}
(0, _createClass2.default)(FormStore, [{
key: "getForm",
value: function getForm() {
var _this = this;
return formInstanceApi.reduce(function (map, item) {
map[item] = _this[item].bind(_this);
return map;
}, {});
}
}, {
key: "registerRequiredMessageCallback",
value: function registerRequiredMessageCallback(callback) {
this.requiredMessageCallback = callback;
}
}, {
key: "setCallback",
value: function setCallback(callback) {
if (callback) this.callback = callback;
}
}, {
key: "setErrorMessage",
value: function setErrorMessage(name_, message) {
var name = Array.isArray(name_) ? name_.join('.') : name_;
if (this.model[name]) {
this.model[name].message = message;
this.model[name].status = 'reject';
this.FormUpdate();
} else {
console.error('form warning: setErrorMessage params.name is not register');
}
}
}, {
key: "dispatch",
value: function dispatch(action) {
if (!action && (0, _typeof2.default)(action) !== 'object') return null;
var type = action.type;
for (var _len = arguments.length, arg = new Array(_len > 1 ? _len - 1 : 0), _key = 1; _key < _len; _key++) {
arg[_key - 1] = arguments[_key];
}
if (~formInstanceApi.indexOf(type)) {
// @ts-ignore
return this[type].apply(this, arg);
} else if (typeof this[type] === 'function') {
// @ts-ignore
return this[type].apply(this, arg);
}
}
}, {
key: "registerValidateFields",
value: function registerValidateFields(name_, control, model) {
var name = Array.isArray(name_) ? name_.join('.') : name_;
var defaultFormValue_ = this.defaultFormValue;
if (name.includes('.') && !model['mutiLevel']) {
defaultFormValue_ = this.transformToSingleLevelData(this.defaultFormValue, name.split('.')[0]);
}
if (defaultFormValue_[name]) {
if (!this.model[name] || this.model[name].value === undefined) {
model['value'] = defaultFormValue_[name];
}
}
if (!model['value'] && this.model[name]) model['value'] = this.model[name].value;
if (model['mutiLevel']) {
if (!this.multiLevelKeys.includes(name)) {
this.multiLevelKeys.push(name);
}
}
if (!model['mutiLevel']) {
var keyIndex = this.multiLevelKeys.indexOf(name);
if (keyIndex > 0) {
this.multiLevelKeys.splice(keyIndex, 1);
}
}
var shouldUpdate = !this.model[name] || this.model[name].value === undefined;
var validate = FormStore.createValidate(model);
this.model[name] = validate;
this.control[name] = control;
if (shouldUpdate) {
control === null || control === void 0 ? void 0 : control['changeValue']();
}
}
}, {
key: "unRegisterValidate",
value: function unRegisterValidate(name_) {
var name = Array.isArray(name_) ? name_.join('.') : name_;
delete this.model[name];
delete this.control[name];
}
}, {
key: "notifyChange",
value: function notifyChange(name_, hiddenFormChange) {
var name = Array.isArray(name_) ? name_.join('.') : name_;
var controller = this.control[name];
if (controller) controller === null || controller === void 0 ? void 0 : controller.changeValue();
if (!hiddenFormChange) {
var onChange = this.callback.onChange;
if (onChange) {
var value = this.model[name].value;
onChange(FormStore.transformMultilevelData((0, _defineProperty2.default)({}, name, value)), this.getFieldsValue());
}
}
}
}, {
key: "setFields",
value: function setFields(object) {
if ((0, _typeof2.default)(object) !== 'object') return;
this.transformModelToSingelLevelData(object, this.multiLevelKeys);
for (var key in this.model) {
var item = this.model[key];
this.setValueClearStatus(item, key, item.value, true); // 批量更新hiddenFormChange
}
var onChange = this.callback.onChange;
if (onChange) {
onChange(object, this.getFieldsValue());
}
}
}, {
key: "setFieldsValue",
value: function setFieldsValue(name_, modelValue) {
var name = Array.isArray(name_) ? name_.join('.') : name_;
var model = this.model[name];
if (!model) return false;
if (toString.call(modelValue) === '[Object, object]' && modelValue.value) {
var message = modelValue.message,
rule = modelValue.rule,
value = modelValue.value;
if (message) model.message = message;
if (rule) model.rule = rule;
if (value && model.value === undefined) model.value = value;
model.status = 'pendding';
this.validateFieldValue(name, true);
} else {
this.setValueClearStatus(model, name, modelValue);
}
}
}, {
key: "setValueClearStatus",
value: function setValueClearStatus(model, name_, value, hiddenFormChange) {
var name = Array.isArray(name_) ? name_.join('.') : name_;
model['value'] = value;
model['status'] = 'pendding';
this.notifyChange(name, hiddenFormChange);
}
// 扁平数据转多层数据结构
}, {
key: "transformModelToSingelLevelData",
value:
// model数据结构扁平化
function transformModelToSingelLevelData(data, multiLevelKeys) {
// eslint-disable-next-line @typescript-eslint/no-this-alias
var that = this;
function unitWork(curKey, dd) {
if (toString.call(dd) === '[object Object]') {
if (multiLevelKeys.includes(curKey)) {
that.model[curKey].value = dd;
} else {
for (var key in dd) {
var value = dd[key];
unitWork(curKey ? "".concat(curKey, ".").concat(key) : key, value);
}
}
} else if (toString.call(dd) === '[object Array]') {
if (multiLevelKeys.includes(curKey)) {
that.model[curKey].value = dd;
} else {
for (var i = 0; i < dd.length; i++) {
var _value = dd[i];
unitWork(curKey ? "".concat(curKey, ".").concat(i) : "".concat(i), _value);
}
}
} else {
if (that.model[curKey]) {
that.model[curKey].value = dd;
}
}
}
unitWork('', data);
}
// 目标数据的多层数据扁平化
}, {
key: "transformToSingleLevelData",
value: function transformToSingleLevelData(data, targetKey) {
var res = {};
var work = function work(prevKey, dd) {
if (toString.call(dd) === '[object Object]') {
for (var k in dd) {
work(prevKey ? "".concat(prevKey, ".").concat(k) : k, dd[k]);
}
} else if (toString.call(dd) === '[object Array]') {
for (var i = 0; i < dd.length; i++) {
work(prevKey ? "".concat(prevKey, ".").concat(i) : i, dd[i]);
}
} else {
res[prevKey] = dd;
}
};
for (var kk in data) {
if (targetKey === kk) {
work(kk, data[kk]);
}
}
return res;
}
}, {
key: "getFieldsValue",
value: function getFieldsValue() {
var _this2 = this;
var formData = {};
Object.keys(this.model).forEach(function (modelName) {
formData[modelName] = _this2.model[modelName].value;
});
return FormStore.transformMultilevelData(formData);
}
}, {
key: "resetFields",
value: function resetFields() {
var _this3 = this;
Object.keys(this.model).forEach(function (modelName) {
_this3.setValueClearStatus(_this3.model[modelName], modelName, null);
});
}
}, {
key: "getFieldModel",
value: function getFieldModel(name_) {
var name = Array.isArray(name_) ? name_.join('.') : name_;
var model = this.model[name];
return model ? model : {};
}
}, {
key: "getFieldValue",
value: function getFieldValue(name_) {
var name = Array.isArray(name_) ? name_.join('.') : name_;
var model = this.model[name];
if (!model && this.defaultFormValue[name]) return this.defaultFormValue[name];
return model ? model.value : null;
}
}, {
key: "validateFieldValue",
value: function () {
var _validateFieldValue = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee(name_) {
var _this4 = this;
var forceUpdate,
name,
model,
lastStatus,
required,
rules,
value,
status,
i,
rule,
message,
validateCallback,
result,
validationMessage,
notify,
_args = arguments;
return _regenerator.default.wrap(function _callee$(_context) {
while (1) switch (_context.prev = _context.next) {
case 0:
forceUpdate = _args.length > 1 && _args[1] !== undefined ? _args[1] : true;
name = Array.isArray(name_) ? name_.join('.') : name_;
model = this.model[name];
/* 记录上次状态 */
lastStatus = model === null || model === void 0 ? void 0 : model.status;
if (model) {
_context.next = 6;
break;
}
return _context.abrupt("return", null);
case 6:
required = model.required, rules = model.rules, value = model.value;
status = 'resolve';
_context.prev = 8;
if (required && FormStore.isFieldNull(value)) {
status = 'reject';
if (this.requiredMessageCallback) {
this.model[name].message = this.requiredMessageCallback(this.model[name].label, name);
} else {
if (this.model[name].label) {
this.model[name].message = this.model[name].label + '不能为空';
} else {
this.model[name].message = '此处不能为空';
}
}
}
i = 0;
case 11:
if (!(i < rules.length)) {
_context.next = 50;
break;
}
rule = rules[i].rule;
message = rules[i].message;
if (!(value || value === 0)) {
_context.next = 47;
break;
}
if (!isReg(rule)) {
_context.next = 22;
break;
}
status = rule.test(value) ? 'resolve' : 'reject';
if (!(status === 'reject')) {
_context.next = 20;
break;
}
this.model[name].message = message;
return _context.abrupt("break", 50);
case 20:
_context.next = 47;
break;
case 22:
if (!(typeof rule === 'function')) {
_context.next = 47;
break;
}
// 传统的回调函数形式
validateCallback = function validateCallback(callbackMessage) {
_this4.model[name].message = callbackMessage;
status = !callbackMessage ? 'resolve' : 'reject';
}; // 检查函数是否返回Promise,传入callback兼容同步回调
result = rule(value, validateCallback);
if (!(0, _validator.isPromise)(result)) {
_context.next = 44;
break;
}
_context.prev = 26;
// 规则函数返回Promise的情况
model.status = 'validating'; // 添加校验中的状态
_context.next = 30;
return result;
case 30:
validationMessage = _context.sent;
status = !validationMessage ? 'resolve' : 'reject';
if (!(status === 'reject')) {
_context.next = 35;
break;
}
this.model[name].message = validationMessage || message;
return _context.abrupt("break", 50);
case 35:
_context.next = 42;
break;
case 37:
_context.prev = 37;
_context.t0 = _context["catch"](26);
// 处理异步校验过程中的错误
status = 'reject';
this.model[name].message = (_context.t0 === null || _context.t0 === void 0 ? void 0 : _context.t0.message) || message || '校验失败';
return _context.abrupt("break", 50);
case 42:
_context.next = 47;
break;
case 44:
// 执行规则函数
rule(value, validateCallback);
// 如果回调没有被立即调用,可能是异步回调
// 但我们不能在这里等待它,因为可能永远不会被调用
if (!(status === 'reject')) {
_context.next = 47;
break;
}
return _context.abrupt("break", 50);
case 47:
i++;
_context.next = 11;
break;
case 50:
_context.next = 56;
break;
case 52:
_context.prev = 52;
_context.t1 = _context["catch"](8);
// 捕获整个校验过程中的任何错误
status = 'reject';
this.model[name].message = (_context.t1 === null || _context.t1 === void 0 ? void 0 : _context.t1.message) || '校验过程发生错误';
case 56:
model.status = status;
if (lastStatus !== status || forceUpdate) {
// 校验的时候不触发form change
notify = this.notifyChange.bind(this, name, true);
this.penddingValidateQueue.push(notify);
}
this.scheduleValidate();
return _context.abrupt("return", status);
case 60:
case "end":
return _context.stop();
}
}, _callee, this, [[8, 52], [26, 37]]);
}));
function validateFieldValue(_x) {
return _validateFieldValue.apply(this, arguments);
}
return validateFieldValue;
}()
}, {
key: "scheduleValidate",
value: function scheduleValidate() {
var _this5 = this;
if (this.isSchedule) return;
this.isSchedule = true;
Promise.resolve().then(function () {
(0, _reactDom.unstable_batchedUpdates)(function () {
do {
var notify = _this5.penddingValidateQueue.shift();
notify && notify();
} while (_this5.penddingValidateQueue.length > 0);
_this5.isSchedule = false;
});
});
}
}, {
key: "validateFields",
value: function validateFields(callback) {
var _this6 = this;
// 使用Promise处理异步校验
setTimeout( /*#__PURE__*/(0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee3() {
var errorsMess, modelNames, validationPromises, results;
return _regenerator.default.wrap(function _callee3$(_context3) {
while (1) switch (_context3.prev = _context3.next) {
case 0:
_context3.prev = 0;
errorsMess = [];
modelNames = Object.keys(_this6.model); // 等待所有字段的异步校验完成
validationPromises = modelNames.map( /*#__PURE__*/function () {
var _ref2 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee2(modelName) {
var status;
return _regenerator.default.wrap(function _callee2$(_context2) {
while (1) switch (_context2.prev = _context2.next) {
case 0:
_context2.next = 2;
return _this6.validateFieldValue(modelName, true);
case 2:
status = _context2.sent;
if (!(status === 'reject')) {
_context2.next = 5;
break;
}
return _context2.abrupt("return", _this6.model[modelName].message);
case 5:
return _context2.abrupt("return", null);
case 6:
case "end":
return _context2.stop();
}
}, _callee2);
}));
return function (_x2) {
return _ref2.apply(this, arguments);
};
}()); // 收集所有错误信息
_context3.next = 6;
return Promise.all(validationPromises);
case 6:
results = _context3.sent;
results.forEach(function (message) {
if (message) errorsMess.push(message);
});
// 调用回调函数
callback(errorsMess, _this6.getFieldsValue());
_context3.next = 15;
break;
case 11:
_context3.prev = 11;
_context3.t0 = _context3["catch"](0);
console.error('表单校验过程发生错误:', _context3.t0);
callback(['表单校验过程发生错误'], _this6.getFieldsValue());
case 15:
case "end":
return _context3.stop();
}
}, _callee3, null, [[0, 11]]);
})));
}
}, {
key: "submit",
value: function submit(cb) {
var _this7 = this;
this.validateFields(function (errorMess) {
var _this7$callback = _this7.callback,
onFinish = _this7$callback.onFinish,
onFinishFailed = _this7$callback.onFinishFailed;
var fieldValues = _this7.getFieldsValue();
var errs = errorMess.length ? errorMess : null;
cb && cb(errs, fieldValues);
if (errs) {
onFinishFailed && typeof onFinishFailed === 'function' && onFinishFailed(errs);
return;
}
onFinish && typeof onFinish === 'function' && onFinish(errs, _this7.getFieldsValue());
});
}
}], [{
key: "createValidate",
value: function createValidate(validateModal) {
var value = validateModal.value,
required = validateModal.required,
rules = validateModal.rules,
label = validateModal.label;
return {
value: value,
rules: Array.isArray(rules) ? rules : [rules],
required: required || false,
status: 'pendding',
label: label
};
}
}, {
key: "isFieldNull",
value: function isFieldNull(value) {
return value === undefined || value === '' || value === null || Array.isArray(value) && value.length === 0;
}
}, {
key: "transformMultilevelData",
value: function transformMultilevelData(data) {
var keys = Object.keys(data);
var hasMultiLevel = keys.some(function (item) {
return item.includes('.');
});
if (hasMultiLevel) {
var res = {};
for (var i = 0; i < keys.length; i++) {
var key = keys[i];
if (key) {
if (!(key !== null && key !== void 0 && key.includes('.'))) {
res[key] = data[key];
} else {
var ks = key.split('.');
var p = res;
for (var j = 0; j < ks.length; j++) {
var k = ks[j];
if (p[k] && j !== ks.length - 1) {
p = p[k];
} else if (!p[k] && j !== ks.length - 1) {
var nextK = ks[j + 1];
if (!isNaN(Number(nextK)) && typeof Number(nextK) === 'number') {
p[k] = [];
} else if (typeof nextK === 'string') {
p[k] = {};
}
p = p[k];
} else {
p[k] = data[key];
}
}
}
}
}
return res;
} else {
return data;
}
}
}]);
return FormStore;
}();
var _default = FormStore;
exports.default = _default;