推送通知(二)-iOS>10的推送通知
接下来主要讲的是iOS10的推送通知
简介
- iOS10有如下几项改进:
- iOS 8以后,APNs推送的字节是2k,iOS8以前是256字节,iOS10现在是4k
- iOS 9以后APNs支持HTTP/2协议栈,优化长连接,具有标准的HTTP返回和管道复用技术
- iOS 10以后,APNs可根据推送消息的唯一标示符查询某条消息是否被用户阅读,可更新某一推送消息,而不用发重读的多条消息
- iOS10新加了一个独立框架:UserNotification.framework,废弃了 UILocalNotification(在UIKit.framework中)这个类,采用了全新的UserNotifications.framework来推送通知,从此推送通知也有了自己的标签UN(,以及对推送功能的一系列增强改进(两个extension,延展)和界面的体验优化)。
- iOS10的通知新功能
- iOS 10通知系统支持Images, GIFs, Audio and Video类型
- iOS 10推出Notification Service Extension与Notification Content Extension,可以实现推送数据在展示前进行下载更新、定制通知UI
- iOS 10统一了通知类型,具有时间间隔通知、地理位置通知和日历通知
- 废话不多说,学习一个新的框架当然就是从他常用的类开始
常见类之间的关系
- 该框架的类的结构分为2部分
- 管理通知相关的类
- 创建通知相关的类
- 常见类分析:
- UNUserNotificationCenter通知中心,用以管理通知的注册、权限获取和管理、通知的删除与更新,通过代理分发事件等。
- UNNotification 通知实体,在UNUserNotificationCenter的代理回调事件中,告知App接收到一条通知,包含一个发起通知的请求UNNotificationRequest
- UNNotificationRequest包含通知内容UNNotificationContent和触发器UNNotificationTrigger
- UNNotificationContent 通知内容,通知的title,sound,badge以及相关的图像、声音、视频附件UNNotificationAttachment,触发打开App时候指定的LacnchImage等
- UNNotificationResponse,用户在触发了按钮或者文本提交的UNNotificationAction的时候,会形成一个response,通过通知中心的代理方法回调给App进行处理或者是交给扩展处理。
- UNNotificationServiceExtension,是一个在接收到APNs服务器推送过来的数据进行处理的服务扩展,如果App提供了服务扩展,那么APNs下发推送后在通知显示触发之前,会在UNNotificationServiceExtension内接收到,此处有大约30秒的处理时间,开发者可以进行一些数据下载、数据解密、更新等操作,然后交由而后的内容扩展(UNNotificationContentExtension)或者是App进行触发显示
- UNNotificationCategory,用以定义一组样式类型,该分类包含了某一个通知包含的交互动作的组合,比如说UNNotificationRequest内包含了一个Category标示,那该通知就会以预定义好的交互按钮或者文本框添加到通知实体上。
- UNNotificationAttachment,通知内容UNNotificationContent包含的附件,一般为图片、视频和音频,虽然iOS10的通知数据容量为4k,但依旧很少,在添加了UNNotificationServiceExtension扩展的情况下,可以在服务里下载图片,生成图片、视频等的本地缓存,UNNotificationAttachment根据缓存数据生成并添加到UNNotificationContent中,交由UI显示
- UNNotificationAction,是通知中添加的action,展示在通知栏的下方。默认以的button样式展示。有一个文本输入的子类UNTextInputNotificationAction。可以在点击button之后弹出一个键盘,输入信息。用户点击信息和输入的信息可以在UNNotificationResponse中获取
- NotificationViewController,App添加Notification Content Extension扩展的时候,自动生成的Controller,可以定义通知UI的主题部分,由StoryBoard指定设计
- UNNotificationContentExtension<协议>,NotificationViewController实现该协议,可以获得iOS展示自定义UI时候分发的UNNotification对象和用户交互的Response协议>
- 管理通知相关的类
本地通知
- 设置通知内容
- 创建通知内容对象
- 设置属性
- 设置通知的附件:视频/音频/图片/gif
- 设置互交类型
- 设置通知触发机制
- 创建一个
UNNotificationRequest
类的实例- 一定要为它设置
identifier
, 在后面的查找,更新, 删除通知,这个标识是可以用来区分这个通知与其他通知 - 如果另一个
request
具有和之前request
相同的标识,不同的内容, 可以达到更新通知的目的
- 一定要为它设置
- 把
request
加到UNUserNotificationCenter
, 并设置触发器,等待触发 -
代码举例如下:
//推送本地通知://使用UNNotification本地通知 -(void)sendLocalNotification{ //1. 设置通知内容 //需创建一个包含待通知内容的UNMutableNotificationContent对象,注意不是UNNotificationContent ,此对象为不可变对象。 UNMutableNotificationContent *content = [[UNMutableNotificationContent alloc] init]; //通知主标题 content.title = @"主标题"; //通知子标题 content.subtitle = @"子标题"; //设置通知的内容 content.body = @"这是通知的内容????????????????????????"; //或者也可以这样创建: //content.title = [NSString localizedUserNotificationStringForKey:@"主标题" arguments:nil]; //content.body= [NSString localizedUserNotificationStringForKey:@"Hello_message_body" arguments:nil]; //设置应用程序图标右上角的数字 content.badge = @0; //设置有通知时的音效 UNNotificationSound *sound = [UNNotificationSound defaultSound]; content.sound = sound; //设置通知的附件:通知右边的图片 //将本地图片的路径形成一个图片附件,加入到content中 //视频 //NSString *path = [[NSBundle mainBundle] pathForResource:@"flv视频测试用例1" ofType:@"mp4"]; NSString *path = [[NSBundle mainBundle] pathForResource:@"beautiful" ofType:@"png"]; NSError *error = nil; UNNotificationAttachment *img_attachment = [UNNotificationAttachment attachmentWithIdentifier:@"att1" URL:[NSURL fileURLWithPath:path] options:nil error:&error]; content.attachments = @[img_attachment]; //设置为@""以后,进入app将没有启动页 content.launchImageName = @""; //通知的互交类型,Identifier可不是乱写的而是,在注册通知时设置好的 content.categoryIdentifier = @"seeCategory1"; //设置额外信息(比如:告诉app点击通知时跳转到哪一个界面) content.userInfo = @{@"type" : @1 }; //2. 设置通知触发机制 //通知触发机制 //UserNotifications提供了三种触发器: //UNTimeIntervalNotificationTrigger:一定时间后触发(若重复提醒,时间间隔要大于60s) //UNCalendarNotificationTrigger:在某月某日某时触发 //UNLocationNotificationTrigger:在用户进入或是离开某个区域时触发 //UNPushNotificationTrigger: 远程推送 //设置通知发出的时间 UNTimeIntervalNotificationTrigger *time_trigger = [UNTimeIntervalNotificationTrigger triggerWithTimeInterval:5 repeats:NO]; //3.创建通知请求 //创建UNNotificationRequest通知请求对象//创建一个发送请求 //通知请求标识,便于管理该通知 NSString *requestIdentifer = @"time interval request"; UNNotificationRequest *request = [UNNotificationRequest requestWithIdentifier:requestIdentifer content:content trigger:time_trigger]; //4.将通知请求添加到通知中心 [[UNUserNotificationCenter currentNotificationCenter] addNotificationRequest:request withCompletionHandler:^(NSError * _Nullable error) {}]; }
- 根据上面内容,大家会发现在创建UNNotificationRequest的时候,会需要UNMutableNotificationContent以及UNTimeIntervalNotificationTrigger这两个类。下面我就对相关的类,以及类扩展,做相应的说明
UNNotificationContent以及UNMutableNotificationContent(通知内容和可变通知内容)
- 通知内容分为可变的以及不可变的两种类型,类似于可变数组跟不可变数组。
- 后续我们通过某一特定标识符更新通知,便是用可变通知了。
- 不管是可变通知还是不可变通知,都有以下的几个属性:
-
附件数组,存放UNNotificationAttachment类
@property (NS_NONATOMIC_IOSONLY, copy) NSArray <UNNotificationAttachment *> *attachments ;
-
应用程序角标,0或者不传,意味着角标消失
@property (NS_NONATOMIC_IOSONLY, copy, nullable) NSNumber *badge;
-
主体内容
@property (NS_NONATOMIC_IOSONLY, copy) NSString *body ;
- 点击通知启动app时的图标
- 程序在后台时,此时程序没有杀死
- 设置任意字符串即可,只会显示启动图片的图标
@property (NS_NONATOMIC_IOSONLY, copy) NSString *launchImageName;
-
UNNotificationSound
类,可以设置默认声音,或者指定名称的声音@property (NS_NONATOMIC_IOSONLY, copy, nullable) UNNotificationSound *sound ;
-
推送内容的子标题
@property (NS_NONATOMIC_IOSONLY, copy) NSString *subtitle ;
-
通知线程的标识
@property (NS_NONATOMIC_IOSONLY, copy) NSString *threadIdentifier;
-
推送内容的标题
@property (NS_NONATOMIC_IOSONLY, copy) NSString *title ;
-
远程通知附加的额外信息
@property (NS_NONATOMIC_IOSONLY, copy) NSDictionary *userInfo;
- 通知的互交类型
- Identifier可不是乱写的,而是在通知中心(
UNUserNotificationCenter
)在程序启动注册应用通知时给整个应用程序设置的所有互交类型,并且每个互交类型都有它的Identifier
@property (NS_NONATOMIC_IOSONLY, copy) NSString *categoryIdentifier;
- Identifier可不是乱写的,而是在通知中心(
-
UNNotificationAttachment
- 在UNNotificationContent类中,有个附件数组的属性,这就是包含UNNotificationAttachment类的数组了。
- 苹果的解释说,UNNotificationAttachment(附件通知)是指可以包含音频,图像或视频内容,并且可以将其内容显示出来的通知。
- 使用本地通知时,可以在通知创建时,将附件加入即可。
- 对于远程通知,则必须实现使用
UNNotificationServiceExtension
类通知服务扩展。 -
创建附件的方法是
+ (nullable instancetype)attachmentWithIdentifier:(NSString *)identifier URL:(NSURL *)URL options:(nullable NSDictionary *)options error:(NSError *__nullable *__nullable)error;
- 在使用时,必须指定使用文件附件的内容,并且文件格式必须是支持的类型之一。
- 创建附件后,将其分配给内容对象的附件属性。
- 对于远程通知,您必须从您的服务扩展做到这一点。
- 附件通知支持的类型如下图:
- 注意:URL必须是一个有效的文件路径,不然会报错
- options参数是一个字典,但是其key实枚举,如下;
UNNotificationAttachmentOptionsTypeHintKey
:- 此键的值(value)是一个描述文件类型的统一类型标识符(UTI)一个NSString。
- 如果不提供该键,附件的文件扩展名来确定其类型
- 常用的类型标识符有:
kUTTypeImage,kUTTypeJPEG2000,kUTTypeTIFF,kUTTypePICT,kUTTypeGIF ,kUTTypePNG,kUTTypeQuickTimeImage等。
- 使用这些标识符之前要导入
#import<MobileCoreServices/MobileCoreServices.h>
框架 -
使用方法如下:
dict[UNNotificationAttachmentOptionsTypeHintKey] = (__bridge id _Nullable)(kUTTypeImage);
UNNotificationAttachmentOptionsThumbnailHiddenKey
:- 是一个BOOL值,为YES时候,缩略图将隐藏(即通知中(右中)带的图片),默认为NO。
-
使用方法如下:
dict[UNNotificationAttachmentOptionsThumbnailHiddenKey] = @YES;
UNNotificationAttachmentOptionsThumbnailClippingRectKey
- 剪贴矩形的缩略图。
-
使用方法;
dict[UNNotificationAttachmentOptionsThumbnailClippingRectKey] = (__bridge id _Nullable)((CGRectCreateDictionaryRepresentation(CGRectMake(0.5, 0.5, 0.25 ,0.25))));
(0.5, 0.5, 0.25 ,0.25)
这句话的意思是,以原缩略图左上角为原点截取一个x坐标为:0.5*长度
,y坐标为:0.5*宽度
,宽度为:0.25*宽度
,长度为:0.25*长度
的矩形图片作为新的缩略图(即通知右中的图片).
UNNotificationAttachmentOptionsThumbnailTimeKey
- 一般影片附件会用到,指的是用影片中的某一秒来做这个缩略图;
-
使用方法如下:
dict[UNNotificationAttachmentOptionsThumbnailTimeKey] =@10;
- 这里我们可以直接传递一个NSNumber的数值,比如使用影片第10s的画面来做缩略图就按照上面的来写。此外,要注意的是,这个秒数必须是这个影片长度范围内的,不然报错。
UNTimeIntervalNotificationTrigger
UNPushNotificationTrigger
- (远程通知触发)一般我们不会使用的
UNTimeIntervalNotificationTrigger
- (本地通知) 一定时间之后,重复或者不重复推送通知。我们可以设置timeInterval(时间间隔)和repeats(是否重复)。
-
使用方法:
UNTimeIntervalNotificationTrigger *triggerOne = [UNTimeIntervalNotificationTrigger triggerWithTimeInterval:5 repeats:NO];
- 解释:上面的方法是指5秒钟之后执行。
repeats
这个属性,如果需要为重复执行的,则TimeInterval
必须大于60s,否则会报: ` Terminating app due to uncaught exception ‘NSInternalInconsistencyException’, reason: ‘time interval must be at least 60 if repeating’`的错误!
UNCalendarNotificationTrigger
- (本地通知) 一定日期之后,重复或者不重复推送通知
- 例如,你每天8点推送一个通知,只需要dateComponents为8。如果你想每天8点都推送这个通知,只要repeats为YES就可以了。
-
代码举例:
// 周一早上 8:00 上班 NSDateComponents *components = [[NSDateComponents alloc] init]; // 注意,weekday是从周日开始的,如果想设置为从周一开始,大家可以自己想想~ components.weekday = 2; components.hour = 8; UNCalendarNotificationTrigger *trigger = [UNCalendarNotificationTrigger triggerWithDateMatchingComponents:components repeats:YES];
UNLocationNotificationTrigger
- (本地通知)地理位置的一种通知,使用这个通知,你需要导入
-
#import<CoreLocation/CoreLocation.h>
这个系统类库。示例代码如下://1、如果用户进入或者走出某个区域会调用下面两个方法 - (void)locationManager:(CLLocationManager *)manager didEnterRegion:(CLRegion *)region - (void)locationManager:(CLLocationManager *)manager didExitRegion:(CLRegion *)region代理方法反馈相关信息 //2、一到某个经纬度就通知,判断包含某一点么 // 不建议使用!!!!!!CLRegion *region = [[CLRegion alloc] init];// 不建议使用!!!!!! CLCircularRegion *circlarRegin = [[CLCircularRegion alloc] init]; [circlarRegin containsCoordinate:(CLLocationCoordinate2D)]; UNLocationNotificationTrigger *trigger4 = [UNLocationNotificationTrigger triggerWithRegion:circlarRegin repeats:NO];
- 注意,这里建议使用
CLCircularRegion
这个继承自CLRegion
的类,因为我看到苹果已经废弃了CLRegion
里面是否包含这一点的方法,并且推荐我们使用CLCircularRegion
这个类型
点击通知(包含远程和本地)
- 第一步在
Appdelegate.m
中导入#import <UserNotifications/UserNotifications.h>
-
我们最好写成这种形式
#ifdef NSFoundationVersionNumber_iOS_9_x_Max #import <UserNotifications/UserNotifications.h> #endif
didFinishLaunchingWithOptions的处理(包含本地和远程)
- 请求用户授权/注册远程通知
-
获取应用的通知管理中心UNUserNotificationCenter,来管理推送通知
UNUserNotificationCenter* center = [UNUserNotificationCenter currentNotificationCenter];
- 设置推送通知中心的代理,实现代理方法,监听通知的推送
-
注意:
UNUserNotificationCenter
的delegate
必须在application:willFinishLaunchingWithOptions: or application:didFinishLaunchingWithOptions:
方法中实现;center.delegate = self;
-
- 设置预设好的交互类型,
NSSet
里面是设置好的UNNotificationCategory
- 就是当接收到通知时,拖拽向下,会看到互交控件:是按钮点击/还是文本输入,不设置没有按钮
-
也就是本地通知中
UNMutableNotificationContent
类的categoryIdentifier
属性要在这些设置好的互交类型中选择[center setNotificationCategories:[self createNotificationCategoryActions]];
-
请求用户授权
//请求获取通知权限(角标,声音,弹框) [center requestAuthorizationWithOptions:(UNAuthorizationOptionBadge | UNAuthorizationOptionSound | UNAuthorizationOptionAlert) completionHandler:^(BOOL granted, NSError * _Nullable error) { if (granted) { //获取用户是否同意开启通知 NSLog(@"request authorization successed!"); } }];
- 注册远程通知(只用本地时不需要)
- 调用该方法就是向苹果的apns服务器发送该设备的udid和bundle id,返回deviceToken
-
如果获取不到deviceToken,Xcode8下要注意开启Capability->Push Notification。
[application registerForRemoteNotifications];
-
- 交互类型的自定义方法
- iOS10通知上的交互只有两种,一种是Button一种是text,就算使用了iOS10 Notification Content Extension也不能添加自定义的按钮或者其他交互组件,因为不会响应。
-
UNNotificationAction 在初始化的时候需要定义UNNotificationActionOptions,这个UNNotificationActionOptions的意思是:
typedef NS_OPTIONS(NSUInteger, UNNotificationActionOptions) { // Whether this action should require unlocking before being performed. //指定该动作是否需要用户解锁验证身份 UNNotificationActionOptionAuthenticationRequired = (1 << 0), // Whether this action should be indicated as destructive. //指定用户执行该动作是否要将通知从iOS的通知中心移除,以防止处理过该通知以后重复处理 UNNotificationActionOptionDestructive = (1 << 1), // Whether this action should cause the application to launch in the foreground. //指定通知action点击后是否要进入app到前台,如果到前台,这个对Notification Content Extension的自定义的通知UI有意义, //可以在Extension中处理用户的点击或者提交文字,那么就可以指定该action不需要进入app, //UNNotificationActionOptionAuthenticationRequired这个就不要加入 UNNotificationActionOptionForeground = (1 << 2), } __IOS_AVAILABLE(10.0) __WATCHOS_AVAILABLE(3.0) __TVOS_PROHIBITED;
-(NSSet *)createNotificationCategoryActions{ //1.设置交互类型1:seeCategory 2个按钮 //1.1 定义按钮的交互button action //Identifier:互交的标识,当用户点击时可以再用户点击方法中查看点击是哪个btn //title:标题 UNNotificationAction * likeButton = [UNNotificationAction actionWithIdentifier:@"see1" title:@"看一看" options:UNNotificationActionOptionAuthenticationRequired|UNNotificationActionOptionDestructive|UNNotificationActionOptionForeground]; UNNotificationAction * dislikeButton = [UNNotificationAction actionWithIdentifier:@"see2" title:@"忽略" options:UNNotificationActionOptionAuthenticationRequired|UNNotificationActionOptionDestructive|UNNotificationActionOptionForeground]; //1.2 将这些action带入category //Identifier:创建通知时会使用到这个,根据这个查看到底选择哪种互交方式 UNNotificationCategory * choseCategory = [UNNotificationCategory categoryWithIdentifier:@"seeCategory" actions:@[likeButton,dislikeButton] intentIdentifiers:@[@"see1",@"see2"] options:UNNotificationCategoryOptionNone]; //2. 设置交互类型2:seeCategory1 文本框输入类型 //2.1 创建textAction UNTextInputNotificationAction * text = [UNTextInputNotificationAction actionWithIdentifier:@"text" title:@"回复" options:UNNotificationActionOptionAuthenticationRequired|UNNotificationActionOptionDestructive|UNNotificationActionOptionForeground]; //2.2 将action加入UNNotificationCategory UNNotificationCategory * comment = [UNNotificationCategory categoryWithIdentifier:@"seeCategory1" actions:@[text] intentIdentifiers:@[@"text"] options:UNNotificationCategoryOptionNone]; //3. 将交互类型插入NSSet中,然后给整个app应用设置 return [NSSet setWithObjects:choseCategory,comment,nil]; }
- 监听deviceToken的获取(远程通知使用)
-
获得Device Token的方法是没有改变的。
// 监听苹果返回devicetoken -(void)application:(UIApplication *)application didRegisterForRemoteNotificationsWithDeviceToken:(NSData *)deviceToken{ //4.将DeviceToken传给服务器 NSLog(@"%@", deviceToken.description); } //向apns请求失败 -(void)application:(UIApplication *)application didFailToRegisterForRemoteNotificationsWithError:(NSError *)error{ NSLog(@"===请求devicetoken失败==%@",error); }
-
UNUserNotificationCenter
的其他使用方法:- 获取当前应用的通知设置
UNNotificationSettings
是只读对象,不能直接修改,只能通过以下方法获取
[center getNotificationSettingsWithCompletionHandler:^(UNNotificationSettings * _Nonnull settings) { // UNAuthorizationStatus NotDetermined :没有做出选择 // UNAuthorizationStatus Denied :用户未授权 // UNAuthorizationStatus Authorized:用户已授权 //进行判断做出相应的处理 if (settings.authorizationStatus == UNAuthorizationStatusNotDetermined) { NSLog(@"未选择"); }else if (settings.authorizationStatus == UNAuthorizationStatusDenied){ NSLog(@"未授权"); }else if (settings.authorizationStatus == UNAuthorizationStatusAuthorized){ NSLog(@"已授权"); } }];
-
获取到当前用户推送中心所有设置的互交类型
[center getNotificationCategoriesWithCompletionHandler:^(NSSet<UNNotificationCategory *> * _Nonnull categories) { }];
-
常见的通知操作
//拿到通知中心 UNUserNotificationCenter* center = [UNUserNotificationCenter currentNotificationCenter];//① //-移除还未展示的通知 [center removePendingNotificationRequestsWithIdentifiers: @[@"RequestIdentifier"]]; //移除所有未展示的通知 [center removeAllPendingNotificationRequests]; //- (void)cancelAllLocalNotifications; //-移除已经展示过的通知 //这里的Identifiers就是你创建通知时设置的,便于管理改通知 [center removeDeliveredNotificationsWithIdentifiers:@[@"RequestIdentifier"]]; [center removeAllDeliveredNotifications]; //-获取未展示的通知请求 [center getPendingNotificationRequestsWithCompletionHandler:^(NSArray * _Nonnull requests) { NSLog(@"%@",requests); }]; //-获取展示过的通知 [center getDeliveredNotificationsWithCompletionHandler:^(NSArray * _Nonnull notifications) { NSLog(@"%@",notifications); }];
- 获取当前应用的通知设置
推动通知的监听
- 此次iOS10系统的更新,苹果给了我们2个代理方法来处理通知的接收和点击事件,这两个方法在
<UNUserNotificationCenterDelegate>
的协议中 - 苹果把本地通知跟远程通知合二为一
- 区分本地通知跟远程通知的类是
UNPushNotificationTrigger
代理方法1:
- 调用时刻:
- 应用程序在前台台时调用(通知即将展示,还没有展示时),即不点击通知就会调用
- 程序处于后台/杀死状态时都不会调用
- 作用:
- 在展示通知前进行处理,即有机会在展示通知前再修改通知内容。
- 如果你的App在前台,一般在这个回调函数里做一些数据加解密、数据下载,然后将下载的数据组装成UNNotificationAttachment或者是根据通知里面的content里面的userinfo里与后端服务约定好的修改通知对应的categoryId,调用相应的交互组件到通知上,completionHandler在你想要做的逻辑完成以后调用。
- 如果App在前台,你接收到通知,不想显示系统提示框,想使用App 自定义的通知消息弹窗,可以在completionHandler回调的时候传入的opinion不要带上UNAuthorizationOptionAlert,然后直接弹自定义的弹窗就Ok。
- 特点:
- 如果该方法没有实现或者没有回调用
completionHandler
则前台通知将不会呈现,也接收不到
- 如果该方法没有实现或者没有回调用
- 应用程序可以通过
completionHandler()
回调,选择怎样呈现这个通知: 只有角标变化的通知/只有声音提示/只有弹框提示或者3种的组合 -
代码如下:
-(void)userNotificationCenter:(UNUserNotificationCenter *)center willPresentNotification:(UNNotification *)notification withCompletionHandler:(void (^)(UNNotificationPresentationOptions))completionHandler{ // 原始请求 UNNotificationRequest *request = notification.request; // 获取请求的额外信息 NSDictionary * userInfo = notification.request.content.userInfo;//userInfo数据 // 请求的内容 UNNotificationContent *content = request.content; // 原始内容 NSString *title = content.title; // 标题 NSString *subtitle = content.subtitle; // 副标题 NSNumber *badge = content.badge; // 角标 NSString *body = content.body; // 推送消息体 UNNotificationSound *sound = content.sound; // 指定的声音 //本地通知的判断:notification.request.trigger类型判断是远程还是本地推送 if ([notification.request.trigger isKindOfClass:[UNPushNotificationTrigger class]]) { NSLog(@"iOS10代理方法一的远程通知:%@",[notification description]); }else{ NSLog(@"iOS10代理方法一的本地通知:%@",[notification description]); } //设置怎样接收通知:只有角标变化的通知/只有声音提示/只有弹框提示/3中的组合 completionHandler(UNNotificationPresentationOptionBadge|UNNotificationPresentationOptionSound|UNNotificationPresentationOptionAlert); }
代理方法二:
- 调用时刻
- 应用程序在后台/杀死状态下都会调用
- 用户点击通知打开app
- 下拉通知,选择一个互交动作:点击互交按钮/文本输入后点击发送
- 跟后台发送content-available没任何关系,必须操作才会调用
- 作用:
- 点击通知处理通知内容
- 该回调函数仅仅用来处理数据和重新选择交互方式,其他远程推送到达设备要做的业务逻辑
- 如果不写
completionHandler()
这个方法,会报错误 -
代码举例:
-(void)userNotificationCenter:(UNUserNotificationCenter *)center didReceiveNotificationResponse:(UNNotificationResponse *)response withCompletionHandler:(void (^)(void))completionHandler{ //1.获取到通知详情 UNNotificationRequest *request = response.notification.request; // 原始请求 NSDictionary * userInfo = request.content.userInfo;//userInfo数据 UNNotificationContent *content = request.content; // 原始内容 //2.判断通知的种类 if ([response.notification.request.trigger isKindOfClass:[UNPushNotificationTrigger class]]) { NSLog(@"代理方法二的远程通知"); }else{ NSLog(@"代理方法二的本地通知"); } //3.根据response的种类判断用户的互交类型 //可根据actionIdentifier来做业务逻辑 if ([response isKindOfClass:[UNTextInputNotificationResponse class]]) { //交互类型为文本输入 UNTextInputNotificationResponse * textResponse = (UNTextInputNotificationResponse*)response; //拿到用户交互的内容 NSLog(@"用户输入的内容为: %@",textResponse.userText); }else{ //交互类型为点击按钮 //点击第一个交互按钮 if ([response.actionIdentifier isEqualToString:@"see1"]) { //看一看的处理 NSLog(@"用户点击的按钮为see1"); } //点击第二个交互按钮 if ([response.actionIdentifier isEqualToString:@"see2"]) { //删除已经推动过的推送需求 NSLog(@"用户点击的按钮为see2"); //忽略的处理 [[UNUserNotificationCenter currentNotificationCenter] removeDeliveredNotificationsWithIdentifiers:@[response.notification.request.identifier]]; } } completionHandler(); }