当前位置权限对话框消失得太快

时间:2011-10-25 11:56:04

标签: objective-c ios core-location

我的应用程序获取用户的位置,获取坐标,并提供与目的地或来源的距离。所有这些可能的目的地都显示在表格视图中,因此我在填充表格的同时获得用户坐标。唯一的问题是,出现要求用户位置的警报视图然后消失得太快就无法点击它!

有没有办法在应用首次加载时手动显示此提醒?我尝试在应用程序加载时获取用户的位置以尝试强制显示警报,但这不起作用。

12 个答案:

答案 0 :(得分:631)

虽然很难追查,但解决方法非常简单。

通过大量试验和错误,我发现当您第一次尝试访问应用程序中的任何位置服务时会弹出位置访问对话框,如果{{},对话框将自行消失(无需任何用户交互)在用户响应对话框之前释放{1}}对象。

我在CLLocationManager方法中创建了CLLocationManager个实例。由于这是该方法的本地实例,因此该方法在方法完成执行后由ARC释放。实例一释放,对话框就消失了。解决方案相当简单。将viewDidLoad实例从方法级变量更改为类级实例变量。现在CLLocationManager实例仅在卸载类时才会释放。

答案 1 :(得分:5)

相同的症状,原因不同:不要连续多次拨打startUpdatingLocation

我意外地构造了这样的东西,使得代码无意中连续两次调用startUpdatingLocation,这显然很糟糕。它可能也与队列的选择有关,因为我等待开始更新等待网络请求的结果,但我不需要做任何GCD魔术来修复它...只需要确保我没有重复开始。

希望有人能够从我的痛苦中受益。 :)

答案 2 :(得分:4)

我陷入同样的​​问题(至少是出现症状)。 就我而言,问题出现在- (void)applicationWillResignActive:(UIApplication *)application;方法中,我正在发布我的CLLocationManager实例,作为准备后台转换的一部分。当我删除它并将其留在- (void)applicationDidEnterBackground:(UIApplication *)application;时,问题就消失了。
棘手的部分是核心位置警报DO暂停你的应用程序,当它仍处于前台时。
希望它会有所帮助你,花了我很多时间才发现那个混蛋:)

答案 3 :(得分:4)

我知道这是一个非常晚的回复。但它可能会帮助某人。 我也面临同样的问题,花了一个小时来确定问题。 起初我的代码是这样的。

CLLocationManager *locationManager = [[CLLocationManager alloc] init];
[locationManager startUpdatingLocation];

CLLocation *location = locationManager.location;
//my stuff with the location

    [locationManager release];

现在,位置警报迅速消失。 当我取消注释最后一行时,它正常工作。

   // [locationManager release];

答案 4 :(得分:3)

我也遇到了这个问题,但我的案例中的解决方案与接受的答案完全不同。

在我的应用中,我从stopUpdatingLocation拨打了applicationWillResignActive。这是一个问题,因为在出​​现权限对话框时会调用applicationWillResignActive。这在stopUpdatingLocation之后立即导致startUpdatingLocation,这就是对话框会立即消失的原因。

解决方案只是从stopUpdatingLocation调用applicationDidEnterBackground而不是。

答案 5 :(得分:2)

使用iOS模拟器时发生了这种情况。我确定它发生了,因为我的Run Scheme正在模拟一个位置。我认为这与在启动时调用 module.exports = (driver) -> InvitationSchema = new driver.schema( id: driver.id createdAt: type: Date 'default': Date.now senderId: driver.id receiverId: driver.id accepted: type: Boolean 'default': false rejected: type: Boolean 'default': false) InvitationSchema.index { senderId: 1, receiverId: 1}, { unique: true } InvitationSchema.index { receiverId: 1, senderId: 1}, { unique: true } return driver.db.model('invitation', InvitationSchema); 具有相同的效果,因此它正在关闭对话框。

取消选中“编辑方案”对话框中的“允许位置模拟”复选框可修复此问题。一旦它按照您的意愿工作并设置了权限,您就可以重新启用位置模拟,从那时起模拟器就可以正常工作。

答案 6 :(得分:2)

Swift 4和iOS 11

请务必在.plist文件中添加隐私行(始终 whenInUse )并将CoreLocation框架添加到您的项目< / p>

我更改后,位置权限对话框会正确显示:

locationManager.requestAlwaysAuthorization()

使用:

locationManager.requestWhenInUseAuthorization()

PS :我已尝试所有建议,但都失败了(请求授权给viewDidLoadvar而不是{{1}对于locationManager,请不要在请求后启动let ..我认为这是一个错误,我希望他们能尽快解决它。

答案 7 :(得分:1)

SWIFT 4 @Zoli解决方案看起来像:

class WhateverViewController: UIViewController {
    let locationManager = CLLocationManager() // here is the point of the @Zoli answer

    // some code
    override func viewDidLoad() {
        super.viewDidLoad()

        // some other code
        locationManager.requestWhenInUseAuthorization()
        // some other code
    }
}

答案 8 :(得分:1)

我将locationManager作为实例var,但在Swift 5,Xcode 11中仍然无济于事(见下文):

class MapViewController: UIViewController {
    
    var locationManager: CLLocationManager {
        let locationManager = CLLocationManager()
        locationManager.desiredAccuracy = .greatestFiniteMagnitude
        locationManager.delegate = self
        locationManager.requestWhenInUseAuthorization()
        return locationManager
    }
    
    override func viewDidLoad() {
        super.viewDidLoad()
        locationManager.startUpdatingLocation()
    }
}

但是,让locationManager var lazy解决了该问题:

class MapViewController: UIViewController {

    lazy var locationManager: CLLocationManager = {
        let locationManager = CLLocationManager()
        locationManager.desiredAccuracy = .greatestFiniteMagnitude
        locationManager.delegate = self
        locationManager.requestWhenInUseAuthorization()
        return locationManager
    }()

    override func viewDidLoad() {
        super.viewDidLoad()
        locationManager.startUpdatingLocation()
    }
}

答案 9 :(得分:0)

你最常将locationManager变量定义为全局对象。

"address1": {
    "city": "bng",
    "street": "dng",
    "zipcode": "23421"
}

"address2": {
    "city": "chn",
    "street": "as",
    "zipcode": "5645"
}

答案 10 :(得分:0)

我遇到了你的同样情况。

  • 我的解决方案已从局部变量更改为成员实例。
  • 原因是方法完成后本地?实例无效,包括本地变量(扩展我的locationManager)
  • 我的环境:Xcode9.3.1

#import 
@interface ViewController ()

@end

@implementation ViewController
@synthesize locManager; // after
- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view, typically from a nib.

    //MyLocationService *locManager = [[BSNLocationService alloc]init:nil]; // before. the loc. delegate did not work because the instance became invalid after this method.
    self->locManager= [[MyLocationService alloc]init:nil]; // after
    locManager.startService;
}

答案 11 :(得分:0)

我也遇到过类似的情况。调试后,我发现

let locationManager = CLLocationManager()

是在方法范围内调用的,但应全局调用。

为什么?

简而言之,方法返回后已释放locationManager。但是在用户给予或拒绝许可之前,不应释放它