Browse Source

Merge remote-tracking branch 'origin/develop' into develop

v3_develop
jos 10 years ago
parent
commit
6a5bf3d3a9
11 changed files with 25322 additions and 25378 deletions
  1. +9
    -0
      HISTORY.md
  2. +25130
    -25324
      dist/vis.js
  3. +1
    -1
      dist/vis.min.css
  4. +1
    -11
      docs/graph2d.html
  5. +22
    -8
      docs/network.html
  6. +4
    -5
      examples/network/02_random_nodes.html
  7. +80
    -0
      examples/network/ex.html
  8. +28
    -12
      lib/network/Edge.js
  9. +4
    -4
      lib/network/Network.js
  10. +31
    -3
      lib/network/Node.js
  11. +12
    -10
      lib/timeline/DataStep.js

+ 9
- 0
HISTORY.md View File

@ -4,6 +4,15 @@ http://visjs.org
## not yet released, version 3.4.3-SNAPSHOT ## not yet released, version 3.4.3-SNAPSHOT
### Network
- Fixed nodes not always being unfixed when using allowedToMove.
- Added dragStart and dragEnd events.
- Added edge selection on edge labels.
### Graph2d
- Fixed dataAxis not showing large numbers correctly.
## 2014-10-12, version 3.4.2 ## 2014-10-12, version 3.4.2

+ 25130
- 25324
dist/vis.js
File diff suppressed because it is too large
View File


+ 1
- 1
dist/vis.min.css
File diff suppressed because it is too large
View File


+ 1
- 11
docs/graph2d.html View File

@ -853,17 +853,7 @@ Graph2d.clear({options: true}); // clear options only
</p> </p>
<p> <p>
Here an example on how to listen for a <code>rangeChanged</code> event.
</p>
<pre class="prettyprint lang-js">
Graph2d.on('select', function (properties) {
alert('selected items: ' + properties.nodes);
});
</pre>
<p>
A listener can be removed via the function <code>off</code>:
Here an example on how to listen for a <code>rangeChanged</code> event. A listener can be removed via the function <code>off</code>:
</p> </p>
<pre class="prettyprint lang-js"> <pre class="prettyprint lang-js">

+ 22
- 8
docs/network.html View File

@ -280,17 +280,13 @@ When using a DataSet, the network is automatically updating to changes in the Da
<td>allowedToMoveX</td> <td>allowedToMoveX</td>
<td>Boolean</td> <td>Boolean</td>
<td>no</td> <td>no</td>
<td>If allowedToMoveX is false, then the node will not move from its supplied position.
If an X position has been supplied, it is fixed in the X-direction.
If no X value has been supplied, this argument will not do anything.</td>
<td>If allowedToMoveX is false, then the node will not move in the X direction from its position.</td>
</tr> </tr>
<tr> <tr>
<td>allowedToMoveY</td> <td>allowedToMoveY</td>
<td>Boolean</td> <td>Boolean</td>
<td>no</td> <td>no</td>
<td>If allowedToMoveY is false, then the node will not move from its supplied position.
If an Y position has been supplied, it is fixed in the Y-direction.
If no Y value has been supplied, this argument will not do anything.</td>
<td>If allowedToMoveY is false, then the node will not move in the Y direction from its position.</td>
</tr> </tr>
<tr> <tr>
@ -344,7 +340,7 @@ When using a DataSet, the network is automatically updating to changes in the Da
<td>number</td> <td>number</td>
<td>no</td> <td>no</td>
<td>Horizontal position in pixels. <td>Horizontal position in pixels.
The horizontal position of the node will be fixed.
The horizontal position of the node will be fixed unless combined with the allowedToMoveX:true option.
The vertical position y may remain undefined.</td> The vertical position y may remain undefined.</td>
</tr> </tr>
<tr> <tr>
@ -352,7 +348,7 @@ When using a DataSet, the network is automatically updating to changes in the Da
<td>number</td> <td>number</td>
<td>no</td> <td>no</td>
<td>Vertical position in pixels. <td>Vertical position in pixels.
The vertical position of the node will be fixed.
The vertical position of the node will be fixed unless combined with the allowedToMoveY:true option.
The horizontal position x may remain undefined.</td> The horizontal position x may remain undefined.</td>
</tr> </tr>
</table> </table>
@ -2423,6 +2419,24 @@ network.off('select', onSelect);
</ul> </ul>
</td> </td>
</tr> </tr>
<tr>
<td>dragStart</td>
<td>Fired when a node is being dragged.</td>
<td>
<ul>
<li><code>nodeIds</code>: Array of ids of the nodes that are being dragged</li>
</ul>
</td>
</tr>
<tr>
<td>dragEnd</td>
<td>Fired when the dragging of a node(s) has ended.</td>
<td>
<ul>
<li><code>nodeIds</code>: Array of ids of the nodes that were being dragged</li>
</ul>
</td>
</tr>
<tr> <tr>
<td>stabilized</td> <td>stabilized</td>
<td>Fired every time the network has been stabilized. This event can be used to trigger the .storePosition() function after stabilization. Fired with an object having the following properties:</td> <td>Fired every time the network has been stabilized. This event can be used to trigger the .storePosition() function after stabilization. Fired with an object having the following properties:</td>

