Android自定义View绘图基础
来源:互联网 发布:五星宏辉网络运行版 编辑:程序博客网 时间:2024/05/18 00:30
转载请说明出处!
作者:kqw攻城狮
出处:个人站 | CSDN
Android自定义View绘图基础
- Android自定义View绘图基础
- View的测量
- View的绘制
- 画笔属性
- Shader
- 点
- 直线
- 矩形
- 圆角矩形
- 圆
- 扇形
- 弧形
- 椭圆
- 文字
- 绘制路径
- 图形裁剪
View的测量
控件的测量可以说是固定写法,原生的View只支持EXACTLY
的测量模式,我们自定义的控件可以重写onMeasure
方法
@Overrideprotected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { setMeasuredDimension(getMeasuredSize(widthMeasureSpec), getMeasuredSize(heightMeasureSpec));}
onMeasure方法给我们返回的widthMeasureSpec
和heightMeasureSpec
,我们并不能直接拿过来使用,需要使用MeasureSpec
类进行解析,来获取测量后的具体值。
首先需要获取测量模式
MeasureSpec.getMode(measureSpec)
getMode方法返回是测量的模式,有以下3种类型:
- MeasureSpec.EXACTLY : 精确值模式(指定值/match_parent)
- MeasureSpec.AT_MOST : 最大值模式(wrap_content)
- MeasureSpec.UNSPECIFIED : 不指定大小的测量模式(一般用不上)
获取到了测量模式以后,获取测量后的大小
MeasureSpec.getSize(measureSpec)
根据上面的意思,可以封装我们的getMeasuredSize
方法
// 默认大小private static final int DEFAULT_SIZE = 200;/** * 获取测量后的大小 * * @param measureSpec measureSpec * @return measuredSize */private int getMeasuredSize(int measureSpec) { switch (MeasureSpec.getMode(measureSpec)) { case MeasureSpec.EXACTLY: // 精确值模式(指定值/match_parent) Log.i(TAG, "getMeasuredSize: 精确值模式"); return MeasureSpec.getSize(measureSpec); case MeasureSpec.AT_MOST: // 最大值模式(wrap_content) Log.i(TAG, "getMeasuredSize: 最大值模式"); return Math.min(DEFAULT_SIZE, MeasureSpec.getSize(measureSpec)); case MeasureSpec.UNSPECIFIED: // 不指定大小的测量模式 return DEFAULT_SIZE; default: return DEFAULT_SIZE; }}
现在我们自定义的View就支持自定义的大小了,包括match_parent
、wrap_content
、具体值
。
View的绘制
画笔属性
创建画笔
Paint paint = new Paint();
Shader
BitmapShader, ComposeShader, LinearGradient, RadialGradient, SweepGradient
点
/** * Helper for drawPoints() for drawing a single point. */public void drawPoint(float x, float y, @NonNull Paint paint)
canvas.drawPoint(10, 10, paint);
直线
绘制一条直线
/** * Draw a line segment with the specified start and stop x,y coordinates, * using the specified paint. * * <p>Note that since a line is always "framed", the Style is ignored in the paint.</p> * * <p>Degenerate lines (length is 0) will not be drawn.</p> * * @param startX The x-coordinate of the start point of the line * @param startY The y-coordinate of the start point of the line * @param paint The paint used to draw the line */public void drawLine(float startX, float startY, float stopX, float stopY, @NonNull Paint paint)
绘制多条直线
public void drawLines(@Size(multiple=4) @NonNull float[] pts, @NonNull Paint paint)
矩形
/** * Draw the specified Rect using the specified paint. The rectangle will * be filled or framed based on the Style in the paint. * * @param left The left side of the rectangle to be drawn * @param top The top side of the rectangle to be drawn * @param right The right side of the rectangle to be drawn * @param bottom The bottom side of the rectangle to be drawn * @param paint The paint used to draw the rect */public void drawRect(float left, float top, float right, float bottom, @NonNull Paint paint)
canvas.drawRect(100, 100, 200, 200, paint);
圆角矩形
/** * Draw the specified round-rect using the specified paint. The roundrect * will be filled or framed based on the Style in the paint. * * @param rx The x-radius of the oval used to round the corners * @param ry The y-radius of the oval used to round the corners * @param paint The paint used to draw the roundRect */public void drawRoundRect(float left, float top, float right, float bottom, float rx, float ry, @NonNull Paint paint)
canvas.drawRoundRect(100, 100, 200, 200, 20, 20, paint);
圆
/** * Draw the specified circle using the specified paint. If radius is <= 0, * then nothing will be drawn. The circle will be filled or framed based * on the Style in the paint. * * @param cx The x-coordinate of the center of the cirle to be drawn * @param cy The y-coordinate of the center of the cirle to be drawn * @param radius The radius of the cirle to be drawn * @param paint The paint used to draw the circle */public void drawCircle(float cx, float cy, float radius, @NonNull Paint paint)
// 画圆canvas.drawCircle(200, 200, 100, paint);
扇形
/** * <p>Draw the specified arc, which will be scaled to fit inside the * specified oval.</p> * * <p>If the start angle is negative or >= 360, the start angle is treated * as start angle modulo 360.</p> * * <p>If the sweep angle is >= 360, then the oval is drawn * completely. Note that this differs slightly from SkPath::arcTo, which * treats the sweep angle modulo 360. If the sweep angle is negative, * the sweep angle is treated as sweep angle modulo 360</p> * * <p>The arc is drawn clockwise. An angle of 0 degrees correspond to the * geometric angle of 0 degrees (3 o'clock on a watch.)</p> * * @param startAngle Starting angle (in degrees) where the arc begins * @param sweepAngle Sweep angle (in degrees) measured clockwise * @param useCenter If true, include the center of the oval in the arc, and close it if it is being stroked. This will draw a wedge * @param paint The paint used to draw the arc */public void drawArc(float left, float top, float right, float bottom, float startAngle, float sweepAngle, boolean useCenter, @NonNull Paint paint)
// 扇形 起始角度0度 旋转角度120度canvas.drawArc(100, 100, 200, 200, 0, 120, true, paint);
弧形
扇形通过调整属性,可以实现弧形的效果,首先画笔设置成空心
// 空心paint.setStyle(Paint.Style.STROKE);
设置画扇形的useCenter
参数为false
// 弧形 起始角度0度 旋转角度120度canvas.drawArc(100, 100, 200, 200, 0, 120, false, paint);
椭圆
/** * Draw the specified oval using the specified paint. The oval will be * filled or framed based on the Style in the paint. */public void drawOval(float left, float top, float right, float bottom, @NonNull Paint paint)
// 椭圆canvas.drawOval(100, 100, 500, 300, paint);
文字
/** * Draw the text, with origin at (x,y), using the specified paint. The * origin is interpreted based on the Align setting in the paint. * * @param text The text to be drawn * @param x The x-coordinate of the origin of the text being drawn * @param y The y-coordinate of the baseline of the text being drawn * @param paint The paint used for the text (e.g. color, size, style) */public void drawText(@NonNull String text, float x, float y, @NonNull Paint paint)
// 文字paint.setTextSize(30);paint.setColor(Color.BLACK);canvas.drawText("KongQingwei", 100, 100, paint);
在指定位置显示每个字符
/** * Draw the text in the array, with each character's origin specified by * the pos array. * * @param text The text to be drawn * @param pos Array of [x,y] positions, used to position each character * @param paint The paint used for the text (e.g. color, size, style) * * @deprecated This method does not support glyph composition and decomposition and * should therefore not be used to render complex scripts. It also doesn't * handle supplementary characters (eg emoji). */@Deprecatedpublic void drawPosText(@NonNull String text, @NonNull @Size(multiple=2) float[] pos, @NonNull Paint paint)
canvas.drawPosText("KongQingwei", new float[]{ 30,30, 60,60, 90,90, 120,120, 150,150, 180,180, 210,210, 240,240, 270,270, 300,300, 330,330}, paint);
绘制路径
可以自定义画出想要的任意图形
五角星
/** * Draw the specified path using the specified paint. The path will be * filled or framed based on the Style in the paint. * * @param path The path to be drawn * @param paint The paint used to draw the path */public void drawPath(@NonNull Path path, @NonNull Paint paint)
Path path = new Path();path.moveTo(0,100);path.lineTo(250,300);path.lineTo(150,0);path.lineTo(50,300);path.lineTo(300,100);path.lineTo(0,100);canvas.drawPath(path,paint);
空心
paint.setStyle(Paint.Style.STROKE);
图形裁剪
以上面的实心五角星为例,以五角星的中心为圆心,裁剪出一个半径为100的圆形
/** * Modify the current clip with the specified path. * * @param path The path to operate on the current clip * @param op How the clip is modified * @return true if the resulting is non-empty */public boolean clipPath(@NonNull Path path, @NonNull Region.Op op)
// 裁剪一个圆形Path path = new Path();path.reset();path.addCircle(150, 150, 100, Path.Direction.CCW);canvas.clipPath(path, Region.Op.INTERSECT);// canvas.save();// 画五角星path.reset();path.moveTo(0,100);path.lineTo(250,300);path.lineTo(150,0);path.lineTo(50,300);path.lineTo(300,100);path.lineTo(0,100);canvas.drawPath(path,paint);
0 0
- Android自定义View绘图基础
- Android 自定义View绘图篇之基础
- 0916Android基础自定义View(Canvas绘图)
- Android自定义View绘图基础(摘自技术前沿)
- Android绘图系列(一)——自定义View基础
- 自定义view—绘图基础Canvas+Paint
- 自定义View-绘图基础之Path
- Android自定义View基础
- android--View自定义基础
- android自定义View基础
- Android 自定义View(基础)
- Android自定义View基础
- Android自定义view基础
- Android的绘图机制学习---自定义View
- Android 自定义View绘图篇之进阶
- Android自定义View和Canvas绘图解析
- 自定义View基础(三)View的绘图篇
- Android绘图机制(一)——自定义View的基础属性和方法
- PL/SQL
- linux下创建用户
- leetcode 之 python篇1
- 海康相机的二次开发
- 5天时间让1000精准客源主动找上你
- Android自定义View绘图基础
- IOS 应用 上架App Store
- shell 脚本截取指定分隔符的第几项
- discovery of a magically Fast source!!!!!!!!!!!!!!!!!!
- 类变量的初始化时机
- gstreamer学习笔记:分享几个appsink和appsrc的example
- QFP封装芯片手工焊接和拆卸技巧
- 开始记录工作的使用的一些比较妙的英语单词或词组
- springMVC前后台交互