通知打开活动,按后退按钮,防止打开后退堆栈活动?

发布于 2024-12-07 17:55:59 字数 3457 浏览 4 评论 0原文

这看起来与我之前的问题非常相似因为这是某种后续行动。我对给出的唯一解决方案不太满意;另外,解决方案是针对与此略有不同的问题。那么让我尝试再次解释一下这个问题...

  1. 启动时会创建一个通知(使用 BroadcastReceiver)。
  2. 我的应用程序主活动已打开并按下主页按钮(该活动将被发送到后堆栈)。
  3. 我拉下状态栏并按下之前在启动时创建的通知。
  4. 这将启动一些与主要活动不同的活动。
  5. 我按下后退按钮,就会显示主要活动。

这与我之前的问题没有太大不同......问题是,“主要活动”只是一个例子。我可以打开应用程序的主要活动,然后通过菜单选项打开“关于”活动并按下主页按钮。返回堆栈现在将是 MainActivity » AboutActivity。这意味着,当在“某个活动”(通过按通知启动)中按下后退按钮时,我们将被带到返回堆栈的顶部,即 about 活动。

基本上想要的是防止当我在“某些活动”中按后退按钮时打开任何其他活动(同样,通过按通知启动)。我希望准确地到达我所在的位置,这可能是桌面或其他应用程序的活动,但不是我的应用程序的 MainActivityAboutAcitivity 因为那不是我所在的位置,那些位于后堆栈中,在后台“睡觉”。

我已经想出了一个解决方案,但我认为它不是很优雅,我一直在寻找更优雅的东西...如果您有任何其他建议,请告诉我。

无论如何,这是我提出的解决方案:

// I use this class for public static (or public static final) members and
// methods

public final class AppHelper {
    public static final String KEY_RESUME_FROM_NOTIFICATION = "resumeFromNotification";

    private static boolean sResumeFromNotification = false;

    public static boolean getResumeFromNotification() {
        return sResumeFromNotification;
    }

    public static void setResumeFromNotification(boolean resumeFromNotification) {
        sResumeFromNotification = resumeFromNotification;
    }
}

public class MainActivity extends ListActivity {

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        (...)
    }

    @Override
    protected void onResume() {
        super.onResume();

        if(AppHelper.getResumeFromNotification()) {
            AppHelper.setResumeFromNotification(false);
            moveTaskToBack(true);
        }
    }

}

public class AboutActivity extends Activity {

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        (...)
    }

    @Override
    protected void onResume() {
        super.onResume();

        if(AppHelper.getResumeFromNotification()) {
            AppHelper.setResumeFromNotification(false);
            moveTaskToBack(true);
        }
    }

}

public class SomeActivity extends Activity {

    // This will be called when the notification is pressed and the activity is
    // not opened yet

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        (...)

        extractIntentExtras(intent);
    }

    // This will be called if the activity is already opened and the
    // notification is pressed

    @Override
    protected void onNewIntent(Intent intent) {
        extractIntentExtras(intent);
        super.onNewIntent(intent);
    }

    private void extractIntentExtras(Intent intent) {
        Bundle bundleExtras = intent.getExtras();

        if(bundleExtras != null) {
            // These intent extras are set on the Intent that starts this activity
            // when the notification is pressed

            AppHelper.setResumeFromNotification(bundleExtras.getBoolean(
                AppHelper.KEY_RESUME_FROM_NOTIFICATION));

            mRowId = bundleExtras.getLong(AgendaNotesAdapter.KEY_ROW_ID);
            populateNoteUpdateFields();
        }
    }

}

我不知道,但这个解决方案对我来说看起来不太优雅(但它按我的预期工作),我正在寻找替代方案或对我提出的解决方案提出强烈意见一个可以接受的、好的解决方案。想法?

This looks very similar to my previous question because it's some sort of follow up. I was not very happy with the only solution given; also, the solution was for a problem slightly different from this one. So let me try to explain the problem again...

  1. A notification is created at boot (with a BroadcastReceiver).
  2. My app main activity is opened and the home button is pressed (the activity will be sent to the back stack).
  3. I pull down the status bar and press on the notification previously created at boot.
  4. That will start some activity, different from the main one.
  5. I press the back button and the main activity is displayed.

This is not very different from my previous question... The thing is, "main activity" was just an example. I could have opened the app main activity and then opened the about activity through a menu option and pressed the home button. The back stack would now be MainActivity » AboutActivity. Which means that when the back button is pressed while in "some activity" (started by pressing the notification), we would be brought to the top of the back stack, that is, the about activity.