+ 4
- 5
examples/network/02_random_nodes.html View File

@ -30,7 +30,7 @@
// randomly create some nodes and edges // randomly create some nodes and edges
var nodeCount = document.getElementById('nodeCount').value; var nodeCount = document.getElementById('nodeCount').value;
for (var i = 0; i < nodeCount; i++) { for (var i = 0; i < nodeCount; i++) {
nodes.push({
nodes.push({
id: i, id: i,
label: String(i) label: String(i)
}); });
@ -69,26 +69,25 @@
connectionCount[to]++; connectionCount[to]++;
} }
} }
// create a network // create a network
var container = document.getElementById('mynetwork'); var container = document.getElementById('mynetwork');
var data = { var data = {
nodes: nodes, nodes: nodes,
edges: edges edges: edges
}; };
var options = {};
var options = {stabilization:false};
network = new vis.Network(container, data, options); network = new vis.Network(container, data, options);
// add event listeners // add event listeners
network.on('select', function(params) { network.on('select', function(params) {
document.getElementById('selection').innerHTML = 'Selection: ' + params.nodes; document.getElementById('selection').innerHTML = 'Selection: ' + params.nodes;
console.log(params)
}); });
network.on('stabilized', function (params) { network.on('stabilized', function (params) {
document.getElementById('stabilization').innerHTML = 'Stabilization took ' + params.iterations + ' iterations.'; document.getElementById('stabilization').innerHTML = 'Stabilization took ' + params.iterations + ' iterations.';
doFocus = false;
}); });
} }
</script> </script>
</head> </head>

+ 80
- 0
examples/network/ex.html View File

@ -0,0 +1,80 @@
<!doctype html>
<html>
<head>
<title>Network | Random nodes</title>
<style type="text/css">
body {
font: 10pt sans;
}
#mynetwork {
width: 600px;
height: 600px;
border: 1px solid lightgray;
}
</style>
<script type="text/javascript" src="../../dist/vis.js"></script>
<link href="../../dist/vis.css" rel="stylesheet" type="text/css" />
<script type="text/javascript">
var nodes = null;
var edges = null;
var network = null;
function draw() {
nodes = new vis.DataSet([
{id: '1001', value: '1'},
{id: '1009', value: '2'},
{id: '1061', value: '3'},
{id: '1226', value: '4'}
]);
edges = new vis.DataSet([
{id: '1001_1061', from: '1001', to: '1061'},
{id: '1001_1226', from: '1001', to: '1226'},
{id: '1009_1061', from: '1009', to: '1061'},
{id: '1009_1226', from: '1009', to: '1226'},
{id: '1061_1226', from: '1061', to: '1226'}
]);
var container = document.getElementById('mynetwork');
var data = {
nodes: nodes,
edges: edges
};
var options = {
nodes: {
shape: 'dot'
},
edges: {
inheritColor: false
},
physics: {
'barnesHut': {
centralGravity: 0.5,
springLength: 150,
springConstant: 0.03,
damping: 0.2
}
}
};
network = new vis.Network(container, data, options);
// add event listeners
network.on('select', function(params) {
document.getElementById('selection').innerHTML = 'Selection: ' + params.nodes;
console.log(params.edges)
console.log(network.getSelection())
});
}
</script>
</head>
<body onload="draw();">
<br>
<div id="mynetwork"></div>
<p id="selection"></p>
</body>
</html>

