当前位置: 首页 > news >正文

【Android View】窗口机制

文章目录

  • 一. 关系图概览
  • 二. 各层级概述
    • 1. Activity
    • 2. Window
    • 3. PhoneWindow
    • 4. DecorView
    • 5. ViewRoot
    • 6. WindowManager
    • 7. WindowManagerService
  • 三. 基于源码的深入分析
    • 1. PhoneWindow,DecorView,setContentView源码理解
    • 2. DecorView创建流程
      • 2.1 ViewManager
      • 2.2 WindowManager
      • 2.3 WindowManagerImpl
    • 3.

  • 参考资料
  • 添加链接描述
  • 添加链接描述

一. 关系图概览

在这里插入图片描述

二. 各层级概述

1. Activity

  • Activity并不负责视图控制,它只是控制生命周期和处理事件。真正控制视图的是Window。
  • 一个Activity包含了一个Window,Window才是真正代表一个窗口。
  • Activity就像一个控制器,统筹视图的添加与显示,以及通过其他回调方法,来与Window、以及View进行交互。

2. Window

  • Window是视图的承载器内部持有一个 DecorView,而这个DecorView才是 view 的根布局。
  • Window是一个抽象类,实际在Activity中持有的是其子类PhoneWindow
  • PhoneWindow中有个内部类DecorView,通过创建DecorView来加载Activity中设置的布局R.layout.activity_main
  • Window 通过WindowManager将DecorView加载其中,并将DecorView交给ViewRoot,进行视图绘制以及其他交互。

3. PhoneWindow

  • 将Decoriew设置为整个应用窗口的根View,是Window的实现类
  • 它是Android中的最基本的窗口系统,每个Activity均会创建一个PhoneWindow对象,是Activity和整个View系统交互的接口

4. DecorView

  • DecorView是FrameLayout的子类,它可以被认为是Android视图树的根节点视图
  • DecorView作为顶级View,一般情况下它内部包含一个竖直方向的LinearLayout,在这个LinearLayout里面有上下三个部分,上面是个ViewStub,延迟加载的视图(应该是设置ActionBar,根据Theme设置),中间的是标题栏(根据Theme设置,有的布局没有),下面的是内容栏。 具体情况和Android版本及主体有关。

5. ViewRoot

  • ViewRoot对应ViewRootImpl类,它是连接WindowManagerService和DecorView的纽带,View的三大流程(测量,布局,绘制)均通过ViewRoot来完成。
  • ViewRoot并不属于View树的一份子。从源码实现上来看,它既非View的子类,也非View的父类,但是,它实现了ViewParent接口,这让它可以作为View的名义上的父视图。ViewRoot继承了Handler类,可以接收事件并分发,Android的所有触屏事件、按键事件、界面刷新等事件都是通过ViewRoot进行分发的

6. WindowManager

  • WindowManager 是 Android提供的一个接口,用于管理应用窗口的显示。它允许应用程序与系统窗口管理器交互,添加、更新或移除窗口
  • 开发者通常通过 Context.getSystemService(Context.WINDOW_SERVICE) 获取其实例。
  • WindowManager 是客户端(应用)用来与 WindowManagerService 通信的代理
  • 应用通过 WindowManager 提交窗口请求,最终由 WindowManagerService 统一调度和管理。

7. WindowManagerService

  • WindowManagerService(简称 WMS)是 Android 系统的核心服务之一,运行在 System Server 进程中
  • 负责管理所有窗口的布局、显示顺序、焦点控制、输入事件分发等核心功能
  • 与底层的 SurfaceFlinger 交互,将窗口内容渲染到屏幕上

三. 基于源码的深入分析

1. PhoneWindow,DecorView,setContentView源码理解

  • Window
    抽象基类,它提供了一系列窗口的方法,比如背景,标题等等,而它的唯一实现类则是PhoneWindow
/*** Abstract base class for a top-level window look and behavior policy.  An* instance of this class should be used as the top-level view added to the* window manager. It provides standard UI policies such as a background, title* area, default key processing, etc.** <p>The only existing implementation of this abstract class is* android.view.PhoneWindow, which you should instantiate when needing a* Window.*/
public abstract class Window {...@Nullablepublic View findViewById(@IdRes int id) {return getDecorView().findViewById(id);}/*** Convenience for * {@link #setContentView(View, android.view.ViewGroup.LayoutParams)}* to set the screen content from a layout resource.  The resource will be * inflated, adding all top-level views to the screen. * * @param layoutResID Resource ID to be inflated.* @see #setContentView(View, android.view.ViewGroup.LayoutParams)*/public abstract void setContentView(@LayoutRes int layoutResID);...
}
  • PhoneWindow
    Window的唯一实现类
