API版本 23
本例從Launcher 啟動(dòng)一個(gè) 應(yīng)用開(kāi)始分析
# Activity.startActivityForResult
public void startActivityForResult(@RequiresPermission Intent intent, int requestCode,
@Nullable Bundle options) {
if (mParent == null) {
options = transferSpringboardActivityOptions(options);
// 調(diào)用 Instrumentation.execStartActivity()
Instrumentation.ActivityResult ar =
mInstrumentation.execStartActivity(
this, mMainThread.getApplicationThread(), mToken, this,
intent, requestCode, options);
//...
} else {
//...
}
}
- mMaintThread -> 類(lèi)型為 ActivityThread, 每個(gè)進(jìn)程都有一份
- mToken -> 類(lèi)型為 IBinder, 指向 ActivityRecord 的 Binder 本地對(duì)象. 每一個(gè)已經(jīng)啟動(dòng)的 Activity 組件在 ActivityManagerService(以下簡(jiǎn)稱(chēng)ASM) 中都有一個(gè)對(duì)應(yīng)的 ActivityRecord 對(duì)象, 用來(lái)維護(hù)對(duì)應(yīng)的 Activity 組件的運(yùn)行狀態(tài)及信息.
- ActivityRecord 為重要變量, 可以把他認(rèn)為是 Activity 即可.
略過(guò)中間部分, 直接來(lái)到 ActivityStackSupervisor.startActivityMayWait 方法, Binder通信, 不是本文重點(diǎn).
ActivityStackSupervisor 整個(gè)系統(tǒng)中只有一個(gè), 可以認(rèn)為是管理全局 Activity 組件的類(lèi)就可以.
# ActivityStackSupervisor.startActivityMayWait
final int startActivityMayWait(IApplicationThread caller, int callingUid,
String callingPackage, Intent intent, String resolvedType,
IVoiceInteractionSession voiceSession, IVoiceInteractor
voiceInteractor,
IBinder resultTo, String resultWho, int requestCode, int
startFlags, ProfilerInfo profilerInfo, WaitResult
outResult, Configuration config,
Bundle options, boolean ignoreTargetSecurity, int userId,
IActivityContainer iContainer, TaskRecord inTask) {
// 是否指明了 Component, 可以省去 Intent匹配搜索
boolean componentSpecified = intent.getComponent() != null;
// 查詢(xún)滿足條件的 Activity, 和 PKMS 交互
ActivityInfo aInfo =
resolveActivity(intent, resolvedType, startFlags, profilerInfo, userId);
synchronized (mService) {
// 獲取調(diào)用者的 pid, 和 uid
final int realCallingPid = Binder.getCallingPid();
final int realCallingUid = Binder.getCallingUid();
// ...
final ActivityStack stack;
if (container == null || container.mStack.isOnHomeDisplay()) {
stack = mFocusedStack;
} else {
stack = container.mStack;
}
int res = startActivityLocked(caller, intent, resolvedType, aInfo,
voiceSession, voiceInteractor, resultTo, resultWho,
requestCode, callingPid, callingUid, callingPackage,
realCallingPid, realCallingUid, startFlags, options,
ignoreTargetSecurity, componentSpecified, null,
container, inTask);
//...
return res;
}
}
- 根據(jù)安裝后的信息, 查詢(xún) Activity 信息.
# ActivityStackSupervisor. startActivityLocked
final int startActivityLocked(IApplicationThread caller,
Intent intent, String resolvedType, ActivityInfo aInfo,
IVoiceInteractionSession voiceSession, IVoiceInteractor
voiceInteractor, IBinder resultTo, String resultWho, int
requestCode, int callingPid, int callingUid, String
callingPackage, int realCallingPid, int realCallingUid, int
startFlags, Bundle options, boolean ignoreTargetSecurity,
boolean componentSpecified, ActivityRecord[] outActivity,
ActivityContainer container, TaskRecord inTask) {
// caller 調(diào)用者即Launcher ApplicationThreadProxy
// aInfo 即將啟動(dòng)的Activity信息
// resultTo 調(diào)用者的 ActivityRecord$Token
int err = ActivityManager.START_SUCCESS;
// 第一步
ProcessRecord callerApp = null;
if (caller != null) {
// 根據(jù)caller 獲取調(diào)用者進(jìn)程信息即Launcher進(jìn)程信息
callerApp = mService.getRecordForAppLocked(caller);
if (callerApp != null) {
// 得到這個(gè)調(diào)用者的 pid 和 uid.
callingPid = callerApp.pid;
callingUid = callerApp.info.uid;
} else {
err = ActivityManager.START_PERMISSION_DENIED;
}
}
//...
// 描述調(diào)用者 Activity即Launcher
ActivityRecord sourceRecord = null;
// 描述接收調(diào)用結(jié)果的 Activity, 本例不接收結(jié)果
ActivityRecord resultRecord = null;
if (resultTo != null) {
// 根據(jù) resultTo 獲取 Launcher的ActivityRecord
sourceRecord = mSupervisor.isInAnyStackLocked(resultTo);
if (sourceRecord != null) {
// requestCode 默認(rèn)傳入 -1, 所以這里 resultRecord 為空
if (requestCode >= 0 && !sourceRecord.finishing) {
resultRecord = sourceRecord;
}
}
}
final int launchFlags = intent.getFlags();
if ((launchFlags & Intent.FLAG_ACTIVITY_FORWARD_RESULT) != 0 && sourceRecord != null) {
// 如果存在這個(gè)標(biāo)志位FLAG_ACTIVITY_FORWARD_RESULT,
// 那么就需要修改 接受調(diào)用結(jié)果的Activity, resultRecord, 與本例無(wú)關(guān)
}
// 一堆跳轉(zhuǎn)驗(yàn)證, 不能解析Intent, 沒(méi)找到Activity, 等等
if (err != ActivityManager.START_SUCCESS) {
// 如果中間出錯(cuò), 并且接收結(jié)果的 resultRecord 不為空, 返回RESULT_CANCELED
if (resultRecord != null) {
resultStack.sendActivityResultLocked(-1,
resultRecord, resultWho, requestCode,
Activity.RESULT_CANCELED, null);
}
ActivityOptions.abort(options);
return err;
}
//...
// 創(chuàng)建ActivityRecord, 用來(lái)描述即將啟動(dòng)的 Activity
ActivityRecord r = new ActivityRecord(mService, callerApp, callingUid, callingPackage,
intent, resolvedType, aInfo,
mService.mConfiguration, resultRecord,
resultWho, requestCode, componentSpecified,
voiceSession != null, mSupervisor, container,
options, sourceRecord);
//...
err = startActivityUnchecked(r, sourceRecord, voiceSession, voiceInteractor, startFlags, true, options, inTask);
//...
return err;
}
- 每個(gè)應(yīng)用程序的進(jìn)程都使用一個(gè) ProcessRecord 來(lái)描述, 并且保存在 AMS 內(nèi)部.
- 權(quán)限驗(yàn)證, 解析 intent 后是否找到了對(duì)應(yīng)的 Activity
- 創(chuàng)建了即將啟動(dòng)頁(yè)面的 ActivityRecord 對(duì)象
中間略過(guò)了比較多的步驟, 例如啟動(dòng) pendingActivity 集合中的 Activity , 是否允許切換App等等. 我們只走主線, 后面代碼可能連 ... 也不會(huì)標(biāo)出來(lái)了.
# ActivityStackSupervisor.startActivityUnchecked
final int startActivityUncheckedLocked(final ActivityRecord r,
ActivityRecord sourceRecord,
IVoiceInteractionSession voiceSession,
IVoiceInteractor voiceInteractor, int startFlags,
boolean doResume, Bundle options,
TaskRecord inTask) {
// r 描述即將啟動(dòng)的 ActivityRecord
// sourceRecord 描述調(diào)用者的 ActivityRecord
// doResume true
// 處理啟動(dòng)模式
final boolean launchSingleTop = r.launchMode == ActivityInfo.LAUNCH_SINGLE_TOP;
final boolean launchSingleInstance = r.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE;
final boolean launchSingleTask = r.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK;
// 當(dāng)存在結(jié)果接收者并且, 標(biāo)志 FLAG_ACTIVITY_NEW_TASK時(shí), 返回 RESULT_CANCELED
if (r.resultTo != null && (launchFlags & Intent.FLAG_ACTIVITY_NEW_TASK) != 0
&& r.resultTo.task.stack != null) {
r.resultTo.task.stack.sendActivityResultLocked(-1, r.resultTo, r.resultWho,
r.requestCode,
Activity.RESULT_CANCELED, null);
r.resultTo = null;
}
boolean addingToTask = false;
TaskRecord reuseTask = null;
// 根據(jù)啟動(dòng)模式標(biāo)志 FLAG_ACTIVITY_NEW_TASK
if (inTask == null) {
if (sourceRecord == null) {
//...
} else if (sourceRecord.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) {
launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK;
} else if (launchSingleInstance || launchSingleTask) {
launchFlags |= Intent.FLAG_ACTIVITY_NEW_TASK;
}
}
ActivityInfo newTaskInfo = null;
Intent newTaskIntent = null;
ActivityStack sourceStack;
boolean movedHome = false;
ActivityStack targetStack;
intent.setFlags(launchFlags);
if (((launchFlags & Intent.FLAG_ACTIVITY_NEW_TASK) != 0 &&
(launchFlags & Intent.FLAG_ACTIVITY_MULTIPLE_TASK) == 0)
|| launchSingleInstance || launchSingleTask) {
// ...
// 根據(jù)flag判斷啟動(dòng)模式, 另開(kāi)文章討論
}
// 上面一堆 flag 判斷, 是為了決定 Activity 該存放在哪個(gè)棧里
if (r.packageName != null) {
// 原焦點(diǎn)Stack, 本例為表示桌面的 ActivityStack
ActivityStack topStack = mFocusedStack;
// 正在頂部運(yùn)行的 Activity 即 Launcher
ActivityRecord top = topStack.topRunningNonDelayedActivityLocked(notTop);
// 如果正在啟動(dòng)的活動(dòng)與當(dāng)前位于頂部的活動(dòng)相同,考慮 singleTop
if (top != null && r.resultTo == null) {
if (top.realActivity.equals(r.realActivity) && top.userId == r.userId) {
// ...
// 處理singleTop
}
}
}
boolean newTask = false;
boolean keepCurTransition = false;
TaskRecord taskToAffiliate = launchTaskBehind && sourceRecord != null ?
sourceRecord.task : null;
if (r.resultTo == null && inTask == null && !addingToTask
&& (launchFlags & Intent.FLAG_ACTIVITY_NEW_TASK) != 0) {
newTask = true;
// 獲取ActivityStack, 如果沒(méi)有就創(chuàng)建
targetStack = computeStackFocus(r, newTask);
// 將targetStack 移至頂部,
// mFocusedStack賦值為targetStack, 變更了焦點(diǎn)Stack
// mLastFocusedStack賦值為原 ActivityStack
targetStack.moveToFront("startingNewTask");
// 給即將啟動(dòng)的ActivityRecord, 設(shè)置TaskRecord
if (reuseTask == null) {
// createTaskRecord() 會(huì)創(chuàng)建TaskRecord
// 并添加到 targetStack 中的 mTaskHistory中
r.setTask(targetStack.createTaskRecord(getNextTaskId(),
newTaskInfo != null ? newTaskInfo
r.info, newTaskIntent != null ?
newTaskIntent : intent,
voiceSession, voiceInteractor,
!launchTaskBehind /* toTop */),
taskToAffiliate);
} else {
r.setTask(reuseTask, taskToAffiliate);
}
}
// mLastPausedActivity 置空
targetStack.mLastPausedActivity = null;
targetStack.startActivityLocked(r, newTask, doResume, keepCurTransition, options);
}
- TaskRecord 表示棧, 它里面保存了在該棧中保存的 Activity 集合.
- ActivityStack 用于管理 TaskRecord , 一般情況下只有表示桌面的 ActivityStack , 和應(yīng)用程序的 ActivityStack, 多屏幕狀態(tài)下可能會(huì)不一樣, 沒(méi)有驗(yàn)證.
桌面的 ActivityStack 存有兩個(gè) TaskRecord , 分別存著 Launcher 和 RecentActivity
ActivityStack , TaskRecord , ActivityRecord 三者的關(guān)系如圖:
- 上面的代碼用一句話概括就是, 根據(jù)配置判斷是否要新建棧 .
# ActivityStack.startActivityLocked
final void startActivityLocked(ActivityRecord r, boolean newTask,
boolean keepCurTransition, ActivityOptions options) {
TaskRecord rTask = r.task;
final int taskId = rTask.taskId;
TaskRecord task = null;
if (!newTask) {
// 如果不是新建Task棧, 則找到合適的棧
}
task = r.task;
// 將要啟動(dòng)的ActivityRecord 添加到TastRecord.mActivityes 集合的最尾部
task.addActivityToTop(r);
// 添加了新的Activity, 所以需要給 ActivityRecord的變量frontOfTask重新賦值
// 該變量在后面會(huì)用到, 表示是否是 TaskRecord集合中第一個(gè)元素, 也就是根元素
task.task.setFrontOfTask();
//...
// 上面?zhèn)鬟^(guò)來(lái) true
if (doResume) {
mStackSupervisor.resumeTopActivitiesLocked(this, r, options);
}
}
- 找到合適的棧, 并且置頂
跳過(guò)兩個(gè)簡(jiǎn)單方法, 直接定位到下面方法
# ActivityStack.resumeTopActivityLocked
private boolean resumeTopActivityInnerLocked(ActivityRecord prev, Bundle options) {
// prev, 即將啟動(dòng)的ActivityRecord
// (只限于該步驟, 多處調(diào)用該方法, 那時(shí)的prev意義不一樣)
// 獲取該ActivityStack, TaskRecord集合中最后一個(gè)元素
// TaskRecord中 Activity集合中最后一個(gè)非finishing的 ActivityRecord
// 因?yàn)樵谏厦娣治鲋? TaskRecord已經(jīng)添加到 mTaskHistory的尾部, 并且
// ActivityRecord 也添加到對(duì)應(yīng)的 TaskRecord當(dāng)中, 所以這里 next 等同于prev
final ActivityRecord next = topRunningActivityLocked(null);
final TaskRecord prevTask = prev != null ? prev.task : null;
next.delayedResume = false;
if (mResumedActivity == next && next.state == ActivityState.RESUMED &&
mStackSupervisor.allResumedActivitiesComplete()) {
// 如果頂部Activity狀態(tài)為RESUMED, 返回
return false;
}
mStackSupervisor.mStoppingActivities.remove(next);
mStackSupervisor.mGoingToSleepActivities.remove(next);
next.sleeping = false;
mStackSupervisor.mWaitingVisibleActivities.remove(next);
//...
// 是否等待 pause
// FLAG_RESUME_WHILE_PAUSING, 這個(gè)標(biāo)志位可以不等待 PAUSE, 進(jìn)行 RESUME
// 我們討論一般情況, 該變量為 false
boolean dontWaitForPause = (next.info.flags&ActivityInfo.FLAG_RESUME_WHILE_PAUSING) != 0;
// 從名字中可以看出, 對(duì)backStack執(zhí)行Pause
// backStack指的是非FocusStack, 因?yàn)樯厦嬉呀?jīng)將焦點(diǎn)Stack變更了
// 這里backstack指的是桌面的ActivitStack
boolean pausing = mStackSupervisor.pauseBackStacks(userLeaving, true, dontWaitForPause);
// mResumedActivity是當(dāng)前ActivityStack的成員變量
// 在本次例中, 新建了ActivityStack, 所以mResumedActivity為空
if (mResumedActivity != null) {
pausing |= startPausingLocked(userLeaving, false, true, dontWaitForPause);
}
// 上面對(duì)兩個(gè)ActivityStack只要有一個(gè)成功執(zhí)行了pause, 那么這里直接返回
// 并且整個(gè)系統(tǒng)進(jìn)程調(diào)用完畢, Launcher進(jìn)程被掛起的線程恢復(fù)
if (pausing) {
// ...
return true;
}
//************重要的分割線************
// 其實(shí)下面有很重要的方法, 但是因?yàn)樯厦嬉呀?jīng)返回了.
// 所以下面暫時(shí)就不用管, 待會(huì)會(huì)執(zhí)行到下面的代碼
// ...
}
- 找到 Resume 狀態(tài)的 Activity 即 Launcher .
- 找到后調(diào)用 ActivityStack.startPausingLocked
看一下兩個(gè)決定 pausing 變量的兩個(gè)函數(shù)
# ActivityStackSupervisor.startPausingLocked
boolean pauseBackStacks(boolean userLeaving, boolean resuming, boolean dontWait) {
boolean someActivityPaused = false;
for (int displayNdx = mActivityDisplays.size() - 1; displayNdx >= 0; --displayNdx) {
ArrayList<ActivityStack> stacks = mActivityDisplays.valueAt(displayNdx).mStacks;
for (int stackNdx = stacks.size() - 1; stackNdx >= 0; --stackNdx) {
final ActivityStack stack = stacks.get(stackNdx);
// isFrontStack() 判斷是否是焦點(diǎn)Stack
if (!isFrontStack(stack) && stack.mResumedActivity != null) {
// 本例中Launcher點(diǎn)擊圖標(biāo), 進(jìn)入應(yīng)用
// Launcher處在的ActivityStack為backStack
// mResumedActivity 為 Launcher
// 調(diào)用 startPausingLocked
someActivityPaused |= stack.startPausingLocked(userLeaving, false,
resuming, dontWait);
}
}
}
return someActivityPaused;
}
# ActivityStack.startPausingLocked
final boolean startPausingLocked(boolean userLeaving, boolean uiSleeping,
boolean resuming, boolean dontWait) {
//...
// 表示 Launcher
ActivityRecord prev = mResumedActivity;
// 將mResumedActivity置空
mResumedActivity = null;
mPausingActivity = prev;
mLastPausedActivity = prev;
// 狀態(tài)變更為 PAUSING
prev.state = ActivityState.PAUSING;
// 返回即將啟動(dòng)的ActivityRecord
final ActivityRecord next = mStackSupervisor.topRunningActivityLocked();
if (prev.app != null && prev.app.thread != null) {
// 查詢(xún) LauncherActivity是否存在
// 走到應(yīng)用進(jìn)程調(diào)用Pause方法
// 在 handlePauseActivity() 中, 在返回到系統(tǒng)進(jìn)程
// 調(diào)用 activityPaused() **重點(diǎn)**
prev.app.thread.schedulePauseActivity(prev.appToken, prev.finishing,
userLeaving, prev.configChangeFlags,
dontWait);
} else {
mPausingActivity = null;
mLastPausedActivity = null;
mLastNoHistoryActivity = null;
}
if (mPausingActivity != null) {
if (dontWait) {
// 特殊標(biāo)志位, 不等待Pause執(zhí)行Resume, 不討論
completePauseLocked(false);
return false;
} else {
// 走到這個(gè)分支
Message msg = mHandler.obtainMessage(PAUSE_TIMEOUT_MSG);
msg.obj = prev;
prev.pauseTime = SystemClock.uptimeMillis();
// 在ServiceThread中執(zhí)行 activityPausedLocked **重點(diǎn)**
mHandler.sendMessageDelayed(msg, PAUSE_TIMEOUT); // 500ms
return true;
}
} else {
return false;
}
}
mResumedActivity 置空, 所以現(xiàn)在系統(tǒng)中是沒(méi)有正在 RESUME 的 Activity , 所以如果下次進(jìn)入 resumeTopActivityInnerLocked , 因?yàn)闆](méi)有要 PAUSE 的 Activity , 所以不會(huì)返回 .
-
以下兩個(gè)方法最終會(huì)掉用同一個(gè)方法.
- ActivityThread.schedulePauseActivity
- 系統(tǒng)進(jìn)程中給 ServiceThread 發(fā)送了 PAUSE_TIMEOUT_MSG 消息
# ActivityThread. handlePauseActivity
private void handlePauseActivity(IBinder token, boolean finished,
boolean userLeaving, int configChanges, boolean dontReport) {
ActivityClientRecord r = mActivities.get(token);
if (r != null) {
if (userLeaving) {
performUserLeavingActivity(r);
}
// 調(diào)用 Activity 的 onPause() 方法
performPauseActivity(token, finished, r.isPreHoneycomb());
// Tell the activity manager we have paused.
if (!dontReport) {
try {
// 調(diào)用 AMS 的 activityPaused()
ActivityManagerNative.getDefault().activityPaused(token);
} catch (RemoteException ex) {
}
}
mSomeActivitiesChanged = true;
}
}
- 執(zhí)行了 Launcher 的 onPause 后, 緊接著回調(diào)給 AMS , AMS.activityPaused() -> ActivityStack.activityPausedLocked(),
接下來(lái)在看在系統(tǒng)進(jìn)程發(fā)送的 PAUSE_TIMEOUT_MSG 消息.
# ActivityStackHandler.handleMessage
public void handleMessage(Message msg) {
//...
case PAUSE_TIMEOUT_MSG: {
ActivityRecord r = (ActivityRecord)msg.obj;
synchronized (mService) {
// 同樣調(diào)用了, activityPausedLocked, 但是在發(fā)送該消息時(shí)是延遲了500秒
activityPausedLocked(r.appToken, true);
}
} break;
}
- 系統(tǒng)中很多類(lèi)似這種超時(shí)消息, 確保在進(jìn)程通信卡住時(shí), 該方法也能夠正確調(diào)用
# ActivityStack.activityPausedLocked
final void activityPausedLocked(IBinder token, boolean timeout) {
// 本例中Launcher
final ActivityRecord r = isInStackLocked(token);
if (r != null) {
// 移除Handler消息, 有可能是Handler進(jìn)到這,
// 有可能是應(yīng)用進(jìn)程通過(guò)系統(tǒng)進(jìn)程進(jìn)入這里, 不同的是參數(shù)timeout
mHandler.removeMessages(PAUSE_TIMEOUT_MSG, r);
if (mPausingActivity == r) {
// 進(jìn)入該分支
completePauseLocked(true);
} else {
if (r.finishing && r.state == ActivityState.PAUSING) {
finishCurrentActivityLocked(r, FINISH_AFTER_VISIBLE, false);
}
}
}
}
- 這個(gè)函數(shù)沒(méi)什么好講的, 移除了PAUSE_TIMEOUT_MSG消息
# ActivityStack.completePauseLocked
private void completePauseLocked(boolean resumeNext) {
ActivityRecord prev = mPausingActivity;
if (prev != null) {
prev.state = ActivityState.PAUSED;
if (prev.finishing) {
// 立即結(jié)束
prev = finishCurrentActivityLocked(prev, FINISH_AFTER_VISIBLE, false);
} else if (prev.app != null) {
if (prev.configDestroy) {
// ...
} else if (!hasVisibleBehindActivity() || mService.isSleepingOrShuttingDown())
{
// 添加到StoppingActivity集合中, 過(guò)會(huì)會(huì)執(zhí)行onStop
mStackSupervisor.mStoppingActivities.add(prev);
// 如果StoppingActivity集合中已經(jīng)堆積了3個(gè)以上要停止的活動(dòng)
// 或者該Activity是TaskRecord棧中最后一個(gè),
// 發(fā)送IDLE_NOW_MSG消息, 該方法中會(huì)執(zhí)行 onStop, onDestroy等
// 文字最后解析
if (mStackSupervisor.mStoppingActivities.size() > 3 ||
prev.frontOfTask && mTaskHistory.size() <= 1) {
mStackSupervisor.scheduleIdleLocked();
} else {
mStackSupervisor.checkReadyForSleepLocked();
}
}
} else {
prev = null;
}
}
if (resumeNext) {
final ActivityStack topStack = mStackSupervisor.getFocusedStack();
// 繼續(xù)調(diào)用 resumeTopActivitiesLocked
if (!mService.isSleepingOrShuttingDown()) {
mStackSupervisor.resumeTopActivitiesLocked(topStack, prev, null);
} else {
mStackSupervisor.checkReadyForSleepLocked();
ActivityRecord top = topStack.topRunningActivityLocked(null);
if (top == null || (prev != null && top != prev)) {
mStackSupervisor.resumeTopActivitiesLocked(topStack, null, null);
}
}
}
}
- 發(fā)送 IDLE_NOW_MSG 消息后, Launcher 因?yàn)槭菞V形ㄒ灰粋€(gè) Activity , 所以會(huì)執(zhí)行 onStop() , 但這不是重點(diǎn). 最后會(huì)貼上執(zhí)行 onStop() 的代碼.
- 調(diào)用了 resumeTopActivitiesLocked
接著看 resumeTopActivitiesLocked 后半段代碼
private boolean resumeTopActivityInnerLocked(ActivityRecord prev, Bundle options) {
// 要啟動(dòng)的 Activity
final ActivityRecord next = topRunningActivityLocked(null);
//... Transition相關(guān)
// nextActivity是否已經(jīng)存在
if (next.app != null && next.app.thread != null) {
// 本例中Launcher點(diǎn)擊啟動(dòng), 所以不存在, 走另外一個(gè)分支
//...
// 狀態(tài)置位 RESUME
next.state = ActivityState.RESUMED;
mResumedActivity = next;
// 應(yīng)用進(jìn)程觸發(fā) onResume()
// 執(zhí)行后回調(diào)系統(tǒng)進(jìn)程 activityResumed
next.app.thread.scheduleResumeActivity(next.appToken, next.app.repProcState,
mService.isNextTransitionForward(),
resumeAnimOptions);
try{
//...
} catch (Exception e) {
// 這里會(huì)try catch一下, 如果在nextActivity存在的情況下執(zhí)行失敗
// 執(zhí)行 else 時(shí)的方法
mStackSupervisor.startSpecificActivityLocked(next, true, false);
}
} else {
// nextActivity不存在, 需要?jiǎng)?chuàng)建
mStackSupervisor.startSpecificActivityLocked(next, true, true);
}
}
- 判斷要啟動(dòng)的 Activity 是否存在, 如果已經(jīng)存在的情況下, 只需要調(diào)用 onResume() 恢復(fù)頁(yè)面就可以了, 本例走不存在的分支
# ActivityStackSupervisor.startSpecificActivityLocked
void startSpecificActivityLocked(ActivityRecord r,
boolean andResume, boolean checkConfig) {
// 根據(jù) uid 和 processName查詢(xún)是否存在進(jìn)程
// 進(jìn)程沒(méi)有被殺死就能查詢(xún)的到
ProcessRecord app = mService.getProcessRecordLocked(r.processName,
r.info.applicationInfo.uid, true);
if (app != null && app.thread != null) {
// 查詢(xún)到了
try {
if ((r.info.flags&ActivityInfo.FLAG_MULTIPROCESS) == 0
|| !"android".equals(r.info.packageName)) {
// 確保不是框架的一部分
app.addPackage(r.info.packageName, r.info.applicationInfo.versionCode,
mService.mProcessStats);
}
// 通知該進(jìn)程啟動(dòng)目標(biāo)Activity
// 雖然本例不進(jìn)入這個(gè)分支, 但請(qǐng)記住這個(gè)方法
// 創(chuàng)建完成進(jìn)程后依然調(diào)用此方法
realStartActivityLocked(r, app, andResume, checkConfig);
return;
} catch (RemoteException e) {
}
}
// 沒(méi)有查詢(xún)到, 需要?jiǎng)?chuàng)建應(yīng)用進(jìn)程
mService.startProcessLocked(r.processName, r.info.applicationInfo, true, 0,
"activity", r.intent.getComponent(), false, false, true);
}
- 本例中進(jìn)程不存在, 需要?jiǎng)?chuàng)建
新建進(jìn)程暫時(shí)還沒(méi)有了解到, 從 Gityuan 博客的圖中了解一下.
新建進(jìn)程完成后
ActivityThread.main() -> AMS.attachApplication() -> AMS.attachApplicationLocked()
# ActivityManagerService.attachApplicationLocked
private final boolean attachApplicationLocked(IApplicationThread thread,
int pid) {
//...
// 如果此應(yīng)用程序記錄仍附加到先前的進(jìn)程擅编,立即清理它攀细。
if (app.thread != null) {
handleAppDiedLocked(app, true, true);
}
//...
// 創(chuàng)建進(jìn)程時(shí), 發(fā)送了創(chuàng)建進(jìn)程超時(shí)的消息, 移除它
mHandler.removeMessages(PROC_START_TIMEOUT_MSG, app);
// 獲取該進(jìn)程中的 ContentProvider
List<ProviderInfo> providers = normalMode ?
generateApplicationProvidersLocked(app) : null;
// 系統(tǒng)進(jìn)程 -> 應(yīng)用進(jìn)程
// 進(jìn)程初次創(chuàng)建時(shí), 進(jìn)程信息為空,
// 這個(gè)方法將告訴該進(jìn)程具體信息
thread.bindApplication(processName, appInfo, providers, app.instrumentationClass,
profilerInfo, app.instrumentationArguments,
app.instrumentationWatcher,
app.instrumentationUiAutomationConnection, testMode,
enableOpenGlTrace, isRestrictedBackupMode || !normalMode,
app.persistent, new Configuration(mConfiguration), app.compat,
getCommonServicesLocked(app.isolated),
mCoreSettingsObserver.getCoreSettingsLocked());
if (normalMode) {
try {
// 啟動(dòng)Activity
if (mStackSupervisor.attachApplicationLocked(app)) {
didSomething = true;
}
} catch (Exception e) {
badApp = true;
}
}
// 啟動(dòng)Service
if (!badApp) {
try {
didSomething |= mServices.attachApplicationLocked(app, processName);
} catch (Exception e) {
badApp = true;
}
}
// 啟動(dòng)廣播?
if (!badApp && isPendingBroadcastProcessLocked(pid)) {
try {
didSomething |= sendPendingBroadcastsLocked(app);
} catch (Exception e) {
badApp = true;
}
}
// ...
// 出錯(cuò)
if (badApp) {
handleAppDiedLocked(app, false, true);
return false;
}
return true
}
- 這個(gè)方法需要兩個(gè)分支都需要跟進(jìn), thread.bindApplication() 和 mStackSupervisor.attachApplicationLocked(app)
- 對(duì)清單文件中的Service和常駐廣播進(jìn)行處理
# activityThread.handleBindApplication
// AMS調(diào)用bindAppliation, 走到應(yīng)用進(jìn)程發(fā)消息給主線程, 并調(diào)用該方法
private void handleBindApplication(AppBindData data) {
//...
// 設(shè)置進(jìn)程名稱(chēng), 剛創(chuàng)建進(jìn)程時(shí)名字為 <pre_initialized>
Process.setArgV0(data.processName);
//獲取LoadedApk對(duì)象
data.info = getPackageInfoNoCheck(data.appInfo, data.compatInfo);
//...
if (data.instrumentationName != null) {
// 正常情況下為空
} else {
mInstrumentation = new Instrumentation();
}
// 創(chuàng)建Application
// 創(chuàng)建ContextImpl, 并執(zhí)行Application的attachBaseContext,
Application app = data.info.makeApplication(data.restrictedBackupMode, null);
// 安裝本Package中攜帶的ContentProvider
if (!data.restrictedBackupMode) {
List<ProviderInfo> providers = data.providers;
if (providers != null) {
installContentProviders(app, providers);
mH.sendEmptyMessageDelayed(H.ENABLE_JIT, 10*1000);
}
}
// 執(zhí)行Application的 onCreate()
mInstrumentation.callApplicationOnCreate(app);
}
- 創(chuàng)建 Application , 安裝 ContentProvider , Application 的生命周期方法
bindApplication 這條分支走完了.
ActivitySupervisor. attachApplicationLocked
boolean attachApplicationLocked(ProcessRecord app) throws RemoteException {
final String processName = app.processName;
boolean didSomething = false;
// ...
// 找到焦點(diǎn)Stack的棧頂Activity
ActivityRecord hr = stack.topRunningActivityLocked(null);
if (hr != null) {
if (hr.app == null && app.uid == hr.info.applicationInfo.uid
&& processName.equals(hr.processName)) {
try {
// 和上面已經(jīng)存在進(jìn)程情況下一樣的方法
if (realStartActivityLocked(hr, app, true, true)) {
didSomething = true;
}
} catch (RemoteException e) {}
}
}
return didSomething;
}
- 進(jìn)程及進(jìn)程的 Application 創(chuàng)建完畢, 該啟動(dòng)對(duì)應(yīng)的 Activity 了.
# ActivityStackSupervisor.realStartActivityLocked
final boolean realStartActivityLocked(ActivityRecord r,
ProcessRecord app, boolean andResume, boolean checkConfig)
throws RemoteException {
int idx = app.activities.indexOf(r);
if (idx < 0) {
app.activities.add(r);
}
// 系統(tǒng)進(jìn)程 -> 應(yīng)用進(jìn)程
// 調(diào)用 ApplicationThread 的 scheduleLaunchActivity() 方法
// 依次調(diào)用 onCreate, onStart, onResume
app.thread.scheduleLaunchActivity(new Intent(r.intent), r.appToken,
System.identityHashCode(r), r.info, new
Configuration(mService.mConfiguration),
new Configuration(stack.mOverrideConfig), r.compat,
r.launchedFromPackage,
task.voiceInteractor, app.repProcState, r.icicle,
r.persistentState, results,
newIntents, !andResume,
mService.isNextTransitionForward(), profilerInfo);
//...
// 本例中 andResume 為true
if (andResume) {
// 不容忽視的方法
stack.minimalResumeActivityLocked(r);
}
}
- 回到應(yīng)用進(jìn)程調(diào)用, scheduleLaunchActivity 這個(gè)方法會(huì)依次調(diào)用 Activity 的, onCreate , onStart , onResume .
- 還有重要的一點(diǎn)是 stack.minimalResumeActivityLocked(r) 這個(gè)方法不容忽視, 等啟動(dòng)代碼分析完后在分析它.
ApplicationThread.scheduleLaunchActivity -> ActivityThread.handleLaunchActivity
# ActivityThread.handleLaunchActivity
private void handleLaunchActivity(ActivityClientRecord r, Intent customIntent) {
//...
// 創(chuàng)建 Activity, 并調(diào)用 onCreate, onStart
Activity a = performLaunchActivity(r, customIntent);
if (a != null) {
//...
// 調(diào)用 onResume
handleResumeActivity(r.token, false, r.isForward,
!r.activity.mFinished && !r.startsNotResumed);
}
}
# ActivityThread. performLaunchActivity
private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
Application app = r.packageInfo.makeApplication(false, mInstrumentation);
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);
// 這個(gè)變量控制是否調(diào)用了Activity.onCreate(),
// Activity.onCreate()里會(huì)把mCalled賦為true
activity.mCalled = false;
if (r.isPersistable()) {
mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState);
} else {
// 調(diào)用onCreate()
mInstrumentation.callActivityOnCreate(activity, r.state);
}
// 沒(méi)有調(diào)用父類(lèi)的onCreate , 拋異常
if (!activity.mCalled) {
throw new SuperNotCalledException(
"Activity " + r.intent.getComponent().toShortString() +
" did not call through to super.onCreate()");
}
if (!r.activity.mFinished) {
// 調(diào)用 onStart()
activity.performStart();
r.stopped = false;
}
}
# ActivityThread. handleResumeActivity
final void handleResumeActivity(IBinder token,
boolean clearHide, boolean isForward, boolean reallyResume) {
// ...
// 調(diào)用Activity的 onResume 方法
ActivityClientRecord r = performResumeActivity(token, clearHide);
if (r != null) {
// ...
if (!r.onlyLocalRequest) {
r.nextIdle = mNewActivities;
mNewActivities = r;
// 主線發(fā)送閑置消息, ***重要***
Looper.myQueue().addIdleHandler(new Idler());
}
r.onlyLocalRequest = false;
// Tell the activity manager we have resumed.
if (reallyResume) {
try {
// 回調(diào)AMS, resume調(diào)用完畢, 只是修改兩個(gè)變量不探討
ActivityManagerNative.getDefault().activityResumed(token);
} catch (RemoteException ex) {
}
}
}
// ...
}
- Looper.myQueue().addIdleHandler(new Idler()) 先記住該方法
# ActivityStack.minimalResumeActivityLocked
void minimalResumeActivityLocked(ActivityRecord r) {
r.state = ActivityState.RESUMED;
r.stopped = false;
mResumedActivity = r;
r.task.touchActiveTime();
mRecentTasks.addLocked(r.task);
// 看下面
completeResumeLocked(r);
mStackSupervisor.checkReadyForSleepLocked();
setLaunchTime(r);
}
private void completeResumeLocked(ActivityRecord next) {
next.idle = false;
next.results = null;
next.newIntents = null;
// 設(shè)置空閑超時(shí)
// 發(fā)送給 AMS 進(jìn)程的handler一個(gè)空閑超時(shí)的消息
// 在 應(yīng)用進(jìn)程的 Handler在空閑時(shí), 會(huì)調(diào)用 系統(tǒng)進(jìn)程的 activityIdle()
// 在該方法中執(zhí)行 finish或stop等方法, 具體總結(jié)后在摘代碼
mStackSupervisor.scheduleIdleTimeoutLocked(next);
}
至此上面記錄的三個(gè)重要函數(shù)在重新列一下
- 系統(tǒng)進(jìn)程 -> mStackSupervisor.scheduleIdleLocked()
- 應(yīng)用進(jìn)程 -> Looper.myQueue().addIdleHandler(new Idler())
- 系統(tǒng)進(jìn)程 -> mStackSupervisor.scheduleIdleTimeoutLocked(next)
這三個(gè)方法最終都會(huì)調(diào)用 ActivitySupervisor.activityIdleInternalLocked
最后一個(gè)方法會(huì)執(zhí)行延遲10秒發(fā)送, 這種方法在上述代碼中提過(guò)一次
# ActivitySupervisor.activityIdleInternalLocked
final ActivityRecord activityIdleInternalLocked(final IBinder token, boolean fromTimeout,
Configuration config) {
// 要執(zhí)行Stop的集合
ArrayList<ActivityRecord> stops = null;
// 要執(zhí)行Finish的集合
ArrayList<ActivityRecord> finishes = null;
ArrayList<UserState> startingUsers = null;
boolean booting = false;
boolean activityRemoved = false;
ActivityRecord r = ActivityRecord.forTokenLocked(token);
if (r != null) {
// 移除超時(shí)消息
mHandler.removeMessages(IDLE_TIMEOUT_MSG, r);
}
// mStoppingActivities集合中, 將即將可見(jiàn)的Activity除外
stops = processStoppingActivitiesLocked(true);
NS = stops != null ? stops.size() : 0;
if ((NF = mFinishingActivities.size()) > 0) {
finishes = new ArrayList<>(mFinishingActivities);
mFinishingActivities.clear();
}
// Stop any activities that are scheduled to do so but have been
// waiting for the next one to start.
for (int i = 0; i < NS; i++) {
r = stops.get(i);
final ActivityStack stack = r.task.stack;
if (stack != null) {
if (r.finishing) {
// 如果要執(zhí)行 stop的狀態(tài)為finish, 立即結(jié)束
stack.finishCurrentActivityLocked(r, ActivityStack.FINISH_IMMEDIATELY, false);
} else {
// 否則執(zhí)行 stop
stack.stopActivityLocked(r);
}
}
}
// Finish any activities that are scheduled to do so but have been
// waiting for the next one to start.
for (int i = 0; i < NF; i++) {
r = finishes.get(i);
final ActivityStack stack = r.task.stack;
if (stack != null) {
// 如果有要結(jié)束的Activity, 結(jié)束掉
activityRemoved |= stack.destroyActivityLocked(r, true, "finish-idle");
}
}
// 如果有被移除的 Activity, 執(zhí)行resumeTopActivitiesLocked
if (activityRemoved) {
resumeTopActivitiesLocked();
}
return r;
}
至此整個(gè)Activity啟動(dòng)流程結(jié)束了.
需要注意的是 resumeTopActivitiesLocked() , 只要操作 Activity , 就會(huì)有 Pause 的界面和 Resume 的界面, 一般情況下 Resume 會(huì)等待 Pause 完后執(zhí)行 . 所以調(diào)用 resumeTopActivitiesLocked 的地方特別多, 要注意在哪里返回, 在哪里繼續(xù)執(zhí)行 .