Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/variables/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 从通知恢复活动_Java_Android_Android Activity_Notifications - Fatal编程技术网

Java 从通知恢复活动

Java 从通知恢复活动,java,android,android-activity,notifications,Java,Android,Android Activity,Notifications,我的应用程序的状态栏中有一个通知: Notification notification = new Notification(R.drawable.icon, null, System.currentTimeMillis()); Intent notificationIntent = new Intent(this.parent, MainActivity.class); PendingIntent contentIntent = PendingIntent.getAc

我的应用程序的状态栏中有一个通知:

    Notification notification = new Notification(R.drawable.icon, null, System.currentTimeMillis());

    Intent notificationIntent = new Intent(this.parent, MainActivity.class);
    PendingIntent contentIntent = PendingIntent.getActivity(this.parent, 0, notificationIntent, 0);

    ...

    notification.flags = Notification.FLAG_ONGOING_EVENT;        
    mNotificationManager.notify(NOTIFICATION_ID, notification);
问题在于,当您从应用程序中按home(主页)按钮(将其推到后台),然后按从状态栏访问的列表中的通知时,它将启动活动的新副本。我想做的就是恢复应用程序(比如当你长按home按钮并按下应用程序图标时)。有没有一种方法可以产生这样的意图?

我使用:

notificationIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_CLEAR_TOP);
notificationIntent.setAction(Intent.ACTION_MAIN);

不确定这些是您需要设置的值,但答案就在这些方法/标志中。

我通过在androidManifest.xml文件中将活动的
启动模式更改为
单任务
解决了这个问题

此属性的默认值为
standard
,允许运行任意数量的实例

“singleTask”和“singleInstance”活动只能开始一项任务。它们始终位于活动堆栈的根。此外,该设备一次只能保存一个活动实例-只有一个这样的任务。[……]

“singleTask”和“singleInstance”模式也仅在一个方面不同:“singleTask”活动允许其他活动成为其任务的一部分。它始终是其任务的根源,但其他活动(必须是“标准”和“单端”活动)可以启动到该任务中。另一方面,“单实例”活动不允许其他活动成为其任务的一部分。这是任务中唯一的活动。如果它启动了另一个活动,则该活动将被分配给另一个任务-就好像FLAG_activity_NEW_task在意图中一样

您可以在


我希望这有帮助

我刚刚找到了解决这个问题的方法:我创建了getPreviousIntent方法,并将其交给PendingEvent,仅此而已:

private Intent getPreviousIntent(Intent newIntent) {
    final ActivityManager am = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);
    final List<ActivityManager.RecentTaskInfo> recentTaskInfos = am.getRecentTasks(1024,0);
    String myPkgNm = getPackageName();

    if (!recentTaskInfos.isEmpty()) {
        ActivityManager.RecentTaskInfo recentTaskInfo;
        for (int i = 0; i < recentTaskInfos.size(); i++) {
            recentTaskInfo = recentTaskInfos.get(i);
            if (recentTaskInfo.baseIntent.getComponent().getPackageName().equals(myPkgNm)) {
                newIntent = recentTaskInfo.baseIntent;
                newIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
            }
        }
    }
    return newIntent;
}
private Intent getPreviousIntent(Intent newIntent){
最终ActivityManager am=(ActivityManager)getSystemService(Context.ACTIVITY_服务);
最终列表recentTaskInfos=am.getRecentTasks(1024,0);
字符串myPkgNm=getPackageName();
如果(!recentTaskInfos.isEmpty()){
ActivityManager.RecentTaskInfo RecentTaskInfo;
对于(int i=0;i
我遇到了类似的问题,正确的处理方法是使用以下标志:Intent.FLAG\u ACTIVITY\u CLEAR\u TOP和Intent.FLAG\u ACTIVITY\u SINGLE\u TOP

notificationIntent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_SINGLE_TOP);
根据文件,这将:

如果已设置,并且正在启动的活动已在当前任务中运行,则不会启动该活动的新实例,而是关闭其上的所有其他活动,并且此意图将作为新意图传递给(现在位于顶部的)旧活动

如果已设置,则如果活动已在历史堆栈顶部运行,则不会启动该活动


将此行添加到应用程序清单文件中的相应活动中

android:launchMode="singleTask"
例如:


我在设备之间有不一致的行为,有一些意图失去额外功能,MainActivity的OnNewIntent和onCreate方法都被调用

什么不起作用

舱单:

    <activity android:name=".MainActivity"
        android:launchMode="singleTask">
    <activity android:name=".MainActivity"
        android:launchMode="singleTask">
什么起作用了

舱单:

    <activity android:name=".MainActivity"
        android:launchMode="singleTask">
    <activity android:name=".MainActivity"
        android:launchMode="singleTask">

您可以模拟启动意图(就像用户单击应用程序图标启动它一样):

这样,您就不必在清单中将应用程序标记为“singleTask”或“singleInstance”(这会产生其他问题)。因此,这应该是正确的解决方案


注意,但是,由于据称存在安卓漏洞,上述解决方案可能无法直接用于您。可以找到有关android错误和解决方法的讨论。

谢谢,这是一个了不起的问题。另外,请查看
android:launchMode=“singleTop”
,这可能也适用,并列在“正常启动”下。使用(singleTask、singleTop、singleInstance)中的任何一个,我发现活动任务堆栈已损坏,任务堆栈清除了所有其他活动使用特殊启动模式“singleTask”和“singleInstance”只应在极少数情况下使用,例如在构建主屏幕替换时。除非您的应用程序非常简单并且只包含一个
活动
,否则此解决方案可能会导致比它所解决的问题更多的问题。事实上,这是一个公认的答案,并且有30张赞成票,这让人难以置信:-(在我的例子中,解决方案是“singleInstance”。非常感谢!我尝试了上述方法,但没有效果,你能给出一个完整的通知示例吗?@Enebattal抱歉,我不再有可用的代码(我的应用程序采用了不同的方式)意向标志这件事真是一团糟。我想我还没有真正弄明白。我们怎么才能把它交给待定的意向呢?你能不能在这里分享代码?问题已经解决了。这是一大堆花哨的代码来做一件简单的事。你可以请求一个“启动意向”对于您的应用程序,请改为使用
PackageManager
,它提供相同的功能。请检查:使用特殊启动模式“singleTask”和“singleInstance”只能在非常罕见的情况下使用,例如当您构建主屏幕替换时。此解决方案可能会导致比它解决的问题更多的问题,除非您的应用程序非常简单并且只包含一个活动。此解决方案在Android 10上正常工作,而classic
SINGLE_TOP | CLEAR_TOP
启动重复
活动在为已有的onNewIntent调用
onNewIntent
后立即调用。
    PackageManager pm = getPackageManager();
    Intent launchIntent = m.getLaunchIntentForPackage(BuildConfig.APPLICATION_ID);
    launchIntent.putExtra("TEST", 2);
val launchIntent = context.packageManager.getLaunchIntentForPackage(context.packageName)

val contentIntent = PendingIntent.getActivity(context, 0, launchIntent, 0)