private void installDecor(){
if(mDecor == null){
mDecor = generateDecor();
mDecor.setDescendantFocusability(ViewGroup.FOCUS_AFTER_DESCENDANTS);
mDecor.setIsRootNamespace(true);
}
if(mContentParent == null){
mContentParent = generateLayout(mDecor);
installDecor()是在 setContentView(int layoutResID)方法内被调用,为windows添加decorview页面
installDecor执行流程
- 使用 generateDecor()创建一个DecorView对象,并赋值给mDecor变量。该变量并不完全等同于窗口修饰,窗口修饰是mDecor内部的唯一一个子视图。
- 根据用户指定的参数选择不用的窗口修饰,并把该窗口修饰作为mDecor的子窗口,这是在generateLayout()中调用mDecor.addView()完成的.
- 给mContentParent变量赋值,其值是通过调用ViewGroup.contentParent = (ViewGroup)findViewById(ID_ANDROID_CONTENT)获得的,ID_ANDROID_CONTENT正是id = content 的 FrameLayout
窗口修饰的XML布局文件
- R.layout.dialog_title_icons
- R.layout.screen_title_icons
- R.layout.screen_progress
- R.layout.dialog_custom_title
- R.layout.screen_custom_title
- R.layout.dialog_title
- R.layout.screen_title
- R.layout.screen_simple
该xml用于添加到窗口修饰中的指定 xml 布局文件
这是在setConetentView()(方法内部)中调用inflate()方法完成的,该方法的第二个参数正是mContentParent,即 id = content 的 FrameLayout
Feature的指定
- 在Activity的onCreate()方法中调用得到当前的Window,然后调用requestFeature()指定,generateLayout()方法中使用getLocalFeature()获取feature值,并根据这些值选择不同的窗口修饰
- 在AndroidMainfest.xml中Activity元素内部使用android:theme="xxx"指定。generateLayout()方法中使用getWindowStyle()方法获取这些值,该方法的调用流程为:
- PhoneWindow: getWindowStyle() 中 generateLayout
- Window: obtainStyleAttributes() 中
- Context: getTheme().obtainStyleAttributes() 中