持续创作,加速成长!这是我参与「掘金日新计划 · 10 月更文挑战」的第7天,点击查看活动详情
Android 自定义view 大致会经历 measure :对 view进行测量 ,Layout:对测量后的view 进行摆放 ,draw:在画布上进行具体的绘制
接下来在draw 方法中 会传入 一个canvas 参数 ,这个canvas就是所有绘制的基础 ,然而canvas 的绘制的api之中都有一个参数paint,这个paint 参数就可以设置所绘画内容的颜色 ,粗细,字形,质量.....
可以理解为canvas 是绘画的骨架 ,paint 来进行上色
paint类常用方法
设置绘制模式
-
Paint.setStyle(Style style) 设置绘制模式
参数
- Paint.Style.STROKE 划线模式(不填充)
- Paint.Style.FILL 填充模式 (默认)
- FILL_AND_STROKE
设置颜色
-
Paint.setColor("颜色")
- 可以用Clolor.BLACK(内部自带的静态对象)
- 也可以Color.Prase("#88880000")
-
Paint.setARGB(a,r,g,b);
- 四个参数值均为int 类型 分别为 透明度 和 RGB三元素
设置抗锯齿
- Paint.setAniAlias(boolean a) 设置抗锯齿开关
总体来说开启看锯齿后绘制的图形会变的更加丝滑一些,所以此项应该开启
-
也可以:
Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
其他一些常用API
- Paint.setTextSize(float textSize) 设置文字大小
- Paint.setStrokeWidth(float width) 设置线条宽度
paint 设置颜色渐变
1.1 线性渐变
构造方法: LinearGradient(float x0, float y0, float x1, float y1, int color0, int color1, Shader.TileMode tile) 。
参数: x0 y0 x1 y1:渐变的两个端点的位置 color0 color1 是端点的颜色 tile:端点范围之外的着色规则,类型是 TileMode。TileMode 一共有 3 个值可选: CLAMP, MIRROR 和 REPEAT。CLAMP 会在端点之外延续端点处的颜色 (这个单词好奇怪 是不是?);MIRROR 是镜像模式;REPEAT 是重复模式。
Shader shader = new LinearGradient(0, 0, 400, 400, Color.parseColor("#E91E63"),
Color.parseColor("#2196F3"), Shader.TileMode.CLAMP);
paint.setShader(shader);
利用线性渐变我们可以实现如下效果 ,tag 标签 渐变颜色
关于tag 标签如何使用可以查看我的另外一篇文章 RecyclerView分割线详解| 青训营笔记 - 掘金 (juejin.cn)
1.2 辐射渐变:
Shader shader = new RadialGradient(300, 300, 200, Color.parseColor("#E91E63"),
Color.parseColor("#2196F3"), Shader.TileMode.CLAMP);
paint.setShader(shader);
...
canvas.drawCircle(300, 300, 200, paint);
构造方法: RadialGradient(float centerX, float centerY, float radius, int centerColor, int edgeColor, TileMode tileMode)。
参数: centerX centerY:辐射中心的坐标 radius:辐射半径 centerColor:辐射中心的颜色 edgeColor:辐射边缘的颜色 tileMode:辐射范围之外的着色模式。
sweepGradient 扫描渐变
SweepGradient(float cx, float cy, int color0, int color1)
参数: cx cy :扫描的中心 color0:扫描的起始颜色 color1:扫描的终止颜色
BitmapShader(bitmap 着色器)
可以于绘制圆形图像
Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.bitmap);
Shader shader = new BitmapShader(bitmap, Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
paint.setShader(shader);
...
canvas.drawCircle(300, 300, 200, paint);//可以绘制圆形图片
//除此之外可以绘制不同形状的图片
构造方法: BitmapShader(Bitmap bitmap, Shader.TileMode tileX, Shader.TileMode tileY)
参数: bitmap:用来做模板的 Bitmap 对象 tileX:横向的 TileMode tileY:纵向的 TileMode。
Matrix matrix=new Matrix();
matrix.setScale(scaleX,scaleY);
shader.setLocalMatrix(matrix);//设置放缩
paint.setStyle(Paint.Style.FILL);
paint.setShader(shader);
在shader 我们说指定的绘制区域 只要我们的画笔经过都会是渐变颜色
setColorFilter
这个可以理解为一种对自定义view绘制内容的滤镜效果
Paint.setColorFilter(ColorFilter filter)
这里的 filter是使用他的子类LightingColorFilter PorterDuffColorFilter 和 ColorMatrixColorFilter。
-
LightingColorFilter
源码文档
/** * Create a colorfilter that multiplies the RGB channels by one color, * and then adds a second color. The alpha components of the mul and add * arguments are ignored. */ public LightingColorFilter(@ColorInt int mul, @ColorInt int add) { mMul = mul; mAdd = add; }
简单来说
mul用来和目标像素相乘,add用来和目标像素相加
这段代码修饰的Paint画出的图为原图
paint=new Paint();
ColorFilter lightingColorFilter = new LightingColorFilter(0xffffff, 0x000000);//乘的倍数为1 ,加的数值为0
paint.setColorFilter(lightingColorFilter);
效果
例如 绘制一张图片,我们添加蓝色的滤镜效果 把add参数的中间两位改为ff
public class myView extends View {
public myView(Context context) {
super(context);
}

public myView(Context context, @Nullable AttributeSet attrs) {
super(context, attrs);
}
public myView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) {
super(context, attrs, defStyleAttr);
}
Bitmap bitmap;
Paint paint;
{
bitmap = BitmapFactory.decodeResource(getResources(),R.mipmap.bitmap);
paint=new Paint();
ColorFilter lightingColorFilter = new LightingColorFilter(0xffffff, 0x00ff00);
paint.setColorFilter(lightingColorFilter);
}
@Override
protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
canvas.save();
canvas.scale(0.5f,0.5f);
canvas.drawBitmap(bitmap,0,0,paint);
canvas.restore();
}
}
效果如图
ox即代表 这个数为16进制的数,由这个数的位数可以看出,这个数只有RGB通道,并没有 alpha 通道