如何关闭 Android 应用程序?

我想关闭我的应用程序,以便它不再在后台运行。

如何做到这一点? 这在 Android 平台上是一个好的实践吗?

如果我依赖于“返回”按钮,它关闭应用程序,但它留在后台。甚至还有一个叫做“任务杀手”的应用程序可以在后台杀死这些应用程序。

350761 次浏览

以下是微软对此事的看法:

Http://blogs.msdn.com/windowsmobile/archive/2006/10/05/the-emperor-has-no-close.aspx (我一直记得2006年那篇博文的标题,是不是很悲哀?我在谷歌上搜索“皇帝没有亲近”(lol)找到了这篇文章

简而言之:

如果系统需要更多的内存 应用程序在后台,它会 关闭应用程序。但是,如果系统 不需要更多的内存,应用程序会 待在内存里,准备好回来 下次用户需要的时候 它。

这个问题中的许多评论表明,Android 的行为方式大致相同,只有当 Android 需要他们正在使用的内存时,才会关闭一段时间没有使用过的应用程序。

由于这是一个标准特性,因此将行为更改为强制关闭将改变用户体验。许多用户已经习惯了对他们的 Android 应用程序的温和拒绝,所以当他们在执行完其他任务后想要重新打开一个应用程序时,他们可能会对应用程序的状态被重置或者需要更长时间才能打开感到相当沮丧。我会坚持标准的行为,因为这是预期的。

使用框架 API 是不可能的。进程何时删除或保留在内存中取决于操作系统(Android)。这是出于效率的考虑: 如果用户决定重新启动应用程序,那么应用程序就已经存在,而不需要将其加载到内存中。

所以不,是 不仅如此阻止了 这是不可能的这么做。

活动上调用 finish()方法会对当前活动产生预期的效果。

太好了!您当然可以关闭应用程序,使其不再在后台运行。就像其他人评论的那样,finish()是谷歌推荐的方式,并不意味着你的程序真的关闭了。

System.exit(0);

这将关闭您的应用程序,不让任何东西在后台运行。但是,要明智地使用它,不要打开文件、数据库句柄等等。这些东西通常会通过 finish()命令清理干净。

我个人非常讨厌在应用程序中选择 Exit 而它并没有真正退出。

Android 有一种机制,可以根据文档安全地关闭应用程序。在退出的最后一个 Activity (通常是在应用程序启动时首次出现的主 Activity)中,只需在 onDestroy ()方法中放置几行代码。对 RunFinalizersOnExit (true)的调用确保在应用程序退出时,所有对象都将被完成并收集垃圾。如果您愿意,也可以通过 Process.kilProcess (android.os. Process.myPid ())快速终止应用程序。最好的方法是将下面这样的方法放到一个 helper 类中,然后在需要关闭应用程序时调用它。例如,在根活动的销毁方法中(假设应用程序永远不会销毁这个活动) :

此外,Android 不会通知应用程序 键事件,所以当按下 键时,您不能关闭应用程序。Android 将 密钥事件保留给自己,这样开发人员就不能阻止用户离开他们的应用程序。然而,您可以通过在假设已经按下 键的助手类中将标志设置为 true 来确定是否按下了 键,然后在发生显示未按下 键的事件时将标志更改为 false,然后在活动的 OnStop ()方法中检查是否按下了 键。

不要忘记处理任何菜单和菜单启动的活动的 键。搜索密钥也是如此。下面是一些示例类来说明:

下面是根活动的一个例子,当应用程序被销毁时,根活动会杀死应用程序:

package android.example;


/**
* @author Danny Remington - MacroSolve
*/


public class HomeKey extends CustomActivity {


public void onDestroy() {
super.onDestroy();


/*
* Kill application when the root activity is killed.
*/
UIHelper.killApp(true);
}


}

下面是一个可以扩展的抽象活动,它可以处理所有扩展它的活动的 键:

package android.example;


/**
* @author Danny Remington - MacroSolve
*/


import android.app.Activity;
import android.view.Menu;
import android.view.MenuInflater;


