UI界面,对于每个应用而言,是它与用户进行交互的门脸。好的门脸,不只是是要亮丽可人,最好还能秀色可餐过目不忘,甚至还应该有涵养有气质,彬彬有理温柔耐心。

  对于开发者来说,锻造这样的面容,不但需要高超的技艺,也需要有称手的工具和对得起党的料子。俗话说,朽木不可雕也,芙蓉不是一日炼成的,不是什么平台都能叫特能书。有套好用的UI框架,对于开发者而言,真有如沙漠中的甘露,而要是撞见了杯具的UI套件,整个界面开发就有如梦魇了。

  Android的UI框架,最核心的,是资源和Layout体系,然后,通过完善的控件库,简明的接口设计,进一步帮助开发者,能够最快的搭建自己需要界面(听到这里,Symbian同学开始钻土。..)。

  UI控件

  做UI,有时候就像搭积木,在Android中,这个最原子的积木块,就是View。所有其他的UI元素,都是派生于此类的子孙类们。

又从SDK中偷来张图,用来描述Android的UI控件结构,在每一个window下,这都是一个标准而完整的树结构。View有一个子类ViewGroup,它相当于一个容器类或者是复合控件,所有派生与ViewGroup的子类在这颗UI树中都可以承担着父节点的职责,而另一些绕过ViewGroup从View直通下来的,就只能蜷局在叶节点的范畴内了。

