【问题标题】:How to make to drawing a SVG with D3.js?如何使用 D3.js 绘制 SVG?
【发布时间】:2021-06-21 15:50:13
【问题描述】:

我正在尝试使用我从API 带来的 GEOJSON 数据在 SVG 中绘制地图,SVG 路径充满了数据,但是,SVG 是空白的,正如在执行下面的代码。注意document.write,数据返回正确。

var svg = d3.select("svg")
d3.json('https://api.mocki.io/v1/d214eb47')
    .then(data => {      
       svg.append('g')
          .selectAll('path')
          .data(data.features)
          .enter()
          .append('path')
          .attr('d', d3.geoPath().projection(d3.geoMercator()))

          document.write(JSON.stringify(data));
    })
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/6.6.0/d3.min.js"></script>
<svg  width="600" height="600"></svg>

我用另一个 GEOJSON file 对其进行了测试,并成功地在 SVG 中进行了绘制,如下面的代码所示:

const link = "https://raw.githubusercontent.com/holtzy/D3-graph-gallery/master/DATA/world.geojson";   

var svg = d3.select("svg")

d3.json(link)
        .then(data => {    
         svg.append("g")
        .selectAll("path")
        .data(data.features)
        .enter()
        .append("path")          
          .attr("d", d3.geoPath()
              .projection(d3.geoMercator())
          )
          
         //document.write('data ', JSON.stringify(data))
        
        });
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/6.6.0/d3.min.js"></script>
<svg width="600" height="600"></svg>

有人知道第一个代码sn-p有什么问题吗?

【问题讨论】:

    标签: javascript svg d3.js geojson


    【解决方案1】:

    数据中没有问题,这里的问题只是您尝试绘制一个非常小的区域(旧金山),这与第二个示例中的世界地图不同。也就是说,您应该设置投影的scalecenter。在你的情况下:

    const projection = d3.geoMercator()
        .scale(100000)
        .center([-122.3, 37.75])
    

    生成的代码:

    var svg = d3.select("svg");
    const projection = d3.geoMercator()
      .scale(100000)
      .center([-122.3, 37.75])
    d3.json('https://api.mocki.io/v1/d214eb47')
      .then(data => {
        svg.append('g')
          .selectAll('path')
          .data(data.features)
          .enter()
          .append('path')
          .attr('d', d3.geoPath().projection(projection))
      })
    path {
      fill: wheat;
      stroke: darkslateblue;
    }
    <script src="https://cdnjs.cloudflare.com/ajax/libs/d3/6.6.0/d3.min.js"></script>
    <svg width="600" height="600"></svg>

    但是,将fitExtent 与您的 SVG 宽度和高度一起使用会更容易:

    const projection = d3.geoMercator()
      .fitExtent([
        [0, 0],
        [600, 600]
      ], data)
    

    这是生成的代码:

    var svg = d3.select("svg");
    d3.json('https://api.mocki.io/v1/d214eb47')
      .then(data => {
        const projection = d3.geoMercator()
          .fitExtent([
            [0, 0],
            [600, 600]
          ], data)
        svg.append('g')
          .selectAll('path')
          .data(data.features)
          .enter()
          .append('path')
          .attr('d', d3.geoPath().projection(projection))
      })
    path {
      fill: wheat;
      stroke: darkslateblue;
    }
    <script src="https://cdnjs.cloudflare.com/ajax/libs/d3/6.6.0/d3.min.js"></script>
    <svg width="600" height="600"></svg>

    【讨论】:

      【解决方案2】:

      您的 GeoJSON 文件的显示区域非常小,但在给定的投影和默认的 SVG 视图框中,形状几乎为零。

      检查我如何使用您的地理数据找到 SVG G 元素的边界。然后我用它来定义 SVG viewBox 属性。如果未设置 SVG 宽度或高度,则 SVG 将扩展为可用的“容器”大小。因此,您可以添加周围的 DIV 元素并根据需要设置其大小(将 SVG 放入容器中,从而放入布局中)。

      更新:您甚至可以稍后使用 javascript 更改 SVG viewBox 属性,方法是使用 getBBox() 函数的返回值。另一个答案中的另一种可能性当然也很好(SVG的拟合程度)。

      var svg = d3.select("svg");
      
      const link = "https://api.mocki.io/v1/d214eb47";   
      //const link = "https://raw.githubusercontent.com/holtzy/D3-graph-gallery/master/DATA/world.geojson";   
      
      d3.json(link)
          .then(data => {      
          svg.append('g')
            .selectAll('path')
            .data(data.features)
            .enter()
            .append('path')
            .attr('d', d3.geoPath().projection(d3.geoMercator()));
      
              //console.log(data.features);
              console.log(document.getElementsByTagName("g")[0].getBBox());
        })
      <script src="https://cdnjs.cloudflare.com/ajax/libs/d3/6.6.0/d3.min.js"></script>
      <svg viewBox="152.95315551757812 140.7493133544922 0.421722412109375 0.4228363037109375"></svg>

      【讨论】:

        猜你喜欢
        • 2017-09-03
        • 2012-12-05
        • 2015-01-01
        • 2018-06-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多