Android控件架构
1. Android UI界面架构
UI界面架构图:
Activity -- PhoneWindow -- DecorView
| -- TitleView
| -- ContentView
- PhoneWindow将DecorView设置为整个应用窗口的根View
- DecorView将要显示的内容呈现在PhoneWindow中
- View的监听事件通过WindowManagerService来进行接收,通过Activity对象来回调相应的onClickListener
- ContentView是一个id为content的FrameLayout,activity_main.xml被设置在里面
DecorView详细视图:
DecorView -- LinearLayout
| -- ActionBar Container -- ActionBar
| -- FramentLayout -- activity_main.xml
2. View绘制流程
| --- 背景 drawBackground() 不能重写 --- |
| |
| --- 主体 onDraw() 可以重写 --- |
draw() ---- | |
| --- 子View dispatchDraw() 可以重写 --- |
可以重写 | |
| --- 滚动条 onDrawForeground() 可以重写 --- |
| --- 前景 onDrawForeground() 可以重写 --- |
- 出于效率的考虑,ViewGroup 默认会绕过 draw() 方法换而直接执行 dispatchDraw(),以此来简化绘制流程。
- 调用 setWillNotDraw(false)可以切换到完整的draw()流程
3. View事件拦截机制
事件拦截机制涉及到的函数
- ViewGroup
- public boolean dispatchTouchEvent(MotionEvent ev);//事件传递
- public boolean onInterceptTouchEvent(MotionEvent ev);//事件拦截
- public boolean onTouchEvent(MotionEvent ev);//事件处理
- View
- public boolean dispatchTouchEvent(MotionEvent ev);//事件传递
- public boolean onTouchEvent(MotionEvent ev);//事件处理
假设有ViewGroupA ViewGroupB View他们关系如下
ViewGroupA -- ViewGroupB -- View
如果不进行任何修改执行结果如下
ViewGroupA dispatchTouchEvent
ViewGroupA onInterceptTouchEvent
ViewGroupB dispatchTouchEvent
ViewGroupB onInterceptTouchEvent
View dispatchTouchEvent
View onTouchEvent
ViewGroupB onTouchEvent
ViewGroupA onTouchEvent
如果将 ViewGroupA onInterceptTouchEvent返回值改为true,结果如下
ViewGroupA dispatchTouchEvent
ViewGroupA onInterceptTouchEvent
ViewGroupA onTouchEvent
如果将 ViewGroupB onInterceptTouchEvent返回值改为true,结果如下
ViewGroupA dispatchTouchEvent
ViewGroupA onInterceptTouchEvent
ViewGroupB dispatchTouchEvent
ViewGroupB onInterceptTouchEvent
ViewGroupB onTouchEvent
ViewGroupA onTouchEvent
如果将 View onTouchEvent返回值改为true,结果如下
ViewGroupA dispatchTouchEvent
ViewGroupA onInterceptTouchEvent
ViewGroupB dispatchTouchEvent
ViewGroupB onInterceptTouchEvent
View dispatchTouchEvent
View onTouchEvent
如果将 ViewGroupB onTouchEvent返回值改为true,结果如下
ViewGroupA dispatchTouchEvent
ViewGroupA onInterceptTouchEvent
ViewGroupB dispatchTouchEvent
ViewGroupB onInterceptTouchEvent
View dispatchTouchEvent
View onTouchEvent
ViewGroupB onTouchEvent
总结:
- dispatchTouchEvent是一个向下传递的过程
- onTouchEvent是向上传递的过程
- onInterceptTouchEvent是在向下传递时候进行拦截操作
- 如果onInterceptTouchEvent 返回true,则事件不会向下传递,直接交由 onTouchEvent处理后向上传递
- 如果onTouchEvent 返回true,则事件不会向上传递
4.自定义View绘制
东西太多,贴个参考网址:http://hencoder.com/
补充:
- Android的绘制API借鉴了很多ps中的概念,所以最好了解一下。
- Canvas.save() 将之前绘制的图像保存起来,之后的的绘制操作就好像再新一层图层上进行,相当于ps中的保存图层。
- Canvas.restore() 将save之后绘制的图像与save的图像合并,相当于ps的合并图层。
- Canvas.translate() 移动视图坐标系,主要用来方便绘制
- Canvas.rotate() 旋转视图坐标系,主要用来方便绘制
- 图像处理
- ColorMatrix 颜色变化矩阵、实现的效果有:灰度效果、图像反转、怀旧效果、去色效果、高饱和度效果。还可以通过像素点分析实现:底片效果、老照片效果、浮雕效果
- Matrix 变形矩阵、实现图片平移、旋转、缩放、错切
- PorterDuffXfermode 设置2个图层交集显示方式、常见的抠图就可以通过他实现
- Shader 渲染器、实现一些渐变、渲染效果
- BitmapShader 位图Shader
- LinearGradient 线性Shader
- RadialGradient 光束Shader
- SweepGradient 梯度Shader
- ComposeShader 混合Shader,用来组合上面的效果
- PathEffect 路径的一些效果
- CornerPathEffect 路径的拐角变的圆滑
- DiscretePathEffect 路径上产生许多杂点
- DashPathEffect 路径为虚线
- PathDashPathEffect 和上面一样,但是可以设置虚线的图形,比如虚线的每个点是三角形
- ComposePathEffect 用来组合上面的效果
网友评论