d3 中地图行为的基准数据差异
Datum-Data difference in map behavior in d3
我是 d3js 的新手,正在尝试了解使用数据和数据将数据附加到元素之间的区别。我已经在网上阅读了一些 material,我想我在理论上理解发生了什么,但我仍然缺乏直观的理解。具体来说,我有一个案例,我正在使用 topojson 创建地图。我正在使用 d3js v7.
首先,我使用以下代码在 div 中创建地图(假设高度、宽度、投影等设置正确):
var svg = d3.select("div#map").append("svg")
.attr("width", width)
.attr("height", height)
.attr("transform", "translate(" + 15 + "," + 0 + ")");
var path = d3.geoPath()
.projection(projection);
var mapGroup = svg.append("g");
d3.json("json/world-110m.json").then(function(world){
console.log(topojson.feature(world, world.objects.land))
mapGroup.append("path")
.datum(topojson.feature(world, world.objects.land))
.attr("class", "land")
.attr("d", path);
});
topojson 功能的控制台日志如下所示:
地图效果很好(在 css 文件中指定了样式):
但是如果我将 datum 更改为 data,地图就会消失。我正在努力提高我对它是如何工作的理解,在阅读了我可以在网上找到的内容后,我有点挣扎。谁能解释一下在这种情况下使用的数据和数据之间的区别,以及为什么一个有效而另一个无效?
感谢您的帮助!
data()
和 datum()
之间存在一些差异,但是对于 你的问题的范围 主要区别在于 data()
接受只有 3 件事:
- 一个数组;
- 一个函数;
- 无(在这种情况下,它是 getter);
如你所见,topojson.feature(world, world.objects.land)
是一个对象。因此,您需要在这里使用 data()
(同样,不是惯用的 D3,我只是在解决您的具体问题)是用数组包装它:
.data([topojson.feature(world, world.objects.land)])
这是您使用 data()
的代码:
var svg = d3.select("div#map").append("svg")
.attr("width", 500)
.attr("height", 300)
.attr("transform", "translate(" + 15 + "," + 0 + ")");
var path = d3.geoPath();
var mapGroup = svg.append("g");
d3.json("https://raw.githubusercontent.com/d3/d3.github.com/master/world-110m.v1.json").then(function(world) {
const projection = d3.geoEqualEarth()
.fitExtent([
[0, 0],
[500, 300]
], topojson.feature(world, world.objects.land));
path.projection(projection);
mapGroup.append("path")
.data([topojson.feature(world, world.objects.land)])
.attr("class", "land")
.attr("d", path);
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js"></script>
<script src="https://unpkg.com/topojson@3"></script>
<div id="map"></div>
我是 d3js 的新手,正在尝试了解使用数据和数据将数据附加到元素之间的区别。我已经在网上阅读了一些 material,我想我在理论上理解发生了什么,但我仍然缺乏直观的理解。具体来说,我有一个案例,我正在使用 topojson 创建地图。我正在使用 d3js v7.
首先,我使用以下代码在 div 中创建地图(假设高度、宽度、投影等设置正确):
var svg = d3.select("div#map").append("svg")
.attr("width", width)
.attr("height", height)
.attr("transform", "translate(" + 15 + "," + 0 + ")");
var path = d3.geoPath()
.projection(projection);
var mapGroup = svg.append("g");
d3.json("json/world-110m.json").then(function(world){
console.log(topojson.feature(world, world.objects.land))
mapGroup.append("path")
.datum(topojson.feature(world, world.objects.land))
.attr("class", "land")
.attr("d", path);
});
topojson 功能的控制台日志如下所示:
地图效果很好(在 css 文件中指定了样式):
但是如果我将 datum 更改为 data,地图就会消失。我正在努力提高我对它是如何工作的理解,在阅读了我可以在网上找到的内容后,我有点挣扎。谁能解释一下在这种情况下使用的数据和数据之间的区别,以及为什么一个有效而另一个无效?
感谢您的帮助!
data()
和 datum()
之间存在一些差异,但是对于 你的问题的范围 主要区别在于 data()
接受只有 3 件事:
- 一个数组;
- 一个函数;
- 无(在这种情况下,它是 getter);
如你所见,topojson.feature(world, world.objects.land)
是一个对象。因此,您需要在这里使用 data()
(同样,不是惯用的 D3,我只是在解决您的具体问题)是用数组包装它:
.data([topojson.feature(world, world.objects.land)])
这是您使用 data()
的代码:
var svg = d3.select("div#map").append("svg")
.attr("width", 500)
.attr("height", 300)
.attr("transform", "translate(" + 15 + "," + 0 + ")");
var path = d3.geoPath();
var mapGroup = svg.append("g");
d3.json("https://raw.githubusercontent.com/d3/d3.github.com/master/world-110m.v1.json").then(function(world) {
const projection = d3.geoEqualEarth()
.fitExtent([
[0, 0],
[500, 300]
], topojson.feature(world, world.objects.land));
path.projection(projection);
mapGroup.append("path")
.data([topojson.feature(world, world.objects.land)])
.attr("class", "land")
.attr("d", path);
});
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/5.7.0/d3.min.js"></script>
<script src="https://unpkg.com/topojson@3"></script>
<div id="map"></div>