I'm trying to place an image in a GMSGroundOverlay but noticed something weird when I zoom out to zoom < 3.0 (world level). The image should cover the whole screen of the iPad which is does fine at zoom >= 3.0. but if I zoom out the image is placed offscreen and is visible if you pan left or right.
It's like its been wrapped around the globe but on the reverse side.
I find the 4 points of the map thats on the iPad.
//southWest = nearLeft
CLLocationCoordinate2D SW_ = CLLocationCoordinate2DMake([vesselTileRequest_.nearLeft_latitude doubleValue],
[vesselTileRequest_.nearLeft_longitude doubleValue]);
//northEast = farRight = top right of ipad screen
CLLocationCoordinate2D NE_ = CLLocationCoordinate2DMake([vesselTileRequest_.farRight_latitude doubleValue],
[vesselTileRequest_.farRight_longitude doubleValue]);
//-----------------------------------------------------------------------------------
CLLocationCoordinate2D SE_ = CLLocationCoordinate2DMake([vesselTileRequest_.nearRight_latitude doubleValue],
[vesselTileRequest_.nearRight_longitude doubleValue]);
//northEast = farRight = top right of ipad screen
CLLocationCoordinate2D NW_ = CLLocationCoordinate2DMake([vesselTileRequest_.farLeft_latitude doubleValue],
[vesselTileRequest_.farLeft_longitude doubleValue]);
I place the image at SW,NE as per google docs:
overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:SW_
coordinate:NE_];
self.overlay = [GMSGroundOverlay groundOverlayWithBounds:overlayBounds
icon:responseImage_];
This works fine for any zoom level higher than 3.0.
But when we zoom out, nothing appears on the map but if you pan left or right the image has bee mapped to the opposite side of the earth.
I've had to turn of overlap mapping when zoom is < 3.0.
I tried every combination of NW/NE/SW/SE combo but all opposite corners just put the image on the wrong side of the earth.
if(self.mapView.camera.zoom < 3.0){
//nothing appears
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:NW_
// coordinate:NE_];
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:NW_
// coordinate:SW_];
//
//appears but off screen
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:NW_
// coordinate:SE_];
// //nothing
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:NE_
// coordinate:NW_];
//off screen
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:NE_
// coordinate:SW_];
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:NE_
// coordinate:SE_];
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:SW_
// coordinate:NW_];
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:SW_
// coordinate:NE_];
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:SW_
// coordinate:SW_];
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:SW_
// coordinate:SE_];
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:SE_
// coordinate:NW_];
// overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:SE_
// coordinate:NE_];
overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:SE_
coordinate:SW_];
overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:SE_
coordinate:SW_];
self.overlay = [GMSGroundOverlay groundOverlayWithBounds:overlayBounds
icon:responseImage_];
//-----------------------------------------------------------------------------------
//// CLLocationCoordinate2D position_farLeft = CLLocationCoordinate2DMake(self.mapView.projection.visibleRegion.farLeft.latitude,
//// self.mapView.projection.visibleRegion.farLeft.longitude);
// CLLocationCoordinate2D position_farLeft = CLLocationCoordinate2DMake(0.0,
// 0.0);
//
// DebugLog(@"self.mapView.camera.zoom:%f",self.mapView.camera.zoom);
// self.overlay = [GMSGroundOverlay groundOverlayWithPosition:position_farLeft
// icon:responseImage_
// zoomLevel:self.mapView.camera.zoom];
//-----------------------------------------------------------------------------------
}else{
//correct as of docs
overlayBounds = [[GMSCoordinateBounds alloc] initWithCoordinate:SW_
coordinate:NE_];
self.overlay = [GMSGroundOverlay groundOverlayWithBounds:overlayBounds
icon:responseImage_];
}
I also tried other methods to create the overlay but if I hard code the position to 0,0 so on the equator. It appears over australia. Its again on the opposite side of the earth to where it should be
CLLocationCoordinate2D position_farLeft = CLLocationCoordinate2DMake(self.mapView.projection.visibleRegion.farLeft.latitude,
self.mapView.projection.visibleRegion.farLeft.longitude);
CLLocationCoordinate2D position_farLeft = CLLocationCoordinate2DMake(0.0,
0.0);
DebugLog(@"self.mapView.camera.zoom:%f",self.mapView.camera.zoom);
self.overlay = [GMSGroundOverlay groundOverlayWithPosition:position_farLeft
icon:responseImage_
zoomLevel:self.mapView.camera.zoom];
Result - nothing appears on the map
If i tap, hold and pan the image is off the screen.
if i do the same and pan to the right you see the image is exactly on the opposite side of the earth to the rect shown on the ipad screen
Digging into this, and for the first issue raised - the GMSGroundOverlay being on the reverse side of the globe at zoom levels of 3.0 or lower it appears that the culprit is that GMSCoordinateBounds initWithCoordinate:coordinate:
initialization method normalizes the coordinates, as per the method documentation:
/**
* Inits the northEast and southWest bounds corresponding
* to the rectangular region defined by the two corners.
*
* It is ambiguous whether the longitude of the box
* extends from |coord1| to |coord2| or vice-versa;
* the box is constructed as the smaller of the two variants, eliminating the
* ambiguity.
*/
It turns out for an iPad, held in landscape mode, that zoom level 3.0 is the point at which a GMSGroundOverlay for the entire visibleRegion
covers 180 degrees. Zoom out, and GMSCoordinateBounds
normalizes to the smaller area, which just happens to be the other side of the globe.
The real answer here is to use GMSTileLayer.