2

I've just updated to the Xcode 9 and Swift 4 and it has broken at lot of my functions. One of which being how I get the user's location, zoom in on it on launch, detecting annotation selection and various other tasks. They don't work at all. My view controller class code is below.

import UIKit
import MapKit
import Firebase
import FirebaseDatabase
import Pulley
import CoreLocation

class ChildMapViewController: UIViewController, CLLocationManagerDelegate, MKMapViewDelegate {


    @IBOutlet weak var mapView: MKMapView!

    let manager = CLLocationManager()

    var isInitialized = false


    func startBackgroundLocationUpdates() {
        self.manager.delegate = self
        manager.requestWhenInUseAuthorization()
        manager.desiredAccuracy = kCLLocationAccuracyThreeKilometers
        manager.pausesLocationUpdatesAutomatically = true
        manager.activityType = .fitness
        manager.allowsBackgroundLocationUpdates = true
        manager.startMonitoringSignificantLocationChanges()
        manager.startUpdatingLocation()
    }

    func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
        let location = locations[0]
        if !isInitialized {
            isInitialized = true
            let span:MKCoordinateSpan = MKCoordinateSpanMake(0.01, 0.01)
            let myLocation:CLLocationCoordinate2D = CLLocationCoordinate2DMake(location.coordinate.latitude, location.coordinate.longitude)
            let region:MKCoordinateRegion = MKCoordinateRegionMake(myLocation, span)
            mapView.setRegion(region, animated: true)
            self.mapView.showsUserLocation = true
    }

}

    struct loc {
        let title: String
        let latitude: Double
        let longitude: Double
    }

    var locs = [
        loc(title: "New York, NY",    latitude: 40.713054, longitude: -74.007228),
        ]

    func placeAnnotations() {
        let annotations = locs.map { location -> MKAnnotation in
            let annotation = MKPointAnnotation()
            annotation.coordinate = CLLocationCoordinate2D(latitude: location.latitude, longitude: location.longitude)
            annotation.title = location.title

            return annotation
        }
        mapView.addAnnotations(annotations)
    }


    var position:PulleyPosition!

    func mapView(_ didSelectmapView: MKMapView, didSelect view: MKAnnotationView) {

        Shared.shared.annotation = view.annotation!



        if Shared.shared.annotation is MKUserLocation {
            Shared.shared.nameString = "My Location"
        } else {
            loadData()
        }
    }

    func mapView(_ mapView: MKMapView, didDeselect view:
        MKAnnotationView) {
        let drawerContent = UIStoryboard(name: "Main", bundle: nil).instantiateViewController(withIdentifier: "DrawerViewController")
        if let drawer = self.parent?.parent as? PulleyViewController {
            drawer.setDrawerContentViewController(controller: drawerContent, animated: false)
            drawer.setDrawerPosition(position: PulleyPosition.partiallyRevealed, animated: true)
        }
    }

    func loadData() {
        let number = (Shared.shared.annotation?.title)!
        if let number = number {
            let ref = FIRDatabase.database().reference()

            ref.child("safehouses").child("\(number)").observeSingleEvent(of: .value, with: { snapshot in
                let snapDict = snapshot.value as? NSDictionary
                let name = snapDict?["name"] as? String
                let phone = snapDict?["phone"] as? String


                let current = CLLocation(latitude: (self.manager.location?.coordinate.latitude)!, longitude: (self.manager.location?.coordinate.longitude)!)
                let destination = CLLocation(latitude: Shared.shared.annotation.coordinate.latitude, longitude: Shared.shared.annotation.coordinate.longitude)

                let distance2 = current.distance(from: destination)
                let distance1 = round(distance2)


                if distance1 >= 1000 {
                    if distance1 < 10000 {
                        let distance3 = distance1/1000
                        let distance = Double(round(10*distance3)/10)
                        Shared.shared.typeString = "Safehouse · " + String(distance) + " km"
                    } else {
                        let distance3 = distance1/1000
                        let distance = round(distance3)
                        Shared.shared.typeString = "Safehouse · " + String(distance) + " km"
                    }
                } else {
                    let distance = self.forTailingZero(temp: distance1)
                    Shared.shared.typeString = "Safehouse · " + distance + " m"
                }



                if let name = name {
                    if let phone = phone {
                        Shared.shared.nameString = name
                        Shared.shared.phoneString = phone
                        let drawerContent = UIStoryboard(name: "Main", bundle: nil).instantiateViewController(withIdentifier: "NewDrawerViewController")
                        if let drawer = self.parent?.parent as? PulleyViewController {
                            drawer.setDrawerContentViewController(controller: drawerContent, animated: false)
                            drawer.setDrawerPosition(position: PulleyPosition.partiallyRevealed, animated: true)
                        }

                    }
                }
            })

        }
    }



    func forTailingZero(temp: Double) -> String{
        var tempVar = String(format: "%g", temp)
        return tempVar
    }

    func loop() {
        let ref = FIRDatabase.database().reference()
        ref.child("safehouses").observeSingleEvent(of: .value, with: { snapshot in
            let snapDict = snapshot.value as? NSDictionary
            let ii = snapDict?["number"] as? Int
            let iii = Int(ii!)
            var i = 1
            while i <= iii{
                let name = String(i)
                ref.child("safehouses").child("\(i)").observeSingleEvent(of: .value, with: { snapshot in
                    let snapDict = snapshot.value as? NSDictionary
                    let longitude = snapDict?["longitude"]
                        as? String
                    let latitude = snapDict?["latitude"] as? String

                    if let longitude = longitude {
                        if let latitude = latitude {
                            let latitude1 = Double(latitude)
                            if let latitude1 = latitude1 {
                                let longitude1 = Double(longitude)
                                if let longitude1 = longitude1 {
                                    self.locs.append(loc(title: name, latitude: latitude1, longitude: longitude1))
                                    self.placeAnnotations()
                                }
                            }
                        }
                    }
                })
                i = i + 1
            }

        })
    }


    @IBOutlet weak var menuButton: UIBarButtonItem!

    override func viewDidLoad() {
        super.viewDidLoad()

        self.revealViewController().rearViewRevealWidth = 175
        self.revealViewController().toggleAnimationType = SWRevealToggleAnimationType.easeOut

        if self.revealViewController() != nil {
            menuButton.target = self.revealViewController()
            menuButton.action = #selector(SWRevealViewController.revealToggle(_:))
            self.view.addGestureRecognizer(self.revealViewController().panGestureRecognizer())
        }



        loop()
        mapView.delegate = self
        manager.delegate = self
        manager.desiredAccuracy = kCLLocationAccuracyBest
        manager.requestAlwaysAuthorization()
        Shared.shared.mapView = self.mapView
        startBackgroundLocationUpdates()
    }



}

