转载

Android 中的Activity、Window、View之间的关系

 1  public void setContentView(int layoutResID) { 2         getWindow().setContentView(layoutResID); 3         initActionBar(); 4     } 

看第二行代码,现实 得到一个 Window 对象。

 1 public Window getWindow() { 2         return mWindow; 3     } 

getWindow 很简单只是返回一个 对象而已,那么,Window对象到底是在哪儿实例化的呢?

我们可以看看,Activity 中的 attach 方法,这里面得到了一个 Window 对象

 mWindow = PolicyManager.makeNewWindow(this); 

2.   由Activity中的 setContentView 方法可以看到,界面绘制并不是由 Activity 完成的,他是调用了 Window 类的 setContentView 来实现的。所以我们就去看看 Window 类的代码:

 public abstract void setContentView(int layoutResID); 

我们可以看到, Window 类是一个抽象类,并且 setContentView  是一个抽象方法。所以说,其具体实现是由 实现 Window类的类来完成的(PhoneWindow)。

3.   在文档中已经描述了:The only existing implementation of this abstract class is  android.policy.PhoneWindow.  我们要来看看这个类才能知道 界面是如何完成绘制的。

  1  @Override  2     public void addContentView(View view, ViewGroup.LayoutParams params) {  3         if (mContentParent == null) {  4             installDecor();  5         }  6         if (hasFeature(FEATURE_CONTENT_TRANSITIONS)) {  7             // TODO Augment the scenes/transitions API to support this.  8             Log.v(TAG, "addContentView does not support content transitions");  9         } 10         mContentParent.addView(view, params); 11         final Callback cb = getCallback(); 12         if (cb != null && !isDestroyed()) { 13             cb.onContentChanged(); 14         } 15     } 

先判断mContentParent是否为空,如果为空就调用 installDecor 方法(自己可以看一下源码),  最后会添加 View。

Window 中有一个 DecorView,可以理解为“ViewRoot”,引号是说其实这个“ViewRoot”是一个View或者说ViewGroup,是最初始的根视图。构建视图就是向这里面添加。所以到这里大概可以知道,installDecor 方法大概是 构建一个根视图。

三、总结

Android 中的Activity、Window、View之间的关系

Activity创建时系统会调用其 attach 方法,将其添加到ActivityThread当中,在attach方法中创建了一个window对象。

我们知道Window组合了一个 DocerView, 当用户调用 setContentView 的时候会把一棵 View 树仍给DocerView。 View树是已经创建好的实例对象,所以我们研究的是DocerView是个什么东西,它是如何被创建的。

我们回头看看Window实现里边的setContentView方法,代码中有一个 installDecor 方法,这个方法中有一个  generateDecor。 generateDecor直接new了一个DecorView对象

 protected DecorView generateDecor() {         return new DecorView(getContext(), -1);  } 

当 DocerView 被创建后,就会调用  mContentParent.addView(view, params); 来将 view  添加到 DocerView当中。

最后总结一下:

Activity在onCreate时调用attach方法,在attach方法中会创建window对象。window对象创建时并没有创建 DocerView 对象。用户在Activity中调用setContentView,然后调用window的

setContentView,这时会检查DecorView是否存在,如果不存在则创建DecorView对象,然后把用户自己的 View  添加到 DecorView 中。

装模作样的 声明 一下:本博文章若非特殊注明皆为原创,若需转载请保留原文链接(http://www.cnblogs.com/kest/p/5141817.html)及作者信息k_est

原文  http://www.cnblogs.com/kest/p/5141817.html
正文到此结束
Loading...