【问题标题】:Error: Failed to handle method call on local notification错误:无法处理本地通知上的方法调用
【发布时间】:2021-10-17 18:30:48
【问题描述】:

我正在使用本地通知。我想在 onMessage 中显示带有本地通知的通知,但我不断收到此错误:Failed to handle method call。在谷歌搜索答案后,请继续参考应用图标。

将应用程序图标更改为我抽屉中的名称后,我仍然收到错误。

我已经尝试过 @mipmap/ic_launcher 和 mipmap/ic_launcher 两者。 app_icon 是我命名的 playstore-icon.png 的名称

这是我的代码

class MyProfile extends StatefulWidget {
  @override
  _MyProfileState createState() => _MyProfileState();
}

class _MyProfileState extends State<MyProfile> {
  Map dataset;
  bool state = false;
  String selected = "first";

  FirebaseMessaging messaging = FirebaseMessaging.instance;

  final FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
      FlutterLocalNotificationsPlugin();

  AndroidNotificationChannel channel = AndroidNotificationChannel(
    'faithmeetslove', // id
    'High Importance Notifications', // title
    'This channel is used for important notifications.', // description
    importance: Importance.max,
  );

  Future<void> saveTokenToDatabase(String token) async {
    String userId = auth.currentUser.uid;
    await firestore.collection("users").doc(userId).update({
      'tokens': token,
    });
  }

  @override
  void initState() {
    super.initState();
    final InitializationSettings initializationSettings =
        InitializationSettings(
            android: AndroidInitializationSettings("playstore-icon.png"),
            iOS: IOSInitializationSettings(
              requestAlertPermission: false,
              requestBadgePermission: false,
              requestSoundPermission: false,
            ));
    getData();
    getTokens();
    getUserLocation();
  }

  getTokens() async {
    String token = await FirebaseMessaging.instance.getToken();
    await saveTokenToDatabase(token);
    FirebaseMessaging.instance.onTokenRefresh.listen(saveTokenToDatabase);
    if (Platform.isIOS) {
      FirebaseMessaging.instance.requestPermission();
    }
    NotificationSettings settings = await messaging.requestPermission(
      alert: true,
      announcement: false,
      badge: true,
      carPlay: false,
      criticalAlert: false,
      provisional: false,
      sound: true,
    );

    FirebaseMessaging.instance
        .getInitialMessage()
        .then((RemoteMessage message) {
      if (message != null) {
        Navigator.pushNamed(context, message.data['view']);
      }
    });
    print('User granted permission: ${settings.authorizationStatus}');
    FirebaseMessaging.onMessage.listen((RemoteMessage message) {
      print('Message data: ${message.data['key']}');

      //message.data
      if (message.notification != null) {
        print('Message also contained a notification: ${message.notification}');
      }
      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) {
        flutterLocalNotificationsPlugin.show(
            notification.hashCode,
            notification.title,
            notification.body,
            NotificationDetails(
              android: AndroidNotificationDetails(
                channel.id,
                channel.name,
                channel.description,
                icon: android?.smallIcon,
                // other properties...
              ),
            ));
      }
    });
    FirebaseMessaging.onMessageOpenedApp.listen((RemoteMessage message) {
      debugPrint('A new onMessageOpenedApp event was published!');
      // _navigator.currentState.pushNamed('/' + message.data['view']);
    });
  }

  getData() async {
    setState(() {
      state = true;
    });
    final datastore =
        await firestore.collection('users').doc(auth.currentUser.uid).get();
    if (mounted) {
      setState(() {
        setState(() {
          dataset = datastore.data();
          state = false;
        });
      });
    }
  }

【问题讨论】:

  • 你是否在AndroidManifest.xml中设置了Firebase Messaging的default_notification_icondefault_notification_channel_id
  • 是的.. 我现在会更新
  • 这是我添加的@PeterKoltai
  • 你的图标有这样的东西吗? &lt;meta-data android:name="com.google.firebase.messaging.default_notification_icon" android:resource="@drawable/ic_notification"/&gt;?
  • @PeterKoltai 我已经更新了问题

标签: flutter dart push-notification


