Activity, Window, View三者之间的关系

Activity创建过程

  1. 创建Activity实例的时候,系统就会创建Activity所属的Window对象,并为Window对象设置回调Callback接口。创建的方法是PolicyManager的makeNewWindow 策略模式创建出来的Window
  2. Activity调用setContentView方法,将布局视图绑定到PhoneWindow上。在setContentView中会调用getWindow().setContentView()。(此时getWindow返回的对象为PhoneWindow)在PhoneWindow中的setContentView(),首先会创建DecoderView(上下结构:标题栏,内容区),然后将视图View设置到DecoderView中的mContentParent
  3. 一旦确定视图绑定到Window上,那会同辉CallBack接口回调给Activity做一些处理
  4. 在ActivtiyThread的handleResumeActivity方法中会调用Activity.makeVisible(),在这个方法中DecoderView真正完成添加和显示过程
Activity 控制层。控制Window显示与隐藏
Window 装载层。 用于装载视图层DecoderView
View 视图层。 真正控制视图UI

ViewRootImpl。用于处理View相关的事件,比如绘制,事件分发,也是DecoderView的parent

Dialog创建过程

  1. 创建Window。同样也是使用Policy.makeNewWindow()创建
  2. 仍然使用Window.setContentView()。创建DecoderView,并将布局视图绑定到DecoderView中的mContentParent之上。
  3. 将DecoderView添加到Window中显示,dialog调用show方法的时候,会通过WindowManager.addView方法添加在指定的window上

Activity,Dialog,PopupWindow,Toast与Window关系

  • Activity。在Activity创建过程中会创建PhoneWindow,是层级最小的Window,叫做应用Window,层级范围为1 ~ 99 (层级范围大的可以覆盖层级范围小的)
  • Dialog。Dialog的Window并不是应用窗口,而是子窗口,层级范围为1000 ~ 1999。子窗口显示必须依赖应用窗口,也会覆盖应用级窗口。这也就是为什么Dialog传入的上下文必须是Activity的context了
  • PopupWindow。PopoupWindow并不是创建PhoneWidow用于承载视图。而是直接创建一个View(PopupDecoderView)。然后通过WindowManager的addView显示出来。没有创建PhoneWindow,是不是就跟Window没关系了?其实只要调用WindowManager的addView方法,那就是创建了Window,跟你有没有PhoneWindow没有关系。View就是Window的表现形式,只不过PhoneWindow的存在让Window更加立体一些
  • Toast。Toast和PopupWindow比较像,没有新建PhoneWindow,直接通过addView方法显示View即可。不同的是它属于系统级Window,层级范围2000-2999,所以无须依附于Activity
四者相同点

只要想显示View,就会涉及到WindowManager的addView方法,也就用到了Window这个概念,然后会根据不同的分层依次显示覆盖到界面上。

四者不相同点

不同的是,Activity和Dialog涉及到了布局比较复杂,还会有布局主题等元素,所以用到了PhoneWindow进行一个解耦,帮助他们管理View。而PopupWindow和Toast结构比较简单,所以直接新建一个类似DecorView的View,通过addView显示到界面。

你可能感兴趣的:(Activity, Window, View三者之间的关系)