fastlion-amis
Version:
一种MIS页面生成工具
357 lines (356 loc) • 17.1 kB
JavaScript
/**
* @file 用来创建一个域,在这个域里面会把里面的运行时实例注册进来,方便组件之间的通信。
* @author fex
*/
Object.defineProperty(exports, "__esModule", { value: true });
exports.HocScoped = exports.ScopedContext = void 0;
var tslib_1 = require("tslib");
var react_1 = (0, tslib_1.__importDefault)(require("react"));
var find_1 = (0, tslib_1.__importDefault)(require("lodash/find"));
var hoist_non_react_statics_1 = (0, tslib_1.__importDefault)(require("hoist-non-react-statics"));
var tpl_builtin_1 = require("./utils/tpl-builtin");
var helper_1 = require("./utils/helper");
var tools_1 = require("./utils/shell/tools");
var lodash_1 = require("lodash");
exports.ScopedContext = react_1.default.createContext(createScopedTools(''));
var scopedComponents = [];
// window['getHaveChildrenComponents']
function createScopedTools(path, parent, env) {
var components = [];
var self = {
components: components,
parent: parent,
path: path,
children: [],
registerComponent: function (component) {
// 不要把自己注册在自己的 Scoped 上,自己的 Scoped 是给子节点们注册的。
if (component.props.$path === self.path && parent) {
return parent.registerComponent(component);
}
if (!~self.components.indexOf(component)) {
self.components.push(component);
if (component.props.type == 'crud' || component.props.type == 'form' || component.props.type == 'data-display') {
scopedComponents.push(component);
}
}
},
unRegisterComponent: function (component) {
// 自己本身实际上注册在父级 Scoped 上。
if (component.props.$path === self.path && parent) {
return parent.unRegisterComponent(component);
}
var idx = self.components.indexOf(component);
var tempIdx = scopedComponents.indexOf(component);
// console.log(component, idx, tempIdx)
if (idx > -1) {
self.components.splice(idx, 1);
}
if (tempIdx > -1) {
scopedComponents.splice(tempIdx, 1);
}
// 取消注册的时候 把自己缓存的components全部清除 防止缓存
self.children = [];
// 情况components
// console.log('取消注册', components, ~idx, ~tempIdx)
// while (components.length) {
// components.pop()
// }
// else {
// const instanceIdx = scopedComponents.findIndex(_component => _component.instacneId === component.instacneId)
// if (~instanceIdx) scopedComponents.splice(instanceIdx, 1)
// }
},
getComponentByName: function (name) {
if (~name.indexOf('.')) {
var paths = name.split('.');
var len_1 = paths.length;
return paths.reduce(function (scope, name, idx) {
if (scope && scope.getComponentByName) {
var result = scope.getComponentByName(name);
return result && idx < len_1 - 1 ? result.context : result;
}
return null;
}, this);
}
var resolved = (0, find_1.default)(self.components, function (component) {
return component.props.name === name || component.props.id === name;
});
return resolved || (parent && parent.getComponentByName(name));
},
getComponentFromArray: function (name) {
return (0, find_1.default)(scopedComponents, function (component) {
return component.props.name === name || component.props.id === name;
});
},
getComponentById: function (id) {
var root = this;
// 找到顶端scoped
while (root.parent) {
root = root.parent;
}
// 向下查找
var component = undefined;
(0, helper_1.findTree)([root], function (item) {
return item.getComponents().find(function (cmpt) {
if (cmpt.props.id === id) {
component = cmpt;
return true;
}
return false;
});
});
return component;
},
getComponents: function () {
return components.concat();
},
getAllChildrenComponets: function (root) {
var componentArr = [];
function getChildComponent(component) {
var components = (0, tslib_1.__spreadArray)([], component.context.components || [], true);
var selfComponentIdx = components.indexOf(component);
if (~selfComponentIdx) {
components.splice(selfComponentIdx, 1);
}
// 如果有子节点 先遍历子节点
componentArr.push(component);
if (components === null || components === void 0 ? void 0 : components.length) {
components.map(function (_) {
// 防止走重复的
if (componentArr.includes(_)) {
return;
}
getChildComponent(_);
});
}
}
getChildComponent(root);
return componentArr;
},
// 增加从触发的位置的context查找上下文的功能
findSubComponent: function (name, currentName, index, delegate) {
if (index === void 0) { index = -1; }
if (!currentName || !name)
return false;
var root = this;
if (root === null || root === void 0 ? void 0 : root.parent) {
root = root === null || root === void 0 ? void 0 : root.parent;
}
// 触发的currentComponets
var currentComponent = this.findTargetComponent(currentName, delegate);
if (currentComponent && (currentComponent === null || currentComponent === void 0 ? void 0 : currentComponent.context.parent)) {
var componentList_1 = [];
(0, helper_1.findTreeList)([currentComponent === null || currentComponent === void 0 ? void 0 : currentComponent.context.parent], function (item) {
return item.getComponents().find(function (cmpt) {
if (cmpt.props.name === name || cmpt.props.id === name) {
componentList_1.push(cmpt);
return true;
}
return false;
});
});
return componentList_1.length > 0 ? componentList_1 : false;
}
return false;
},
// 增加从触发的位置的context查找上下文的功能
findTargetComponent: function (name, delegate) {
var root = (delegate === null || delegate === void 0 ? void 0 : delegate.parent) || this;
// 向下查找
var component = undefined;
(0, helper_1.findTree)([root], function (item) {
return item.getComponents().find(function (cmpt) {
if (cmpt.props.name === name || cmpt.props.id === name) {
component = cmpt;
return true;
}
return false;
});
});
return component;
},
reload: function (target, ctx, currentName, isItemAction, delegate) {
var scoped = this;
var targets = typeof target === 'string' ? target.split(/\s*,\s*/) : target;
targets.forEach(function (name, index) {
var _a;
var idx2 = name.indexOf('?');
var query = null;
if (~idx2) {
var queryObj = (0, helper_1.qsparse)(name
.substring(idx2 + 1)
.replace(/\$\{(.*?)\}/, function (_, match) { return '${' + encodeURIComponent(match) + '}'; }));
query = (0, tpl_builtin_1.dataMapping)(queryObj, ctx);
name = name.substring(0, idx2);
}
var idx = name.indexOf('.');
var subPath = '';
if (~idx) {
subPath = name.substring(1 + idx);
name = name.substring(0, idx);
}
if (name === 'window') {
if (query) {
var link = location.pathname + '?' + (0, helper_1.qsstringify)(query);
env ? env.updateLocation(link, true) : location.replace(link);
}
else {
location.reload();
}
}
else {
var component = scoped.findSubComponent(name, currentName, index, delegate) || scoped.getComponentByName(name) || scoped.findTargetComponent(name, delegate) || scoped.getComponentFromArray(name);
if (tools_1.tools.isArray(component)) {
component.forEach(function (item) {
var _a;
(_a = item.reload) === null || _a === void 0 ? void 0 : _a.call(item, subPath, query, ctx, isItemAction);
});
}
else {
(_a = component === null || component === void 0 ? void 0 : component.reload) === null || _a === void 0 ? void 0 : _a.call(component, subPath, query, ctx, isItemAction);
}
}
});
},
send: function (receive, values, currentName, withTarget) {
var flag = false;
var scoped = this;
var receives = typeof receive === 'string' ? receive.split(/\s*,\s*/) : receive;
var withValues = undefined;
if (withTarget) {
var withComponent = scoped.findSubComponent(withTarget) || scoped.getComponentByName(withTarget) || scoped.findTargetComponent(withTarget) || scoped.getComponentFromArray(withTarget);
if (withComponent) {
withValues = withComponent.props.data;
}
}
var newValue = (0, lodash_1.cloneDeep)(values);
// todo 没找到做提示!
receives.forEach(function (name, index) {
var _a;
var askIdx = name.indexOf('?');
if (~askIdx) {
var query = name.substring(askIdx + 1);
var queryObj = (0, helper_1.qsparse)(query.replace(/\$\{(.*?)\}/, function (_, match) { return '${' + encodeURIComponent(match) + '}'; }));
name = name.substring(0, askIdx);
newValue = (0, tpl_builtin_1.dataMapping)(queryObj, values);
if (withValues) {
newValue = (0, tslib_1.__assign)((0, tslib_1.__assign)({}, newValue), withValues);
}
}
else {
if (withValues) {
newValue = (0, tslib_1.__assign)((0, tslib_1.__assign)({}, newValue), withValues);
}
}
var idx = name.indexOf('.');
var subPath = '';
if (~idx) {
subPath = name.substring(1 + idx);
name = name.substring(0, idx);
}
var component = scoped.findSubComponent(name, currentName, index) || scoped.getComponentByName(name) || scoped.findTargetComponent(name) || scoped.getComponentFromArray(name);
if (component) {
flag = true;
}
if (name === 'window' && env && env.updateLocation) {
var query = (0, tslib_1.__assign)((0, tslib_1.__assign)({}, (location.search ? (0, helper_1.qsparse)(location.search.substring(1)) : {})), values);
var link = location.pathname + '?' + (0, helper_1.qsstringify)(query);
env.updateLocation(link, true);
}
else {
if (tools_1.tools.isArray(component)) {
component.forEach(function (item) {
var _a;
(_a = item === null || item === void 0 ? void 0 : item.receive) === null || _a === void 0 ? void 0 : _a.call(item, newValue, subPath);
});
}
else {
(_a = component === null || component === void 0 ? void 0 : component.receive) === null || _a === void 0 ? void 0 : _a.call(component, newValue, subPath);
}
}
});
return flag;
},
/**
* 主要是用来关闭指定弹框的
*
* @param target 目标 name
*/
close: function (target) {
var scoped = this;
if (typeof target === 'string') {
// 过滤已经关掉的,当用户 close 配置多个弹框 name 时会出现这种情况
target
.split(/\s*,\s*/)
.map(function (name) { return scoped.getComponentByName(name); })
.filter(function (component) { return component && component.props.show; })
.forEach(closeDialog);
}
}
};
if (!parent) {
return self;
}
!parent.children && (parent.children = []);
// 把孩子带上
parent.children.push(self);
return self;
}
function closeDialog(component) {
component.context
.getComponents()
.filter(function (item) {
return item &&
(item.props.type === 'dialog' || item.props.type === 'drawer') &&
item.props.show;
})
.forEach(closeDialog);
component.props.onClose && component.props.onClose();
}
function HocScoped(ComposedComponent) {
var ScopedComponent = /** @class */ (function (_super) {
(0, tslib_1.__extends)(ScopedComponent, _super);
function ScopedComponent(props, context) {
var _this = _super.call(this, props) || this;
_this.scoped = createScopedTools(_this.props.$path, context, _this.props.env);
var scopeRef = props.scopeRef;
scopeRef && scopeRef(_this.scoped);
return _this;
}
ScopedComponent.prototype.getWrappedInstance = function () {
return this.ref;
};
ScopedComponent.prototype.childRef = function (ref) {
while (ref && ref.getWrappedInstance) {
ref = ref.getWrappedInstance();
}
this.ref = ref;
};
ScopedComponent.prototype.componentWillUnmount = function () {
var scopeRef = this.props.scopeRef;
scopeRef && scopeRef(null);
delete this.scoped;
};
ScopedComponent.prototype.render = function () {
var _a = this.props, scopeRef = _a.scopeRef, rest = (0, tslib_1.__rest)(_a, ["scopeRef"]);
return (react_1.default.createElement(exports.ScopedContext.Provider, { value: this.scoped },
react_1.default.createElement(ComposedComponent, (0, tslib_1.__assign)({}, rest /* todo */, { ref: this.childRef }))));
};
ScopedComponent.displayName = "Scoped(" + (ComposedComponent.displayName || ComposedComponent.name) + ")";
ScopedComponent.contextType = exports.ScopedContext;
ScopedComponent.ComposedComponent = ComposedComponent;
(0, tslib_1.__decorate)([
helper_1.autobind,
(0, tslib_1.__metadata)("design:type", Function),
(0, tslib_1.__metadata)("design:paramtypes", [Object]),
(0, tslib_1.__metadata)("design:returntype", void 0)
], ScopedComponent.prototype, "childRef", null);
return ScopedComponent;
}(react_1.default.Component));
(0, hoist_non_react_statics_1.default)(ScopedComponent, ComposedComponent);
return ScopedComponent;
}
exports.HocScoped = HocScoped;
exports.default = HocScoped;
//# sourceMappingURL=./Scoped.js.map
;