I have an issue. My current location is displayed and centered in a map view however the map region doesn\'t get zoomed in to. I tried taking Rob\'s advice by taking span an
You can get the current region
, multiply or divide the span
by two, as appropriate (dividing on zoom in, multiplying on zoom out), and then set the region
:
- (IBAction)zoomIn:(id)sender {
MKCoordinateRegion region = self.mapView.region;
region.span.latitudeDelta /= 2.0;
region.span.longitudeDelta /= 2.0;
[self.mapView setRegion:region animated:YES];
}
- (IBAction)zoomOut:(id)sender {
MKCoordinateRegion region = self.mapView.region;
region.span.latitudeDelta = MIN(region.span.latitudeDelta * 2.0, 180.0);
region.span.longitudeDelta = MIN(region.span.longitudeDelta * 2.0, 180.0);
[self.mapView setRegion:region animated:YES];
}
If you want to have the map automatically zoom to your location, you can use:
self.mapView.userTrackingMode = MKUserTrackingModeFollow;
If you want to do this manually, you can do something like the following. First, define an class property for whether you've zoomed in already or not:
@property (nonatomic) BOOL alreadySetZoomScale;
then change your didUpdateLocations
(or didUpdateToLocation
) to check this and set the zoom scale once:
- (void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations
{
CLLocation* newLocation = [locations lastObject]; // if less than zero, then valid lat and long not found
if (newLocation.horizontalAccuracy < 0)
return;
if (!self.alreadySetZoomScale)
{
MKCoordinateRegion region = MKCoordinateRegionMakeWithDistance(newLocation.coordinate, 1609, 1609); // 1 mile = 1609.34 meters
self.mapView.region = region;
[self.mapView setRegion:region animated:YES];
self.alreadySetZoomScale = YES;
}
else
{
[self.mapView setCenterCoordinate:newLocation.coordinate animated:YES];
}
}
- (void)locationManager:(CLLocationManager *)manager didUpdateToLocation:(CLLocation *)newLocation fromLocation:(CLLocation *)oldLocation
{
// if prior to iOS 6, use this old `MKMapViewDelegate` method, but call our
// other routine.
if (SYSTEM_VERSION_LESS_THAN(@"6.0"))
[self locationManager:manager didUpdateLocations:@[newLocation]];
}
This basically says, "if I haven't zoomed in yet, set the region based upon the newLocation
and a certain number of meters around that location, but if I have already done that, the just set the center coordinate based upon my current location, but don't change the zoom scale (in case I already zoomed in or out). This also does some conditional iOS version number logic (using the macros shown here), making sure if the end-user is running iOS prior to 6.0, that it will call our updated method.
By the way, if you're showing the user location on the map (e.g. self.mapView.showsUserLocation = YES;
), you might want to have this didUpdateLocations
also remove the overlay associated with the MKUserLocation
before moving the map center, otherwise it can leave the old overlay sitting around:
[self.mapView removeOverlays:self.mapView.overlays];