finish、killProcess 使用必知_one App one Activity

博客 退出 android 应用程序 说了很多关于如何退出 android app 的方法。但是,有很多实际情况,我们还是要好好考虑一下。


为了更好的说明这篇博客的目的,需要写两个 project,一个是在后台跑一个 Service 检查系统中运行与 Task 的 Activity,另一个是待测试的。


Service 很简单,只要启动这个 App,后台 Service(由Activity启动) 就会每隔 0.5 秒检查一下 Task。


Service Project 主要代码:

package com.google;

import android.app.ActivityManager;
import android.app.Service;
import android.app.ActivityManager.RunningTaskInfo;
import android.content.Context;
import android.content.Intent;
import android.os.Handler;
import android.os.IBinder;
import android.util.Log;

import java.util.List;

public class MyService extends Service {
    
    private ActivityManager am = null;
    private  List<RunningTaskInfo> taskInfo = null;
    
    private final Handler mHandler = new Handler();
    
    private final Runnable mRunnable = new Runnable() {
        
        @Override
        public void run() {
            taskInfo = am.getRunningTasks(Integer.MAX_VALUE);
            int len = taskInfo.size();
            for(int i=0; i<len; i++) {
                Log.d("mark2", taskInfo.get(i).topActivity.getPackageName());
            }
            mHandler.postDelayed(mRunnable, 500);
        }
    };

    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }

    @Override
    public void onCreate() {
        super.onCreate();
        am = (ActivityManager) getSystemService(Context.ACTIVITY_SERVICE);
    }

    @Override
    public void onDestroy() {
        super.onDestroy();
        mHandler.removeCallbacks(mRunnable);
    }

    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        mHandler.postDelayed(mRunnable, 500);
        return super.onStartCommand(intent, flags, startId);
    }
}


为了后边看的比较清楚,需要启动这个 Service 之后,点击 Back 退出启动它的 Activity。

另外,使用 getRunningTasks 需要下面的权限:


<uses-permission android:name="android.permission.GET_TASKS"/>


再说,第二个 Project,说到这里,只写了一个 Activity,里面都是关于 Activity 的回调方法。

界面只有一个按钮,点击按钮触发 onOver 方法,效果图:




代码:


package mark.zhang.demo;

import android.app.Activity;
import android.os.Bundle;
import android.util.Log;
import android.view.View;

public class TaskDemoActivity extends Activity {

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        Log.d("mark", "onCreate() ");
    }

    @Override
    protected void onResume() {
        super.onResume();
        Log.d("mark", "onResume() ");
    }

    @Override
    protected void onStart() {
        super.onStart();
        Log.d("mark", "onStart() ");
    }

    @Override
    protected void onRestart() {
        super.onRestart();
        Log.d("mark", "onRestart() ");
    }

    @Override
    protected void onPause() {
        super.onPause();
        Log.d("mark", "onPause() ");
    }

    @Override
    protected void onStop() {
        super.onStop();
        Log.d("mark", "onStop() ");
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        Log.d("mark", "onDestroy() ");
    }
    
    public void onOver(View view) {
        // 待续
    }
}


说明:下面只给出修改部分代码,没有修改的部分与上面代码一致。


第一个测试:


 public void onOver(View view) {
       finish();
 }


这个很简单,跟点击 back 按键的效果一致,点击按钮,该 Activity 正常退出(回调其那几个方法)。


然后,Service 打印的结果是 Task 中没有了 TaskDemoActivity(很快就没有了),这说明 finish 可以将 Activity 从 Task 中清除!


第二个测试:(不同与上一个!)


 @Override
 protected void onDestroy() {
       super.onDestroy();
       Log.d("mark", "onDestroy() ");

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

public void onOver(View view) {
       finish();
 }


点击按钮,回调方法调用(ok):


D/mark    ( 1523): onCreate() 
D/mark    ( 1523): onStart() 
D/mark    ( 1523): onResume() 
D/mark    ( 1523): onPause() 
D/mark    ( 1523): onStop() 
D/mark    ( 1523): onDestroy() 


但是,Service 大概在我点击按钮 2 秒钟内,还在打印:


D/mark2   (  978): mark.zhang.demo
D/mark2   (  978): com.android.launcher
D/mark2   (  978): mark.zhang.demo
D/mark2   (  978): com.android.launcher


这就说明,这种方式结束 Activity(App),需要一段时间,Activity 才会从 Task 中清除。

试想一下,如果我们想获取当前 Task 中的 Activity,如果不等会再去获取的话,获取的结果肯定不对。前段时间,做一个项目,就范了这麽个错误。


第三个测试:


public void onOver(View view) {
        android.os.Process.killProcess(android.os.Process.myPid());
}


这个时候,并没有调用 onPause() onStop() onDestroy() ,而是直接结束了 App,如果有其它组件如 Service 也会被kill。

Service 也很迅速的检查到当前 Task 中没有 TaskDemoActivity。


这个时候,你会想没有调用这些回调方法,那麽我先 finish,看下面测试。


第四个测试:


public void onOver(View view) {
        finish();
        android.os.Process.killProcess(android.os.Process.myPid());
}


测试结果,跟第三个测试一样的。说明 android.os.Process.killProcess(android.os.Process.myPid()); 前面 finish 也无济于事!


当然,你需要根据实际需求做测试,我这里只是抛砖引玉。下篇博客,再做关于 one App two Activity 的情况分析!






©️2020 CSDN 皮肤主题: 酷酷鲨 设计师:CSDN官方博客 返回首页