2013-04-18 66 views
5

我开始更新当前位置,当视图确实出现时,并且只要调用locationManager:didUpdateLocations:就停止更新位置。但为什么总是多次调用locationManager:didUpdateLocations:?我错过了什么?locationManager:didUpdateLocations:总是被多次调用

#import "ViewController.h" 

@interface ViewController(){ 
    CLLocationManager *locationManager; // location manager for current location 
} 
@end 

@implementation ViewController 
- (void)viewDidLoad 
{ 
    [super viewDidLoad]; 
} 

- (void)viewDidAppear:(BOOL)animated 
{ 
    [super viewDidAppear:animated]; 
    [self startUpdatingCurrentLocation]; 
} 

- (void)startUpdatingCurrentLocation 
{ 
    if (!locationManager) 
    { 
     locationManager = [[CLLocationManager alloc] init]; 
     [locationManager setDelegate:self]; 
     locationManager.distanceFilter = 10.0f; // we don't need to be any more accurate than 10m 
    } 
    [locationManager startUpdatingLocation]; 
} 

-(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations{ 
    [locationManager stopUpdatingLocation]; 
} 
@end 
+0

http://stackoverflow.com/questions/22292835/how-to-stop -dultiple-times-method-calling-of-didupdatelocations-in-ios – Sanju 2016-05-27 10:02:25

回答

7

可能取决于您设置到locationManager的准确性。您有三种本地化的Cell Radio,WiFi Map,GPS。如果您将精度设置得最好,位置管理器将继续检查您的位置,如果精度更高的位置超出距离过滤器的范围,委托方法将再次被调用。

+0

why [locationManager stopUpdatingLocat离子]不能立即停止位置更新? – 2013-04-18 07:43:04

+1

可能不是,因为位置队列来自硬件缓冲区,但是如果问题存在,那么只需在停止并检查之前添加一个静态BOOL即可。如果BOOL说你已经停止从该方法返回。 – Andrea 2013-04-18 07:59:18

+0

是的,这是一个解决方案。 – 2013-04-18 08:01:17

3

SWIFT版本

我犯了一个辅助类为HelperLocationManager,并增加了notification- observer模式

import UIKit 
import CoreLocation 



class HelperLocationManager: NSObject { 

    var locationManager = CLLocationManager() 
    static let sharedInstance = HelperLocationManager() 
    var currentLocation :CLLocation? 
    var notGotUserLocation = true 

    override init() { 

     super.init() 

     var code = CLLocationManager.authorizationStatus() 

     if code == CLAuthorizationStatus.NotDetermined { 

      locationManager.requestAlwaysAuthorization() 
      locationManager.requestWhenInUseAuthorization() 

     } 
     locationManager.requestAlwaysAuthorization() 
     locationManager.requestWhenInUseAuthorization() 
     locationManager.delegate = self 
     locationManager.distanceFilter = 100; 

    } 


} 


extension HelperLocationManager: CLLocationManagerDelegate{ 


    func locationManager(manager: CLLocationManager!, didUpdateLocations locations: [AnyObject]!) { 

      var locValue = locations.last as! CLLocation 
      println(locValue) 
      self.currentLocation = locValue 
      NSNotificationCenter.defaultCenter().postNotificationName("sendCurrentAddressToViewController", object:self.currentLocation) 
      notGotUserLocation = false 


    } 

    func locationManager(manager: CLLocationManager!, didFailWithError error: NSError!) { 

     println("Your error is ", error.localizedDescription) 

    } 


} 

现在,如果你Viewcontroller类需要的位置,然后放在一个观察者有

var helperLocation:HelperLocationManager? 

viewDidLoad as

 override func viewDidLoad() { 

     helperLocation = HelperLocationManager() 
     NSNotificationCenter.defaultCenter().addObserver(self, selector: "getCurrentAddressToViewController:", name: "sendCurrentAddressToViewController", object: nil) 

    } 

//和观察者

func getCurrentAddressToViewController(notification: NSNotification) { 

     currentLocation = notification.object as? CLLocation 
     NSNotificationCenter.defaultCenter().removeObserver(self, name: "sendCurrentAddressToViewController", object: nil) 

    } 

//虽然didUpdateLocation被多次调用你只能得到因为删除observer你的位置之后的一个时间位置。

编辑:我refractored这个辅助类,这样你不需要添加notificationobserver模式

class HelperLocationManager: NSObject { 

    private lazy var locationManager = CLLocationManager() 
    static let sharedInstance = HelperLocationManager() 
    var currentLocation :CLLocation? 

    override init() { 

     super.init() 
     locationManager.desiredAccuracy = kCLLocationAccuracyBest 
     locationManager.delegate = self 
    } 
} 

extension HelperLocationManager: CLLocationManagerDelegate{ 

    func locationManager(manager: CLLocationManager, didChangeAuthorizationStatus status: CLAuthorizationStatus) { 

     switch status { 

     case CLAuthorizationStatus.NotDetermined: 

      locationManager.requestWhenInUseAuthorization() 


     case CLAuthorizationStatus.Restricted: 

      PrinterHelper.messagePrinter("Restricted Access to location") 

     case CLAuthorizationStatus.Denied: 

      PrinterHelper.messagePrinter("User denied access to location") 

     case CLAuthorizationStatus.AuthorizedWhenInUse: 

      if #available(iOS 9.0, *) { 

       locationManager.requestLocation() 

      } else { 

       locationManager.startUpdatingLocation() 
      } 

     default: 

      PrinterHelper.messagePrinter("default authorization") 

     } 
    } 

    func locationManager(manager: CLLocationManager, didUpdateLocations locations: [CLLocation]) { 

     let locValue = locations.last 
     HelperLocationManager.sharedInstance.currentLocation = locValue 
     locationManager.stopUpdatingLocation() 

    } 

    func locationManager(manager: CLLocationManager, didFailWithError error: NSError) { 

     PrinterHelper.errorPrinter(error.localizedDescription) 

    } 
} 

视图控制器,你需要得到用户许可

var helperLocationManager:HelperLocationManager? 
viewDidLoad

 override func viewDidLoad() { 

     helperLocationManager = HelperLocationManager.sharedInstance 


    } 

而得到的位置,你需要调用singleton属性currentLocation作为

if let userCurentLoc = HelperLocationManager.sharedInstance.currentLocation{ 

      //userCurrentLoc is the user Location 

     } 
0

以补充阿尼什的答案,如果你想知道当你的助手类没有叫位置更新(即当您已关闭您的位置服务),则可以使用locationManager:didChangeAuthorizationStatus:方法管理这一点,如果不允许你的位置,你可以调用另一个notification- observer

func locationManager(manager: CLLocationManager, didChangeAuthorizationStatus status: CLAuthorizationStatus) { 
    var shouldIAllow = false 

    switch status { 
    case CLAuthorizationStatus.Restricted: 
     locationStatus = "Restricted Access to location" 
    case CLAuthorizationStatus.Denied: 
     locationStatus = "User denied access to location" 
    case CLAuthorizationStatus.NotDetermined: 
     locationStatus = "Status not determined" 
    default: 
     locationStatus = "Allowed to location Access" 
     shouldIAllow = true 
    } 

    if (shouldIAllow == true) { 
     print("Location to Allowed") 
     // Start location services 
     locationManager!.startUpdatingLocation() 
    } else { 
     print("Denied access: \(locationStatus)") 
     NSNotificationCenter.defaultCenter().postNotificationName("deniedLocation", object:locationStatus) 
    } 
}