Search code examples
iosmapkitmkmapviewcllocation

How to set MKMapView region to zoom to the accuracy of the userLocation?


I have a button that should go to the user's current location when tapped. The map should center on that coordinate and zoom in or out on their location such that the accuracy circle is entirely visible on screen. This is especially important on iOS 14 where they may not grant access to their precise location in which case the circle is very large.

Currently I have:

if let location = mapView.userLocation.location {
    let meters = max(location.horizontalAccuracy, location.verticalAccuracy, 250)
    mapView.setRegion(MKCoordinateRegion(center: location.coordinate, latitudinalMeters: meters, longitudinalMeters: meters), animated: true)
}

Running this code now with precision disabled, horizontalAccuracy is 9633 and verticalAccuracy is -1. This centers the map on their approximate location as expected, but it doesn't set the correct zoom level as you can see below. The first screenshot is the result of running the code - you can't see the precision circle because it's zoomed in too far. In the second screenshot I've manually zoomed out to the desired region to show the entire circle. (Ignore the pin that's not related to the user's location.)

Screenshot 1 enter image description here


Solution

  • At the very least

    • The verticalAccuracy is the accuracy of the altitude and should not be included in the latitude/longitude span calculation. Because it is negative in your example, it is not affecting the result, but it simply not applicable here.

    • You should multiply the accuracy by two, as the horizontalAccuracy is the radius of the circle around the user’s estimated user location and you presumably want it to encompass the full circle. I'd also add some margin (I used 25%) around this circle to allow it to breath visually:

      let meters = max(location.horizontalAccuracy * 2 * 1.25, 250)
      

    That yields:

    enter image description here