How can I add title text to this chart in d3? - d3.js

I'm following this tutorial for a D3 Circle Pack chart. https://bl.ocks.org/denjn5/6d5ddd4226506d644bb20062fc60b53f
How can I add the text from the ID column of the CSV to each circle?

Instead of creating a circle, you can create a group and have a circle and a text inside it.
So instead of:
// Draw on screen
vSlices.attr('cx', function (d) { return d.x; })
.attr('cy', function (d) { return d.y; })
.attr('r', function (d) { return d.r; });
You would do:
var gNode = vSlices
.enter()
.append("g")
.attr("transform", function(d) {
return "translate(" + d.x + "," + d.y + ")";
});
gNode.append("circle").attr("r", function(d) {
return d.r;
});
gNode
.append("text")
.style("font", "10px sans-serif")
.attr("text-anchor", "middle")
.text(function(d) {
return d.data.id;
});
Notice that the translation is being done in the group and the attributes are different.
I hope it helps.

Related

d3.js migrate sankey drag and drop funcitonality to v4

Anyone managed to make the example
Sankey diagram with horizontal and vertical node movement
work in v4
since sankey.relayout() is not available anymore
d3.drag has no .origin anymore.
My attempt do the wildest things while attempting to drag a node and since some behaviors have changed in both sankey and drag specifications I'm unable to figure how to migrate the example to v4.
var graph = { "nodes": [...], "links": [...] };
var layout = d3.sankey();
layout
.extent([[1, 1], [width - 1, height - 6]])
.nodeId(function (d) {
return d.id;
})
.nodeWidth(12)
.nodePadding(padding)
.nodeAlign(d3.sankeyRight)
layout(graph);
// Add Links
var link = svg.append("g")
.attr("fill", "none")
.selectAll(".link")
.data(graph.links)
.enter()
.append("g")
.attr("class", "link")
link.append("path")
.attr("d", d3.sankeyLinkHorizontal())
.attr("stroke", "#000")
.style("stroke-width", function (d) {
return d.width;
})
.append("title")
.text("Some text");
// Drag behavior for node elements
var drag = d3.drag()
//.origin(function (d) { return d; }) // Deprecated but maybe unnecessary
.on("drag", dragmove)
// Add nodes
var node = svg.append("g")
.selectAll(".node")
.data(graph.nodes)
.enter()
.append("g")
.attr("transform", function (d) {
return "translate(" + [d.x0, d.y0] + ")";
})
.call(drag) // The g element should be now draggable
// Add element inside g element
node.append("rect")
.attr("height", function (d) { return d.y1 - d.y0; })
.attr("width", function (d) { return d.x1 - d.x0; })
.attr("fill", ...)
node.append("text")
.attr("x", function (d) { return (d.x1 - d.x0) - 6; })
.attr("y", function (d) { return (d.y1 - d.y0) / 2; })
.attr("dy", "0.35em")
.attr("text-anchor", "end")
.text(function (d) { return d.name; })
.filter(function (d) { return d.x0 < width / 2; })
.attr("x", function (d) { return (d.x1 - d.x0) + 6 })
.attr("text-anchor", "start");
// Called by d3.drag
function dragmove(d) {
var dx = Math.round(d.x = Math.max(0, Math.min(width , evt.x)));
var dy = Math.round(d.y = Math.max(0, Math.min(height, evt.y)));
d3.select(this).attr("transform", "translate(" + [dx, dy] + ")")
// Now should redraw the links but
sankey.relayout(); // not a function anymore.
// path references sankey.link() that is also deprecated in v4 in
// favour of d3.sankeyLinkHorizontal() ? (I'm not sure)
// link references the g element containing the path elements
// classed .link
link.attr("d", path);
};

How to fit text inside nodes at bottom in pack layout in d3?

I created d3 pack layout.Text is added in nodes. Requirement is text should be fit in circular nodes in such way that Text should be at bottom, proportional to node size and should be fit inside node.but text is either overlapping or hides behind another node or not proportional to nodes as in JSFiddle examples
http://jsfiddle.net/oo66o0q0/11/,
http://jsfiddle.net/oo66o0q0/12/,
http://jsfiddle.net/oo66o0q0/13/
.So how to resolve all issue with one code?
function treeLayout(nodes){
var node = diagramLayout.selectAll(".node");
node = node.data(nodes.descendants(), function(d) {
return d.uid;
});
var nodeEnter = node.enter().append("g")
.attr("class", "node")
.attr("height", nodeHeight)
.attr("width", nodeWidth)
nodeEnter.append("circle")
.attr("id", function(d) { return "node-" + d.data.name; })
.attr("r", function(d) { return d.r; })
.style("fill", function(d) { return color(d.depth); });
nodeEnter.attr("transform", function(d) { return "translate(" + d.x + "," + d.y + ")"; });
var nodeText = nodeEnter.append("text")
.text(function(d) { return d.data.name; })
.attr("clip-path", function(d) { return "url(#clip-" + d.data.name + ")"; })
.style("text-anchor", "middle")
.style("stroke", "#000")
.style("stroke-width", "0.1px")
.attr("y", function(d) {
return d.r-(d.r/d.data.name.length);
})
.style("font-family", "sans-serif")
.style("font-size", function(d) {
return d.r/(d.data.name.length)+ "px";
})
}
}

