@drawable/screen_background_selector_light
…
到这里我们就很容易明白啦,Theme.Light的父类原来是Theme哇,也在这个文件中,如下:
看注释吧,这货有接近400多个item属性,这也就是我们Android关于Theme的开山鼻祖了,在我们自定义时其实来这看比去API查还方便呢(其实需要两个互相配合,一个查,一个看解释,哈哈),因为它里面定义了关于我们整个应用中文字样式、按钮样式、列表样式、窗体样式、对话框样式等,这些样式都是默认样式,它还有很多我们常用的扩展样式,譬如Theme.Light、Theme.NoTitleBar、Theme.NoTitleBar.Fullscreen等等,反正你要有需求来这里搞就行。当我们继承使用时只用在前加上android:即可,有些属性可能是找不到的。同理,我们所谓的style、attr等等也都是这么个框架,大致位置也类似主题Theme的,所以这里不再过多说明,自行脑补即可。
3-2 Theme、Style等res资源客户化流程
对于纯App开发来说这一个知识点可以忽略,因为本小节需要大致了解Android源码的结构和编译框架,对于固件等开发来说这个还是比较重要的,记得以前做TV盒子开发时很多系统资源需要替换及添加,也就是说会稍微涉及到修改System UI及FW的res,那时候好坑爹,虽然修改的地方不多,只是换几个图标和加几个资源,但是那时候自己还是蒙圈了一段时间才搞明白,所以说有必要啰嗦几句。
首先我们先要明白设备里系统目录下的这些常见jar与apk的来源,如下:
| 名字 | 解释 |
| — | — |
| am.jar | 执行am命令所需的java lib,对应FW的base/cmds/am目录,具体可以参考下面的Android.mk定义。 |
| framework-res.apk | Android系统资源库集合,对应FW的core/res目录,具体同理参见Android.mk定义。 |
| framework.jar | Android SDK核心代码,对应FW的base目录,具体可以参考目录下的Android.mk的MOUDLE定义。 |
| SystemUI.apk | 从Android2.2开始状态栏和下拉通知栏被分割出一个单独的SystemUI.apk,一般在system的app或者priv-app下(还有很多其他模块呢,譬如SettingProvider等,具体可以在设备下看看),对应的源码在FW的packages下的SystemUI中。 |
| Others | 其他的jar比较多,不做一一介绍,不同厂商可能还会不同定制,具体可在厂商设备的system下看看有哪些包,对应回去通过Android.mk文件寻找即可。 |
| android.jar | 切记这个特例,这货是make sdk生成的,多方整合,别以为也可以找到对应目录,木有的!还有就是这个jar很实用的,很多时候我们想用AS直接调运系统的hide API等,自己编译一个就能派上用场啦! |
有了上边这几个和我们本文相关的核心常识后我们简单说下怎么修改编译:
-
修改FW/base/XXX/下面需要修改的代码;
-
单独在XXX下mm编译生成XXX.jar(apk);
-
把编译的jar(apk)包(在out目录对应路径下)push到设备系统system的FW目录下;
-
reboot重启设备验证;
不过这里有些坑大家要明白,我们在mm前最好每次都去清除对应out/obj目录下的中间文件,特别是资源文件更新时,否则容易被坑。还有就是切记添加系统API或者修改@hide的API或者添加资源(包含添加修改public.xml等)后,需要执行make update-api命令来同步base/api下的current.txt的修改,完事再make就行啦,这些编译文档都有介绍。
有了上面这些相信大家对于客户化资源也就有了一些认识啦,想想如果我们需要用到framework.jar的hide资源或者fra
mework-res.apk中新加的资源时又不想用反射和源码下编译怎么办?当然是编译一个no hide的jar引入我们工程即可哇,要注意我们引入以后一定是Providered的模式,也就是该jar只编译不打包入该apk,还有就是依赖的先后优先级顺序,否则又用的是sdk默认的。还有就是万能的android.jar也是一种曲线救国的办法。当然啦,如果是SDK开发则完全可以复制一份自己搞,完事编译进系统即可,同时提供给App开发。
3-3 Theme、Style加载时机及加载源码浅析
前面我们介绍了Android的Theme、Style的定义及使用及Theme、Style等res的由来,这里我们来看看这些被使用的Theme的最终是何时、怎样被加载生效的。我们都知道对于Theme有两种方式来使用,具体如下(Style等attr在View的使用也比较同类,这里只分析Theme、其他的请在View等地自行分析脑补):
-
在AndroidManifest.xml中
<application>
或者<activity>
节点设置android:theme属性;