title: Swift / CoreLocation : North heading from didUpdateLocation
body: <p>Is it the way to get heading from inside the <code>didUpdateLocation</code> method ? I am grapple with task which is about sending the data about user location to container class called <code>Ping</code>. The Ping class have to contain basics user location as well as with <code>north heading</code>. </p>
  
  <ul>
  <li>Is it the way to enable compass from code in iOS ?</li>
  </ul>
  
  <p>My location service saving the data after period of <code>time</code> or <code>degree turn</code> of the device or <code>distance traveled</code> - also if we turn faster or we traveled the distance then timer going to be restarted. </p>
  
  <p>I have not test it yet on physical device ( only simulator ) so I am not able to see If I am counting well traveled distance and the angle.</p>
  
  <pre><code>import Foundation
  import CoreLocation
  import CoreMotion
  import UIKit
  
  class LocationService: NSObject, CLLocationManagerDelegate {
  
      var _locationManager: CLLocationManager!
      var _motionManager: CMMotionManager!
      var _timer = Timer()
      var _heading: Double!
      var _accuracy: Double!
      var _latitude: Double!
      var _longitude: Double!
      var _velocity: Double!
      var _startLocation: CLLocation!
      var _lastLocation: CLLocation!
      var _traveledDistance: Double = 0
      var _seconds = 0
      var _deferringUpdates: Bool = false
  
      static let _instance : LocationService = LocationService()
  
      public static var Instance : LocationService {
          get{ return _instance}
      }
  
      public func InitLocationManager() {
  
          _locationManager = CLLocationManager()
          _locationManager.delegate = self
          _locationManager.distanceFilter = 1000
          _locationManager.desiredAccuracy = kCLLocationAccuracyKilometer
          _locationManager.requestAlwaysAuthorization()
          _locationManager.startUpdatingLocation()
          if CLLocationManager.headingAvailable() {
  
              _locationManager.headingFilter = 5
              _locationManager.startUpdatingHeading()
          }
      }
  
      func locationManager(_ manager: CLLocationManager, didUpdateHeading _newHeading: CLHeading) {
  
          if _newHeading.headingAccuracy &lt; 0 {
              return
          }
  
          let _theHeading : CLLocationDirection = _newHeading.trueHeading &gt; 0 ? _newHeading.trueHeading : _newHeading.magneticHeading
  
          self._heading = _theHeading
      }
  
      func locationManager(_ manager: CLLocationManager, didUpdateLocations _locations: [CLLocation]) {
  
          let _location = _locations[0]
  
          self._accuracy = _location.horizontalAccuracy
          self._latitude = _location.coordinate.latitude
          self._longitude = _location.coordinate.longitude
          self._velocity = _location.speed
  
          _timer = Timer.scheduledTimer(timeInterval: 1, target: self, selector: #selector(UpdateTimer), userInfo: nil, repeats: true)
  
          if _startLocation == nil {
              _startLocation = _locations.first
          } else {
              if let _lastLocation = _locations.last {
                  let _distance = _startLocation.distance(from: _lastLocation)
                  let _lastDistance = _lastLocation.distance(from: _lastLocation)
                  _traveledDistance += _lastDistance
  
                  if _traveledDistance &lt;= 100 {
                      PostNotificationWithLocation()
                      _traveledDistance = 0
                      _timer.invalidate()
                  }
              }
          }
          _lastLocation = _locations.last
  
          _motionManager = CMMotionManager()
          if _motionManager?.isDeviceMotionAvailable == true {
              _motionManager?.deviceMotionUpdateInterval = 0.1
  
              let queue = OperationQueue()
  
              _motionManager?.startDeviceMotionUpdates(to: queue, withHandler: { (_motion, _error) in
                  if let attitude = _motion?.attitude {
                      if(attitude.pitch == 30/M_PI) {
                          self.PostNotificationWithLocation()
                          self._timer.invalidate()
                      }
                  }
              })
          }
  
          _locationManager.stopUpdatingLocation()
      }
  
      func PostNotificationWithLocation() -&gt; Void {
           NotificationCenter.default.post(name: LOCATION_NOTIFICATION, object: nil, userInfo: ["latitude":_latitude, "longitude":_longitude, "velocity":_velocity, "traveledDistance":_traveledDistance])
      }
  
      func UpdateTimer() {
          _seconds += 1
          if _seconds == 10 {
              PostNotificationWithLocation()
              _timer.invalidate()
              _seconds = 0
          }
      }
  
  }
  </code></pre>
  
  <p>Thanks in advance !!</p>