Merge branch 'review'
* review: Avoid divide by zero and massive forces at small distances Renamed f -> a. f is actually representing acceleration. A few updates based on code review by amcameron add review comments for springyui.js Add some code review comments.
This commit is contained in:
commit
9a196f8673
17
springy.js
17
springy.js
|
@ -310,7 +310,7 @@ Layout.ForceDirected.prototype.applyCoulombsLaw = function() {
|
|||
if (point1 !== point2)
|
||||
{
|
||||
var d = point1.p.subtract(point2.p);
|
||||
var distance = d.magnitude() + 1.0;
|
||||
var distance = d.magnitude() + 0.1; // avoid massive forces at small distances (and divide by zero)
|
||||
var direction = d.normalise();
|
||||
|
||||
// apply force to each end point
|
||||
|
@ -343,22 +343,27 @@ Layout.ForceDirected.prototype.attractToCentre = function() {
|
|||
|
||||
Layout.ForceDirected.prototype.updateVelocity = function(timestep) {
|
||||
this.eachNode(function(node, point) {
|
||||
point.v = point.v.add(point.f.multiply(timestep)).multiply(this.damping);
|
||||
point.f = new Vector(0,0);
|
||||
// Is this, along with updatePosition below, the only places that your
|
||||
// integration code exist?
|
||||
point.v = point.v.add(point.a.multiply(timestep)).multiply(this.damping);
|
||||
point.a = new Vector(0,0);
|
||||
});
|
||||
};
|
||||
|
||||
Layout.ForceDirected.prototype.updatePosition = function(timestep) {
|
||||
this.eachNode(function(node, point) {
|
||||
// Same question as above; along with updateVelocity, is this all of
|
||||
// your integration code?
|
||||
point.p = point.p.add(point.v.multiply(timestep));
|
||||
});
|
||||
};
|
||||
|
||||
// Calculate the total kinetic energy of the system
|
||||
Layout.ForceDirected.prototype.totalEnergy = function(timestep) {
|
||||
var energy = 0.0;
|
||||
this.eachNode(function(node, point) {
|
||||
var speed = point.v.magnitude();
|
||||
energy += speed * speed;
|
||||
energy += 0.5 * point.m * speed * speed;
|
||||
});
|
||||
|
||||
return energy;
|
||||
|
@ -488,11 +493,11 @@ Layout.ForceDirected.Point = function(position, mass) {
|
|||
this.p = position; // position
|
||||
this.m = mass; // mass
|
||||
this.v = new Vector(0, 0); // velocity
|
||||
this.f = new Vector(0, 0); // force
|
||||
this.a = new Vector(0, 0); // acceleration
|
||||
};
|
||||
|
||||
Layout.ForceDirected.Point.prototype.applyForce = function(force) {
|
||||
this.f = this.f.add(force.divide(this.m));
|
||||
this.a = this.a.add(force.divide(this.m));
|
||||
};
|
||||
|
||||
// Spring
|
||||
|
|
|
@ -34,6 +34,7 @@ jQuery.fn.springy = function(params) {
|
|||
|
||||
var canvas = this[0];
|
||||
var ctx = canvas.getContext("2d");
|
||||
|
||||
var layout = this.layout = new Layout.ForceDirected(graph, stiffness, repulsion, damping);
|
||||
|
||||
// calculate bounding box of graph layout.. with ease-in
|
||||
|
@ -82,6 +83,8 @@ jQuery.fn.springy = function(params) {
|
|||
selected = nearest = dragged = layout.nearest(p);
|
||||
|
||||
if (selected.node !== null) {
|
||||
// Part of the same bug mentioned later. Store the previous mass
|
||||
// before upscaling it for dragging.
|
||||
dragged.point.m = 10000.0;
|
||||
}
|
||||
|
||||
|
@ -102,6 +105,9 @@ jQuery.fn.springy = function(params) {
|
|||
});
|
||||
|
||||
jQuery(window).bind('mouseup',function(e) {
|
||||
// Bug! Node's mass isn't reset on mouseup. Nodes which have been
|
||||
// dragged don't repulse very well. Store the initial mass in mousedown
|
||||
// and then restore it here.
|
||||
dragged = null;
|
||||
});
|
||||
|
||||
|
@ -122,6 +128,7 @@ jQuery.fn.springy = function(params) {
|
|||
};
|
||||
|
||||
Node.prototype.getHeight = function() {
|
||||
// Magic number with no explanation.
|
||||
return 20;
|
||||
};
|
||||
|
||||
|
|
Loading…
Reference in New Issue
Block a user