Browse Source

tweaked clustering

css_transitions
Alex de Mulder 10 years ago
parent
commit
4af15843fb
3 changed files with 74 additions and 40 deletions
  1. +1
    -1
      src/graph/Graph.js
  2. +36
    -19
      src/graph/cluster.js
  3. +37
    -20
      vis.js

+ 1
- 1
src/graph/Graph.js View File

@ -57,7 +57,7 @@ function Graph (container, data, options) {
edges: { edges: {
widthMin: 1, widthMin: 1,
widthMax: 15, widthMax: 15,
width: 1,
width: 10,
style: 'line', style: 'line',
color: '#343434', color: '#343434',
fontColor: '#343434', fontColor: '#343434',

+ 36
- 19
src/graph/cluster.js View File

@ -4,6 +4,7 @@
*/ */
function Cluster() { function Cluster() {
this.clusterSession = 0; this.clusterSession = 0;
this.hubThreshold = 5;
} }
/** /**
@ -371,11 +372,14 @@ Cluster.prototype._forceClustersByZoom = function() {
}; };
/**
* this functions starts clustering by hubs
* The minimum hub threshold is set globally
*/
Cluster.prototype.aggregateHubs = function() { Cluster.prototype.aggregateHubs = function() {
var isMovingBeforeClustering = this.moving; var isMovingBeforeClustering = this.moving;
var hubThreshold = 4;
this._forceClustersByHub(hubThreshold);
this._forceClustersByHub();
// if the simulation was settled, we restart the simulation if a cluster has been formed or expanded // if the simulation was settled, we restart the simulation if a cluster has been formed or expanded
if (this.moving != isMovingBeforeClustering) { if (this.moving != isMovingBeforeClustering) {
@ -384,23 +388,39 @@ Cluster.prototype.aggregateHubs = function() {
}; };
Cluster.prototype._getHubSize = function() {
var distribution = {};
for (var i = 0; i < this.nodeIndices.length; i++) {
// TODO get the distribution
}
};
/** /**
* *
* @param hubThreshold * @param hubThreshold
* @private * @private
*/ */
Cluster.prototype._forceClustersByHub = function(hubThreshold) {
for (var nodeID = 0; nodeID < this.nodeIndices.length; nodeID++) {
if (this.nodes.hasOwnProperty(this.nodeIndices[nodeID])) {
var hubNode = this.nodes[this.nodeIndices[nodeID]];
if (hubNode.dynamicEdges.length >= hubThreshold) {
Cluster.prototype._forceClustersByHub = function() {
// we loop over all nodes in the list
for (var i = 0; i < this.nodeIndices.length; i++) {
// we check if it is still available since it can be used by the clustering in this loop
if (this.nodes.hasOwnProperty(this.nodeIndices[i])) {
var hubNode = this.nodes[this.nodeIndices[i]];
// we decide if the node is a hub
// TODO: check if dynamicEdgesLength is required
if (hubNode.dynamicEdges.length >= this.hubThreshold) {
// we create a list of edges because the dynamicEdges change over the course of this loop
var edgesIDarray = [] var edgesIDarray = []
var amountOfInitialEdges = hubNode.dynamicEdges.length; var amountOfInitialEdges = hubNode.dynamicEdges.length;
for (var i = 0; i < amountOfInitialEdges; i++) {
edgesIDarray.push(hubNode.dynamicEdges[i].id);
for (var j = 0; j < amountOfInitialEdges; j++) {
edgesIDarray.push(hubNode.dynamicEdges[j].id);
} }
for (var i = 0; i < amountOfInitialEdges; i++) {
var edge = this.edges[edgesIDarray[i]];
// we loop over all edges INITIALLY connected to this hub
for (var j = 0; j < amountOfInitialEdges; j++) {
var edge = this.edges[edgesIDarray[j]];
var childNode = this.nodes[(edge.fromId == hubNode.id) ? edge.toId : edge.fromId]; var childNode = this.nodes[(edge.fromId == hubNode.id) ? edge.toId : edge.fromId];
this._addToCluster(hubNode,childNode,true); this._addToCluster(hubNode,childNode,true);
} }
@ -409,13 +429,8 @@ Cluster.prototype._forceClustersByHub = function(hubThreshold) {
} }
} }
this._updateNodeIndexList(); this._updateNodeIndexList();
this._updateDynamicEdges();
//this._updateDynamicEdges();
this._updateLabels(); this._updateLabels();
if (this.moving != isMovingBeforeClustering) {
this.start();
}
}; };
@ -433,9 +448,11 @@ Cluster.prototype._addToCluster = function(parentNode, childNode, forceLevelColl
// join child node in the parent node // join child node in the parent node
parentNode.containedNodes[childNode.id] = childNode; parentNode.containedNodes[childNode.id] = childNode;
/*
if (forceLevelCollapse == false) { if (forceLevelCollapse == false) {
parentNode.dynamicEdgesLength += childNode.dynamicEdges.length - 2; parentNode.dynamicEdgesLength += childNode.dynamicEdges.length - 2;
} }
*/
for (var i = 0; i < childNode.dynamicEdges.length; i++) { for (var i = 0; i < childNode.dynamicEdges.length; i++) {
var edge = childNode.dynamicEdges[i]; var edge = childNode.dynamicEdges[i];
@ -443,7 +460,6 @@ Cluster.prototype._addToCluster = function(parentNode, childNode, forceLevelColl
this._addToContainedEdges(parentNode,childNode,edge); this._addToContainedEdges(parentNode,childNode,edge);
} }
else { else {
console.log('connecting edge to cluster');
this._connectEdgeToCluster(parentNode,childNode,edge); this._connectEdgeToCluster(parentNode,childNode,edge);
} }
} }
@ -464,9 +480,10 @@ Cluster.prototype._addToCluster = function(parentNode, childNode, forceLevelColl
} }
else { else {
parentNode.formationScale = this.scale; // The latest child has been added on this scale parentNode.formationScale = this.scale; // The latest child has been added on this scale
parentNode.dynamicEdgesLength = parentNode.dynamicEdges.length;
} }
parentNode.dynamicEdgesLength = parentNode.dynamicEdges.length;
// recalculate the size of the node on the next time the node is rendered // recalculate the size of the node on the next time the node is rendered
parentNode.clearSizeCache(); parentNode.clearSizeCache();

+ 37
- 20
vis.js View File

@ -14945,6 +14945,7 @@ Images.prototype.load = function(url) {
*/ */
function Cluster() { function Cluster() {
this.clusterSession = 0; this.clusterSession = 0;
this.hubThreshold = 5;
} }
/** /**
@ -15312,11 +15313,14 @@ Cluster.prototype._forceClustersByZoom = function() {
}; };
/**
* this functions starts clustering by hubs
* The minimum hub threshold is set globally
*/
Cluster.prototype.aggregateHubs = function() { Cluster.prototype.aggregateHubs = function() {
var isMovingBeforeClustering = this.moving; var isMovingBeforeClustering = this.moving;
var hubThreshold = 4;
this._forceClustersByHub(hubThreshold);
this._forceClustersByHub();
// if the simulation was settled, we restart the simulation if a cluster has been formed or expanded // if the simulation was settled, we restart the simulation if a cluster has been formed or expanded
if (this.moving != isMovingBeforeClustering) { if (this.moving != isMovingBeforeClustering) {
@ -15325,23 +15329,39 @@ Cluster.prototype.aggregateHubs = function() {
}; };
Cluster.prototype._getHubSize = function() {
var distribution = {};
for (var i = 0; i < this.nodeIndices.length; i++) {
// TODO get the distribution
}
};
/** /**
* *
* @param hubThreshold * @param hubThreshold
* @private * @private
*/ */
Cluster.prototype._forceClustersByHub = function(hubThreshold) {
for (var nodeID = 0; nodeID < this.nodeIndices.length; nodeID++) {
if (this.nodes.hasOwnProperty(this.nodeIndices[nodeID])) {
var hubNode = this.nodes[this.nodeIndices[nodeID]];
if (hubNode.dynamicEdges.length >= hubThreshold) {
Cluster.prototype._forceClustersByHub = function() {
// we loop over all nodes in the list
for (var i = 0; i < this.nodeIndices.length; i++) {
// we check if it is still available since it can be used by the clustering in this loop
if (this.nodes.hasOwnProperty(this.nodeIndices[i])) {
var hubNode = this.nodes[this.nodeIndices[i]];
// we decide if the node is a hub
// TODO: check if dynamicEdgesLength is required
if (hubNode.dynamicEdges.length >= this.hubThreshold) {
// we create a list of edges because the dynamicEdges change over the course of this loop
var edgesIDarray = [] var edgesIDarray = []
var amountOfInitialEdges = hubNode.dynamicEdges.length; var amountOfInitialEdges = hubNode.dynamicEdges.length;
for (var i = 0; i < amountOfInitialEdges; i++) {
edgesIDarray.push(hubNode.dynamicEdges[i].id);
for (var j = 0; j < amountOfInitialEdges; j++) {
edgesIDarray.push(hubNode.dynamicEdges[j].id);
} }
for (var i = 0; i < amountOfInitialEdges; i++) {
var edge = this.edges[edgesIDarray[i]];
// we loop over all edges INITIALLY connected to this hub
for (var j = 0; j < amountOfInitialEdges; j++) {
var edge = this.edges[edgesIDarray[j]];
var childNode = this.nodes[(edge.fromId == hubNode.id) ? edge.toId : edge.fromId]; var childNode = this.nodes[(edge.fromId == hubNode.id) ? edge.toId : edge.fromId];
this._addToCluster(hubNode,childNode,true); this._addToCluster(hubNode,childNode,true);
} }
@ -15350,13 +15370,8 @@ Cluster.prototype._forceClustersByHub = function(hubThreshold) {
} }
} }
this._updateNodeIndexList(); this._updateNodeIndexList();
this._updateDynamicEdges();
//this._updateDynamicEdges();
this._updateLabels(); this._updateLabels();
if (this.moving != isMovingBeforeClustering) {
this.start();
}
}; };
@ -15374,9 +15389,11 @@ Cluster.prototype._addToCluster = function(parentNode, childNode, forceLevelColl
// join child node in the parent node // join child node in the parent node
parentNode.containedNodes[childNode.id] = childNode; parentNode.containedNodes[childNode.id] = childNode;
/*
if (forceLevelCollapse == false) { if (forceLevelCollapse == false) {
parentNode.dynamicEdgesLength += childNode.dynamicEdges.length - 2; parentNode.dynamicEdgesLength += childNode.dynamicEdges.length - 2;
} }
*/
for (var i = 0; i < childNode.dynamicEdges.length; i++) { for (var i = 0; i < childNode.dynamicEdges.length; i++) {
var edge = childNode.dynamicEdges[i]; var edge = childNode.dynamicEdges[i];
@ -15384,7 +15401,6 @@ Cluster.prototype._addToCluster = function(parentNode, childNode, forceLevelColl
this._addToContainedEdges(parentNode,childNode,edge); this._addToContainedEdges(parentNode,childNode,edge);
} }
else { else {
console.log('connecting edge to cluster');
this._connectEdgeToCluster(parentNode,childNode,edge); this._connectEdgeToCluster(parentNode,childNode,edge);
} }
} }
@ -15405,9 +15421,10 @@ Cluster.prototype._addToCluster = function(parentNode, childNode, forceLevelColl
} }
else { else {
parentNode.formationScale = this.scale; // The latest child has been added on this scale parentNode.formationScale = this.scale; // The latest child has been added on this scale
parentNode.dynamicEdgesLength = parentNode.dynamicEdges.length;
} }
parentNode.dynamicEdgesLength = parentNode.dynamicEdges.length;
// recalculate the size of the node on the next time the node is rendered // recalculate the size of the node on the next time the node is rendered
parentNode.clearSizeCache(); parentNode.clearSizeCache();
@ -15641,7 +15658,7 @@ function Graph (container, data, options) {
edges: { edges: {
widthMin: 1, widthMin: 1,
widthMax: 15, widthMax: 15,
width: 1,
width: 10,
style: 'line', style: 'line',
color: '#343434', color: '#343434',
fontColor: '#343434', fontColor: '#343434',

Loading…
Cancel
Save