【解决方案1】:

我认为您缺少一些初始化步骤,例如我没有看到您在 FlutterLocalNotificationsPlugin 上调用 initalize 的位置。我写在这里的方式是结合远程和本地消息传递,希望对您有所帮助。

首先,确保您已将这些行添加到 AndroidManifest.xml 以及您想要的图标:

<meta-data
  android:name="com.google.firebase.messaging.default_notification_icon"
  android:resource="@drawable/ic_notification"/>
<meta-data
  android:name="com.google.firebase.messaging.default_notification_channel_id"
  android:value="mychannel" /> 

然后完成初始化步骤,像这样,我从initState调用它:

void initNotifications() async {
  FirebaseMessaging messaging = FirebaseMessaging.instance;

  NotificationSettings notificationSettings =
      await messaging.requestPermission(
    alert: true,
    announcement: false,
    badge: true,
    carPlay: false,
    criticalAlert: false,
    provisional: false,
    sound: true,
  );

  if (notificationSettings.authorizationStatus ==
      AuthorizationStatus.authorized) {
    await FirebaseMessaging.instance
        .setForegroundNotificationPresentationOptions(
      alert: true,
      badge: true,
      sound: true,
    );

    const AndroidNotificationChannel channel = AndroidNotificationChannel(
      'mychannel', 
      'title',
      'description',
      importance: Importance.max,
    );

    final FlutterLocalNotificationsPlugin flutterLocalNotificationsPlugin =
        FlutterLocalNotificationsPlugin();

    flutterLocalNotificationsPlugin.initialize(
        InitializationSettings(
            android:
                AndroidInitializationSettings('@drawable/ic_notification'),
            iOS: IOSInitializationSettings()),
        onSelectNotification: _onSelectNotification);

    await flutterLocalNotificationsPlugin
        .resolvePlatformSpecificImplementation<
            AndroidFlutterLocalNotificationsPlugin>()
        ?.createNotificationChannel(channel);

    FirebaseMessaging.onMessage.listen((RemoteMessage message) {
      if (message.notification == null) {
        return;
      }

      RemoteNotification notification = message.notification!;

      if (notification.android != null) {
        flutterLocalNotificationsPlugin.show(
            notification.hashCode,
            notification.title,
            notification.body,
            NotificationDetails(
                android: AndroidNotificationDetails(
              channel.id,
              channel.name,
              channel.description,
            )));
      }
    });


    FirebaseMessaging.onMessageOpenedApp.listen((RemoteMessage message) {
      // do something with message
    });

    messaging.getInitialMessage().then((RemoteMessage? message) {

      if (message == null) {
        return;
      }

      // do something with message

    });
  }
}

在上面的代码中,_onSelectNotification 是一个在应用程序处于活动状态时用户推送通知时运行的函数,我认为只在 Android 上。这个函数看起来像:

Future _onSelectNotification(String? payload) {
   // do something with payload
}

【讨论】:

  • @drawable/ic_notification' 我在这里很困惑。我应该将我的图标添加到可绘制文件夹中吗?因为图标在 res 文件夹中
  • 请检查问题中的图片?我的图标是 playstore-icon.png
  • 我收到错误:失败:构建失败并出现异常。 * 出了什么问题:任务 ':app:processDebugResources' 执行失败。 > 执行 com.android.build.gradle.internal.tasks.Workers$ActionFacade 时发生故障 > Android 资源链接失败 /Users/mac/Documents/FaithMeetsLove-App-main/build/app/intermediates/packaged_manifests/debug/AndroidManifest .xml:69:AAPT:错误:找不到资源 drawable/playstore-icon(又名 com.FaithMeetsLove.FaithMeetsLove:drawable/playstore-icon)。
  • 您需要不同大小的图标,并将它们放入drawable-hdpi等文件夹,以便Android找到它。查看接受的答案here,并查看此icon generator
  • 是的...谢谢..你能帮我解决一下安卓和ios推送通知有效负载吗..
猜你喜欢
  • 2020-03-31
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-09-16
  • 2020-09-04
  • 1970-01-01
相关资源
最近更新 更多