当前位置: 首页 > 知识库问答 >
问题:

Firebase -当用户单击通知时,活动重新启动

桑宇
2023-03-14

我正在编写一个使用fire base来实现通知的应用程序。在我的Mainactive中,我有一个带有一些url的WebView,但问题是当用户单击通知时,我想在WebView中使用不同的url打开MainActiviy。我读了很多,我在意图中添加了一个捆绑包(在单击通知时打开Mainactive),它会生成所需的url。但是当我单击通知时,Mainactive会重新启动,我的意思是,它不会转到onNewIntent,而是在创建上运行。这就是我实现它的方式:

private void sendNotification(String messageTitle, String messageBody, String url){

    Intent intent = new Intent(this, MainActivity.class);
    intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);

    //This adds the url to the intent
    if(!url.equals("")){
        Bundle bundle = new Bundle();
        bundle.putString("url", url);
        intent.putExtras(bundle);
    }

    PendingIntent pendingIntent = PendingIntent.getActivity(this, 0,intent, PendingIntent.FLAG_ONE_SHOT);

    String channelId = getString(R.string.default_notification_channel_id);

    NotificationCompat.Builder notificationBuilder = new NotificationCompat
            .Builder(this, channelId)
            .setContentTitle(messageTitle)
            .setContentText(messageBody)
            .setPriority(NotificationCompat.PRIORITY_DEFAULT)
            .setAutoCancel(true)
            .setSmallIcon(R.drawable.ic_launcher_background)
            .setContentIntent(pendingIntent);

    NotificationManager notificationManager = (NotificationManager) getSystemService(Context.NOTIFICATION_SERVICE);

    if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.O){
        NotificationChannel channel = new NotificationChannel(channelId,
                "Notification channel",
                NotificationManager.IMPORTANCE_DEFAULT);
        notificationManager.createNotificationChannel(channel);
    }

    notificationManager.notify(0, notificationBuilder.build());

}

onNewIntent我有这个:

Bundle bundle = intent.getExtras();
        if (bundle != null) {
            String url = bundle.getString("url");
            mWebView.loadUrl(url);
        }

但是,当单击通知时,活动只是重新启动,因此它不会在NewIntent上运行,并且日志会给我以下错误:

02-08 12:51:12.140 19056-19056/com.example.android.app E/ActivityThread: Activity com.example.android.app.MainActivity has leaked IntentReceiver com.example.android.app.MainActivity$1@d7818db that was originally registered here. Are you missing a call to unregisterReceiver()?
android.app.IntentReceiverLeaked: Activity com.example.android.app.MainActivity has leaked IntentReceiver com.example.android.app.MainActivity$1@d7818db that was originally registered here. Are you missing a call to unregisterReceiver()?
    at android.app.LoadedApk$ReceiverDispatcher.<init>(LoadedApk.java:999)
    at android.app.LoadedApk.getReceiverDispatcher(LoadedApk.java:795)
    at android.app.ContextImpl.registerReceiverInternal(ContextImpl.java:1329)
    at android.app.ContextImpl.registerReceiver(ContextImpl.java:1309)
    at android.app.ContextImpl.registerReceiver(ContextImpl.java:1303)
    at android.content.ContextWrapper.registerReceiver(ContextWrapper.java:554)
    at com.example.android.app.MainActivity.onCreate(MainActivity.java:264)
    at android.app.Activity.performCreate(Activity.java:6367)
    at android.app.Instrumentation.callActivityOnCreate(Instrumentation.java:1110)
    at android.app.ActivityThread.performLaunchActivity(ActivityThread.java:2404)
    at android.app.ActivityThread.handleLaunchActivity(ActivityThread.java:2511)
    at android.app.ActivityThread.access$900(ActivityThread.java:165)
    at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1375)
    at android.os.Handler.dispatchMessage(Handler.java:102)
    at android.os.Looper.loop(Looper.java:150)
    at android.app.ActivityThread.main(ActivityThread.java:5621)
    at java.lang.reflect.Method.invoke(Native Method)
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:794)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:684)

我在stackoverflow上读到一个类似的问题是取消注册BroadCastRecencer以修复此错误,但我有点迷失了如何做到这一点。

我已尝试将发送通知的意图更改为

Intent intent = new Intent("android.intent.action.MAIN");

但在这种情况下,当用户单击通知时,它不会执行任何操作。

有人知道如何修复它,以便用户单击时加载url吗?提前谢谢你

共有2个答案

秦俊豪
2023-03-14

