此后每个人都可能继续前进,但我想分享我对这个问题的解决方案。(对不起长变量名称......)
这个想法很简单:永远保持fireDate在未来。
- 每次调用 didFinishLaunchingWithOptions 或 didReceiveLocalNotification 时,只需取消您当前的通知并在未来重新安排一个带有 fireDate 间隔单位的新通知
- 当您的应用程序启动时,遍历所有计划的通知,如果 fireDate 不在未来,您就知道它被忽略了
就我而言,通知每周重复一次。我首先在 didFinishLaunchingWithOptions 中重新安排任何确认的通知:
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
UILocalNotification* localNotif = [launchOptions objectForKey:UIApplicationLaunchOptionsLocalNotificationKey];
if (localNotif != nil)
{
[NotificationsHelper rescheduleNotification:localNotif];
}
}
还有在 didReceiveLocalNotification 中:
- (void)application:(UIApplication *)application didReceiveLocalNotification:(UILocalNotification *) notification
{
[NotificationsHelper rescheduleNotification:notification];
}
在 App Launch 中,我会检查所有过去是否有任何带有 fireDate 的通知:
- (void)applicationDidBecomeActive:(UIApplication *)application
{
[self checkLocalNotifications:application];
}
我的“checkLocalNotifications”函数的代码:
- (void) checkLocalNotifications:(UIApplication *) application
{
UIApplication* app = [UIApplication sharedApplication];
NSArray* eventArray = [app scheduledLocalNotifications];
for (int i = 0; i < [eventArray count]; i++)
{
UILocalNotification* notification = [eventArray objectAtIndex:i];
if ([NotificationsHelper wasWeeklyRepeatingNotificationIgnored:notification])
{
[NotificationsHelper rescheduleNotification:notification];
NSLog(@"NotificationWasIgnored: %@ %@",notification.alertAction, notification.alertBody );
}
}
}
我的“wasWeeklyRepeatingNotificationIgnored”函数的代码:
+ (BOOL) wasWeeklyRepeatingNotificationIgnored:(UILocalNotification*) the_notification
{
BOOL result;
NSDate* now = [NSDate date];
// FireDate is earlier than now
if ([the_notification.fireDate compare:now] == NSOrderedAscending)
{
result = TRUE;
}
else
{
result = FALSE;
}
return result;
}
我的“重新安排通知”功能的代码:
+ (void) rescheduleNotification:(UILocalNotification*) the_notification
{
UILocalNotification* new_notification = [[UILocalNotification alloc] init];
NSMutableDictionary* userinfo = [[NSMutableDictionary alloc] init];
[new_notification setUserInfo:userinfo];
[new_notification setRepeatInterval:the_notification.repeatInterval];
[new_notification setSoundName:UILocalNotificationDefaultSoundName];
[new_notification setTimeZone:[NSTimeZone defaultTimeZone]];
[new_notification setAlertAction:the_notification.alertAction];
[new_notification setAlertBody:the_notification.alertBody];
[new_notification setRepeatCalendar:[NSCalendar currentCalendar]];
[new_notification setApplicationIconBadgeNumber:the_notification.applicationIconBadgeNumber];
NSCalendar* gregorian = [[NSCalendar alloc] initWithCalendarIdentifier:NSGregorianCalendar];
NSDateComponents* weekdayComponents = [gregorian components:NSWeekdayCalendarUnit
fromDate:the_notification.fireDate];
NSInteger weekday = [weekdayComponents weekday];
NSDate* next_week = [self addDay:weekday toHourMinute:the_notification.fireDate];
[new_notification setFireDate:next_week];
[[UIApplication sharedApplication] scheduleLocalNotification:new_notification];
[[UIApplication sharedApplication] cancelLocalNotification:the_notification];
}