[objective-c] registerForRemoteNotificationTypes : iOS 8.0 이상에서 지원되지 않습니다

iOS 8.x에서 푸시 알림을 등록하려고 할 때 :

application.registerForRemoteNotificationTypes(UIRemoteNotificationType.Alert | UIRemoteNotificationType.Badge | UIRemoteNotificationType.Sound)

다음과 같은 오류가 발생합니다.

registerForRemoteNotificationTypes: is not supported in iOS 8.0 and later.

그것을하는 새로운 방법은 무엇입니까? iOS 7.x 에서이 Swift 앱을 실행할 때 작동합니다.

편집하다

iOS 7.x에서 조건부 코드를 포함하면 (SystemVersion 조건부 또는 #if __IPHONE_OS_VERSION_MAX_ALLOWED> = 80000)

dyld: Symbol not found: _OBJC_CLASS_$_UIUserNotificationSettings



답변

설명했듯이 iOS 버전에 따라 다른 방법을 사용해야합니다. 팀에서 Xcode 5 (iOS 8 선택기에 대해 알지 못함)와 Xcode 6을 모두 사용하는 경우 다음과 같이 조건부 컴파일을 사용해야합니다.

#if __IPHONE_OS_VERSION_MAX_ALLOWED >= 80000
if ([application respondsToSelector:@selector(registerUserNotificationSettings:)]) {
    // use registerUserNotificationSettings
} else {
    // use registerForRemoteNotificationTypes:
}
#else
// use registerForRemoteNotificationTypes:
#endif

Xcode 6 만 사용하는 경우 다음과 같이 할 수 있습니다.

if ([application respondsToSelector:@selector(registerUserNotificationSettings:)]) {
    // use registerUserNotificationSettings
} else {
    // use registerForRemoteNotificationTypes:
}

그 이유는 iOS 8에서 알림 권한을 얻는 방법이 변경 되었기 때문입니다. A UserNotification는 원격이든 로컬이든 사용자에게 표시되는 메시지입니다. 하나를 표시하려면 권한이 필요합니다. 이는 WWDC 2014 비디오 “iOS 알림의 새로운 기능”에 설명되어 있습니다.


답변

iOS <10의 경우

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary*)launchOptions
{
    //-- Set Notification
    if ([application respondsToSelector:@selector(isRegisteredForRemoteNotifications)])
    {
           // iOS 8 Notifications
           [application registerUserNotificationSettings:[UIUserNotificationSettings settingsForTypes:(UIUserNotificationTypeSound | UIUserNotificationTypeAlert | UIUserNotificationTypeBadge) categories:nil]];

           [application registerForRemoteNotifications];
    }
    else
    {
          // iOS < 8 Notifications
          [application registerForRemoteNotificationTypes:
                     (UIRemoteNotificationTypeBadge | UIRemoteNotificationTypeAlert | UIRemoteNotificationTypeSound)];
    }

     //--- your custom code
     return YES;
}

iOS10의 경우

https://stackoverflow.com/a/39383027/3560390


답변

@Prasath의 답변을 바탕으로합니다. 이것이 Swift 에서 수행하는 방법입니다 .

if application.respondsToSelector("isRegisteredForRemoteNotifications")
{
    // iOS 8 Notifications
    application.registerUserNotificationSettings(UIUserNotificationSettings(forTypes: (.Badge | .Sound | .Alert), categories: nil));
    application.registerForRemoteNotifications()
}
else
{
    // iOS < 8 Notifications
    application.registerForRemoteNotificationTypes(.Badge | .Sound | .Alert)
}


답변

iOS 8은 이전 버전과 호환되지 않는 방식으로 알림 등록을 변경했습니다. iOS 7 및 8을 지원해야하지만 (8 SDK로 빌드 된 앱은 허용되지 않는 동안) 필요한 선택기를 확인하고 실행중인 버전에 대해 조건부로 올바르게 호출 할 수 있습니다.

다음은 Xcode 5와 Xcode 6 모두에서 작동하는 깔끔한 인터페이스 뒤에이 논리를 숨기는 UIApplication의 범주입니다.

