View 的绘制系列文章:
Android View 绘制流程之 DecorView 与 ViewRootImpl
Android View 的绘制流程之 Measure 过程详解 (一)
Android View 的绘制流程之 Layout 和 Draw 过程详解 (二)
Android View 的事件分发原理解析
对于 Android 开发者来说,原生控件往往无法满足要求,需要开发者自定义一些控件,因此,需要去了解自定义 view 的实现原理。这样即使碰到需要自定义控件的时候,也可以游刃有余。
基础知识 自定义 View 分类
自定义 View 的实现方式有以下几种:
类型 定义自定义组合控件 多个控件组合成为一个新的控件,方便多处复用
继承系统 View 控件 继承自TextView等系统控件,在系统控件的基础功能上进行扩展
继承 View 不复用系统控件逻辑,继承View进行功能定义
继承系统 ViewGroup 继承自LinearLayout等系统控件,在系统控件的基础功能上进行扩展
继承 View ViewGroup 不复用系统控件逻辑,继承ViewGroup进行功能定义
从上到下越来越难,需要的了解的知识也是越来越多的。
构造函数当我们在自定义 View 的时候,构造函数都是不可缺少,需要对构造函数进行重写,构造函数有多个,至少要重写其中一个才行。例如我们新建 MyTextView:
/** * 在java代码里new的时候会用到 * @param context */ public MyTextView(Context context) { super(context); } /** * 在xml布局文件中使用时自动调用 * @param context */ public MyTextView(Context context, @Nullable AttributeSet attrs) { super(context, attrs); } /** * 不会自动调用,如果有默认style时,在第二个构造函数中调用 * @param context * @param attrs * @param defStyleAttr */ public MyTextView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) { super(context, attrs, defStyleAttr); } /** * 只有在API版本>21时才会用到 * 不会自动调用,如果有默认style时,在第二个构造函数中调用 * @param context * @param attrs * @param defStyleAttr * @param defStyleRes */ @RequiresApi(api = Build.VERSION_CODES.LOLLIPOP) public MyTextView(Context context, @Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes) { super(context, attrs, defStyleAttr, defStyleRes); }