JSFiddle - React, Tailwind, and code Playground
CSS
svg {
border: 1px dashed #ccc;
}
JavaScript
(function(){
/// generate some ipsum data ///
var id = 0;
function generateFakeData(depth, childrenMin, childrenMax)
{
var data = {
id: id++,
children: []
};
if ( --depth > 0 ) {
var childrenCount = Math.floor(Math.random()*(childrenMax-childrenMin)+childrenMin);
for (var i=0; i < childrenCount; i++) {
data.children.push(generateFakeData(depth, childrenMin, childrenMax));
};
};
return data;
}
var data = generateFakeData(5, 3, 4);
/// actual code ///
var margin = 20,
width = 350 - margin*2,
height = 500 - margin*2;
var container = d3.select('body');
var zoom = d3.behavior.zoom();
zoom.on('zoom', function(){
var scale = d3.event.scale;
svg.attr('transform', 'translate('+d3.event.translate+') scale('+scale+')');
}).scaleExtent([0.2, 2]);
var svg = container.append('svg')
.attr('width', width+margin*2)
.attr('height', height+margin*2)
.call(zoom)
.append('g')
.attr('transform', 'translate('+margin+','+margin+')');
var diagonal = d3.svg.diagonal()
.projection(function(d) { return [d.y, d.x]; });
var tree = d3.layout.tree()
.size([height, width]);
draw(data);
function draw(source) {
svg.attr('opacity', '0');
var leafsNumber = countLeafs(source),
nodeHeight = 10;
var newHeight = leafsNumber * (nodeHeight + nodeHeight/2) + margin*2;
tree = tree.size([ newHeight, width]);
var nodes = tree.nodes(source),
links = tree.links(nodes);
nodes.forEach(function(node){
node.y = node.depth * 50;
});
svg.selectAll('.link')
.data(links)
.enter()
.append('path')
.attr('class', 'link')
.attr('fill', 'none')
...