我有一个页面,给用户一个选择,他可以切换我显示的传单地图。
在初始传单地图加载后,我的问题是当我想要刷新地图时。
我总是得到#34;地图容器已经初始化":
问题在于:
var map = L.map('mapa').setView([lat, lon], 15);
最初它加载得很好,但是当我在表单中选择另一个参数并希望再次显示地图时它会崩溃。
顺便说一下,我试图在第二个$('#mapa')
之前使用jQuery销毁并重新创建setView()
,但它显示相同的错误。
答案 0 :(得分:83)
在尝试重新加载地图之前尝试map.remove();
。这将使用Leaflet的库(而不是jquery' s)删除以前的地图元素。
答案 1 :(得分:19)
<强> HTML 强>
<div id="weathermap"></div>
<强> JavaScript的:强>
function buildMap(lat,lon) {
document.getElementById('weathermap').innerHTML = "<div id='map' style='width: 100%; height: 100%;'></div>";
var osmUrl = 'http://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png',
osmAttribution = 'Map data © <a href="http://openstreetmap.org">OpenStreetMap</a> contributors,' +
' <a href="http://creativecommons.org/licenses/by-sa/2.0/">CC-BY-SA</a>',
osmLayer = new L.TileLayer(osmUrl, {maxZoom: 18, attribution: osmAttribution});
var map = new L.Map('map');
map.setView(new L.LatLng(lat,lon), 9 );
map.addLayer(osmLayer);
var validatorsLayer = new OsmJs.Weather.LeafletLayer({lang: 'en'});
map.addLayer(validatorsLayer);
}
我用这个:
document.getElementById('weathermap').innerHTML = "<div id='map' style='width: 100%; height: 100%;'></div>";
重新加载渲染地图的div内容。
答案 2 :(得分:18)
最好的方式
map.off();
map.remove();
你应该添加map.off(),它也可以更快地运行,并且不会导致事件出现问题
答案 3 :(得分:5)
我结束时没有重新绘制地图,但打印一次并重新绘制每个新的ajax调用上的点,所以问题是如何清理旧点并仅打印新点。我结束了这样做:
var point = L.marker([new_marker[0], new_marker[1]]).addTo(map).bindPopup('blah blah');
points.push(point);
//points is a temporary array where i store the points for removing them afterwards
所以,在每次新的ajax调用,之前绘制新点时,我会执行以下操作:
for (i=0;i<points.length;i++) {
map.removeLayer(points[i]);
}
points=[];
到目前为止,非常好: - )
答案 4 :(得分:5)
当您删除地图时,它会破坏div id引用,因此,在remove()之后,您需要再次构建将显示地图的div,以避免出现&#34; Uncaught Error:Map未找到容器&#34;。
if(map != undefined || map != null){
map.remove();
$("#map").html("");
$("#preMap").empty();
$( "<div id=\"map\" style=\"height: 500px;\"></div>" ).appendTo("#preMap");
}
答案 5 :(得分:3)
在初始化地图检查之前,地图已经启动或未启动
var container = L.DomUtil.get('map');
if(container != null){
container._leaflet_id = null;
}
答案 6 :(得分:3)
如果您想更新地图视图(例如更改地图中心),则不必删除然后重新创建地图,只需更新坐标
const mapInit = () => {
let map.current = w.L.map('map');
L.tileLayer('http://{s}.tile.osm.org/{z}/{x}/{y}.png', {
attribution: '© <a href="http://osm.org/copyright" target="_blank">OpenStreetMap</a> contributors'
}).addTo(map.current);
}
const setCoordinate = (gps_lat, gps_long) => {
map.setView([gps_lat, gps_long], 13);
}
initMap();
setCoordinate(50.403723 30.623538);
setTimeout(() => {
setCoordinate(51.505, -0.09);
}, 3000);
答案 7 :(得分:1)
我遇到了同样的问题。然后我设置全局地图变量,例如var map = null,然后为显示地图我检查
if(map==null)then map=new L.Map('idopenstreet').setView();
通过此解决方案,您的地图将在该地图将由L.Map填充后第一次初始化,然后它将不为空。所以没有像地图容器已初始化那样的错误。
答案 8 :(得分:1)
切换页面时,我在角度上遇到了同样的问题。我必须在离开页面之前添加此代码才能使其正常工作:
$scope.$on('$locationChangeStart', function( event ) {
if(map != undefined)
{
map.remove();
map = undefined
document.getElementById('mapLayer').innerHTML = "";
}
});
如果没有document.getElementById('mapLayer').innerHTML = ""
,地图就不会显示在下一页上。
答案 9 :(得分:1)
答案 10 :(得分:1)
在初始化地图之前,检查地图是否已经启动
var container = L.DomUtil.get('map');
if(container != null){
container._leaflet_id = null;
}
对我有用
答案 11 :(得分:0)
我在 reactjs 中做到了这一点
// Create map (dev = reuse existing map)
let myMap = L.DomUtil.get('map');
if(myMap == null){
myMap = L.map('mapid').setView(currentLocation, zoom);
}
答案 12 :(得分:0)
我遇到了同样的问题,所以我在地图实例中创建了一个方法来重新加载它。
var map = L.map('mapa').setView([lat, lon], 15);
map.reload = function(){
map.remove();
map = L.map('mapa').setView([lat, lon], 15);
}
....
map.reload();
答案 13 :(得分:0)
我在反应上遇到了同样的问题我通过在 useEffect 的顶部初始化解决了它 这是我的 React 代码。
const mapContainerRef = useRef(null);
useEffect( async () => {
const res =await Axios.get(BASE_PATH + 'fetchProperty')
const container = L.DomUtil.get(mapContainerRef.current); if(container != null){ container._leaflet_id = null; }
if(container) {
const mapView = L.map( mapContainerRef.current, {
zoom: 13,
center: [19.059984, 72.889999]
// maxZoom: 13
// minZoom: 15
});
// const canvas = mapView.getCanvasContainer();
mapView.zoomControl.setPosition("bottomright");
mapView.attributionControl.addAttribution(
"<a href='https://mascots.pro'>Mascots. pro</a>"
);
L.tileLayer(
// "https://api.mapbox.com/styles/v1/mapbox/dark-v9/tiles/{z}/{x}/{y}?access_token=" + https://api.mapbox.com/styles/v1/anonymousmw/cko1eb1r20mdu18qqtps8i03p/tiles/{z}/{x}/{y}?access_token=
"https://api.mapbox.com/styles/v1/mapbox/dark-v9/tiles/{z}/{x}/{y}?access_token=" +
access_token,
{
attribution: '<a href="http://mascots.work">Mascots</a>'
}
).addTo(mapView);
const mask = L.tileLayer.mask(
"https://api.mapbox.com/styles/v1/anonymousmw/cko1eb1r20mdu18qqtps8i03p/tiles/{z}/{x}/{y}?access_token=" +
access_token,
{
attribution: '<a href="https://mascots.pro">Mascots pro</a>',
maskSize: 300
// maxZoom: 18,
// maxNativeZoom: 16
// tms: true
}
)
.addTo(mapView);
mapView.on("mousemove", function (e) {
mask.setCenter(e.containerPoint);
});
res.data.map((marker) => {
const innerHtmlContent = `<div id='popup-container' class='popup-container'> <h3> Property Details</h3>
<div class='popup-label'>Building Name :<p>${marker.Building}</p></div>
<div class='popup-address-label'> Address : <p>${marker.Landmark}, ${marker.Location}</p></div>
<div class='popup-rent-label'>Monthly Rent : <p> ₹ ${marker.Price}</p></div>
</div>`;
const divElement = document.createElement("div");
const assignBtn = document.createElement("div");
assignBtn.className = "map-link";
assignBtn.innerHTML = `<button class="view-btn">View Property</button>`;
divElement.innerHTML = innerHtmlContent;
divElement.appendChild(assignBtn);
assignBtn.addEventListener("click", (e) => {
console.log("dsvsdvb");
});
var iconOptions = {
iconUrl: "/images/location_pin2.svg",
iconSize: [25, 25]
};
var customIcon = L.icon(iconOptions);
// create popup contents
var customPopup = divElement;
// specify popup options
var customOptions = {
maxWidth: "500",
className: "custom"
};
const markerOptions = {
// title: "MyLocation",
// draggable: true
clickable: true,
icon: customIcon
};
const mark = L.marker([marker.Latitude,marker.Longitude], markerOptions);
mark.bindPopup(customPopup, customOptions);
mark.addTo(mapView);
// return mapView.off();
});
return () => mapView.remove();
}
}, [])
return (
<div className="map-box">
<div className="map-container" ref={mapContainerRef}></div>
</div>
);
答案 14 :(得分:0)
您应该尝试卸载该函数以移除现有地图。
const Map = () => {
const mapContainer = useRef();
const [map, setMap] = useState({});
useEffect(()=>{
const map = L.map(mapContainer.current, {attributionControl: false}).setView([51.505, -0.09], 13);
L.tileLayer('https://api.mapbox.com/styles/v1/{id}/tiles/{z}/{x}/{y}?access_token=pk.eyJ1IjoibWFwYm94IiwiYSI6ImNpejY4NXVycTA2emYycXBndHRqcmZ3N3gifQ.rJcFIG214AriISLbB6B5aw', {
maxZoom: 18,
attribution: 'Map',
id: 'mapbox/streets-v11',
tileSize: 512,
zoomOffset: -1
}).addTo(map);
// unmount map function
return () => map.remove();
}, []);
return (
<div style={{padding: 0, margin: 0, width: "100%", height: "100vh",}}
ref={el => mapContainer.current = el}>
</div>
);
}
答案 15 :(得分:0)
要刷新同一页面中的地图,可以使用以下代码在该页面上创建地图
if (!map) {
this.map = new L.map("mapDiv", {
center: [24.7136, 46.6753],
zoom: 5,
renderer: L.canvas(),
attributionControl: true,
});
}
然后使用下面的一行刷新地图,但请确保使用相同的纬度,经度和缩放选项
map.setView([24.7136, 46.6753], 5);
此外,在使用angular 2+在同一页面的选项卡之间切换时,我遇到了相同的问题,并且能够通过在组件constructor
中添加以下代码来解决此问题
var container = L.DomUtil.get('mapDiv');
if (container != null) {
container.outerHTML = ""; // Clear map generated HTML
// container._leaflet_id = null; << didn't work for me
}
答案 16 :(得分:0)
对于刷新传单地图,您可以使用以下代码:
this.map.fitBounds(this.map.getBounds());
答案 17 :(得分:0)
如果您不全局存储地图对象引用,我建议
if (L.DomUtil.get('map-canvas') !== undefined) {
L.DomUtil.get('map-canvas')._leaflet_id = null;
}
其中<div id="map-canvas"></div>
是映射到其中的对象。
这样,您避免重新创建html元素(如果您remove()
使用它,则会发生这种情况)。
答案 18 :(得分:0)
我们今天面对这个问题,我们已经解决了。我们做什么?
传单地图的加载范围如下。
<div id="map_container">
<div id="listing_map" class="right_listing"></div>
</div>
在表单输入更改或提交时,请按照以下步骤操作。在我的页面中删除传单地图容器后,再次创建新容器。
$( '#map_container' ).html( ' ' ).append( '<div id="listing_map" class="right_listing"></div>' );
这段代码之后,我的传单地图可以与表单过滤器一起正常工作,以重新加载。
谢谢。
答案 19 :(得分:0)
您可以尝试在初始化地图或离开页面时删除地图:
if(this.map) {
this.map.remove();
}
答案 20 :(得分:0)
使用redrawAll()函数而不是renderAll()。