Daily Local Notifications Are Not Working

Daily Local Notifications Are Not Working

Look at the comments within the code

import SwiftUI
//struct and class should start with an uppercase
struct NotificationView: View {
//Central location for Notification code including the delegate
// A call to the notificationManager just like the line of code below has to be included in
// application(_:willFinishLaunchingWithOptions:) or
// application(_:didFinishLaunchingWithOptions:)
//https://developer.apple.com/documentation/usernotifications/unusernotificationcenterdelegate
//https://www.hackingwithswift.com/quick-start/swiftui/how-to-add-an-appdelegate-to-a-swiftui-app
let notificationManager: NotificationManager = NotificationManager.shared
var body: some View {
VStack {
VStack {
Button("Request Permission") {
//Call a func here don't define it
notificationManager.requestAuthorization()
}
.frame(width: 200, height: 60, alignment: .center)
.foregroundColor(.black)
.background(Color.blue)
.cornerRadius(10.0)
.padding()
Button("Add Notifications For Morning") {
//Unique date components
var dateComponents = DateComponents()
dateComponents.hour = 6
dateComponents.minute = 30
//Reusable method
self.notificationManager.scheduleTriggerNotification(title: "Morning Time", body: "Wake Up And Be Productive!", categoryIdentifier: "reminder", dateComponents: dateComponents, repeats: true)
}
.padding()
Button("Add Notifications For Middle Of The Day") {
var dateComponents = DateComponents()
dateComponents.hour = 12
dateComponents.minute = 30
//Reusable method
self.notificationManager.scheduleTriggerNotification(title: "Middle Of The Day", body: "Did you have your daily run?", categoryIdentifier: "reminder", dateComponents: dateComponents, repeats: true)

}
.padding()
Button("Add Notifications For Night") {
var dateComponents = DateComponents()
dateComponents.hour = 20
dateComponents.minute = 51
//Reusable method
self.notificationManager.scheduleTriggerNotification(title: "Night Time", body: "Time to sleep", categoryIdentifier: "reminder", dateComponents: dateComponents, repeats: true)

}
.foregroundColor(.blue)
.padding()

Button("Print Notifications") {
//Reusable method
self.notificationManager.printNotifications()
}
.foregroundColor(.blue)
.padding()
Button("Delete Notifications") {
//Reusable method
self.notificationManager.deleteNotifications()
}
.foregroundColor(.blue)
.padding()
}
}
}
}
//You need a central location for the notification code because
// it is needed in more than 1 spot. At launch in the AppDelegate
// and wherever you schedule your notifications
class NotificationManager: NSObject, UNUserNotificationCenterDelegate{
//Singleton is requierd because of delegate
static let shared: NotificationManager = NotificationManager()
let notificationCenter = UNUserNotificationCenter.current()

private override init(){
super.init()
//This assigns the delegate
notificationCenter.delegate = self
}

func requestAuthorization() {
print(#function)
notificationCenter.requestAuthorization(options: [.alert, .badge, .sound]) { (granted, error) in
if granted {
print("Access Granted!")
} else {
print("Access Not Granted")
}
}
}

func deleteNotifications(){
print(#function)
notificationCenter.removeAllPendingNotificationRequests()
}
///This is just a reusable form of all the copy and paste you did in your buttons. If you have to copy and paste make it reusable.
func scheduleTriggerNotification(title: String, body: String, categoryIdentifier: String, dateComponents : DateComponents, repeats: Bool) {
print(#function)
let content = UNMutableNotificationContent()
content.title = title
content.body = body
content.categoryIdentifier = categoryIdentifier
content.sound = UNNotificationSound.default

let trigger = UNCalendarNotificationTrigger(dateMatching: dateComponents, repeats: repeats)

let request = UNNotificationRequest(identifier: UUID().uuidString, content: content, trigger: trigger)
notificationCenter.add(request)
}
///Prints to console schduled notifications
func printNotifications(){
print(#function)
notificationCenter.getPendingNotificationRequests { request in
for req in request{
if req.trigger is UNCalendarNotificationTrigger{
print((req.trigger as! UNCalendarNotificationTrigger).nextTriggerDate()?.description ?? "invalid next trigger date")
}
}
}
}
//MARK: UNUserNotificationCenterDelegate
func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: @escaping (UNNotificationPresentationOptions) -> Void) {

completionHandler(.banner)
}
}
struct NotificationView_Previews: PreviewProvider {
static var previews: some View {
NotificationView()
}
}

Ionic 3/4 - Daily Local Notifications not working

So I found the solution to this one by myself. It's an error in the typings file of LocalNotifications package.

The correct usage for the options look like this:

    {
id: 1,
title: 'Notification Title',
text: 'Your notification text',
foreground: true,
trigger: {
every: {
hour: 8,
minute: 15
}
}
}

Just go into your node_modules/@ionic-native/local-notifications find the index.d.ts and find the line which says every?: ELocalNotificationTriggerUnit and change it to every?: any; now it should work perfectly.

Scheduled local notifications are not coming in flutter

Please read documentation in flutter_local_notifications carefully.In order to schedule notifications work, you have to add the lines below. Solution is this: add these lines after in AndroidManifest.xml

<receiver android:name="com.dexterous.flutterlocalnotifications.ScheduledNotificationBootReceiver">
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED"></action>
</intent-filter>
</receiver>
<receiver android:name="com.dexterous.flutterlocalnotifications.ScheduledNotificationReceiver" />

UNNotificationRequest to send local notification daily at a specific time

You can use UNCalendarNotificationTrigger for creating a notification that fires repeatedly using UNUserNotificationCenter. You can do something like this. The trick is to only have the time component in the Trigger date.

        let center = UNUserNotificationCenter.current()

let content = UNMutableNotificationContent()
content.title = "Attention!"
content.body = "Your daily alert is ready for you!"
content.sound = UNNotificationSound.default

let identifier = "com.yourdomain.notificationIdentifier"

var triggerDate = DateComponents()
triggerDate.hour = 18
triggerDate.minute = 30
let trigger = UNCalendarNotificationTrigger(dateMatching: triggerDate, repeats: true)

let request = UNNotificationRequest(identifier: identifier, content: content, trigger: trigger)

center.add(request, withCompletionHandler: { (error) in
if let error = error {
// Something went wrong
print("Error : \(error.localizedDescription)")
} else {
// Something went right
print("Success")
}
})

How to schedule multiple time specific local notifications in flutter

After hours of research I have solved this problem.
The full code is below.

import 'package:flutter_local_notifications/flutter_local_notifications.dart';
import 'package:flutter_native_timezone/flutter_native_timezone.dart';
import 'package:timezone/data/latest.dart' as tz;
import 'package:timezone/timezone.dart' as tz;

class NotificationHelper {
FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
FlutterLocalNotificationsPlugin();

/// Initialize notification
initializeNotification() async {
_configureLocalTimeZone();
const IOSInitializationSettings initializationSettingsIOS = IOSInitializationSettings();

const AndroidInitializationSettings initializationSettingsAndroid =
AndroidInitializationSettings("ic_launcher");

const InitializationSettings initializationSettings = InitializationSettings(
iOS: initializationSettingsIOS,
android: initializationSettingsAndroid,
);
await flutterLocalNotificationsPlugin.initialize(initializationSettings);
}

/// Set right date and time for notifications
tz.TZDateTime _convertTime(int hour, int minutes) {
final tz.TZDateTime now = tz.TZDateTime.now(tz.local);
tz.TZDateTime scheduleDate = tz.TZDateTime(
tz.local,
now.year,
now.month,
now.day,
hour,
minutes,
);
if (scheduleDate.isBefore(now)) {
scheduleDate = scheduleDate.add(const Duration(days: 1));
}
return scheduleDate;
}

Future<void> _configureLocalTimeZone() async {
tz.initializeTimeZones();
final String timeZone = await FlutterNativeTimezone.getLocalTimezone();
tz.setLocalLocation(tz.getLocation(timeZone));
}

/// Scheduled Notification
scheduledNotification({
required int hour,
required int minutes,
required int id,
required String sound,
}) async {
await flutterLocalNotificationsPlugin.zonedSchedule(
id,
'It\'s time to drink water!',
'After drinking, touch the cup to confirm',
_convertTime(hour, minutes),
NotificationDetails(
android: AndroidNotificationDetails(
'your channel id $sound',
'your channel name',
channelDescription: 'your channel description',
importance: Importance.max,
priority: Priority.high,
sound: RawResourceAndroidNotificationSound(sound),
),
iOS: IOSNotificationDetails(sound: '$sound.mp3'),
),
androidAllowWhileIdle: true,
uiLocalNotificationDateInterpretation: UILocalNotificationDateInterpretation.absoluteTime,
matchDateTimeComponents: DateTimeComponents.time,
payload: 'It could be anything you pass',
);
}

/// Request IOS permissions
void requestIOSPermissions() {
flutterLocalNotificationsPlugin
.resolvePlatformSpecificImplementation<IOSFlutterLocalNotificationsPlugin>()
?.requestPermissions(
alert: true,
badge: true,
sound: true,
);
}

cancelAll() async => await flutterLocalNotificationsPlugin.cancelAll();
cancel(id) async => await flutterLocalNotificationsPlugin.cancel(id);
}

add your custom times like this

for (int i = 0; i < _provider.getScheduleRecords.length; i++) {
_notificationHelper.scheduledNotification(
hour: int.parse(_provider.getScheduleRecords[i].time.split(":")[0]),
minutes: int.parse(_provider.getScheduleRecords[i].time.split(":")[1]),
id: _provider.getScheduleRecords[i].id,
sound: 'sound0',
);
}

Repeat Daily Local Notifications in iOS 10 does not get triggered when manually setting the Time and Date?

You are calling repeats on a Date with a day and month. Therefore, this date will not occur again until next year. Thus, no notification will be sent the following day. The trigger for your notification must only contain an hour and minute value using DateComponents to allow the notification to repeat every day:

var date = DateComponents()
date.hour = 11
date.minute = 41

let trigger = UNCalendarNotificationTrigger(dateMatching: date, repeats: true)
let content = UNNotificationContent()

let notification = UNNotificationRequest(identifier: "myNotification", content: content, trigger: trigger)

Schedule local notification every n days (timezone safe)

You can set them up upfront using UNCalendarNotificationTrigger for an n number of times and using an adjusted calendar for the current timeZone

import SwiftUI

class NotificationManager: NSObject, UNUserNotificationCenterDelegate{
static let shared: NotificationManager = NotificationManager()
let notificationCenter = UNUserNotificationCenter.current()

private override init(){
super.init()
requestNotification()
notificationCenter.delegate = self
getnotifications()
}

func requestNotification() {
print(#function)
notificationCenter.requestAuthorization(options: [.alert, .sound, .badge]) { granted, error in

if let error = error {
// Handle the error here.
print(error)
}

// Enable or disable features based on the authorization.
}
}
/// Uses [.day, .hour, .minute, .second] in current timeZone
func scheduleCalendarNotification(title: String, body: String, date: Date, repeats: Bool = false, identifier: String) {
print(#function)

let content = UNMutableNotificationContent()
content.title = title
content.body = body

let calendar = NSCalendar.current

let components = calendar.dateComponents([.day, .hour, .minute, .second], from: date)

let trigger = UNCalendarNotificationTrigger(dateMatching: components, repeats: repeats)

let request = UNNotificationRequest(identifier: identifier, content: content, trigger: trigger)
notificationCenter.add(request) { (error) in
if error != nil {
print(error!)
}
}
}
///Sets up multiple calendar notification based on a date
func recurringNotification(title: String, body: String, date: Date, identifier: String, everyXDays: Int, count: Int){
print(#function)
for n in 0..<count{
print(n)
let newDate = date.addingTimeInterval(TimeInterval(60*60*24*everyXDays*n))
//Idenfier must be unique so I added the n
scheduleCalendarNotification(title: title, body: body, date: newDate, identifier: identifier + n.description)
print(newDate)
}
}
///Prints to console schduled notifications
func getnotifications(){
notificationCenter.getPendingNotificationRequests { request in
for req in request{
if req.trigger is UNCalendarNotificationTrigger{
print((req.trigger as! UNCalendarNotificationTrigger).nextTriggerDate()?.description ?? "invalid next trigger date")
}
}
}
}

func userNotificationCenter(_ center: UNUserNotificationCenter, willPresent notification: UNNotification, withCompletionHandler completionHandler: @escaping (UNNotificationPresentationOptions) -> Void) {

completionHandler(.banner)
}
}
class ZuluNotTriggerViewModel:NSObject, ObservableObject, UNUserNotificationCenterDelegate{
@Published var currentTime: Date = Date()
let notificationMgr = NotificationManager.shared


///Sets up multiple calendar notification based on a date
func recurringNotification(title: String, body: String, date: Date, identifier: String, everyXDays: Int, count: Int){
print(#function)
notificationMgr.recurringNotification(title: title, body: body, date: date, identifier: identifier, everyXDays: everyXDays, count: count)

//just for show now so you can see the current date in ui
self.currentTime = Date()
}
///Prints to console schduled notifications
func getnotifications(){
notificationMgr.getnotifications()
}

}
struct ZuluNotTriggerView: View {
@StateObject var vm: ZuluNotTriggerViewModel = ZuluNotTriggerViewModel()
var body: some View {
VStack{
Button(vm.currentTime.description, action: {
vm.currentTime = Date()
})
Button("schedule-notification", action: {
let twoMinOffset = 120
//first one will be in 120 seconds
//gives time to change settings in simulator
//initial day, hour, minute, second
let initialDate = Date().addingTimeInterval(TimeInterval(twoMinOffset))
//relevant components will be day, hour minutes, seconds
vm.recurringNotification(title: "test", body: "repeat body", date: initialDate, identifier: "test", everyXDays: 2, count: 10)
})

Button("see notification", action: {
vm.getnotifications()
})
}
}
}

struct ZuluNotTriggerView_Previews: PreviewProvider {
static var previews: some View {
ZuluNotTriggerView()
}
}


Related Topics



Leave a reply



Submit