Removing scheduled local notification
First, let me explain why what you're doing is not working.
Let's say you have many different dates, for example: April 27th, May 4th, May 11th, May 18th etc..
You're assigning dateComp as
dateComp = Calendar.current.dateComponents([.weekday, .hour, .minute], from: myCoreDataEntity.date)
so for each of those mentioned dates your dateComp will look like:
dateComp = [Monday, 10, 30] // April 27th
dateComp = [Monday, 10, 30] // May 4th
dateComp = [Monday, 10, 30] // May 11th
dateComp = [Monday, 10, 30] // May 18th
and next you put that dateComp in your trigger, do you see where i'm going with this? Trigger doesn't have anything to do with your date except those three parameters, by changing date week later, you're actually using exactly the same trigger.
The moment you add your request to notification center your notification is set up to show on NEXT AVAILABLE Monday at 10:30, NOT on your date Monday 10:30.
I had the same problem and posted similar question here. From all my research and what others said it is not possible to set up repeated notification from specific future date in current UNNotificationCenter, i will be more than happy if someone could prove me wrong about this.
You could set up whole dateComp from your date, for example [.month, .day, .hour, .minute] but then if you set repeat to true it will repeat only on the same [.month, .day, .hour, .minute] which will end up repeating yearly.
Solution can be either to set up non-repeating notification for each specific date (there is limit of 64 notifications you can have in the same time) or like in my case set up seven repeating notifications for each weekday and then just remove the one you don't want at a time and add it again some other day but NOT the same day yet because it will be triggered again.
You can check out code i used in my app to do that here:
How to set up daily local notification for tasks but don't show it when user completes the task before
How do I stop a scheduled local notification from triggering after a particular date?
I think the best solution is : add 28 UNNotificationRequest
into UNUserNotificationCenter
with the UNCalendarNotificationTrigger
from 6.1-6.28
, the notification will never be triggered after 6.28, so in this way you don't need to remove that request manually.
for(int i = 1; i < 29; i++)
{
NSDateComponents d = new NSDateComponents() { Year = 2018, Month = 6,Day = i,Hour= 14 };
UNCalendarNotificationTrigger trigger = UNCalendarNotificationTrigger.CreateTrigger(d, true);
UNMutableNotificationContent content = new UNMutableNotificationContent() { Title = "xxx", Body = "xxx", CategoryIdentifier = "xxx" };
UNNotificationRequest request = UNNotificationRequest.FromIdentifier(i.ToString(), content, trigger);
UNUserNotificationCenter.Current.AddNotificationRequest(request,null);
}
how to cancel a localNotification with the press of a button in swift?
You could try to remove all notifications if this is acceptable in your context.
Like this:
for notification in UIApplication.sharedApplication().scheduledLocalNotifications as! [UILocalNotification] {
UIApplication.sharedApplication().cancelLocalNotification(notification)
}
Or as stated by Logan:
UIApplication.sharedApplication().cancelAllLocalNotifications()
Or as stated by Gerard Grundy for Swift 4:
UNUserNotificationCenter.current().removeAllPendingNotificationRequests()
Cancel a local notification which has been scheduled
You can not listen status change. Only way is when user opens the app check getNotificationSettings
I want to avoid to display a local scheduled notification if the user
has disabled notification authorisation from the app settings.
If user has disabled notification permission through the Settings. So there will be no notification to show.
Stop local notification after specific time period
So as per @Paulw11 and @TiranU answer, I scheduled the required number of individual notification. The solution is as follows:-
func localNotificationFire(timeInterval: Int, totalHours: Int) {
let num = totalHours/timeInterval
for i in 0..<num {
let center = UNUserNotificationCenter.current()
center.delegate = self
center.requestAuthorization(options: [.alert, .sound]) { (granted, error) in
// Enable or disable features based on authorization.
if error != nil {
print("Request authorization failed!")
} else {
print("Request authorization succeeded!")
let content = UNMutableNotificationContent()
content.title = ""
content.body = kNotificationReminder
content.sound = UNNotificationSound.default
content.badge = 1
let trigger = UNTimeIntervalNotificationTrigger(timeInterval: TimeInterval((i+1)*timeInterval), repeats: false)
let request = UNNotificationRequest(identifier: "notification.id.\(i)", content: content, trigger: trigger)
// 4
UNUserNotificationCenter.current().add(request, withCompletionHandler: nil)
}
}
}
}
Where total hours is the time till I want to trigger the notification and timeInterval is the time gap to trigger a notification.
Delete a particular local notification
You can save a unique value for key in your local notification's userinfo.
Get all local notification, loop through the array and delete the particular notification.
Code as follows,
OBJ-C:
UIApplication *app = [UIApplication sharedApplication];
NSArray *eventArray = [app scheduledLocalNotifications];
for (int i=0; i<[eventArray count]; i++)
{
UILocalNotification* oneEvent = [eventArray objectAtIndex:i];
NSDictionary *userInfoCurrent = oneEvent.userInfo;
NSString *uid=[NSString stringWithFormat:@"%@",[userInfoCurrent valueForKey:@"uid"]];
if ([uid isEqualToString:uidtodelete])
{
//Cancelling local notification
[app cancelLocalNotification:oneEvent];
break;
}
}
SWIFT:
var app:UIApplication = UIApplication.sharedApplication()
for oneEvent in app.scheduledLocalNotifications {
var notification = oneEvent as UILocalNotification
let userInfoCurrent = notification.userInfo! as [String:AnyObject]
let uid = userInfoCurrent["uid"]! as String
if uid == uidtodelete {
//Cancelling local notification
app.cancelLocalNotification(notification)
break;
}
}
UserNotification:
If you use UserNotification (iOS 10+), just follow this steps:
When creating the UserNotification content, add an unique identifier
Remove specific pending notification using removePendingNotificationRequests(withIdentifiers:)
Remove specific delivered notification using removeDeliveredNotifications(withIdentifiers:)
For more info, UNUserNotificationCenter
How to cancel a local notification trigger in Swift
You can cancel or remove notifications by calling:
let center = UNUserNotificationCenter.current()
Remove pending notifications with given identifier
center.removePendingNotificationRequests(withIdentifiers: [“givenIdentifier”])
And remove delivered notifications with given identifier
center.removeDeliveredNotifications(withIdentifiers: [“givenIdentifier”])
Related Topics
How to Calculate The Camera Position from Vuforia Gl Matrix
Dynamic Links Firebase Function Not Being Called at All Xcode 12
Rlmexception', Reason: 'Attempting to Modify Object Outside of a Write Transaction
Parse Migration Error to Mlabs and Heroku
Swift Error "Static Member Cannot Be Used on Instance of Type"
Why Do I Get Rgb Values of (0,0,0) for an Nsimage with a Transparent Background
Reduce Float Precision Using Regexp in Swift
Appdelegate#Applicationdidfinishlaunching Not Called for Swift 4 Macos App Built from Command Line
Cannot Authenticate User for Aws Appsync with Swift Sdk
Can Not Get Correct Position of View in Swiftui
Flattened Objects in JSON File to Nested Object Structure in Swift
Geofire/Firebase Function Is Executing Handler Multiple Times in Swift
Pie Chart Entries Outside Slices Have Different Position Offsets
Map Dictionary Keys to Add Values - Swift
Command Center Scrubber on Lock Screen Swift
How Do We Use of Nsselectorfromstring in Swift