var margin = {top: 0, right: 0, bottom: 0, left: 0}, width = 960, height = 500, diameter = Math.min(width, height), radius = diameter / 2; var tree = d3.layout.balloon() .size([width, height]) .value(function(d) { return d.size; }) .gap(function(d) { return d.externalLinkCount * 50; }); var bundle = d3.layout.bundle(); var vis = d3.select("#vis").append("svg") .attr("width", width + margin.left + margin.right) .attr("height", height + margin.top + margin.bottom) .append("g") .attr("transform", "translate(" + (margin.left + radius) + "," + (margin.top + radius) + ")"); var nodes, node, links, nodeData, linkData, data; function draw() { var line = d3.svg.line() .interpolate("bundle") .tension(0.95) .x(function(d) { return d.lx; }) .y(function(d) { return d.ly; }); var link = vis.selectAll("path.link") .data(links); link.enter().append("path") .attr("class", "link"); d3.selectAll("path.link") .transition() .duration(1500) .attr("d", line); node = vis.selectAll("circle.node") .data(nodes, function(d) { return d.name; }); node.enter().append("circle") .attr("class", "node"); d3.selectAll("circle.node") .transition() .duration(1500) .attr("r", function(d) { return d.r; }) .attr("cx", function(d) { return d.x; }) .attr("cy", function(d) { return d.y; }); } function resetLayout() { nodes = tree.nodes(nodeData); links = bundle(linkData); } function randInt(from, to) { return Math.floor(from + Math.random() * (to - from + 1)); } function flipCoin(tosses) { return Math.floor(Math.random() * 2 * (tosses || 1)) == 1; } function pickRandomNode() { return data[randInt(0, data.length)]; } function pickRandomSize() { return randInt(4000, 20000); } function walkToAddRandomNode(d) { var children = d.children; if (!children) return false; var n = children.length; if (flipCoin(n)) { d.children.push({ "name": d.name + "." + randInt(0, 200), "size": pickRandomSize() }); return true; } else { var added = false, i = -1; while (++i < n && !added) { if (walkToAddRandomNode(children[i])) added = true; } } } function addRandomNode() { walkToAddRandomNode(nodeData); } function resizeRandomNode() { d = pickRandomNode(); d.size = pickRandomSize(); } function addOrResizeRandomNode() { (flipCoin() ? resizeRandomNode : addRandomNode)(); resetLayout(); draw(); } d3.json("./readme.json", function(json) { data = json; nodeData = packages.root(data); linkData = packages.imports(data); resetLayout(); draw(); setInterval(addOrResizeRandomNode, 2000); });