I have a problem with showing notification for open file in my app.
Here's the code for create a csv file
getCsv() async {
if (await Permission.storage.request().isGranted) {
//store file in documents folder
String dir =
"${(await getExternalStorageDirectory())!.path}/csv_bodega.csv";
String file = dir;
File f = File(file);
// convert rows to String and write as csv file
String csv = const ListToCsvConverter().convert(itemsList);
f.writeAsString(csv);
// ignore: use_build_context_synchronously
ScaffoldMessenger.of(context).showSnackBar(
const SnackBar(content: Text('Archivo descargado')),
);
const android = AndroidNotificationDetails('0', 'Adun Accounts',
channelDescription: 'channel description',
priority: Priority.high,
importance: Importance.max,
icon: '');
const platform = NotificationDetails(android: android);
await flutterLocalNotificationsPlugin
.show(0, "CSV Bodega", "Descarga completada", platform, payload: dir);
} else {
// ignore: unused_local_variable
Map<Permission, PermissionStatus> statuses = await [
Permission.storage,
].request();
}
}
Here's the code I paste in main.dart for initializate flutterLocalNotificationsPlugin
FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
FlutterLocalNotificationsPlugin();
Future<void> initNotification() async {
// initialise the plugin. app_icon needs to be a added as a drawable resource to the Android head project
const AndroidInitializationSettings initializationSettingsAndroid =
AndroidInitializationSettings('notification_icon');
const InitializationSettings initializationSettings = InitializationSettings(
android: initializationSettingsAndroid,
);
}
I get this error:
PlatformException (PlatformException(error, Attempt to invoke virtual method 'int java.lang.Integer.intValue()' on a null object reference, null, java.lang.NullPointerException: Attempt to invoke virtual method 'int java.lang.Integer.intValue()' on a null object reference
at com.dexterous.flutterlocalnotifications.FlutterLocalNotificationsPlugin.setSmallIcon(FlutterLocalNotificationsPlugin.java:425)
at com.dexterous.flutterlocalnotifications.FlutterLocalNotificationsPlugin.createNotification(FlutterLocalNotificationsPlugin.java:326)
at com.dexterous.flutterlocalnotifications.FlutterLocalNotificationsPlugin.showNotification(FlutterLocalNotificationsPlugin.java:1146)
at com.dexterous.flutterlocalnotifications.FlutterLocalNotificationsPlugin.show(FlutterLocalNotificationsPlugin.java:1462)
at com.dexterous.flutterlocalnotifications.FlutterLocalNotificationsPlugin.onMethodCall(FlutterLocalNotificationsPlugin.java:1299)
at io.flutter.plugin.common.MethodChannel$IncomingMethodCallHandler.onMessage(MethodChannel.java:262)
at io.flutter.embedding.engine.dart.DartMessenger.invokeHandler(DartMessenger.java:295)
at io.flutter.embedding.engine.dart.DartMessenger.lambda$dispatchMessageToQueue$0$io-flutter-embedding-engine-dart-DartMessenger(DartMessenger.java:319)
at io.flutter.embedding.engine.dart.DartMessenger$$ExternalSyntheticLambda0.run(Unknown Source:12)
at android.os.Handler.handleCallback(Handler.java:938)
at android.os.Handler.dispatchMessage(Handler.java:99)
at android.os.Looper.loop(Looper.java:236)
at android.app.ActivityThread.main(ActivityThread.java:7861)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:600)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:967)
))
I don't know what to do. Apart from that, I searched that the plugin open_filex helps for open a file with a specified path. But I don't know where to use in my code. Help me, please.
Related
I tried to download an image when push notification is coming. When application is opened this feature is work fine, but when application is closed I can't download the image and got this error :
MissingPluginException(No implementation found for method getApplicationDocumentsDirectory on channel plugins.flutter.io/path_provider)
I've tried to register the path provider in MainActivity but doesn't work.
Here are sample of my code
Future<void> _firebaseMessagingBackgroundHandler(RemoteMessage message) async {
logger.d("Handling a background message: ${message.data}");
if (message.data != null) {
final data = message.data;
final title = data['title'];
final body = data['content'];
await CustomLocalNotification.showNotification(title, body, data['type'], data['image']);
}
return Future<void>.value();
}
There is an image that i try to download and show it on push notification. And here is the code to download and handle push notification
static Dio dio = DioUtil.instance(baseUrl:"" );
static Future<String> _downloadAndSaveFile(String url, String fileName) async {
final Directory directory = Platform.isIOS?await getApplicationSupportDirectory(): await getApplicationDocumentsDirectory();
final String filePath = Platform.isIOS?'${directory.path}/$fileName.jpg': '${directory.path}/$fileName';
final response = await dio.get(url, options: Options(
responseType: ResponseType.bytes,
followRedirects: false,
validateStatus: (status) { return status < 500; }
),);
final File file = File(filePath);
if(Platform.isIOS){
final imageBytes = response.data;
final bytes = imageBytes.buffer.asUint8List();
await file.writeAsBytes(bytes);
}else{
var raf = file.openSync(mode: FileMode.write);
raf.writeFromSync(response.data);
await raf.close();
}
return filePath;
}
static Future<void> showNotification(String title, String body, String type, String images,) async {
StyleInformation styleInformation;
IOSNotificationDetails iosNotificationDetails;
if((type==NotificationType.Promo.title || type == NotificationType.News.title) && images !=""){
final String largeIconPath = await _downloadAndSaveFile(
'$images', 'largeIcon');
styleInformation = BigPictureStyleInformation(FilePathAndroidBitmap(largeIconPath),
contentTitle: '$type',
htmlFormatContentTitle: true,
summaryText: '$title',
htmlFormatSummaryText: true
);
iosNotificationDetails =
IOSNotificationDetails(attachments: <IOSNotificationAttachment>[
IOSNotificationAttachment(largeIconPath),
]);
}else{
styleInformation = DefaultStyleInformation(true, true);
iosNotificationDetails =
IOSNotificationDetails();
}
AndroidNotificationDetails androidPlatformChannelSpecifics = AndroidNotificationDetails(
'xx',
'xx_channel_name',
channelDescription: 'xx_channel_description',
importance: Importance.max,
priority: Priority.high,
ticker: 'ticker',
styleInformation: styleInformation
);
NotificationDetails platformChannelSpecifics = NotificationDetails(android: androidPlatformChannelSpecifics, iOS: iosNotificationDetails);
await flutterLocalNotificationsPlugin.show(0, '$type', '$title', platformChannelSpecifics);
}
}
Seems i got error in this line :
final Directory directory = Platform.isIOS?await getApplicationSupportDirectory(): await getApplicationDocumentsDirectory();
Could you please suggest me how to fix this. I Thank you.
Register path provider in MainActivity look like this
override fun registerWith(registry: PluginRegistry) {
io.flutter.plugins.firebasemessaging.FirebaseMessagingPlugin.registerWith(registry?.registrarFor("io.flutter.plugins.firebasemessaging.FirebaseMessagingPlugin"));
PathProviderPlugin.registerWith(registry.registrarFor("io.flutter.plugins.pathprovider.PathProviderPlugin"))
}
but it doesn't work
I am trying to show notifications in my Flutter app but I am getting this exception:
Unhandled Exception: PlatformException(error, Attempt to invoke virtual method 'boolean java.lang.Boolean.booleanValue()' on a null object reference, null, java.lang.NullPointerException: Attempt to invoke virtual method 'boolean java.lang.Boolean.booleanValue()' on a null object reference
this is the method I'm using. How can I fix it?
void sendNotification({String? title, String? body}) async {
FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
FlutterLocalNotificationsPlugin();
const AndroidInitializationSettings initializationSettingsAndroid =
AndroidInitializationSettings('#mipmap/ic_launcher');
const IOSInitializationSettings initializationSettingsIOS =
IOSInitializationSettings(
requestAlertPermission: true,
requestBadgePermission: true,
requestSoundPermission: true,
);
const InitializationSettings initializationSettings = InitializationSettings(
android: initializationSettingsAndroid,
iOS: initializationSettingsIOS,);
await flutterLocalNotificationsPlugin.initialize(
initializationSettings,
);
flutterLocalNotificationsPlugin.show(
0,
title,
body,
const NotificationDetails(
android:
AndroidNotificationDetails(
'channel id',
'channel',
'channel description',
importance: Importance.max
)),
);
}
I am working on a flutter app. I am creating a pdf file in the "Downloads" folder, after creating the file in the "Downloads" folder, showing a notification "Download Completed" using the "local_notification" plugin.
Now I want to show that pdf when the user clicks on the notification. Can anybody guide me on how I can do that?
Below is my code
final android = AndroidNotificationDetails('0', 'Adun Accounts',
channelDescription: 'channel description',
priority: Priority.high,
importance: Importance.max,
icon: '');
final iOS = IOSNotificationDetails();
final platform = NotificationDetails(android: android, iOS: iOS);
await flutterLocalNotificationsPlugin.show(
0, // notification id
fileName,
'Download complete.',
platform);
show() has a parameter called payload , you can pass the path to the pdf file here. Add the plugin open_file in your pubspec.yaml. Then inside main.dart, add the following code
FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
FlutterLocalNotificationsPlugin();
Future<void> initNotification() async {
// initialise the plugin. app_icon needs to be a added as a drawable resource to the Android head project
const AndroidInitializationSettings initializationSettingsAndroid =
AndroidInitializationSettings('notification_icon');
final IOSInitializationSettings initializationSettingsIOS =
IOSInitializationSettings();
final MacOSInitializationSettings initializationSettingsMacOS =
MacOSInitializationSettings();
final InitializationSettings initializationSettings = InitializationSettings(
android: initializationSettingsAndroid,
iOS: initializationSettingsIOS,
macOS: initializationSettingsMacOS);
await flutterLocalNotificationsPlugin.initialize(initializationSettings,
onSelectNotification: (String? payload) {
if (payload != null) OpenFile.open(payload);
});
}
Note: This function should not be inside any class.
I'm using flutterlocalnotifications package and FCM to send notifications to my users. Everything working perfectly. I can show notifications to my users when my app is in the background, foreground, or closed. I can reach payload value in foreground and background, but when the app is killed I can't reach payload anymore. I test in catlog but there isn't any print in the onSelectNotification.
How can reach this payload?
This is my notification handler class
import 'package:flutter/cupertino.dart';
import 'package:flutter/material.dart';
import 'package:flutter_local_notifications/flutter_local_notifications.dart';
AndroidNotificationChannel channel = AndroidNotificationChannel(
'high_importance_channel', // id
'High Importance Notifications', // title
'This channel is used for important notifications.', // description
importance: Importance.high,
);
final FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
FlutterLocalNotificationsPlugin();
Future<void> _firebaseMessagingBackgroundHandler(RemoteMessage message) async {
// await Firebase.initializeApp();
//Bildirim geldiği anda datayı elde ettiğimiz alan
final dynamic data = message.data;
print('Data in background : ${data.toString()}');
NotificationHandler.showNotification(data);
}
class NotificationHandler {
final FirebaseMessaging _firebaseMessaging = FirebaseMessaging.instance;
static final NotificationHandler _singleton = NotificationHandler._internal();
factory NotificationHandler() {
return _singleton;
}
NotificationHandler._internal();
BuildContext myContext;
initializeFCMNotifications(BuildContext context) async {
await _firebaseMessaging.setForegroundNotificationPresentationOptions(
alert: true, badge: true, sound: true);
var initializationSettingsAndroid =
AndroidInitializationSettings('app_icon');
var initializationSettingsIOS = IOSInitializationSettings(
onDidReceiveLocalNotification: onDidReceiveLocalNotification);
var initializationSettings = InitializationSettings(
android: initializationSettingsAndroid, iOS: initializationSettingsIOS);
await flutterLocalNotificationsPlugin.initialize(initializationSettings,
onSelectNotification: onSelectNotification);
await _firebaseMessaging.subscribeToTopic("all");
await FirebaseMessaging.instance
.getInitialMessage()
.then((RemoteMessage message) {
if (message != null) {
print('initialmessage tetiklendi : ' + message.data.toString());
}
});
FirebaseMessaging.onMessage.listen((RemoteMessage message) {
var notification = message.notification;
var android = message.notification?.android;
print('ONMESSAGE ÇALIŞTI');
print('onmessage tetiklendi data : ' +
message.data['message'] +
' title ' +
message.data['title']);
showNotification(message.data);
});
FirebaseMessaging.onBackgroundMessage(_firebaseMessagingBackgroundHandler);
FirebaseMessaging.onMessageOpenedApp.listen((RemoteMessage message) {
print('Onmessageopened : ' + message.data.toString());
});
}
static void showNotification(Map<String, dynamic> data) async {
const androidPlatformChannelSpecifics = AndroidNotificationDetails(
'1234', 'Yeni Mesaj', 'your channel description',
importance: Importance.max, priority: Priority.high, ticker: 'ticker');
const IOSPlatformChannelSpecifics = IOSNotificationDetails();
const platformChannelSpecifics = NotificationDetails(
android: androidPlatformChannelSpecifics,
iOS: IOSPlatformChannelSpecifics);
await flutterLocalNotificationsPlugin.show(
0, data['title'], data['message'], platformChannelSpecifics,
payload: 'The value when notification tapped');
}
Future onSelectNotification(String payload) async {
if (payload != null) {
debugPrint('notification payload : $payload');
}
}
Future onDidReceiveLocalNotification(
int id, String title, String body, String payload) {}
}
and these are the versions of the packages I use
firebase_messaging: ^9.1.1
flutter_local_notifications: ^5.0.0+1
I am trying to navigate to a specific page using local notification, the moment the user touches the notification, below I leave the code of how I am doing it, basically, the problem is when onSelectNotification is called everything that is before is executed but Once Navigator.push is called, it does not go to the screen that I tell it and it does not raise any exceptions and what is after is not executed either.
/// Allows you to navigate to a specific screen from the notification
Future onSelectNotification(String payload) async {
if (payload != null) {
debugPrint('Notification payload: $payload');//it shows
}
await Navigator.push(context, MaterialPageRoute(builder: (context) => AnyScreen()));
debugPrint("go to AnyScreen");//does not show it
}
#override
void initState() {
// TODO: implement initState
super.initState();
/// local notication inicialization
const AndroidNotificationChannel channel = AndroidNotificationChannel(
'high_importance_channel', // id
'High Importance Notifications', // title
'This channel is used for important notifications.', // description
importance: Importance.max,
);
FlutterLocalNotificationsPlugin flip =
new FlutterLocalNotificationsPlugin();
flip
.resolvePlatformSpecificImplementation<
AndroidFlutterLocalNotificationsPlugin>()
?.createNotificationChannel(channel);
const AndroidInitializationSettings android =
AndroidInitializationSettings('app_icon');
final IOSInitializationSettings iOS = IOSInitializationSettings();
final MacOSInitializationSettings macOS = MacOSInitializationSettings();
final InitializationSettings initializationSettings =
InitializationSettings(android: android, iOS: iOS, macOS: macOS);
flip.initialize(initializationSettings,
onSelectNotification: onSelectNotification);
/// listen when the app is open
FirebaseMessaging.onMessage.listen((RemoteMessage message) {
RemoteNotification notification = message.notification;
AndroidNotification android = message.notification?.android;
// If `onMessage` is triggered with a notification, construct our own
// local notification to show to users using the created channel.
if (notification != null && android != null) {
flip.show(
notification.hashCode,
notification.title,
notification.body,
NotificationDetails(
android: AndroidNotificationDetails(
channel.id, channel.name, channel.description,
icon: android?.smallIcon,
// other properties...
priority: Priority.high),
));
}
});
}
...