深入Android系统(十一)AMS-2-Activity生命周期管理

Activity管理

Activity是最复杂的一个组件,它负责UI的显示以及处理各种输入事件。Activity提供窗口供应用在其中绘制界面,同时也提供了各种各样的控件方便开发。Activity 官网传送门

另外,Android中并没有对外提供启动进程的接口,只是在启动ActivityService时,由系统根据需要来启动进程。

Activity的生命周期

关于Activity的生命周期,我们先看下官方图示:
深入Android系统(十一)AMS-2-Activity生命周期管理_第1张图片

Activity的生命周期图中隐含了Activity运行时的三种状态,分别是:

  • 激活态:新启动的Activity位于屏幕的最前端,可以接受用户输入的状态
  • 暂停态:当Activity被一个透明或半透明的Activity覆盖,此时Activity虽然不能接收用户的输入,但还是可见的
  • 停止态:当一个Activity完全被另一Activity覆盖,不能接受用户输入也不可见时

当一个Activity对象的状态发生变化时,会调用上图中定义的抽象接口来通知应用。相关描述如下:

  • onCreate():当Activity对象被创建时调用
  • onStart():当ActivityFramework中的数据结构准备完毕后调用
  • onResume():当Activity来到栈的最前端变成激活态时调用
  • onPause():当Activity从栈的最前端切换到后台时,进入暂停态,并调用该方法
  • onStop():当Activity已经完全不可见时调用
  • onDestroy():在销毁Activity前,系统会先调用该方法

上面的知识在初学Android时我们就已经知道了,接下来我们要从AMS的角度看下这几个方法是如何调用的,不过在此之前我们先熟悉下另外的几个相关知识:IntentTaskLaunchMode

IntentTaskLaunchMode

理解Intent

Intent是所请求执行动作的抽象描述,通常作为参数来使用,用于完成各个组件之间的消息传递。更为详细的姿势可以参考官网描述:官网传送门

Intent类的相关定义如下:

public class Intent implements Parcelable, Cloneable {
    private String mAction;
    private Uri mData;
    private String mType;
    private String mPackage;
    private ComponentName mComponent;
    private int mFlags;
    private ArraySet<String> mCategories;
    private Bundle mExtras;
    private Rect mSourceBounds;
    private Intent mSelector;
    private ClipData mClipData;
}

常用字段含义如下:

  • mAction是一个字符串,用来指明要执行的操作是什么。
    • Intent类中定义了大量的Action,例如ACTION_VIEWACTION_SEND等。
    • 这些Action的作用与具体的功能模块相关,表达要执行的意图
  • mData储存需要传递的数据,类型是URI
    • URI是统一资源标识符(Uniform Resources Identifier)的简称
    • 最初用于表示Web中的各种资源,如HTML文档、图片、文件等
    • URL(Uniform Resource Locator)URI的一种
  • mTypeMIME格式的字符串,表示数据类型。
    • MIME是多功能Internet邮件扩充服务(Multipurpose Internet Mail Extensions)的缩写
    • 最早英语电子邮件系统,后来应用到浏览器。格式例如:text/plain``application/x-gzip
    • 通常该数据类型不需要指定,如果设置了这个字段,可以加快Intent的匹配速度
  • mComponent用于指定接收Intent的目标组件的名称
    • mComponent的类型是ComponentName,它包含两个字符串:mPackagemClass,前者用于指定包名,后者用于指定类名
    • Intent中如果定义了mComponent,该Intent将直接发送到指定的组件,不会在通过其他属性组合查找
  • mFlags称为标志,在Intent类中定义了很多flag的相关常量。主要分为两种
    • FLAG_ACTIVITY_...开头的,用来控制Activity启动的相关参数,如FLAG_ACTIVITY_NEW_TASK
    • FLAG_RECEIVER_...开头的,用来进行广播的参数
  • mCategories一个包含应处理Intent组件类型的附加信息的字符串。常见的类别有两种:
    • CATEGORY_BROWSABLE:目标Activity允许本身通过网络浏览器启动,以显示链接引用的数据
    • CATEGORY_LAUNCHER:该Activity是任务的初始Activity
    • 可以将任意数量的类别描述放入一个 Intent中,但大多数Intent均不需要类别
  • mExtras表示所有附加信息的集合。
    • mExtras数据类型是Bundle
    • 可以使用各种putExtra()方法添加extra数据,每种方法均接受两个参数:keyvalue

Task

TaskActivity的集合。Android把用户一次相关操作中使用的Activity按照先后顺序保存在Task中,这样当按back键时就能按照相反的顺序回退。

Task像一个栈,以后进先出的方式管理着Activity。系统运行时内存中会存在着多个Task,当我们按recent键时,会弹出一个选择列表,这个列表就是系统中存在的Task的集合,选择一个Task将把它所包含的Activity作为一个整体带到前台。Task中的Activity的顺序通常是不能改变的,只能通过出栈入栈的方式来增加或移除。

AMS中使用ActivityStack来管理Task,它管理的Task都存放在成员变量mTaskHistory中,定义如下:

