1、前言
最近发现自己如同并不是很会自界说View这一块捏,像个癌症晚期患者上不去,下不来,就卡那儿了,所以特发此篇文章学习和共享一下自界说View。
2、概述
我将自界说View分为三个过程:
- 自界说View特点以及获取
- 重写View的onDraw办法
- 重写View的onMeasure办法
本篇将说明自界说View特点以及获取
3、自界说View特点以及获取
自界说View特点
首要在选中项目目录中的values文件夹并新建attrs资源文件。如下图:
Ok,创立完成后咱们会看到这样的内容:
<?xml version="1.0" encoding="utf-8"?>
<resources></resources>
之后就需求咱们在里面声明咱们需求的自界说特点了。 特点的声明格式如下:
<attr name="xxxx" format="xxxx"/>
-
name:便是你想要声明特点的姓名,到时候获取对应特点依托的便是这个name。
-
format:声明特点的格式,表明你这个特点它详细是什么,像色彩、字符串或者是其他的类型,可是这个format并不是随意给值的,一下是format的详细可取值的范围:
format format类型 color 表明色彩 string 表明字符串 boolean 表明布尔值 reference 表明引证(如drawable dimension 表明尺寸 float 表明浮点类型 integer 表明整形 fraction 表明百分数 enum 表明枚举 flags 表明位运算
声明特点的办法有多种,这儿给出最常用的两种办法:
-
普通写法
<!--布景色彩--> <attr name="solid_color" format="color"/> <!--文字--> <attr name="text" format="string"/> <!--文字色彩--> <attr name="text_color" format="color"/> <!--文字大小--> <attr name="text_size" format="dimension"/>
-
declare-styleable 标签封装 attr
<declare-styleable name="MyCustomView"> <!--布景色彩--> <attr name="solid_color" format="color"/> <!--文字--> <attr name="text" format="string"/> <!--文字色彩--> <attr name="text_color" format="color"/> <!--文字大小--> <attr name="text_size" format="dimension"/> </declare-styleable>
完成之后,咱们去创立一个自界说的View,本文类名为MyCustomView承继View,之后补全结构办法即可。
获取自界说特点
首要依据第一步中咱们创立的特点在MyCustomView中创立对应的目标:
private int mSolidColor; //布景色彩
private String mText; //文字
private int mTextColor; //文字色彩
private float mTextSize; //文字大小
private Paint mPaint; //画笔
private Rect mTextBound; //接受文字鸿沟
然后写一个获取自界说特点的办法给结构办法调用:
private void obtainAttrs(Context context, AttributeSet attrs) {
}
接着便是最重要的过程——运用创立TypedArray目标并用其获取到咱们创立的特点然后应用到画笔中:
-
普通写法获取特点:
int[] attrsKey = new int[]{R.attr.solid_color, R.attr.text, R.attr.text_color, R.attr.text_size}; TypedArray a = context.obtainStyledAttributes(attrs, attrsKey); mSolidColor = a.getColor(0, 0xFF000000); mText = a.getString(1); mTextColor = a.getColor(2, 0xFFFFFFFF); mTextSize = a.getDimension(3, 14F); a.recycle();
其间attrsKey代表自界说特点的调集,在context的obtainStyledAttributes办法中依托这个调集的索引来获取详细的特点
-
带有declare-styleable标签获取特点:
TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.MyCustomView); mSolidColor = a.getColor(R.styleable.MyCustomView_solid_color, 0); mText = a.getString(R.styleable.MyCustomView_text); mTextColor = a.getColor(R.styleable.MyCustomView_text_color,0xFFFFFFFF); mTextSize = a.getDimension(R.styleable.MyCustomView_text_size,sp2px(14)); a.recycle();
其间MyCustomView是自界说特点中你声明的标签姓名,在后续获取详细的特点时传入的参数格式就为“声明的styleable名称_自界说特点名“ 应用到画笔中:
mPaint = new Paint();
mPaint.setTextSize(mTextSize); //设置文字大小
mTextBound = new Rect();
mPaint.getTextBounds(mText, 0, mText.length(), mTextBound);//丈量文字鸿沟
获取到TypedArray目标之后就能够运用它的办法来获取对应的特点,这些办法一般都需求索引(index以及一个默认值,最终最重要的一点便是在用完TypedArray目标之后必定必定要记住收回:
a.recycle();//收回
最终重写onDraw,画一个简单的带布景的文字图形:
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
mPaint.setColor(mSolidColor);//布景色彩
canvas.drawRect(0, 0, getMeasuredWidth(), getMeasuredHeight(), mPaint);//制作布景
mPaint.setColor(mTextColor);//文字色彩
canvas.drawText(mText, getWidth() / 2 - mTextBound.width() / 2, getHeight() / 2 + mTextBound.height() / 2, mPaint);//制作文字
}
在布局文件引入咱们的自界说View:
<?xml version="1.0" encoding="utf-8"?>
<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/white"
tools:context=".MainActivity">
<com.my.mycustomview.MyCustomView
android:layout_width="200dp"
android:layout_height="200dp"
app:solid_color="@color/black"
app:text="AAA"
app:text_color="@color/white"
app:text_size="25sp"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>
效果图如下:
4、更多
复用自界说特点
当咱们一个自界说View有许多承继的子类,这些字类有共用的特点时能够选择复用自界说特点(以本文中的MyCustomView举例:
<!--布景色彩-->
<attr name="solid_color" format="color"/>
<!--文字-->
<attr name="text" format="string"/>
<!--文字色彩-->
<attr name="text_color" format="color"/>
<!--文字大小-->
<attr name="text_size" format="dimension"/>
<declare-styleable name="MyCustomView">
<attr name="solid_color"/>
<attr name="text"/>
<attr name="text_color"/>
<attr name="text_size"/>
</declare-styleable>
<!--另一个View-->
<declare-styleable name="XXXView">
<attr name="solid_color"/>
<attr name="text"/>
<attr name="text_color"/>
<attr name="text_size"/>
<!--特有特点-->
<attr name="xxxx" format="xxxx"/>
</declare-styleable>
这样共用的特点不必重复界说,在取值的时候只需求改变你声明的styleable姓名即可:
TypedArray a = context.obtainStyledAttributes(attrs, R.styleable.XXXView);
关于attrs
以第3点中的attrs为例子,attr 标签特点会在R类下的attr类中生成16进制地址静态常量:
而运用declare-styleable封装的attr会在R类下的styleable类封装attr类下的16进制地址生成int[]数组,并生成下标索引:
完毕
那么到这儿这篇内容就完毕了,在这篇文章中讲述了自界说View的根本过程,以及如何自界说特点和如何获取这些特点,关于重写onDraw办法会放到下一章节说明,时间不定,作者懒狗一条,拜拜捏!