Objective C,iOS 7 - CLLocationManager:didUpdateLocations只被调用一次

时间:2014-02-14 00:16:27

标签: ios objective-c gps cllocationmanager

编辑:好的,我刚刚注意到问题不包括在iOS 7中。但是,我仍然无法解决它,所以我支持我会尝试下面的sugestions。谢谢大家!

?嗨!我正在编写导航器应用程序,我需要尽可能更新用户位置。我有两个使用CLLocation管理器的View Controller。在这两个中我添加了这一行:

#import <CoreLocation/CoreLocation.h>

然后将其添加到接口声明中,我将其设置为.h文件中的属性,然后进行合成:

@property (strong, nonatomic) CLLocationManager *locationManager;

之后,我在viewDidLoad中启动de locationManager,这样:

if(self){
    locationManager = [[CLLocationManager alloc] init];
    //locationManager.delegate = self;
    [locationManager setDelegate:self];
    [locationManager setDistanceFilter:kCLHeadingFilterNone];
    [locationManager setDesiredAccuracy:kCLLocationAccuracyBestForNavigation];
    [locationManager startUpdatingLocation];
}

这是我的委托方法。

第一个视图:

#pragma mark - CLLocationManagerDelegate

- (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error
{
    NSLog(@"didFailWithError: %@", error);
    UIAlertView *errorAlert = [[UIAlertView alloc]
                           initWithTitle:@"Error" message:@"Failed to Get Your Location" delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil];
    [errorAlert show];
}

- (void)locationManager:(CLLocationManager *)manager didUpdateToLocation:(CLLocation *)newLocation fromLocation:(CLLocation *)oldLocation
{
    NSLog(@"didUpdateToLocation: %@", newLocation);
    CLLocation *currentLocation = newLocation;

    if (currentLocation != nil) {
        homeLatitude = [[NSString stringWithFormat:@"%.8f",  currentLocation.coordinate.latitude] doubleValue];
        homeLongitude = [[NSString stringWithFormat:@"%.8f", currentLocation.coordinate.longitude] doubleValue];
        NSLog(@"Updated! -> hl = %f, hlg = %f", homeLatitude, homeLongitude);
    }
}

对于第二种观点。正如您所看到的,我用didUpdateLocations替换了旧的didUpdateToLocation,这是一种绝望的尝试。

#pragma mark - CLLocationManagerDelegate

- (void)locationManager:(CLLocationManager *)manager didFailWithError:(NSError *)error
{
    NSLog(@"didFailWithError: %@", error);
    UIAlertView *errorAlert = [[UIAlertView alloc]
                           initWithTitle:@"Error" message:@"Failed to Get Your Location"       delegate:nil cancelButtonTitle:@"OK" otherButtonTitles:nil];
    [errorAlert show];
}

/*- (void)locationManager:(CLLocationManager *)manager didUpdateToLocation:(CLLocation   *)newLocation fromLocation:(CLLocation *)oldLocation
{
    NSLog(@"didUpdateToLocation: %@", newLocation);
    CLLocation *currentLocation = newLocation;

    if (currentLocation != nil) {
        NSLog(@"Tarzan boy");
        _testLabel.text = [NSString stringWithFormat:@"Oh DAMN!!!!"];
    }
}*/

-(void)locationManager:(CLLocationManager *)manager didUpdateLocations:(NSArray *)locations {
    NSLog(@"didUpdateToLocation: %@", [locations lastObject]);
    CLLocation *currentLocation = [locations lastObject];
    if (currentLocation != nil) {
        currentLatitude = [[NSString stringWithFormat:@"%.8f", currentLocation.coordinate.latitude] doubleValue];
        currentLongitude = [[NSString stringWithFormat:@"%.8f", currentLocation.coordinate.longitude] doubleValue];
        NSLog(@"Updated! (MapWithRoutesViewController) -> hl = %f, hlg = %f", currentLatitude, currentLongitude);
        _testLabel.text = [NSString stringWithFormat:@"Update! -> hl = %f, hlg = %f", currentLatitude, currentLongitude];

        //Aquí es donde borramos el lugar al que llegaron.
        if(mapView){
            if(followMe){
                CLLocationCoordinate2D *c = &((CLLocationCoordinate2D){.latitude = currentLatitude, .longitude = currentLongitude});
                [mapView.mapView as_setCenterCoordinate:*c zoomLevel:32 animated:NO];
                _ourStepper.value = [mapView.mapView as_zoomLevel];
            }

        if([mapView getNearestDestinyDistance:currentLocation] < 150.0){
            NSLog(@"Hay que eliminar el primer destino del MapView");
            mapView.destinoActual++;
        }

        if([mapView getNearestPointDistance:currentLocation] > 200.0){
            NSLog(@"Hay que recalcular la ruta al destinoActual");
            SpinnerView *spinner = [SpinnerView loadSpinnerIntoView:self.view];
            spinner.tag = 98;
            while (![mapView recalculateRoutesTo:currentLocation]) {
                //do nothin...
            }
            [spinner removeSpinner];

        }
    }
}
//[locationManager stopUpdatingLocation];
}

如您所见,行

//[locationManager stopUpdatingLocation];

被评论。好吧,问题是让我发疯的是上面的代码在第一个视图控制器中作为魅力,并按照我的预期定期更新。但在第二种观点中,它只是第一次起作用,并且永远不会再次更新。我在不同的时间对这些方法进行了编程,所以我不记得我是否对第一个视图做了一些事情。但它们在同一个应用程序中,所以我认为库或权限没有问题。欢迎任何帮助或提示,谢谢!

3 个答案:

答案 0 :(得分:2)

首先,如果您正在进行导航,则应注册重要更改通知。请阅读here上的文档。效率更高。当你不使用它时你将不得不关闭它,但它会好得多。支持它一直回到iOS 4.这肯定是99%的用户群。

答案 1 :(得分:0)

我的应用程序中有类似的情况,并实现了一个处理所有位置更新的单例,然后将NSNotificaitons触发到前台线程。

  • 创建一个处理位置更新的单例类View
  • 注册以收听LOCATION_CHANGE更新或许背景
  • 单例对象注册为位置管理器的委托

这可能不是您正在寻找的答案,但我知道它适用于我的情况。

答案 2 :(得分:0)

找到解决方案here。当我以这种方式启动时,locationManager可以工作:

if(self){
     locationManager = [[CLLocationManager alloc] init];
     [locationManager setDelegate:self];
     [locationManager setDistanceFilter:kCLHeadingFilterNone];
     //change the desired accuracy to kCLLocationAccuracyBest
     [locationManager setDesiredAccuracy:kCLLocationAccuracyBest];
     //SOLUTION: set setPausesLocationUpdatesAutomatically to NO
     [locationManager setPausesLocationUpdatesAutomatically:NO];
     [locationManager startUpdatingLocation];
}

我会像Rob建议的那样在表演中工作。感谢大家的帮助!