UNLocationNotificationTrigger работает в симуляторе, но не на физическом устройстве
Я подписался на напоминание на основе местоположения со следующим кодом:
let center = CLLocationCoordinate2D(latitude: tapp.location.latitude, longitude: tapp.location.longitude)
let region = CLCircularRegion(center: center, radius: CLLocationDistance(tapp.reminder), identifier: tapp.name)
locationManager.distanceFilter = 100
locationManager.startMonitoring(for: region)
region.notifyOnEntry = true
region.notifyOnExit = false
let trigger = UNLocationNotificationTrigger(region: region, repeats: false)
let request = UNNotificationRequest(identifier: "\(tapp.location.latitude)|\(tapp.location.longitude)", content: content, trigger: trigger)
UNUserNotificationCenter.current().add(request, withCompletionHandler: nil)
Код работает, чтобы напомнить мне, когда я ввел регион в симуляторе iOS, но когда я загружаю приложение на физическое устройство и захожу в регион, он никогда не уведомляет меня.
Я помню, как читал кое-что о режиме низкого энергопотребления, влияющем на то, можете ли вы подписаться на уведомления о местоположении, есть ли что-то еще, что мешает приложению получать фоновые обновления? Кроме того, мой код правильный?
1 ответ
Я в похожей ситуации. Уведомления о местоположении запускаются на симуляторе, пробуются на переднем плане, в фоновом режиме и в закрытом состоянии приложения. На симуляторе срабатывает во всех случаях, а на реальном устройстве вообще не срабатывает, даже на переднем плане.
Вот мой код для запроса разрешения на местоположение
lazy var locationManager: CLLocationManager = createLocationManager()
private func createLocationManager() -> CLLocationManager {
let manager = CLLocationManager()
manager.allowsBackgroundLocationUpdates = true
return manager
}
init() {
super.init()
locationManager.delegate = self
locationManager.desiredAccuracy = kCLLocationAccuracyBest
locationManager.startMonitoringSignificantLocationChanges()
locationManager.startUpdatingLocation()
locationManager.allowsBackgroundLocationUpdates = true
}
func askForPermissionIfNeeded() {
if CLLocationManager.locationServicesEnabled() {
if !self.isLocationPermissionAsked {
locationManager.requestAlwaysAuthorization()
locationManager.startUpdatingLocation()
}
}
}
И вот мой код для запроса разрешений на уведомления
func requestNotificationAuthorization(completion: @escaping () -> Void) {
let options: UNAuthorizationOptions = [.sound, .alert, .badge]
notificationCenter
.requestAuthorization(options: options) { result, _ in
print("Notification Auth Request result: \(result)")
completion()
}
}
И вот мой код для регистрации уведомления о местоположении
private func registerNotification(region: CLRegion) {
let notificationContent = UNMutableNotificationContent()
notificationContent.title = "Active location nearby"
notificationContent.body = "Do you want to bla bla bla?"
notificationContent.sound = .default
let trigger = UNLocationNotificationTrigger(region: region, repeats: false)
let request = UNNotificationRequest(
identifier: region.identifier,
content: notificationContent,
trigger: trigger)
notificationCenter
.add(request) { error in
if error != nil {
print("Error: \(String(describing: error))")
}
}
}
Все это работает на симуляторе и не работает на устройстве... или, по крайней мере, уведомление не срабатывает.
НО я нашел обходной путь, который по крайней мере в моем случае работает -> Мониторинг региона
Я всегда запрашиваю разрешение на определение местоположения и отслеживаю, какие регионы с помощью locationManager подобны этому
locationManager.startMonitoring(for: fenceRegion)
И с помощью метода делегата didEnterRegion я регистрирую там уведомление и заменяю триггер на триггер времени вместо триггера местоположения
func locationManager(_ manager: CLLocationManager, didEnterRegion region: CLRegion) {
if region is CLCircularRegion {
registerNotification(region: region)
// Replace let timeTrigger = UNTimeIntervalNotificationTrigger(timeInterval: 1, repeats: false) in registerNotification
}
}
Я понимаю, что это не обязательно хорошее решение для всех, но, по крайней мере, в моем случае оно работает. Надеюсь, это поможет и другим