mirror of
https://github.com/mermaid-js/mermaid.git
synced 2025-01-28 07:03:17 +08:00
#1295 Render fix for flowchart, correct marker handling and some cleanup
This commit is contained in:
parent
704d56d193
commit
c3f2e8dde1
@ -7,7 +7,7 @@
|
|||||||
<link href="https://fonts.googleapis.com/css?family=Noto+Sans+SC&display=swap" rel="stylesheet">
|
<link href="https://fonts.googleapis.com/css?family=Noto+Sans+SC&display=swap" rel="stylesheet">
|
||||||
<style>
|
<style>
|
||||||
body {
|
body {
|
||||||
background: white;
|
background: rgb(221, 208, 208);
|
||||||
font-family: 'Arial';
|
font-family: 'Arial';
|
||||||
}
|
}
|
||||||
h1 { color: white;}
|
h1 { color: white;}
|
||||||
@ -98,9 +98,20 @@ flowchart TD
|
|||||||
d
|
d
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
A -- oAo --> B
|
A -- oAo --o B
|
||||||
A --> C
|
A --> C
|
||||||
</div>
|
</div>
|
||||||
|
<div class="mermaid" style="width: 100%; height: 100%;">
|
||||||
|
flowchart TD
|
||||||
|
subgraph A
|
||||||
|
a
|
||||||
|
end
|
||||||
|
subgraph B
|
||||||
|
b
|
||||||
|
end
|
||||||
|
c-->A
|
||||||
|
c-->B
|
||||||
|
</div>
|
||||||
<div class="mermaid2" style="width: 100%; height: 100%;">
|
<div class="mermaid2" style="width: 100%; height: 100%;">
|
||||||
stateDiagram-v2
|
stateDiagram-v2
|
||||||
[*] --> First
|
[*] --> First
|
||||||
|
@ -3,7 +3,7 @@ import { logger as log } from '../logger'; // eslint-disable-line
|
|||||||
import createLabel from './createLabel';
|
import createLabel from './createLabel';
|
||||||
|
|
||||||
const rect = (parent, node) => {
|
const rect = (parent, node) => {
|
||||||
log.info('Creating subgraph rect for ', node.id, node);
|
log.trace('Creating subgraph rect for ', node.id, node);
|
||||||
|
|
||||||
// Add outer g element
|
// Add outer g element
|
||||||
const shapeSvg = parent
|
const shapeSvg = parent
|
||||||
@ -25,7 +25,7 @@ const rect = (parent, node) => {
|
|||||||
const padding = 0 * node.padding;
|
const padding = 0 * node.padding;
|
||||||
const halfPadding = padding / 2;
|
const halfPadding = padding / 2;
|
||||||
|
|
||||||
log.info('Data ', node, JSON.stringify(node));
|
log.trace('Data ', node, JSON.stringify(node));
|
||||||
// center the rect around its coordinate
|
// center the rect around its coordinate
|
||||||
rect
|
rect
|
||||||
.attr('rx', node.rx)
|
.attr('rx', node.rx)
|
||||||
@ -35,9 +35,7 @@ const rect = (parent, node) => {
|
|||||||
.attr('width', node.width + padding)
|
.attr('width', node.width + padding)
|
||||||
.attr('height', node.height + padding);
|
.attr('height', node.height + padding);
|
||||||
|
|
||||||
// log.info('bbox', bbox.width, node.x, node.width);
|
|
||||||
// Center the label
|
// Center the label
|
||||||
// label.attr('transform', 'translate(' + adj + ', ' + (node.y - node.height / 2) + ')');
|
|
||||||
label.attr(
|
label.attr(
|
||||||
'transform',
|
'transform',
|
||||||
'translate(' +
|
'translate(' +
|
||||||
@ -130,9 +128,7 @@ const roundedWithTitle = (parent, node) => {
|
|||||||
.attr('width', node.width + padding)
|
.attr('width', node.width + padding)
|
||||||
.attr('height', node.height + padding - bbox.height - 3);
|
.attr('height', node.height + padding - bbox.height - 3);
|
||||||
|
|
||||||
// log.info('bbox', bbox.width, node.x, node.width);
|
|
||||||
// Center the label
|
// Center the label
|
||||||
// label.attr('transform', 'translate(' + adj + ', ' + (node.y - node.height / 2) + ')');
|
|
||||||
label.attr(
|
label.attr(
|
||||||
'transform',
|
'transform',
|
||||||
'translate(' +
|
'translate(' +
|
||||||
@ -158,7 +154,7 @@ const shapes = { rect, roundedWithTitle, noteGroup };
|
|||||||
let clusterElems = {};
|
let clusterElems = {};
|
||||||
|
|
||||||
export const insertCluster = (elem, node) => {
|
export const insertCluster = (elem, node) => {
|
||||||
log.info('Inserting cluster');
|
log.trace('Inserting cluster');
|
||||||
const shape = node.shape || 'rect';
|
const shape = node.shape || 'rect';
|
||||||
clusterElems[node.id] = shapes[shape](elem, node);
|
clusterElems[node.id] = shapes[shape](elem, node);
|
||||||
};
|
};
|
||||||
|
@ -64,7 +64,7 @@ const outsideNode = (node, point) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
const intersection = (node, outsidePoint, insidePoint) => {
|
const intersection = (node, outsidePoint, insidePoint) => {
|
||||||
logger.info('intersection o:', outsidePoint, ' i:', insidePoint, node);
|
logger.trace('intersection o:', outsidePoint, ' i:', insidePoint, node);
|
||||||
const x = node.x;
|
const x = node.x;
|
||||||
const y = node.y;
|
const y = node.y;
|
||||||
|
|
||||||
@ -98,11 +98,10 @@ const intersection = (node, outsidePoint, insidePoint) => {
|
|||||||
};
|
};
|
||||||
|
|
||||||
export const insertEdge = function(elem, edge, clusterDb, diagramType) {
|
export const insertEdge = function(elem, edge, clusterDb, diagramType) {
|
||||||
logger.info('\n\n\n\n');
|
|
||||||
let points = edge.points;
|
let points = edge.points;
|
||||||
if (edge.toCluster) {
|
if (edge.toCluster) {
|
||||||
logger.info('edge', edge);
|
logger.trace('edge', edge);
|
||||||
logger.info('to cluster', clusterDb[edge.toCluster]);
|
logger.trace('to cluster', clusterDb[edge.toCluster]);
|
||||||
points = [];
|
points = [];
|
||||||
let lastPointOutside;
|
let lastPointOutside;
|
||||||
let isInside = false;
|
let isInside = false;
|
||||||
@ -110,11 +109,11 @@ export const insertEdge = function(elem, edge, clusterDb, diagramType) {
|
|||||||
const node = clusterDb[edge.toCluster].node;
|
const node = clusterDb[edge.toCluster].node;
|
||||||
|
|
||||||
if (!outsideNode(node, point) && !isInside) {
|
if (!outsideNode(node, point) && !isInside) {
|
||||||
logger.info('inside', edge.toCluster, point, lastPointOutside);
|
logger.trace('inside', edge.toCluster, point, lastPointOutside);
|
||||||
|
|
||||||
// First point inside the rect
|
// First point inside the rect
|
||||||
const insterection = intersection(node, lastPointOutside, point);
|
const insterection = intersection(node, lastPointOutside, point);
|
||||||
logger.info('intersect', insterection);
|
logger.trace('intersect', insterection);
|
||||||
points.push(insterection);
|
points.push(insterection);
|
||||||
isInside = true;
|
isInside = true;
|
||||||
} else {
|
} else {
|
||||||
@ -125,8 +124,8 @@ export const insertEdge = function(elem, edge, clusterDb, diagramType) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (edge.fromCluster) {
|
if (edge.fromCluster) {
|
||||||
logger.info('edge', edge);
|
logger.trace('edge', edge);
|
||||||
logger.info('from cluster', clusterDb[edge.toCluster]);
|
logger.trace('from cluster', clusterDb[edge.toCluster]);
|
||||||
const updatedPoints = [];
|
const updatedPoints = [];
|
||||||
let lastPointOutside;
|
let lastPointOutside;
|
||||||
let isInside = false;
|
let isInside = false;
|
||||||
@ -135,17 +134,17 @@ export const insertEdge = function(elem, edge, clusterDb, diagramType) {
|
|||||||
const node = clusterDb[edge.fromCluster].node;
|
const node = clusterDb[edge.fromCluster].node;
|
||||||
|
|
||||||
if (!outsideNode(node, point) && !isInside) {
|
if (!outsideNode(node, point) && !isInside) {
|
||||||
logger.info('inside', edge.toCluster, point);
|
logger.trace('inside', edge.toCluster, point);
|
||||||
|
|
||||||
// First point inside the rect
|
// First point inside the rect
|
||||||
const insterection = intersection(node, lastPointOutside, point);
|
const insterection = intersection(node, lastPointOutside, point);
|
||||||
// logger.info('intersect', intersection(node, lastPointOutside, point));
|
// logger.trace('intersect', intersection(node, lastPointOutside, point));
|
||||||
updatedPoints.unshift(insterection);
|
updatedPoints.unshift(insterection);
|
||||||
// points.push(insterection);
|
// points.push(insterection);
|
||||||
isInside = true;
|
isInside = true;
|
||||||
} else {
|
} else {
|
||||||
// at the outside
|
// at the outside
|
||||||
logger.info('Outside point', point);
|
logger.trace('Outside point', point);
|
||||||
if (!isInside) updatedPoints.unshift(point);
|
if (!isInside) updatedPoints.unshift(point);
|
||||||
}
|
}
|
||||||
lastPointOutside = point;
|
lastPointOutside = point;
|
||||||
@ -195,7 +194,7 @@ export const insertEdge = function(elem, edge, clusterDb, diagramType) {
|
|||||||
url = url.replace(/\(/g, '\\(');
|
url = url.replace(/\(/g, '\\(');
|
||||||
url = url.replace(/\)/g, '\\)');
|
url = url.replace(/\)/g, '\\)');
|
||||||
}
|
}
|
||||||
// logger.info('arrowType', edge.arrowType);
|
logger.info('arrowType', edge.arrowType);
|
||||||
switch (edge.arrowType) {
|
switch (edge.arrowType) {
|
||||||
case 'arrow_cross':
|
case 'arrow_cross':
|
||||||
svgPath.attr('marker-end', 'url(' + url + '#' + diagramType + '-crossEnd' + ')');
|
svgPath.attr('marker-end', 'url(' + url + '#' + diagramType + '-crossEnd' + ')');
|
||||||
|
@ -9,30 +9,20 @@ import {
|
|||||||
findNonClusterChild
|
findNonClusterChild
|
||||||
} from './mermaid-graphlib';
|
} from './mermaid-graphlib';
|
||||||
import { insertNode, positionNode, clear as clearNodes, setNodeElem } from './nodes';
|
import { insertNode, positionNode, clear as clearNodes, setNodeElem } from './nodes';
|
||||||
import { insertCluster, clear as clearClusters } from './clusters';
|
import { insertCluster, clear as clearClusters, positionCluster } from './clusters';
|
||||||
import { insertEdgeLabel, positionEdgeLabel, insertEdge, clear as clearEdges } from './edges';
|
import { insertEdgeLabel, positionEdgeLabel, insertEdge, clear as clearEdges } from './edges';
|
||||||
import { logger as log } from '../logger';
|
import { logger as log } from '../logger';
|
||||||
|
|
||||||
// let clusterDb = {};
|
const recursiveRender = (_elem, graph, diagramtype, parentCluster) => {
|
||||||
|
log.trace('Graph in recursive render:', graphlib.json.write(graph), parentCluster);
|
||||||
const getAnchorId = id => {
|
|
||||||
// Only insert an achor once
|
|
||||||
if (clusterDb[id]) {
|
|
||||||
return clusterDb[id].id;
|
|
||||||
}
|
|
||||||
return id;
|
|
||||||
};
|
|
||||||
|
|
||||||
const recursiveRender = (_elem, graph, diagramtype) => {
|
|
||||||
log.info('Graph in recursive render:', graphlib.json.write(graph));
|
|
||||||
const elem = _elem.insert('g').attr('class', 'root'); // eslint-disable-line
|
const elem = _elem.insert('g').attr('class', 'root'); // eslint-disable-line
|
||||||
if (!graph.nodes()) {
|
if (!graph.nodes()) {
|
||||||
log.info('No nodes found for', graph);
|
log.trace('No nodes found for', graph);
|
||||||
} else {
|
} else {
|
||||||
log.info('Recursive render', graph.nodes());
|
log.trace('Recursive render', graph.nodes());
|
||||||
}
|
}
|
||||||
if (graph.edges().length > 0) {
|
if (graph.edges().length > 0) {
|
||||||
log.info('Recursive edges', graph.edge(graph.edges()[0]));
|
log.trace('Recursive edges', graph.edge(graph.edges()[0]));
|
||||||
}
|
}
|
||||||
const clusters = elem.insert('g').attr('class', 'clusters'); // eslint-disable-line
|
const clusters = elem.insert('g').attr('class', 'clusters'); // eslint-disable-line
|
||||||
const edgePaths = elem.insert('g').attr('class', 'edgePaths');
|
const edgePaths = elem.insert('g').attr('class', 'edgePaths');
|
||||||
@ -43,11 +33,18 @@ const recursiveRender = (_elem, graph, diagramtype) => {
|
|||||||
// to the abstract node and is later used by dagre for the layout
|
// to the abstract node and is later used by dagre for the layout
|
||||||
graph.nodes().forEach(function(v) {
|
graph.nodes().forEach(function(v) {
|
||||||
const node = graph.node(v);
|
const node = graph.node(v);
|
||||||
log.info('(Insert) Node ' + v + ': ' + JSON.stringify(graph.node(v)));
|
if (typeof parentCluster !== 'undefined') {
|
||||||
|
const data = JSON.parse(JSON.stringify(parentCluster.clusterData));
|
||||||
|
// data.clusterPositioning = true;
|
||||||
|
log.trace('Setting data for cluster', data);
|
||||||
|
graph.setNode(parentCluster.id, data);
|
||||||
|
graph.setParent(v, parentCluster.id, data);
|
||||||
|
}
|
||||||
|
log.trace('(Insert) Node ' + v + ': ' + JSON.stringify(graph.node(v)));
|
||||||
if (node.clusterNode) {
|
if (node.clusterNode) {
|
||||||
// const children = graph.children(v);
|
// const children = graph.children(v);
|
||||||
log.info('Cluster identified', v, node, graph.node(v));
|
log.trace('Cluster identified', v, node, graph.node(v));
|
||||||
const newEl = recursiveRender(clusters, node.graph, diagramtype);
|
const newEl = recursiveRender(nodes, node.graph, diagramtype, graph.node(v));
|
||||||
updateNodeBounds(node, newEl);
|
updateNodeBounds(node, newEl);
|
||||||
setNodeElem(newEl, node);
|
setNodeElem(newEl, node);
|
||||||
|
|
||||||
@ -56,12 +53,12 @@ const recursiveRender = (_elem, graph, diagramtype) => {
|
|||||||
if (graph.children(v).length > 0) {
|
if (graph.children(v).length > 0) {
|
||||||
// This is a cluster but not to be rendered recusively
|
// This is a cluster but not to be rendered recusively
|
||||||
// Render as before
|
// Render as before
|
||||||
log.info('Cluster - the non recursive path', v, node.id, node, graph);
|
log.trace('Cluster - the non recursive path', v, node.id, node, graph);
|
||||||
log.info(findNonClusterChild(node.id, graph));
|
log.trace(findNonClusterChild(node.id, graph));
|
||||||
clusterDb[node.id] = { id: findNonClusterChild(node.id, graph), node };
|
clusterDb[node.id] = { id: findNonClusterChild(node.id, graph), node };
|
||||||
// insertCluster(clusters, graph.node(v));
|
// insertCluster(clusters, graph.node(v));
|
||||||
} else {
|
} else {
|
||||||
log.info('Node - the non recursive path', v, node.id, node);
|
log.trace('Node - the non recursive path', v, node.id, node);
|
||||||
insertNode(nodes, graph.node(v));
|
insertNode(nodes, graph.node(v));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -74,22 +71,22 @@ const recursiveRender = (_elem, graph, diagramtype) => {
|
|||||||
graph.edges().forEach(function(e) {
|
graph.edges().forEach(function(e) {
|
||||||
const edge = graph.edge(e.v, e.w, e.name);
|
const edge = graph.edge(e.v, e.w, e.name);
|
||||||
log.trace('Edge ' + e.v + ' -> ' + e.w + ': ' + JSON.stringify(e));
|
log.trace('Edge ' + e.v + ' -> ' + e.w + ': ' + JSON.stringify(e));
|
||||||
log.info('Edge ' + e.v + ' -> ' + e.w + ': ', e, ' ', JSON.stringify(graph.edge(e)));
|
log.trace('Edge ' + e.v + ' -> ' + e.w + ': ', e, ' ', JSON.stringify(graph.edge(e)));
|
||||||
|
|
||||||
let v = e.v;
|
let v = e.v;
|
||||||
let w = e.w;
|
let w = e.w;
|
||||||
// Check if link is either from or to a cluster
|
// Check if link is either from or to a cluster
|
||||||
log.info('Fix', clusterDb, 'ids:', e.v, e.w, 'Translateing: ', clusterDb[e.v], clusterDb[e.w]);
|
log.trace('Fix', clusterDb, 'ids:', e.v, e.w, 'Translateing: ', clusterDb[e.v], clusterDb[e.w]);
|
||||||
// Todo handle case with links
|
// Todo handle case with links
|
||||||
|
|
||||||
// if (clusterDb[e.v] || clusterDb[e.w]) {
|
// if (clusterDb[e.v] || clusterDb[e.w]) {
|
||||||
// log.info('Fixing and trixing - removing', e.v, e.w, e.name);
|
// log.trace('Fixing and trixing - removing', e.v, e.w, e.name);
|
||||||
// v = getAnchorId(e.v, graph, nodes);
|
// v = getAnchorId(e.v, graph, nodes);
|
||||||
// w = getAnchorId(e.w, graph, nodes);
|
// w = getAnchorId(e.w, graph, nodes);
|
||||||
// graph.removeEdge(e.v, e.w, e.name);
|
// graph.removeEdge(e.v, e.w, e.name);
|
||||||
// if (v !== e.v) edge.fromCluster = e.v;
|
// if (v !== e.v) edge.fromCluster = e.v;
|
||||||
// if (w !== e.w) edge.toCluster = e.w;
|
// if (w !== e.w) edge.toCluster = e.w;
|
||||||
// log.info('Fixing Replacing with', v, w, e.name);
|
// log.trace('Fixing Replacing with', v, w, e.name);
|
||||||
// graph.setEdge(v, w, edge, e.name);
|
// graph.setEdge(v, w, edge, e.name);
|
||||||
// }
|
// }
|
||||||
insertEdgeLabel(edgeLabels, edge);
|
insertEdgeLabel(edgeLabels, edge);
|
||||||
@ -98,17 +95,17 @@ const recursiveRender = (_elem, graph, diagramtype) => {
|
|||||||
graph.edges().forEach(function(e) {
|
graph.edges().forEach(function(e) {
|
||||||
log.trace('Edge ' + e.v + ' -> ' + e.w + ': ' + JSON.stringify(e));
|
log.trace('Edge ' + e.v + ' -> ' + e.w + ': ' + JSON.stringify(e));
|
||||||
});
|
});
|
||||||
log.info('#############################################');
|
log.trace('#############################################');
|
||||||
log.info('### Layout ###');
|
log.trace('### Layout ###');
|
||||||
log.info('#############################################');
|
log.trace('#############################################');
|
||||||
log.info(graph);
|
log.trace(graph);
|
||||||
dagre.layout(graph);
|
dagre.layout(graph);
|
||||||
log.warn('Graph after layout:', graphlib.json.write(graph));
|
log.warn('Graph after layout:', graphlib.json.write(graph));
|
||||||
// Move the nodes to the correct place
|
// Move the nodes to the correct place
|
||||||
graph.nodes().forEach(function(v) {
|
graph.nodes().forEach(function(v) {
|
||||||
const node = graph.node(v);
|
const node = graph.node(v);
|
||||||
// log.info('Position ' + v + ': ' + JSON.stringify(graph.node(v)));
|
// log.trace('Position ' + v + ': ' + JSON.stringify(graph.node(v)));
|
||||||
log.info(
|
log.trace(
|
||||||
'Position ' + v + ': (' + node.x,
|
'Position ' + v + ': (' + node.x,
|
||||||
',' + node.y,
|
',' + node.y,
|
||||||
') width: ',
|
') width: ',
|
||||||
@ -118,6 +115,7 @@ const recursiveRender = (_elem, graph, diagramtype) => {
|
|||||||
);
|
);
|
||||||
if (node && node.clusterNode) {
|
if (node && node.clusterNode) {
|
||||||
// clusterDb[node.id].node = node;
|
// clusterDb[node.id].node = node;
|
||||||
|
|
||||||
positionNode(node);
|
positionNode(node);
|
||||||
} else {
|
} else {
|
||||||
// Non cluster node
|
// Non cluster node
|
||||||
@ -135,7 +133,7 @@ const recursiveRender = (_elem, graph, diagramtype) => {
|
|||||||
// Move the edge labels to the correct place after layout
|
// Move the edge labels to the correct place after layout
|
||||||
graph.edges().forEach(function(e) {
|
graph.edges().forEach(function(e) {
|
||||||
const edge = graph.edge(e);
|
const edge = graph.edge(e);
|
||||||
log.info('Edge ' + e.v + ' -> ' + e.w + ': ' + JSON.stringify(edge), edge);
|
log.trace('Edge ' + e.v + ' -> ' + e.w + ': ' + JSON.stringify(edge), edge);
|
||||||
|
|
||||||
insertEdge(edgePaths, edge, clusterDb, diagramtype);
|
insertEdge(edgePaths, edge, clusterDb, diagramtype);
|
||||||
positionEdgeLabel(edge);
|
positionEdgeLabel(edge);
|
||||||
|
@ -16,7 +16,7 @@ const extension = (elem, type, id) => {
|
|||||||
elem
|
elem
|
||||||
.append('defs')
|
.append('defs')
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'extensionStart')
|
.attr('id', type + '-extensionStart')
|
||||||
.attr('class', 'extension ' + type)
|
.attr('class', 'extension ' + type)
|
||||||
.attr('refX', 0)
|
.attr('refX', 0)
|
||||||
.attr('refY', 7)
|
.attr('refY', 7)
|
||||||
@ -29,7 +29,7 @@ const extension = (elem, type, id) => {
|
|||||||
elem
|
elem
|
||||||
.append('defs')
|
.append('defs')
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'extensionEnd ' + type)
|
.attr('id', type + '-extensionEnd ' + type)
|
||||||
.attr('class', 'extension ' + type)
|
.attr('class', 'extension ' + type)
|
||||||
.attr('refX', 19)
|
.attr('refX', 19)
|
||||||
.attr('refY', 7)
|
.attr('refY', 7)
|
||||||
@ -44,7 +44,7 @@ const composition = (elem, type) => {
|
|||||||
elem
|
elem
|
||||||
.append('defs')
|
.append('defs')
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'compositionStart')
|
.attr('id', type + '-compositionStart')
|
||||||
.attr('class', 'extension ' + type)
|
.attr('class', 'extension ' + type)
|
||||||
.attr('refX', 0)
|
.attr('refX', 0)
|
||||||
.attr('refY', 7)
|
.attr('refY', 7)
|
||||||
@ -57,7 +57,7 @@ const composition = (elem, type) => {
|
|||||||
elem
|
elem
|
||||||
.append('defs')
|
.append('defs')
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'compositionEnd')
|
.attr('id', type + '-compositionEnd')
|
||||||
.attr('class', 'extension ' + type)
|
.attr('class', 'extension ' + type)
|
||||||
.attr('refX', 19)
|
.attr('refX', 19)
|
||||||
.attr('refY', 7)
|
.attr('refY', 7)
|
||||||
@ -71,7 +71,7 @@ const aggregation = (elem, type) => {
|
|||||||
elem
|
elem
|
||||||
.append('defs')
|
.append('defs')
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'aggregationStart')
|
.attr('id', type + '-aggregationStart')
|
||||||
.attr('class', 'extension ' + type)
|
.attr('class', 'extension ' + type)
|
||||||
.attr('refX', 0)
|
.attr('refX', 0)
|
||||||
.attr('refY', 7)
|
.attr('refY', 7)
|
||||||
@ -84,7 +84,7 @@ const aggregation = (elem, type) => {
|
|||||||
elem
|
elem
|
||||||
.append('defs')
|
.append('defs')
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'aggregationEnd')
|
.attr('id', type + '-aggregationEnd')
|
||||||
.attr('class', type)
|
.attr('class', type)
|
||||||
.attr('refX', 19)
|
.attr('refX', 19)
|
||||||
.attr('refY', 7)
|
.attr('refY', 7)
|
||||||
@ -98,7 +98,7 @@ const dependency = (elem, type) => {
|
|||||||
elem
|
elem
|
||||||
.append('defs')
|
.append('defs')
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'dependencyStart')
|
.attr('id', type + '-dependencyStart')
|
||||||
.attr('class', 'extension ' + type)
|
.attr('class', 'extension ' + type)
|
||||||
.attr('refX', 0)
|
.attr('refX', 0)
|
||||||
.attr('refY', 7)
|
.attr('refY', 7)
|
||||||
@ -111,7 +111,7 @@ const dependency = (elem, type) => {
|
|||||||
elem
|
elem
|
||||||
.append('defs')
|
.append('defs')
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'dependencyEnd')
|
.attr('id', type + '-dependencyEnd')
|
||||||
.attr('class', type)
|
.attr('class', type)
|
||||||
.attr('refX', 19)
|
.attr('refX', 19)
|
||||||
.attr('refY', 7)
|
.attr('refY', 7)
|
||||||
@ -158,7 +158,7 @@ const point = (elem, type) => {
|
|||||||
const circle = (elem, type) => {
|
const circle = (elem, type) => {
|
||||||
elem
|
elem
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'circleEnd')
|
.attr('id', type + '-circleEnd')
|
||||||
.attr('class', type)
|
.attr('class', type)
|
||||||
.attr('viewBox', '0 0 10 10')
|
.attr('viewBox', '0 0 10 10')
|
||||||
.attr('refX', 11)
|
.attr('refX', 11)
|
||||||
@ -177,7 +177,7 @@ const circle = (elem, type) => {
|
|||||||
|
|
||||||
elem
|
elem
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'circleStart')
|
.attr('id', type + '-circleStart')
|
||||||
.attr('class', type)
|
.attr('class', type)
|
||||||
.attr('viewBox', '0 0 10 10')
|
.attr('viewBox', '0 0 10 10')
|
||||||
.attr('refX', -1)
|
.attr('refX', -1)
|
||||||
@ -197,7 +197,7 @@ const circle = (elem, type) => {
|
|||||||
const cross = (elem, type) => {
|
const cross = (elem, type) => {
|
||||||
elem
|
elem
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'crossEnd')
|
.attr('id', type + '-crossEnd')
|
||||||
.attr('class', type)
|
.attr('class', type)
|
||||||
.attr('viewBox', '0 0 11 11')
|
.attr('viewBox', '0 0 11 11')
|
||||||
.attr('refX', 12)
|
.attr('refX', 12)
|
||||||
@ -215,7 +215,7 @@ const cross = (elem, type) => {
|
|||||||
|
|
||||||
elem
|
elem
|
||||||
.append('marker')
|
.append('marker')
|
||||||
.attr('id', 'crossStart')
|
.attr('id', type + '-crossStart')
|
||||||
.attr('class', type)
|
.attr('class', type)
|
||||||
.attr('viewBox', '0 0 11 11')
|
.attr('viewBox', '0 0 11 11')
|
||||||
.attr('refX', -1)
|
.attr('refX', -1)
|
||||||
|
@ -19,7 +19,14 @@ export const clear = () => {
|
|||||||
const isDecendant = (id, ancenstorId) => {
|
const isDecendant = (id, ancenstorId) => {
|
||||||
// if (id === ancenstorId) return true;
|
// if (id === ancenstorId) return true;
|
||||||
|
|
||||||
log.info('In isDecendant', ancenstorId, ' ', id, ' = ', decendants[ancenstorId].indexOf(id) >= 0);
|
log.debug(
|
||||||
|
'In isDecendant',
|
||||||
|
ancenstorId,
|
||||||
|
' ',
|
||||||
|
id,
|
||||||
|
' = ',
|
||||||
|
decendants[ancenstorId].indexOf(id) >= 0
|
||||||
|
);
|
||||||
if (decendants[ancenstorId].indexOf(id) >= 0) return true;
|
if (decendants[ancenstorId].indexOf(id) >= 0) return true;
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
@ -30,7 +37,7 @@ const edgeInCluster = (edge, clusterId) => {
|
|||||||
if (!(edge.v === clusterId || edge.w === clusterId)) return false;
|
if (!(edge.v === clusterId || edge.w === clusterId)) return false;
|
||||||
|
|
||||||
if (!decendants[clusterId]) {
|
if (!decendants[clusterId]) {
|
||||||
log.info('Tilt, ', clustedId, ',not in decendants');
|
log.debug('Tilt, ', clustedId, ',not in decendants');
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -42,50 +49,6 @@ const edgeInCluster = (edge, clusterId) => {
|
|||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
|
|
||||||
const copyOld = (clusterId, graph, newGraph, rootId) => {
|
|
||||||
log.info('Copying to', rootId, ' from ', clusterId, graph.node(clusterId), rootId);
|
|
||||||
const nodes = graph.children(clusterId);
|
|
||||||
log.info('Copying (nodes)', nodes);
|
|
||||||
if (nodes) {
|
|
||||||
nodes.forEach(node => {
|
|
||||||
if (graph.children(node).length > 0) {
|
|
||||||
copy(node, graph, newGraph, rootId);
|
|
||||||
} else {
|
|
||||||
// if (clusterId === rootId) {
|
|
||||||
const data = graph.node(node);
|
|
||||||
log.info('cp ', node, ' to ', rootId, ' with parent ', clusterId); //,node, data, ' parent is ', clusterId);
|
|
||||||
newGraph.setNode(node, data);
|
|
||||||
newGraph.setParent(node, clusterId);
|
|
||||||
const edges = graph.edges(node);
|
|
||||||
log.trace('Copying Edges', edges);
|
|
||||||
edges.forEach(edge => {
|
|
||||||
log.trace('Edge', edge);
|
|
||||||
const data = graph.edge(edge.v, edge.w, edge.name);
|
|
||||||
log.trace('Edge data', data, rootId);
|
|
||||||
try {
|
|
||||||
// Do not copy edges in and out of the root cluster, they belong to the parent graph
|
|
||||||
if (edgeInCluster(edge, rootId)) {
|
|
||||||
log.trace('Copying as ', edge.v, edge.w, data, edge.name);
|
|
||||||
newGraph.setEdge(edge.v, edge.w, data, edge.name);
|
|
||||||
log.trace('newGraph edges ', newGraph.edges(), newGraph.edge(newGraph.edges()[0]));
|
|
||||||
} else {
|
|
||||||
log.trace('Skipping copy of edge as ', rootId, edge.v, edge.w, clusterId);
|
|
||||||
}
|
|
||||||
} catch (e) {
|
|
||||||
log.error(e);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
// } else {
|
|
||||||
// log.info('Skipping leaf as root ', rootId, ' !== ', clusterId, ' leaf id = ', node);
|
|
||||||
// }
|
|
||||||
}
|
|
||||||
// log.info('Removing node', node, graphlib.json.write(graph));
|
|
||||||
log.info('Removing node', node);
|
|
||||||
graph.removeNode(node);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
// newGraph.setNode(clusterId, graph.node(clusterId));
|
|
||||||
};
|
|
||||||
const copy = (clusterId, graph, newGraph, rootId) => {
|
const copy = (clusterId, graph, newGraph, rootId) => {
|
||||||
log.trace(
|
log.trace(
|
||||||
'Copying children of ',
|
'Copying children of ',
|
||||||
@ -103,7 +66,7 @@ const copy = (clusterId, graph, newGraph, rootId) => {
|
|||||||
nodes.push(clusterId);
|
nodes.push(clusterId);
|
||||||
}
|
}
|
||||||
|
|
||||||
log.info('Copying (nodes)', nodes);
|
log.debug('Copying (nodes)', nodes);
|
||||||
|
|
||||||
nodes.forEach(node => {
|
nodes.forEach(node => {
|
||||||
if (graph.children(node).length > 0) {
|
if (graph.children(node).length > 0) {
|
||||||
@ -113,11 +76,11 @@ const copy = (clusterId, graph, newGraph, rootId) => {
|
|||||||
log.trace('cp ', node, ' to ', rootId, ' with parent ', clusterId); //,node, data, ' parent is ', clusterId);
|
log.trace('cp ', node, ' to ', rootId, ' with parent ', clusterId); //,node, data, ' parent is ', clusterId);
|
||||||
newGraph.setNode(node, data);
|
newGraph.setNode(node, data);
|
||||||
if (clusterId !== rootId && node !== clusterId) {
|
if (clusterId !== rootId && node !== clusterId) {
|
||||||
log.info('Setting parent', node, clusterId);
|
log.debug('Setting parent', node, clusterId);
|
||||||
newGraph.setParent(node, clusterId);
|
newGraph.setParent(node, clusterId);
|
||||||
}
|
}
|
||||||
const edges = graph.edges(node);
|
const edges = graph.edges(node);
|
||||||
log.info('Copying Edges', edges);
|
log.debug('Copying Edges', edges);
|
||||||
edges.forEach(edge => {
|
edges.forEach(edge => {
|
||||||
log.trace('Edge', edge);
|
log.trace('Edge', edge);
|
||||||
const data = graph.edge(edge.v, edge.w, edge.name);
|
const data = graph.edge(edge.v, edge.w, edge.name);
|
||||||
@ -136,12 +99,12 @@ const copy = (clusterId, graph, newGraph, rootId) => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
log.info('Removing node', node);
|
log.debug('Removing node', node);
|
||||||
graph.removeNode(node);
|
graph.removeNode(node);
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
export const extractDecendants = (id, graph) => {
|
export const extractDecendants = (id, graph) => {
|
||||||
// log.info('Extracting ', id);
|
// log.debug('Extracting ', id);
|
||||||
const children = graph.children(id);
|
const children = graph.children(id);
|
||||||
let res = [].concat(children);
|
let res = [].concat(children);
|
||||||
|
|
||||||
@ -153,66 +116,6 @@ export const extractDecendants = (id, graph) => {
|
|||||||
return res;
|
return res;
|
||||||
};
|
};
|
||||||
|
|
||||||
export const extractGraphFromCluster = (clusterId, graph) => {
|
|
||||||
log.info('Extracting graph ', clusterId);
|
|
||||||
const clusterGraph = new graphlib.Graph({
|
|
||||||
multigraph: true,
|
|
||||||
compound: true
|
|
||||||
})
|
|
||||||
.setGraph({
|
|
||||||
rankdir: 'TB',
|
|
||||||
// Todo: set proper spacing
|
|
||||||
nodesep: 50,
|
|
||||||
ranksep: 50,
|
|
||||||
marginx: 8,
|
|
||||||
marginy: 8
|
|
||||||
})
|
|
||||||
.setDefaultEdgeLabel(function() {
|
|
||||||
return {};
|
|
||||||
});
|
|
||||||
|
|
||||||
// const conf = getConfig().flowchart;
|
|
||||||
// const nodeSpacing = conf.nodeSpacing || 50;
|
|
||||||
// const rankSpacing = conf.rankSpacing || 50;
|
|
||||||
|
|
||||||
// // Create the input mermaid.graph
|
|
||||||
// const g = new graphlib.Graph({
|
|
||||||
// multigraph: true,
|
|
||||||
// compound: true
|
|
||||||
// })
|
|
||||||
// .setGraph({
|
|
||||||
// rankdir: 'TB',
|
|
||||||
// nodesep: nodeSpacing,
|
|
||||||
// ranksep: rankSpacing,
|
|
||||||
// marginx: 8,
|
|
||||||
// marginy: 8
|
|
||||||
// })
|
|
||||||
// .setDefaultEdgeLabel(function() {
|
|
||||||
// return {};
|
|
||||||
// });
|
|
||||||
|
|
||||||
log.trace('Extracting before copy', graphlib.json.write(graph));
|
|
||||||
log.trace('Extracting before copy', graphlib.json.write(graph));
|
|
||||||
copy(clusterId, graph, clusterGraph, clusterId);
|
|
||||||
log.trace('Extracting after copy', graphlib.json.write(graph));
|
|
||||||
log.trace('Extracting after copy', clusterGraph.nodes());
|
|
||||||
graphs[clusterId] = clusterGraph;
|
|
||||||
|
|
||||||
// Remove references to extracted cluster
|
|
||||||
// graph.edges().forEach(edge => {
|
|
||||||
// if (isDecendant(edge.v, clusterId) || isDecendant(edge.w, clusterId)) {
|
|
||||||
// graph.removeEdge(edge);
|
|
||||||
// }
|
|
||||||
// });
|
|
||||||
// graph.nodes().forEach(node => {
|
|
||||||
// if (isDecendant(node, clusterId)) {
|
|
||||||
// log.info('Removing ', node, ' from ', clusterId);
|
|
||||||
// graph.removeNode(node);
|
|
||||||
// }
|
|
||||||
// });
|
|
||||||
return clusterGraph;
|
|
||||||
};
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Validates the graph, checking that all parent child relation points to existing nodes and that
|
* Validates the graph, checking that all parent child relation points to existing nodes and that
|
||||||
* edges between nodes also ia correct. When not correct the function logs the discrepancies.
|
* edges between nodes also ia correct. When not correct the function logs the discrepancies.
|
||||||
@ -274,10 +177,10 @@ const getAnchorId = id => {
|
|||||||
|
|
||||||
export const adjustClustersAndEdges = (graph, depth) => {
|
export const adjustClustersAndEdges = (graph, depth) => {
|
||||||
if (!graph || depth > 10) {
|
if (!graph || depth > 10) {
|
||||||
log.info('Opting out, no graph ');
|
log.debug('Opting out, no graph ');
|
||||||
return;
|
return;
|
||||||
} else {
|
} else {
|
||||||
log.info('Opting in, graph ');
|
log.debug('Opting in, graph ');
|
||||||
}
|
}
|
||||||
// Go through the nodes and for each cluster found, save a replacment node, this can be used when
|
// Go through the nodes and for each cluster found, save a replacment node, this can be used when
|
||||||
// faking a link to a cluster
|
// faking a link to a cluster
|
||||||
@ -291,7 +194,7 @@ export const adjustClustersAndEdges = (graph, depth) => {
|
|||||||
findNonClusterChild(id, graph)
|
findNonClusterChild(id, graph)
|
||||||
);
|
);
|
||||||
decendants[id] = extractDecendants(id, graph);
|
decendants[id] = extractDecendants(id, graph);
|
||||||
clusterDb[id] = { id: findNonClusterChild(id, graph) };
|
clusterDb[id] = { id: findNonClusterChild(id, graph), clusterData: graph.node(id) };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@ -300,9 +203,9 @@ export const adjustClustersAndEdges = (graph, depth) => {
|
|||||||
const children = graph.children(id);
|
const children = graph.children(id);
|
||||||
const edges = graph.edges();
|
const edges = graph.edges();
|
||||||
if (children.length > 0) {
|
if (children.length > 0) {
|
||||||
log.info('Cluster identified', id, decendants);
|
log.debug('Cluster identified', id, decendants);
|
||||||
edges.forEach(edge => {
|
edges.forEach(edge => {
|
||||||
// log.info('Edge, decendants: ', edge, decendants[id]);
|
// log.debug('Edge, decendants: ', edge, decendants[id]);
|
||||||
|
|
||||||
// Check if any edge leaves the cluster (not the actual cluster, thats a link from the box)
|
// Check if any edge leaves the cluster (not the actual cluster, thats a link from the box)
|
||||||
if (edge.v !== id && edge.w !== id) {
|
if (edge.v !== id && edge.w !== id) {
|
||||||
@ -314,8 +217,8 @@ export const adjustClustersAndEdges = (graph, depth) => {
|
|||||||
|
|
||||||
// d1 xor d2 - if either d1 is true and d2 is false or the other way around
|
// d1 xor d2 - if either d1 is true and d2 is false or the other way around
|
||||||
if (d1 ^ d2) {
|
if (d1 ^ d2) {
|
||||||
log.info('Edge: ', edge, ' leaves cluster ', id);
|
log.debug('Edge: ', edge, ' leaves cluster ', id);
|
||||||
log.info('Decendants of ', id, ': ', decendants[id]);
|
log.debug('Decendants of ', id, ': ', decendants[id]);
|
||||||
clusterDb[id].externalConnections = true;
|
clusterDb[id].externalConnections = true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -347,7 +250,7 @@ export const adjustClustersAndEdges = (graph, depth) => {
|
|||||||
graph.setEdge(v, w, edge, e.name);
|
graph.setEdge(v, w, edge, e.name);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
log.info('Adjusted Graph', graphlib.json.write(graph));
|
log.debug('Adjusted Graph', graphlib.json.write(graph));
|
||||||
|
|
||||||
log.trace(clusterDb);
|
log.trace(clusterDb);
|
||||||
|
|
||||||
@ -359,91 +262,8 @@ export const adjustClustersAndEdges = (graph, depth) => {
|
|||||||
// });
|
// });
|
||||||
};
|
};
|
||||||
|
|
||||||
export const transformClustersToNodes = (graph, depth) => {
|
|
||||||
log.info('transformClustersToNodes - ', depth);
|
|
||||||
if (depth > 10) {
|
|
||||||
log.error('Bailing out');
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
// For clusters without incoming and/or outgoing edges, create a new cluster-node
|
|
||||||
// containing the nodes and edges in the custer in a new graph
|
|
||||||
// for (let i = 0;)
|
|
||||||
const nodes = graph.nodes();
|
|
||||||
let hasChildren = false;
|
|
||||||
for (let i = 0; i < nodes.length; i++) {
|
|
||||||
const node = nodes[i];
|
|
||||||
const children = graph.children(node);
|
|
||||||
hasChildren = hasChildren || children.length > 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!hasChildren) {
|
|
||||||
log.info('Done, no node has children', graph.nodes());
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
// const clusters = Object.keys(clusterDb);
|
|
||||||
// clusters.forEach(clusterId => {
|
|
||||||
log.info('Nodes = ', nodes);
|
|
||||||
for (let i = 0; i < nodes.length; i++) {
|
|
||||||
const node = nodes[i];
|
|
||||||
|
|
||||||
log.info(
|
|
||||||
'Handling node',
|
|
||||||
node,
|
|
||||||
clusterDb,
|
|
||||||
clusterDb[node] && !clusterDb[node].externalConnections,
|
|
||||||
!graph.parent(node),
|
|
||||||
graph.node(node)
|
|
||||||
);
|
|
||||||
// Note that the node might have been removed after the Object.keys call so better check
|
|
||||||
// that it still is in the game
|
|
||||||
if (clusterDb[node]) {
|
|
||||||
if (
|
|
||||||
!clusterDb[node].externalConnections &&
|
|
||||||
!graph.parent(node) &&
|
|
||||||
graph.children(node) &&
|
|
||||||
graph.children(node).length > 0
|
|
||||||
) {
|
|
||||||
log.info('Cluster without external connections', node);
|
|
||||||
// const parentGraph = parent && graphs[parent] ? graphs[parent] : graph;
|
|
||||||
// New graph with the nodes in the cluster
|
|
||||||
log.info('before Extracting ', node, ' parent is ', graph.parent(node));
|
|
||||||
const clusterGraph = extractGraphFromCluster(node, graph);
|
|
||||||
|
|
||||||
if (clusterGraph) {
|
|
||||||
log.trace('Cluster graph', clusterGraph.nodes());
|
|
||||||
log.trace('Graph', graph.edges());
|
|
||||||
|
|
||||||
log.info('Creating node in original', node, clusterGraph);
|
|
||||||
|
|
||||||
// Create a new node in the original graph, this new node is not a cluster
|
|
||||||
// but a regular node with the cluster content as a new attached graph
|
|
||||||
graph.setNode(node, {
|
|
||||||
clusterNode: true,
|
|
||||||
id: node,
|
|
||||||
clusterData: clusterDb[node],
|
|
||||||
labelText: clusterDb[node].labelText,
|
|
||||||
graph: clusterGraph
|
|
||||||
});
|
|
||||||
|
|
||||||
// if any node in the clusterGraph still has children
|
|
||||||
transformClustersToNodes(clusterGraph, depth + 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
// The original edges in and out of the cluster is applied
|
|
||||||
// edges.forEach(edge => {
|
|
||||||
// log.info('Setting edge', edge);
|
|
||||||
// const data = graph.edge(edge);
|
|
||||||
// graph.setEdge(edge.v, edge.w, data);
|
|
||||||
// });
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
log.info('Not a cluster ', node);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
export const extractor = (graph, depth) => {
|
export const extractor = (graph, depth) => {
|
||||||
log.info('extractor - ', depth, graphlib.json.write(graph), graph.children('D'));
|
log.debug('extractor - ', depth, graphlib.json.write(graph), graph.children('D'));
|
||||||
if (depth > 10) {
|
if (depth > 10) {
|
||||||
log.error('Bailing out');
|
log.error('Bailing out');
|
||||||
return;
|
return;
|
||||||
@ -460,16 +280,16 @@ export const extractor = (graph, depth) => {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!hasChildren) {
|
if (!hasChildren) {
|
||||||
log.info('Done, no node has children', graph.nodes());
|
log.debug('Done, no node has children', graph.nodes());
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
// const clusters = Object.keys(clusterDb);
|
// const clusters = Object.keys(clusterDb);
|
||||||
// clusters.forEach(clusterId => {
|
// clusters.forEach(clusterId => {
|
||||||
log.info('Nodes = ', nodes, depth);
|
log.debug('Nodes = ', nodes, depth);
|
||||||
for (let i = 0; i < nodes.length; i++) {
|
for (let i = 0; i < nodes.length; i++) {
|
||||||
const node = nodes[i];
|
const node = nodes[i];
|
||||||
|
|
||||||
log.info(
|
log.debug(
|
||||||
'Extracting node',
|
'Extracting node',
|
||||||
node,
|
node,
|
||||||
clusterDb,
|
clusterDb,
|
||||||
@ -484,7 +304,7 @@ export const extractor = (graph, depth) => {
|
|||||||
// that it still is in the game
|
// that it still is in the game
|
||||||
if (!clusterDb[node]) {
|
if (!clusterDb[node]) {
|
||||||
// Skip if the node is not a cluster
|
// Skip if the node is not a cluster
|
||||||
log.info('Not a cluster', node, depth);
|
log.debug('Not a cluster', node, depth);
|
||||||
// break;
|
// break;
|
||||||
} else if (
|
} else if (
|
||||||
!clusterDb[node].externalConnections &&
|
!clusterDb[node].externalConnections &&
|
||||||
@ -492,7 +312,7 @@ export const extractor = (graph, depth) => {
|
|||||||
graph.children(node) &&
|
graph.children(node) &&
|
||||||
graph.children(node).length > 0
|
graph.children(node).length > 0
|
||||||
) {
|
) {
|
||||||
log.info(
|
log.debug(
|
||||||
'Cluster without external connections, without a parent and with children',
|
'Cluster without external connections, without a parent and with children',
|
||||||
node,
|
node,
|
||||||
depth
|
depth
|
||||||
@ -518,47 +338,14 @@ export const extractor = (graph, depth) => {
|
|||||||
graph.setNode(node, {
|
graph.setNode(node, {
|
||||||
clusterNode: true,
|
clusterNode: true,
|
||||||
id: node,
|
id: node,
|
||||||
clusterData: clusterDb[node],
|
clusterData: clusterDb[node].clusterData,
|
||||||
labelText: clusterDb[node].labelText,
|
labelText: clusterDb[node].labelText,
|
||||||
graph: clusterGraph
|
graph: clusterGraph
|
||||||
});
|
});
|
||||||
log.info('New graph after copy', graphlib.json.write(clusterGraph));
|
log.debug('New graph after copy', graphlib.json.write(clusterGraph));
|
||||||
log.info('Old graph after copy', graphlib.json.write(graph));
|
log.debug('Old graph after copy', graphlib.json.write(graph));
|
||||||
|
|
||||||
/*
|
|
||||||
// New graph with the nodes in the cluster
|
|
||||||
log.info('before Extracting ', node, ' parent is ', graph.parent(node));
|
|
||||||
const clusterGraph = extractGraphFromCluster(node, graph);
|
|
||||||
|
|
||||||
if (clusterGraph) {
|
|
||||||
log.trace('Cluster graph', clusterGraph.nodes());
|
|
||||||
log.trace('Graph', graph.edges());
|
|
||||||
|
|
||||||
log.info('Creating node in original', node, clusterGraph);
|
|
||||||
|
|
||||||
// Create a new node in the original graph, this new node is not a cluster
|
|
||||||
// but a regular node with the cluster content as a new attached graph
|
|
||||||
graph.setNode(node, {
|
|
||||||
clusterNode: true,
|
|
||||||
id: node,
|
|
||||||
clusterData: clusterDb[node],
|
|
||||||
labelText: clusterDb[node].labelText,
|
|
||||||
graph: clusterGraph
|
|
||||||
});
|
|
||||||
|
|
||||||
// if any node in the clusterGraph still has children
|
|
||||||
transformClustersToNodes(clusterGraph, depth + 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
// The original edges in and out of the cluster is applied
|
|
||||||
// edges.forEach(edge => {
|
|
||||||
// log.info('Setting edge', edge);
|
|
||||||
// const data = graph.edge(edge);
|
|
||||||
// graph.setEdge(edge.v, edge.w, data);
|
|
||||||
// });
|
|
||||||
*/
|
|
||||||
} else {
|
} else {
|
||||||
log.info(
|
log.debug(
|
||||||
'Cluster ** ',
|
'Cluster ** ',
|
||||||
node,
|
node,
|
||||||
' **not meeting the criteria !externalConnections:',
|
' **not meeting the criteria !externalConnections:',
|
||||||
@ -570,16 +357,16 @@ export const extractor = (graph, depth) => {
|
|||||||
graph.children('D'),
|
graph.children('D'),
|
||||||
depth
|
depth
|
||||||
);
|
);
|
||||||
log.info(clusterDb);
|
log.debug(clusterDb);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
nodes = graph.nodes();
|
nodes = graph.nodes();
|
||||||
log.info('New list of nodes', nodes);
|
log.debug('New list of nodes', nodes);
|
||||||
for (let i = 0; i < nodes.length; i++) {
|
for (let i = 0; i < nodes.length; i++) {
|
||||||
const node = nodes[i];
|
const node = nodes[i];
|
||||||
const data = graph.node(node);
|
const data = graph.node(node);
|
||||||
log.info(' Now next leveö', node, data);
|
log.debug(' Now next leveö', node, data);
|
||||||
if (data.clusterNode) {
|
if (data.clusterNode) {
|
||||||
extractor(data.graph, depth + 1);
|
extractor(data.graph, depth + 1);
|
||||||
}
|
}
|
||||||
|
@ -248,7 +248,7 @@ const cylinder = (parent, node) => {
|
|||||||
const rect = (parent, node) => {
|
const rect = (parent, node) => {
|
||||||
const { shapeSvg, bbox, halfPadding } = labelHelper(parent, node, 'node ' + node.classes);
|
const { shapeSvg, bbox, halfPadding } = labelHelper(parent, node, 'node ' + node.classes);
|
||||||
|
|
||||||
logger.info('Classes = ', node.classes);
|
logger.trace('Classes = ', node.classes);
|
||||||
// add the rect
|
// add the rect
|
||||||
const rect = shapeSvg.insert('rect', ':first-child');
|
const rect = shapeSvg.insert('rect', ':first-child');
|
||||||
|
|
||||||
@ -396,7 +396,22 @@ export const clear = () => {
|
|||||||
|
|
||||||
export const positionNode = node => {
|
export const positionNode = node => {
|
||||||
const el = nodeElems[node.id];
|
const el = nodeElems[node.id];
|
||||||
logger.debug('Transforming node', node);
|
logger.trace(
|
||||||
el.attr('transform', 'translate(' + node.x + ', ' + node.y + ')');
|
'Transforming node',
|
||||||
// el.attr('transform', 'translate(' + node.x / 2 + ', ' + 0 + ')');
|
node,
|
||||||
|
'translate(' + (node.x - node.width / 2 - 5) + ', ' + (node.y - node.height / 2 - 5) + ')'
|
||||||
|
);
|
||||||
|
const padding = 8;
|
||||||
|
if (node.clusterNode) {
|
||||||
|
el.attr(
|
||||||
|
'transform',
|
||||||
|
'translate(' +
|
||||||
|
(node.x - node.width / 2 - padding) +
|
||||||
|
', ' +
|
||||||
|
(node.y - node.height / 2 - padding) +
|
||||||
|
')'
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
el.attr('transform', 'translate(' + node.x + ', ' + node.y + ')');
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
@ -188,6 +188,8 @@ export const addEdges = function(edges, g) {
|
|||||||
} else {
|
} else {
|
||||||
edgeData.arrowhead = 'normal';
|
edgeData.arrowhead = 'normal';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
logger.info(edgeData, edge);
|
||||||
edgeData.arrowType = edge.type;
|
edgeData.arrowType = edge.type;
|
||||||
|
|
||||||
let style = '';
|
let style = '';
|
||||||
|
Loading…
x
Reference in New Issue
Block a user