Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Charge based on size - d3 force layout

I'm trying to make a force directed graph using d3.layout.force, and I need the container to be resizable - that is I'd like to be able calculate appropriate charge and linkDistance values based on the size, or have d3 do it for me in some magical way.

I've made an attempt (link: http://jsfiddle.net/VHdUe/6/) which only uses nodes. I'm setting the charge to a value that's based on the number of nodes that would fit across the radius of the circle that it tends to be shaped like.

The solution works for some middle-sized containers, but if you click resize a few times, you can see it doesn't really work for all sizes...

The only way forward I can see is using an svg scale transform, which will mess up the size of my elements unfavorable. Any other options?

PS: I have seen http://mbostock.github.com/d3/talk/20110921/bounding.html (the answer to D3 force directed layout with bounding box), but I'd rather have a gravity-based solution than a bounding box one.

like image 596
XwipeoutX Avatar asked Mar 28 '12 05:03

XwipeoutX


1 Answers

In addition to charge and linkDistance, you also have gravity. If you want the graph to maintain the same relative density to the layout size, then you'll want to scale both charge and gravity. These are the main two computing forces that determine the overall size of the blob. See my force layout talk for more details.

I tried a few different versions, and this one seemed to work pretty well:

var k = Math.sqrt(nodes.length / (width * height));

layout
    .charge(-10 / k)
    .gravity(100 * k)

Here nodes.length / (width * height) is linearly proportional to the graph density: the area of the nodes divided by the area of the layout. The charge force follows the inverse-square law, so that might explain why the square root works well. D3's "gravity" is a virtual spring that scales linearly with distance from the layout center, so this also increases the gravity as the graph becomes denser and discourages nodes from escaping the bounding box.

like image 95
mbostock Avatar answered Sep 23 '22 15:09

mbostock