헤더:

//Call these from your application code for both iOS 7 and 8
//put this in the public header
@interface UIApplication (RemoteNotifications)

- (BOOL)pushNotificationsEnabled;
- (void)registerForPushNotifications;

@end

이행:

//these declarations are to quiet the compiler when using 7.x SDK
//put this interface in the implementation file of this category, so they are
//not visible to any other code.
@interface NSObject (IOS8)

- (BOOL)isRegisteredForRemoteNotifications;
- (void)registerForRemoteNotifications;

+ (id)settingsForTypes:(NSUInteger)types categories:(NSSet*)categories;
- (void)registerUserNotificationSettings:(id)settings;

@end

@implementation UIApplication (RemoteNotifications)

- (BOOL)pushNotificationsEnabled
{
    if ([self respondsToSelector:@selector(isRegisteredForRemoteNotifications)])
    {
        return [self isRegisteredForRemoteNotifications];
    }
    else
    {
        return ([self enabledRemoteNotificationTypes] & UIRemoteNotificationTypeAlert);
    }
}

- (void)registerForPushNotifications
{
    if ([self respondsToSelector:@selector(registerForRemoteNotifications)])
    {
        [self registerForRemoteNotifications];

        Class uiUserNotificationSettings = NSClassFromString(@"UIUserNotificationSettings");

        //If you want to add other capabilities than just banner alerts, you'll need to grab their declarations from the iOS 8 SDK and define them in the same way.
        NSUInteger UIUserNotificationTypeAlert   = 1 << 2;

        id settings = [uiUserNotificationSettings settingsForTypes:UIUserNotificationTypeAlert categories:[NSSet set]];
        [self registerUserNotificationSettings:settings];

    }
    else
    {
        [self registerForRemoteNotificationTypes:UIRemoteNotificationTypeAlert];
    }
}

@end


답변

우리 가이 접근법을 사용하면 이전 버전과의 호환성을 유지하는 것이 더 좋은 방법이라고 생각합니다. 내 경우에는 효과가 있으며 희망은 당신에게 도움이 될 것입니다. 또한 이해하기 쉽습니다.

if ([[[UIDevice currentDevice] systemVersion] floatValue] >= 8.0)
{
    [[UIApplication sharedApplication] registerUserNotificationSettings:[UIUserNotificationSettings settingsForTypes:(UIUserNotificationTypeSound | UIUserNotificationTypeAlert | UIUserNotificationTypeBadge) categories:nil]];
    [[UIApplication sharedApplication] registerForRemoteNotifications];
}
else
{
    [[UIApplication sharedApplication] registerForRemoteNotificationTypes:
         (UIUserNotificationTypeBadge | UIUserNotificationTypeSound | UIUserNotificationTypeAlert)];
}


답변

스위프트 경사의 경우 :

if let registration: AnyObject = NSClassFromString("UIUserNotificationSettings") { // iOS 8+
    let notificationTypes: UIUserNotificationType = (.Alert | .Badge | .Sound)
    let notificationSettings: UIUserNotificationSettings = UIUserNotificationSettings(forTypes: notificationTypes, categories: nil)

    application.registerUserNotificationSettings(notificationSettings)
} else { // iOS 7
    application.registerForRemoteNotificationTypes(.Alert | .Badge | .Sound)
}


답변

“범주”NSSet 변수가 무엇으로 설정되어야하는지 알 수 없었습니다. 누군가 누군가 나를 채울 수 있다면이 글을 기꺼이 편집하겠습니다. 그러나 다음은 푸시 알림 대화 상자를 표시합니다.

[[UIApplication sharedApplication] registerForRemoteNotifications];
UIUserNotificationSettings *settings = [UIUserNotificationSettings settingsForTypes:(UIUserNotificationTypeBadge | UIUserNotificationTypeSound | UIUserNotificationTypeAlert) categories:nil];
[[UIApplication sharedApplication] registerUserNotificationSettings:settings];

편집 :이 코드로 휴대 전화로 보낼 푸시 알림을 받았으므로 categories 매개 변수가 필요한지 확실하지 않습니다.