What basically want is to prevent any other activity to be opened when I press the back button while in "some activity" (again, started by pressing the notification). I want to be brought exactly where I was, that could be the desktop or some other app's activity, but not my app's MainActivity nor AboutAcitivity cause that's not where I was, those were in the back stack, "sleeping" in the background.

I have come up with a solution, but I don't think it's very elegant and I was looking for something more, well, elegant... If you have any other suggestion, please, let me know.

Anyway, this is my proposed solution:

// I use this class for public static (or public static final) members and
// methods

public final class AppHelper {
    public static final String KEY_RESUME_FROM_NOTIFICATION = "resumeFromNotification";

    private static boolean sResumeFromNotification = false;

    public static boolean getResumeFromNotification() {
        return sResumeFromNotification;
    }

    public static void setResumeFromNotification(boolean resumeFromNotification) {
        sResumeFromNotification = resumeFromNotification;
    }
}

public class MainActivity extends ListActivity {

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        (...)
    }

    @Override
    protected void onResume() {
        super.onResume();

        if(AppHelper.getResumeFromNotification()) {
            AppHelper.setResumeFromNotification(false);
            moveTaskToBack(true);
        }
    }

}

public class AboutActivity extends Activity {

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        (...)
    }

    @Override
    protected void onResume() {
        super.onResume();

        if(AppHelper.getResumeFromNotification()) {
            AppHelper.setResumeFromNotification(false);
            moveTaskToBack(true);
        }
    }

}

public class SomeActivity extends Activity {

    // This will be called when the notification is pressed and the activity is
    // not opened yet

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        (...)

        extractIntentExtras(intent);
    }

    // This will be called if the activity is already opened and the
    // notification is pressed

    @Override
    protected void onNewIntent(Intent intent) {
        extractIntentExtras(intent);
        super.onNewIntent(intent);
    }

    private void extractIntentExtras(Intent intent) {
        Bundle bundleExtras = intent.getExtras();

        if(bundleExtras != null) {
            // These intent extras are set on the Intent that starts this activity
            // when the notification is pressed

            AppHelper.setResumeFromNotification(bundleExtras.getBoolean(
                AppHelper.KEY_RESUME_FROM_NOTIFICATION));

            mRowId = bundleExtras.getLong(AgendaNotesAdapter.KEY_ROW_ID);
            populateNoteUpdateFields();
        }
    }

}

I don't know, but this solution doesn't look very elegant to me (but it works as I expect it) and I'm looking for alternatives or for strong opinions on my proposed solution as an acceptable and good solution. Thoughts?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(3

无言温柔 2024-12-14 17:55:59

经过更多阅读后,也许这就是您需要的标志组合:

Intent intent = new Intent(mContext, SomeActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_MULTIPLE_TASK);
startActivity(intent);

我认为这应该强制您的 SomeActivity 类在全新的任务中启动。

After doing some more reading perhaps this is the combination of flags you need:

Intent intent = new Intent(mContext, SomeActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK | Intent.FLAG_ACTIVITY_MULTIPLE_TASK);
startActivity(intent);

I think that should force your SomeActivity class to be launched in a completely new task.

旧梦荧光笔 2024-12-14 17:55:59

从通知启动 Activity 时,您可以控制如何将要打开的 Activity 放入返回堆栈,以及它与 Intent 标志关联的任务。您可以尝试以下操作:

Intent intent = new Intent(mContext, SomeActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);

如果这不起作用,请尝试设置一些 其他标志,直到获得所需的行为。

When launching the Activity from the notification, you can control how the Activity you are about to open is put on the back stack, and what task it's associated with with Intent flags. You can try something like:

Intent intent = new Intent(mContext, SomeActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(intent);

If that doesn't work, try setting a few of the other flags until you get the desired behavior.

饮惑 2024-12-14 17:55:59

您是否希望您的 MainActivity 留在历史中?如果不是,那么我简单粗暴的解决方案是在 MainActivity 暂停时完成它。
(在您的 MainActivity 中调用此方法)

@Override
public void onPause() {
    finish();
}

这将确保您的 MainActivity 在您离开它时从历史记录中删除,并且在按下后退按钮时永远不会出现。
这也可以用于 AboutActivity。

Do you ever want your MainActivity to stay in history? If not then my simple, crude solution is to finish the MainActivity when it is paused.
(Call this in your MainActivity)

@Override
public void onPause() {
    finish();
}

This will ensure that your MainActivity is removed from history when you navigate away from it, and will never appear when the back button is pressed.
This could be used for AboutActivity as well.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文