如上图所示,假设你做了个如同虚线框中结构的一个界面,通过Activity的setContentView方法,塞进了Activity中,就会形成图示的一个逻辑关系。每一个Activity,都包含一个Window对象,它表示的是一个顶级的一整屏幕上面的界面逻辑。在Android源码中,其实现是MidWindow,它包含了一个FrameLayout对象,呈现出来就是那种带着一个title的界面样子。自定义的一堆控件,会插进Window的界面部分,在Activity中,所有事件的处理逻辑,是Window先享用,没消费掉在交由这堆控件吃剩的。

  在整个控件树的最顶端,是一个逻辑的树顶,ViewParent,在源码中的实现是ViewRoot。它是整个控件树和WindowManager之间的事件信息的翻译者。WindowManager是Android中一个重要的服务。它将用户的操作,翻译成为指令,发送给呈现在界面上的各个Window。Activity,会将顶级的控件注册到WindowManager中,当用户真是触碰屏幕或键盘的时候,WindowManager就会通知到,而当控件有一些请求产生,也会经由ViewParent送回到WindowManager中。从而完成整个通信流程。

  之所有说这是一个很标准的控件树,是因为父控件对子控件有绝对的掌控权,每个子控件的占地面积和位置,都是基于父控件来分配的,它能够接受和处理的事件,也是父控件派发下去的。这样的结构,被很多平台和框架广泛的认可,和传统的win开发和杯具的Symbian相比,虽然因为事件传播途径变长了,很多操作的效率变低了,但整个结构更有层次性,每个控件只需要多其父控件负责指挥子控件就好,职责明确,逻辑简单,利于开发和设计。

  谈及任何平台的控件,都有一些不可避免的主题,比如,每个控件如何标识,如何设定大小和位置,如何接受和处理事件,如何绘制,诸如此类。

  标识

  在Android中,你可以为每个控件选择设定一个id,这个id的全局的唯一性不需要保证,但在某个局部的范围内具有可识别性,这样就可以通过这个id找到这个控件(如果不需要查找,就别设置了。..)。

  但是,在父控件中逐级的find比较,找到id匹配的控件,然后再做转型,是一个比较重量的操作,于是Android又为控件憋出另一个属性,tag。它接受任意object类型的数据,你可以把和这个控件对象相关的内容堆在里面。比如,在list中,我们常常将和每个list item相关的所有控件元素封装成一个object,扔到tag中,就不需要每次都去比较id进行寻找,更加高效快捷。

  尺寸

  在Android中,控件最重要的大小属性,就是width/height,开发者可以明确的指明控件的大小,可以设定成为fill_parent和wrap_content,这样的概念性的大小。丈量并设定控件的位置,是通过两步来进行的。

  第一步是measure。它传入此控件的width/height信息,控件会根据自己的参数,计算出真实需要的width/height,然后调用setMeasuredDimension方法,缓存成成员变量,留作后用。

  在计算出大小之后,会进行另一个步骤,layout。在这个过程中,父控件会计算其上各个子控件的位置,从而完成整个大小和位置的确定流程。整个measure和layout的流程,都是自上到下,从树顶往叶子来推进的。

  当开发人员需要自定义控件的时候,可能需要关注这些内容,通过重载onMeasure和onLayout方法,可以定义自己控件的丈量方式。

  事件

  在Android中,所有的按键,触屏等事件,都是从顶至下进行分发的。每个ViewGroup的对象,会维系一个focused变量,它表示在这个父控件中具备focus的控件,当有按键时间发生的时候,会找到这个focused子控件,并传递给它。同理,触屏事件的分发也是类似,只不过和focus无关,父控件会遍历所有子控件,看看谁处于触碰位置,从而传递给谁。

  另外还有一些事件,逻辑上并不是从顶至下发起的。比如,当你修改某个子控件的内容,使得该子控件的大小和内容都发生了变化,就需要进行控件的重排和重绘,这些操作不仅是子控件自己的事情,需要整个控件树上的所有控件都需要配合。在Android中,处理这类事情的实现策略是子控件维系一个ViewParent对象,该对象象征着整个控件树的管理者,子控件产生影响整个控件树的事件时,会通知到ViewParent,ViewParent会将其转换成一个自顶向下的事件,分发下去。

  Android的事件处理逻辑,采用的是观察者模式。Android的控件提供了一些列的add/set Listener的接口,使得外部观察者,有机会处理控件事件。比如,你需要在某个button被点击时做一些事情,你就需要派生一个View.OnClickListener对象作为观察者,调用该控件的setOnClickListener接口注册进去,当button被点击,就可以获得处理点击事件的机会了。当然,有的时候,你需要处理的逻辑更为复杂,光是站在外面围观叫好不能解决问题,可能就需要派生某个控件,去重载onXXXX之类的事件处理函数,进行更完整的控制。

  焦点

  对于一个非触屏的机器,焦点的维系是一个极其重要的事情,而在有触屏的年代,焦点的地位虽有所下降,但依然还是需要妥善保护的。

  Android中,是以控件树为单位,来管理焦点的。每个控件,可以设置上下左右四向的focus转移对象。当在一个控件上发生焦点转移事件,Android会如前述,自顶向下根据设定好的焦点转移逻辑,跳转到正确的控件上。和Symbian相比,真是,真是。。。

  Layout

  Layout是一类特殊的ViewGroup控件,它们本身没有任何可显示内容,形如透明的玻璃盒子,存活的唯一理由,就是其中的内部结构,能够更好的摆放它的子控件们。

  比如线性的Layout,LinearLayout。放入这个Layout的子控件,会按水平或垂直方向,排排坐,一个挨着一个按顺序排列下去。TableLayout,可以将子控件按照表格的形式,一枚枚放置好。而RelativeLayout则更灵活,可以设定各个控件之间的对齐和排列关系,适合定制复杂的界面。

  有了Layout的存在,控件和控件之间不再割裂的存在,而是更有机的结合在了一起,设定起来也更为方便。比Symbian那样人肉维系各个控件的关系,轻松自在多了。

  更多

  这些问题的完整答案,参见SDK中View的页面:/reference/android/view/View.html。

http://developer.android.com/guide/topics/ui/index.html

  实现

  有了这些对Android的UI控件的认知,可以看更整体性的实现细节,那就是Activity的UI实现。

