|
|
@ -15302,6 +15302,8 @@ return /******/ (function(modules) { // webpackBootstrap |
|
|
|
s.node.xFixed = s.xFixed; |
|
|
|
s.node.yFixed = s.yFixed; |
|
|
|
}); |
|
|
|
this.moving = true; |
|
|
|
this.start(); |
|
|
|
} |
|
|
|
this._redraw(); |
|
|
|
}; |
|
|
@ -16974,9 +16976,6 @@ return /******/ (function(modules) { // webpackBootstrap |
|
|
|
var yVia = null; |
|
|
|
var factor = this.smoothCurves.roundness; |
|
|
|
var type = this.smoothCurves.type; |
|
|
|
if (factor == 0) { |
|
|
|
return {x:null,y:null}; |
|
|
|
} |
|
|
|
|
|
|
|
var dx = Math.abs(this.from.x - this.to.x); |
|
|
|
var dy = Math.abs(this.from.y - this.to.y); |
|
|
@ -17033,22 +17032,42 @@ return /******/ (function(modules) { // webpackBootstrap |
|
|
|
} |
|
|
|
} |
|
|
|
else if (type == "straightCross") { |
|
|
|
if (Math.abs(this.from.x - this.to.x) < Math.abs(this.from.y - this.to.y)) { |
|
|
|
if (Math.abs(this.from.x - this.to.x) < Math.abs(this.from.y - this.to.y)) { // up - down
|
|
|
|
xVia = this.from.x; |
|
|
|
yVia = this.to.y |
|
|
|
if (this.from.y < this.to.y) { |
|
|
|
yVia = this.to.y - (1-factor) * dy; |
|
|
|
} |
|
|
|
else { |
|
|
|
yVia = this.to.y + (1-factor) * dy; |
|
|
|
} |
|
|
|
} |
|
|
|
else if (Math.abs(this.from.x - this.to.x) > Math.abs(this.from.y - this.to.y)) { |
|
|
|
xVia = this.to.x; |
|
|
|
else if (Math.abs(this.from.x - this.to.x) > Math.abs(this.from.y - this.to.y)) { // left - right
|
|
|
|
if (this.from.x < this.to.x) { |
|
|
|
xVia = this.to.x - (1-factor) * dx; |
|
|
|
} |
|
|
|
else { |
|
|
|
xVia = this.to.x + (1-factor) * dx; |
|
|
|
} |
|
|
|
yVia = this.from.y; |
|
|
|
} |
|
|
|
} |
|
|
|
else if (type == 'horizontal') { |
|
|
|
xVia = this.to.x; |
|
|
|
if (this.from.x < this.to.x) { |
|
|
|
xVia = this.to.x - (1-factor) * dx; |
|
|
|
} |
|
|
|
else { |
|
|
|
xVia = this.to.x + (1-factor) * dx; |
|
|
|
} |
|
|
|
yVia = this.from.y; |
|
|
|
} |
|
|
|
else if (type == 'vertical') { |
|
|
|
xVia = this.from.x; |
|
|
|
yVia = this.to.y; |
|
|
|
if (this.from.y < this.to.y) { |
|
|
|
yVia = this.to.y - (1-factor) * dy; |
|
|
|
} |
|
|
|
else { |
|
|
|
yVia = this.to.y + (1-factor) * dy; |
|
|
|
} |
|
|
|
} |
|
|
|
else { // continuous
|
|
|
|
if (Math.abs(this.from.x - this.to.x) < Math.abs(this.from.y - this.to.y)) { |
|
|
@ -25089,26 +25108,31 @@ return /******/ (function(modules) { // webpackBootstrap |
|
|
|
var nodeId, node; |
|
|
|
|
|
|
|
// start placing all the level 0 nodes first. Then recursively position their branches.
|
|
|
|
for (nodeId in distribution[0].nodes) { |
|
|
|
if (distribution[0].nodes.hasOwnProperty(nodeId)) { |
|
|
|
node = distribution[0].nodes[nodeId]; |
|
|
|
if (this.constants.hierarchicalLayout.direction == "UD" || this.constants.hierarchicalLayout.direction == "DU") { |
|
|
|
if (node.xFixed) { |
|
|
|
node.x = distribution[0].minPos; |
|
|
|
node.xFixed = false; |
|
|
|
for (var level in distribution) { |
|
|
|
if (distribution.hasOwnProperty(level)) { |
|
|
|
|
|
|
|
distribution[0].minPos += distribution[0].nodeSpacing; |
|
|
|
} |
|
|
|
} |
|
|
|
else { |
|
|
|
if (node.yFixed) { |
|
|
|
node.y = distribution[0].minPos; |
|
|
|
node.yFixed = false; |
|
|
|
for (nodeId in distribution[level].nodes) { |
|
|
|
if (distribution[level].nodes.hasOwnProperty(nodeId)) { |
|
|
|
node = distribution[level].nodes[nodeId]; |
|
|
|
if (this.constants.hierarchicalLayout.direction == "UD" || this.constants.hierarchicalLayout.direction == "DU") { |
|
|
|
if (node.xFixed) { |
|
|
|
node.x = distribution[level].minPos; |
|
|
|
node.xFixed = false; |
|
|
|
|
|
|
|
distribution[0].minPos += distribution[0].nodeSpacing; |
|
|
|
distribution[level].minPos += distribution[level].nodeSpacing; |
|
|
|
} |
|
|
|
} |
|
|
|
else { |
|
|
|
if (node.yFixed) { |
|
|
|
node.y = distribution[level].minPos; |
|
|
|
node.yFixed = false; |
|
|
|
|
|
|
|
distribution[level].minPos += distribution[level].nodeSpacing; |
|
|
|
} |
|
|
|
} |
|
|
|
this._placeBranchNodes(node.edges,node.id,distribution,node.level); |
|
|
|
} |
|
|
|
} |
|
|
|
this._placeBranchNodes(node.edges,node.id,distribution,node.level); |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
@ -25140,11 +25164,11 @@ return /******/ (function(modules) { // webpackBootstrap |
|
|
|
else { |
|
|
|
node.x = this.constants.hierarchicalLayout.levelSeparation*node.level; |
|
|
|
} |
|
|
|
if (!distribution.hasOwnProperty(node.level)) { |
|
|
|
if (distribution[node.level] === undefined) { |
|
|
|
distribution[node.level] = {amount: 0, nodes: {}, minPos:0, nodeSpacing:0}; |
|
|
|
} |
|
|
|
distribution[node.level].amount += 1; |
|
|
|
distribution[node.level].nodes[node.id] = node; |
|
|
|
distribution[node.level].nodes[nodeId] = node; |
|
|
|
} |
|
|
|
} |
|
|
|
|
|
|
@ -26744,8 +26768,8 @@ return /******/ (function(modules) { // webpackBootstrap |
|
|
|
|
|
|
|
var util = __webpack_require__(1); |
|
|
|
var RepulsionMixin = __webpack_require__(52); |
|
|
|
var HierarchialRepulsionMixin = __webpack_require__(53); |
|
|
|
var BarnesHutMixin = __webpack_require__(54); |
|
|
|
var HierarchialRepulsionMixin = __webpack_require__(54); |
|
|
|
var BarnesHutMixin = __webpack_require__(53); |
|
|
|
|
|
|
|
/** |
|
|
|
* Toggling barnes Hut calculation on and off. |
|
|
@ -30130,136 +30154,6 @@ return /******/ (function(modules) { // webpackBootstrap |
|
|
|
|
|
|
|
/***/ }, |
|
|
|
/* 53 */ |
|
|
|
/***/ function(module, exports, __webpack_require__) { |
|
|
|
|
|
|
|
/** |
|
|
|
* Calculate the forces the nodes apply on eachother based on a repulsion field. |
|
|
|
* This field is linearly approximated. |
|
|
|
* |
|
|
|
* @private |
|
|
|
*/ |
|
|
|
exports._calculateNodeForces = function () { |
|
|
|
var dx, dy, distance, fx, fy, combinedClusterSize, |
|
|
|
repulsingForce, node1, node2, i, j; |
|
|
|
|
|
|
|
var nodes = this.calculationNodes; |
|
|
|
var nodeIndices = this.calculationNodeIndices; |
|
|
|
|
|
|
|
// approximation constants
|
|
|
|
var b = 5; |
|
|
|
var a_base = 0.5 * -b; |
|
|
|
|
|
|
|
|
|
|
|
// repulsing forces between nodes
|
|
|
|
var nodeDistance = this.constants.physics.hierarchicalRepulsion.nodeDistance; |
|
|
|
var minimumDistance = nodeDistance; |
|
|
|
var a = a_base / minimumDistance; |
|
|
|
|
|
|
|
// we loop from i over all but the last entree in the array
|
|
|
|
// j loops from i+1 to the last. This way we do not double count any of the indices, nor i == j
|
|
|
|
for (i = 0; i < nodeIndices.length - 1; i++) { |
|
|
|
|
|
|
|
node1 = nodes[nodeIndices[i]]; |
|
|
|
for (j = i + 1; j < nodeIndices.length; j++) { |
|
|
|
node2 = nodes[nodeIndices[j]]; |
|
|
|
if (node1.level == node2.level) { |
|
|
|
|
|
|
|
dx = node2.x - node1.x; |
|
|
|
dy = node2.y - node1.y; |
|
|
|
distance = Math.sqrt(dx * dx + dy * dy); |
|
|
|
|
|
|
|
|
|
|
|
if (distance < 2 * minimumDistance) { |
|
|
|
repulsingForce = a * distance + b; |
|
|
|
var c = 0.05; |
|
|
|
var d = 2 * minimumDistance * 2 * c; |
|
|
|
repulsingForce = c * Math.pow(distance,2) - d * distance + d*d/(4*c); |
|
|
|
|
|
|
|
// normalize force with
|
|
|
|
if (distance == 0) { |
|
|
|
distance = 0.01; |
|
|
|
} |
|
|
|
else { |
|
|
|
repulsingForce = repulsingForce / distance; |
|
|
|
} |
|
|
|
fx = dx * repulsingForce; |
|
|
|
fy = dy * repulsingForce; |
|
|
|
|
|
|
|
node1.fx -= fx; |
|
|
|
node1.fy -= fy; |
|
|
|
node2.fx += fx; |
|
|
|
node2.fy += fy; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
/** |
|
|
|
* this function calculates the effects of the springs in the case of unsmooth curves. |
|
|
|
* |
|
|
|
* @private |
|
|
|
*/ |
|
|
|
exports._calculateHierarchicalSpringForces = function () { |
|
|
|
var edgeLength, edge, edgeId; |
|
|
|
var dx, dy, fx, fy, springForce, distance; |
|
|
|
var edges = this.edges; |
|
|
|
|
|
|
|
// forces caused by the edges, modelled as springs
|
|
|
|
for (edgeId in edges) { |
|
|
|
if (edges.hasOwnProperty(edgeId)) { |
|
|
|
edge = edges[edgeId]; |
|
|
|
if (edge.connected) { |
|
|
|
// only calculate forces if nodes are in the same sector
|
|
|
|
if (this.nodes.hasOwnProperty(edge.toId) && this.nodes.hasOwnProperty(edge.fromId)) { |
|
|
|
edgeLength = edge.customLength ? edge.length : this.constants.physics.springLength; |
|
|
|
// this implies that the edges between big clusters are longer
|
|
|
|
edgeLength += (edge.to.clusterSize + edge.from.clusterSize - 2) * this.constants.clustering.edgeGrowth; |
|
|
|
|
|
|
|
dx = (edge.from.x - edge.to.x); |
|
|
|
dy = (edge.from.y - edge.to.y); |
|
|
|
distance = Math.sqrt(dx * dx + dy * dy); |
|
|
|
|
|
|
|
if (distance == 0) { |
|
|
|
distance = 0.01; |
|
|
|
} |
|
|
|
|
|
|
|
distance = Math.max(0.8*edgeLength,Math.min(5*edgeLength, distance)); |
|
|
|
|
|
|
|
// the 1/distance is so the fx and fy can be calculated without sine or cosine.
|
|
|
|
springForce = this.constants.physics.springConstant * (edgeLength - distance) / distance; |
|
|
|
|
|
|
|
fx = dx * springForce; |
|
|
|
fy = dy * springForce; |
|
|
|
|
|
|
|
edge.to.fx -= fx; |
|
|
|
edge.to.fy -= fy; |
|
|
|
edge.from.fx += fx; |
|
|
|
edge.from.fy += fy; |
|
|
|
|
|
|
|
|
|
|
|
var factor = 5; |
|
|
|
if (distance > edgeLength) { |
|
|
|
factor = 25; |
|
|
|
} |
|
|
|
|
|
|
|
if (edge.from.level > edge.to.level) { |
|
|
|
edge.to.fx -= factor*fx; |
|
|
|
edge.to.fy -= factor*fy; |
|
|
|
} |
|
|
|
else if (edge.from.level < edge.to.level) { |
|
|
|
edge.from.fx += factor*fx; |
|
|
|
edge.from.fy += factor*fy; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
}; |
|
|
|
|
|
|
|
/***/ }, |
|
|
|
/* 54 */ |
|
|
|
/***/ function(module, exports, __webpack_require__) { |
|
|
|
|
|
|
|
/** |
|
|
@ -30657,6 +30551,136 @@ return /******/ (function(modules) { // webpackBootstrap |
|
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
/***/ }, |
|
|
|
/* 54 */ |
|
|
|
/***/ function(module, exports, __webpack_require__) { |
|
|
|
|
|
|
|
/** |
|
|
|
* Calculate the forces the nodes apply on eachother based on a repulsion field. |
|
|
|
* This field is linearly approximated. |
|
|
|
* |
|
|
|
* @private |
|
|
|
*/ |
|
|
|
exports._calculateNodeForces = function () { |
|
|
|
var dx, dy, distance, fx, fy, combinedClusterSize, |
|
|
|
repulsingForce, node1, node2, i, j; |
|
|
|
|
|
|
|
var nodes = this.calculationNodes; |
|
|
|
var nodeIndices = this.calculationNodeIndices; |
|
|
|
|
|
|
|
// approximation constants
|
|
|
|
var b = 5; |
|
|
|
var a_base = 0.5 * -b; |
|
|
|
|
|
|
|
|
|
|
|
// repulsing forces between nodes
|
|
|
|
var nodeDistance = this.constants.physics.hierarchicalRepulsion.nodeDistance; |
|
|
|
var minimumDistance = nodeDistance; |
|
|
|
var a = a_base / minimumDistance; |
|
|
|
|
|
|
|
// we loop from i over all but the last entree in the array
|
|
|
|
// j loops from i+1 to the last. This way we do not double count any of the indices, nor i == j
|
|
|
|
for (i = 0; i < nodeIndices.length - 1; i++) { |
|
|
|
|
|
|
|
node1 = nodes[nodeIndices[i]]; |
|
|
|
for (j = i + 1; j < nodeIndices.length; j++) { |
|
|
|
node2 = nodes[nodeIndices[j]]; |
|
|
|
if (node1.level == node2.level) { |
|
|
|
|
|
|
|
dx = node2.x - node1.x; |
|
|
|
dy = node2.y - node1.y; |
|
|
|
distance = Math.sqrt(dx * dx + dy * dy); |
|
|
|
|
|
|
|
|
|
|
|
if (distance < 2 * minimumDistance) { |
|
|
|
repulsingForce = a * distance + b; |
|
|
|
var c = 0.05; |
|
|
|
var d = 2 * minimumDistance * 2 * c; |
|
|
|
repulsingForce = c * Math.pow(distance,2) - d * distance + d*d/(4*c); |
|
|
|
|
|
|
|
// normalize force with
|
|
|
|
if (distance == 0) { |
|
|
|
distance = 0.01; |
|
|
|
} |
|
|
|
else { |
|
|
|
repulsingForce = repulsingForce / distance; |
|
|
|
} |
|
|
|
fx = dx * repulsingForce; |
|
|
|
fy = dy * repulsingForce; |
|
|
|
|
|
|
|
node1.fx -= fx; |
|
|
|
node1.fy -= fy; |
|
|
|
node2.fx += fx; |
|
|
|
node2.fy += fy; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
}; |
|
|
|
|
|
|
|
|
|
|
|
/** |
|
|
|
* this function calculates the effects of the springs in the case of unsmooth curves. |
|
|
|
* |
|
|
|
* @private |
|
|
|
*/ |
|
|
|
exports._calculateHierarchicalSpringForces = function () { |
|
|
|
var edgeLength, edge, edgeId; |
|
|
|
var dx, dy, fx, fy, springForce, distance; |
|
|
|
var edges = this.edges; |
|
|
|
|
|
|
|
// forces caused by the edges, modelled as springs
|
|
|
|
for (edgeId in edges) { |
|
|
|
if (edges.hasOwnProperty(edgeId)) { |
|
|
|
edge = edges[edgeId]; |
|
|
|
if (edge.connected) { |
|
|
|
// only calculate forces if nodes are in the same sector
|
|
|
|
if (this.nodes.hasOwnProperty(edge.toId) && this.nodes.hasOwnProperty(edge.fromId)) { |
|
|
|
edgeLength = edge.customLength ? edge.length : this.constants.physics.springLength; |
|
|
|
// this implies that the edges between big clusters are longer
|
|
|
|
edgeLength += (edge.to.clusterSize + edge.from.clusterSize - 2) * this.constants.clustering.edgeGrowth; |
|
|
|
|
|
|
|
dx = (edge.from.x - edge.to.x); |
|
|
|
dy = (edge.from.y - edge.to.y); |
|
|
|
distance = Math.sqrt(dx * dx + dy * dy); |
|
|
|
|
|
|
|
if (distance == 0) { |
|
|
|
distance = 0.01; |
|
|
|
} |
|
|
|
|
|
|
|
distance = Math.max(0.8*edgeLength,Math.min(5*edgeLength, distance)); |
|
|
|
|
|
|
|
// the 1/distance is so the fx and fy can be calculated without sine or cosine.
|
|
|
|
springForce = this.constants.physics.springConstant * (edgeLength - distance) / distance; |
|
|
|
|
|
|
|
fx = dx * springForce; |
|
|
|
fy = dy * springForce; |
|
|
|
|
|
|
|
edge.to.fx -= fx; |
|
|
|
edge.to.fy -= fy; |
|
|
|
edge.from.fx += fx; |
|
|
|
edge.from.fy += fy; |
|
|
|
|
|
|
|
|
|
|
|
var factor = 5; |
|
|
|
if (distance > edgeLength) { |
|
|
|
factor = 25; |
|
|
|
} |
|
|
|
|
|
|
|
if (edge.from.level > edge.to.level) { |
|
|
|
edge.to.fx -= factor*fx; |
|
|
|
edge.to.fy -= factor*fy; |
|
|
|
} |
|
|
|
else if (edge.from.level < edge.to.level) { |
|
|
|
edge.from.fx += factor*fx; |
|
|
|
edge.from.fy += factor*fy; |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
} |
|
|
|
}; |
|
|
|
|
|
|
|
/***/ }, |
|
|
|
/* 55 */ |
|
|
|
/***/ function(module, exports, __webpack_require__) { |
|
|
|