final class Shared {
    static let shared = Shared()

    var nameString : String!
    var phoneString : String!
    var annotation : MKAnnotation!
    var mapView : MKMapView!
    var typeString : String!

}
halfer
  • 19,824
  • 17
  • 99
  • 186
Max Kortge
  • 527
  • 7
  • 23

2 Answers2

1

First add these property in info.plist

<key>NSLocationAlwaysAndWhenInUseUsageDescription</key>
    <string>description1</string>
    <key>NSLocationAlwaysUsageDescription</key>
    <string>description2</string>
    <key>NSLocationUsageDescription</key>
    <string>description3</string>
    <key>NSLocationWhenInUseUsageDescription</key>
    <string>accept to get location</string>
    <key>UIBackgroundModes</key>

And then after copy this view controller in your project

import UIKit
import CoreLocation
class ViewController: UIViewController,CLLocationManagerDelegate {

 var locationManager:CLLocationManager!
    override func viewDidLoad() {
        super.viewDidLoad()
        determineMyCurrentLocation()
        // Do any additional setup after loading the view.
    }


    func determineMyCurrentLocation() {
        locationManager = CLLocationManager()
        locationManager.delegate = self
        locationManager.desiredAccuracy = kCLLocationAccuracyBest
        locationManager.requestAlwaysAuthorization()
        locationManager!.allowsBackgroundLocationUpdates = true
        locationManager!.pausesLocationUpdatesAutomatically = false
        let value =   locationManager.startMonitoringSignificantLocationChanges()

        if CLLocationManager.locationServicesEnabled() {
            locationManager.startUpdatingLocation()
        }
    }
    func locationManager(_ manager: CLLocationManager, didStartMonitoringFor region: CLRegion) {
         print("ankur :- \(region)")
    }
    func locationManager(_ manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) {
        let userLocation:CLLocation = locations[0] as CLLocation

        print("user latitude = \(userLocation.coordinate.latitude)")
        print("user longitude = \(userLocation.coordinate.longitude)")
    }

    func locationManager(_ manager: CLLocationManager, didFailWithError error: Error)
    {
        print("Error \(error)")
    }

}

Last step :- Open Capabilities -> In background modes -> click on location updates

If any query comment it

Ankur Purwar
  • 275
  • 2
  • 9
0

You need to add these keys in info plist :

<key>UIBackgroundModes</key>
<array>
    <string>location</string>
</array>
Vini App
  • 7,339
  • 2
  • 26
  • 43
  • Only when I select an annotation and run my function. It throws `Thread 1: EXC_BREAKPOINT (code=1, subcode=0x100795c6c)` on this line of code ` let current = CLLocation(latitude: (self.manager.location?.coordinate.latitude)!, longitude: (self.manager.location?.coordinate.longitude)!)` – Max Kortge Sep 25 '17 at 06:36