iOS 10 的推送 User Notifications Framework

介紹

User Notifications Framework 是蘋果在 WWDC 2016 推出的。iOS 10 中之前雜亂的和通知相關的 API 都被統一了,如今開發者可使用獨立的 UserNotifications.framework 來集中管理和使用 iOS 系統中通知的功能。在此基礎上,Apple 還增長了撤回單條通知,更新已展現通知,中途修改通知內容,在通知中展現圖片視頻,自定義通知 UI 等一系列新功能,很是強大。服務器

iOS 10 之前的推送

iOS 10 之前推送分爲 Local Notifications(本地推送) 和 Remote Notifications(遠程推送)。app

本地推送:經過 App 本地定製,加入到系統的 Schedule 裏,而後在指定的時間推送指定文字。框架

遠程推送:經過服務端向蘋果推送服務器 Apple Push Notification Service (APNs) 發送 Notification Payload,以後 APNs 再將推送下發到指定設備的 指定 App 上。ide

User Notifications Framework

基本配置

若是隻是簡單的本地推送,跳過 1 、2 步驟,直接到步驟 3。測試

一、 若是你的 App 有遠端推送的話,那你須要開發者帳號的,須要新建一個對應你 bundle 的 push 證書。 具體的證書製做請參考這裏
二、 Capabilities 中打開 Push Notifications 開關在 XCode7 中這裏的開關不打開,推送也是能夠正常使用的,可是在 XCode8 中,這裏的開關必需要打開,否則會報錯:spa

Error Domain=NSCocoaErrorDomain Code=3000 "未找到應用程序的「aps-environment」的受權字符串" UserInfo={NSLocalizedDescription=未找到應用程序的「aps-environment」的受權字符串}

權限申請

在使用 UserNotifications 框架的 API 的時候,首先要導入 UserNotifications 框架:代理

#import <UserNotifications/UserNotifications.h>

註冊推送code

UNUserNotificationCenter *center = [UNUserNotificationCenter currentNotificationCenter];
[center requestAuthorizationWithOptions:(UNAuthorizationOptionBadge | UNAuthorizationOptionSound | UNAuthorizationOptionAlert) completionHandler:^(BOOL granted, NSError * _Nullable error) {
    if (!error)
        {
            NSLog(@"請求受權成功");
        }
        else
        {
            NSLog(@"請求受權失敗");
        }
}];

Notification settings:以前註冊推送服務,用戶點擊了贊成仍是不一樣意,以及用戶以後又作了怎樣的更改咱們都無從得知,如今 apple 開放了這個 API,咱們能夠直接獲取到用戶的設定信息了。注意 UNNotificationSettings 是隻讀對象哦,不能直接修改!只能經過如下方式獲取component

[center getNotificationSettingsWithCompletionHandler:^(UNNotificationSettings * _Nonnull settings) {
    NSLog(@"%@", settings);
}];

打印視頻

<UNNotificationSettings: 0x6000022f9dc0; 
authorizationStatus: NotDetermined, 
notificationCenterSetting: NotSupported, 
soundSetting: NotSupported, 
badgeSetting: NotSupported, 
lockScreenSetting: NotSupported, 
carPlaySetting: NotSupported, 
criticalAlertSetting: NotSupported, 
alertSetting: NotSupported, 
alertStyle: None, 
providesAppNotificationSettings: No>

Token Registration

[[UIApplication sharedApplication] registerForRemoteNotifications];

獲取設備的Device Token

