このソースコードはAndroid11の分析に基づいています
関連するソースコード:
/frameworks/base/services/core/java/com/android/server/am/ActivityManagerService.java
/frameworks/base/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
/frameworks/base/services/core/java/com/android/server/wm/RootWindowContainer.java
/packages/apps/Launcher3/src/com/android/launcher3/Launcher.java
/packages/apps/Launcher3/src/com/android/launcher3/LauncherModel.java
/packages/apps/Launcher3/src/com/android/launcher3/model/LoaderTask.java
复制代码
前回の記事では、ActivityManagerService(ActivityTaskManagerService)およびPackageManagerServiceシステムサービスがSystemServerプロセスの** startBootstrapServices()およびstartOtherServices()**メソッドで開始されることを説明しました。
- ActivityManagerService:主に4つの主要コンポーネントの作成と管理を担当します。
- PackageManagerService:主に、インストールパッケージのクエリ、インストール、およびアンインストールを担当します。
システムのデスクトッププロセスランチャーは、 ActivityManagerServiceサービスが開始された後に開始されます。
ランチャープロセスが開始します
ActivityManagerService.systemReady
このメソッドは、ランチャープロセスの起動を開始します
public class ActivityManagerService extends IActivityManager.Stub
implements Watchdog.Monitor, BatteryStatsImpl.BatteryCallback {
// mAtmInternal为ActivityTaskManagerService.LocalService类
public ActivityTaskManagerInternal mAtmInternal;
// ActivityManagerService准备完成
public void systemReady(final Runnable goingCallback, @NonNull TimingsTraceAndSlog t) {
// 调用启动Launcher进程
mAtmInternal.startHomeOnAllDisplays(currentUserId, "systemReady");
}
}
public class ActivityTaskManagerService extends IActivityTaskManager.Stub {
RootWindowContainer mRootWindowContainer;
final class LocalService extends ActivityTaskManagerInternal {
@Override
public boolean startHomeOnAllDisplays(int userId, String reason) {
synchronized (mGlobalLock) {
return mRootWindowContainer.startHomeOnAllDisplays(userId, reason);
}
}
}
}
复制代码
- LauncherプロセスはAMSのsystemReadyメソッドで開始されますが、プロセスは実際には開始されていません。これは単なる開始であり
ActivityTaskManagerService.LocalService
、クラスのstartHomeOnAllDisplaysメソッドは引き続き実行されます。 - ActivityTaskManagerServiceには処理はありませんが、
RootWindowContainer.startHomeOnAllDisplays
メソッド処理が呼び出されます。
RootWindowContainer.startHomeOnAllDisplays
メソッドは、一連の呼び出しを通じて最終的に呼び出されますRootWindowContainer.startHomeOnTaskDisplayArea
。
class RootWindowContainer extends WindowContainer<DisplayContent>
implements DisplayManager.DisplayListener {
ActivityTaskManagerService mService;
boolean startHomeOnAllDisplays(int userId, String reason) {
boolean homeStarted = false;
// getChildCount获取显示设备数目,这个主要从mChildren参数中获取对应的数量
// mChildren是一个WindowList的一个对象,其包含的数据是在setWindowManager函数被调用时,从DisplayManagerService中获取到的Display的数目
for (int i = getChildCount() - 1; i >= 0; i--) {
// 获取到对应新建的DisplayContent的displayId
final int displayId = getChildAt(i).mDisplayId;
// 调用startHomeOnDisplay函数
homeStarted |= startHomeOnDisplay(userId, reason, displayId);
}
return homeStarted;
}
//一系列调用最终调用startHomeOnTaskDisplayArea.......
boolean startHomeOnTaskDisplayArea(int userId, String reason, TaskDisplayArea taskDisplayArea,
boolean allowInstrumenting, boolean fromHomeKey) {
// Fallback to top focused display area if the provided one is invalid.
if (taskDisplayArea == null) {
final ActivityStack stack = getTopDisplayFocusedStack();
taskDisplayArea = stack != null ? stack.getDisplayArea()
: getDefaultTaskDisplayArea();
}
Intent homeIntent = null;
ActivityInfo aInfo = null;
if (taskDisplayArea == getDefaultTaskDisplayArea()) {
// 1.向ActivityTaskManagerService获取 Launcher 的启动意图
homeIntent = mService.getHomeIntent();
//2. 向PackageManagerService通过意图解析到 ActivityInfo
aInfo = resolveHomeActivity(userId, homeIntent);
} else if (shouldPlaceSecondaryHomeOnDisplayArea(taskDisplayArea)) {
Pair<ActivityInfo, Intent> info = resolveSecondaryHomeActivity(userId, taskDisplayArea);
aInfo = info.first;
homeIntent = info.second;
}
if (aInfo == null || homeIntent == null) {
return false;
}
if (!canStartHomeOnDisplayArea(aInfo, taskDisplayArea, allowInstrumenting)) {
return false;
}
// Updates the home component of the intent.
homeIntent.setComponent(new ComponentName(aInfo.applicationInfo.packageName, aInfo.name));
homeIntent.setFlags(homeIntent.getFlags() | FLAG_ACTIVITY_NEW_TASK);
// Updates the extra information of the intent.
if (fromHomeKey) {
homeIntent.putExtra(WindowManagerPolicy.EXTRA_FROM_HOME_KEY, true);
mWindowManager.cancelRecentsAnimation(REORDER_KEEP_IN_PLACE, "startHomeActivity");
}
// Update the reason for ANR debugging to verify if the user activity is the one that
// actually launched.
final String myReason = reason + ":" + userId + ":" + UserHandle.getUserId(
aInfo.applicationInfo.uid) + ":" + taskDisplayArea.getDisplayId();
// 根据homeIntent、aInfo,调用 startHomeActivity 方法去启动和创建 Launcher
mService.getActivityStartController().startHomeActivity(homeIntent, aInfo, myReason,
taskDisplayArea);
return true;
}
// 根据Intent的Component向PackageManagerService找到对应的ActivityInfo
ActivityInfo resolveHomeActivity(int userId, Intent homeIntent) {
final int flags = ActivityManagerService.STOCK_PM_FLAGS;
final ComponentName comp = homeIntent.getComponent();
ActivityInfo aInfo = null;
try {
if (comp != null) {
// Factory test.
aInfo = AppGlobals.getPackageManager().getActivityInfo(comp, flags, userId);
} else {
final String resolvedType =
homeIntent.resolveTypeIfNeeded(mService.mContext.getContentResolver());
final ResolveInfo info = AppGlobals.getPackageManager()
.resolveIntent(homeIntent, resolvedType, flags, userId);
if (info != null) {
aInfo = info.activityInfo;
}
}
} catch (RemoteException e) {
// ignore
}
if (aInfo == null) {
Slog.wtf(TAG, "No home screen found for " + homeIntent, new Throwable());
return null;
}
aInfo = new ActivityInfo(aInfo);
aInfo.applicationInfo = mService.getAppInfoForUser(aInfo.applicationInfo, userId);
return aInfo;
}
}
public class ActivityTaskManagerService extends IActivityTaskManager.Stub {
String mTopAction = Intent.ACTION_MAIN;
String mTopData;
// homeIntent.action = Intent.ACTION_MAIN ACTION_MAIN = "android.intent.action.MAIN"
// homeIntent的flags包含Intent.FLAG_DEBUG_TRIAGED_MISSING
// homeIntent的category包含Intent.CATEGORY_HOME CATEGORY_HOME = "android.intent.category.HOME";
Intent getHomeIntent() {
Intent intent = new Intent(mTopAction, mTopData != null ? Uri.parse(mTopData) : null);
intent.setComponent(mTopComponent);
intent.addFlags(Intent.FLAG_DEBUG_TRIAGED_MISSING);
if (mFactoryTest != FactoryTest.FACTORY_TEST_LOW_LEVEL) {
intent.addCategory(Intent.CATEGORY_HOME);
}
return intent;
}
}
复制代码
コードは長いですが、2つのことを行います。
- ActivityTaskManagerService.getHomeIntentメソッドを呼び出して、インテントインテントを取得します
- インテントIntent.Componentに従って、PackageManagerServiceから対応するActivityInfoをクエリします
最後に、ActivityStartController.startHomeActivityメソッドを介して、最後の呼び出しProcess.start
メソッドがレイヤーを介して呼び出され、ランチャーが開始および作成されます。次の記事では、後続のプロセスの作成とアクティビティの開始について説明します。この記事では、ランチャーの開始後にすべてのアプリ情報をクエリする方法を引き続き分析します。
アプリ情報を照会するランチャー
Launcher
アクティビティでは、すべてonCreate
のアプリ情報が次の方法で照会されます。
public class Launcher extends StatefulActivity<LauncherState> implements LauncherExterns,
Callbacks, InvariantDeviceProfile.OnIDPChangeListener, PluginListener<OverlayPlugin> {
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
// 实例化LauncherAppState
LauncherAppState app = LauncherAppState.getInstance(this);
// 根据LauncherAppState获取到LauncherModel
mModel = app.getModel();
// LauncherModel.addCallbacksAndLoad就会去查询App信息
if (!mModel.addCallbacksAndLoad(this)) {
if (!internalStateHandled) {
// If we are not binding synchronously, show a fade in animation when
// the first page bind completes.
mDragLayer.getAlphaProperty(ALPHA_INDEX_LAUNCHER_LOAD).setValue(0);
}
}
}
}
复制代码
onCreateを呼び出してアプリ情報をクエリしLauncherModel.addCallbacksAndLoad
ます。このメソッドは、ハンドラーを介してRunnableを実行し、クエリタスクを実行します。
public class LauncherModel extends LauncherApps.Callback implements InstallSessionTracker.Callback {
// Launcher也实现了Callbacks
public boolean addCallbacksAndLoad(Callbacks callbacks) {
synchronized (mLock) {
// 将Launcher加入到回调列表
addCallbacks(callbacks);
// 调用startLoader()
return startLoader();
}
}
public boolean startLoader() {
synchronized (mLock) {
//.....
stopLoader();
LoaderResults loaderResults = new LoaderResults(
mApp, mBgDataModel, mBgAllAppsList, callbacksList, mMainExecutor);
// 开始查询App信息
startLoaderForResults(loaderResults);
return false;
}
}
public void startLoaderForResults(LoaderResults results) {
synchronized (mLock) {
stopLoader();
// LoaderTask是一个Runnable
mLoaderTask = new LoaderTask(mApp, mBgAllAppsList, mBgDataModel, results);
// Handler去执行LoaderTask
MODEL_EXECUTOR.post(mLoaderTask);
}
}
}
复制代码
キーコードを確認することで、LauncherModelはLoaderTask
RunnableforHandlerを送信して実行します。したがって、クエリAppはLoaderTask
クラスのrun()メソッドにあります。
public class LoaderTask implements Runnable {
public void run() {
//.....
// 加载所有App
List<LauncherActivityInfo> allActivityList = loadAllApps();
//.....
}
// 查询所有App
private List<LauncherActivityInfo> loadAllApps() {
final List<UserHandle> profiles = mUserCache.getUserProfiles();
List<LauncherActivityInfo> allActivityList = new ArrayList<>();
// Clear the list of apps
mBgAllAppsList.clear();
for (UserHandle user : profiles) {
// Query for the set of apps
final List<LauncherActivityInfo> apps = mLauncherApps.getActivityList(null, user);
// Fail if we don't have any apps
// TODO: Fix this. Only fail for the current user.
if (apps == null || apps.isEmpty()) {
return allActivityList;
}
//....
allActivityList.addAll(apps);
}
//.....
return allActivityList;
}
}
public class LauncherApps {
public List<LauncherActivityInfo> getActivityList(String packageName, UserHandle user) {
logErrorForInvalidProfileAccess(user);
try {
return convertToActivityList(mService.getLauncherActivities(mContext.getPackageName(),
packageName, user), user);
} catch (RemoteException re) {
throw re.rethrowFromSystemServer();
}
}
}
复制代码
LoaderTaskのrunメソッドは、すべてのアプリの情報を照会します。
要約する
Launcherは、システムのデスクトッププロセスでありActivityManagerService
、準備が完了した後に開始されます。開始すると、ActivityManagerServiceからIntentインテントを取得し、PackageManagerServiceから対応するActivityInfoを取得します。Launcherアクティビティが開始すると、onCreate()メソッドですべてのアプリ情報が照会されます。