创建一个类似这样的方法

private PendingIntent retrievePlaybackAction(final String action) {
    Intent intent = new Intent(action);
    return PendingIntent.getBroadcast(this, 0, intent, PendingIntent.FLAG_UPDATE_CURRENT);
}

现在像这样添加您的意图

builder.setContentIntent(retrievePlaybackAction("OPEN_MAIN")); //change action text as you want

创建一个简单的类NotificationRecencer,我想你已经创建了,现在从您发送通知的地方创建此类的对象

private NotificationReceiver notificationReceiver;

onCreate()中注册您的接收器

notificationReceiver = new NotificationReceiver();

IntentFilter intentFilterNextClick = new IntentFilter("OPEN_MAIN");

registerReceiver(notificationReceiver, intentFilterNextClick); 
//can create exception, better to surround with try catch

在<code>onDestroy()中

unregisterReceiver(notificationReceiver); 
//can create exception, better to surround with try catch

要打开或执行某些操作,请在接收器中添加此内容

@Override
public void onReceive(Context context, Intent intent) {
    Log.e(TAG, "onReceive: received " + intent.getAction());

    String action = intent.getAction();

    //no need to create switch you can also use if
    switch (action) {
        case "OPEN_MAIN":
            openMain();
            break;
    }

}

//here is openMain();
private void openMain(Context context) {
    Intent openMainIntent = new Intent(context, MainActivity.class);
    openMainIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); //this flag is important
    context.startActivity(openMainIntent);
}

如果应用程序最小化或关闭,这也将起作用

希望这会有所帮助!

请询问您是否需要更多帮助!

龚志
2023-03-14

从Android文档中可以看出:

如果它已声明其启动模式为“多”(默认),并且您没有以相同的意图设置< code > FLAG _ ACTIVITY _ SINGLE _ TOP ,则它将被完成并重新创建。对于所有其他启动模式,或者如果设置了< code > FLAG _ ACTIVITY _ SINGLE _ TOP ,则此意图将被传递给当前实例的onNewIntent()。

因此,在创建新意图时设置FLAG_ACTIVITY_SINGLE_TOP标志应该解决并运行onNewIntent()方法,而不是重新创建应用程序

 类似资料:
  • 现在,我需要服务器向这个活动传递一个额外的参数,一个,这样我就可以显示与通知相关联的所需细节。就像电子邮件应用程序一样,当我们点击通知时会打开指定电子邮件的详细信息。 我怎么能这么做?

  • 问题内容: 我试图将我在教程中找到的一些代码转换为自己使用。最初,当用户单击我的应用程序生成的通知时,该代码启动了系统联系人列表。我正在尝试自己启动一个,而不是启动联系人列表,但是它不起作用。更具体地说,什么也没有发生。没有错误,我也不会加载。单击后,通知窗口消失,原始窗口仍然可见。 这是我的代码: 这是我在文件中的条目… 这是我要启动的… 问题答案: 我解决了这个问题。我忘记在清单文件的活动声明

  • 我目前遇到以下问题: 我已经实现了自定义FirebaseMessagingService,并且覆盖了方法onMessageReceived()。此外,当应用程序在后台时,我从getExtras()获取捆绑包 我需要通知内容,以便在db中本地保存 发生了什么: 当应用程序处于后台时,从Firebase控制台发送3个通知 创建了3个状态栏通知 单击其中一个- 你能帮忙吗? 启动器活动代码: 自定义Fi

  • 我正在写一个UWP应用程序,我有一个ScheduledToastNotification在应用程序挂起时添加到日程中(例如,像一个提醒)。但是,如果我关闭了app,通知准时出现,但是当我点击通知时(没有按钮,一般只是在通知上),app没有正确启动,停在闪屏处。 如何使应用程序正确地重新启动? 多谢了。

  • 我有一个问题,恢复活动的通知点击。我有一个应用程序可以播放一首歌一段时间。这个想法是,当你播放一首歌,并按下Home键时,应该会有一个通知,让你返回到可以停止这首歌的应用程序。 以下是我发出通知的方式: 这是我的舱单:

  • 我有两个活动Main activity和ReceivedMessageActivity。以及一个后台服务,用于从中获取上下文并传递给SMSReceiver,SMSReceiver扩展BroadcastReceiver以接收sms。当收到短信时,SMSReceiver会创建通知。我希望当我点击通知时,如果应用程序未运行ReceivedMessageActivity,则打开该通知;如果应用程序正在运行