在D3中点击地图要素时,如何获取所有要素的属性?(含问题代码)
如何在D3中点击地图要素时获取所有要素的属性?
我明白你现在遇到的问题啦——点击哥伦比亚地图里的省份要素时,想要获取所有省份的AREA和PERIMETER属性,但写的代码报错提示properties未定义。这是因为你对D3选择集的遍历方式不对,咱们来一步步解决这个问题:
问题根源
你代码里的polys = effectLayer.selectAll("path")得到的是D3选择集对象,不是普通的DOM元素数组,也不是直接包含GeoJSON数据的数组。用for (x in polys)遍历的话,拿到的是选择集的内部属性(比如_groups、_parents),根本不是每个省份对应的GeoJSON要素数据,自然找不到properties属性。
解决方法
这里有两种靠谱的实现方式,你可以根据自己的代码结构选择:
方法一:初始化时提前保存所有省份数据
在加载GeoJSON并绘制地图的时候,把所有省份的要素数据存起来,点击时直接遍历这个数组:
// 假设你加载GeoJSON的代码框架是这样的 d3.json("colombia.geojson").then(function(geoData) { // 把所有省份的要素数据保存到变量中(可以是全局或闭包变量) const allProvinceData = geoData.features; // 绘制地图路径 effectLayer.selectAll("path") .data(geoData.features) .enter() .append("path") .attr("d", d3.geoPath()) .on("click", handleProvinceClick); // 绑定点击事件 // 点击事件处理函数 function handleProvinceClick() { let resultText = ""; // 遍历提前保存的所有省份数据 allProvinceData.forEach(province => { resultText += `AREA: ${province.properties.AREA}, PERIMETER: ${province.properties.PERIMETER}\n`; }); alert(resultText); } });
方法二:直接从D3选择集中提取绑定的数据
如果不想提前保存数据,也可以用D3提供的.each()方法遍历选择集,直接获取每个路径绑定的GeoJSON要素:
function clicked() { let txt = ""; // 使用D3的.each()遍历选择集中的每个元素 effectLayer.selectAll("path").each(function(provinceFeature) { // provinceFeature就是当前路径绑定的GeoJSON要素对象 txt += `AREA: ${provinceFeature.properties.AREA} | PERIMETER: ${provinceFeature.properties.PERIMETER} \n`; }); alert(txt); }
额外提示
如果你需要在点击时同时获取被点击省份的信息,还可以在clicked函数的参数里拿到当前点击的要素数据,比如:
function clicked(currentProvince) { alert(`你点击的省份AREA是:${currentProvince.properties.AREA}`); // 再获取所有省份的数据... }
内容的提问来源于stack exchange,提问作者Mohsen
相关产品推荐
相关产品推荐

