Android 启动过程Activity 启动源码分析 ( ActivityThread -> Activity主线程阶段 二 )
Posted 韩曙亮
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Android 启动过程Activity 启动源码分析 ( ActivityThread -> Activity主线程阶段 二 )相关的知识,希望对你有一定的参考价值。
文章目录
前言
上一篇博客 【Android 启动过程】Activity 启动源码分析 ( ActivityThread -> Activity、主线程阶段 一 ) 分析了在 ActivityThread 主线程中将要调用 handleLaunchActivity
方法 , 启动新的 Activity ;
一、ActivityThread 类 handleLaunchActivity -> performLaunchActivity 方法
在 ActivityThread
的 handleLaunchActivity
中 , 调用了 performLaunchActivity
方法 ,
在 performLaunchActivity
方法中 , 调用了 mInstrumentation.newActivity
方法 , 正式创建 Activity 实例对象 ;
/**
* 管理应用程序进程中主线程的执行、调度和执行活动、广播以及活动管理器请求的其他操作。
*
* {@hide}
*/
public final class ActivityThread extends ClientTransactionHandler {
/**
* Activity 启动的扩展实现。当服务器请求启动或重新启动时使用。
*/
@Override
public Activity handleLaunchActivity(ActivityClientRecord r,
PendingTransactionActions pendingActions, Intent customIntent) {
// 创建页面 , 窗口初始化
WindowManagerGlobal.initialize();
// 启动 Activity 核心方法
final Activity a = performLaunchActivity(r, customIntent);
return a;
}
/** Activity 启动的核心实现。 */
private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
ActivityInfo aInfo = r.activityInfo;
ContextImpl appContext = createBaseContextForActivity(r);
Activity activity = null;
try {
java.lang.ClassLoader cl = appContext.getClassLoader();
// 正式创建 Activity 对象
activity = mInstrumentation.newActivity(
cl, component.getClassName(), r.intent);
StrictMode.incrementExpectedActivityCount(activity.getClass());
r.intent.setExtrasClassLoader(cl);
r.intent.prepareToEnterProcess();
if (r.state != null) {
r.state.setClassLoader(cl);
}
} catch (Exception e) {
}
return activity;
}
}
完整代码参考 /frameworks/base/core/java/android/app/ActivityThread.java
二、Instrumentation.newActivity 方法
在 Instrumentation
的 newActivity
方法中 , 调用了 getFactory(pkg).instantiateActivity(cl, className, intent)
方法 , 创建 Activity
;
实际调用的是 AppComponentFactory
的 Activity instantiateActivityCompat(@NonNull ClassLoader cl, @NonNull String className, @Nullable Intent intent)
方法 ;
/**
* 用于实现应用程序检测代码的基类。
* 当在启用检测的情况下运行时,该类将在任何应用程序代码之前为您实例化,
* 从而允许您监视系统与应用程序之间的所有交互。
* 通过androidManifest.xml的<仪器仪表>标签。
*/
public class Instrumentation {
/**
* 执行流程{@link Activity}对象的实例化。默认实现提供正常的系统行为。
*
* @param cl 用于实例化对象的类加载器。
* @param className 实现活动的类的名称对象
* @param intent 指定要实例化的活动类的intent对象。
*
* @return The newly instantiated Activity object.
*/
public Activity newActivity(ClassLoader cl, String className,
Intent intent)
throws InstantiationException, IllegalAccessException,
ClassNotFoundException {
String pkg = intent != null && intent.getComponent() != null
? intent.getComponent().getPackageName() : null;
return getFactory(pkg).instantiateActivity(cl, className, intent);
}
}
完整代码参考 /frameworks/base/core/java/android/app/Instrumentation.java ;
三、AppComponentFactory.instantiateActivityCompat方法
在 AppComponentFactory
的 instantiateActivityCompat
方法中 , 通过反射创建新的 Activity
;
由于不知道要启动哪个类 , 只能传入一个类名称 , 因此这里只能使用反射创建 Activity
;
/**
* 使用androidx库的{@link android.app.AppComponentFactory}版本。
*
* 注意:这只适用于API 28+,不支持AppComponentFactory功能。
*/
@RequiresApi(28)
public class AppComponentFactory extends android.app.AppComponentFactory {
/**
* 允许应用程序覆盖活动的创建。这可以用于对这些类执行依赖项注入或类装入器更改等操作。
*
* 此方法仅用于提供用于实例化的挂钩。它不提供对活动对象的早期访问。
* 返回的对象尚未初始化为上下文,不应用于与其他android API交互。
*
* @param cl 用于实例化的默认类加载器。
* @param className 要实例化的类。
* @intent 创建类的意图。
*/
public @NonNull Activity instantiateActivityCompat(@NonNull ClassLoader cl,
@NonNull String className, @Nullable Intent intent)
throws InstantiationException, IllegalAccessException, ClassNotFoundException {
try {
// 通过反射方式创建 Activity
return (Activity) cl.loadClass(className).getDeclaredConstructor().newInstance();
} catch (InvocationTargetException | NoSuchMethodException e) {
throw new RuntimeException("Couldn't call constructor", e);
}
}
}
完整代码参考 /frameworks/support/compat/src/main/java/androidx/core/app/AppComponentFactory.java ;
四、ActivityThread.performLaunchActivity 方法后续细节
再次回到 ActivityThread
类的 performLaunchActivity
进行分析 ,
ContextImpl appContext = createBaseContextForActivity(r)
是应用中的 Context
上下文的唯一实现 ;
mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState)
代码就是触发调用 Activity
的 OnCreate
方法 ;
/**
* 管理应用程序进程中主线程的执行、调度和执行活动、广播以及活动管理器请求的其他操作。
*
* {@hide}
*/
public final class ActivityThread extends ClientTransactionHandler {
/** Activity 启动的核心实现。 */
private Activity performLaunchActivity(ActivityClientRecord r, Intent customIntent) {
ActivityInfo aInfo = r.activityInfo;
ContextImpl appContext = createBaseContextForActivity(r);
Activity activity = null;
try {
java.lang.ClassLoader cl = appContext.getClassLoader();
// 正式创建 Activity 对象
activity = mInstrumentation.newActivity(
cl, component.getClassName(), r.intent);
StrictMode.incrementExpectedActivityCount(activity.getClass());
r.intent.setExtrasClassLoader(cl);
r.intent.prepareToEnterProcess();
if (r.state != null) {
r.state.setClassLoader(cl);
}
} catch (Exception e) {
}
try {
Application app = r.packageInfo.makeApplication(false, mInstrumentation);
if (activity != null) {
activity.mCalled = false;
if (r.isPersistable()) {
// 调用 Activity 的 onCreate 方法
mInstrumentation.callActivityOnCreate(activity, r.state, r.persistentState);
} else {
mInstrumentation.callActivityOnCreate(activity, r.state);
}
r.activity = activity;
}
mActivities.put(r.token, r);
} catch (SuperNotCalledException e) {
throw e;
} catch (Exception e) {
}
return activity;
}
}
完整代码参考 /frameworks/base/core/java/android/app/ActivityThread.java
五、Instrumentation.callActivityOnCreate 方法
Instrumentation
的 callActivityOnCreate(Activity activity, Bundle icicle, PersistableBundle persistentState)
方法 , 主要是调用 Activity
的 performCreate
方法 , 之后会调用 Activity
的 onCreate
方法 ;
/**
* 用于实现应用程序检测代码的基类。
* 当在启用检测的情况下运行时,该类将在任何应用程序代码之前为您实例化,
* 从而允许您监视系统与应用程序之间的所有交互。
* 通过AndroidManifest.xml的<仪器仪表>标签。
*/
public class Instrumentation {
/**
* 执行对活动的{@link activity#onCreate}方法的调用。默认实现只是调用该方法。
*
* @param activity 正在创建的活动。
* @param icicle 要传递到的先前冻结状态(或null)
* @param persistentState 以前的持久化状态(或null)
*/
public void callActivityOnCreate(Activity activity, Bundle icicle,
PersistableBundle persistentState) {
prePerformCreate(activity);
activity.performCreate(icicle, persistentState);
postPerformCreate(activity);
}
}
完整代码参考 /frameworks/base/core/java/android/app/Instrumentation.java ;
总结
截止到此处 , AMS 通过 Binder 机制调用 ActivityThread
, 创建 Activity
, 并调用 Activity
的 onCreate
方法 , 整个流程分析完毕 ;
以上是关于Android 启动过程Activity 启动源码分析 ( ActivityThread -> Activity主线程阶段 二 )的主要内容,如果未能解决你的问题,请参考以下文章
Android 启动过程Activity 启动源码分析 ( ActivityThread -> Activity主线程阶段 一 )
Android 启动过程Activity 启动源码分析 ( AMS -> ActivityThreadAMS 线程阶段 二 )
Android 启动过程Activity 启动源码分析 ( AMS -> ActivityThreadAMS 线程阶段 )
Android 启动过程Activity 启动源码分析 ( ActivityThread -> Activity主线程阶段 二 )