WWDC Notes

Build location-aware enterprise apps

Show Apple's description.
Develop location-aware enterprise apps for your business and personalize your employee’s everyday experience. Learn how Apple built the Caffe Macs app for its on-campus cafeterias using iBeacons and Location Services and how you can apply these tools and frameworks to your own apps, while preserving employee privacy. From there, discover how you can use localization to deliver a great experience for your international employees.

This session is mostly an introduction to how to use Core Location (see related session below) plus some tips.

Determine device support

Before asking for authorization, check whether the current device supports the feature you're interested in:

if CLLocationManager.isMonitoringAvailable(for: CLBeaconRegion.self) {
    // Supports region monitoring to detect beacon regions
}

if CLLocationManager.isRangingAvailable() {
    // Supports obtaining the relative distance to a nearby iBeacon device
}

If the device doesn't support what you're interested in, offer the user a list of options (e.g. a list of locations/cafes/..)

iBeacon

  • A beacon is a device that emits a signal which can be detected by the system and passed to your app
  • Those signals can identify when a user is within a certain location
  • Once we detect a specific beacon signal, we can trigger something in our app.
  • When deploying your beacon hardware, you must program each beacon with an appropriate proximity UUID, major value and minor value.
  • The values identify each of your beacons uniquely and make it possible for your app to differentiate between them.
  • Use region monitoring to detect the presence of a beacon
  • Use ranging to determine the proximity of a detected beacon
// Stage 1: Region Monitoring

func monitorBeacons() {
    if CLLocationManager.isMonitoringAvailable(for: CLBeaconRegion.self) {

        let constraint = CLBeaconIdentityConstraint(uuid: proximityUUID)

		// Contains the proximity UUID, major value and minor value, of the beacons that you want to detect.
        let beaconRegion = CLBeaconRegion(
            beaconIdentityConstraint: constraint,
            identifier: beaconID
        )
        
        self.locationManager.startMonitoring(for: beaconRegion)
    }
}
// Stage 2: Beacon Ranging

func locationManager(_ manager: CLLocationManager, didEnterRegion region: CLRegion) {
    guard let region = region as? CLBeaconRegion,
        CLLocationManager.isRangingAvailable()
        else { return }
    
    let constraint = CLBeaconIdentityConstraint(uuid: region.uuid)
    manager.startRangingBeacons(satisfying: constraint)
    beaconsToRange.append(region)
}

func locationManager(_ manager: CLLocationManager, didExitRegion region: CLRegion) {
    ...
}

func locationManager(
    _ manager: CLLocationManager,
    didRangeBeacons beacons: [CLBeacon],
    in region: CLBeaconRegion) {
    
    guard let nearestBeacon = beacons.first else { return }
    let major = CLBeaconMajorValue(truncating: nearestBeacon.major)
    let minor = CLBeaconMinorValue(truncating: nearestBeacon.major)
    
    switch nearestBeacon.proximity {
    case .near, .immediate:
        displayInformation(for: major, and: minor)
        
    default:
        handleUnknownOrFarBeacon(for: major, and: minor)
    }
}

Missing anything? Corrections? Contributions are welcome 😃

Related

Written by

zntfdr

Federico Zanetello

Federico Zanetello is an iOS Engineer with strong passion for Swift, minimalism, and design. When he’s not busy automating things, he can be found writing at fivestars.blog and/or playing with the latest shiny toys.