【问题标题】:Finish an activity from another activity从另一个活动完成一个活动
【发布时间】:2012-04-30 05:59:38
【问题描述】:

我想从另一项活动中完成一项活动,例如:

在 Activity [A] 中,单击按钮时,我正在调用 Activity [B] 而不完成 Activity [A]。

现在在 Activity [B] 中,有两个按钮,NewModify。当用户点击修改然后从堆栈中弹出一个活动 [A] 并勾选所有选项..

但是当用户从 Activity [B] 中单击 New 按钮时,我将不得不从堆栈中完成 Activity [A] 并将该 Activity [A] 重新加载到堆栈中。

我正在尝试,但我无法从堆栈中完成 Activity [A]... 我该怎么做?

我将代码用作:

来自活动 [A]:

Intent GotoB = new Intent(A.this,B.class);
startActivityForResult(GotoB,1);

同一活动中的另一种方法

public void onActivityResult(int requestCode, int resultCode, Intent intent) {

    if (requestCode == 1)
    {
        if (resultCode == 1) {
            Intent i = getIntent();
            overridePendingTransition(0, 0);
            i.addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION);
            finish();

            overridePendingTransition(0, 0);
            startActivity(i);
        }
    }
}

在 Activity [B] 中,点击按钮:

setResult(1);
finish();

【问题讨论】:

标签: android android-intent android-activity


【解决方案1】:
  1. 在清单文件中创建您的活动 A:launchMode = "singleInstance"

  2. 当用户点击new时,执行FirstActivity.fa.finish();并调用新的Intent。

  3. 当用户点击修改时,调用新的Intent或者干脆完成Activity B。

第一路

在你的第一个活动中,像这样声明一个Activity object

public static Activity fa;
onCreate()
{
    fa = this;
}

现在在另一个 Activity 中使用该对象来完成这样的第一个活动,

onCreate()
{
    FirstActivity.fa.finish();
}

第二种方式

在调用您的活动FirstActivity 时,您希望在继续前进时立即完成, 您可以在调用FirstActivity时添加标志

intent.addFlags(Intent.FLAG_ACTIVITY_NO_HISTORY);

但是使用这个标志,即使你不希望它完成,活动也会完成。有时onBack,如果你想显示FirstActivity,你将不得不使用intent来调用它。

【讨论】:

  • 您持有对活动的静态引用。除非您从某个地方手动清除它,否则这永远不会消失 -> 您正在创建内存泄漏!
  • 好吧,你有我的 +1 开箱即用的想法:D,我只想改为 singleTop。但是,在做类似的事情时,它仍然不是我的首选。通过清理代码,我的意思是一种摆脱静态引用的方法,因此没有内存泄漏,但这取决于应用程序结构。
  • 请不要使用第一种解决方案,这是完全错误的。在创建僵尸对象时,您正在以一种非常骇人听闻的方式绕过 Android 框架。使用广播接收器。
  • 很棒的解决方案。对于我从活动 A->B->C 和 C 的 onBackPressed 开始的问题非常有效,我正在启动 B 的新实例。但是如果我在 B 的新实例上执行 onBackPressed,它曾经转到 B 的旧实例而不是 A 的旧实例(我想要的)。所以我在 C 的 onBackPressed 中遵循了你的第一个方法,它给了我想要的行为 :) 非常感谢 :)
  • @Darko关于你在第一种方式提到的泄漏问题,如果on_Destroy我们使fa = null,那么垃圾收集器不会将它从ram中删除吗?
【解决方案2】:

你可以这样做,但我认为你不应该打破正常的活动流程。如果你想完成你的活动,那么你可以简单地从你的活动 B 发送一个广播到活动 A。

在开始你的活动 B 之前创建一个广播接收器:

BroadcastReceiver broadcastReceiver = new BroadcastReceiver() {

    @Override
    public void onReceive(Context arg0, Intent intent) {
        String action = intent.getAction();
        if (action.equals("finish_activity")) {
            finish();
            // DO WHATEVER YOU WANT.
        }
    }
};
registerReceiver(broadcastReceiver, new IntentFilter("finish_activity"));

当你想从 B 完成活动 A 时,从活动 B 向活动 A 发送广播

Intent intent = new Intent("finish_activity");
sendBroadcast(intent);

我希望它对你有用......

【讨论】:

【解决方案3】:

这是一个相当标准的沟通问题。一种方法是在 Activity A 中使用 ResultReceiver:

