Search code examples
iosswiftdistancecore-locationmeasure

Measure distance in real time with CoreLocation in Swift


I'm making an app that measure's speed and distance in real time. so I'm having problem with measuring distance. I tried to figure out something by getting location variable outside of function by return. But if I do this, speed measurement doesn't work. So how can I start measuring distance when "start" tapped then stop when "stop" button tapped?

@IBAction func startStopButtonDidTouch(_ sender: UIButton) {
    if isStarted { //When tapped STOP
        timer?.invalidate()
        isStarted = false
        locationManager.stopUpdatingLocation()
        startStopButton.setTitle("START", for: .normal)
   
    } else { //When tapped START
        locationManager.startUpdatingLocation()
        timer = Timer.scheduledTimer(timeInterval: 1, target: self, selector: #selector(updateTimeLabel), userInfo: nil, repeats: true)
        isStarted = true
        startStopButton.setTitle("STOP", for: .normal)
    }
}

func locationManager (_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
    let location = locations[0]
    speedLabel.text = "\(Int(location.speed * 3.6))" 
}

Solution

  • Starting the location updates you will get updates in the didUpdateLocations method.

    This method will work fine to start the location updates and to stop it.

    var startLocation:CLLocation!
    @IBAction func startStopButtonDidTouch(_ sender: UIButton) {
        if isStarted { //When tapped STOP
            timer?.invalidate()
            isStarted = false
            locationManager.stopUpdatingLocation()
            startStopButton.setTitle("START", for: .normal)
       
      } else { //When tapped START
        locationManager.startUpdatingLocation()
        isStarted = true
        startStopButton.setTitle("STOP", for: .normal)
       }
    }
    

    Here you have to update your labels with distance and speed in real-time.

    func locationManager (_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) 
    {
                let location = locations[0]
                speedLabel.text = "\(Int(location.speed * 3.6))"
       if (startLocation == nil)
       {
          startLocation = location;
       }
       let endLocation = location;
                //Distance measure code will be placed here.
       //In KM
       let distance = startLocation.distance(from: endLocation) / 1000
    }