/**
* Activity that includes custom behavior shared across the application. For
* example, bringing up a menu with the settings icon when the menu button is
* pressed by the user and then starting the settings activity when the user
* clicks on the settings icon.
*/
public abstract class CustomActivity extends Activity {
public void onStart() {
super.onStart();


/*
* Check if the app was just launched. If the app was just launched then
* assume that the HOME key will be pressed next unless a navigation
* event by the user or the app occurs. Otherwise the user or the app
* navigated to this activity so the HOME key was not pressed.
*/


UIHelper.checkJustLaunced();
}


public void finish() {
/*
* This can only invoked by the user or the app finishing the activity
* by navigating from the activity so the HOME key was not pressed.
*/
UIHelper.homeKeyPressed = false;
super.finish();
}


public void onStop() {
super.onStop();


/*
* Check if the HOME key was pressed. If the HOME key was pressed then
* the app will be killed. Otherwise the user or the app is navigating
* away from this activity so assume that the HOME key will be pressed
* next unless a navigation event by the user or the app occurs.
*/
UIHelper.checkHomeKeyPressed(true);
}


public boolean onCreateOptionsMenu(Menu menu) {
MenuInflater inflater = getMenuInflater();
inflater.inflate(R.menu.settings_menu, menu);


/*
* Assume that the HOME key will be pressed next unless a navigation
* event by the user or the app occurs.
*/
UIHelper.homeKeyPressed = true;


return true;
}


public boolean onSearchRequested() {
/*
* Disable the SEARCH key.
*/
return false;
}
}

下面是一个处理 键的菜单屏幕示例:

/**
* @author Danny Remington - MacroSolve
*/


package android.example;


import android.os.Bundle;
import android.preference.PreferenceActivity;


/**
* PreferenceActivity for the settings screen.
*
* @see PreferenceActivity
*
*/
public class SettingsScreen extends PreferenceActivity {
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
addPreferencesFromResource(R.layout.settings_screen);
}


public void onStart() {
super.onStart();


/*
* This can only invoked by the user or the app starting the activity by
* navigating to the activity so the HOME key was not pressed.
*/
UIHelper.homeKeyPressed = false;
}


public void finish() {
/*
* This can only invoked by the user or the app finishing the activity
* by navigating from the activity so the HOME key was not pressed.
*/
UIHelper.homeKeyPressed = false;
super.finish();
}


public void onStop() {
super.onStop();


/*
* Check if the HOME key was pressed. If the HOME key was pressed then
* the app will be killed either safely or quickly. Otherwise the user
* or the app is navigating away from the activity so assume that the
* HOME key will be pressed next unless a navigation event by the user
* or the app occurs.
*/
UIHelper.checkHomeKeyPressed(true);
}


public boolean onSearchRequested() {
/*
* Disable the SEARCH key.
*/
return false;
}


}

下面是一个 Helper 类的例子,它处理整个应用程序中的 键:

package android.example;


/**
* @author Danny Remington - MacroSolve
*
*/


