将项目添加到地图,一次一个,每个属性 id
add items to map, collectively, one at a time, per attribute id
我已经成功地能够通过属性 id 过滤,例如 shakemaps - 我已经成功地实现了多种方式 - 但都以同样的问题结束。
1.) 与 where 过滤器 2.) 定义表达式 3.)遍历所有属性 ID 并将它们带回来。
问题: 全部只存在 allowing/displaying 每 attribute id
一次..我的目标是养活 attribute ids
进入一个复选框列表(我已经完成),但允许通过属性 id 的项目在被检查时添加到地图中,一次一个地集体检查 - 目前我似乎无法让它与方面一起工作在地图上同时出现多个或多个然后一个。
1.) 即 下面的过滤器(尝试逻辑 1)& CodePen:
.....
function filterByID(event) {
const selectedID = event.target.getAttribute("data-id");
eqLayerView.filter = {
where: "id = '" + selectedID + "'"
};
}
view.whenLayerView(fl)
.then(function(layerView) {
eqLayerView = layerView;
eqLayerView.filter = {
where: "id = ''"
};
.............
2.) 即另一个尝试的逻辑(在这里一次添加多个,逐行,或通过数组):
layer.definitionExpression = "id = 'us70008jr5'",
layer.definitionExpression = "id = 'cgi988jr52'",
3.) 即 第三次尝试在 GIS 交换上提出建议:https://gis.stackexchange.com/questions/364578/loop-through-attribute-ids-of-featurelayer
layer
.load()
.then(() => {
// create a query from the layer
const query = layer.createQuery();
query.returnDistinctValues = true;
query.where = "grid_value > 2"; // or 1=1 if you need them all
// the field you want distinct values for
query.outFields = ["id"];
return layer.queryFeatures(query);
})
.then(({ features }) => {
// extract the ids to a list
const ids = features.map(({ attributes }) => attributes.id);
return ids;
})
.then((ids) => {
// You can store them how you want, in this case,
// I put them in a dropdown select menu
const fragment = document.createDocumentFragment();
ids.forEach((id) => {
const option = document.createElement('option');
option.value = id;
option.innerText = id;
fragment.appendChild(option);
});
list.appendChild(fragment);
map.add(layer);
});
以上所有尝试的逻辑都会导致 attribute id
一次只显示一个摇动图 — 通过打开一个新的,关闭前一个,我需要能够同时显示多个能够立即存在于地图上。
ArcGIS - javascript - 4.15
我很确定我在几周前回答了这个问题,但我找不到我的答案所以也许我只是以为我回答了,那样的话我很抱歉。
无论如何,通过一些修复,您的代码应该可以正常工作。我认为这里的主要问题是如果您要使用复选框,您的查询是不正确的。您需要使用像 IN
这样的集合查询。如果你使用单选按钮我会很好。
这里有你的示例以及我提到的修复,
<!DOCTYPE html>
<html>
<head>
<meta charset='utf-8' />
<meta name='viewport' content='initial-scale=1,maximum-scale=1,user-scalable=no' />
<title>Filter features by attribute - 4.15</title>
<link rel='stylesheet' href='https://js.arcgis.com/4.15/esri/themes/light/main.css' />
<script src='https://js.arcgis.com/4.15/'></script>
<style>
html,
body,
#viewDiv {
padding: 0;
margin: 0;
height: 500px;
width: 100%;
}
</style>
<script>
require([
'esri/views/MapView',
'esri/Map',
'esri/layers/FeatureLayer',
'esri/widgets/Expand'
], function (MapView, Map, FeatureLayer, Expand) {
const layer = new FeatureLayer({
url: 'https://services9.arcgis.com/RHVPKKiFTONKtxq3/arcgis/rest/services/USGS_Seismic_Data_v1/FeatureServer/1/',
outFields: ['*']
, definitionExpression: 'eventTime >= CURRENT_TIMESTAMP - 30 AND grid_value > 2'
});
const map = new Map({
basemap: 'gray-vector'
, layers: [layer]
});
const view = new MapView({
map: map,
container: 'viewDiv',
center: [-98, 40],
zoom: 4
});
let eqLayerView;
let selectedIDs = {};
function updatedFilter() {
const ids = [];
for(const [key, value] of Object.entries(selectedIDs)) {
if (value) {
ids.push(`'${key}'`);
}
}
eqLayerView.filter = {
where: `id IN (${ids.join(',')})`
};
console.log(`[updateFilter] ${eqLayerView.filter.where}`);
}
const idElement = document.getElementById('id-filter');
idElement.addEventListener('click', filterByID);
function filterByID(event) {
const chk = event.target;
console.log(`[filterByID] ${chk.getAttribute('data-id')} ${chk.checked}`);
selectedIDs[chk.getAttribute('data-id')] = chk.checked;
updatedFilter();
}
view.whenLayerView(layer).then(function (layerView) {
eqLayerView = layerView;
updatedFilter();
var query = layer.createQuery();
query.outFields = ['id'];
query.returnDistinctValues = true;
query.returnGeometry = false;
layer.queryFeatures(query).then(function (results) {
results.features.map(function (feat) {
let id = feat.attributes['id'];
let opt = document.createElement('input');
opt.type = 'checkbox';
let label = document.createElement('label')
label.innerHTML = id;
opt.className = 'id-item visible-id';
opt.setAttribute('data-id', id);
idElement.appendChild(opt);
idElement.appendChild(label);
selectedIDs[id] = false;
});
});
});
});
</script>
</head>
<body>
<div id='id-filter' class='esri-widget'>
</div>
<div id='viewDiv'></div>
</body>
</html>
顺便说一句,我添加了一些日志供您查看我认为是事件的导入信息。
最后,我使用辅助词典来跟踪要过滤的可见特征。另一种方法是简单地查询所有复选框并将 id
添加到过滤器,如果它是 checked
.
我已经成功地能够通过属性 id 过滤,例如 shakemaps - 我已经成功地实现了多种方式 - 但都以同样的问题结束。
1.) 与 where 过滤器 2.) 定义表达式 3.)遍历所有属性 ID 并将它们带回来。
问题: 全部只存在 allowing/displaying 每 attribute id
一次..我的目标是养活 attribute ids
进入一个复选框列表(我已经完成),但允许通过属性 id 的项目在被检查时添加到地图中,一次一个地集体检查 - 目前我似乎无法让它与方面一起工作在地图上同时出现多个或多个然后一个。
1.) 即 下面的过滤器(尝试逻辑 1)& CodePen:
.....
function filterByID(event) {
const selectedID = event.target.getAttribute("data-id");
eqLayerView.filter = {
where: "id = '" + selectedID + "'"
};
}
view.whenLayerView(fl)
.then(function(layerView) {
eqLayerView = layerView;
eqLayerView.filter = {
where: "id = ''"
};
.............
2.) 即另一个尝试的逻辑(在这里一次添加多个,逐行,或通过数组):
layer.definitionExpression = "id = 'us70008jr5'",
layer.definitionExpression = "id = 'cgi988jr52'",
3.) 即 第三次尝试在 GIS 交换上提出建议:https://gis.stackexchange.com/questions/364578/loop-through-attribute-ids-of-featurelayer
layer
.load()
.then(() => {
// create a query from the layer
const query = layer.createQuery();
query.returnDistinctValues = true;
query.where = "grid_value > 2"; // or 1=1 if you need them all
// the field you want distinct values for
query.outFields = ["id"];
return layer.queryFeatures(query);
})
.then(({ features }) => {
// extract the ids to a list
const ids = features.map(({ attributes }) => attributes.id);
return ids;
})
.then((ids) => {
// You can store them how you want, in this case,
// I put them in a dropdown select menu
const fragment = document.createDocumentFragment();
ids.forEach((id) => {
const option = document.createElement('option');
option.value = id;
option.innerText = id;
fragment.appendChild(option);
});
list.appendChild(fragment);
map.add(layer);
});
以上所有尝试的逻辑都会导致 attribute id
一次只显示一个摇动图 — 通过打开一个新的,关闭前一个,我需要能够同时显示多个能够立即存在于地图上。
ArcGIS - javascript - 4.15
我很确定我在几周前回答了这个问题,但我找不到我的答案所以也许我只是以为我回答了,那样的话我很抱歉。
无论如何,通过一些修复,您的代码应该可以正常工作。我认为这里的主要问题是如果您要使用复选框,您的查询是不正确的。您需要使用像 IN
这样的集合查询。如果你使用单选按钮我会很好。
这里有你的示例以及我提到的修复,
<!DOCTYPE html>
<html>
<head>
<meta charset='utf-8' />
<meta name='viewport' content='initial-scale=1,maximum-scale=1,user-scalable=no' />
<title>Filter features by attribute - 4.15</title>
<link rel='stylesheet' href='https://js.arcgis.com/4.15/esri/themes/light/main.css' />
<script src='https://js.arcgis.com/4.15/'></script>
<style>
html,
body,
#viewDiv {
padding: 0;
margin: 0;
height: 500px;
width: 100%;
}
</style>
<script>
require([
'esri/views/MapView',
'esri/Map',
'esri/layers/FeatureLayer',
'esri/widgets/Expand'
], function (MapView, Map, FeatureLayer, Expand) {
const layer = new FeatureLayer({
url: 'https://services9.arcgis.com/RHVPKKiFTONKtxq3/arcgis/rest/services/USGS_Seismic_Data_v1/FeatureServer/1/',
outFields: ['*']
, definitionExpression: 'eventTime >= CURRENT_TIMESTAMP - 30 AND grid_value > 2'
});
const map = new Map({
basemap: 'gray-vector'
, layers: [layer]
});
const view = new MapView({
map: map,
container: 'viewDiv',
center: [-98, 40],
zoom: 4
});
let eqLayerView;
let selectedIDs = {};
function updatedFilter() {
const ids = [];
for(const [key, value] of Object.entries(selectedIDs)) {
if (value) {
ids.push(`'${key}'`);
}
}
eqLayerView.filter = {
where: `id IN (${ids.join(',')})`
};
console.log(`[updateFilter] ${eqLayerView.filter.where}`);
}
const idElement = document.getElementById('id-filter');
idElement.addEventListener('click', filterByID);
function filterByID(event) {
const chk = event.target;
console.log(`[filterByID] ${chk.getAttribute('data-id')} ${chk.checked}`);
selectedIDs[chk.getAttribute('data-id')] = chk.checked;
updatedFilter();
}
view.whenLayerView(layer).then(function (layerView) {
eqLayerView = layerView;
updatedFilter();
var query = layer.createQuery();
query.outFields = ['id'];
query.returnDistinctValues = true;
query.returnGeometry = false;
layer.queryFeatures(query).then(function (results) {
results.features.map(function (feat) {
let id = feat.attributes['id'];
let opt = document.createElement('input');
opt.type = 'checkbox';
let label = document.createElement('label')
label.innerHTML = id;
opt.className = 'id-item visible-id';
opt.setAttribute('data-id', id);
idElement.appendChild(opt);
idElement.appendChild(label);
selectedIDs[id] = false;
});
});
});
});
</script>
</head>
<body>
<div id='id-filter' class='esri-widget'>
</div>
<div id='viewDiv'></div>
</body>
</html>
顺便说一句,我添加了一些日志供您查看我认为是事件的导入信息。
最后,我使用辅助词典来跟踪要过滤的可见特征。另一种方法是简单地查询所有复选框并将 id
添加到过滤器,如果它是 checked
.