I'm using OL4 on my project and I have a feature layer
where I can click and a popup appears, I also use a draw layer
where I can plot a Marker (in the example it's just a point)
My problem is that if I plot the marker above the feature layer
, the click propagate through the draw layer
till the feature layer
and the popup appears, I know it exists the stopPropagation()
event but I really don't find the correct place to insert it.
I tried to insert the event on marklayer
and map
on(click...)
but doesn't work.
Here my code:
var container = document.getElementById('popup');
var content = document.getElementById('popup-content');
var closer = document.getElementById('popup-closer');
var overlay = new ol.Overlay({
element: container,
autoPan: true,
autoPanAnimation: {
duration: 250
}
});
closer.onclick = function() {
overlay.setPosition(undefined);
closer.blur();
return false;
};
// DRAW Layer
var Msource = new ol.source.Vector();
var markLayer = new ol.layer.Vector({
source: Msource,
style: new ol.style.Style({
fill: new ol.style.Fill({
color: 'rgba(255, 255, 255, 0.2)'
}),
stroke: new ol.style.Stroke({
color: '#328cc1',
width: 4
}),
image: new ol.style.Circle({
radius: 7,
fill: new ol.style.Fill({
color: '#328cc1'
})
})
})
});
// DRAW Layer
var Msource = new ol.source.Vector();
var markLayer = new ol.layer.Vector({
source: Msource,
style: new ol.style.Style({
fill: new ol.style.Fill({
color: 'rgba(255, 255, 255, 0.2)'
}),
stroke: new ol.style.Stroke({
color: '#328cc1',
width: 4
}),
image: new ol.style.Circle({
radius: 7,
fill: new ol.style.Fill({
color: '#328cc1'
})
})
})
});
// MAP
var map = new ol.Map({
layers: [
new ol.layer.Tile({
source: new ol.source.TileJSON({
url: 'https://api.tiles.mapbox.com/v3/mapbox.natural-earth-hypso-bathy.json?secure',
crossOrigin: 'anonymous'
})
})
],
overlays: [overlay,markLayer],
target: 'map',
view: new ol.View({
center: [0, 0],
zoom: 2
})
});
// POPUP INTERACTION
map.on('singleclick', function(evt) {
var coordinate = evt.coordinate;
var hdms = ol.coordinate.toStringHDMS(ol.proj.transform(
coordinate, 'EPSG:3857', 'EPSG:4326'));
content.innerHTML = '<p>You clicked here:</p><code>' + hdms + '</code>';
overlay.setPosition(coordinate);
});
// MARKER INTERACTION
$("#marker").click(function(e) {
addMark("Point");
});
var mark;
function addMark(Type) {
mark = new ol.interaction.Draw({
source: Msource,
type: Type
});
map.addInteraction(mark);
mark.on("drawend", function(){
//to do stuff
});
markLayer.on("change", function(){
// remove the interaction after you have plotted a marker
map.removeInteraction(mark);
});
}
here my CodePen: REMOVED
On the live system, I have a map layer
feature layer
drawing layer
so not all the map is clickable but, for the purpose of showing my problem, the example is OK, you can see that if you draw a circle you open also the popup
AFAIK, you cannot use stopPropagation in this context.
One quick and (very) dirty solution could be setting a (global) variable in the drawend callback (eg. skipCoordinatesPopup) and checking it inside the singleclick callback.
Here's the codepen modified https://codepen.io/anon/pen/NyrKBm
map.on('singleclick', function(evt) {
if(skipCoordinatesPopup) {
console.log('skip popup while drawing marker');
return;
}
var coordinate = evt.coordinate;
var hdms = ol.coordinate.toStringHDMS(ol.proj.transform(
coordinate, 'EPSG:3857', 'EPSG:4326'));
content.innerHTML = '<p>You clicked here:</p><code>' + hdms + '</code>';
overlay.setPosition(coordinate);
});
...
map.addInteraction(mark);
skipCoordinatesPopup = true;
Instead, while dealing with controls that relies on the same gesture (click in your example), I suggest you to "activate" and "deactivate" (using the setActive functions or add/removeInteraction) them using a "toggling system", like a radio button or a combobox.
You can find something similar in this example https://openlayers.org/en/latest/examples/draw-freehand.html