3

Why does FramedCloud popup steal click events inside the popup?

current_popup = new OpenLayers.Popup.FramedCloud(
    "featurePopup",
    f.geometry.getBounds().getCenterLonLat(),
    new OpenLayers.Size(0,0),
    "<b>Наблюдения</b><br/>" + $.map(features, function(fe) { return fe.attributes.description; }).join('<br/>'),
    null, false, null);
    map.addPopup(current_popup, true);



$('#map').on('click', function() { console.log('test'); return false; });

Captures click events always except when I click a link inside a popup. The popup and the anchors are descendants of #map.

  • Click the map => callback is fired
  • Click a marker => callback is fired, popup is shown
  • click inside popup (not on a link) => callback is not fired
  • click a link inside a popup => same way, nothing happens

The code in that part of OL is quite obscure.

Why does it catch clicks inside the popup? How do I take them back?

edit: debugging deeper in OL: this function is fired:

bindAsEventListener: function(func, object) {
    return function(event) {
        return func.call(object, event || window.event);
    };

event.target is the anchor, exactly what I expect:

<a class="edit-card-link" href="/form/?id=806">...</a>

func is:

handleBrowserEvent: function(evt) {
    var type = evt.type, listeners = this.listeners[type];
    if (!listeners || listeners.length == 0) {
        return;
    }
    var touches = evt.touches;
    if (touches && touches[0]) {
        var x = 0;
        var y = 0;
        var num = touches.length;
        var touch;
        for (var i = 0; i < num; ++i) {
            touch = touches[i];
            x += touch.clientX;
            y += touch.clientY;
        }
        evt.clientX = x / num;
        evt.clientY = y / num;
    }
    if (this.includeXY) {
        evt.xy = this.getMousePosition(evt);
    }
    this.triggerEvent(type, evt);
}

this is OpenLayers.Event class instance, evt.target is still that anchor, listeners contains 1 listener:

function (evt){OpenLayers.Event.stop(evt,true);}

Is this the reason? How do I take it out?

Brian Tompsett - 汤莱恩
  • 5,753
  • 72
  • 57
  • 129
culebrón
  • 34,265
  • 20
  • 72
  • 110

2 Answers2

4

If you want to stop the popup from stealing a mouse event then in your CSS you could, as suggested here, set the pointer-events: none; for the id corresponding to the popup id given at its creation. Thus in your case it would be:

#featurePopup{
    pointer-events: none;
}

It worked like a charm for me when I wanted to avoid flickering of a popup which I showed on mouseover.

Community
  • 1
  • 1
Boro
  • 7,913
  • 4
  • 43
  • 85
  • It looks like `pointer-events` isn't supported in IE: http://css-tricks.com/almanac/properties/p/pointer-events/ – colllin Sep 13 '13 at 23:07
  • Thanks Boro! I've been trying to solve that mouseover popup flickering issue all afternoon. – sfletche Oct 08 '13 at 22:49
3

I did it another way. I let OpenLayers capture the event, but before that I trigger another one.

 $('a', current_popup.contentDiv).on('click', function(evt) {
      var jtarget = $(evt.target);
      hide_popup();  // hides OpenLayers popup
      $(document).trigger('edit_link_clicked', {
           feature: features[jtarget.parent().find('a').index(jtarget)],
           cluster: f,
           url: jtarget.attr('href')
      });
      return false;
 });
culebrón
  • 34,265
  • 20
  • 72
  • 110
  • This feels so wrong, but it works, which feels so right. My click event was being swallowed by a vector feature, so my workaround looked more like: `myVectorLayer.events.register('click', null, function(e) { var map = myVectorLayer.map; var offset = jQuery(map.div).offset(); map.events.triggerEvent('click', {xy: {x: e.x - offset.left, y: e.y - offset.top}, target: document.body}); }, true);` – colllin Sep 14 '13 at 00:14