Search code examples
javascriptd3.jsvoronoi

How to properly resize voronoi in a reponsive chart


I have a responsive line chart made with d3, but have problem resizing the voronoi used for hover state. I suspect I don't refer to it the right way...

I added the voronoi here:

var voronoiGroup = svg.append("g")

.attr("class", "voronoi");

voronoiGroup.selectAll("line")
.data(voronoi(d3.nest()
      .key(function(d) { return xScale(d.date) + "," + yScale(d.value); })
      .rollup(function(v) { return v[0]; })
      .entries(d3.merge(ranksFiltered.map(function(d) { return d.values;})))
      .map(function(d) { return d.values; })))
.enter()

.append("path")
   .attr("id", "cells")
  .attr("d", function(d) { return "M" + d.join("L") + "Z"; })
  .datum(function(d) { return d.point; });

and in my resize function, I attempt to redraw it:

  svg.select("#cells path")
  .attr("d", function(d) { return "M" + d.join("L") + "Z"; })
  .datum(function(d) { return d.point; });;

If someone wants to take a stab at it, there's a plunk here:

http://plnkr.co/edit/Jj4QpF1bqK901WalNMmR

Thanks for you time!


Solution

  • The Voronoi Geom is calculating pixel positions in relation to the clipExtent. Since you are changing your width (the clipextent), you need to rerun the calculations. This is one of the few times with d3 that I'd recommend just remove the paths under your voronoi group and re-adding them:

            voronoi.clipExtent([[0, -10], [width+10, height]]);
            voronoiGroup.selectAll("path").remove();
    
            voronoiGroup.selectAll("cells")
              .data(voronoi(vd))
              .enter()
              .append("path")
              .attr("class", "cells")
              .attr("d", function(d) { return "M" + d.join("L") + "Z"; })
              .datum(function(d) { return d.point; })
              .attr("stroke", "red")
              .on("mouseover", mouseover)
              .on("mouseout", mouseout);
    

    Updated plunker.