我如何检查用户是否在iOS 9或iOS 10上启用了远程通知?
如果用户没有允许或点击了“不允许”,我想切换一条消息,询问他们是否要启用通知。
我如何检查用户是否在iOS 9或iOS 10上启用了远程通知?
如果用户没有允许或点击了“不允许”,我想切换一条消息,询问他们是否要启用通知。
苹果建议使用UserNotifications
框架代替共享实例。因此,不要忘记导入UserNotifications
框架。由于该框架在iOS 10中是新的,因此只有构建iOS 10及以上版本的应用程序才能确保安全使用此代码。
let current = UNUserNotificationCenter.current()
current.getNotificationSettings(completionHandler: { (settings) in
if settings.authorizationStatus == .notDetermined {
// Notification permission has not been asked yet, go for it!
} else if settings.authorizationStatus == .denied {
// Notification permission was previously denied, go to settings & privacy to re-enable
} else if settings.authorizationStatus == .authorized {
// Notification permission was already granted
}
})
您可以查看官方文档以获取更多信息:https://developer.apple.com/documentation/usernotifications
iOS 10之后使用UNUserNotificationCenter
。首先需要import UserNotifications
,然后
let current = UNUserNotificationCenter.current()
current.getNotificationSettings(completionHandler: { permission in
switch permission.authorizationStatus {
case .authorized:
print("User granted permission for notification")
case .denied:
print("User denied notification permission")
case .notDetermined:
print("Notification permission haven't been asked yet")
case .provisional:
// @available(iOS 12.0, *)
print("The application is authorized to post non-interruptive user notifications.")
case .ephemeral:
// @available(iOS 14.0, *)
print("The application is temporarily authorized to post notifications. Only available to app clips.")
@unknown default:
print("Unknow Status")
}
})
这段代码适用于iOS 9及以下版本,如果是iOS 10,请使用上面的代码片段。
let isRegisteredForRemoteNotifications = UIApplication.shared.isRegisteredForRemoteNotifications
if isRegisteredForRemoteNotifications {
// User is registered for notification
} else {
// Show alert user is not registered for notification
}
我尝试了Rajat的解决方案,但在iOS 10(Swift 3)上对我没有用。它总是说推送通知已启用。以下是我解决问题的方法。如果用户已经点击了“不允许”或者你还没有询问用户,那么它会显示“未启用”。
let notificationType = UIApplication.shared.currentUserNotificationSettings!.types
if notificationType == [] {
print("notifications are NOT enabled")
} else {
print("notifications are enabled")
}
PS:iOS 10.0已经将currentUserNotificationSettings
方法标为过时,但它仍然可用。
如果您的应用程序支持iOS 10和iOS 8、9,请使用以下代码
// At the top, import UserNotifications
// to use UNUserNotificationCenter
import UserNotifications
那么,
if #available(iOS 10.0, *) {
let current = UNUserNotificationCenter.current()
current.getNotificationSettings(completionHandler: { settings in
switch settings.authorizationStatus {
case .notDetermined:
// Authorization request has not been made yet
case .denied:
// User has denied authorization.
// You could tell them to change this in Settings
case .authorized:
// User has given authorization.
}
})
} else {
// Fallback on earlier versions
if UIApplication.shared.isRegisteredForRemoteNotifications {
print("APNS-YES")
} else {
print("APNS-NO")
}
}
iOS 11中,Swift 4...
UNUserNotificationCenter.current().getNotificationSettings { (settings) in
if settings.authorizationStatus == .authorized {
// Already authorized
}
else {
// Either denied or notDetermined
UNUserNotificationCenter.current().requestAuthorization(options: [.alert, .sound, .badge]) {
(granted, error) in
// add your own
UNUserNotificationCenter.current().delegate = self
let alertController = UIAlertController(title: "Notification Alert", message: "please enable notifications", preferredStyle: .alert)
let settingsAction = UIAlertAction(title: "Settings", style: .default) { (_) -> Void in
guard let settingsUrl = URL(string: UIApplicationOpenSettingsURLString) else {
return
}
if UIApplication.shared.canOpenURL(settingsUrl) {
UIApplication.shared.open(settingsUrl, completionHandler: { (success) in
})
}
}
let cancelAction = UIAlertAction(title: "Cancel", style: .default, handler: nil)
alertController.addAction(cancelAction)
alertController.addAction(settingsAction)
DispatchQueue.main.async {
self.window?.rootViewController?.present(alertController, animated: true, completion: nil)
}
}
}
}
Use of unresolved identifier 'UNUserNotificationCenter'; did you mean 'NSNotificationCenter'?
- ChrisO@Rajat的回答不够。
isRegisteredForRemoteNotifications
表示您的应用程序已连接到APNS并获取设备令牌,这可以用于静默推送通知。currentUserNotificationSettings
是用于用户权限的,如果没有此权限,则无法向应用程序发送警报、横幅或声音推送通知。以下是检查:
static var isPushNotificationEnabled: Bool {
guard let settings = UIApplication.shared.currentUserNotificationSettings
else {
return false
}
return UIApplication.shared.isRegisteredForRemoteNotifications
&& !settings.types.isEmpty
}
对于iOS 10,你应该使用UserNotifications
框架来替代检查currentUserNotificationSettings
center.getNotificationSettings(completionHandler: { settings in
switch settings.authorizationStatus {
case .authorized, .provisional:
print("authorized")
case .denied:
print("denied")
case .notDetermined:
print("not determined, ask user for permission now")
}
})
推送通知可以通过多种方式发送到我们的应用程序,并且我们可以请求此功能。
UNUserNotificationCenter.current()
.requestAuthorization(options: [.alert, .sound, .badge])
用户可以随时打开设置应用并关闭其中任何一个,因此最好在settings
对象中检查这一点。
open class UNNotificationSettings : NSObject, NSCopying, NSSecureCoding {
open var authorizationStatus: UNAuthorizationStatus { get }
open var soundSetting: UNNotificationSetting { get }
open var badgeSetting: UNNotificationSetting { get }
open var alertSetting: UNNotificationSetting { get }
open var notificationCenterSetting: UNNotificationSetting { get }
}
iOS12和Swift 4都支持,同时也支持iOS13和Swift5。
我还为此创建了一个Git,你可以在这里查看。
只需将此单例文件添加到您的XCode项目中即可。
import Foundation
import UserNotifications
import UIKit
class NotificaionStatusCheck {
var window: UIWindow?
private var currentViewController : UIViewController? = nil
static let shared = NotificaionStatusCheck()
public func currentViewController(_ vc: UIViewController?) {
self.currentViewController = vc
checkNotificationsAuthorizationStatus()
}
private func checkNotificationsAuthorizationStatus() {
let userNotificationCenter = UNUserNotificationCenter.current()
userNotificationCenter.getNotificationSettings { (notificationSettings) in
switch notificationSettings.authorizationStatus {
case .authorized:
print("The app is authorized to schedule or receive notifications.")
case .denied:
print("The app isn't authorized to schedule or receive notifications.")
self.NotificationPopup()
case .notDetermined:
print("The user hasn't yet made a choice about whether the app is allowed to schedule notifications.")
self.NotificationPopup()
case .provisional:
print("The application is provisionally authorized to post noninterruptive user notifications.")
self.NotificationPopup()
}
}
}
private func NotificationPopup(){
let alertController = UIAlertController(title: "Notification Alert", message: "Please Turn on the Notification to get update every time the Show Starts", preferredStyle: .alert)
let settingsAction = UIAlertAction(title: "Settings", style: .default) { (_) -> Void in
guard let settingsUrl = URL(string: UIApplication.openSettingsURLString) else {
return
}
if UIApplication.shared.canOpenURL(settingsUrl) {
UIApplication.shared.open(settingsUrl, completionHandler: { (success) in
})
}
}
let cancelAction = UIAlertAction(title: "Cancel", style: .default, handler: nil)
alertController.addAction(cancelAction)
alertController.addAction(settingsAction)
DispatchQueue.main.async {
self.currentViewController?.present(alertController, animated: true, completion: nil)
}
}
}
在 ViewController 中访问此代码,请在 viewDidLoad 上使用以下方法:
NotificaionStatusCheck.shared.currentViewController(self)
notDetermined
情况,权限尚未被请求,那么将用户发送到设置页面有什么意义呢?在这种情况下应该要求获取权限。 - jzeferinoimport UserNotifications
private static func getNotificationPermissionString() -> Promise<String> {
let promise = Promise<String>()
if #available(iOS 10.0, *) {
let notificationCenter = UNUserNotificationCenter.current()
notificationCenter.getNotificationSettings { (settings) in
switch settings.authorizationStatus {
case .notDetermined: promise.resolve("not_determined")
case .denied: promise.resolve("denied")
case .authorized: promise.resolve("authorized")
}
}
} else {
let status = UIApplication.shared.isRegisteredForRemoteNotifications ? "authorized" : "not_determined"
promise.resolve(status)
}
return promise
}
private func checkPushNotificationAllowed(completionHandler: @escaping (Bool) -> Void) {
if #available(iOS 10.0, *) {
UNUserNotificationCenter.current().getNotificationSettings { (settings) in
if settings.authorizationStatus == .notDetermined || settings.authorizationStatus == .denied {
completionHandler(false)
}
else {
completionHandler(true)
}
}
}
else {
if let settings = UIApplication.shared.currentUserNotificationSettings {
if settings.types.isEmpty {
completionHandler(false)
}
else {
completionHandler(true)
}
}
else {
completionHandler(false)
}
}
}
class func isRegisteredForRemoteNotifications() -> Bool {
if #available(iOS 10.0, *) {
var isRegistered = false
let semaphore = DispatchSemaphore(value: 0)
let current = UNUserNotificationCenter.current()
current.getNotificationSettings(completionHandler: { settings in
if settings.authorizationStatus != .authorized {
isRegistered = false
} else {
isRegistered = true
}
semaphore.signal()
})
_ = semaphore.wait(timeout: .now() + 5)
return isRegistered
} else {
return UIApplication.shared.isRegisteredForRemoteNotifications
}
}
if
、if else
和if else
呢? - Jeremy Bader