我正在制作带有标记的传单 map 。我正在从一个文件中获取标记经纬度数据,该文件每 5 秒更新一次,其中包含大约 100 个标记的新位置数据。
然后,我使用 switch 将标记分成 2 组,并在 map 上用不同的图标表示。
我的问题是,每次更新新的位置数据时都会创建新的标记,但旧的标记仍然存在,因此不久之后就会出现标记的踪迹,并且 map 变得非常慢。
我想在每次创建新标记时清除旧标记,并尝试使用clearLayers()函数但没有效果。没有错误,但标记仍然存在。我已将 clearLayers() 移至代码中的其他级别,以使其不起作用或完全删除所有标记(包括任何新标记)。
geojson.js
async function getData() {
const response = await fetch('../../Export.log');
var data = await response.text();
var formatted = JSON.parse('[' + data.trim().replace(/\n/g, ',') + ']')
var enemyForces = L.layerGroup().addTo(map);
var alliedForces = L.layerGroup().addTo(map);
alliedForces.clearLayers();
enemyForces.clearLayers();
for (var i = 0; i < formatted.length; i++){
var unit = formatted[i];
var coalition = unit.coalition;
var Lat = unit.Lat;
var Long = unit.Long;
var LatLong = [Lat, Long];
var LongLat = [Long, Lat];
var name = unit.name;
var ID = unit.ID;
switch (coalition) {
case "Enemies":
L.marker([Lat, Long], {icon: enemyIcon}).bindPopup(name + "<br>" + coalition + "<br>" + ID).addTo(enemyForces);
break;
case "Allies":
L.marker([Lat, Long], {icon: alliedIcon}).bindPopup(name + "<br>" + coalition + "<br>" + ID).addTo(alliedForces);
} // End switch
} // End for
}
getData();
setInterval(getData, 5000);
index.html
<!DOCTYPE html>
<html>
<head>
<title>Test Map</title>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<link rel="shortcut icon" type="image/x-icon" href="/favicon.ico" />
<link rel="stylesheet" href="https://unpkg.com/<a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="2a464f4b4c464f5e6a1b041c041a" rel="noreferrer noopener nofollow">[email protected]</a>/dist/leaflet.css" integrity="sha512-xwE/Az9zrjBIphAcBb3F6JVqxf46+CDLwfLMHloNu6KEQCAWi6HcDUbeOfBIptF7tcCzusKFjFw2yuvEpDL9wQ==" crossorigin=""/>
<script src="https://unpkg.com/<a href="https://stackoverflow.com/cdn-cgi/l/email-protection" class="__cf_email__" data-cfemail="aec2cbcfc8c2cbdaee9f8098809e" rel="noreferrer noopener nofollow">[email protected]</a>/dist/leaflet.js" integrity="sha512-gZwIG9x3wUXg2hdXF6+rVkLF/0Vi9U8D2Ntg4Ga5I5BZpVkVxlJWbSQtXPSiUTtC0TjtGOmxa1AJPuV0CPthew==" crossorigin=""></script>
<style>
html, body {
height: 100%;
margin: 0;
}
#map {
width: 100%;
height: 100%;
}
</style>
</head>
<body>
<div id='map'></div>
<script src="js/geojson.js" type="text/javascript"></script>
<script src="js/map.js" type="text/javascript"></script>
</body>
</html>
map .js
// Start Map
var map = L.map('map').setView([33.5, -117.0], 7);
L.tileLayer('https://api.mapbox.com/styles/v1/{id}/tiles/{z}/{x}/{y}?access_token=pk.eyJ1IjoibWFwYm94IiwiYSI6ImNpejY4NXVycTA2emYycXBndHRqcmZ3N3gifQ.rJcFIG214AriISLbB6B5aw', {
maxZoom: 18,
attribution: 'Map data © <a href="https://www.openstreetmap.org/">OpenStreetMap</a> contributors, ' +
'<a href="https://creativecommons.org/licenses/by-sa/2.0/">CC-BY-SA</a>, ' +
'Imagery © <a href="https://www.mapbox.com/">Mapbox</a>',
id: 'mapbox/light-v9',
tileSize: 512,
zoomOffset: -1
}).addTo(map);
var unitIcon = L.Icon.extend({
options: {
iconSize: [32, 37],
iconAnchor: [0, 0],
popupAnchor: [0, -5]
}
});
var alliedIcon = new unitIcon({iconUrl: 'img/ally.png'}),
enemyIcon = new unitIcon({iconUrl: 'img/enemy.png'});
function onEachFeature(feature, layer) {
// does this feature have a property named popupContent?
if (feature.properties && feature.properties.popupContent) {
layer.bindPopup(feature.properties.popupContent);
}
}
导出.log
{"ID" : 50, "name" : "Blue1", "coalition" : "Allies", "Lat" : 33.331, "Long" : -117.162, "Alt" : 10.160897, "heading" : 6.283185}
{"ID" : 51, "name" : "Red1", "coalition" : "Enemies", "Lat" : 33.374, "Long" : -116.835, "Alt" : 0.045466, "heading" : 4.879922}
{"ID" : 52, "name" : "Blue2", "coalition" : "Allies", "Lat" : 33.783, "Long" : -117.228, "Alt" : 6.703342, "heading" : 3.078192}
最佳答案
每次调用getData
时,您都会创建一个全新的enemyForces
和alliedForces
。您正在将其添加到 map 中。当您运行 switch 语句时,if 会修改当前函数闭包的 enemyForces
和 alliedForces
,但不会影响之前函数闭包中的那些变量。将这些变量声明移到函数之外。
// move these definitions outside of your function
var enemyForces = L.layerGroup().addTo(map);
var alliedForces = L.layerGroup().addTo(map);
async function getData(){
...
enemyForces.clearLayers();
alliedForces.clearLayers();
for (...){
...
switch (coalition) {
case "Enemies":
L.marker([Lat, Long], {icon: enemyIcon}).bindPopup(...).addTo(enemyForces);
break;
case "Allies":
L.marker([Lat, Long], {icon: alliedIcon}).bindPopup(...).addTo(alliedForces);
} // end switch
} // end for
}
编辑:
更改了答案。使用 clearLayer
就足够了,无需调用 remove()
关于javascript - 新位置数据之前的传单 map 标记clearLayers(),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/62646569/