【问题标题】:Center/Set Zoom of Map to cover all visible Markers?中心/设置地图缩放以覆盖所有可见标记?
【发布时间】:2013-10-18 17:35:35
【问题描述】:

我在我的地图上设置了多个标记,我可以静态设置缩放级别和中心,但我想要的是覆盖所有标记并尽可能缩放,让所有市场都可见

可用方法如下

setZoom(zoom:number)

setCenter(latlng:LatLng)

setCenter 既不支持多个位置或位置数组输入,setZoom 也不支持此类功能

【问题讨论】:

标签: javascript google-maps-api-3


【解决方案1】:

您需要使用fitBounds() 方法。

var markers = [];//some array
var bounds = new google.maps.LatLngBounds();
for (var i = 0; i < markers.length; i++) {
 bounds.extend(markers[i]);
}

map.fitBounds(bounds);

文档来自developers.google.com/maps/documentation/javascript

fitBounds(bounds[, padding])

参数:

`bounds`:  [`LatLngBounds`][1]|[`LatLngBoundsLiteral`][1]
`padding` (optional):  number|[`Padding`][1]

返回值:

设置视口以包含给定的边界。
注意:当地图设置为 display: none 时,fitBounds 函数将地图的大小读取为 0x0,因此不做任何事情。要在地图隐藏时更改视口,请将地图设置为 visibility: hidden,从而确保地图 div 具有实际大小。

【讨论】:

  • getPosition 方法从何而来?
  • @Pratheep - 它是 google.maps.Marker 类的一部分; developers.google.com/maps/documentation/javascript/…
  • 作为新手的旁白,与 Pratheep 有同样的问题...如果您对 Maps API 有经验,您就会知道这一点,但您始终可以传入 LatLngLiteral而不是拥有一个 Marker 实例。例如,bounds.extend({lat: 123, lng: 456}).
  • 由于某种原因,当我遍历一组标记时,getPosition 总是返回未定义的。我通过每次创建标记时调用 bounds.extend 来解决此问题。
  • 对任何感兴趣的人的额外提示。您可以使用fitBounds(bounds, int) 定义填充,这将允许您在标记和地图边缘之间留出一点空间(或者如果需要,可以减少空间)。 See Documentation
【解决方案2】:

用一些有用的技巧来扩展给定的答案:

var markers = //some array;
var bounds = new google.maps.LatLngBounds();
for(i=0;i<markers.length;i++) {
   bounds.extend(markers[i].getPosition());
}

//center the map to a specific spot (city)
map.setCenter(center); 

//center the map to the geometric center of all markers
map.setCenter(bounds.getCenter());

map.fitBounds(bounds);

//remove one zoom level to ensure no marker is on the edge.
map.setZoom(map.getZoom()-1); 

// set a minimum zoom 
// if you got only 1 marker or all markers are on the same address map will be zoomed too much.
if(map.getZoom()> 15){
  map.setZoom(15);
}

//Alternatively this code can be used to set the zoom for just 1 marker and to skip redrawing.
//Note that this will not cover the case if you have 2 markers on the same address.
if(count(markers) == 1){
    map.setMaxZoom(15);
    map.fitBounds(bounds);
    map.setMaxZoom(Null)
}

更新:
该主题的进一步研究表明 fitBounds() 是一个异步的 并且最好使用在调用 Fit Bounds 之前定义的侦听器进行缩放操作。
感谢@Tim,@xr280xr,有关该主题的更多示例:SO:setzoom-after-fitbounds

google.maps.event.addListenerOnce(map, 'bounds_changed', function(event) {
  this.setZoom(map.getZoom()-1);

  if (this.getZoom() > 15) {
    this.setZoom(15);
  }
});
map.fitBounds(bounds);

【讨论】:

  • 很好的补充。谢谢!
  • .getZoom() 返回了 undefined。 This answer 帮助我解决了这个问题,方法是在 zoom_changed 上使用 addListenerOnce 在其值初始化后设置缩放。
  • 感谢@d.raev,但在已设置边界时设置最大缩放不起作用。您必须做的是在初始化地图时设置“maxZoom”选项。 developers.google.com/maps/documentation/javascript/…
  • 在关于缩放操作(UPDATE)的部分中,您混合了几个变量和范围。您使用yourMapmapthis。也许让它更加一致是个好主意。
【解决方案3】:

数组的大小必须大于零。 Ο否则你会得到意想不到的结果。

function zoomeExtends(){
  var bounds = new google.maps.LatLngBounds();
  if (markers.length>0) { 
      for (var i = 0; i < markers.length; i++) {
         bounds.extend(markers[i].getPosition());
        }    
        myMap.fitBounds(bounds);
    }
}

【讨论】:

    【解决方案4】:

    有这个MarkerClusterer 客户端实用程序可用于谷歌地图,如在Google Map developer Articles 上指定的,这里简要介绍它的用途:

    有很多方法可以满足您的要求:

    • 基于网格的聚类
    • 基于距离的聚类
    • 视口标记管理
    • 融合表
    • 标记聚类器
    • 标记管理器

    您可以在上面提供的链接上阅读它们。

    Marker Clusterer 使用基于网格的聚类 对希望网格的所有标记进行聚类。基于网格的聚类的工作原理是将地图划分为一定大小的正方形(每次缩放时大小都会发生变化),然后将标记分组到每个网格正方形中。

    聚类之前

    聚类后

    我希望这就是您要找的,这将解决您的问题:)

    【讨论】:

      猜你喜欢
      • 2016-11-01
      • 2015-12-27
      • 2016-04-26
      • 2015-09-23
      • 2020-09-04
      • 2019-05-25
      • 1970-01-01
      • 2012-12-13
      • 1970-01-01
      相关资源
      最近更新 更多