"singleTask"模式 切換到新的棧中
本文截取了網絡資源的結論部分 對singletask 啟動模式做筆記記錄。
盡管SubActivity的launchMode被設置為"singleTask"模式,可是它並不像官方文檔描寫敘述的一樣:The system creates a new task and instantiates the activity at the root of the new task。而是在跟它有同樣taskAffinity的任務中啟動。而且位於這個任務的堆棧頂端,於是。前面那個圖中,就會出現一個帶著"singleTask"標簽的箭頭指向一個任務堆棧頂端的Activity Y了。
那麽,我們有沒有辦法讓一個"singleTask"的Activity在新的任務中啟動呢?答案是肯定的。從上面的代碼分析中,僅僅要我們可以進入函數startActivityUncheckedLocked的這個if語句中: [java]- if (r.resultTo == null && !addingToTask
- && (launchFlags&Intent.FLAG_ACTIVITY_NEW_TASK) != 0) {
- // todo: should do better management of integers.
- mService.mCurTask++;
- if (mService.mCurTask <= 0) {
- mService.mCurTask = 1;
- }
- r.task = new TaskRecord(mService.mCurTask, r.info, intent,
- (r.info.flags&ActivityInfo.FLAG_CLEAR_TASK_ON_LAUNCH) != 0);
- if (DEBUG_TASKS) Slog.v(TAG, "Starting new activity " + r
- + " in new task " + r.task);
- newTask = true;
- if (mMainStack) {
- mService.addRecentTaskLocked(r.task);
- }
- }
我們能夠略微改動一下上面的AndroidManifest.xml配置文件來做一下這個實驗:
[java] view plaincopy- <?xml version="1.0" encoding="utf-8"?
>
- <manifest xmlns:android="http://schemas.android.com/apk/res/android"
- package="shy.luo.task"
- android:versionCode="1"
- android:versionName="1.0">
- <application android:icon="@drawable/icon" android:label="@string/app_name">
- <activity android:name=".MainActivity"
- android:label="@string/app_name"
- android:taskAffinity="shy.luo.task.main.activity">
- <intent-filter>
- <action android:name="android.intent.action.MAIN" />
- <category android:name="android.intent.category.LAUNCHER" />
- </intent-filter>
- </activity>
- <activity android:name=".SubActivity"
- android:label="@string/sub_activity"
- android:launchMode="singleTask"
- android:taskAffinity="shy.luo.task.sub.activity">
- <intent-filter>
- <action android:name="shy.luo.task.subactivity"/>
- <category android:name="android.intent.category.DEFAULT"/>
- </intent-filter>
- </activity>
- </application>
- </manifest>
又一次編譯一下程序。在模擬器上把這個應用程序再次跑起來。用“adb shell dumpsys activity”命令再來查看一下系統執行的的任務,就會看到:
- Running activities (most recent first):
- TaskRecord{4069c020 #4 A shy.luo.task.sub.activity}
- Run #2: HistoryRecord{40725040 shy.luo.task/.SubActivity}
- TaskRecord{40695220 #3 A shy.luo.task.main.activity}
- Run #1: HistoryRecord{406b26b8 shy.luo.task/.MainActivity}
- TaskRecord{40599c90 #2 A com.android.launcher}
- Run #0: HistoryRecord{40646628 com.android.launcher/com.android.launcher2.Launcher}
至此,我們總結一下,設置了"singleTask"啟動模式的Activity的特點:
1. 設置了"singleTask"啟動模式的Activity,它在啟動的時候,會先在系統中查找屬性值affinity等於它的屬性值taskAffinity的任務存在。假設存在這種任務,它就會在這個任務中啟動。否則就會在新任務中啟動。因此。假設我們想要設置了"singleTask"啟動模式的Activity在新的任務中啟動。就要為它設置一個獨立的taskAffinity屬性值。
2. 假設設置了"singleTask"啟動模式的Activity不是在新的任務中啟動時,它會在已有的任務中查看是否已經存在對應的Activity實例。假設存在,就會把位於這個Activity實例上面的Activity所有結束掉,即終於這個Activity實例會位於任務的堆棧頂端中。
"singleTask"模式 切換到新的棧中