import 'package:flutter_local_notifications/flutter_local_notifications.dart'; import 'package:timezone/timezone.dart' as tz; import 'package:timezone/data/latest.dart' as tz_data; class NotificationsRepository { final FlutterLocalNotificationsPlugin _notificationsPlugin; NotificationsRepository() : _notificationsPlugin = FlutterLocalNotificationsPlugin() { _initialize(); } Future _initialize() async { tz_data.initializeTimeZones(); const androidSettings = AndroidInitializationSettings('@mipmap/ic_launcher'); const iosSettings = DarwinInitializationSettings(); const initSettings = InitializationSettings( android: androidSettings, iOS: iosSettings, ); await _notificationsPlugin.initialize(initSettings); } Future showNotification({ required int id, required String title, required String body, String? payload, }) async { const androidDetails = AndroidNotificationDetails( 'lifetimer_channel', 'LifeTimer Notifications', channelDescription: 'Notifications for LifeTimer app', importance: Importance.high, priority: Priority.high, ); const iosDetails = DarwinNotificationDetails(); const notificationDetails = NotificationDetails( android: androidDetails, iOS: iosDetails, ); await _notificationsPlugin.show( id, title, body, notificationDetails, payload: payload, ); } Future scheduleNotification({ required int id, required String title, required String body, required DateTime scheduledDate, String? payload, }) async { const androidDetails = AndroidNotificationDetails( 'lifetimer_channel', 'LifeTimer Notifications', channelDescription: 'Notifications for LifeTimer app', importance: Importance.high, priority: Priority.high, ); const iosDetails = DarwinNotificationDetails(); const notificationDetails = NotificationDetails( android: androidDetails, iOS: iosDetails, ); await _notificationsPlugin.zonedSchedule( id, title, body, tz.TZDateTime.from(scheduledDate, tz.local), notificationDetails, uiLocalNotificationDateInterpretation: UILocalNotificationDateInterpretation.absoluteTime, payload: payload, ); } Future scheduleDailyReminder({ required int id, required String title, required String body, required int hour, required int minute, }) async { const androidDetails = AndroidNotificationDetails( 'lifetimer_daily_channel', 'Daily Reminders', channelDescription: 'Daily reminder notifications', importance: Importance.high, priority: Priority.high, ); const iosDetails = DarwinNotificationDetails(); const notificationDetails = NotificationDetails( android: androidDetails, iOS: iosDetails, ); await _notificationsPlugin.zonedSchedule( id, title, body, _nextInstanceOfTime(hour, minute), notificationDetails, uiLocalNotificationDateInterpretation: UILocalNotificationDateInterpretation.absoluteTime, matchDateTimeComponents: DateTimeComponents.time, payload: 'daily_reminder', ); } Future cancelNotification(int id) async { await _notificationsPlugin.cancel(id); } Future cancelAllNotifications() async { await _notificationsPlugin.cancelAll(); } Future> getPendingNotifications() async { return await _notificationsPlugin.pendingNotificationRequests(); } tz.TZDateTime _nextInstanceOfTime(int hour, int minute) { final now = tz.TZDateTime.now(tz.local); final scheduledDate = tz.TZDateTime( tz.local, now.year, now.month, now.day, hour, minute, 0, ); if (scheduledDate.isBefore(now)) { return scheduledDate.add(const Duration(days: 1)); } return scheduledDate; } }