public class PhoneWindow extends Window implements MenuBuilder.Callback {private final static String TAG = "PhoneWindow";...// This is the top-level view of the window, containing the window decor.private DecorView mDecor;// This is the view in which the window contents are placed. It is either// mDecor itself, or a child of mDecor where the contents go.private ViewGroup mContentParent;private ViewGroup mContentRoot;...
}

在PhoneWindow里面,出现了成员变量DecorView的而这里,DecorView则是PhoneWindow里面的一个内部类,它是继承与FrameLayout

// 既然是FrameLayout,也就可以加载布局文件,也就是说,我们那些标题栏,内容栏,
/ 顶级上看是加载在DecorView上的。而DecorView则是由PhoneWindow负责添加private final class DecorView extends FrameLayout implements RootViewSurfaceTaker {/* package */int mDefaultOpacity = PixelFormat.OPAQUE;/** The feature ID of the panel, or -1 if this is the application's DecorView */private final int mFeatureId;private final Rect mDrawingBounds = new Rect();private final Rect mBackgroundPadding = new Rect();private final Rect mFramePadding = new Rect();private final Rect mFrameOffsets = new Rect();....}
  • setContentView源码流程
    activity.setContentView,实际上调用到的是它的实现类方法phoneWindow.setContentView
@Override
public void setContentView(View view, ViewGroup.LayoutParams params) {// 如果没有创建 mContentParent,则初始化 DecorView 和内容父布局if (mContentParent == null) {installDecor();} else if (!hasFeature(FEATURE_CONTENT_TRANSITIONS)) {// 如果不使用过渡动画,直接移除旧内容mContentParent.removeAllViews();}if (hasFeature(FEATURE_CONTENT_TRANSITIONS)) {// 使用过渡动画时,将新 View 作为过渡内容添加final Scene newScene = Scene.getSceneForLayout(mContentParent, view, mContext);transitionTo(newScene);} else {// 否则直接添加 View 到内容父布局中mContentParent.addView(view, params);}
}

2. DecorView创建流程

前置知识:

  • ViewManager
  • WindowManager
  • WindowManagerImpl
    在这里插入图片描述

2.1 ViewManager

2.2 WindowManager

2.3 WindowManagerImpl

3.

http://www.dtcms.com/a/406684.html

相关文章:

  • 基于Spring Boot的竞赛管理系统架构设计
  • php代码删除网站温州市建设工程管理网站
  • 【开题答辩全过程】以 Bug交流网站为例,包含答辩的问题和答案
  • Agent开发02-关键思想(ReAct、ReWOO、Reflexion、LLM Compiler等)
  • 【Python语法基础学习笔记】输入输出进阶
  • 整站排名服务手机p2p网站开发
  • Flex布局完全指南:从容器到项目的全方位解析
  • 网站开发搜索功能怎么实现装潢公司设计效果图
  • 营销网站建设都是专业技术人员广西玉林网站建设
  • AI论文写作工作流:从输入到输出的五步模型
  • 《从0到1搭建客户画像系统:AI工具矩阵如何解决开发困局》
  • 阿里云云效将本地的maven相关文件批量推送到阿里云仓库以及使用
  • Docker Swarm主机编排
  • [论文阅读] 人工智能+ | 突破LLM情报分析瓶颈!MAKR多Agent框架让长文本因果推理更精准
  • apifox对一批文件批量请求一个接口
  • 情绪识别论文阅读——Eyemotion
  • 帝国建站软件全栈网站开发工程师
  • 嵌入式单线程编程模型的整理
  • 永磁同步电机无速度算法--改进滑模观测器(幂次指数趋近律)
  • 综合案例2:爬取某客栈的漫画
  • C++笔记(基础)初始化输入输出 const
  • 成都网站设计培训有了网址可以建网站吗
  • 【Redis】分布式集群
  • 人工智能大模型是怎样喂数据的?
  • 其他 | 把 csdn 博客的内容导出成 pdf 文件
  • h5网站开发定制网站如何做优化排名
  • 宁夏网站建设报价网站开发全栈工程师技能图
  • AI“驯服”光伏云:卫星+深度学习预测沙尘遮蔽,发电量提升7%
  • Y3入门(1、创建一个项目)
  • Ubuntu 20.04下安装Miniconda、配置conda环境,安装PyTorch,安装YOLO等相关库(二)