how to get the real bounds with google maps when fully zoomed out
I have a map th开发者_如何学JAVAat shows location points based on the gbounds of the map. For example, any time the map is moved/zoomed, i find the bounds and query for locations that fall within those bounds. Unfortunately I'm unable to display all my locations when fully zoomed out. Reason being, gmaps reports the min/max long as whatever is at the edge of the map, but if you zoom out enough, you can get a longitudinal range that excludes visible locations.
For instance, if you zoom your map so that you see NorthAmerica twice, on the far left and far right. The min/max long are around: -36.5625 to 170.15625. But this almost completely excludes NorthAmerica which lies in the -180 to -60 range. Obviously this is bothersome as you can actually see the continent NorthAmerica (twice), but when I query my for locations in the range from google maps, NorthAmerica isn't returned.
My code for finding the min/max long is:
bounds = gmap.getBounds();
min_lat = bounds.getSouthWest().lat()
max_lat = bounds.getNorthEast().lat()
Has anyone encountered this and can anyone suggest a workaround? Off the top of my head I can only thing of a hack: to check the zoom level and hardcode the min/max lats to -180/180 if necessary, which is definitely unacceptable.
This isn't the most elegant solution, but I tested it and it does work. Check to see if the current bounds contains the bounds of the full map. Google doesn't actually include the north and south pole, so I had to tweak it to go almost all the way north and south.
bounds = gmap.getBounds();
var fullEarth = new GLatLngBounds(new GLatLng(-85, 180), new GLatLng(85, -180)))
var isFull = bounds.containsBounds(fullEarth);
min_lat = isFull ? -90 : bounds.getSouthWest().lat()
max_lat = isFull ? 90 : bounds.getNorthEast().lat()
min_lng = isFull ? 180 : bounds.getSouthWest().lng()
max_lng = isFull ? -180 : bounds.getNorthEast().lng()
Can not even imagine how this HUGE bug is still there !!!
isFullLng and toSpan functions are buggy and you can not rely on them.
My bug workaround for this:
var zoom = map.getZoom();
var bounds = map.getBounds();
var span = bounds.toSpan();
var isFull = span.lng() > 277 || zoom < 2;
Here is my solution, I only need isFullLng() which was apparently removed from API v3:
isFullLng: function() {
var scale = Math.pow(2, map.getZoom()),
bounds = map.getBounds(),
ne = bounds.getNorthEast(),
sw = bounds.getSouthWest(),
lat = (ne.lat() <= 0 && sw.lat() >= 0) || (ne.lat() >= 0 && sw.lat() <= 0) ? 0 : Math.min(Math.abs(ne.lat()), Math.abs(sw.lat())), // closest latitude to equator
deg1 = new google.maps.LatLng(lat, 0),
deg2 = new google.maps.LatLng(lat, 1),
coord1 = map.getProjection().fromLatLngToPoint(deg1),
coord2 = map.getProjection().fromLatLngToPoint(deg2);
// distance for one long degree in pixels for this zoom level
var pixelsPerLonDegree = (coord2.x - coord1.x) * scale;
// width of map's holder should be <= 360 (deg) * pixelsPerLonDegree if full map is displayed
var width = $this.width(); // width of map's holder div
return pixelsPerLonDegree * 360 <= width;
},
isFullLat: function() {
var bounds = map.getBounds(),
ne = bounds.getNorthEast(),
sw = bounds.getSouthWest(),
maxLat = 85; // max lat degree
return ne.lat() >= maxLat && sw.lat() <= -maxLat;
},
So isFull could then be:
isFullLng() && isFullLat()
Note that in isFullLng() the width of map's placeholder is needed, I'm using jQuery and map is rendered in div referenced by $this, so I only call
$this.width()
You should should change that to apply it to your problem.
精彩评论