/**
* Helper class to help handling of UI.
*/
public class UIHelper {
public static boolean homeKeyPressed;
private static boolean justLaunched = true;


/**
* Check if the app was just launched. If the app was just launched then
* assume that the HOME key will be pressed next unless a navigation event
* by the user or the app occurs. Otherwise the user or the app navigated to
* the activity so the HOME key was not pressed.
*/
public static void checkJustLaunced() {
if (justLaunched) {
homeKeyPressed = true;
justLaunched = false;
} else {
homeKeyPressed = false;
}
}


/**
* Check if the HOME key was pressed. If the HOME key was pressed then the
* app will be killed either safely or quickly. Otherwise the user or the
* app is navigating away from the activity so assume that the HOME key will
* be pressed next unless a navigation event by the user or the app occurs.
*
* @param killSafely
*            Primitive boolean which indicates whether the app should be
*            killed safely or quickly when the HOME key is pressed.
*
* @see {@link UIHelper.killApp}
*/
public static void checkHomeKeyPressed(boolean killSafely) {
if (homeKeyPressed) {
killApp(true);
} else {
homeKeyPressed = true;
}
}


/**
* Kill the app either safely or quickly. The app is killed safely by
* killing the virtual machine that the app runs in after finalizing all
* {@link Object}s created by the app. The app is killed quickly by abruptly
* killing the process that the virtual machine that runs the app runs in
* without finalizing all {@link Object}s created by the app. Whether the
* app is killed safely or quickly the app will be completely created as a
* new app in a new virtual machine running in a new process if the user
* starts the app again.
*
* <P>
* <B>NOTE:</B> The app will not be killed until all of its threads have
* closed if it is killed safely.
* </P>
*
* <P>
* <B>NOTE:</B> All threads running under the process will be abruptly
* killed when the app is killed quickly. This can lead to various issues
* related to threading. For example, if one of those threads was making
* multiple related changes to the database, then it may have committed some
* of those changes but not all of those changes when it was abruptly
* killed.
* </P>
*
* @param killSafely
*            Primitive boolean which indicates whether the app should be
*            killed safely or quickly. If true then the app will be killed
*            safely. Otherwise it will be killed quickly.
*/
public static void killApp(boolean killSafely) {
if (killSafely) {
/*
* Notify the system to finalize and collect all objects of the app
* on exit so that the virtual machine running the app can be killed
* by the system without causing issues. NOTE: If this is set to
* true then the virtual machine will not be killed until all of its
* threads have closed.
*/
System.runFinalizersOnExit(true);


/*
* Force the system to close the app down completely instead of
* retaining it in the background. The virtual machine that runs the
* app will be killed. The app will be completely created as a new
* app in a new virtual machine running in a new process if the user
* starts the app again.
*/
System.exit(0);
} else {
/*
* Alternatively the process that runs the virtual machine could be
* abruptly killed. This is the quickest way to remove the app from
* the device but it could cause problems since resources will not
* be finalized first. For example, all threads running under the
* process will be abruptly killed when the process is abruptly
* killed. If one of those threads was making multiple related
* changes to the database, then it may have committed some of those
* changes but not all of those changes when it was abruptly killed.
*/
android.os.Process.killProcess(android.os.Process.myPid());
}


}
}

我是这样做的:

我只是把

Intent intent = new Intent(Main.this, SOMECLASSNAME.class);
Main.this.startActivityForResult(intent, 0);

打开一个活动的方法的内部,然后是 SOMECLASSNAME 的方法的内部,这个方法被设计用来关闭我放置的应用程序:

setResult(0);
finish();

我在我的主课上写了以下内容:

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
if(resultCode == 0) {
finish();
}
}

finish();声明放置如下:

myIntent.putExtra("key1", editText2.getText().toString());


finish();


LoginActivity.this.startActivity(myIntent);

在每个活动中。

现在回答我自己的问题,经过这么长时间(因为 CommonsWare 评论了最流行的答案,告诉我们不应该这样做) :

当我想退出这个应用程序时:

  1. 我使用 FLAG_ACTIVITY_CLEAR_TOP启动我的第一个活动(或者是启动画面,或者是当前位于活动堆栈底部的任何活动)(它将退出在它之后启动的所有其他活动,这意味着——所有活动)。只需要在活动堆栈中保存这个活动(由于某种原因不要提前完成)。
  2. 这次行动我要求 finish()

就是这样,对我很有效。

2.3是不可能的。我搜索了很多,尝试了很多应用程序。最好的解决方案是同时安装(转到任务管理器)和(快速重启)。当他们一起使用它将工作,并将释放内存。另一个选择是升级到安卓冰淇淋三明治4.0.4,它允许控制(关闭)应用程序。

通过调用 Finish () ; 在 OnClick 按钮或菜单中

Case R.id.menu _ sets:

      finish();
return true;
@Override
protected void onPause() {
super.onPause();
System.exit(0);
}

只需在单击按钮 EXIT 时写下这段代码。