class ActivityStack{
    private final ArrayList<TaskRecord> mTaskHistory = new ArrayList<>();
}

mTaskHistory是一个列表,储存的是TaskRecord对象。TaskRecord对象表示一个Task,它的成员变量mActivities也是一个列表,储存了该Task中所有的ActivityRecord对象。mActivities的定义如下:

class TaskRecord{
    final ArrayList<ActivityRecord> mActivities;
}

那么,如何才能开始一个新的Task呢?

  • Intent中定义了一个标志FLAG_ACTIVITY_NEW_TASK,在startActivity()Intent参数中加入该标志就能开启一个新的Task
  • 但是如果系统中已经有相同affinityTask存在,并不会再启动一个Task,而是将旧的Task带到前台

那么,affinity在哪里定义的呢?

  • affinity的意思是亲和度,是通过标签的android:taskAffinity属性来定义的
  • 当使用标志FLAG_ACTIVITY_NEW_TASK启动一个Activity时,这个ActivitytaskAffinity属性中的字符串就会成为Taskaffinity
  • 以后加入这个TaskActivity,即使它们的taskAffinity属性定义了一个不同的字符串,也不会改变Task已有的affinity
  • 如果标签中没有指定android:taskAffinity属性,这个Activity会继承标签的android:taskAffinity属性
  • 如果标签的android:taskAffinity属性也没有定义,将会使用应用包名作为缺省值
    • 正因为如此,如果在应用中启动本应用的另一个Activity,即使使用了FLAG_ACTIVITY_NEW_TASK标志也不一定会启动一个新的Task
    • 除非这个Activity定义了不同的taskAffinity属性

LaunchMode

Activity的启动模式隐含的是Activity对象的复用问题,关于启动模式官网的介绍也很详细:官方传送门

当启动一个Activity时,如果系统的后台Task中已经有一个该Activity的实例存在了,系统是创建一个新的Activity还是将已经存在的Activity切换到前台呢?

答案是都有可能,有多种因素可以影响结果。包括Activity的属性值以及Intent中指定的标志

我们先看下Activity的属性launchMode会有哪些影响:

  • standard模式:默认。
    • standard模式下的Activity每次启动时都会创建该Activity的实例对象
    • 同一个Task中可以同时存在该Activity的多个实例
    • 一个Activity的多个实例可以出现在多个Task栈中
  • singleTop模式
    • 如果目标Task的顶部已存在该Activity实例,则系统会通过调用该实例的onNewIntent()方法向其传送Intent,而非创建新的Activity实例。
    • 如果不在栈顶,这standard模式一样创建新的实例对象
  • singleTask模式
    • 设置singleTask模式的Activity具有系统唯一性,只能在系统中创建该Activity的一个实例对象
    • 启动设置为singleTask模式的Activity时,如果系统中已经存在该Activity的实例对象,则将其所在的Task中排在它前面的Activity都弹出栈,将该Activity带到栈顶,并调用其onNewIntent()方法传递新的Intent对象
    • 如果系统中不存在该Activity的实例对象,则会创建一个该Activity的实例对象
      • 如果该ActivitytaskAffinity属性值和当前Taskaffinity值相同,它会加入当前的Task
      • 否则,即使启动该ActivityIntent中没有指定FLAG_ACTIVITY_NEW_TASK标志,也会启动新的Task,并将Activity至于其中
  • singleInstance模式
    • 设置为singleInstance模式的Activity同样具有系统唯一性,系统中只有该Activity的一个实例对象
    • 同时系统不会将任何其他Activity启动到包含该Activity实例的Task
    • Activity始终是其Task中的唯一Activity

通常情况下,一个Activity创建出来后,会停留在某个Task中,直到它被销毁

  • 但是,如果ActivityallowTaskReparenting属性设置为true,该Activity可以在不同的Task之间转移
  • 不过,这个属性只有在启动ActivityIntent中设置了FLAG_ACTIVITY_RESET_TASK_IF_NEEDED标志时才起作用

除了上面介绍的内容,ActivityTask的工作逻辑大家可以参考官网:任务和返回堆栈

比如,下面部分提到的技巧就很重要(摘抄自官网):

只有当 Activity 具有 ACTION_MAIN 和 CATEGORY_LAUNCHER 过滤器时,才应使用 “singleTask” 和 “singleInstance” 这两种启动模式,它们会将 Activity 标记为始终启动任务。比如,可以想象一下,如果缺少该过滤器会发生什么情况:intent 会启动 “singleTask” Activity,随之启动新任务,用户花了一些时间在该任务上。然后,用户按主屏幕按钮。此时,该任务会转到后台,不再可见。现在,用户无法返回到该任务,因为它未显示在应用启动器中。

了解ClientTransactionHandler的作用

ClientTransactionHandler是在Android 9.0上出现的,用来串联起AMSActivity的整个生命周期管理的类,很重要

我们已经知道应用的入口是ActivityThread类的main()函数,仔细看下类结构的话会发现要ActivityThread继承了一个特殊的类。定义如下