How to add text to Cluster Force Layout bubbles

I am trying to add some text from the name field in my JSON file to each bubble in a cluster.
https://plnkr.co/edit/hwxxG34Z2wYZ0bc51Hgu?p=preview
I have added what I thought was correct attributes to the nodes with
node.append("text")
.text(function (d) {
return d.name;
})
.attr("dx", -10)
.attr("dy", "5em")
.text(function (d) {
return d.name
})
.style("stroke", "white");
function tick(e) {
node.each(cluster(10 * e.alpha * e.alpha))
.each(collide(.5))
.attr("transform", function (d) {
var k = "translate(" + d.x + "," + d.y + ")";
return k;
})
}
Everything works fine except the labels.
What am I missing here?
Thanks
Kev
For that you will need to make a group like this:
var node = svg.selectAll("g")
.data(nodes)
.enter().append("g").call(force.drag);//add drag to the group
To the group add circle.
var circles = node.append("circle")
.style("fill", function(d) {
return color(d.cluster);
})
To the group add text:
node.append("text")
.text(function(d) {
return d.name;
})
.attr("dx", -10)
.text(function(d) {
return d.name
})
.style("stroke", "white");
Add tween to the circle in group like this:
node.selectAll("circle").transition()
.duration(750)
.delay(function(d, i) {
return i * 5;
})
.attrTween("r", function(d) {
var i = d3.interpolate(0, d.radius);
return function(t) {
return d.radius = i(t);
};
});
Now the tick method will translate the group and with the group the circle and text will take its position.
working code here
The problem: a text SVG element cannot be child of a circle SVG element.
The solution is creating another selection for the texts:
var nodeText = svg.selectAll(".nodeText")
.data(nodes)
.enter().append("text")
.text(function (d) {
return d.name;
})
.attr("text-anchor", "middle")
.style("stroke", "white")
.call(force.drag);
Here is the plunker: https://plnkr.co/edit/qnx7CQox0ge89zBL9jxc?p=preview

How to position path to node center in tree layout

I have created a cluster tree layout and I want to add custom node styles to selected nodes. To be more precise, I'm adding treemap as node.
I managed to add those, but they are not positioned in the center of node.
I have tried all sort of x,y attributes and translations but I quess I don't get svg that much yet.
Part of code where I add the node is here (for JSfiddle see below):
nodeEnter.each(function(d) {
if (d.status == "D") {
var treemap = d3.layout.treemap()
.size([20, 20])
.sticky(true)
.value(function(d) {
return 1;
});
var cell = d3.select(this)
.selectAll("g")
.data(function(d) {
return treemap.nodes(d.annotations);
})
.enter().append("g")
.attr("class", "cell")
.attr("transform", function(d) {
return "translate(" + d.x + "," + d.y + ")";
});
cell.append("rect")
.attr("width", function(d) {
return d.dx;
})
.attr("height", function(d) {
return d.dy;
})
.style("fill", function(d) {
return d.children ? null : hex2rgb(color(d.parent.name));
});
}
})
Any help would be appreciated
Here is my JSfiddle.
L.
Assuming you wanted the lines to connect to the middle of the appended rect. I just added a third .attr to your JSfiddle
cell.append("rect")
.attr("width", function(d) {
return d.dx;
})
.attr("height", function(d) {
return d.dy;
})
.attr("transform","translate(0,-10)")
.style("fill", function(d) {
return d.children ? null : hex2rgb(color(d.parent.name));
});

Tooltip in bubble chart using d3.js

I am using d3.js for bubble chart.its working fine but i need to write custom tool tip for the data which i am showing.currently i just appended one title tag so it just showing one data with tooltip
what if i have more data to show and want to show in form of a table.
Here is my code.
d3.json("data/bubble.json", function(error, root) {
var node = svg.selectAll(".node")
.data(bubble.nodes(classes(root))
.filter(function(d) { return !d.children; }))
.enter().append("g")
.attr("class", "node")
.attr("transform", function(d) { return "translate(" + d.x + "," + d.y + ")"; });
node.append("title")
.text(function(d) { return d.className + ": " + format(d.value); });
node.append("circle")
.attr("r", function(d) { return d.r; })
.style("fill", function(d) { return color(d.packageName); });
node.append("text")
.attr("dy", ".3em")
.style("text-anchor", "middle")
.text(function(d) { return d.className.substring(0, d.r / 3); });
});

Resources