PopupWindow是我们经常使用的一个控件,严格来说这个PopuWindow就用来在指定位置显示一个View。
经过分析源码,PopupWindow里面没有Window对象,只是把View设置到屏幕而已。
从构造函数中可知,我们只是把Context对象传递了过去,这个Context是Activity,通过Context获得WindowManager对象。
从源码可以得出一个结论是,即使没有Window对象,也可以添加窗口到屏幕。
构造函数就不多说了,自己看下就行。

就看下如何让PopupWindow显示出来

显示PopuWindow的时候,应用程序开发者一般调用PopupWindow的如下方法:
    public void showAsDropDown(View anchor) 
     showAsDropDown(View anchor, int xoff, int yoff)
    showAtLocation(View parent, int gravity, int x, int y) 

第一个方法调用了第二个,最后那个方法又和第二个类似,那么下面就只分析下第二个方法:

先解释下参数:
anchor:就是PopupWindow要显示的相对于谁的位置的那个谁,哈哈,这样描述的有点搞笑,就是参照的View
xoff: PopupWindow相对于anchor的左下角x轴方向的偏移大小
yoff: PopupWindow相对于anchor的左下角y轴方向的偏移大小

第800行:判断当前PopupWindow是否显示,或者mContentView是否为空,是的话就不用去继续执行下面的代码了,为什么
    不去执行,你懂的....
第804行:registerForScrollChanged(anchor, xoff, yoff);这个方法起名起的也很有意思,为了滑动改变注册,就是有可能anchor有
        滑动,或者ContentView过大,有的地方放不开。

  就是注册一下滑动的全局的监听,注册之前先注销一下之前的注册,防止ViewTreeObserver失效。
 在这里使用了一个弱引用对anchor,防止anchor这个类已经无用了,anchor仍然无法回收内存。
806行:把mIsShowing设置为true,代表正在处于PopupWindow的显示过程。
807行:mIsDropdown设置为true,代表是防止anchor下面
809行:为PopupWindow设置显示参数,调用了createPopupLayout(anchor.getWindowToken())
看下这个方法:
(1)创建一个WindowManager.LayoutParams的实例p
(2)设置一些参数
   设置了gravity,width,heigt
   设置format
   couputeFlags()方法,为p设置了一系列的flag,设置flag的时候也很有意思,使用这些运算符~、&、|
   设置了输入法模式
   设置标题
第810行:使用p准备popupwindow,就是为创建popupwindow做一些必要的准备工作,一会解释一下怎么准备的
867行:做了一些必要的检查,在写程序的时候就不能出错的地方
872行:如果mBackground不为null的话(背景不为空的话),接着就创建一个PopuViewContainner,这个FrameLayout的一个子类,
        把背景设置给PopuViewContainner,然后再把mContentView放进去,然后把PopuViewContainner赋值给mPopupView,返回回去
        否则的话mPopupView就是mContentView

893,894行,把高度和宽度分别赋值一下mPopupWidth和mPopupHeight

回到showAsDropDown()方法继续分析
812行:方法updateAboveAnchor(findDropDownPosition(anchor, p, xoff, yoff));主要是用来计算mPopupView显示的位置和层次,还有
        当位置不够,滑动时处理的一些东西,自己详细的分一下即可。

817行:p.windowAnimations = computeAnimationResource();就是用来设置一些显示动画

819行:invokePopup(p);才是真正的把PopupWindow显示在特定的位置上。其实就使用Activity中的WindowManager对象对mPopupView进行了添加显示。

还有一点需要注意的是PopupWindow是什么类型的窗口,可以明确的说是子窗口,因为在PopupWindow这个类里面定义了窗口类型
TYPE_APPLICATION_PANEL就是子窗口,默认的第一种子窗口


先写到这里,个人能力有限,难免会出现错误,如发现错误敬请指正。

