我有一个带有自定义HTML标记和MarkerClusterer的地图,群集工作正常,但我想通过半径将标记过滤到一个位置,我能够获得给定半径内的标记,但是我无法隐藏给定半径之外的标记,并仅显示MarkerClusterer中该半径内的标记。
我正在定义我的自定义标记:
function CustomMarker(latlng, map, args)
{
this.latlng = latlng;
this.args = args;
this.setMap(map);
this.map = map;
}
CustomMarker.prototype = new google.maps.OverlayView();
CustomMarker.prototype.draw = function ()
{
var self = this;
if (!this.div)
{
var div = document.createElement('div');
div.className = 'marker';
div.style.position = 'absolute';
div.style.cursor = 'pointer';
var span = document.createElement('span');
span.innerHTML = 'X';
div.appendChild(span);
var panes = this.getPanes();
panes.overlayImage.appendChild(div);
this.div = div;
}
var point = this.getProjection().fromLatLngToDivPixel(this.latlng);
if (point)
{
this.div.style.left = (point.x - 20) + 'px';
this.div.style.top = (point.y - 20) + 'px';
}
google.maps.event.addDomListener(this.div, "click", function (event)
{
google.maps.event.trigger(self, "click");
});
};
CustomMarker.prototype.remove = function ()
{
if (this.div)
{
this.div.parentNode.removeChild(this.div);
this.div = null;
}
};
CustomMarker.prototype.getPosition = function ()
{
return this.latlng;
};
CustomMarker.prototype.getDraggable = function ()
{
return false;
};
CustomMarker.prototype.setVisible = function (visible)
{
if (this.div)
{
if (visible)
{
this.div.style.display = 'table';
this.visible = true;
}
else
{
this.div.style.display = 'none';
this.visible = false;
}
}
};
CustomMarker.prototype.getVisible = function ()
{
return this.visible;
};
我正在使用MarkerClustererPlus并使用setIgnoreHidden(true)
将隐藏所有标记,包括应该可见的标记。
我注意到,{+ 1}}在使用marker.getVisible()
时由MC +使用,对于给定半径之外的标记按预期返回false,但对于集群内的标记未定义。
我认为这是因为当一个簇形成时,它内部的元素被移除,而不仅仅是隐藏,因此将它们设置为null。
setIgnoreHidden(true)
参见JS Fiddle示例。
答案 0 :(得分:2)
如果您希望标记可见,则需要设置其map
属性:
for (var n = 0; n < this.markers.length; n++) {
var marker = this.markers[n];
var distance = google.maps.geometry.spherical.computeDistanceBetween(marker.getPosition(), location) / 1609;
if (distance > radius) {
// 4 Markers over 10 mile radius should be hidden
marker.setVisible(false);
} else {
// Only 1 marker should be kept visible
marker.setMap(this.map);
visibleMarkers.push(marker);
}
console.log(marker.getVisible());
}
代码段
/* ==========================================================================
Google Maps
========================================================================== */
var map = {
'map': '',
'markers': [],
'lat': 31.862491,
'lng': -106.3650707,
'createMap': function() {
this.map = new google.maps.Map(document.getElementById('map'), {
center: {
lat: this.lat,
lng: this.lng
},
zoom: 6,
maxZoom: 18,
scrollwheel: false,
disableDefaultUI: true,
zoomControl: true
});
this.createMarkers($object);
},
'createMarkers': function(response) {
var self = this;
var infoWindow = new google.maps.InfoWindow({
content: 'Loading'
});
var bounds = new google.maps.LatLngBounds();
for (var n = 0; n < response.length; n++) {
var el = response[n];
var lat = parseFloat(el.lat);
var lng = parseFloat(el.lng);
var latLng = new google.maps.LatLng(lat, lng);
var marker = new CustomMarker(latLng, this.map, {
title: el.title
});
this.markers.push(marker);
bounds.extend(marker.getPosition());
google.maps.event.addListener(marker, 'click', function() {
infoWindow.setContent('<b>' + this.args.title + '</b>');
infoWindow.open(self.map, this);
self.map.panTo(this.getPosition());
self.map.setZoom(14);
});
}
// New markerClustererPlus
this.mc = new MarkerClusterer(this.map, this.markers);
},
'filter': function(location) {
var bounds = new google.maps.LatLngBounds();
var visibleMarkers = [];
// For testing purposes
var radius = 10;
var location = new google.maps.LatLng(this.lat, this.lng);
// Hide Markers not inside given radius
for (var n = 0; n < this.markers.length; n++) {
var marker = this.markers[n];
var distance = google.maps.geometry.spherical.computeDistanceBetween(marker.getPosition(), location) / 1609;
if (distance > radius) {
// 4 Markers over 10 mile radius should be hidden
marker.setVisible(false);
} else {
// Only 1 marker should be kept visible
marker.setMap(this.map);
visibleMarkers.push(marker);
}
console.log(marker.getVisible());
}
for (var n = 0; n < visibleMarkers.length; n++) {
bounds.extend(visibleMarkers[n].getPosition());
}
this.mc.setIgnoreHidden(true);
this.map.fitBounds(bounds);
}
};
var btn = document.getElementById('filter');
btn.addEventListener('click', function() {
map.filter();
});
var $object = [{
"lat": -20.823485,
"lng": 23.24177,
"title": "Explicabo voluptates voluptatibus quas sed laborum minus quia."
}, {
"lat": -27.503418,
"lng": 32.594705,
"title": "Repellat ea reiciendis quae dolores sit facilis ut."
}, {
"lat": -53.468797,
"lng": -125.400102,
"title": "Perspiciatis voluptates consectetur nulla inventore illo debitis delectus alias."
}, {
"lat": "31.80666009999999",
"lng": "-106.50467950000001",
"title": "321 Mesa St"
}, {
"lat": "31.831369",
"lng": "-106.55140799999998",
"title": "123 Main St"
}];
/* ==========================================================================
Custom Maker
========================================================================== */
function CustomMarker(latlng, map, args) {
this.latlng = latlng;
this.args = args;
this.setMap(map);
this.map = map;
}
CustomMarker.prototype = new google.maps.OverlayView();
CustomMarker.prototype.draw = function() {
var self = this;
if (!this.div) {
var div = document.createElement('div');
div.className = 'marker';
div.style.position = 'absolute';
div.style.cursor = 'pointer';
var span = document.createElement('span');
span.innerHTML = 'X';
div.appendChild(span);
var panes = this.getPanes();
panes.overlayImage.appendChild(div);
this.div = div;
}
var point = this.getProjection().fromLatLngToDivPixel(this.latlng);
if (point) {
this.div.style.left = (point.x - 20) + 'px';
this.div.style.top = (point.y - 20) + 'px';
}
google.maps.event.addDomListener(this.div, "click", function(event) {
google.maps.event.trigger(self, "click");
});
};
CustomMarker.prototype.remove = function() {
if (this.div) {
this.div.parentNode.removeChild(this.div);
this.div = null;
}
};
CustomMarker.prototype.getPosition = function() {
return this.latlng;
};
CustomMarker.prototype.getDraggable = function() {
return false;
};
CustomMarker.prototype.setVisible = function(visible) {
if (this.div) {
if (visible) {
this.div.style.display = 'table';
this.visible = true;
} else {
this.div.style.display = 'none';
this.visible = false;
}
}
};
CustomMarker.prototype.getVisible = function() {
return this.visible;
};
map.createMap();
#map {
height: 400px;
}
.marker {
display: table;
width: 40px;
height: 40px;
background-color: #353535;
border: 3px solid #FF9000;
border-radius: 50px;
color: #fff;
font-size: 1em;
font-weight: bold;
text-align: center;
}
.marker span {
display: table-cell;
vertical-align: middle;
}
<script src="https://maps.googleapis.com/maps/api/js?libraries=geometry"></script>
<script src="https://google-maps-utility-library-v3.googlecode.com/svn/tags/markerclustererplus/2.1.2/src/markerclusterer.js"></script>
<div id="map"></div>
<button id="filter">Filter</button>
<p>
Clicking the Filter button should display 1 marker, bounds get properly set but marker is not visible.
</p>
<p>
If you click on the cluster before clicking the filter button, the markers inside it get visible, and clicking filter will work as expected, as there are no markers inside a cluster.
</p>