当使用fitbounds时,将打开的信息窗口包含在地图范围内

6
我有一张地图,其中包含多个带有信息窗口的标记。这些信息窗口需要在页面加载时打开。使用setbounds对地图进行居中处理以包含所有标记,这个方法可行,但是还需要将信息窗口也包含在内。目前,信息窗口在某些地方被裁剪了。
JS:
function initialize() {
    var map = new google.maps.Map(document.getElementById('map-canvas'));
    var bounds = new google.maps.LatLngBounds();
    var myLatlng1 = new google.maps.LatLng(51.525209,-0.09402479999994284)
    var contentString1 = '<div class="map-content"><p>Test1<br/ >dsfasdf<br/ >dsfasdf<br/ >dsfasdf<br/ >dsfasdf<br/ >dsfasdf<br/ >dsfasdf</p></div>'
    var infowindow1 = new google.maps.InfoWindow({content: contentString1});
    var marker1 = new google.maps.Marker({position: myLatlng1,map: map,title: 'Test1'});

    google.maps.event.addListener(marker1, 'click', function() {infowindow1.open(map,marker1);});
    infowindow1.open(map,marker1);
    bounds.extend(myLatlng1);

    var myLatlng2 = new google.maps.LatLng(51.52106840183588,-0.10866641049801729)
    var contentString2 = '<div class="map-content"><p><br/ >dsfasdf<br/ >dsfasdf<br/ >dsfasdf<br/ >dsfasdf<br/ >dsfasdf</p></div>'
    var infowindow2 = new google.maps.InfoWindow({content: contentString2});
    var marker2 = new google.maps.Marker({position: myLatlng2,map: map,title: 'Test2'});
    google.maps.event.addListener(marker2, 'click', function() {infowindow2.open(map,marker2);});
    infowindow2.open(map,marker2);
    bounds.extend(myLatlng2)

    //  Fit these bounds to the map
    map.fitBounds(bounds);
}
google.maps.event.addDomListener(window, 'load', initialize);

CSS:

#map-canvas { width: 100%; height: 520px; }

这里可以查看一个代码演示:http://jsfiddle.net/mKKVM/

有人能否建议如何将信息窗口放置在范围内?


你的 jsfiddle 代码真的很丑,看起来很难受。你听说过缩进吗? :) 另外,JavaScript 代码应该放在 JavaScript 部分(左下角),而不是 HTML 部分。 - Tomas
感谢反馈,Tomas。目标是让所有内容都出现在地图范围内。点击标记会移动地图并可能使其他标记(部分)超出视野,这是不令人满意的。 - Dan
1个回答

4

概念验证jsfiddle

  1. 正常显示地图。
  2. 计算标记锚点到信息窗口上边缘的像素距离。
  3. 计算标记锚点到信息窗口左边缘的像素距离。
  4. 计算标记锚点到信息窗口右边缘的像素距离。
  5. 使用范围的右下角加上信息窗口宽度一半和范围顶部加上信息窗口高度,扩展原始范围。
  6. 使用范围的左下角减去信息窗口宽度一半和范围顶部加上信息窗口高度,扩展原始范围。
  7. 适应新范围的地图。

可能可以改进为使用三个点:顶部中心、左侧中心和右侧中心。这是第一次尝试,概念验证,可能需要整理和改进。

function initialize() {
  var map = new google.maps.Map(document.getElementById('map-canvas'));
  var projection = null; 
  google.maps.event.addListener(map,'projection_changed', function() {
    projection = map.getProjection();
  }); 

  var bounds = new google.maps.LatLngBounds();
  if (!projection) 
    google.maps.event.addListener(map, 'idle', computeBounds);
  else 
    computeBounds();

  var myLatlng1 = new google.maps.LatLng(51.525209,-0.09402479999994284);
  bounds.extend(myLatlng1);
  var myLatlng2 = new google.maps.LatLng(51.52106840183588,-0.10866641049801729);
  bounds.extend(myLatlng2);
  //  Fit these bounds to the map
  map.fitBounds(bounds);

  function computeBounds() {    

    var contentString1 = '<div class="map-content"><p>Test1<br />dsfasdf<br />dsfasdf<br />dsfasdf<br />dsfasdf<br />dsfasdf<br />dsfasdf</p></div>'
    var infowindow1 = new google.maps.InfoWindow({content: contentString1});
    var marker1 = new google.maps.Marker({position: myLatlng1,map: map,title: 'Test1'});

    google.maps.event.addListener(marker1, 'click', function() {
      infowindow1.open(map,marker1);
    });
    infowindow1.open(map,marker1);
    google.maps.event.addListenerOnce(infowindow1,'domready',calcInfoWindowBounds); 

    var contentString2 = '<div class="map-content"><p><br />dsfasdf<br />dsfasdf<br />dsfasdf<br />dsfasdf<br />dsfasdf</p></div>'
    var infowindow2 = new google.maps.InfoWindow({content: contentString2});
    var marker2 = new google.maps.Marker({position: myLatlng2,map: map,title: 'Test2'});
    google.maps.event.addListener(marker2, 'click', function() {
      infowindow2.open(map,marker2);
    });
    infowindow2.open(map,marker2);

    google.maps.event.addListenerOnce(infowindow2,'domready',calcInfoWindowBounds); 

    function calcInfoWindowBounds(){
      domEls = document.getElementsByClassName('map-content');
      var markerSpace = 32+8;
      var maxTop = 0;
      var maxLeft = 0;
      var maxRight = 0;
      for (var i=0; i<domEls.length; i++) {
        var topOfWindow = domEls[i].offsetHeight + markerSpace;
        var leftOfWindow = domEls[i].offsetWidth/2;
        var rightOfWindow = domEls[i].offsetWidth/2;

        if (topOfWindow > maxTop) maxTop = topOfWindow;
        if (leftOfWindow > maxLeft) maxLeft = leftOfWindow;
        if (rightOfWindow > maxRight) maxRight = rightOfWindow;
      }

      var leftBounds = projection.fromLatLngToPoint(new google.maps.LatLng(bounds.getNorthEast().lat(),bounds.getSouththWest().lng()));
      var rightBounds = projection.fromLatLngToPoint(new google.maps.LatLng(bounds.getNorthEast()));
      var topBounds0 = rightBounds.y + maxTop;
      var rightBounds0 = rightBounds.x + maxRight;
      var leftBounds0 = leftBounds.x - maxLeft;
      bounds.extend(projection.fromPointToLatLng(leftBounds0,topBounds0));
      bounds.extend(projection.fromPointToLatLng(rightBounds0,topBounds0));
      map.fitBounds(bounds);
    }   

  }

}
google.maps.event.addDomListener(window, 'load', initialize);

1
getSouththWest() 应该是 getSouthWest(),我猜测。然后在 var rightBounds = 这一行出现了 InvalidValueError: in property lat: not a number 错误。这一行似乎将 bounds 对象的一个子属性转换为了 NaN:http://imgur.com/RMZOlPi.png - Andrey
那里有一个无限循环。问题出在哪里?我有一个像这样长的infoBox,它不能正常工作。http://jsfiddle.net/tayfunyasar/H7bPE/27/ - Tayfun Yaşar
有一个错误。不像@Andrey说的那样工作。var leftBounds = projection.fromLatLngToPoint(new google.maps.LatLng(bounds.getNorthEast().lat(),bounds.getSouthWest().lng())); var rightBounds = projection.fromLatLngToPoint(new google.maps.LatLng(bounds.getNorthEast().lat(), bounds.getNorthEast().lng())); - Eriks

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接