Files
Tracker/lib/services/notification_service.dart

125 lines
3.9 KiB
Dart

import 'package:flutter_local_notifications/flutter_local_notifications.dart';
import 'package:timezone/timezone.dart' as tz;
import 'package:timezone/data/latest.dart' as tz;
import 'package:flutter/foundation.dart'; // For kIsWeb
class NotificationService {
static final NotificationService _instance = NotificationService._internal();
factory NotificationService() {
return _instance;
}
NotificationService._internal();
final FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
FlutterLocalNotificationsPlugin();
bool _isInitialized = false;
Future<void> initialize() async {
if (_isInitialized) return;
// Timezone initialization
if (!kIsWeb) {
tz.initializeTimeZones();
}
const AndroidInitializationSettings initializationSettingsAndroid =
AndroidInitializationSettings('@mipmap/ic_launcher');
final DarwinInitializationSettings initializationSettingsDarwin =
DarwinInitializationSettings(
requestAlertPermission: true,
requestBadgePermission: true,
requestSoundPermission: true,
);
// Linux initialization (optional, but good for completeness)
final LinuxInitializationSettings initializationSettingsLinux =
LinuxInitializationSettings(defaultActionName: 'Open notification');
final InitializationSettings initializationSettings = InitializationSettings(
android: initializationSettingsAndroid,
iOS: initializationSettingsDarwin,
macOS: initializationSettingsDarwin,
linux: initializationSettingsLinux,
);
await flutterLocalNotificationsPlugin.initialize(
initializationSettings,
onDidReceiveNotificationResponse: (NotificationResponse details) async {
// Handle notification tap
},
);
_isInitialized = true;
}
Future<void> scheduleNotification({
required int id,
required String title,
required String body,
required DateTime scheduledDate,
}) async {
if (kIsWeb) {
// Web platform limitation: Background scheduling is complex.
// For this demo/web preview, we'll just log it or rely on the UI confirmation.
print('Web Notification Scheduled: $title - $body at $scheduledDate');
return;
}
await flutterLocalNotificationsPlugin.zonedSchedule(
id,
title,
body,
tz.TZDateTime.from(scheduledDate, tz.local),
const NotificationDetails(
android: AndroidNotificationDetails(
'pad_tracker_channel',
'Pad Tracker Reminders',
channelDescription: 'Reminders to change pad/tampon',
importance: Importance.max,
priority: Priority.high,
),
iOS: DarwinNotificationDetails(),
),
androidScheduleMode: AndroidScheduleMode.exactAllowWhileIdle,
uiLocalNotificationDateInterpretation:
UILocalNotificationDateInterpretation.absoluteTime,
);
}
// New method for specific notification types
Future<void> showLocalNotification({
required int id,
required String title,
required String body,
String? channelId,
String? channelName,
}) async {
if (kIsWeb) {
print('Web Local Notification: $title - $body');
return;
}
const AndroidNotificationDetails androidNotificationDetails =
AndroidNotificationDetails(
'tracker_general', 'General Notifications',
channelDescription: 'General app notifications',
importance: Importance.max,
priority: Priority.high,
ticker: 'ticker');
const NotificationDetails notificationDetails =
NotificationDetails(android: androidNotificationDetails);
await flutterLocalNotificationsPlugin.show(
id, title, body, notificationDetails,
payload: 'item x');
}
Future<void> cancelNotification(int id) async {
await flutterLocalNotificationsPlugin.cancel(id);
}
}