Domanda

I am a noob with d3.js. I am using topoJSON data to render maps and so far it's been working great. Now I want to overlay some data such as text or circles on top of each country/region and I am hitting a wall. I have code similar to this:

var countries = g.append("g")
    .attr("id", "countries")
    .selectAll("path")
    .data(topojson.feature(collection, collection.objects.countries).features)
    .enter().append("path")
    .attr("d", path)
    .style("fill", colorize)
    .attr("class", "country")
    .on("click", clicked)

which properly renders my map. In order to overlay some circles on it, I do the following:

countries
    .append("circle")
    .attr("r", function(d, i, j) {
      return 10; // for now
    })
    // getCentroid below is a function that returns the 
    // center of the poligon/path bounding box
    .attr("cy", function(d, i, j) { return getCentroid(countries[0][j])[0]})
    .attr("cx", function(d, i, j) { return getCentroid(countries[0][j])[1]})
    .style("fill", "red")

Which is pretty cumbersome (specially the way it accesses the countries array), but it succeeds at appending a circle for each path representing a country. The problem is that the circle exists in the SVG markup, but doesn't show up at all in the document. I am obviously doing something wrong, but I am at a loss of what is it.

È stato utile?

Soluzione

The problem is that you're appending the circle elements to path elements, which you can't do in SVG. You need to append them to the parent g elements. The code would look something like this.

var countries = g.selectAll("g.countries")
  .data(topojson.feature(collection, collection.objects.countries).features)
  .enter().append("g")
  .attr("id", "countries");

countries.append("path")
  .datum(function(d) { return d; })
  .attr("d", path)
  // etc

countries.append("circles")
  // etc
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top