HattrickNZ HattrickNZ - 5 months ago 8x
HTML Question

d3 + positioning data lables in bar chart + top, middle, bottom, center

This is my fiddle, which I am building with from this example

this is the code that I got to add the text labels

.attr("class", "barText")
.attr("x", function(d) { return x(d.letter); })
.attr("y", function(d) { return y(d.frequency); })
.text(function(d) { return Math.floor(d.frequency*100)+"%"; });

How do I control the position of the label so that it sits:

  1. inside the bar

  2. on top of the bar

  3. the bottom of the bar

  4. and always being in the center of the bar

Ideally I don't want it hard coded, just want it dynamic coded.

This is my attempt, but is there a better/other way?

// appears central(of xaxis of bar) but only in this example not sure how dynamic it would be

.attr("x", function(d) { return x(d.letter) + x.rangeBand()/5; })

//label appears slightly above the bar

.attr("y", function(d) { return y(d.frequency) - 10; })


Might be useful for me to go through this

here is my code and fiddle to put the rect and text in the 1 group. But not sure how to control the text labels reslative to the bar using this method, other than using the below answer?

//create a bar group for the bar and the labels
barGroup = svg.append("g")
.attr("class", "barGroup")

.attr("class", "bar")
.attr("x", function(d) { return x(d.letter); })
.attr("width", x.rangeBand())
.attr("y", function(d) { return y(d.frequency); })
.attr("height", function(d) { return height - y(d.frequency); });

.attr("class", "barText")
.attr("x", function(d) { return x(d.letter); })
.attr("y", function(d) { return y(d.frequency); })
.text(function(d) { return d.frequency; });

  1. inside the bar: .attr("y", function(d) { return Math.min(y(d.frequency) + 10, height); })

  2. on top of the bar: .attr("y", function(d) { return y(d.frequency); })

  3. bottom of the bar: .attr("y", height)

  4. center of the bar: .attr("y", function(d) { return y(d.frequency/2); })


to align horizontally, use text-anchor: middle, and align text with the bar like so:

text.barText { text-anchor: middle; }

.attr("x", function(d) { return x(d.letter) + x.rangeBand()/2; })