2

カスタムの Google マップ情報ウィンドウを作成しようとしていますが、カスタム情報ウィンドウの下にあるマーカーが情報ウィンドウからクリックできるという問題が発生しています。

ここに例があります(基本的にGoogleの例から直接ここに

<html>
<head>
<meta name="viewport" content="initial-scale=1.0, user-scalable=no" />
<meta http-equiv="content-type" content="text/html; charset=UTF-8"/>
<title>Google Maps JavaScript API v3 Example: Info Window Custom</title>
<script type="text/javascript" src="http://maps.google.com/maps/api/js?sensor=false"></script>
<script type="text/javascript">

/* An InfoBox is like an info window, but it displays
 * under the marker, opens quicker, and has flexible styling.
 * @param {GLatLng} latlng Point to place bar at
 * @param {Map} map The map on which to display this InfoBox.
 * @param {Object} opts Passes configuration options - content,
 *   offsetVertical, offsetHorizontal, className, height, width
 */
function InfoBox(opts) {
  google.maps.OverlayView.call(this);
  this.latlng_ = opts.latlng;
  this.map_ = opts.map;
  this.offsetVertical_ = -195;
  this.offsetHorizontal_ = 0;
  this.height_ = 165;
  this.width_ = 266;

  var me = this;
  this.boundsChangedListener_ =
    google.maps.event.addListener(this.map_, "bounds_changed", function() {
      return me.panMap.apply(me);
    });

  // Once the properties of this OverlayView are initialized, set its map so
  // that we can display it.  This will trigger calls to panes_changed and
  // draw.
  this.setMap(this.map_);
}

/* InfoBox extends GOverlay class from the Google Maps API
 */
InfoBox.prototype = new google.maps.OverlayView();

/* Creates the DIV representing this InfoBox
 */
InfoBox.prototype.remove = function() {
  if (this.div_) {
    this.div_.parentNode.removeChild(this.div_);
    this.div_ = null;
  }
};

/* Redraw the Bar based on the current projection and zoom level
 */
InfoBox.prototype.draw = function() {
  // Creates the element if it doesn't exist already.
  this.createElement();
  if (!this.div_) return;

  // Calculate the DIV coordinates of two opposite corners of our bounds to
  // get the size and position of our Bar
  var pixPosition = this.getProjection().fromLatLngToDivPixel(this.latlng_);
  if (!pixPosition) return;

  // Now position our DIV based on the DIV coordinates of our bounds
  this.div_.style.width = this.width_ + "px";
  this.div_.style.left = (pixPosition.x + this.offsetHorizontal_) + "px";
  this.div_.style.height = this.height_ + "px";
  this.div_.style.top = (pixPosition.y + this.offsetVertical_) + "px";
  this.div_.style.display = 'block';
};

/* Creates the DIV representing this InfoBox in the floatPane.  If the panes
 * object, retrieved by calling getPanes, is null, remove the element from the
 * DOM.  If the div exists, but its parent is not the floatPane, move the div
 * to the new pane.
 * Called from within draw.  Alternatively, this can be called specifically on
 * a panes_changed event.
 */
InfoBox.prototype.createElement = function() {
  var panes = this.getPanes();
  var div = this.div_;
  if (!div) {
    // This does not handle changing panes.  You can set the map to be null and
    // then reset the map to move the div.
    div = this.div_ = document.createElement("div");
    div.style.border = "0px none";
    div.style.position = "absolute";
    div.style.background = "url('http://gmaps-samples.googlecode.com/svn/trunk/images/blueinfowindow.gif')";
    div.style.width = this.width_ + "px";
    div.style.height = this.height_ + "px";
    var contentDiv = document.createElement("div");
    contentDiv.style.padding = "30px"
    contentDiv.innerHTML = "<b>Hello World!</b>";

    var topDiv = document.createElement("div");
    topDiv.style.textAlign = "right";
    var closeImg = document.createElement("img");
    closeImg.style.width = "32px";
    closeImg.style.height = "32px";
    closeImg.style.cursor = "pointer";
    closeImg.src = "http://gmaps-samples.googlecode.com/svn/trunk/images/closebigger.gif";
    topDiv.appendChild(closeImg);

    function removeInfoBox(ib) {
      return function() {
        ib.setMap(null);
      };
    }

    google.maps.event.addDomListener(closeImg, 'click', removeInfoBox(this));

    div.appendChild(topDiv);
    div.appendChild(contentDiv);
    div.style.display = 'none';
    panes.floatPane.appendChild(div);
    this.panMap();
  } else if (div.parentNode != panes.floatPane) {
    // The panes have changed.  Move the div.
    div.parentNode.removeChild(div);
    panes.floatPane.appendChild(div);
  } else {
    // The panes have not changed, so no need to create or move the div.
  }
}

/* Pan the map to fit the InfoBox.
 */
InfoBox.prototype.panMap = function() {
};

function initialize() {
    var myOptions = {
      zoom: 8,
      center: new google.maps.LatLng(-33.397, 150.644),
      mapTypeId: google.maps.MapTypeId.ROADMAP,
      sensor: 'true'
    }
    var map = new google.maps.Map(document.getElementById("map_canvas"), myOptions);

    var marker = new google.maps.Marker({
        position: new google.maps.LatLng(-34, 150),
        map: map
    });
    google.maps.event.addListener(marker, "click", function(e) {
      var infoBox = new InfoBox({latlng: marker.getPosition(), map: map});
    });

    var m2 = new google.maps.Marker({
        position: new google.maps.LatLng(-33.5, 150.5),
        map: map
    });
    google.maps.event.addListener(m2, "click", function(e) {
      var infoBox = new InfoBox({latlng: m2.getPosition(), map: map});
    });

  }
</script>
</head>
<body style="margin:0px; padding:0px;" onload="initialize()">
  <div id="map_canvas" style="width:100%; height:100%"></div>
</body>
</html>

2 つのマーカーを作成していることがわかります。1 つはもう一方のちょうど北東にあります。一番下のマーカーをクリックしてから、他のマーカーがマーカーを介してどのようにクリックできるかを観察します (「W」のすぐ近く)。

どうすればこれを修正できますか?! z-index を変更しようとしましたが、役に立たなかったようです。

これはAPI v3 btwを使用しています。

4

5 に答える 5

1

overlayMouseTargetの代わりにMapPane を使用してみてくださいfloatPane

于 2011-11-09T18:54:58.483 に答える
1

後世のために、マーカー ポップアップ DOM で一連のイベントを無効にする必要があります。これはやり過ぎのように感じますが、規定の方法でした。代わりに、クリックされたマーカー以外に存在するすべてのマーカーを循環し、それらのクリックを無効にすることもできます (実際には、後知恵でおそらくより良い解決策です)。持っているマーカーの数にもよりますが、たくさんありました。

このようなもの(私のcoffeescriptからテストせずにここに転記したので...)

// All in a google.maps.OverlayView subclass.

...
this.listeners = new Array(); // save listeners for unbinding later
...
this.cancelEvents = function(){
    events = ['mousedown', 'mousemove', 'mouseover', 
            'mouseout', 'mouseup', 'mousewheel', 
            'DOMMouseScroll', 'touchstart', 'touchend', 
            'touchmove', 'dblclick', 'contextmenu'];
    // Note, don't disable 'click' if you want to be able to click links in the dom. Some things we're disabling here will can effect how your user might interact with the popup (double click to select text etc)
    for(var i = 0; i < events.length; i++){
        var event = events[i];
        this.listeners.push(
            google.maps.event.addDomListener(
                this.popup_dom_element,
                event,
                function(ev){
                    e.cancelBubble = true;
                    if(e.stopPropagation){
                        e.stopPropagation();
                    }
                }
            );
        );
    }
}

this.onAdd = function (){
    // build your html popup
    var html_code = "...";
    // easy way to get a dom element but probably over kill if its your only JQ
    this.popup_dom_element = $(html_code);
    this.cancelEvents();
}

this.onRemove = function(){
    // any other removal code you have
    ...
    for(var i = 0; i < this.listeners.length; i++){
        // remove our event listeners
        google.maps.event.removeListener(this.listeners[i]);
    }
}
于 2012-02-26T14:23:31.553 に答える
0

私は同じ問題を抱えていましたが、実際には非常に簡単です:/

uがjqueryを使用している場合は、

$(div).bind("click",function(e) {
 return false;
});

InfoBox.prototype.createElement関数で。これは役立つはずです。

乾杯

于 2012-06-26T13:55:40.890 に答える
0

使用する:

google.maps.event.addDomListener

それ以外の

google.maps.event.addListener

于 2013-10-28T15:27:22.237 に答える
0

人々がマーカーをクリックできないようにしたい場合は、電話していただけますかmarker.setClickable(false)

于 2011-09-22T22:12:37.177 に答える