Context 之 内核剖析 读笔

本文深入探讨了Android中Context的创建过程及其继承关系,详细解释了ContextWrapper、ContextThemeWrapper、ContextImpl等关键组件的作用,并展示了如何在Application、Activity、Service中创建和使用Context。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >



我们先来看一眼Context的类继承关系


可以看到,Activity Service 都是context.

我们首先来说下ContextWrapper,  顾名思义 , wrapper 译为 "包裹", So~ ContextWrapper 只是对Context的一个包裹作用. 

ContextThemeWrapper. 看Theme我们就可以知道它是与 主题相关的.  想到什么了 ? 没错,就是在AndroidManifest内为application 或activity 指定的 theme.  而Service 没有主题, 是运行在后台的. 所以Service直接继承了ContextWrapper, 而Activity 继承至 ContextThemeWrapper


而ContextImpl 真正实现了 Context 的所有函数. 其操作context时, 其实现都是来自ContextImpl.  由以上可以看出,有多少个Activity 和Service 就有多少个 Context.


关于Context的创建 .

 通过书中得知 , Activity本质上是一个Context, Activity基于ContextWrapper类. 然而ContextWrapper必须为其指定真正的Context对象,而真正实现了Context类的是 ContextImpl. 所以我们要知道ContextImpl是如何被创建的.


 程序都是由ActivityThread 开始的. 创建Context对象也是在该类中完成,  在ActivityThread类中一共有7处创建ContextImpl.



其中只有attach()方法 仅在  Framework进程(system_server)启动时调用,程序运行时不会调用.



关于Application的 Context :

  程序第一次启动时, 会调用handleBindApplication()方法中, 该方法两处创建了ContextImpl.但是都在if(data.instrumentationName!=null)中,   一般都不会进入该条件中. 只有创建了Android Unit Test 才会进入(2.3)


  在API 23中 进入到handleBindApplication()中



会先直接创建一个ContextImpl对象, 在往下走. 会执行到data.info.makeApplication  会在其内又创建一个ContextImpl,这里为什么会创建两个ContextImpl对象还没有研究...等下回再分析.


然后这个然而我们需要一个PackageInfo,  这个info 是从何而来 ?  把代码往上推点 可看到


由图可以看到.  调用getPackageInfoNoCheck方法 会返回一个data.info.    然而data是什么 ?   data其实是一个AppBindData. 它从何而来 ?

 当第一次运行程序时,  AMS 通过IPC会调用ActivityThread 中的 bindApplication方法, 在其内会构建一个AppBindData


之后会发送消息 调用 handleBindApplication.






下面我们来看看Activity 的 Context创建

 启动Activity时, AMS会通过IPC调用到 scheduleLaunchActivity()方法,

scheduleLaunchActivity 会根据传入参数 构造一个本地的ActivityRecode数据类, 如图所示


之后会利用H (Handler) 发送消息 后 执行handleLaunchActivity, 将ActivityRecord传入


在handleLaunchActivity内 会调用performLaunchActivity 


performLaunchActivity内会执行r.packageInfo,makeApplication  然后在其内创建ContextImpl.








关于Service 创建Context

 启动Service 时,AMS会通过IPC调用 ActivityThread 的 scheduleCreateService()方法,会在其内构建一个CreateServiceData 本地数据


 之后会调用handleCreateService 

获取packageInfo




创建ContextImpl,  接着执行makeApplication


在makeApplication 又创建了一次ContextImpl,   同上面Application一样,还没有研究.. 以上就是Context, 以及ContextImpl的由来了.


 Context之间的关系

 由上面我们可以知道Application、Activity、Service创建Context 的步骤大体一样,不同之处在于 Application、Activity、Service 使用了不同的数据对象.



 所以 Context个数 = Activity个数 +Service个数 +1;


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值