Getting Location Information using the iOS 10 Core Location Framework

From Techotopia
Revision as of 04:38, 10 November 2016 by Neil (Talk | contribs) (Configuring the Desired Location Accuracy)

Jump to: navigation, search

PreviousTable of ContentsNext
An Example iOS 10 MKMapItem ApplicationAn Example iOS 10 Location Application


Learn SwiftUI and take your iOS Development to the Next Level
SwiftUI Essentials – iOS 16 Edition book is now available in Print ($39.99) and eBook ($29.99) editions. Learn more...

Buy Print Preview Book


iOS devices are able to employ a number of different techniques for obtaining information about the current geographical location of the device. These mechanisms include GPS, cell tower triangulation and finally (and least accurately), by using the IP address of available Wi-Fi connections. The mechanism that is used by iOS to detect location information is, however, largely transparent to the application developer and the system will automatically use the most accurate solution available at any given time. In fact, all that is needed to integrate location based information into an iOS 10 application is an understanding of how to use the Core Location Framework which, incidentally, is the subject of this chapter.

Once the basics of location tracking with Core Location have been covered in this chapter, the next chapter will provide detailed steps on how to create An Example iOS 10 Location Application.


Contents


The Core Location Manager

The key classes contained within the Core Location Framework are CLLocationManager and CLLocation. An instance of the CLLocationManager class can be created using the following Swift code:

var locationManager: CLLocationManager = CLLocationManager()

Once a location manager instance has been created, it must seek permission from the user to collect location information before it can begin to track data.

Requesting Location Access Authorization

Before any application can begin to track location data it must first seek permission to do so from the user. This can be achieved by making a call to one of two methods on the CLLocationManager instance depending on the specific requirement. If the application only needs to track location information when the application is in the foreground then a call should be made to the requestWhenInUseAuthorization method of the location manager instance. For example:

Learn SwiftUI and take your iOS Development to the Next Level
SwiftUI Essentials – iOS 16 Edition book is now available in Print ($39.99) and eBook ($29.99) editions. Learn more...

Buy Print Preview Book

locationManager.requestWhenInUseAuthorization()

In the event that tracking is also required when the application is running in the background, the requestAlwaysAuthorization method should be used instead:

locationManager.requestAlwaysAuthorization()

Each method call requires that a specific key-value pair be added to the Information Property List dictionary contained within the application’s Info.plist file. The value takes the form of a string and must describe the reason why the application needs access to the user’s current location. The keys associated with these values are as follows:

NSLocationWhenInUseUsageDescription – A string value describing to the user why the application needs access to the current location when running in the foreground.

NSLocationAlwaysUsageDescription – A string describing to the user why the application needs access to the current location data all the time that the application is running (including when it is in the background).


Configuring the Desired Location Accuracy

The level of accuracy to which location information is to be tracked is specified via the desiredAccuracy property of the CLLocationManager object. It is important to keep in mind when configuring this property that the greater the level of accuracy selected the greater the drain on the device battery. An application should, therefore, never request a greater level of accuracy than is actually needed.

A number of predefined constant values are available for use when configuring this property:

kCLLocationAccuracyBestForNavigation – Uses the highest possible level of accuracy augmented by additional sensor data. This accuracy level is intended solely for use when the device is connected to an external power supply.

kCLLocationAccuracyBest – The highest recommended level of accuracy for devices running on battery power.

kCLLocationAccuracyNearestTenMeters - Accurate to within 10 meters.

kCLLocationAccuracyHundredMeters – Accurate to within 100 meters.

kCLLocationAccuracyKilometer – Accurate to within one kilometer.

kCLLocationAccuracyThreeKilometers – Accurate to within three kilometers.

The following code, for example, sets the level of accuracy for a location manager instance to “best accuracy”:

locationManager.desiredAccuracy = kCLLocationAccuracyBest

Learn SwiftUI and take your iOS Development to the Next Level
SwiftUI Essentials – iOS 16 Edition book is now available in Print ($39.99) and eBook ($29.99) editions. Learn more...

Buy Print Preview Book

Configuring the Distance Filter

The default configuration for the location manager is to report updates whenever any changes are detected in the location of the device. The distanceFilter property of the location manager allows applications to specify the amount of distance the device location must change before an update is triggered. If, for example, the distance filter is set to 1000 meters the application will only receive a location update when the device travels 1000 meters or more from the location of the last update. For example, to specify a distance filter of 1500 meters:

locationManager.distanceFilter = 1500.0

The distance filter may be cancelled, thereby returning to the default setting, using the kCLDistanceFilterNone constant:

locationManager.distanceFilter = kCLDistanceFilterNone

The Location Manager Delegate

