Flutter Local Notification点击通知如何跳转至非初始路由页面
Flutter 本地通知点击跳转指定页面实现方案
你之前查阅onSelectNotification相关资料未实现成功,核心是漏配了点击回调、未处理应用前后台/冷启动全场景,同时缺少全局导航上下文支持,按以下步骤修改即可:
1. 新增全局导航Key
首先在应用全局位置定义导航Key,解决通知触发时无可用BuildContext无法跳转的问题:
// 放在main.dart全局位置即可 final GlobalKey<NavigatorState> navigatorKey = GlobalKey<NavigatorState>();
在MaterialApp/CupertinoApp中注册该Key:
MaterialApp( navigatorKey: navigatorKey, // 注册全局导航key // 保留原有其他配置:路由、主题、首页等 )
2. 修改NotificationService代码
主要调整3处:
- 初始化插件时配置通知点击回调,兼容新旧版本API
- 增加冷启动场景(应用完全被杀掉时点击通知)的启动判断
- 发送通知方法增加
payload参数,用于传递跳转目标标识
class NotificationService { static final NotificationService _notificationService = NotificationService._internal(); factory NotificationService() { return _notificationService; } final FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin = FlutterLocalNotificationsPlugin(); NotificationService._internal(); Future<void> initNotification() async { // Android 初始化配置 final AndroidInitializationSettings initializationSettingsAndroid = AndroidInitializationSettings('@mipmap/ic_launcher'); // iOS 初始化配置 final IOSInitializationSettings initializationSettingsIOS = IOSInitializationSettings( requestAlertPermission: true, requestBadgePermission: true, requestSoundPermission: true, ); final InitializationSettings initializationSettings = InitializationSettings( android: initializationSettingsAndroid, iOS: initializationSettingsIOS); // 初始化插件,绑定点击回调 await flutterLocalNotificationsPlugin.initialize( initializationSettings, // 适配低版本插件API:应用在前台/后台时点击通知触发 onSelectNotification: (String? payload) async { _handleNotificationClick(payload); }, // 适配高版本(10.0+)插件API:应用在前台/后台时点击通知触发 onDidReceiveNotificationResponse: (NotificationResponse response) { _handleNotificationClick(response.payload); }, ); // 处理冷启动场景:应用完全关闭时点击通知打开APP final NotificationAppLaunchDetails? launchDetails = await flutterLocalNotificationsPlugin.getNotificationAppLaunchDetails(); if (launchDetails != null && launchDetails.didNotificationLaunchApp) { _handleNotificationClick(launchDetails.notificationResponse?.payload); } } // 统一处理通知点击跳转逻辑 void _handleNotificationClick(String? payload) { if (payload == null) return; // 按payload匹配跳转目标,两种跳转方式二选一即可 switch(payload) { case 'target_page': // 方式1:直接跳转对应Widget页面 navigatorKey.currentState?.push( MaterialPageRoute(builder: (_) => const YourTargetStatefulWidget()) ); // 方式2:命名路由跳转 // navigatorKey.currentState?.pushNamed('/yourTargetRoute'); break; // 可扩展其他页面的跳转匹配规则 } } // 发送通知方法新增payload参数 Future<void> showNotification( int id, String title, String body, int time, {String? payload}) async { await flutterLocalNotificationsPlugin.zonedSchedule( id, title, body, tz.TZDateTime.now(tz.local).add(Duration(seconds: time)), const NotificationDetails( android: AndroidNotificationDetails('main_channel', 'Main Channel', channelDescription: "ashwin", importance: Importance.max, priority: Priority.max), iOS: IOSNotificationDetails( sound: 'default.wav', presentAlert: true, presentBadge: true, presentSound: true, ), ), uiLocalNotificationDateInterpretation: UILocalNotificationDateInterpretation.absoluteTime, androidAllowWhileIdle: true, payload: payload, // 传入跳转标识 ); } }
3. 发送通知时传入对应跳转标识
在触发通知的位置调用方法时,传入对应页面的payload值即可:
TextButton( onPressed: () { NotificationService().showNotification( 1, "7 secondes", "7 secondes", 7, payload: 'target_page' // 和跳转逻辑里的匹配值保持对应 ); }, child: Card( child: ListTile( contentPadding: EdgeInsets.all(10), title: Text("Schedule Notification"), ), ), )
注意事项
- 请确保在APP启动第一时间(比如main函数
runApp之后,或者首页initState中)调用NotificationService().initNotification()完成初始化 - 如果使用命名路由,提前在MaterialApp中完成路由表注册
- 高版本Android需要确保通知权限已经申请,否则通知无法正常弹出,点击逻辑不会触发
内容的提问来源于stack exchange,提问作者frenchconnection
相关产品推荐
相关产品推荐