+ 28
- 12
lib/network/Edge.js View File

@ -38,6 +38,7 @@ function Edge (properties, network, networkConstants) {
this.value = undefined; this.value = undefined;
this.selected = false; this.selected = false;
this.hover = false; this.hover = false;
this.labelDimensions = {top:0,left:0,width:0,height:0};
this.from = null; // a node this.from = null; // a node
this.to = null; // a node this.to = null; // a node
@ -547,22 +548,26 @@ Edge.prototype._label = function (ctx, text, x, y) {
// TODO: cache the calculated size // TODO: cache the calculated size
ctx.font = ((this.from.selected || this.to.selected) ? "bold " : "") + ctx.font = ((this.from.selected || this.to.selected) ? "bold " : "") +
this.options.fontSize + "px " + this.options.fontFace; this.options.fontSize + "px " + this.options.fontFace;
ctx.fillStyle = this.options.fontFill;
var lines = String(text).split('\n'); var lines = String(text).split('\n');
var lineCount = lines.length; var lineCount = lines.length;
var fontSize = (Number(this.options.fontSize) + 4); var fontSize = (Number(this.options.fontSize) + 4);
var yLine = y + (1 - lineCount) / 2 * fontSize; var yLine = y + (1 - lineCount) / 2 * fontSize;
var width = ctx.measureText(lines[0]).width;
for (var i = 1; i < lineCount; i++) {
var lineWidth = ctx.measureText(lines[i]).width;
width = lineWidth > width ? lineWidth : width;
}
var height = this.options.fontSize * lineCount;
var left = x - width / 2;
var top = y - height / 2;
this.labelDimensions = {top:top,left:left,width:width,height:height};
if (this.options.fontFill !== undefined && this.options.fontFill !== null && this.options.fontFill !== "none") { if (this.options.fontFill !== undefined && this.options.fontFill !== null && this.options.fontFill !== "none") {
var width = ctx.measureText(lines[0]).width;
for (var i = 1; i < lineCount; i++) {
var lineWidth = ctx.measureText(lines[i]).width;
width = lineWidth > width ? lineWidth : width;
}
var height = this.options.fontSize * lineCount;
var left = x - width / 2;
var top = y - height / 2;
ctx.fillStyle = this.options.fontFill;
ctx.fillRect(left, top, width, height); ctx.fillRect(left, top, width, height);
} }
@ -918,6 +923,7 @@ Edge.prototype._drawArrow = function(ctx) {
* @private * @private
*/ */
Edge.prototype._getDistanceToEdge = function (x1,y1, x2,y2, x3,y3) { // x3,y3 is the point Edge.prototype._getDistanceToEdge = function (x1,y1, x2,y2, x3,y3) { // x3,y3 is the point
var returnValue = 0;
if (this.from != this.to) { if (this.from != this.to) {
if (this.options.smoothCurves.enabled == true) { if (this.options.smoothCurves.enabled == true) {
var xVia, yVia; var xVia, yVia;
@ -943,10 +949,10 @@ Edge.prototype._getDistanceToEdge = function (x1,y1, x2,y2, x3,y3) { // x3,y3 is
} }
lastX = x; lastY = y; lastX = x; lastY = y;
} }
return minDistance
returnValue = minDistance;
} }
else { else {
return this._getDistanceToLine(x1,y1,x2,y2,x3,y3);
returnValue = this._getDistanceToLine(x1,y1,x2,y2,x3,y3);
} }
} }
else { else {
@ -963,7 +969,17 @@ Edge.prototype._getDistanceToEdge = function (x1,y1, x2,y2, x3,y3) { // x3,y3 is
} }
dx = x - x3; dx = x - x3;
dy = y - y3; dy = y - y3;
return Math.abs(Math.sqrt(dx*dx + dy*dy) - radius);
returnValue = Math.abs(Math.sqrt(dx*dx + dy*dy) - radius);
}
if (this.labelDimensions.left < x3 &&
this.labelDimensions.left + this.labelDimensions.width > x3 &&
this.labelDimensions.top < y3 &&
this.labelDimensions.top + this.labelDimensions.height > y3) {
return 0;
}
else {
return returnValue;
} }
}; };