Location manager updates and errors result in calls to two delegate methods defined within the CLLocationManagerDelegate protocol. Templates for the two delegate methods that must be implemented to comply with this protocol are as follows:

func locationManager(_ manager: CLLocationManager,
                didUpdateLocations locations: [CLLocation])
{
   // Handle location updates here
}

func locationManager(_ manager: CLLocationManager,
         didFailWithError error: Error)
{
   // Handle errors here 
}

Each time the location changes, the didUpdateLocations delegate method is called and passed as an argument an array of CLLocation objects with the last object in the array containing the most recent location data.

Learn SwiftUI and take your iOS Development to the Next Level
SwiftUI Essentials – iOS 16 Edition book is now available in Print ($39.99) and eBook ($29.99) editions. Learn more...

Buy Print Preview Book

Changes to the location tracking authorization status of an application are reported via a call to the optional didChangeAuthorization delegate method:

func locationManager(_ manager: CLLocationManager, didChangeAuthorization status: CLAuthorizationStatus) {

	// App may no longer be authorized to obtain location
        //information. Check status here and respond accordingly.

}
<pre>

Once a class has been configured to act as the delegate for the location manager, that object must be assigned to the location manager instance. In most cases, the delegate will be the same view controller class in which the location manager resides, for example:

<pre>
locationManager.delegate = self

Starting Location Updates

Once suitably configured and authorized, the location manager can then be instructed to start tracking location information:

locationManager.startUpdatingLocation()

With each location update, the didUpdateLocations delegate method is called by the location manager and passed information about the current location.

Obtaining Location Information from CLLocation Objects

Location information is passed through to the didUpdateLocation delegate method in the form of CLLocation objects. A CLLocation object encapsulates the following data:

• Latitude

• Longitude

• Horizontal Accuracy

• Altitude

• Altitude Accuracy

Longitude and Latitude

Longitude and latitude values are stored as type CLLocationDegrees and may be obtained from a CLLocation object as follows:

Learn SwiftUI and take your iOS Development to the Next Level
SwiftUI Essentials – iOS 16 Edition book is now available in Print ($39.99) and eBook ($29.99) editions. Learn more...

Buy Print Preview Book

let currentLatitude: CLLocationDistance = 
			location.coordinate.latitude

let currentLongitude: CLLocationDistance = 
			location.coordinate.longitude

Accuracy

Horizontal and vertical accuracy are stored in meters as CLLocationAccuracy values and may be accessed as follows:

let verticalAccuracy: CLLocationAccuracy = 
			location.verticalAccuracy

let horizontalAccuracy: CLLocationAccuracy = 
			location.horizontalAccuracy

Altitude

The altitude value is stored in meters as a type CLLocationDistance value and may be accessed from a CLLocation object as follows:

let altitude: CLLocationDistance = location.altitude

Getting the Current Location

If all that is required from the location manager is the user’s current location without the need for continuous location updates, this can be achieved via a call to the requestLocation method of the location manager instance. This method will identify the current location and call the didUpdateLocations delegate one time passing through the current location information. Location updates are then automatically turned off:

locationManager.requestLocation()

Learn SwiftUI and take your iOS Development to the Next Level
SwiftUI Essentials – iOS 16 Edition book is now available in Print ($39.99) and eBook ($29.99) editions. Learn more...

Buy Print Preview Book

Calculating Distances

The distance between two CLLocation points may be calculated by calling the distance(from:) method of the end location and passing through the start location as an argument. For example, the following code calculates the distance between the points specified by startLocation and endLocation:

var distance: CLLocationDistance = 
	endLocation.distance(from: startLocation)

Location Information and Multitasking

Location based iOS applications are one of the three categories of application that are permitted to continue executing when placed into the background (for a detailed description of multitasking refer to iOS 10 Multitasking, Background Transfer Service and Fetching). If location updates are required when the application is in the background state it is strongly recommended that the desired accuracy setting be reduced within the applicationDidEnterBackground method by making a call to the startMonitoringSignificantLocationChanges method of the location manager object. This will ensure that the application is only notified of significant changes to the location of the device thereby reducing the load on the battery.

Summary

This chapter has provided an overview of the use of the iOS Core Location Framework to obtain location information within an iOS application. This theory will be put into practice in the next chapter entitled An Example iOS 10 Location Application.


Learn SwiftUI and take your iOS Development to the Next Level
SwiftUI Essentials – iOS 16 Edition book is now available in Print ($39.99) and eBook ($29.99) editions. Learn more...

Buy Print Preview Book


PreviousTable of ContentsNext
An Example Swift iOS 8 MKMapItem ApplicationA Swift Example iOS 8 Location Application