Visualize Data with a Bar Chart - Can't pass test #13

Hello everyone,

I am able to pass all the tests except for the final test (#13/14). I think i am misunderstanding what I need to accomplish. The goal is for the tooltip to have a “data-date” property that corresponds to the “data-date” of the active area. Can the community please take a look and provide some guidance?

Here is the link to CodePen:
CodePen link

Part of the code relevant to my question:

d3.json(url)
  .then(data => {
    // get data from url
    const years = data.data.map(item => new Date (item[0]))
    const dataset = data.data
    
    // create a div tooltip that will be triggered when a mouse hovers over
    const tooltip = d3.select("body")
        .append("div")
        .attr("id","tooltip")
        .style("position", "absolute")
        .style("z-index", "10")
        .style("visibility", "hidden")
        .style("background", "lightblue")
        .style("pointer-events", "none")
        .attr("data-date", function (d,i) {  // why is this wrong?
           return dataset[i][0];
        })
            
    // create svg object
    const svg = d3.select("body")
      .append("svg")
      .attr("width", width + margin.left + margin.right)
      .attr("height", height + margin.top + margin.bottom)
      .attr("class","svg")
      .append("g")
      .attr("transform", "translate(" + margin.left + ", " + margin.top + ")")
   
    // scale data
    let xScale = d3.scaleTime()
      .domain([d3.min(years),d3.max(years)])
      .range([0, width])

    const yScale = d3.scaleLinear()
      .domain([0, d3.max(dataset, (d) => d[1])])
      .range([height, 0]);

    // add rectangles to the bar chart
    svg.selectAll("rect")
      .data(dataset)
      .enter()
      .append("rect")
      .attr("class", "bar")
      .attr("data-date", (d,i) => dataset[i][0]) // what's the point of this line? I added it just to pass the test.
      .attr("data-gdp", (d,i) => dataset[i][1]) //  ditto!
      .attr("x", (d, i) => i*(width/dataset.length)) // x value is tied directly to the width of SVG and the number of values in the data set. Bars will be evenly spaced.
      .attr("y", (d, i) => yScale(d[1]))
      .attr("width", width/dataset.length - barPadding) // set as a fraction of the SVG width and number of data points, minus a padding value
      .attr("height",  (d, i) => height-yScale(d[1]))
      .on("mouseover", function(d,i){
        tooltip.text("GDP:"+this.getAttribute("data-gdp")+ "\nDate:"+this.getAttribute("data-date") )
        return tooltip.style("visibility", "visible");
      })
      .on("mousemove", function(){
        return tooltip.style("top", (event.pageY-100)+"px")
                      .style("left",(event.pageX+10)+"px");
      })
      .on("mouseout", function(){
        return tooltip.style("visibility", "hidden");
      });  

Challenge: Data Visualization Projects - Visualize Data with a Bar Chart

Link to the challenge:

¡Hola!

@ nocrecimientonovalor

El siguiente codigo en su ubicacion actual siempre tendra el valor "1947-01-01", por lo que puedes eliminarlo y moverlo dentro de la funcion "mouseover".

.attr("data-date", function (d,i) {  // why is this wrong?
   return dataset[i][0];
})

Revisando el codigo que ya tienes puedes hacerlo de la siguiente forma:

.on("mouseover", function(d,i){
  tooltip
     .attr("data-date", this.getAttribute("data-date"))
     .text("GDP:" + this.getAttribute("data-gdp") + "\nDate:" + this.getAttribute("data-date"))     
     return tooltip.style("visibility", "visible");
})

saludos

1 Like

This is wrong because there is no data to iterate over and so there is no datum or index to provide to the function you’ve defined. This attribute has to be defined where you manipulate the tooltip when you are iterating over the data while creating the bars.

These are required to pass the tests. You have to set the data-date attribute of each rect so it can be compared to the same attribute in the tooltip. Be aware that you should be using the index (i) as little as possible since the datum is passed in as d. You don’t have to look it up in dataset every iteration.

Here is where you should define any dynamic tooltip attributes. Again, it’s faster to use the datum passed in as d as opposed to using this.getAttribute().

1 Like

Muchas gracias. Su sugerencia es muy apreciada.

Thank you for explaining why this piece of code is wrong:

.attr("data-date", function (d,i) {  // why is this wrong?
      return dataset[i][0];
}

Also thank you for pointing out that using index (i) uses resources. Going forward, i will try to minimize its use. Good to know that this.getAttribute() is undesirable.

Appreciate your response.

This topic was automatically closed 182 days after the last reply. New replies are no longer allowed.