PopupWindow源码分析的更多相关文章

  1. Android View事件分发-从源码分析

    View事件分发-从源码分析 学习自 <Android开发艺术探索> https://blog.csdn.net/qian520ao/article/details/78555397?lo ...

  2. ABP源码分析一:整体项目结构及目录

    ABP是一套非常优秀的web应用程序架构,适合用来搭建集中式架构的web应用程序. 整个Abp的Infrastructure是以Abp这个package为核心模块(core)+15个模块(module ...

  3. HashMap与TreeMap源码分析

    1. 引言     在红黑树--算法导论(15)中学习了红黑树的原理.本来打算自己来试着实现一下,然而在看了JDK(1.8.0)TreeMap的源码后恍然发现原来它就是利用红黑树实现的(很惭愧学了Ja ...

  4. nginx源码分析之网络初始化

    nginx作为一个高性能的HTTP服务器,网络的处理是其核心,了解网络的初始化有助于加深对nginx网络处理的了解,本文主要通过nginx的源代码来分析其网络初始化. 从配置文件中读取初始化信息 与网 ...

  5. zookeeper源码分析之五服务端(集群leader)处理请求流程

    leader的实现类为LeaderZooKeeperServer,它间接继承自标准ZookeeperServer.它规定了请求到达leader时需要经历的路径: PrepRequestProcesso ...

  6. zookeeper源码分析之四服务端(单机)处理请求流程

    上文: zookeeper源码分析之一服务端启动过程 中,我们介绍了zookeeper服务器的启动过程,其中单机是ZookeeperServer启动,集群使用QuorumPeer启动,那么这次我们分析 ...

  7. zookeeper源码分析之三客户端发送请求流程

    znode 可以被监控,包括这个目录节点中存储的数据的修改,子节点目录的变化等,一旦变化可以通知设置监控的客户端,这个功能是zookeeper对于应用最重要的特性,通过这个特性可以实现的功能包括配置的 ...

  8. java使用websocket,并且获取HttpSession,源码分析

    转载请在页首注明作者与出处 http://www.cnblogs.com/zhuxiaojie/p/6238826.html 一:本文使用范围 此文不仅仅局限于spring boot,普通的sprin ...

  9. ABP源码分析二:ABP中配置的注册和初始化

    一般来说,ASP.NET Web应用程序的第一个执行的方法是Global.asax下定义的Start方法.执行这个方法前HttpApplication 实例必须存在,也就是说其构造函数的执行必然是完成 ...

随机推荐

  1. Oracel用rownum实现真分页

    因为oracle的rownum是一个伪列,使用的时候如果要用必须查询出来显示的标记例如本sql中标记为 num. 值得一提的是最内层的这个查询sql:“select a.集团规范编码...”本身有一个 ...

  2. DOM中的范围 createRange()

    学习<JavaScript 高级程序设计> 12章dom范围的笔记 dom2级在Document类型中定义了 createRange()方法: 创建range对象很简单 var range ...

  3. js&&node set_cookie、get_cookie

    js: function set_cookie(key, val,now){ var exdate = new Date(now); exdate.setDate(exdate.getDate() + ...

  4. asp.net中的<%%>形式的详细用法实例讲解

    asp.net中的代码分离模式我们肯定都不陌生,C#(或者其它语言)写的代码一般不会和设计语言HTML混在一起,但是有的时候也避免不了,这时就会在UI页面里用<%%>来绑定显示.绑定变量数 ...

  5. 哈希表(hashtable)的javascript简单实现

    javascript中没有像c#,java那样的哈希表(hashtable)的实现.在js中,object属性的实现就是hash表,因此只要在object上封装点方法,简单的使用obejct管理属性的 ...

  6. Memcache,Redis

    Memcache Memcached 是一个高性能的分布式内存对象缓存系统,用于动态Web应用以减轻数据库负载.它通过在内存中缓存数据和对象来减少读取数据库的次数,从而提高动态.数据库驱动网站的速度. ...

  7. JSP中两种模式的总结

    运用JSP/Servlet实现的Web动态交互,主要采用: 模式一:JSP+JavaBean 链接:http://wxmimperio.coding.io/?p=155 模式二;JSP+Servlet ...

  8. 关于执行ST_Geometry的st_centroid函数时报ORA-28579错误的问题

    环境 SDE版本:10./10.2/10.2.1/10.2.2 Oracle版本:11g R2 11.2.0.1 Windows版本:Windows Server 2008 R2 问题描述及原因 以全 ...

  9. [BZOJ 3669] [Noi2014] 魔法森林 【LCT】

    题目链接:BZOJ - 3669 题目分析 如果确定了带 x 只精灵A,那么我们就是要找一条 1 到 n 的路径,满足只经过 Ai <= x 的边,而且要使经过的边中最大的 Bi 尽量小. 其实 ...

  10. Prefixes and Suffixes

    Codeforces Round #246 (Div. 2) D:http://codeforces.com/contest/432/problem/D 题意:给你一个长度不超过10^5的字符串.要你 ...