Antworten:
Rufen Sie an enabledRemoteNotificationsTypes
und überprüfen Sie die Maske.
Beispielsweise:
UIRemoteNotificationType types = [[UIApplication sharedApplication] enabledRemoteNotificationTypes];
if (types == UIRemoteNotificationTypeNone)
// blah blah blah
iOS8 und höher:
[[UIApplication sharedApplication] isRegisteredForRemoteNotifications]
iOS 8
und höher ist falsch, da nur geprüft wird, ob der Benutzer für die Remote-Benachrichtigung registriert ist. Laut Dokumentation:This method reflects only the successful completion of the remote registration process that begins when you call the registerForRemoteNotifications method. This method does not reflect whether remote notifications are actually available due to connectivity issues. The value returned by this method takes into account the user’s preferences for receiving remote notifications.
[[UIApplication sharedApplication] currentUserNotificationSettings];
Quantumpotatos Ausgabe:
Wo types
ist gegeben durch
UIRemoteNotificationType types = [[UIApplication sharedApplication] enabledRemoteNotificationTypes];
man kann verwenden
if (types & UIRemoteNotificationTypeAlert)
anstatt
if (types == UIRemoteNotificationTypeNone)
Hier können Sie nur überprüfen, ob Benachrichtigungen aktiviert sind (und sich keine Gedanken über Sounds, Abzeichen, Benachrichtigungscenter usw. machen). Die erste Codezeile ( types & UIRemoteNotificationTypeAlert
) wird zurückgegeben, YES
wenn "Warnstil" auf "Banner" oder "Warnungen" eingestellt ist und NO
wenn "Warnstil" unabhängig von anderen Einstellungen auf "Keine" eingestellt ist.
grantedSettings.types.contains(notificationType)
In der neuesten Version von iOS ist diese Methode jetzt veraltet. Um sowohl iOS 7 als auch iOS 8 zu unterstützen, verwenden Sie:
UIApplication *application = [UIApplication sharedApplication];
BOOL enabled;
// Try to use the newer isRegisteredForRemoteNotifications otherwise use the enabledRemoteNotificationTypes.
if ([application respondsToSelector:@selector(isRegisteredForRemoteNotifications)])
{
enabled = [application isRegisteredForRemoteNotifications];
}
else
{
UIRemoteNotificationType types = [application enabledRemoteNotificationTypes];
enabled = types & UIRemoteNotificationTypeAlert;
}
UserNotifications
. Leider habe ich jetzt keine vollständige Antwort.
Aktualisierter Code für swift4.0, iOS11
import UserNotifications
UNUserNotificationCenter.current().getNotificationSettings { (settings) in
print("Notification settings: \(settings)")
guard settings.authorizationStatus == .authorized else { return }
//Not authorised
UIApplication.shared.registerForRemoteNotifications()
}
Code für swift3.0, iOS10
let isRegisteredForRemoteNotifications = UIApplication.shared.isRegisteredForRemoteNotifications
if isRegisteredForRemoteNotifications {
// User is registered for notification
} else {
// Show alert user is not registered for notification
}
Ab iOS9 ist Swift 2.0 UIRemoteNotificationType veraltet. Verwenden Sie den folgenden Code
let notificationType = UIApplication.shared.currentUserNotificationSettings!.types
if notificationType == UIUserNotificationType.none {
// Push notifications are disabled in setting by user.
}else{
// Push notifications are enabled in setting by user.
}
Überprüfen Sie einfach, ob Push-Benachrichtigungen aktiviert sind
if notificationType == UIUserNotificationType.badge {
// the application may badge its icon upon a notification being received
}
if notificationType == UIUserNotificationType.sound {
// the application may play a sound upon a notification being received
}
if notificationType == UIUserNotificationType.alert {
// the application may display an alert upon a notification being received
}
Unten finden Sie ein vollständiges Beispiel, das sowohl iOS8 als auch iOS7 (und niedrigere Versionen) abdeckt. Bitte beachten Sie, dass Sie vor iOS8 nicht zwischen "Remote-Benachrichtigungen deaktiviert" und "Nur im Sperrbildschirm anzeigen aktiviert" unterscheiden können.
BOOL remoteNotificationsEnabled = false, noneEnabled,alertsEnabled, badgesEnabled, soundsEnabled;
if ([[UIApplication sharedApplication] respondsToSelector:@selector(registerUserNotificationSettings:)]) {
// iOS8+
remoteNotificationsEnabled = [UIApplication sharedApplication].isRegisteredForRemoteNotifications;
UIUserNotificationSettings *userNotificationSettings = [UIApplication sharedApplication].currentUserNotificationSettings;
noneEnabled = userNotificationSettings.types == UIUserNotificationTypeNone;
alertsEnabled = userNotificationSettings.types & UIUserNotificationTypeAlert;
badgesEnabled = userNotificationSettings.types & UIUserNotificationTypeBadge;
soundsEnabled = userNotificationSettings.types & UIUserNotificationTypeSound;
} else {
// iOS7 and below
UIRemoteNotificationType enabledRemoteNotificationTypes = [UIApplication sharedApplication].enabledRemoteNotificationTypes;
noneEnabled = enabledRemoteNotificationTypes == UIRemoteNotificationTypeNone;
alertsEnabled = enabledRemoteNotificationTypes & UIRemoteNotificationTypeAlert;
badgesEnabled = enabledRemoteNotificationTypes & UIRemoteNotificationTypeBadge;
soundsEnabled = enabledRemoteNotificationTypes & UIRemoteNotificationTypeSound;
}
if ([[UIApplication sharedApplication] respondsToSelector:@selector(registerUserNotificationSettings:)]) {
NSLog(@"Remote notifications enabled: %@", remoteNotificationsEnabled ? @"YES" : @"NO");
}
NSLog(@"Notification type status:");
NSLog(@" None: %@", noneEnabled ? @"enabled" : @"disabled");
NSLog(@" Alerts: %@", alertsEnabled ? @"enabled" : @"disabled");
NSLog(@" Badges: %@", badgesEnabled ? @"enabled" : @"disabled");
NSLog(@" Sounds: %@", soundsEnabled ? @"enabled" : @"disabled");
Swift 3+
if #available(iOS 10.0, *) {
UNUserNotificationCenter.current().getNotificationSettings(completionHandler: { (settings: UNNotificationSettings) in
// settings.authorizationStatus == .authorized
})
} else {
return UIApplication.shared.currentUserNotificationSettings?.types.contains(UIUserNotificationType.alert) ?? false
}
RxSwift Observable Version für iOS10 +:
import UserNotifications
extension UNUserNotificationCenter {
static var isAuthorized: Observable<Bool> {
return Observable.create { observer in
DispatchQueue.main.async {
current().getNotificationSettings(completionHandler: { (settings: UNNotificationSettings) in
if settings.authorizationStatus == .authorized {
observer.onNext(true)
observer.onCompleted()
} else {
current().requestAuthorization(options: [.badge, .alert, .sound]) { (granted, error) in
observer.onNext(granted)
observer.onCompleted()
}
}
})
}
return Disposables.create()
}
}
}
getNotificationSettings(...)
ist asynchron, so dass die Rückkehr im Inneren ignoriert wird
Bei dem Versuch, sowohl iOS8 als auch niedriger zu unterstützen, hatte ich nicht viel Glück damit, isRegisteredForRemoteNotifications
wie Kevin vorgeschlagen hatte. Stattdessen habe ich verwendet currentUserNotificationSettings
, was bei meinen Tests großartig funktioniert hat.
+ (BOOL)notificationServicesEnabled {
BOOL isEnabled = NO;
if ([[UIApplication sharedApplication] respondsToSelector:@selector(currentUserNotificationSettings)]){
UIUserNotificationSettings *notificationSettings = [[UIApplication sharedApplication] currentUserNotificationSettings];
if (!notificationSettings || (notificationSettings.types == UIUserNotificationTypeNone)) {
isEnabled = NO;
} else {
isEnabled = YES;
}
} else {
UIRemoteNotificationType types = [[UIApplication sharedApplication] enabledRemoteNotificationTypes];
if (types & UIRemoteNotificationTypeAlert) {
isEnabled = YES;
} else{
isEnabled = NO;
}
}
return isEnabled;
}
isEnabled = NO;
In Ihren if
Fällen wird er nicht benötigt, da er alsNO
Leider lieferte keine dieser Lösungen löst das Problem wirklich , da letztendlich die APIs ernsthaft fehlen, wenn es um die Bereitstellung der relevanten Informationen geht. Sie können ein paar Vermutungen currentUserNotificationSettings
anstellen, aber die Verwendung von (iOS8 +) reicht in der aktuellen Form einfach nicht aus, um die Frage wirklich zu beantworten. Obwohl viele der Lösungen hier darauf hindeuten, dass dies entweder isRegisteredForRemoteNotifications
eine endgültige Antwort ist oder eher eine endgültige Antwort ist, ist dies wirklich nicht der Fall.
Bedenken Sie:
mit isRegisteredForRemoteNotifications
Dokumentationszuständen:
Gibt JA zurück, wenn die Anwendung derzeit für Remote-Benachrichtigungen registriert ist, wobei systemweite Einstellungen berücksichtigt werden ...
Wenn Sie jedoch einen einfachen NSLog
in Ihren App-Delegaten werfen , um das Verhalten zu beobachten, ist klar, dass sich dies nicht so verhält, wie wir es erwarten. Es bezieht sich tatsächlich direkt auf Remote-Benachrichtigungen, die für diese App / dieses Gerät aktiviert wurden. Einmal aktiviert, kehrt dies immer zurück YES
. Selbst wenn Sie sie in den Einstellungen (Benachrichtigungen) deaktivieren, wird diese zurückgegebenYES
deaktiviert werden, Dies liegt daran, dass sich eine App ab iOS8 möglicherweise für Remote-Benachrichtigungen registriert und sogar an ein Gerät sendet, ohne dass der Benutzer Benachrichtigungen aktiviert hat. Sie führt möglicherweise keine Warnungen aus. Abzeichen und Sound, ohne dass der Benutzer dies einschaltet. Stille Benachrichtigungen sind ein gutes Beispiel für etwas, das Sie möglicherweise auch bei deaktivierten Benachrichtigungen weiterhin tun.
So weit wie currentUserNotificationSettings
es eines von vier Dingen anzeigt:
Warnungen sind eingeschaltet Abzeichen sind eingeschaltet Ton ist eingeschaltet Keine sind eingeschaltet.
Dies gibt Ihnen keinerlei Hinweis auf die anderen Faktoren oder den Benachrichtigungsschalter selbst.
Ein Benutzer kann tatsächlich Ausweise, Ton und Warnungen ausschalten, die Anzeige jedoch weiterhin auf dem Sperrbildschirm oder im Benachrichtigungscenter anzeigen. Dieser Benutzer sollte weiterhin Push-Benachrichtigungen erhalten und diese sowohl auf dem Sperrbildschirm als auch im Benachrichtigungscenter sehen können. Sie haben den Benachrichtigungsschalter eingeschaltet. ABER currentUserNotificationSettings
wird zurückkehren: UIUserNotificationTypeNone
in diesem Fall. Dies ist kein wirklicher Hinweis auf die tatsächlichen Einstellungen des Benutzers.
Ein paar Vermutungen kann man machen:
isRegisteredForRemoteNotifications
istNO
, dann können Sie davon ausgehen , dass dieses Gerät für Remote - Benachrichtigungen nie erfolgreich registriert hat.application:didRegisterUserNotificationSettings:
erfolgt zu diesem Zeitpunkt ein Rückruf mit Einstellungen für Benutzerbenachrichtigungen, da dies das erste Mal ist, dass ein Benutzer registriert wurde. In den Einstellungen sollte angegeben werden, was der Benutzer im Hinblick auf die Berechtigungsanforderung ausgewählt hat. Wenn die Einstellungen etwas anderem entsprechen als UIUserNotificationTypeNone
:, wurde die Push-Berechtigung erteilt, andernfalls wurde sie abgelehnt. Der Grund dafür ist, dass der Benutzer von dem Moment an, in dem Sie mit dem Fernregistrierungsprozess beginnen, nur die Möglichkeit hat, zu akzeptieren oder abzulehnen, wobei die anfänglichen Einstellungen einer Akzeptanz die Einstellungen sind, die Sie während des Registrierungsprozesses vorgenommen haben.Um die Antwort zu vervollständigen, könnte es so etwas funktionieren ...
UIRemoteNotificationType types = [[UIApplication sharedApplication] enabledRemoteNotificationTypes];
switch (types) {
case UIRemoteNotificationTypeAlert:
case UIRemoteNotificationTypeBadge:
// For enabled code
break;
case UIRemoteNotificationTypeSound:
case UIRemoteNotificationTypeNone:
default:
// For disabled code
break;
}
bearbeiten: Das ist nicht richtig. Da es sich um bitweise Dinge handelt, funktioniert es nicht mit einem Schalter, daher habe ich Folgendes verwendet:
UIRemoteNotificationType types = [[UIApplication sharedApplication] enabledRemoteNotificationTypes];
UIRemoteNotificationType typesset = (UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeBadge);
if((types & typesset) == typesset)
{
CeldaSwitch.chkSwitch.on = true;
}
else
{
CeldaSwitch.chkSwitch.on = false;
}
Für iOS7 und früher sollten Sie in der Tat verwenden enabledRemoteNotificationTypes
und prüfen, ob es gleich ist (oder nicht, je nachdem, was Sie wollen) UIRemoteNotificationTypeNone
.
Für iOS8 reicht es jedoch nicht immer aus, nur mit isRegisteredForRemoteNotifications
so vielen Status wie oben zu überprüfen . Sie sollten auch prüfen, ob application.currentUserNotificationSettings.types
gleich (oder nicht gleich, je nachdem, was Sie wollen) UIUserNotificationTypeNone
!
isRegisteredForRemoteNotifications
könnte return true obwohl currentUserNotificationSettings.types
Renditen UIUserNotificationTypeNone
.
iOS8 + (ZIEL C)
#import <UserNotifications/UserNotifications.h>
[[UNUserNotificationCenter currentNotificationCenter]getNotificationSettingsWithCompletionHandler:^(UNNotificationSettings * _Nonnull settings) {
switch (settings.authorizationStatus) {
case UNAuthorizationStatusNotDetermined:{
break;
}
case UNAuthorizationStatusDenied:{
break;
}
case UNAuthorizationStatusAuthorized:{
break;
}
default:
break;
}
}];
UIRemoteNotificationType types = [[UIApplication sharedApplication] enabledRemoteNotificationTypes];
if (types & UIRemoteNotificationTypeAlert)
// blah blah blah
{
NSLog(@"Notification Enabled");
}
else
{
NSLog(@"Notification not enabled");
}
Hier erhalten wir den UIRemoteNotificationType von UIApplication. Es stellt den Status der Push-Benachrichtigung dieser App in der Einstellung dar, als Sie ihren Typ leicht überprüfen können
Ich versuche, iOS 10 und höher mit der von @Shaheen Ghiassy bereitgestellten Lösung zu unterstützen, finde aber ein Problem mit dem Entzug enabledRemoteNotificationTypes
. Die Lösung, die ich finde, isRegisteredForRemoteNotifications
anstatt enabledRemoteNotificationTypes
sie in iOS 8 zu verwenden, ist veraltet. Nachfolgend ist meine aktualisierte Lösung aufgeführt, die für mich perfekt funktioniert hat:
- (BOOL)notificationServicesEnabled {
BOOL isEnabled = NO;
if ([[UIApplication sharedApplication] respondsToSelector:@selector(currentUserNotificationSettings)]){
UIUserNotificationSettings *notificationSettings = [[UIApplication sharedApplication] currentUserNotificationSettings];
if (!notificationSettings || (notificationSettings.types == UIUserNotificationTypeNone)) {
isEnabled = NO;
} else {
isEnabled = YES;
}
} else {
if ([[UIApplication sharedApplication] isRegisteredForRemoteNotifications]) {
isEnabled = YES;
} else{
isEnabled = NO;
}
}
return isEnabled;
}
Und wir können diese Funktion einfach aufrufen und auf ihren Bool
Wert zugreifen und sie dadurch in den Zeichenfolgenwert konvertieren:
NSString *str = [self notificationServicesEnabled] ? @"YES" : @"NO";
Hoffe, es wird auch anderen helfen :) Viel Spaß beim Codieren.
Obwohl Zacs Antwort bis iOS 7 vollkommen richtig war, hat sie sich seit der Ankunft von iOS 8 geändert. Weil enabledRemoteNotificationTypes ab iOS 8 veraltet ist. Für iOS 8 und höher müssen Sie isRegisteredForRemoteNotifications verwenden .
Diese Swifty- Lösung hat bei mir gut funktioniert ( iOS8 + ),
Methode :
func isNotificationEnabled(completion:@escaping (_ enabled:Bool)->()){
if #available(iOS 10.0, *) {
UNUserNotificationCenter.current().getNotificationSettings(completionHandler: { (settings: UNNotificationSettings) in
let status = (settings.authorizationStatus == .authorized)
completion(status)
})
} else {
if let status = UIApplication.shared.currentUserNotificationSettings?.types{
let status = status.rawValue != UIUserNotificationType(rawValue: 0).rawValue
completion(status)
}else{
completion(false)
}
}
}
Verwendung :
isNotificationEnabled { (isEnabled) in
if isEnabled{
print("Push notification enabled")
}else{
print("Push notification not enabled")
}
}
Re:
das ist richtig
if (types & UIRemoteNotificationTypeAlert)
aber folgendes ist auch richtig! (da UIRemoteNotificationTypeNone 0 ist)
if (types == UIRemoteNotificationTypeNone)
siehe folgendes
NSLog(@"log:%d",0 & 0); ///false
NSLog(@"log:%d",1 & 1); ///true
NSLog(@"log:%d",1<<1 & 1<<1); ///true
NSLog(@"log:%d",1<<2 & 1<<2); ///true
NSLog(@"log:%d",(0 & 0) && YES); ///false
NSLog(@"log:%d",(1 & 1) && YES); ///true
NSLog(@"log:%d",(1<<1 & 1<<1) && YES); ///true
NSLog(@"log:%d",(1<<2 & 1<<2) && YES); ///true
So geht's in Xamarin.ios.
public class NotificationUtils
{
public static bool AreNotificationsEnabled ()
{
var settings = UIApplication.SharedApplication.CurrentUserNotificationSettings;
var types = settings.Types;
return types != UIUserNotificationType.None;
}
}
Wenn Sie iOS 10+ unterstützen, verwenden Sie nur die UNUserNotificationCenter-Methode.
In Xamarin funktioniert die oben genannte Lösung bei mir nicht. Dies ist, was ich stattdessen benutze:
public static bool IsRemoteNotificationsEnabled() {
return UIApplication.SharedApplication.CurrentUserNotificationSettings.Types != UIUserNotificationType.None;
}
Es wird auch live aktualisiert, nachdem Sie den Benachrichtigungsstatus in den Einstellungen geändert haben.
Vollständiger einfacher Code zum Kopieren und Einfügen, der aus der Lösung von @ ZacBowling ( https://stackoverflow.com/a/1535427/2298002) erstellt wurde )
Dadurch wird der Benutzer auch zu Ihren App-Einstellungen gebracht und kann diese sofort aktivieren
Ich habe auch eine Lösung hinzugefügt, mit der überprüft werden kann, ob Ortungsdienste aktiviert sind (und auch Einstellungen vorgenommen werden).
// check if notification service is enabled
+ (void)checkNotificationServicesEnabled
{
if (![[UIApplication sharedApplication] isRegisteredForRemoteNotifications])
{
UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Notification Services Disabled!"
message:@"Yo don't mess around bro! Enabling your Notifications allows you to receive important updates"
delegate:self
cancelButtonTitle:@"Cancel"
otherButtonTitles:@"Settings", nil];
alertView.tag = 300;
[alertView show];
return;
}
}
// check if location service is enabled (ref: https://stackoverflow.com/a/35982887/2298002)
+ (void)checkLocationServicesEnabled
{
//Checking authorization status
if (![CLLocationManager locationServicesEnabled] || [CLLocationManager authorizationStatus] == kCLAuthorizationStatusDenied)
{
UIAlertView *alertView = [[UIAlertView alloc] initWithTitle:@"Location Services Disabled!"
message:@"You need to enable your GPS location right now!!"
delegate:self
cancelButtonTitle:@"Cancel"
otherButtonTitles:@"Settings", nil];
//TODO if user has not given permission to device
if (![CLLocationManager locationServicesEnabled])
{
alertView.tag = 100;
}
//TODO if user has not given permission to particular app
else
{
alertView.tag = 200;
}
[alertView show];
return;
}
}
// handle bringing user to settings for each
+ (void)alertView:(UIAlertView *)alertView clickedButtonAtIndex:(NSInteger)buttonIndex
{
if(buttonIndex == 0)// Cancel button pressed
{
//TODO for cancel
}
else if(buttonIndex == 1)// Settings button pressed.
{
if (alertView.tag == 100)
{
//This will open ios devices location settings
[[UIApplication sharedApplication] openURL:[NSURL URLWithString:@"prefs:root=LOCATION_SERVICES"]];
}
else if (alertView.tag == 200)
{
//This will open particular app location settings
[[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]];
}
else if (alertView.tag == 300)
{
//This will open particular app location settings
[[UIApplication sharedApplication] openURL:[NSURL URLWithString:UIApplicationOpenSettingsURLString]];
}
}
}
VIEL GLÜCK UND VIEL SPASS!