如何使用 Bootleaf/esri-leaflet 查询具有多边形图层的点?

How to query points with a polygon layer using Bootleaf / esri-leaflet?

我正在使用 Bootleaf IAG framework.

我不知道如何获取过滤层的边界坐标。

我正在修改 bootleaf 代码以使用多边形图层查询点。查询小部件已经允许用户绘制多边形,但我想 select 从我的 arcgis 服务器上托管的图层绘制多边形。我通过删除文本字段并允许我的用户从下拉菜单中 select 多边形图层和值来修改过滤器小部件。这很好用。

现在我需要获取 layer.setWhere(where, handleError); 代码的结果并将其与下面的查询一起使用。我需要 selectedPolygon 等于 layer.setWhere(where, handleError); 的结果,并在查询的 .within 部分使用边界坐标。

我尝试了很多东西,L.latLngBoundsgetBounds()toGeoJSON().features[0].geometry.coordinates 等等,但我不知道如何拉出界限。正确的代码是什么?

    const query = L.esri.query({ url: pointInPolygonUrl })
        .token(pointInPolygonData.token)
        .within(selectedPolygon)
    query.run(function (error, data, response) {
        if (error) {
            console.log(error);
            return;
        }

6/8/2021 编辑(基于 Seth Lutske 的评论:

我没有提供代码沙箱有两个原因:1 - bootleaf 有很多文件,2 - 我的所有图层都需要安全登录到 arcgis。希望我能提供足够的信息以在没有它的情况下获得帮助。

  1. selectedPolygon 是否改变了我的预期方式?目前有 没有变量叫 selectedPolygon 因为我想不通 格式化它的正确方法。 selectedPolygon是我想要的 调用过滤结果 layer.setWhere(where, handleError);。我设置 随着值的变化,多边形图层在地图上过滤。我 可以验证它是否按预期过滤。

  2. selectedPolygon 格式 - 这就是我的问题所在。我不能 似乎根据 bootleaf 层的方式找到了正确的格式 配置。我从 var selectedPolygon = 开始 layer.features.geometry.coordinates; 并得到一个未定义的几何体 错误。我继续尝试我能想到的所有其他代码 界限。

  3. 边界坐标 可能不是正确的术语。我想要 运行 查询以查找过滤后的多边形内的所有点。 为此,我的理解是我需要使用 查询的 within 部分中过滤的多边形的边界。

2021 年 6 月 8 日编辑 #2

link 可能最有利于展示图层的构造方式。我修改了这段代码以删除文本输入并添加一个下拉列表,但基本定义应该是相同的。

第 1605 行是 function addFilter()

第 1804 行是 function applyFilter()

第 1927 行是 layer.setWhere(where, handleFilterError);

照片 1:console.log("polygon layer", layer)

Photo 1

照片 2:展开 _layers

Photo 2

图3:展开_rings(我没有找到ToGetJSON,但我在这个部分找到了ToGeoJSON

Photo 3

看起来如果我能达到_rings就应该没问题,但这就是我所缺乏的知识。

我对 bootleaf 了解不多,但这里有一些帮助您入门的提示。根据您的问题和评论,这有望澄清问题并指导您如何在您的场景中应用您需要的内容。

挂钩 UI 到 setWhere

当用户从 UI 中选择一个选项时,您可以在您从 arcgis server 提供的图层上调用 setWhere。假设有一个多边形层,在我的示例中,称为 statesFeatureLayer,其中 is an L.esri.featureLayer

// Create polygon layer of states
const statesFeatureLayer = EL.featureLayer({
  url: "polygon_featurelayer_url_from_arcgis_server"
}).addTo(map);

还有一个点层:

// Create points layer
const pointsFeatureLayer = EL.featureLayer({
  url: "points_featurelayer_url"
}).addTo(map);

现在有一些UI,必须触发setWhere才能在这一层调用。所以在 UI 的任何地方你想要 运行 在层上设置过滤器的这个功能,然后根据结果查询其他层,我们将 运行 一个函数调用runQuery:

function runQuery(){
  statesFeatureLayer.setWhere(querystring, callback)
}

运行 setWhere 触发后的回调

听起来您已经弄清楚了这一部分,并且您的 setWhere 功能 运行 正确。但是,setWhere 还采用可选的回调函数作为其第二个参数,在设置 where 并刷新图层后 运行s。让我们深入研究一下。在回调中,我们将要获取地图上当前处于活动状态的所有要素:

function runQuery(){
  statesFeatureLayer.setWhere(querystring, () => {
    statesFeatureLayer.eachActiveFeature(feature => {
      // do something with features
    })
  })
}

运行 查询以针对多边形图层的活动要素测试点图层

eachActiveFeature 内,我们可以 运行 查询 pointsFeatureLayer:

function runQuery(){
  statesFeatureLayer.setWhere(querystring, () => {
    statesFeatureLayer.eachActiveFeature(feature => {
      pointsFeatureLayer
        .query()
        .within(feature.toGeoJSON())
        .run((error, data) => {
          console.log(data);
        });
    })
  })
}

现在我们正在 运行 查询 pointsFeatureLayer 中位于 statesFeatureLayer.[=41= 的每个活动特征的几何中的任何点]

这样做的缺点是我们无法 运行 将所有活动功能作为一个组进行查询。 within 查询方法(以及大多数其他 query methods)可以接受奇异特征,无论是 L.Polygon、L.Polyline 还是 L.GeoJSON.虽然我曾尝试创建一个 L.featureGroup 并在其上调用 .toGeoJSON,但 within 似乎需要一个仅描述单个形状的 GeoJSON。因此,如果您有多个功能,则必须将它们整合在一起。例如,您可能在全局范围级别有一些变量 results = [],然后在 run 的回调中,您可以将结果推送到 results,这将把所有结果集中在一起多变的。这可能需要在 js 中进行一些修改才能正确完成。

Working Codesandbox

此处有 2 个 UI 个元素导致 runQuery 到 运行。下拉列表或复选框。您会看到,在每次 UI 更改时,都会使用从 UI 构建的查询字符串调用 setWhere ).当 setWhere 被调用时,它的回调然后 运行 仅针对当前活动的特征对点层进行查询,然后 returns 来自点层的任何点都是 within 每个活跃的特征。