检测 requestAlwaysAuthorization 何时未调用 iOS 14

Posted

技术标签:

【中文标题】检测 requestAlwaysAuthorization 何时未调用 iOS 14【英文标题】:Detect when requestAlwaysAuthorization not called iOS 14 【发布时间】:2020-11-10 01:28:33 【问题描述】:

我正在尝试使用多步骤流程请求用户的位置;但是,当调用requestAlwaysAuthorization 时,如果它没有被执行,我想移动以显示一条消息。

让我通过展示我的流程来更好地解释

这是我目前的流程

    请求While in use 用户选择Allow Once -> 转到2 用户选择Allow While Using App -> 转到2 用户选择Don't Allow -> 显示错误信息 请求Always permission 用户选择 Keep Only While Using -> 显示错误消息(问题 #1:我无法检测到这个) 用户选择Change to Always Allow -> 显示成功消息

如果用户从1 选择Allow Once,我什至不能调用requestAlwaysAuthorization,因为调用它会导致任何结果,甚至Apple 状态

如果用户使用 Allow Once 响应 requestWhenInUseAuthorization(),则由于临时授权,Core Location 将忽略对 requestAlwaysAuthorization() 的进一步调用。

Source

我的目标是,如果用户从1 中选择Allow Once,那么应该一起跳过requestAlwaysAuthorization

如果从1 选择Allow Wile Using App 并从requestAlwaysAuthorization 选择Keep Only while using,那么我想知道那个状态。

我知道可以做到,只是不知道怎么做。这是一个可以实现我想要实现的应用程序

从第一张图片中,用户选择了Allow While Using App,然后选择了Keep Only While Using,他们能够检测到它,或者能够检测到对话出现的事实,并且在用户响应之前他们没有移动到第三张图片。

另一种情况如下:

从用户选择的第一张图片Allow Once 和从第二张图片,无论用户选择什么,他们都会转到图片 3,而不显示始终权限(请记住,第二张图片不是真正的权限,它只是用来欺骗用户的按钮);因此他们能够分辨出对话没有出现,或者用户从上一步中选择了Allow Once(一个或另一个,我不能做任何一个)。

显然我无法记录每个组合并以 gif 格式发布,所以如果您想体验应用程序名称是 Zenly

因此,最终目标是能够等待用户响应对话(如果出现对话),否则只需移动到下一个屏幕。

这是我所做的,引用自苹果

核心位置将授权保留为使用时。委托没有收到任何更新。

我想也许在总是请求时我也应该手动执行委托,所以我在函数 requestAlwaysLocation() 中添加了这一行

self.locationManagerDidChangeAuthorization(self.locationManager)

但是,这显然行不通,因为在Allow While Using App 是从步骤1 中选择的情况下,Change to Always Allow 是从步骤2 中选择的,现在委托将被调用两次...

然后我想如果我可以从步骤1 检测到配置When in Use,我也许可以绕过但我不知道该怎么做。

这是LocationManager的sn-p

    func requestWhenInUserLocation()  
        self.locationManager.requestWhenInUseAuthorization()
    
    
    func requestAlwaysLocation() 
        self.locationManager.requestAlwaysAuthorization()
    


    func locationManagerDidChangeAuthorization(_ manager: CLLocationManager) 
        print("authroizatino changed")
//        let accuracyAuthorization = manager.accuracyAuthorization
        let status = manager.authorizationStatus

        // -change function will just change some internal properties and will post a notification so views that subscribe to it can react accordingly.
        
        switch status 
            case CLAuthorizationStatus.authorizedAlways:
                self.change(permission: .Location, to: .Location(.Always))
                break
            case CLAuthorizationStatus.authorizedWhenInUse:
                self.change(permission: .Location, to: .Location(.WhenInUse))
                break
            case CLAuthorizationStatus.denied:
                self.change(permission: .Location, to: .Denied)
                break
            case CLAuthorizationStatus.notDetermined:
                self.change(permission: .Location, to: .NotDetermined)
                break
            case CLAuthorizationStatus.restricted:
                self.change(permission: .Location, to: .Location(.Restricted))
                break
            @unknown default:
                self.change(permission: .Location, to: .Unknown)
                break
        
    


我希望我能够清楚地解释我想要什么

【问题讨论】:

这看起来像是一个用例,您不应该尝试绕过 Apple 实施的流程。只需询问“始终”,然后启用后台位置更新。 ios会在适当的时候提示用户升级你的位置访问权限。 如何解决? Apple 确实允许您在任何时候提示always 许可。我认为您指的是我正在尝试检测Allow Once 或者在请求always 时权限保持不变。不幸的是,有这种要求的有效案例;例如,像Zenly 这样的应用程序没有它就无法运行,因此他们需要它作为入职培训的一部分。我正在构建的应用程序处于类似情况。我不想实现它,因为我明白为什么它可以被视为workaround,但它不是我的应用程序,这是客户的应用程序。 另外请注意,使用 iOS 14,您不必等待 iOS 选择何时升级通知。如果您像我一样将其分解为 2 个步骤,您可以随时提出请求。 我理解这个过程。更改的行为是在 iOS 13.4 中引入的,我在商店中有一个应用程序可以执行您正在尝试的操作,因为它确实需要始终获得许可,或者它只是不起作用。但是,如果你告诉用户为什么你总是需要,总是提示他们而你没有它,那么你就不得不忍受它。您可以在下次应用启动时再次检查。您还可以在 didBecomeActive 事件之后检查,因为这意味着对话框已被关闭 我曾尝试向他们解释这一点,但如果未提供always,他们坚持要阻止用户在入职期间访问应用程序。话虽如此,你写的最后一句话是golden key。非常感谢,我不知道我怎么从来没想过这样做。 hiding in plain sight 这句话在这里绝对适用。再次感谢。 【参考方案1】:

感谢@Paulw11,我能够解决它。其实很简单。

我不能在这里添加任何实现,因为它真的取决于一个人的用例,而且我使用的是 SwiftUI。

所以我所做的就是在按下Request Always 按钮时创建一个bool 状态并将其设置为true,我还有一个应用程序的活动状态的观察者这是解决这个问题的关键 我在bool 状态上也有一个观察者。

如果布尔状态发生变化,而应用的活动状态没有变化,则用户选择了Allow Once;但是,如果状态确实发生了变化,那么我会等待它再次处于活动状态。

如果它变为活动状态,我会检查位置权限,如果它仍然是When in Use,那么用户选择Keep Only While Using,否则他们选择Change to Always

所有学分都归于 Paulw11

编辑:如果用户从设置更改位置权限,我也有应用程序从后台进入前台的观察者

注意:如果您在 SwiftUI 中使用Combine,上述算法可以得到很大的改进。我写的大部分都没用,你可以订阅权限和应用的活动状态。

【讨论】:

以上是关于检测 requestAlwaysAuthorization 何时未调用 iOS 14的主要内容,如果未能解决你的问题,请参考以下文章

行人检测(人体检测)3:Android实现人体检测(含源码,可实时人体检测)

行人检测(人体检测)3:Android实现人体检测(含源码,可实时人体检测)

行人检测(人体检测)3:Android实现人体检测(含源码,可实时人体检测)

[计算机视觉]人脸应用:人脸检测人脸对比五官检测眨眼检测活体检测疲劳检测

行人检测(人体检测)1:人体检测数据集(含下载链接)

行人检测(人体检测)2:YOLOv5实现人体检测(含人体检测数据集和训练代码)