如何避免Google Map上的InfoWindow重叠?
解决Google Maps InfoWindow重叠及位置自定义问题
我明白你遇到的困扰了——Site 2和Site 4的InfoWindow挤在一起,还想找类似Bootstrap tooltip那样的位置控制属性对吧?咱们一步步来解决:
一、先修复你代码里的setPosition失效问题
你之前尝试用setPosition时没生效,是因为变量名大小写不一致!你定义的是infowindow,但代码里写的是infoWindow.setPosition,这就导致调用失败了。修正这个错误后,setPosition就能正常工作,你可以手动指定InfoWindow的坐标来避开重叠。
二、自定义InfoWindow的显示位置(类似tooltip的placement)
Google Maps原生InfoWindow没有直接的data-placement属性,但我们可以通过两种方式实现类似效果:
1. 利用pixelOffset偏移位置
通过设置InfoWindow的pixelOffset属性,可以让它相对于标记点偏移一定像素,比如显示在标记的左侧、右侧、上方或下方:
// 示例:让InfoWindow显示在标记右侧 var infowindow = new google.maps.InfoWindow({ pixelOffset: new google.maps.Size(100, 0) // 向右偏移100px,向下偏移0px });
不同方向的偏移参考:
- 上方:
new google.maps.Size(0, -100) - 下方:
new google.maps.Size(0, 100) - 左侧:
new google.maps.Size(-100, 0) - 右侧:
new google.maps.Size(100, 0)
2. 手动计算位置(更精准)
如果需要更精准的位置,比如基于标记点的经纬度偏移,可以计算出新的坐标后用setPosition设置:
// 示例:在标记点的经纬度基础上,纬度增加0.005(向北偏移) var offsetLat = lat + 0.005; var winLatLng = new google.maps.LatLng(offsetLat, long); infowindow.setPosition(winLatLng);
三、修改后的完整可运行代码
我把你的代码做了修正,修复了setPosition的变量名错误,并且给Site 4的InfoWindow设置了偏移位置,避免和Site 2重叠:
var locations = [ // Array Format: Site Name, Site Info, Marker lat, Marker lng, InfoWindow lat, InfoWindow lng ['Site 1', '<div>' + '<h6>Site 1</h6>' + 'PR 84.68 <br />' + 'kWh 1618' + '</div>', 23.141162, 120.120495, 23.141162, 120.120495], ['Site 2', '<div>' + '<h6>Site 2</h6>' + 'PR 84.68 <br />' + 'kWh 1618' + '</div>', 22.711022, 120.541029, 22.711022, 120.541029], ['Site 3', '<div>' + '<h6>Site 3</h6>' + 'PR 84.68 <br />' + 'kWh 1618' + '</div>', 23.317840, 120.267284, 23.317840, 120.267284], ['Site 4', '<div>' + '<h6>Site 4</h6>' + 'PR 84.68 <br />' + 'kWh 1618' + '</div>', 22.71637, 120.54331, 22.72137, 120.54331], // 这里修改了InfoWindow的纬度,向北偏移一点 ]; var infowindow; var marker, i; function initMap() { var mapOptions = { center: { lat: 24.56331, lng: 120.72904 }, zoom: 9, gestureHandling: "greedy", scrollwheel: false, zoomControl: true, }; var map = new google.maps.Map( document.getElementById("map-canvas"), mapOptions ); setMarkers(map, locations) function setMarkers(map, locations) { var i for (i = 0; i < locations.length; i++) { var name = locations[i][0] var lat = locations[i][2] var long = locations[i][3] var latInfo = locations[i][4] var longInfo = locations[i][5] var latlngset = new google.maps.LatLng(lat, long); var marker = new google.maps.Marker({ title: name, position: latlngset, map: map }); var content = locations[i][1]; var infowindow = new google.maps.InfoWindow() var winLatLng = new google.maps.LatLng(latInfo, longInfo); google.maps.event.addListener(marker, 'click', (function(marker, content, infowindow, winLatLng) { return function() { infowindow.setContent(content); infowindow.setPosition(winLatLng); // 修正变量名,现在可以正常设置位置了 infowindow.open(map); }; })(marker, content, infowindow, winLatLng)); google.maps.event.trigger(marker, 'click'); } } } google.maps.event.addDomListener(window, "resize", initMap); google.maps.event.addDomListener(window, "load", initMap);
#map-canvas { width: 100%; height: 1000px; border: 1px solid #343a40; } html, body { height: 100%; margin: 0; padding: 0; }
<script src="https://maps.googleapis.com/maps/api/js?libraries=geometry,places&ext=.js"></script> <div id="map-canvas"></div>
四、额外提示:自动避免InfoWindow重叠
如果你的标记点很多,手动调整位置太麻烦,可以考虑使用第三方增强组件(比如InfoBox,它是Google Maps InfoWindow的扩展,支持更多位置控制和自动避让逻辑);如果想原生实现,也可以通过计算相邻InfoWindow的坐标,动态调整偏移量,不过这需要额外的位置计算逻辑。
内容的提问来源于stack exchange,提问作者Penny Liu
相关产品推荐
相关产品推荐