Intent intent = new Intent(getApplicationContext(), MainActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
intent.putExtra("LOGOUT", true);
startActivity(intent);

MainActivity.classOnCreate ()方法中,写下代码作为第一行,

if (getIntent().getBooleanExtra("LOGOUT", false))
{
finish();
}

复制下面的代码并将 AndroidManifest.xml 文件粘贴到 First Activity 标签下。

<activity
android:name="com.SplashActivity"
android:clearTaskOnLaunch="true"
android:launchMode="singleTask"
android:excludeFromRecents="true">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER"
/>
</intent-filter>
</activity>

在 AndroidManifest.xml 文件的 Activity Tag 下添加以下代码

 android:finishOnTaskLaunch="true"

退出应用程序的方式:

方法一:

调用 finish();并覆盖 onDestroy();。在 onDestroy()中输入以下代码:

System.runFinalizersOnExit(true)

或者

android.os.Process.killProcess(android.os.Process.myPid());

方法二:

public void quit() {
int pid = android.os.Process.myPid();
android.os.Process.killProcess(pid);
System.exit(0);
}

方法三:

Quit();


protected void Quit() {
super.finish();
}

方法四:

Intent intent = new Intent(getApplicationContext(), LoginActivity.class);
intent.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
intent.putExtra("EXIT", true);
startActivity(intent);


if (getIntent().getBooleanExtra("EXIT", false)) {
finish();
}

方法5:

有时调用 finish()只会退出当前活动,而不会退出整个应用程序。但是,有一个解决办法。每次启动 activity时,使用 startActivityForResult()启动它。当你想关闭整个应用程序时,你可以这样做:

setResult(RESULT_CLOSE_ALL);
finish();

然后定义每个活动的 onActivityResult(...)回调函数,这样当 activity返回 RESULT_CLOSE_ALL值时,它也会调用 finish():

@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
switch(resultCode){
case RESULT_CLOSE_ALL:{
setResult(RESULT_CLOSE_ALL);
finish();
}
}
super.onActivityResult(requestCode, resultCode, data);
}

我想回到我的机器人设备的主屏幕, 所以我简单地说:

moveTaskToBack(true);

如果你想关闭应用程序的所有活动,使用 finishAffinity()可能是一个很好的选择。根据 Android 文件-

Finish this activity as well as all activities immediately below it in the current task that have the same affinity.

以上所有的答案都不适用于我的应用程序

这是我的工作代码

在你的退出按钮上:

Intent intent = new Intent(getApplicationContext(), MainActivity.class);
ComponentName cn = intent.getComponent();
Intent mainIntent = IntentCompat.makeRestartActivityTask(cn);
mainIntent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);
mainIntent.addFlags(Intent.FLAG_ACTIVITY_NO_HISTORY);
mainIntent.putExtra("close", true);
startActivity(mainIntent);
finish();

代码是关闭任何其他活动并将 MainActivity 置于顶部 现在在你的主要活动:

if( getIntent().getBooleanExtra("close", false)){
finish();
}

我认为它将关闭您的活动和所有与之相关的子活动。

public boolean onOptionsItemSelected(MenuItem item) {


int id = item.getItemId();]
if (id == R.id.Exit) {
this.finishAffinity();
return true;
}


return super.onOptionsItemSelected(item);
}
public class CloseAppActivity extends AppCompatActivity
{
public static final void closeApp(Activity activity)
{
Intent intent = new Intent(activity, CloseAppActivity.class);
intent.addCategory(Intent.CATEGORY_HOME);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK |
IntentCompat.FLAG_ACTIVITY_CLEAR_TASK);
activity.startActivity(intent);
}


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

清单如下:

<activity
android:name=".presenter.activity.CloseAppActivity"
android:noHistory="true"
android:clearTaskOnLaunch="true"/>

然后您可以调用 CloseAppActivity.closeApp(fromActivity)和应用程序将关闭。

只需在 onBackPress 中编写以下代码:

@Override
public void onBackPressed() {
// super.onBackPressed();


//Creating an alert dialog to logout
AlertDialog.Builder alertDialogBuilder = new AlertDialog.Builder(this);
alertDialogBuilder.setMessage("Do you want to Exit?");
alertDialogBuilder.setPositiveButton("Yes",
new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface arg0, int arg1) {
Intent intent = new Intent(Intent.ACTION_MAIN);
intent.addCategory(Intent.CATEGORY_HOME);
startActivity(intent);
}
});


alertDialogBuilder.setNegativeButton("No",
new DialogInterface.OnClickListener() {
@Override
public void onClick(DialogInterface arg0, int arg1) {


}
});


//Showing the alert dialog
AlertDialog alertDialog = alertDialogBuilder.create();
alertDialog.show();
}

使用表 System.exit 的最佳和最短方法。

System.exit(0);

虚拟机停止进一步的执行,程序将退出。

使用“ this.FinishAndRemoveTask();”-它适当关闭应用程序