public final class ActivityThread extends ClientTransactionHandler {
    ...
}

可以看到ActivityThread继承了ClientTransactionHandler类。这个类是在Android 9.0加入的,关键定义如下:

public abstract class ClientTransactionHandler {
    void scheduleTransaction(ClientTransaction transaction) {
        transaction.preExecute(this);
        sendMessage(ActivityThread.H.EXECUTE_TRANSACTION, transaction);
    }
    ......
    public abstract void handleDestroyActivity(...);
    public abstract void handlePauseActivity(...);
    public abstract void handleResumeActivity(...);
    public abstract void handleStopActivity(...);
    ......
    public abstract Activity handleLaunchActivity(...);
    public abstract void handleStartActivity(...);
    ......
    public abstract void handleNewIntent(...);
    ......
}

类中定义了和声明周期有关的方法,机智的我们可以猜到,AMS后面生命周期的回调控制应该就是通过它来实现的,相关类继承关系如下:
深入Android系统(十一)AMS-2-Activity生命周期管理_第2张图片

可以AndroidActivity相关的生命周期要做的事情抽象了出来,在上面定义的类中,真正业务实现包括:

  • LaunchActivityItem就是要执行launch activity任务
  • resume activity则是通过ResumeActivityItem实现
  • pause activity则是通过PauseActivityItem实现
  • stop activity则是通过StopActivityItem实现
  • destroy activity则是通过DestoryActivityItem实现

ClientTransaction的调用逻辑

我们看下整个调用流程:
ActivityThread中的ApplicationThread类有一个scheduleTransaction()方法,

ApplicationThread类是一个Binder服务类,AMS会作为client调用这个服务类,当然也就可以调用它的scheduleTransaction()方法

scheduleTransaction()方法内容如下:

@Override
public void scheduleTransaction(ClientTransaction transaction) throws RemoteException {
    ActivityThread.this.scheduleTransaction(transaction);
}

调用的是ActivityThreadscheduleTransaction()方法,也就是ClientTransactionHandler类的scheduleTransaction()方法,方法如下:

    void scheduleTransaction(ClientTransaction transaction) {
        transaction.preExecute(this);
        sendMessage(ActivityThread.H.EXECUTE_TRANSACTION, transaction);
    }

发送了一个EXECUTE_TRANSACTION消息给ActivityThreadHandler实现类H,消息处理如下:

case EXECUTE_TRANSACTION:
    final ClientTransaction transaction = (ClientTransaction) msg.obj;
    mTransactionExecutor.execute(transaction);
    if (isSystem()) {
        transaction.recycle();
    }
    break;

消息处理中使用了mTransactionExecutor.execute(),不出意外,执行逻辑肯定在TransactionExecutor中了,我们看下:

    public void execute(ClientTransaction transaction) {
        final IBinder token = transaction.getActivityToken();
        executeCallbacks(transaction);
        executeLifecycleState(transaction);
        mPendingActions.clear();
    }
    public void executeCallbacks(ClientTransaction transaction) {
        final List<ClientTransactionItem> callbacks = transaction.getCallbacks();
        if (callbacks == null) {
            return;
        }
        ......
        final int size = callbacks.size();
        for (int i = 0; i < size; ++i) {
            ......
            item.execute(mTransactionHandler, token, mPendingActions);
            item.postExecute(mTransactionHandler, token, mPendingActions);
            ......
        }
    }
    private void executeLifecycleState(ClientTransaction transaction) {
        final ActivityLifecycleItem lifecycleItem = transaction.getLifecycleStateRequest();
        if (lifecycleItem == null) {
            // No lifecycle request, return early.
            return;
        }
        ......
        // 很重要的一个方法
        cycleToPath(r, lifecycleItem.getTargetState(), true /* excludeLastState */);
        // Execute the final transition with proper parameters.
        lifecycleItem.execute(mTransactionHandler, token, mPendingActions);
        lifecycleItem.postExecute(mTransactionHandler, token, mPendingActions);
    }

可以看到,最后分别在executeCallbacks()executeLifecycleState()两个方中执行了item.execute()lifecycleItem.execute()两个方法

executeCallbacks()executeLifecycleState()目的分别是干什么呢?结合类关系图我们可以这样推断:

  • executeCallbacks()遍历执行的是ClientTransaction类中List mActivityCallbacks集合中的元素
    • ClientTransactionItem类的直接子类实现只有LaunchActivityItem
    • 也就是说executeCallbacks()主要执行的是launch activity的通知操作
  • executeLifecycleState()执行的是ClientTransaction类中的ActivityLifecycleItem mLifecycleStateRequest
    • mLifecycleStateRequest被称为final state
    • 从继承关系上可以看到,resume activitypasue activitystop activitydestory activity都在这里

了解完调用流程会发现,实现类中并没有StartActivityItem,为什么呢?那怎么调用onStart()函数呢?
核心就在cycleToPath()函数身上

TransactionExecutor.cycleToPath()

针对Activity的生命周期,Android并没有定义出所有的*ActivityItem类,例如StartActivityItem就并不存在,那么怎么去执行这个start阶段的函数呢?

请留意类图中ActivityLifecycleItem有关生命周期的常量定义,Android在这里通过cycleToPath()采用了一种比较取巧的操作,核心逻辑就是:

  • 指定一个Activityfinal state
  • 根据Activity的当前状态去计算过程中需要的状态,并保存到集合中
  • 最后按顺序执行集合中的状态

以文章后面的realStartActivityLocked()方法为例

  • LaunchActivityItem类型的对象添加到callback
    • TransactionExecutor会先执行LaunchActivityItem
    • 执行完后Activity进入到ON_CREATE状态
  • 方法中指定了final stateResumeActivityItem
    • TransactionExecutor通过cycleToPath()计算当前状态与final state的差异
    • 当前状态为ON_CREATE状态,final stateON_RESUME
    • TransactionExecutor通过帮助类的getLifecyclePath方法将两者之间缺失的状态整理到集合中
    • 然后调用performLifecycleSequence()循环处理

performLifecycleSequence()方法如下:

    private void performLifecycleSequence(ActivityClientRecord r, IntArray path) {
        final int size = path.size();
        for (int i = 0, state; i < size; i++) {
            state = path.get(i);
            switch (state) {
                case ON_CREATE:
                    mTransactionHandler.handleLaunchActivity(...);
                    break;
                case ON_START:
                    mTransactionHandler.handleStartActivity(r, mPendingActions);
                    break;
                case ON_RESUME:
                    mTransactionHandler.handleResumeActivity(...);
                    break;
                case ON_PAUSE:
                    mTransactionHandler.handlePauseActivity(...);
                    break;
                case ON_STOP:
                    mTransactionHandler.handleStopActivity(...);
                    break;
                case ON_DESTROY:
                    mTransactionHandler.handleDestroyActivity(...);
                    break;
                case ON_RESTART:
                    mTransactionHandler.performRestartActivity(...);
                    break;
                default:
                    throw new IllegalArgumentException("Unexpected lifecycle state: " + state);
            }
        }
    }

PauseActivityItem的调用分析

PauseActivityItem类为例,我们看看具体的执行逻辑:

public class PauseActivityItem extends ActivityLifecycleItem {
    ......
    @Override
    public void execute(ClientTransactionHandler client, IBinder token,
            PendingTransactionActions pendingActions) {
        ......
        client.handlePauseActivity(token, mFinished, mUserLeaving, mConfigChanges, pendingActions,
                "PAUSE_ACTIVITY_ITEM");
        ......
    }
}

执行的是ClientTransactionHandler抽象类,其实也就是ActivityThread类的handlePauseActivity()方法。

handlePauseActivity()方法调用了ActivityThread类的performPauseActivity()方法,最后调用到的是performPauseActivityIfNeeded()方法,代码如下:

    private void performPauseActivityIfNeeded(ActivityClientRecord r, String reason) {
        ......
        mInstrumentation.callActivityOnPause(r.activity);
        ......
    }

执行的是Instrumentation类的callActivityOnPause()方法,内容如下:

    public void callActivityOnPause(Activity activity) {
        activity.performPause();
    }

很简洁,继续查看:

public class Activity{
    final void performPause() {
        mDoReportFullyDrawn = false;
        mFragments.dispatchPause();
        mCalled = false;
        onPause();
        writeEventLog(LOG_AM_ON_PAUSE_CALLED, "performPause");
        mResumed = false;
        ......
    }
}

有木有!有木有!onPause();终于调用到了。。。。。。

我们已经从应用端找到了调用的流程,但是,对于AMS来说它是怎么触发的呢?

接下来,我们分析下Activity的启动,在Activity启动的过程我们就可以找到AMS触发声明周期的例子

启动Activity

研究Activity生命周期的调用细节,我们还是得从最熟悉的地方入手,也就是常用的Activity对象的startActivity (Intent intent)方法

Activty.startActivty()

跟踪startActivity (Intent intent)方法,发现调用关系如下:

class Activity{
    public void startActivity(Intent intent, @Nullable Bundle options) {
        if (options != null) {
            startActivityForResult(intent, -1, options);
        } else {
            startActivityForResult(intent, -1);
        }
    }
    public void startActivityForResult(...) {
        ......
        Instrumentation.ActivityResult ar =
            mInstrumentation.execStartActivity(
                this, mMainThread.getApplicationThread(), mToken, who,
                intent, requestCode, options);
        ......
    }
}
class Instrumentation{
    public ActivityResult execStartActivity(...) {
        IApplicationThread whoThread = (IApplicationThread) contextThread;
        ......
        try {
            intent.migrateExtraStreamToClipData();
            intent.prepareToLeaveProcess(who);
            int result = ActivityManager.getService()
                .startActivity(...);
            checkStartActivityResult(result, intent);
        } catch (RemoteException e) {
            throw new RuntimeException("Failure from system", e);
        }
        return null;
    }
}
class ActivityManagerService{
    public final int startActivity(...) {
        return startActivityAsUser(...);
    }
    public final int startActivityAsUser(...) {
        ......
        return mActivityStartController.obtainStarter(intent, "startActivityAsUser")
                ...
                .execute();
    }
}

我们看到最后是调用的是AMSstartActivityAsUser方法。跟踪startActivityAsUser方法的调用过程就会发现最后执行的是ActivityStarter类的execute()方法来执行Activity的启动,相关代码如下:

class ActivityStater{
    int execute() {
        try {
            if (mRequest.mayWait) {
                return startActivityMayWait(...);
            } else {
                return startActivity(...);
            }
        } finally {
            onExecutionComplete();
        }
    }
}

我们看到execute()有两个启动Activity的方法,接下来我们以startActivityMayWait()方法继续分析,因为最后也会走到startActivity()中。

ActivityStarter.startActivityMayWait()

简要代码如下:

private int startActivityMayWait(...) {
    ......
    // 获取要启动的 Activity 的信息
    ActivityInfo aInfo = mSupervisor.resolveActivity(intent, rInfo, startFlags, profilerInfo);
    synchronized (mService) {
        ......
        int res = startActivity(caller, ...);
        ......
        if (outResult != null) { // 需要返回结果
            outResult.result = res;
            final ActivityRecord r = outRecord[0];
            switch(res) {
                case START_SUCCESS: {
                    // 添加到特定集合中
                    mSupervisor.mWaitingActivityLaunched.add(outResult);
                    do {
                        try {
                            // 等待应用进程中的 Activity 启动完成
                            mService.wait();
                        } catch (InterruptedException e) {
                        }
                    } while (outResult.result != START_TASK_TO_FRONT
                            && !outResult.timeout && outResult.who == null);
                    ......
                    break;
                }
                ......
            }
        }
        return res;
    }
}

startActivityMayWait()方法的流程如下:

  • 首先调用resolveActivity()方法来获取要启动的Activity的信息
  • 得到Activity的信息后,继续调用startActivity()方法来继续启动Activity
  • 如果启动Activity的应用需要获取返回结果,则调用mService对象的wait()方法挂起线程等待启动的结果

接下来就是调用ActivityStarterstartActivity()方法的代码,我们看下部分细节:

private int startActivity(IApplicationThread caller, ...) {
    int err = ActivityManager.START_SUCCESS;
    ......
    if (caller != null) {
        // 获取启动Activity的进程的信息
        callerApp = mService.getRecordForAppLocked(caller);
        if (callerApp != null) {
            callingPid = callerApp.pid;
            callingUid = callerApp.info.uid;
        } else {
            err = ActivityManager.START_PERMISSION_DENIED;
        }
    }
    final int userId = aInfo != null && aInfo.applicationInfo != null
            ? UserHandle.getUserId(aInfo.applicationInfo.uid) : 0;
    ......// 省略很多错误检查
    // 检查调用者的相关权限
    boolean abort = !mSupervisor.checkStartAnyActivityPermission(...);
    // 检查 Intent 防火墙是否屏蔽了该 Intent
    abort |= !mService.mIntentFirewall.checkStartActivity(...);
    ......
    if (mService.mController != null) {
        try {
            // 将 Activity 启动的消息通知监听系统Activity变动的接口 IActivityControler
            Intent watchIntent = intent.cloneFilter();
            abort |= !mService.mController.activityStarting(watchIntent,
                    aInfo.applicationInfo.packageName);
        } catch (RemoteException e) {
            mService.mController = null;
        }
    }
    ......
    if (abort) {
        ......// 如果 abort 为true,直接退出
        return START_ABORTED;
    }
    ......
    // 创建 ActivityRecord  对象
    ActivityRecord r = new ActivityRecord(...);
    if (outActivity != null) {
        outActivity[0] = r;
    }
    ......
    // 当前用户正在操作的 ActivityStack
    final ActivityStack stack = mSupervisor.mFocusedStack;
    // 针对经常切换进程的情况,检查调用者是否有权限进行进程切换
    if (voiceSession == null && (stack.getResumedActivity() == null
            || stack.getResumedActivity().info.applicationInfo.uid != realCallingUid)) {
        if (!mService.checkAppSwitchAllowedLocked(callingPid, callingUid,
                realCallingPid, realCallingUid, "Activity start")) {
            // 对于不能切换进程的情况,把 Activity 信息放入 mPendingActivityLaunches 列表中
            mController.addPendingActivityLaunch(new PendingActivityLaunch(r,
                    sourceRecord, startFlags, stack, callerApp));
            ActivityOptions.abort(checkedOptions);
            return ActivityManager.START_SWITCHES_CANCELED;
        }
    }
    if (mService.mDidAppSwitch) {
        mService.mAppSwitchesAllowedTime = 0;
    } else {
        mService.mDidAppSwitch = true;// 打开开关,允许进程间切换
    }
    // 启动挂起等待的 Activity,其实就是逐个启动 mPendingActivityLaunches 列表中的 Activity。
    // 最后也是调用了 startActivity
    // 个人理解,大多数情况下 mPendingActivityLaunches 列表应该是空的吧
    mController.doPendingActivityLaunches(false);
    ......
    // 调用startActivity另一个重载方法,第一个参数为 ActivityRecord
    return startActivity(r, ...);
}
private int startActivity(final ActivityRecord r, ...) {
    int result = START_CANCELED;
    ......
    result = startActivityUnchecked(r, ...);
    ......
    return result;
}

这里其实不用记录太多细节,重要的是了解启动Activity方法的调用流程,这里最后调用的是startActivityUnchecked()方法,我们来继续看下。

ActivityStarter.startActivityUnchecked()

方法如下:

private int startActivityUnchecked(final ActivityRecord r, ...) {
    // 初始化环境和lunchModeFlags   
    setInitialState(r, options, inTask, doResume, startFlags, sourceRecord, voiceSession,
            voiceInteractor);
    computeLaunchingTaskFlags();
    computeSourceStack();
    mIntent.setFlags(mLaunchFlags);

    // 判断 Activity 是否需要插入新的 Task,以下情况 reusedActivity 不为空
    // 1.设置了FLAG_ACTIVITY_NEW_TASK:
    // 2.启动模式为singleTask:
    // 3.启动模式为singleInstance
    ActivityRecord reusedActivity = getReusableIntentActivity();
    ......
    final boolean dontStart = top != null && mStartActivity.resultTo == null
            && top.realActivity.equals(mStartActivity.realActivity)
            && top.userId == mStartActivity.userId
            && top.app != null && top.app.thread != null
            && ((mLaunchFlags & FLAG_ACTIVITY_SINGLE_TOP) != 0
            || isLaunchModeOneOf(LAUNCH_SINGLE_TOP, LAUNCH_SINGLE_TASK));
    if (dontStart) { // 不需要启动的情况
        // For paranoia, make sure we have correctly resumed the top activity.
        topStack.mLastPausedActivity = null;
        if (mDoResume) {
            mSupervisor.resumeFocusedStackTopActivityLocked();
        }
        ......
        deliverNewIntent(top);
        ......
        return START_DELIVERED_TO_TOP;
    }
    boolean newTask = false;
    final TaskRecord taskToAffiliate = (mLaunchTaskBehind && mSourceRecord != null)
            ? mSourceRecord.getTask() : null;
    // 判断当前 Activity 是否需要一个新的 Task
    int result = START_SUCCESS;
    if (mStartActivity.resultTo == null && mInTask == null && !mAddingToTask
            && (mLaunchFlags & FLAG_ACTIVITY_NEW_TASK) != 0) {
        newTask = true;
        result = setTaskFromReuseOrCreateNewTask(taskToAffiliate, topStack);
    } else if (mSourceRecord != null) {
        result = setTaskFromSourceRecord();
    } else if (mInTask != null) {
        result = setTaskFromInTask();
    } else {
        // This not being started from an existing activity, and not part of a new task...
        // just put it in the top task, though these days this case should never happen.
        setTaskToCurrentTopOrCreateNewTask();
    }
    ......
    // 启动 Activity
    // startActivityLocked 这里主要是将 ActivityRecord 对象加入到 Task 的顶部
    // 同时将 Task 添加到 mTaskHistory 的顶部
    mTargetStack.startActivityLocked(mStartActivity, topFocused, newTask, mKeepCurTransition,
            mOptions);
    // 利用 WindowManager 使 Activity 可见
    if (mDoResume) {
        final ActivityRecord topTaskActivity = mStartActivity.getTask().topRunningActivityLocked();
        if (!mTargetStack.isFocusable() || (topTaskActivity != null && topTaskActivity.mTaskOverlay && mStartActivity != topTaskActivity)) {
            mTargetStack.ensureActivitiesVisibleLocked(null, 0, !PRESERVE_WINDOWS);
            mService.mWindowManager.executeAppTransition(); // 此处应该是执行应用间的切换动画
        } else {
            .......
            mSupervisor.resumeFocusedStackTopActivityLocked(mTargetStack, mStartActivity,
                    mOptions);
        }
    } else if (mStartActivity != null) {
        mSupervisor.mRecentTasks.add(mStartActivity.getTask());
    }
    ......
    return START_SUCCESS;
}

startActivityUnchecked()方法主要是通过Intent的标志和Activity的属性来确定ActivityTask,然后将其调整至栈顶,细节我们先略过,需要重点关注的方法是mSupervisor.resumeFocusedStackTopActivityLocked()方法的调用。跟踪调用就会发现,最后执行的是ActivityStack类的resumeTopActivityInnerLocked()方法

ActivityStack.resumeTopActivityInnerLocked()

我们前面已经知道resumeFocusedStackTopActivityLocked()方法最终会调用ActivityStack类的resumeTopActivityInnerLocked()方法。

resumeTopActivityInnerLocked()方法主要的作用是将位于栈顶的Activity显示出来,不过在此之前,旧的Activity(变量mResumedActivity引用的就是)还显示在屏幕上。方法内容如下:

private boolean resumeTopActivityInnerLocked(ActivityRecord prev, ActivityOptions options) {
    if (!mService.mBooting && !mService.mBooted) {
        // Not ready yet!
        return false;
    }
    // 从要 mTaskHistory 中查找要启动的 Activity
    // 这里这样做应该是因为前面已经将 Activity 放入堆栈中了
    final ActivityRecord next = topRunningActivityLocked(true /* focusableOnly */);
    final boolean hasRunningActivity = next != null;
    ......
    if (!hasRunningActivity) {
        // There are no activities left in the stack, let's look somewhere else.
        return resumeTopActivityInNextFocusableStack(prev, options, "noMoreActivities");
    }
    next.delayedResume = false;
    // 如果当前显示的 Activity 就是要启动的 Activity,直接返回
    if (mResumedActivity == next && next.isState(RESUMED)
            && mStackSupervisor.allResumedActivitiesComplete()) {
        executeAppTransition(options);
        return false;
    }
    // 如果正在休眠或者关机,直接返回
    if (shouldSleepOrShutDownActivities()
            && mLastPausedActivity == next
            && mStackSupervisor.allPausedActivitiesComplete()) {
        executeAppTransition(options);
        return false;
    }
    // user 状态检查
    if (!mService.mUserController.hasStartedUserState(next.userId)) {
        return false;
    }
    // 将要启动的 Activity 从相关队列中移除
    mStackSupervisor.mStoppingActivities.remove(next);
    mStackSupervisor.mGoingToSleepActivities.remove(next);
    next.sleeping = false;
    mStackSupervisor.mActivitiesWaitingForVisibleActivity.remove(next);
    // 检查是否有正在 Pause 的 Activity
    if (!mStackSupervisor.allPausedActivitiesComplete()) {
        return false;
    }
    // 设置要启动的 applicationInfo
    mStackSupervisor.setLaunchSource(next.info.applicationInfo.uid);
    ......
    boolean pausing = mStackSupervisor.pauseBackStacks(userLeaving, next, false);
    if (mResumedActivity != null) {
        // 暂停当前 Activity
        // startPausingLocked() 中便会触发 旧Activity 的 onPause() 操作
        pausing |= startPausingLocked(userLeaving, false, next, false);
    }
    ......
    ActivityStack lastStack = mStackSupervisor.getLastStack();
    if (next.app != null && next.app.thread != null) {
        // 如果 Activity 所在的应用已经存在,只需要把 Activity 显示出来
        ......
        synchronized(mWindowManager.getWindowManagerLock()) {
            // This activity is now becoming visible.
            if (!next.visible || next.stopped || lastActivityTranslucent) {
                next.setVisibility(true);
            }
            ......
            try {
                final ClientTransaction transaction = ClientTransaction.obtain(next.app.thread,
                        next.appToken);
                ......
                // 如果当前 Activity 还有等待返回的结果,添加 ActivityResultItem,
                // 其中会执行 onActivityResult 回调
                ArrayList<ResultInfo> a = next.results;
                if (a != null) {
                    final int N = a.size();
                    if (!next.finishing && N > 0) {
                        if (DEBUG_RESULTS) Slog.v(TAG_RESULTS,
                                "Delivering results to " + next + ": " + a);
                        transaction.addCallback(ActivityResultItem.obtain(a));
                    }
                }
                // 添加 NewIntentItem,其中会执行 onNewIntent
                if (next.newIntents != null) {
                    transaction.addCallback(NewIntentItem.obtain(next.newIntents,
                            false /* andPause */));
                }
                transaction.setLifecycleStateRequest(
                        ResumeActivityItem.obtain(next.app.repProcState,
                                mService.isNextTransitionForward()));
                mService.getLifecycleManager().scheduleTransaction(transaction);
                ......
            } catch (Exception e) {
                // Whoops, need to restart this activity!
                ......
                mStackSupervisor.startSpecificActivityLocked(next, true, false);
                if (DEBUG_STACK) mStackSupervisor.validateTopActivitiesLocked();
                return true;
            }
        }
        ......
    } else {
        // Whoops, need to restart this activity!
        ......
        mStackSupervisor.startSpecificActivityLocked(next, true, true);
    }
    ......
    return true;
}

resumeTopActivityInnerLocked()代码比较长作了精简,核心逻辑如下:

  • 先是通过startPausingLocked()暂停旧的ActivitystartPausingLocked()方法如下:
    final boolean startPausingLocked(boolean userLeaving, boolean uiSleeping,
            ActivityRecord resuming, boolean pauseImmediately) {
        ......
        mService.getLifecycleManager().scheduleTransaction(prev.app.thread, prev.appToken,
                        PauseActivityItem.obtain(prev.finishing, userLeaving,
                                prev.configChangeFlags, pauseImmediately));
        ......
    }
    
    • 这里四不四就和前面的ClientTransaction呼应上了,嘿嘿
  • 如果Activity所在的应用已经启动,对Activity进行显示处理,创建ResumeActivityItem进行生命周期通知
    • 最终会导致Activity对象的onResume()方法的执行
  • 如果应用还没有启动,则调用startSpecificActivityLocked()方法继续处理,方法如下:
    void startSpecificActivityLocked(ActivityRecord r,
            boolean andResume, boolean checkConfig) {
        // 获取 Activity 对应的进程
        ProcessRecord app = mService.getProcessRecordLocked(r.processName,
                r.info.applicationInfo.uid, true);
        if (app != null && app.thread != null) {
            try {
                ......
                // 如果应用进程已经存在的情况,执行 realStartActivityLocked() 
                // andResume = true
                realStartActivityLocked(r, app, andResume, checkConfig);
                // 然后返回
                return;
            } catch (RemoteException e) {
            }
    
        }
        // Activity 对应的进程为空,通过 AMS 的 startProcessLocked() 创建新的进程
        mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0,
                "activity", r.intent.getComponent(), false, false, true);
    }
    
    • 核心方法是realStartActivityLocked(),就算是重新启动进程的情况,最后执行的也是realStartActivityLocked()

ActivityStackSupervisor.realStartActivityLocked()

对于realStartActivityLocked()方法,我们简单看下和生命周期相关的内容:

    final boolean realStartActivityLocked(ActivityRecord r, ProcessRecord app,
            boolean andResume, boolean checkConfig) throws RemoteException {
        ......
        // Create activity launch transaction.
        final ClientTransaction clientTransaction = ClientTransaction.obtain(app.thread,
                r.appToken);
        // 添加 LaunchActivityItem,这个会触发 onCreate 方法
        clientTransaction.addCallback(LaunchActivityItem.obtain(new Intent(r.intent), ...);
        // 设置最终状态,resume 还是 pause
        final ActivityLifecycleItem lifecycleItem;
        // 根据前面的调用参数可以确定,andResume = true
        if (andResume) {
            // 设置最终状态为 ON_RESUME
            lifecycleItem = ResumeActivityItem.obtain(mService.isNextTransitionForward());
        } else {
            lifecycleItem = PauseActivityItem.obtain();
        }
        clientTransaction.setLifecycleStateRequest(lifecycleItem);
        // Schedule transaction.
        mService.getLifecycleManager().scheduleTransaction(clientTransaction);
        ......
        return true;
    }

方法中添加了LaunchActivityItemResumeActivityItem类的对象,并调用了scheduleTransaction()方法。

LaunchActivityItem属于比较复杂的调用逻辑

LaunchActivityItem类为例,我们来看跟踪下调用关系:

public class LaunchActivityItem extends ClientTransactionItem {
    @Override
    public void execute(ClientTransactionHandler client, IBinder token,
            PendingTransactionActions pendingActions) {
        ......
        client.handleLaunchActivity(r, pendingActions, null /* customIntent */);
        ......
    }
}

调用的是ActivityThreadhandleLaunchActivity()的方法:

    public Activity handleLaunchActivity(ActivityClientRecord r,
            PendingTransactionActions pendingActions, Intent customIntent) {
        ......
        final Activity a = performLaunchActivity(r, customIntent);
        ......
        return a;
    }
    private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
        ......
        Activity activity = null;
        try {
            java.lang.ClassLoader cl = appContext.getClassLoader();
            activity = mInstrumentation.newActivity(cl, component.getClassName(), r.intent);
            ......
        } catch (Exception e) {
            ...
        }
        try {
            ......
            if (activity != null) {
                ......
                activity.mCalled = false;
                if (r.isPersistable()) {
                    mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState);
                } else {
                    mInstrumentation.callActivityOnCreate(activity, r.state);
                }
                if (!activity.mCalled) {
                    throw new SuperNotCalledException(
                        "Activity " + r.intent.getComponent().toShortString() +
                        " did not call through to super.onCreate()");
                }
                r.activity = activity;
            }
            // 将状态设置为 ON_CREATE
            r.setState(ON_CREATE);
        } catch (SuperNotCalledException e) {
            throw e;
        } catch (Exception e) {
            ......
        }
        return activity;
    }

调用的是Instrumentation.callActivityOnCreate()方法,内容如下:

    public void callActivityOnCreate(Activity activity, Bundle icicle) {
        prePerformCreate(activity);
        activity.performCreate(icicle);
        postPerformCreate(activity);
    }

最后通过是调用的Activity.performCreate()方法:

    final void performCreate(Bundle icicle, PersistableBundle persistentState) {
        ......
        if (persistentState != null) {
            onCreate(icicle, persistentState);
        } else {
            onCreate(icicle);
        }
        ......
    }

到这里,LaunchActivityItem的逻辑就结束了,也执行完了onCreate()回调,状态设置为了ON_CREATE

但是由于realStartActivityLocked()中设置的最终状态为ON_RESUME,当前Activity的状态不是最终状态,所以TransactionExecutor还会继续执行。

你可能感兴趣的:(深入Android系统,android,Activity,startActivty,Instrumentation,AMS)