Android UI框架深度解析相关推荐

  1. 太全了,一线互联网大厂都在用的Android UI框架完全解析,拿去吧你

    在学习Android过程中,会使用到很多UI框架,而使用时对框架的实现方式应有一定的了解,这个过程最好的方式就是阅读源码,学习大厂的使用方法.但UI框架很多,不时会有新的出现,而且对一些通用框架来说, ...

  2. 得到谷歌认证的《Android UI框架进阶解密》开源了,亮瞎我的钛合金

    根据调查显示,,iOS与Android的市场份额差距正越来越大.Android设备正在成为手机应用市场的主力军.如何从设计层面创造一个优美的App界面来吸引用户已然成为广大App开发者们必做的功课之一 ...

  3. 【Android】Handler 深度解析

    [Android]Handler 深度解析 前言 Handler 可以说贯穿了整个 Android 系统,在 Android 中扮演着相当重要的角色.我们开发中接触到的四大组件如 Activity.S ...

  4. 腾讯 android ui,腾讯开源的Android UI框架——QMUI Android

    各位同学,早上好,我是你们的老朋友D_clock爱吃葱花,前些天忙着发版本,最近也在看各种各样的新知识,有好多东西想写啊啊啊啊啊.嗯,先冷静捋一下,卖个关子.扯回正题,今天继续为大家推荐一个Githu ...

  5. android ui框架详解,多图详解 “Android UI”设计官方教程(二)

    编者注:本文为Android的官方开发者博客发了一份幻灯片的翻译文档的第二部分,专门介绍了一些Android UI设计的小贴士,我们在介绍这个幻灯片的第一部分<多图详解 "Androi ...

  6. 推荐一个腾讯出品的Android UI框架 —— QMUI

    近期发现了一个腾讯出品的Android UI框架库,旨在快速开发,这些没有什么可多说的.(在最后附上SDK官网和GitHub地址)说几个比较常用的,具体的可以去看官方的文档: UI类 QMUIFloa ...

  7. Android UI框架集结

    Android UI框架集结 通过这些框架,感觉自己菜出了底线- Android Studio Android Studio可将导入jar包变成简单的一行代码: 在app/build.gradle文件 ...

  8. GitHub标星5.6K,2020腾讯又一力作开源的Android UI框架——QMUI Android

    各位同学,早上好,我是你们的老朋友D_clock爱吃葱花,前些天忙着发版本,最近也在看各种各样的新知识,有好多东西想写啊啊啊啊啊.嗯,先冷静捋一下,卖个关子.扯回正题,今天继续为大家推荐一个Githu ...

  9. 腾讯开源android项目管理,腾讯开源的Android UI框架——QMUI Android

    各位同学,早上好,我是你们的老朋友D_clock爱吃葱花,前些天忙着发版本,最近也在看各种各样的新知识,有好多东西想写啊啊啊啊啊.嗯,先冷静捋一下,卖个关子.扯回正题,今天继续为大家推荐一个Githu ...

最新文章

  1. ROS2概述和实践入门
  2. linux重命名命令
  3. 与老外交谈的常用句子
  4. 傻瓜式制作的U盘winpe(支持4G以上U盘)--速度超快
  5. linux下watch常见用法,watch命令详解(linux)
  6. 【转】linx 设备名字来由 sd sr sg st
  7. 快速判断一个数是否是2的幂次方
  8. python的一些问题解决方法
  9. leetcode 374. Guess Number Higher or Lower 、375. Guess Number Higher or Lower II
  10. 字节跳动 AI Lab 21届校招启动啦!
  11. JavaWeb出现404一个很隐蔽的原因
  12. html文本框部分字体变颜色,实现文本框内,部分字体颜色、字号等自定义
  13. Atitit BLE 协议栈 艾提拉总结 目录 1. ——关于BLE的一些基本概念——
  14. JSP-tomcat设置编码格式 配置utf-8(以防网页框以及网页显示的时候中文乱码)
  15. 客户需求分析工具-$APPEALS
  16. 企业微信小程序 windows 使用 vconsole 调试
  17. BIOS 从FFFF0H处开始执行指令的理解
  18. Your Command Line Tools are too outdated
  19. 卢松松博客专访胡茬:解密程序员互联网创业历程
  20. 如何在 Linux 中查找一个文件

热门文章

  1. 大数据与算法系列之海量数据查找算法
  2. js代码 实现购物车功能
  3. 致所有看到这段话的朋友们
  4. js 定时器的开启与关闭
  5. vue尚品汇商城项目-day04【29.加入购物车操作(难点)】
  6. WPF 用户控件和 WPF自定义控件区别
  7. Ubuntu 20.10 引导修复(boot repair)
  8. NetToPlcSim_PLC_西门子PLC访问DEMO
  9. 夜神模拟器开机全屏并自启动自己的app
  10. CSS预处理器之Sass与Less