我使用以下代码在地图上创建了一个点击事件。
mymap.on('click', onMapClick);
还有一个带有弹出窗口的标记。
var marker = new mapboxgl.Marker().setLngLat([loc.lon,loc.lat]);
marker.setPopup(new mapboxgl.Popup({closeOnMove:true}).setText(`Hello`));
marker.addTo(mymap);
当我单击标记时,两个事件都会被触发。
我期望发生的只是标记事件(显示弹出窗口)被触发。但是函数
onMapClick
也被触发了。
在我的例子中,我将事件绑定到我的图层,但它应该是相同的。这是我为防止地图单击和标记单击之间发生冲突以正确显示弹出窗口所做的操作。
map.on('click', 'myLayerId', (e) => {
if (e.originalEvent.target.classList.contains('mapboxgl-marker')) return;
doSomething...
}
希望有帮助
当触发地图“点击”事件时,您可以检查被点击的原始元素是否是标记,如果是,则提前返回该函数 - 从而不执行地图点击操作。
map.on('click', (e) => {
if (e.originalEvent.target.closest('.mapboxgl-marker')) {
return // Click target was a marker so do nothing…
}
// Do something...
}
mokokom 的解决方案已经差不多了,但是由于标记是内联 svg,因此单击的元素往往是内部 svg 元素,例如
<path>
或 <circle>
。这些元素没有 .mapboxgl-marker
类,因此您需要使用 .closest
查找树才能找到它
这可能是一个更小众的情况,但是我发现与
map.on('click',Layername,(e)=>{});
有冲突
使用 Nextjs 13 和 mapbox-gl,在客户端组件上构建地图时,您可能会遇到相同的冲突。
为了解决这个问题,我将 on('click') 组件添加到 on('load') 函数的末尾。我没有调用任何指定的图层,而是用我的图层名称创建了一个单独的数组。
for(var x in clickLayer)
{
if(clickLayer[x].includes("Layer"))
{
continue;
}
clickLayer[x]+="Layer";
try{console.log(map.getLayer(clickLayer[x]))}
catch(e){console.error(e)}
}
let ActivePopup;
map.on('click',(e)=>{
const features = map.queryRenderedFeatures(e.point,{layers:clickLayer});
if(features.length<0)
{
console.log("Click binding failed.");
return;
}
const feature = features[0];
console.log("Clicked: ",feature.properties.title);
let newpop = makePopup(feature);
newpop.addTo(map);
ActivePopup = new mapboxgl.Popup({offset:[0,0]}).addTo(map);
ActivePopup.setText(feature.properties.description);
})