Intent GotoB=new Intent(A.this,B.class);
GotoB.putExtra("finisher", new ResultReceiver(null) {
    @Override
    protected void onReceiveResult(int resultCode, Bundle resultData) {
        A.this.finish();
    }
});
startActivityForResult(GotoB,1);

然后在活动 B 中,您可以像这样按需完成它:

((ResultReceiver)getIntent().getExtra("finisher")).send(1, new Bundle());

尝试类似的方法。

【讨论】:

  • +1 只是 , ((ResultReceiver)getIntent().getParcelableExtra("finisher")).send(1, new Bundle());
【解决方案4】:

您可以在自己的情况下使用一种方法。

Step1:从Activity A启动Activity B

startActivity(new Intent(A.this, B.class));

Step2:如果用户点击修改按钮启动Activity A,使用FLAG_ACTIVITY_CLEAR_TOP。另外,额外传递flag。

Intent i = new Intent(B.this, A.class);
i.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
i.putExtra("flag", "modify");
startActivity(i);
finish();

步骤 3:如果用户单击添加按钮,则使用 FLAG_ACTIVITY_CLEAR_TOP 启动 Activity A。此外,额外传递标志。 FLAG_ACTIVITY_CLEAR_TOP 将清除所有打开到目标的活动,如果目标活动中没有定义启动模式,则重新启动

Intent i = new Intent(B.this, A.class);
i.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
i.putExtra("flag", "add");
startActivity(i);
finish();

Step4:现在Activity A的onCreate()方法,需要取回那个flag。

String flag = getIntent().getStringExtra("flag");
if(flag.equals("add")) {
    //Write a code for add
}else {
    //Write a code for modifying
}

【讨论】:

    【解决方案5】:

    使用请求代码开始您的活动:

    StartActivityForResult(intent,1234);
    

    你可以从任何其他活动中关闭它:

    finishActivity(1234);
    

    【讨论】:

    • 用什么语言??
    【解决方案6】:

    my answer to Stack Overflow question Finish All previous activities

    您需要添加Intent.FLAG_CLEAR_TOP。此标志确保堆栈中目标活动之上的所有活动都已完成并显示。

    您需要的另一件事是SINGLE_TOP 标志。如果堆栈中已经创建了一个活动,则使用这个可以防止 Android 创建一个新活动。

    请注意,如果 Activity 已经创建,带有这些标志的 Intent 将在目标 Activity 中名为 onNewIntent(intent) 的方法中传递(您需要重载它来处理它)。

    然后在onNewIntent 中,您有一个称为restart 的方法或将调用finish() 并向自身发起新意图的方法,或者有一个将设置新数据的repopulate() 方法。我更喜欢第二种方法,它更便宜,你总是可以提取 onCreate 逻辑到一个单独的方法中,您可以调用它来进行填充。

    【讨论】:

      【解决方案7】:

      我刚刚应用了 Nepster 的解决方案,效果很好。有一个小的修改可以从 Fragment 运行它。

      到你的片段

      // sending intent to onNewIntent() of MainActivity
      Intent intent = new Intent(getActivity(), MainActivity.class);
      intent.putExtra("transparent_nav_changed", true);
      intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
      startActivity(intent);
      

      对于您想要重新启动的 Activity 的 OnNewIntent()。

      // recreate activity when transparent_nav was just changed
      if (getIntent().getBooleanExtra("transparent_nav_changed", false)) {
          finish(); // finish and create a new Instance
          Intent restarter = new Intent(MainActivity.this, MainActivity.class);
          startActivity(restarter);
      }
      

      【讨论】:

        【解决方案8】:

        我认为我有最简单的方法...在 B 中按 new ..

        Intent intent = new Intent(B.this, A.class);
        intent.putExtra("NewClicked", true);
         intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
        startActivity(intent);
        

        在 A 中得到它

          if (getIntent().getBooleanExtra("NewClicked", false)) {
                finish();// finish yourself and make a create a new Instance of yours.
              Intent intent = new Intent(A.this,A.class);
              startActivity(intent);
            }
        

        【讨论】:

          【解决方案9】:

          我知道这是一个老问题,其中一些方法对我不起作用,所以对于任何展望未来或遇到麻烦的人来说,这对我有用

          我在该方法中覆盖了onPause 并调用了finish()

          【讨论】:

            【解决方案10】:

            首先调用startactivity(),然后使用finish()

            【讨论】:

              猜你喜欢
              • 2013-03-25
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 2013-01-31
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              相关资源
              最近更新 更多