0

I am creating a legend for my chart. I need to dynamically select x values for the different elements, based on the width of the preceding element. I am using getBoundingClientRect() for this. The problem is that it is returning the same values for all the different elements(The value of the first element). I am logging it to console.

var primaryTotal = legend.append('text')
    .attr("x", function () {
        console.log(nameText.node().getBoundingClientRect());
        return ((nameText.node().getBoundingClientRect().right)+100);
    })
    .attr("y", 0)
    .text(function (d) {

        return d["total"] + " " + parameter[DS1].units_scaled;
    })
    .style("fill", function (d) {
        return d["colour"];
    })

nameText is the element that I am drawing before primaryTotal.

    var legend = groups.selectAll('.legend')
    .data(rowObjectArray)
    .enter()
    .append('g')
    .attr("transform", function (d, i) {
        // console.log(d);
        // console.log(i);
        return "translate(0," + ((i * 20) + 20) + ")";
    })

I am appending it to the group created here.

var legendRect = legend.append('rect')
    .attr("x", 0)
    .attr("y", -10)
    .attr("width", 10)
    .attr("height", 10)
    .style("fill", function (d, i) {
        return d["colour"];
    })

var nameText = legend.append('text')
    .attr("x", function () {
        return (legendRect.node().getBoundingClientRect().right);
    })
    .attr("y", 0)
    .text(function (d) {
        return d["name"];
    })
    .style("fill", function (d) {
        return d["colour"];
    })

declaration of nameText and legendRect. They are both elements I am using in my legend.

This is what is getting logged to console....

console log showing the getBoundingClientRect() output

Don't know how to proceed. Any help would be greatly appreciated. Thank you

  • 2
    Since the problem seems to be that `nameText` is always the same element, it would help a lot if you could show its declaration and how it is expected to be updated. – Kaiido May 02 '18 at 02:44
  • @Kaiido I am appending each element of my legend to the 'legend' element that takes in an array as a dataset. The array . (rowObjectArray) contains the data that I want to display in my legend. – amateurcoder May 02 '18 at 13:36
  • I found a temporary fix to it...I don't think it is efficient though.. I am creating arrays that store the element objects and then extracting the getBoundingClientRect().right value from it once it is done being plotted. – amateurcoder May 02 '18 at 16:01

1 Answers1

0

I am creating arrays that store the element objects and then extracting the getBoundingClientRect().right value from it once it is done being plotted.

 var nameTextCoordArray = [];
var nameTextArray = [];
count = 0;

var nameText = legend.append('text')
    .attr("x", function (d, i) {
        return (rectCoordArray[i]);
    })
    .attr("y", 0)
    .text(function (d) {
        nameTextArray[count] = this;
        count = (count + 1);
        return d["name"];
    })
    .style("fill", function (d) {
        return d["colour"];
    })

nameTextCoordArray = getCoordArray(nameTextArray);


var primaryTotal = legend.append('text')
    .attr("x", function (d, i) {
        return d3.max(nameTextCoordArray);
    })
    .attr("y", 0)
    .text(function (d) {
        primaryTotalArray[count] = this;
        count = (count + 1);
        return d["total"] + " " + parameter[DS1].units_scaled;
    })
    .style("fill", function (d) {
        return d["colour"];
    })

The getCoordArray method:

var getCoordArray = function (array) {

var returnArray = [];

for (x in array) {
    returnArray[x] = (array[x].getBoundingClientRect().right + 20);
}
return returnArray;

}

If Anyone can come up with a more efficient solution, please share...Thanks