+ 4
- 4
lib/network/Network.js View File

@ -853,6 +853,8 @@ Network.prototype._handleDragStart = function() {
this._selectObject(node,false); this._selectObject(node,false);
} }
this.emit("dragStart",{nodeIds:this.getSelection().nodes});
// create an array with the selected nodes and their original location and status // create an array with the selected nodes and their original location and status
for (var objectId in this.selectionObj.nodes) { for (var objectId in this.selectionObj.nodes) {
if (this.selectionObj.nodes.hasOwnProperty(objectId)) { if (this.selectionObj.nodes.hasOwnProperty(objectId)) {
@ -898,10 +900,10 @@ Network.prototype._handleOnDrag = function(event) {
return; return;
} }
// remove the focus on node if it is focussed on by the focusOnNode
this.releaseNode(); this.releaseNode();
var pointer = this._getPointer(event.gesture.center); var pointer = this._getPointer(event.gesture.center);
var me = this; var me = this;
var drag = this.drag; var drag = this.drag;
var selection = drag.selection; var selection = drag.selection;
@ -966,7 +968,7 @@ Network.prototype._onDragEnd = function () {
else { else {
this._redraw(); this._redraw();
} }
this.emit("dragEnd",{nodeIds:this.getSelection().nodes});
}; };
/** /**
@ -2074,7 +2076,6 @@ Network.prototype._animationStep = function() {
var renderTime = Date.now(); var renderTime = Date.now();
this._redraw(); this._redraw();
this.renderTime = Date.now() - renderTime; this.renderTime = Date.now() - renderTime;
}; };
if (typeof window !== 'undefined') { if (typeof window !== 'undefined') {
@ -2110,7 +2111,6 @@ Network.prototype.start = function() {
} }
else { else {
this._redraw(); this._redraw();
if (this.stabilizationIterations > 0) { if (this.stabilizationIterations > 0) {
// trigger the "stabilized" event. // trigger the "stabilized" event.
// The event is triggered on the next tick, to prevent the case that // The event is triggered on the next tick, to prevent the case that

+ 31
- 3
lib/network/Node.js View File

@ -42,6 +42,8 @@ function Node(properties, imagelist, grouplist, networkConstants) {
this.id = undefined; this.id = undefined;
this.x = null; this.x = null;
this.y = null; this.y = null;
this.allowedToMoveX = false;
this.allowedToMoveY = false;
this.xFixed = false; this.xFixed = false;
this.yFixed = false; this.yFixed = false;
this.horizontalAlignLeft = true; // these are for the navigation controls this.horizontalAlignLeft = true; // these are for the navigation controls
@ -64,7 +66,6 @@ function Node(properties, imagelist, grouplist, networkConstants) {
this.damping = networkConstants.physics.damping; // written every time gravity is calculated this.damping = networkConstants.physics.damping; // written every time gravity is calculated
this.fixedData = {x:null,y:null}; this.fixedData = {x:null,y:null};
this.setProperties(properties, constants); this.setProperties(properties, constants);
// creating the variables for clustering // creating the variables for clustering
@ -183,8 +184,23 @@ Node.prototype.setProperties = function(properties, constants) {
} }
} }
this.xFixed = this.xFixed || (properties.x !== undefined && !properties.allowedToMoveX);
this.yFixed = this.yFixed || (properties.y !== undefined && !properties.allowedToMoveY);
if (properties.allowedToMoveX !== undefined) {
this.xFixed = !properties.allowedToMoveX;
this.allowedToMoveX = properties.allowedToMoveX;
}
else if (properties.x !== undefined && this.allowedToMoveX == false) {
this.xFixed = true;
}
if (properties.allowedToMoveY !== undefined) {
this.yFixed = !properties.allowedToMoveY;
this.allowedToMoveY = properties.allowedToMoveY;
}
else if (properties.y !== undefined && this.allowedToMoveY == false) {
this.yFixed = true;
}
this.radiusFixed = this.radiusFixed || (properties.radius !== undefined); this.radiusFixed = this.radiusFixed || (properties.radius !== undefined);
if (this.options.shape == 'image') { if (this.options.shape == 'image') {
@ -193,6 +209,7 @@ Node.prototype.setProperties = function(properties, constants) {
} }
// choose draw method depending on the shape // choose draw method depending on the shape
switch (this.options.shape) { switch (this.options.shape) {
case 'database': this.draw = this._drawDatabase; this.resize = this._resizeDatabase; break; case 'database': this.draw = this._drawDatabase; this.resize = this._resizeDatabase; break;
@ -211,6 +228,7 @@ Node.prototype.setProperties = function(properties, constants) {
} }
// reset the size of the node, this can be changed // reset the size of the node, this can be changed
this._reset(); this._reset();
}; };
/** /**
@ -334,6 +352,10 @@ Node.prototype.discreteStep = function(interval) {
this.vx += ax * interval; // velocity this.vx += ax * interval; // velocity
this.x += this.vx * interval; // position this.x += this.vx * interval; // position
} }
else {
this.fx = 0;
this.vx = 0;
}
if (!this.yFixed) { if (!this.yFixed) {
var dy = this.damping * this.vy; // damping force var dy = this.damping * this.vy; // damping force
@ -341,6 +363,10 @@ Node.prototype.discreteStep = function(interval) {
this.vy += ay * interval; // velocity this.vy += ay * interval; // velocity
this.y += this.vy * interval; // position this.y += this.vy * interval; // position
} }
else {
this.fy = 0;
this.vy = 0;
}
}; };
@ -360,6 +386,7 @@ Node.prototype.discreteStepLimited = function(interval, maxVelocity) {
} }
else { else {
this.fx = 0; this.fx = 0;
this.vx = 0;
} }
if (!this.yFixed) { if (!this.yFixed) {
@ -371,6 +398,7 @@ Node.prototype.discreteStepLimited = function(interval, maxVelocity) {
} }
else { else {
this.fy = 0; this.fy = 0;
this.vy = 0;
} }
}; };

+ 12
- 10
lib/timeline/DataStep.js View File

@ -180,16 +180,18 @@ DataStep.prototype.previous = function() {
*/ */
DataStep.prototype.getCurrent = function() { DataStep.prototype.getCurrent = function() {
var toPrecision = '' + Number(this.current).toPrecision(5); var toPrecision = '' + Number(this.current).toPrecision(5);
for (var i = toPrecision.length-1; i > 0; i--) {
if (toPrecision[i] == "0") {
toPrecision = toPrecision.slice(0,i);
}
else if (toPrecision[i] == "." || toPrecision[i] == ",") {
toPrecision = toPrecision.slice(0,i);
break;
}
else{
break;
if (toPrecision.indexOf(",") != -1 || toPrecision.indexOf(".") != -1) {
for (var i = toPrecision.length-1; i > 0; i--) {
if (toPrecision[i] == "0") {
toPrecision = toPrecision.slice(0,i);
}
else if (toPrecision[i] == "." || toPrecision[i] == ",") {
toPrecision = toPrecision.slice(0,i);
break;
}
else{
break;
}
} }
} }

Loading…
Cancel
Save