D3 TopoJSON渲染工件

问题描述

enter image description here

在我深入兔子洞之前,我注意到我的TopoJSON中有一个相当奇怪的渲染工件,我不知所措。上面呈现的是在TopoJSON World Atlas repository上找到的官方D3发行版countries-110m.json。可以看到,俄罗斯北部的部分地区在加拿大北部的上方似乎向左/向右倒转。在我开始制定计划B之前,我的代码中是否有引起这种情况的东西?

async function drawMap() {
    map_obj = await getRAWMapData(); // Map topojson
    const geojson_obj = topojson.feature(map_obj,map_obj.objects.countries);

    var projection = d3.geoIdentity().fitWidth(width,geojson_obj).reflectY(true); // Map Projection
    var path = d3.geoPath().projection(projection);

    paths = SVGmap.selectAll('path').data(geojson_obj.features).enter().append('path');

    paths
        .attr('d',path)
        .attr('fill','#ddd')
        .attr('stroke','white')
        .attr('stroke-linejoin','round');
} 
drawMap();

解决方法

问题

您正在使用球形数据并将其绘制在平面上(具有d3.geoIdentity),就像数据是平面的一样。

俄罗斯在西半球拥有部分领土-人造物是从远东延伸到远西的路径渲染器,并且在绘制俄罗斯时路径数据越过反子午线时再次延伸。身份转换不会“知道”它应该包裹在一个球体后面-您只是在获取经度和纬度,并将其在屏幕上拉伸,就好像它是2D数据一样。

D3.geoIdentity()拟合方法仅可操纵数据的缩放和平移-无法说明数据的反子午线或地理投影。

解决方案

使用投影-D3地理投影使用球面数学-它们剪切了与反子午线交叉的特征(在本例中为东西向180度)。在这种情况下,俄罗斯将包括两个路径要素:一个在西方,一个在东方。这样可以消除因将两个零件连接到一个零件所需的拉伸而导致的假象。

因此,如果要保持plate carrée的外观,可以使用:

var projection = d3.geoEquirectangular().fitWidth...

任何D3投影都可以使用,d3.geoMercator在外观方面可能会更熟悉。

另一种解决方案是找到已经在反子午线上切过的预投影几何-但是此选项的灵活性远不如使用D3地理投影来投影数据。

相关问答

Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其...
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。...
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbc...