1. 应用进程启动 Activity
当应用中的某个 Activity
调用 startActivity
方法时,实际上是通过 ContextImpl
类中的 startActivity
方法发起的。
public class ContextImpl extends Context {@Overridepublic void startActivity(Intent intent) {// 调用 Instrumentation 的 startActivity 方法mInstrumentation.execStartActivity(getOuterContext(), mMainThread.getApplicationThread(), null,(Activity) null, intent, -1, null);}
}
2. 通过 Instrumentation
发起请求
ContextImpl
会调用 Instrumentation
类中的 execStartActivity
方法来处理启动请求。
public class Instrumentation {public ActivityResult execStartActivity(
Context who, IBinder contextThread, IBinder token, Activity target,
Intent intent, int requestCode, Bundle options) {IApplicationThread appThread = (IApplicationThread) contextThread;// 通过 Binder 调用 AMS(ActivityTaskManagerService)int result = ActivityTaskManager.getService().startActivity(appThread, who.getBasePackageName(), intent,intent.resolveTypeIfNeeded(who.getContentResolver()),token, target != null ? target.mEmbeddedID : null,requestCode, 0, null, options);return new ActivityResult(result, null);}
}
3. 跨进程通信到 ActivityTaskManagerService
(ATMS)
startActivity
请求通过 Binder
机制传递给系统服务进程中的 ActivityTaskManagerService
(ATMS)。ATMS 是运行在 SystemServer 进程中的一个服务,负责管理所有应用的 Activity
生命周期和任务栈。
ATMS 处理启动请求
在 ATMS 中,启动 Activity
的逻辑主要由 ActivityStarter
类处理。它会解析 Intent
并根据启动模式(如 singleTask
、singleInstance
等)决定如何启动或复用 Activity
。
public class ActivityStarter {public int startActivityMayWait(IApplicationThread caller, String callingPackage, Intent intent,
String resolvedType, IBinder resultTo, String resultWho, int requestCode,
int flags, ProfilerInfo profilerInfo, Bundle options) {// 解析 Intent 和启动模式TaskRecord task = findTaskForActivity(intent.getComponent());if (task != null && isSingleTaskMode(intent)) {// 如果任务栈已存在且是 singleTask 模式bringTaskToFront(task);return START_TASK_TO_FRONT;} else {// 创建新的任务栈并启动 ActivityTaskRecord newTask = createNewTask(intent);startNewActivity(newTask, intent);return START_SUCCESS;}}private boolean isSingleTaskMode(Intent intent) {// 判断是否是 singleTask 模式return intent.getComponent().getLaunchMode() == ActivityInfo.LAUNCH_SINGLE_TASK;}private TaskRecord findTaskForActivity(ComponentName componentName) {// 查找包含指定 Activity 的任务栈for (TaskRecord task : mTaskStacks) {if (task.containsActivity(componentName)) {return task;}}return null;}private void bringTaskToFront(TaskRecord task) {// 将任务栈置于前台,并清理位于目标 Activity 之上的所有 ActivitymoveTaskToFront(task);}private void moveTaskToFront(TaskRecord task) {// 将任务栈置于前台mTaskStacks.remove(task);mTaskStacks.add(task); // 或者使用特定的方法将任务栈置于前台}private TaskRecord createNewTask(Intent intent) {// 创建新的任务栈TaskRecord newTask = new TaskRecord();// 设置任务栈属性return newTask;}private void startNewActivity(TaskRecord task, Intent intent) {// 启动新的 Activity 并将其添加到任务栈中ActivityRecord activityRecord = new ActivityRecord(intent);task.addActivity(activityRecord);}
}
4. 通知客户端启动 Activity
一旦 ATMS 决定了如何启动或复用 Activity
,它会通过 ApplicationThread
通知客户端应用启动新的 Activity
。这个过程涉及到 Binder
调用,具体是通过 IApplicationThread
接口进行的。
public interface IApplicationThread {void scheduleLaunchActivity(Intent intent, IBinder token, int ident,
ActivityInfo info, Configuration curConfig, CompatibilityInfo compatInfo,
String referrer, IVoiceInteractor voiceInteractor, int procState, Bundle state,
PersistableBundle persistentState, List<ResultInfo> pendingResults,
List<ReferrerIntent> pendingNewIntents, boolean notResumed, boolean isForward,
ProfilerInfo profilerInfo);
}
5. 客户端应用处理启动请求
在客户端应用进程中,ApplicationThread
实现了 IApplicationThread
接口,并且在收到 scheduleLaunchActivity
调用后,会将请求转发给 ActivityThread
的 handleLauncherActivity
方法。
public class ActivityThread {final ApplicationThread mAppThread = new ApplicationThread();private class ApplicationThread extends IApplicationThread.Stub {@Overridepublic void scheduleLaunchActivity(Intent intent, IBinder token, int ident,
ActivityInfo info, Configuration curConfig, CompatibilityInfo compatInfo,
String referrer, IVoiceInteractor voiceInteractor, int procState, Bundle state,
PersistableBundle persistentState, List<ResultInfo> pendingResults,
List<ReferrerIntent> pendingNewIntents, boolean notResumed, boolean isForward,
ProfilerInfo profilerInfo) {sendMessage(H.LAUNCH_ACTIVITY, new ActivityClientRecord(r, data));}}private void handleLauncherActivity(ActivityClientRecord r) {// 创建并启动 ActivityClientTransaction transaction = ClientTransaction.obtain(applicationThread, r.token);transaction.addCallback(LaunchActivityItem.obtain(r.intent, r.info,new Configuration(), r.compatInfo, r.referrer, r.voiceInteractor, windowIsFloating,r.config, r.overrideConfig, r.pendingResults, r.pendingNewIntents,mLastNonConfigurationInstances, r.isForward, profilerInfo));executeTransaction(transaction);}private void executeTransaction(ClientTransaction transaction) {// 执行事务,包括创建和启动 ActivityActivity activity = performLaunchActivity(transaction.getActivityClientRecord());if (activity != null) {performResumeActivity(transaction.getActivityClientRecord());}}private Activity performLaunchActivity(ActivityClientRecord r) {// 创建 Activity 实例Activity activity = null;try {java.lang.ClassLoader cl = appContext.getClassLoader();activity = mInstrumentation.newActivity(cl, component.getClassName(), r.intent);...activity.attach(appContext, this, getInstrumentation(), r.token,r.ident, app, r.intent, r.activityInfo, title, r.parent,r.embeddedID, r.lastNonConfigurationInstances, config,r.referrer, r.voiceInteractor);...if (r.state != null || r.persistentState != null) {mInstrumentation.callActivityOnRestoreInstanceState(activity, r.state,r.persistentState);}activity.mCalled = false;mInstrumentation.callActivityOnCreate(activity, r.state);...return activity;} catch (Exception e) {...}}
}
关键点解释
-
跨进程通信:
- 客户端通过
Binder
调用ActivityTaskManagerService
(ATMS)的方法来启动Activity
。 ATMS
处理任务栈和ActivityRecord
,决定如何启动或复用Activity
。
- 客户端通过
-
任务栈管理:
ActivityTaskManagerService
使用ActivityStarter
类来解析Intent
并根据启动模式决定如何启动或复用Activity
。- 如果需要启动新的
Activity
,则将其添加到适当的任务栈中;如果需要复用现有实例,则调整任务栈以确保该实例位于栈顶。
-
通知客户端:
ActivityTaskManagerService
通过ApplicationThread
通知客户端应用启动新的Activity
。ApplicationThread
实现了IApplicationThread
接口,并在收到scheduleLaunchActivity
调用后,将请求转发给ActivityThread
的handleLauncherActivity
方法。
-
启动
Activity
:- 在客户端应用进程中,
ActivityThread
的handleLauncherActivity
方法负责创建并启动Activity
实例。 performLaunchActivity
方法用于创建Activity
实例,并调用其生命周期方法(如onCreate
、onStart
等)。
- 在客户端应用进程中,
总结
以下是经过整理后的完整流程:
-
应用进程启动
Activity
:- 应用中的某个
Activity
调用startActivity
方法,实际通过ContextImpl
类中的startActivity
方法发起请求。
- 应用中的某个
-
通过
Instrumentation
发起请求:ContextImpl
调用Instrumentation
类中的execStartActivity
方法来处理启动请求。
-
跨进程通信到
ActivityTaskManagerService
(ATMS):startActivity
请求通过Binder
机制传递给系统服务进程中的ActivityTaskManagerService
(ATMS)。- ATMS 解析
Intent
并根据启动模式决定如何启动或复用Activity
。
-
通知客户端启动
Activity
:- ATMS 通过
ApplicationThread
通知客户端应用启动新的Activity
。 ApplicationThread
实现了IApplicationThread
接口,并在收到scheduleLaunchActivity
调用后,将请求转发给ActivityThread
的handleLauncherActivity
方法。
- ATMS 通过
-
客户端应用处理启动请求:
- 在客户端应用进程中,
ActivityThread
的handleLauncherActivity
方法负责创建并启动Activity
实例。 performLaunchActivity
方法用于创建Activity
实例,并调用其生命周期方法(如onCreate
、onStart
等)。
- 在客户端应用进程中,
通过这一系列步骤,Android 系统能够高效地管理和调度 Activity
的生命周期,确保应用的正常运行。希望这个详细的流程描述能帮助你更好地理解 Activity
启动的过程。