【问题标题】:How to get unique feature properties from geojson source in Mapbox GL JS?如何从 Mapbox GL JS 中的 geojson 源获取独特的特征属性?
【发布时间】:2019-08-25 20:01:13
【问题描述】:

我已经定义了一个 mapbox geojson 来源:

map.addSource("places", {
    type: "geojson",
    data: "http://example.com/myfile.geojson",
});

我的 geojson 源文件有这样的结构:

{
"type": "FeatureCollection",
"features": [{
    "type": "Feature",
    "properties": {
        "icon": "theatre"
    },
    "geometry": {
        "type": "Point",
        "coordinates": [-77.038659, 38.931567]
    }},

    {
    "type": "Feature",
    "properties": {
        "icon": "music"
    },
    "geometry": {
        "type": "Point",
        "coordinates": [-77.020945, 38.878241]
    }},
    ...]
}

我想获得“图标”属性的唯一名称(这里:剧院和音乐)。我如何遍历源以获得这些唯一值?此处的目标是从这些唯一名称中添加一个图层以进行过滤。

【问题讨论】:

    标签: javascript mapbox mapbox-gl-js


    【解决方案1】:

    我找到了here 我的问题的答案。基本上,向源添加一个图层,使用 mapbox 函数 queryRenderedFeatures 获取特征,然后借助专用函数 getUniqueFeatures 获取唯一特征。在我可以遍历 uniqueFeatures 以打印元素之后:

    var features = map.queryRenderedFeatures({layers: ['my_layer']});
    var uniqueFeatures = getUniqueFeatures(features, "icon"); 
    
    uniqueFeatures.forEach(function(feature) {
            var prop = feature.properties;
            console.log(prop.icon);
    })
    

    getUniqueFeatures 函数:

    function getUniqueFeatures(array, comparatorProperty) {
        var existingFeatureKeys = {};
        // Because features come from tiled vector data, feature geometries may be split
        // or duplicated across tile boundaries and, as a result, features may appear
        // multiple times in query results.
        var uniqueFeatures = array.filter(function(el) {
            if (existingFeatureKeys[el.properties[comparatorProperty]]) {
                return false;
            } else {
                existingFeatureKeys[el.properties[comparatorProperty]] = true;
                return true;
            }
        });
    
        return uniqueFeatures;
    }
    

    【讨论】:

    • 注意:queryRenderedFeatures 过滤地图视图中的功能 - 因此,如果数据在地图视图中不可见,您将错过数据。即getUniqueFeatures 将根据地图位置/缩放返回不同的数据。简而言之,您不是“循环遍历源”-而是循环遍历源中当前可见特征的子集。需要注意的是,queryRenderedFeaturesquerySourceFeatures 都有同样的限制。
    【解决方案2】:

    我们可以使用 JavaScript Set 对象来存储唯一值。

    const uniqueIcons = new Set();
    
    const data = {}; // Your JSON data.
    
    data.features.forEach((item) => {
      uniqueIcons.add(item.properties.icon);
    });
    

    示例:

    const uniqueIcons = new Set();
    
    const data = {
      "type": "FeatureCollection",
      "features": [{
          "type": "Feature",
          "properties": {
            "icon": "theatre"
          },
          "geometry": {
            "type": "Point",
            "coordinates": [-77.038659, 38.931567]
          }
        },
    
        {
          "type": "Feature",
          "properties": {
            "icon": "music"
          },
          "geometry": {
            "type": "Point",
            "coordinates": [-77.020945, 38.878241]
          }
        },
        {
          "type": "Feature",
          "properties": {
            "icon": "theatre"
          },
          "geometry": {
            "type": "Point",
            "coordinates": [-77.038659, 38.931567]
          }
        }
      ]
    };
    
    data.features.forEach((item) => {
      uniqueIcons.add(item.properties.icon);
    });
    
    for(let icon of uniqueIcons) {
      console.log(icon);
    }

    【讨论】:

    • 我的数据不是 JSON,它是 GeoJSON 类型的 mapbox 源。
    • 即使这样它也应该工作。您能发布一些示例数据以便我进行测试吗?
    • @Patrick - 查看我回答中的示例。您可以运行它来查看结果。
    • 我的数据不是 geojson 它是一个 mapbox 源。请参阅我编辑的问题中的链接。
    • @Patrick - geojson 数据格式没有什么特别之处。 JavaScript 将其视为另一个 JSON 对象。
    猜你喜欢
    • 1970-01-01
    • 2020-12-22
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-04-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多