flow-graph-designer
Version:
A React component capable of flow graph designer.
359 lines (341 loc) • 11.2 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.getNewIdFunc = undefined;
exports.setLang = setLang;
exports.getLang = getLang;
exports.getNodeById = getNodeById;
exports.getParentNodeById = getParentNodeById;
exports.getPasteResultById = getPasteResultById;
exports.getcopyResultById = getcopyResultById;
exports.getNewFlowByAdd = getNewFlowByAdd;
exports.getColorByNode = getColorByNode;
exports.getAllId = getAllId;
exports.getNewFlowByDel = getNewFlowByDel;
exports.getNewFlowByMove = getNewFlowByMove;
exports.getNewFlowByPaste = getNewFlowByPaste;
exports.getNewFlowByCopy = getNewFlowByCopy;
exports.getNewNode = getNewNode;
var _immer = require("immer");
var _immer2 = _interopRequireDefault(_immer);
var _style = require("./style");
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
var lang = "en_US";
function setLang(lg) {
lang = lg;
}
function getLang() {
return lang;
}
function getNodeById(node, id) {
if (node.id === id) {
return node;
}
if (node.children) {
for (var i = 0; i < node.children.length; i += 1) {
var nodeRes = getNodeById(node.children[i], id);
if (nodeRes) {
return nodeRes;
}
}
}
return null;
}
function getParentNodeById(node, id) {
if (!node.children) {
return null;
}
if (node.children.find(function (x) {
return x.id === id;
})) {
return node;
}
for (var i = 0; i < node.children.length; i += 1) {
var nodeRes = getParentNodeById(node.children[i], id);
if (nodeRes) {
return nodeRes;
}
}
return null;
}
function getPasteResultById(config, node, newIdFunc) {
var copyResult = { node: {}, copyDetail: [] };
var copydNode = node; // 拷贝节点
var newIds = []; // 存储新创建的ID
// 处理克隆后的节点,重新设置节点的ID
var processcopydNode = function processcopydNode(node) {
var prevId = node.id;
var nextId = newIdFunc(newIds); // 传递新创建的ID,避免重复
newIds.push(nextId);
node.id = nextId;
copyResult.copyDetail.push({ from: prevId, to: nextId });
if (node.children) {
for (var i = 0; i < node.children.length; i += 1) {
processcopydNode(node.children[i]);
}
}
};
processcopydNode(copydNode);
copyResult.node = copydNode;
return copyResult;
}
function getcopyResultById(config, id, newIdFunc) {
var copyResult = { node: {}, copyDetail: [] };
var sourceNode = getNodeById(config, id); // 源节点
var str = JSON.stringify(sourceNode);
var copydNode = JSON.parse(str); // 拷贝节点
var newIds = []; // 存储新创建的ID
// 处理克隆后的节点,重新设置节点的ID
var processcopydNode = function processcopydNode(node) {
var prevId = node.id;
var nextId = newIdFunc(newIds); // 传递新创建的ID,避免重复
newIds.push(nextId);
node.id = nextId;
copyResult.copyDetail.push({ from: prevId, to: nextId });
if (node.children) {
for (var i = 0; i < node.children.length; i += 1) {
processcopydNode(node.children[i]);
}
}
};
processcopydNode(copydNode);
copyResult.node = copydNode;
return copyResult;
}
/**
* 返回添加节点后的新流程对象,以及被添加的节点id数组
* @param {*} param0
*/
function getNewFlowByAdd(_ref) {
var config = _ref.config,
node = _ref.node,
containerId = _ref.containerId,
containerIndex = _ref.containerIndex;
var flow = (0, _immer2.default)(config, function (draft) {
var containerNode = getNodeById(draft, containerId);
// 【判断节点】不接受从图标栏拖拽其他节点
if (containerNode.type === "switch") {
return;
}
if (!containerNode.children) {
containerNode.children = [];
}
containerNode.children.splice(containerIndex, 0, node);
});
var nodes = getAllId(node);
return { flow: flow, nodes: nodes };
}
// 返回节点的颜色
function getColorByNode(node, template) {
var color = _style.defaultColor;
if (node.color) {
color = node.color;
} else {
var templateNodeId = template.nodes.find(function (x) {
return template.entities.node[x].props.action === node.action;
});
if (templateNodeId) {
color = template.entities.node[templateNodeId].color || _style.defaultColor;
}
}
return (_style.colors.find(function (x) {
return x.name === color;
}) || _style.colors.find(function (x) {
return x.name === _style.defaultColor;
})).value;
}
// 返回包含节点及其子节点的所有ID的数组
function getAllId(node) {
var ids = [];
var pushId = function pushId(n) {
ids.push(n.id);
if (n.children && n.children.length) {
for (var i = 0; i < n.children.length; i += 1) {
pushId(n.children[i]);
}
}
};
pushId(node);
return ids;
}
/**
* 返回删除节点后的新流程对象,以及被删除的节点id数组
* @param {*} param0
*/
function getNewFlowByDel(_ref2) {
var config = _ref2.config,
sourceId = _ref2.sourceId;
var nodes = [];
var flow = (0, _immer2.default)(config, function (draft) {
var sourceParentNode = getParentNodeById(draft, sourceId);
var sourceIndex = sourceParentNode.children.findIndex(function (x) {
return x.id === sourceId;
});
var sourceNode = sourceParentNode.children[sourceIndex];
if (sourceNode.children && sourceNode.children.length) {
var shouldDeleteNodeIds = getAllId(sourceNode);
for (var i = 0; i < shouldDeleteNodeIds.length; i += 1) {
nodes.push(shouldDeleteNodeIds[i]);
}
}
// 删除移动的节点
sourceParentNode.children.splice(sourceIndex, 1);
// 如果拖拽的节点是条件分支并且是唯一分支,删除整个判断流程
if (sourceNode.type === "case" && !sourceParentNode.children.length) {
var switchParentNode = getParentNodeById(draft, sourceParentNode.id);
var switchIndex = switchParentNode.children.findIndex(function (x) {
return x.id === sourceParentNode.id;
});
switchParentNode.children.splice(switchIndex, 1);
nodes.push(sourceParentNode.id);
}
return;
});
return { flow: flow, nodes: nodes };
}
function getNewFlowByMove(_ref3) {
var config = _ref3.config,
sourceId = _ref3.sourceId,
containerId = _ref3.containerId,
containerIndex = _ref3.containerIndex;
var nodes = [];
var flow = (0, _immer2.default)(config, function (draft) {
var sourceParentNode = getParentNodeById(draft, sourceId);
var sourceIndex = sourceParentNode.children.findIndex(function (x) {
return x.id === sourceId;
});
var sourceNode = sourceParentNode.children[sourceIndex];
nodes = getAllId(sourceNode);
var containerNode = getNodeById(draft, containerId);
// 【条件分支节点】只能移动或复制到【判断节点】
if (sourceNode.type === "case" && containerNode.type !== "switch") {
return;
}
// 其他节点不能移动或复制到【判断节点】
if (sourceNode.type !== "case" && containerNode.type === "switch") {
return;
}
// 如果只是在同一个容器中移动前后的顺序
// 根据目标位置和当前位置的关系,计算节点被删除后再次插入的位置
var newIndex = containerId === sourceParentNode.id && containerIndex > sourceIndex ? containerIndex - 1 : containerIndex;
sourceParentNode.children.splice(sourceIndex, 1);
containerNode.children.splice(newIndex, 0, sourceNode);
if (sourceNode.type === "case" && !sourceParentNode.children.length) {
// 如果移动的是 switch 节点的唯一 case 节点,要删除 switch 节点
var node = getParentNodeById(draft, sourceParentNode.id);
var idnex = node.children.findIndex(function (x) {
return x.id === sourceParentNode.id;
});
node.children.splice(idnex, 1);
}
});
return { flow: flow, nodes: nodes };
}
/**
* 返回节点粘贴后的新的流程对象,以及操作信息
* @param {*} param0
*/
function getNewFlowByPaste(_ref4) {
var config = _ref4.config,
sourceNode = _ref4.sourceNode,
containerId = _ref4.containerId,
containerIndex = _ref4.containerIndex;
var copyDetail = [];
var data = (0, _immer2.default)(config, function (draft) {
var containerNode = getNodeById(draft, containerId);
var copyResult = getPasteResultById(config, sourceNode, getNewIdFunc(config));
copyDetail = copyResult.copyDetail;
containerNode.children.splice(containerIndex, 0, copyResult.node);
});
return {
data: data,
copyDetail: copyDetail
};
}
/**
* 返回节点拷贝后的新的流程对象,以及操作信息
* @param {*} param0
*/
function getNewFlowByCopy(_ref5) {
var config = _ref5.config,
sourceId = _ref5.sourceId,
containerId = _ref5.containerId,
containerIndex = _ref5.containerIndex;
var copyDetail = [];
var data = (0, _immer2.default)(config, function (draft) {
var sourceParentNode = getParentNodeById(draft, sourceId);
var sourceIndex = sourceParentNode.children.findIndex(function (x) {
return x.id === sourceId;
});
var sourceNode = sourceParentNode.children[sourceIndex];
var containerNode = getNodeById(draft, containerId);
// 【条件分支节点】只能移动或复制到【判断节点】
if (sourceNode.type === "case" && containerNode.type !== "switch") {
return;
}
// 其他节点不能移动或复制到【判断节点】
if (sourceNode.type !== "case" && containerNode.type === "switch") {
return;
}
var copyResult = getcopyResultById(config, sourceId, getNewIdFunc(config));
copyDetail = copyResult.copyDetail;
containerNode.children.splice(containerIndex, 0, copyResult.node);
});
return {
data: data,
copyDetail: copyDetail
};
}
function getNewNode(type, action, name, newIdFunc) {
var newIds = [];
var id = newIdFunc(newIds);
newIds.push(id);
var newNode = {
id: id
};
newNode.name = name;
newNode.type = type;
newNode.action = action;
if (type === "loop") {
newNode.type = "loop";
newNode.children = [];
} else if (type === "switch") {
newNode.type = "switch";
var caseId1 = newIdFunc(newIds);
newIds.push(caseId1);
var caseId2 = newIdFunc(newIds);
newIds.push(caseId2);
newNode.children = [{
id: caseId1,
type: "case",
action: "case",
name: "\u6761\u4EF6\u5206\u652F" + caseId1,
children: []
}, {
id: caseId2,
type: "case",
action: "case",
name: "\u6761\u4EF6\u5206\u652F" + caseId2,
children: []
}];
}
return newNode;
}
/**
* 获取新的节点ID并保证唯一
* @param {*} flow
*/
var getNewIdFunc = exports.getNewIdFunc = function getNewIdFunc(flow) {
var prefix = arguments.length > 1 && arguments[1] !== undefined ? arguments[1] : "";
return function (ids) {
var prevIds = getAllId(flow);
var id = void 0;
var index = 0;
do {
index += 1;
id = "" + prefix + index;
} while (prevIds.includes(id) || ids.includes(id));
return id;
};
};