Android 为什么选择0个挂起的通知
我正在使用并调用flatterLocalNotificationsPlugin.pendingNotificationRequests() 始终返回0(零),即使我执行 flatterLocalNotificationsPlugin().show 两次,不要点击通知,留下通知,代码如下所示,取自示例,只需简单修改,添加IDOFMG作为消息的idAndroid 为什么选择0个挂起的通知,android,flutter,push-notification,localnotification,flutter-local-notification,Android,Flutter,Push Notification,Localnotification,Flutter Local Notification,我正在使用并调用flatterLocalNotificationsPlugin.pendingNotificationRequests() 始终返回0(零),即使我执行 flatterLocalNotificationsPlugin().show 两次,不要点击通知,留下通知,代码如下所示,取自示例,只需简单修改,添加IDOFMG作为消息的id import 'dart:async'; import 'dart:io'; import 'dart:typed_data'; import 'dar
import 'dart:async';
import 'dart:io';
import 'dart:typed_data';
import 'dart:ui';
import 'package:device_info/device_info.dart';
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:flutter_local_notifications/flutter_local_notifications.dart';
import 'package:flutter_native_timezone/flutter_native_timezone.dart';
import 'package:http/http.dart' as http;
import 'package:path_provider/path_provider.dart';
import 'package:rxdart/subjects.dart';
final FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
FlutterLocalNotificationsPlugin();
/// Streams are created so that app can respond to notification-related events
/// since the plugin is initialised in the `main` function
final BehaviorSubject<ReceivedNotification> didReceiveLocalNotificationSubject =
BehaviorSubject<ReceivedNotification>();
final BehaviorSubject<String?> selectNotificationSubject =
BehaviorSubject<String?>();
const MethodChannel platform =
MethodChannel('dexterx.dev/flutter_local_notifications_example');
class ReceivedNotification {
ReceivedNotification({
required this.id,
required this.title,
required this.body,
required this.payload,
});
final int id;
final String? title;
final String? body;
final String? payload;
}
String? selectedNotificationPayload;
/// IMPORTANT: running the following code on its own won't work as there is
/// setup required for each platform head project.
///
/// Please download the complete example app from the GitHub repository where
/// all the setup has been done
Future<void> main() async {
// needed if you intend to initialize in the `main` function
WidgetsFlutterBinding.ensureInitialized();
final NotificationAppLaunchDetails? notificationAppLaunchDetails =
await flutterLocalNotificationsPlugin.getNotificationAppLaunchDetails();
String initialRoute = HomePage.routeName;
if (notificationAppLaunchDetails?.didNotificationLaunchApp ?? false) {
selectedNotificationPayload = notificationAppLaunchDetails!.payload;
initialRoute = SecondPage.routeName;
}
const AndroidInitializationSettings initializationSettingsAndroid =
AndroidInitializationSettings('@mipmap/ic_launcher');
/// Note: permissions aren't requested here just to demonstrate that can be
/// done later
final IOSInitializationSettings initializationSettingsIOS =
IOSInitializationSettings(
requestAlertPermission: false,
requestBadgePermission: false,
requestSoundPermission: false,
onDidReceiveLocalNotification:
(int id, String? title, String? body, String? payload) async {
didReceiveLocalNotificationSubject.add(ReceivedNotification(
id: id, title: title, body: body, payload: payload));
});
const MacOSInitializationSettings initializationSettingsMacOS =
MacOSInitializationSettings(
requestAlertPermission: false,
requestBadgePermission: false,
requestSoundPermission: false);
final InitializationSettings initializationSettings = InitializationSettings(
android: initializationSettingsAndroid,
iOS: initializationSettingsIOS,
macOS: initializationSettingsMacOS);
await flutterLocalNotificationsPlugin.initialize(initializationSettings,
onSelectNotification: (String? payload) async {
if (payload != null) {
debugPrint('notification payload: $payload');
}
selectedNotificationPayload = payload;
selectNotificationSubject.add(payload);
});
runApp(
MaterialApp(
initialRoute: initialRoute,
routes: <String, WidgetBuilder>{
HomePage.routeName: (_) => HomePage(notificationAppLaunchDetails),
SecondPage.routeName: (_) => SecondPage(selectedNotificationPayload)
},
),
);
}
class PaddedElevatedButton extends StatelessWidget {
const PaddedElevatedButton({
required this.buttonText,
required this.onPressed,
Key? key,
}) : super(key: key);
final String buttonText;
final VoidCallback onPressed;
@override
Widget build(BuildContext context) => Padding(
padding: const EdgeInsets.fromLTRB(0, 0, 0, 8),
child: ElevatedButton(
onPressed: onPressed,
child: Text(buttonText),
),
);
}
class HomePage extends StatefulWidget {
const HomePage(
this.notificationAppLaunchDetails, {
Key? key,
}) : super(key: key);
static const String routeName = '/';
final NotificationAppLaunchDetails? notificationAppLaunchDetails;
bool get didNotificationLaunchApp =>
notificationAppLaunchDetails?.didNotificationLaunchApp ?? false;
@override
_HomePageState createState() => _HomePageState();
}
class _HomePageState extends State<HomePage> {
@override
void initState() {
super.initState();
_requestPermissions();
_configureDidReceiveLocalNotificationSubject();
_configureSelectNotificationSubject();
}
void _configureSelectNotificationSubject() {
selectNotificationSubject.stream.listen((String? payload) async {
await Navigator.pushNamed(context, '/secondPage');
});
}
void _requestPermissions() {
flutterLocalNotificationsPlugin
.resolvePlatformSpecificImplementation<
IOSFlutterLocalNotificationsPlugin>()
?.requestPermissions(
alert: true,
badge: true,
sound: true,
);
flutterLocalNotificationsPlugin
.resolvePlatformSpecificImplementation<
MacOSFlutterLocalNotificationsPlugin>()
?.requestPermissions(
alert: true,
badge: true,
sound: true,
);
}
void _configureDidReceiveLocalNotificationSubject() {
didReceiveLocalNotificationSubject.stream
.listen((ReceivedNotification receivedNotification) async {
await showDialog(
context: context,
builder: (BuildContext context) => CupertinoAlertDialog(
title: receivedNotification.title != null
? Text(receivedNotification.title!)
: null,
content: receivedNotification.body != null
? Text(receivedNotification.body!)
: null,
actions: <Widget>[
CupertinoDialogAction(
isDefaultAction: true,
onPressed: () async {
Navigator.of(context, rootNavigator: true).pop();
await Navigator.push(
context,
MaterialPageRoute<void>(
builder: (BuildContext context) =>
SecondPage(receivedNotification.payload),
),
);
},
child: const Text('Ok'),
)
],
),
);
});
}
@override
void dispose() {
didReceiveLocalNotificationSubject.close();
selectNotificationSubject.close();
super.dispose();
}
@override
Widget build(BuildContext context) => MaterialApp(
home: Scaffold(
appBar: AppBar(
title: const Text('Plugin example app'),
),
body: SingleChildScrollView(
child: Padding(
padding: const EdgeInsets.all(8),
child: Center(
child: Column(
children: <Widget>[
const Padding(
padding: EdgeInsets.fromLTRB(0, 0, 0, 8),
child: Text(
'Tap on a notification when it appears to trigger'
' navigation'),
),
Padding(
padding: const EdgeInsets.fromLTRB(0, 0, 0, 8),
child: Text.rich(
TextSpan(
children: <InlineSpan>[
const TextSpan(
text: 'Did notification launch app? ',
style: TextStyle(fontWeight: FontWeight.bold),
),
TextSpan(
text: '${widget.didNotificationLaunchApp}',
)
],
),
),
),
if (widget.didNotificationLaunchApp)
Padding(
padding: const EdgeInsets.fromLTRB(0, 0, 0, 8),
child: Text.rich(
TextSpan(
children: <InlineSpan>[
const TextSpan(
text: 'Launch notification payload: ',
style: TextStyle(fontWeight: FontWeight.bold),
),
TextSpan(
text: widget
.notificationAppLaunchDetails!.payload,
)
],
),
),
),
PaddedElevatedButton(
buttonText: 'Show 1 plain notification with payload',
onPressed: () async {
await _showNotification(1);
},
),
PaddedElevatedButton(
buttonText: 'Show 2 plain notification with payload',
onPressed: () async {
await _showNotification(2);
},
),
PaddedElevatedButton(
buttonText: 'Check pending notifications',
onPressed: () async {
await _checkPendingNotificationRequests();
},
),
],
),
),
),
),
),
);
Future<void> _showNotification(int idOfMsg) async {
const AndroidNotificationDetails androidPlatformChannelSpecifics =
AndroidNotificationDetails(
'your channel id', 'your channel name', 'your channel description',
importance: Importance.max,
priority: Priority.high,
ticker: 'ticker');
const NotificationDetails platformChannelSpecifics =
NotificationDetails(android: androidPlatformChannelSpecifics);
await flutterLocalNotificationsPlugin.show(
idOfMsg, 'plain title'+ idOfMsg.toString(), 'plain body', platformChannelSpecifics,
payload: 'item x' + idOfMsg.toString());
}
Future<void> _cancelNotification() async {
await flutterLocalNotificationsPlugin.cancel(0);
}
Future<void> _checkPendingNotificationRequests() async {
final List<PendingNotificationRequest> pendingNotificationRequests =
await flutterLocalNotificationsPlugin.pendingNotificationRequests();
return showDialog<void>(
context: context,
builder: (BuildContext context) => AlertDialog(
content:
Text('${pendingNotificationRequests.length} pending notification '
'requests'),
actions: <Widget>[
TextButton(
onPressed: () {
Navigator.of(context).pop();
},
child: const Text('OK'),
),
],
),
);
}
Future<void> _cancelAllNotifications() async {
await flutterLocalNotificationsPlugin.cancelAll();
}
}
class SecondPage extends StatefulWidget {
const SecondPage(
this.payload, {
Key? key,
}) : super(key: key);
static const String routeName = '/secondPage';
final String? payload;
@override
State<StatefulWidget> createState() => SecondPageState();
}
class SecondPageState extends State<SecondPage> {
String? _payload;
@override
void initState() {
super.initState();
_payload = widget.payload;
}
@override
Widget build(BuildContext context) => Scaffold(
appBar: AppBar(
title: Text('Second Screen ${_payload ?? ''} with payload: '),
),
body: Center(
child: ElevatedButton(
onPressed: () {
Navigator.pop(context);
},
child: const Text('Go back!'),
),
),
);
}
导入'dart:async';
导入“dart:io”;
导入“dart:键入的_数据”;
导入“dart:ui”;
导入“package:device_info/device_info.dart”;
进口“包装:颤振/cupertino.dart”;
进口“包装:颤振/材料.省道”;
导入“包:flifter/services.dart”;
导入“package:flatter_local_notifications/flatter_local_notifications.dart”;
导入“package:flatter_native_timezone/flatter_native_timezone.dart”;
将“package:http/http.dart”导入为http;
导入“package:path_provider/path_provider.dart”;
导入“package:rxdart/subjects.dart”;
最终颤振局部通知图京颤振局部通知图京=
flatterLocalNotificationsPlugin();
///创建流以便应用程序能够响应通知相关事件
///因为插件是在“main”函数中初始化的
最终行为主体未收到本地通知主体=
行为主体();
最终行为主体选择通知主体=
行为主体();
const MethodChannel平台=
MethodChannel('dexterx.dev/flatter_local_notification_example');
收到通知的班级{
收到通知({
需要这个.id,
需要这个标题,
需要这个机构,
需要这个有效载荷,
});
最终int id;
最终字符串?标题;
最后一串?主体;
最终串?有效载荷;
}
一串选择通知有效载荷;
///重要提示:单独运行以下代码将无法正常工作
///每个平台头部项目所需的设置。
///
///请从GitHub存储库下载完整的示例应用程序,其中
///所有设置都已完成
Future main()异步{
//如果要在“main”函数中初始化,则需要
WidgetsFlutterBinding.ensureInitialized();
最终通知ApplaunchDetails?通知ApplaunchDetails=
等待LocalNotificationsPlugin.getNotificationAppLaunchDetails();
字符串initialRoute=HomePage.routeName;
if(notificationAppLaunchDetails?.didNotificationLaunchApp??false){
selectedNotificationPayload=notificationAppLaunchDetails!.payload;
initialRoute=SecondPage.routeName;
}
常量AndroidInitializationSettings initializationSettingsAndroid=
AndroidInitializationSettings(“@mipmap/ic_launcher”);
///注意:此处请求权限不仅仅是为了证明可以
///以后做
最终IOS初始化设置初始化设置SIOS=
IOS初始化设置(
requestAlertPermission:false,
请求权限:false,
请求权限:false,
onDidReceiveLocalNotification:
(int-id、String-title、String-body、String-payload)异步{
didReceiveLocalNotificationSubject.add(ReceivedNotification(
id:id,title:title,body:body,payload:payload));
});
常量MacOSInitializationSettings初始化设置Smacos=
MacOSInitializationSettings(
requestAlertPermission:false,
请求权限:false,
请求权限:false);
最终初始化设置初始化设置=初始化设置(
android:initializationSettingsAndroid,
iOS:初始化设置SIOS,
macOS:初始化设置SMACOS);
等待LocalNotificationsPlugin.initialize(初始化设置,
onSelectNotification:(字符串?有效负载)异步{
如果(有效负载!=null){
debugPrint('notification payload:$payload');
}
selectedNotificationPayload=有效载荷;
选择NotificationSubject.add(有效载荷);
});
runApp(
材料聚丙烯(
initialRoute:initialRoute,
路线:{
HomePage.routeName:()=>主页(notificationAppLaunchDetails),
SecondPage.routeName:()=>SecondPage(selectedNotificationPayload)
},
),
);
}
类PaddedElevatedButton扩展了无状态小部件{
常数paddedelevated按钮({
需要此.buttonText,
需要这个。按下按钮,
钥匙?,钥匙,
}):super(key:key);
最后一个字符串buttonText;
最后一次按下按钮;
@凌驾
小部件构建(BuildContext上下文)=>填充(
padding:const EdgeInsets.fromLTRB(0,0,0,8),
儿童:升降按钮(
onPressed:onPressed,
子项:文本(buttonText),
),
);
}
类主页扩展了StatefulWidget{
康斯特网页(
此通知适用于详细信息{
钥匙?,钥匙,
}):super(key:key);
静态常量字符串routeName='/';
最终通知ApplaunchDetails?通知ApplaunchDetails;
bool get didNotificationLaunchApp=>
notificationAppLaunchDetails?.didNotificationLaunchApp??错误;
@凌驾
_HomePageState createState()=>\u HomePageState();
}
类_HomePageState扩展状态{
@凌驾
void initState(){
super.initState();
_请求权限();
_configureDidReceiveLocalNotificationSubject();
_配置SelectNotificationSubject();
}
void(配置SelectNotificationSubject){
selectNotificationSubject.stream.listen((字符串?有效负载)异步{
wait Navigator.pushNamed(上下文“/secondPage”);
});
}
void _requestPermissions(){
局部通知
.resolvePlatformSpecificImplementation<
IostLocalNotificationsPlugin>()
?请求权限(
警报:是的,
徽章:没错,
听起来:是的,
);
局部通知
.resolvePlatformSpecificImplementation<
MacOSLocalNotificationsPlugin>()
?请求权限(
警报:是的,
徽章:没错,
flutterLocalNotificationsPlugin
.resolvePlatformSpecificImplementation<
AndroidFlutterLocalNotificationsPlugin>()!
.getActiveNotifications();