iOS 定位服务提示未向用户显示

iOS location services prompt not being shown to users

提问人:boomersooner 提问时间:11/8/2023 最后编辑:boomersooner 更新时间:11/9/2023 访问量:65

问:

因此,我的 SwiftUI 应用程序遇到了一个独特的问题,该问题需要始终访问用户的位置。调用时不显示权限提示(测试是在 iOS 17.0.3 上的物理设备上完成的,并且应用程序在再次运行之前被卸载)。请求授权代码如下所示,所有打印语句都显示用户登录后已触发请求,但一旦完成,授权状态为零。info.plist 值也都是正确的。

.onReceive(authViewModel.$isSignedIn) { isSignedIn in
            if isSignedIn {
                locationManager.requestPermission()
            }
        }

位置管理器:

func locationManager(_ manager: CLLocationManager, didChangeAuthorization status: CLAuthorizationStatus) {
    DispatchQueue.main.async {
        self.authorizationStatus = status
    }
    print("Authorization status changed: \(status.rawValue)")

    switch status {
    case .notDetermined:
        print("Permission not determined, requesting permission.")
        locationManager.requestWhenInUseAuthorization()
    case .restricted, .denied:
        print("Location access restricted or denied.")
    case .authorizedAlways, .authorizedWhenInUse:
        print("Location access granted.")
        // Optionally setup geofences here if needed
    @unknown default:
        fatalError("Unhandled authorization status: \(status.rawValue)")
    }
}

请求权限方式:

class LocationManager: NSObject, ObservableObject, CLLocationManagerDelegate {
    private var locationManager = CLLocationManager()
    @Published var authorizationStatus: CLAuthorizationStatus

//..........Other methods

    func requestPermission() {
        DispatchQueue.main.async {
            self.locationManager.requestWhenInUseAuthorization()
        }
    }

主应用文件:

struct myApp: App {
    @UIApplicationDelegateAdaptor(AppDelegate.self) var appDelegate
    @StateObject var authViewModel = UserAuthViewModel()
    @StateObject var barViewModel = BarViewModel()
    @StateObject private var locationManager = LocationManager.shared

控制台输出:

Authorization status changed: 0

Permission not determined, requesting permission.

Starting location request permissions

Requesting location permission.

Location permissions requested

我尝试添加延迟以确保在应用程序处于前台并且所有 UI 组件都已加载时调用提示。

.onAppear {
        DispatchQueue.main.asyncAfter(deadline: .now() + 3) {
            barViewModel.fetchData()
            print("Starting location request permissions")
            self.requestLocationPermission()
            print("Location permissions requested")
        }
    }

即使我修改了我的应用程序委托以在启动时调用请求方法,它仍然不会提示用户:

class AppDelegate: NSObject, UIApplicationDelegate {
    
    var locationManager: LocationManager?
    
    func application(_ application: UIApplication, didFinishLaunchingWithOptions launchOptions: [UIApplication.LaunchOptionsKey: Any]?) -> Bool {
        FirebaseApp.configure()
        
        // Setup location manager
        self.locationManager = LocationManager.shared
        self.locationManager?.requestPermission() // Request permission as soon as the app launches
        
        return true
    }
}
iOS Swift iPhone SwiftUI

评论

0赞 Teja Nandamuri 11/8/2023
locationManager.requestPermission()似乎不是一个正确的方法。这是 CoreLocation 方法还是您的方法?
0赞 Paulw11 11/8/2023
是的,寿命是多少?它是注入到环境中还是注入环境中?提示未显示的一个常见原因是基础被解除分配。locationManager@StateObjectCLLocationManager
0赞 boomersooner 11/8/2023
嗨 - 是的,它是使用状态对象注入到环境中的。我也刚刚在原始帖子中添加了请求权限方法。
0赞 Paulw11 11/8/2023
尝试从语句中删除 。此时,您不应请求授权。locationManager.requestWhenInUseAuthorization().notDeterminedcase

答:

0赞 malhal 11/8/2023 #1

您不能在 SwiftUI 中使用 DispatchQueue,因为 View 结构只是没有生存期的值,回调将位于已经消失的旧值上。

视图模型类术语在 SwiftUI 中没有意义,因为视图结构体的工作是保存用于稍后构建 UI 的视图数据。

onReceive 是一个非常古老的修饰符,自从我们有 onChange 以来,现在已经真正有用了。

使另一个控制器类 AuthorizationController 具有仅用于授权的位置管理器委托。请求此类 init 中的权限,因为这发生在 on 自动出现。制作一个@Published var isAuthorized bool。在 Views 正文中,创建一个 if 来检查此布尔值,然后初始化另一个具有自己的状态对象 LocationController,该对象具有另一个位置管理器并具有位置更新委托方法。这样,如果授权发生更改,则此视图将被销毁,位置委托状态对象也将随之销毁。

评论

0赞 boomersooner 11/9/2023
非常感谢。仍然掌握 SwiftUI 的窍门,因此了解这个旧词汇不再适用会有所帮助。我将回顾我的整个项目并进行这些更改。
0赞 boomersooner 11/9/2023 #2

想通了!将键添加到自定义目标属性中,并在进一步查看后发现我的 info.plist 文件实际上没有分配给任何目标,这可能是问题所在。