//獲取DeviceToken成功
- (void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken
{
    NSString *deviceString = [[deviceToken description] stringByTrimmingCharactersInSet:[NSCharacterSet characterSetWithCharactersInString:@"<>"]];
    deviceString = [deviceString stringByReplacingOccurrencesOfString:@" " withString:@""];
    NSLog(@"deviceToken:%@",deviceString);
}

//獲取DeviceToken失敗
- (void)application:(UIApplication *)application didFailToRegisterForRemoteNotificationsWithError:(NSError *)error
{
    NSLog(@"[DeviceToken Error]:%@\n",error.description);
}

接收推送的代理方法

// App處於前臺接收通知時
// 只有app處於前臺狀態下才會調用,後臺狀態或者應用殺死下是不會調用這個方法的
- (void)userNotificationCenter:(UNUserNotificationCenter *)center willPresentNotification:(UNNotification *)notification withCompletionHandler:(void (^)(UNNotificationPresentationOptions options))completionHandler 

// App通知的點擊事件
// 用戶點擊消息纔會觸發
- (void)userNotificationCenter:(UNUserNotificationCenter *)center didReceiveNotificationResponse:(UNNotificationResponse *)response withCompletionHandler:(void(^)())completionHandler

蘋果把本地通知跟遠程通知合二爲一。區分本地通知跟遠程通知的類是UNPushNotificationTrigger.h 類中,UNPushNotificationTrigger 的類型是新增長的。

UNPushNotificationTrigger (遠程通知) 遠程推送的通知類型
UNTimeIntervalNotificationTrigger (本地通知) 必定時間以後,重複或者不重複推送通知。咱們能夠設置timeInterval(時間間隔)和repeats(是否重複)。
UNCalendarNotificationTrigger(本地通知) 必定日期以後,重複或者不重複推送通知 例如,你天天8點推送一個通知,只要dateComponents爲8,若是你想天天8點都推送這個通知,只要repeats爲YES就能夠了。
UNLocationNotificationTrigger (本地通知)地理位置的一種通知,
當用戶進入或離開一個地理區域來通知。

內容

之前只能展現一條文字,如今能夠有 title 、subtitle 以及 body 了。

定製方法以下:

//本地通知
UNMutableNotificationContent *content = [[UNMutableNotificationContent alloc] init];
content.title = @"CALENDAR";
content.subtitle = @"Lunch";
content.body = @"Today at 12:00 PM";
content.badge = @1;

//遠程推送
{
"aps" : {
    "alert" : { 
         "title" : "CALENDAR", 
         "subtitle" : "Lunch",         
         "body" : "Today at 12:00 PM"
                },
    "badge" : 1
        },
}

Triggers

UNTimeIntervalNotificationTrigger 定時推送
UNCalendarNotificationTrigger 按期推送
UNLocationNotificationTrigger 定點推送

//60 秒後提醒
//timeInterval:單位爲秒(s)  repeats:是否循環提醒
UNTimeIntervalNotificationTrigger *trigger1 = [UNTimeIntervalNotificationTrigger triggerWithTimeInterval:60 repeats:NO];

// 在每週一早上 8:00 提醒
NSDateComponents *components = [[NSDateComponents alloc] init];
components.weekday = 2;
components.hour = 8;
UNCalendarNotificationTrigger *trigger3 = [UNCalendarNotificationTrigger triggerWithDateMatchingComponents:components repeats:YES];

//首先得導入#import <CoreLocation/CoreLocation.h>,否則會regin建立有問題。
CLLocationCoordinate2D center1 = CLLocationCoordinate2DMake(31.234567, 117.4567890);
  CLCircularRegion *region = [[CLCircularRegion alloc] initWithCenter:center1 radius:500 identifier:@"桂林路"];
UNLocationNotificationTrigger *trigger4 = [UNLocationNotificationTrigger triggerWithRegion:region repeats:NO];

Add Request

NSString *requestIdentifier = @"sampleRequest";
UNNotificationRequest *request = [UNNotificationRequest requestWithIdentifier:requestIdentifier
                                                                          content:content
                                                                          trigger:trigger1];
[center addNotificationRequest:request withCompletionHandler:^(NSError * _Nullable error) {

}];

推送小結

整個推送的過程以下

Local Notifications 經過定義 Content 和 Trigger 向 UNUserNotificationCenter 進行 request 這三部曲來實現。
Remote Notifications 則向 APNs 發送 Notification Payload 。

Notification Handling

設定了推送,而後就結束了?iOS 10 並無這麼簡單!
經過實現協議,使 App 處於前臺時捕捉並處理即將觸發的推送:

@interface AppDelegate () <UNUserNotificationCenterDelegate>

- (void)userNotificationCenter:(UNUserNotificationCenter *)center willPresentNotification:(UNNotification *)notification withCompletionHandler:(void (^)(UNNotificationPresentationOptions))completionHandler
{
    completionHandler(UNNotificationPresentationOptionAlert | UNNotificationPresentationOptionSound);
}

讓它只顯示 alert 和 sound ,而忽略 badge 。

Notification Management

完全掌控整個推送週期:

Local Notification 經過更新 request
Remote Notification 經過新的字段 apns-collapse-id

經過以前的 addNotificationRequest: 方法,在 id 不變的狀況下從新添加,就能夠刷新原有的推送。

NSString *requestIdentifier = @"sampleRequest";
UNNotificationRequest *request = [UNNotificationRequest requestWithIdentifier:requestIdentifier
                                                                      content:newContent
                                                                      trigger:newTrigger1];
[center addNotificationRequest:request withCompletionHandler:^(NSError * _Nullable error) {

}];

刪除計劃的推送:

[center removePendingNotificationRequestsWithIdentifiers:@[requestIdentifier]];

此外 UNUserNotificationCenter.h 中還有諸如刪除全部推送、查看已經發出的推送、刪除已經發出的推送等等強大的接口。

刷新原有的推送後,在通知中心的顯示裏,也會有相應的變化,這裏注意第 2 條信息,如今比分是 1:0

比分刷新後爲 1:1,在不產生新的推送條目的狀況下位置被前置了!

上面簡單介紹了 iOS 10 的新框架 User Notifications Framework,瞭解完 iOS 10 的框架以後,還要適配iOS 8 9 系統,是否是以爲很麻煩,筆者最近發現了一款 SDK ---- MobPush,兼容 iOS 8-12 系統,接入很是簡單,3行代碼就能夠搞定推送。

MPushNotificationConfiguration *configuration = [[MPushNotificationConfiguration alloc] init];
configuration.types = MPushAuthorizationOptionsBadge | MPushAuthorizationOptionsSound | MPushAuthorizationOptionsAlert;
[MobPush setupNotification:configuration];

同時,MobPush 支持多樣化推送場景、用戶分羣、AB 測試、智能推送等等功能,還有完善的數據統計後臺能夠從多個維度實時瞭解 APP 和用戶的使用狀況

相關文章
相關標籤/搜索