如何在Flutter中安排多个特定时间的本地通知

10
我正在使用Flutter开发一个水喝提醒应用。 我想要安排一系列特定时间的本地通知,用户可以将其添加到列表中并从列表中删除。

enter image description here

3个回答

14
我已经解决了这个问题。完整的代码如下所示。
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);
}

添加自定义时间的方法如下:
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',
  );
}

6

您可以使用 flutter_local_notifications 插件,它可以发送定时、即时和重复通知。

await flutterLocalNotificationsPlugin.zonedSchedule(
0,
'scheduled title',
'scheduled body',
tz.TZDateTime.now(tz.local).add(const Duration(seconds: 5)),
const NotificationDetails(
    android: AndroidNotificationDetails(
        'your channel id', 'your channel name',
        channelDescription: 'your channel description')),
androidAllowWhileIdle: true,
uiLocalNotificationDateInterpretation:
    UILocalNotificationDateInterpretation.absoluteTime);

这个例子将安排一个通知,在5秒后出现。


2
请注意,为了拥有多个通知,您需要改变通知的ID(这里是“0”),否则您将始终覆盖先前的通知而不是添加新的通知。 - sigma1510
@Rohith,你在这里提到通知将每5秒出现一次。请问是哪个东西让它每5秒重复一次?因为这是一个zonedSchedule()调用,会按照定义的时间表触发(在这种情况下是当前本地时间之后的5秒)。我也尝试了这个例子,但它只在5秒后显示一次通知,不会重复。 - Wassauf Khalid
@WassaufKhalid,答案中提供的代码片段不会产生重复通知,这里有一些示例展示了如何使用flutter_local_notifications。 - Rohith Nambiar

2

尝试使用Awesome Notifications

它具有许多功能,包括秒级精度的预定通知。

示例代码片段:

Future<void> scheduleNewNotification() async {
    
        await AwesomeNotifications().createNotification(
            content: NotificationContent(
                id: -1, // -1 is replaced by a random number
                channelKey: 'alerts',
                title: "Huston! The eagle has landed!",
                body:
                    "A small step for a man, but a giant leap to Flutter's community!",
                bigPicture: 'https://storage.googleapis.com/cms-storage-bucket/d406c736e7c4c57f5f61.png',
                largeIcon: 'https://storage.googleapis.com/cms-storage-bucket/0dbfcc7a59cd1cf16282.png',
                //'asset://assets/images/balloons-in-sky.jpg',
                notificationLayout: NotificationLayout.BigPicture,
                payload: {
                  'notificationId': '1234567890'
                }),
            actionButtons: [
              NotificationActionButton(key: 'REDIRECT', label: 'Redirect'),
              NotificationActionButton(
                  key: 'DISMISS',
                  label: 'Dismiss',
                  actionType: ActionType.DismissAction,
                  isDangerousOption: true)
            ],
            schedule: NotificationCalendar.fromDate(
                date: DateTime.now().add(const Duration(seconds: 10))));
      }

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接