当前位置:   article > 正文

自定义View (四): onDraw 之 Canvas画布_ondraw()保存canvas

ondraw()保存canvas
前面我们了解了自定义View的onDraw之paint方法,接下来我们看一下一个比较重要的方法Canvas。
一:认识下Canvas。
Canvas类简单理解就标示一块画布,用paint(画笔)在上面画我们想画的东西,Canvas的方法有很多,可以绘制很多对象,比如:
1.弧线(arcs)
2.填充颜色(grab和color)
3.Bitmap
4.圆(circle和oval)
5.点(point)
6.线(line)
7.矩形(Rect)
8.图片(Picture)
9.圆角矩形 (RoundRect)
10.文本(text)
11.顶点(Vertices)
12.路径(path)
canvas.save():把当前的绘制的图像保存起来,让后续的操作相当于是在一个新的图层上的操作。
canvas.restore(); 把当前画布返回(调整)到上一个save()状态之前
canvas.translate(dx, dy); //把当前画布的原点移到(dx,dy),后面的操作都以(dx,dy)作为参照点,默认原点为(0,0)
canvas.scale(x,y);扩大。x为水平方向的放大倍数,y为竖直方向的放大倍数
canvas.rotate(angel):旋转.angle指旋转的角度,顺时针旋转。
canvas.transform():切变。所谓切变,其实就是把图像的顶部或底部推到一边。

canvas.saveLayer(bounds, paint, saveFlags);

推荐文章:http://www.jcodecraeer.com/a/anzhuokaifa/androidkaifa/2012/1212/703.html

二:Canvas的简单使用
有了上面对Canvas 方法的认识,那么下面我就用上面的方法来进行相关练习:
1.drawARGB(int a, int r, int g, int b)和drawColor(int color)
不用画笔,直接填充画板颜色

  1. @Override
  2. protected void onDraw(Canvas canvas) {
  3. super.onDraw(canvas);
  4. drawNomal(canvas);
  5. // drawTest(canvas);
  6. }
  7. /**
  8. * 常规绘制 以(0,0)作为坐标原点参考点
  9. * @param canvas
  10. */
  11. private void drawNomal(Canvas canvas){
  12. // 绘制画布背景
  13. canvas.drawColor(Color.GRAY);
  14. }


2.drawLine(float startX, float startY, float stopX, float stopY, Paint paint)
画线。
参数一:线的起始点的X坐标
参数二:线的起始点的Y坐标
参数三:线的结束点的X坐标
参数四:显得结束点的Y坐标
参数五:不说了

canvas.drawLine(50, 50, 450, 50, mPaint);

3.drawArc(RectF oval, float startAngle, float sweepAngle, boolean useCenter, Paint paint)
画圆弧(顺时针):
第一个参数—固定一块矩形区域作为画圆弧的范围。以矩形中心作为圆心画弧线
第二个参数—起始弧角度
第三个参数—画过的角度 , 从起始角度顺时针转过的角度画弧
第四个参数—是否画出半径区域,true画出来的是一个区域块,false画出来的是一个弧线。
第五个参数—画笔

  1. mPaint.setStyle(Paint.Style.FILL);
  2. mPaint.setColor(Color.RED);
  3. //RectF(float left, float top, float right, float bottom)
  4. // RectF re1 = new RectF(0,300,800,500);
  5. // canvas.drawArc(re1, 0, 50, false, mPaint);
  6. RectF re2 = new RectF(0,300,800,500);
  7. canvas.drawArc(re2, 0, 50, true, mPaint);

RectF 类中四个参数:
第一个参数:矩形区域左边距离view左侧的距离
第二个参数:矩形区域上边距离view左侧的距离
第三个参数:矩形区域右边距离view顶部的距离, 第三减去第一即是矩形宽度
第四个参数:矩形区域下边距离view顶部的距离,第四减去第二即是矩形高度
RectF rectF = new RectF(左,上,右,下);

4.drawCircle(float cx, float cy, float radius, Paint paint)
画圆,至于画的是实心圆还是圆圈,跟paint的Style属性有关。
参数一:圆心X坐标
参数二:圆心Y坐标
参数三:圆半径
参数四:这还用说么??!

  1. mPaint =new Paint();
  2. // 绘制画布背景
  3. canvas.drawColor(Color.WHITE);
  4. //设置画笔颜色
  5. mPaint.setColor(Color.RED);
  6. //设置画笔为空心 ,实心
  7. mPaint.setStyle(Paint.Style.FILL);
  8. // 画圆
  9. canvas.drawCircle(100, 500, 50, mPaint);


5.drawOval(RectF oval, Paint paint)
绘制一个区域的内切圆或内切椭圆(视所定义的矩形而定):

  1. RectF oval = new RectF(350, 500, 450, 700);
  2. // 画椭圆
  3. canvas.drawOval(oval, mPaint);

6.drawPath(Path path, Paint paint)

绘制路径。
参数一:
此类很简单,但是有几个注意点:
1.path的起始点的设置调用方法是 moveTo();如果没有调用此方法,则默认起始点为(0,0)
2.如果要连接起始点和终点,只需要调用path.closed();即可
3.连接两个点,使用path.lineTo();
参数二:画笔

  1. //设置Path路径
  2. mPaint.setStyle(Paint.Style.STROKE);
  3. mPaint.setColor(Color.GREEN);
  4. mPaint.setStrokeWidth(3);
  5. Path path = new Path();
  6. path.moveTo(200, 100);
  7. path.lineTo(620, 80);
  8. path.lineTo(420, 200);
  9. path.lineTo(300, 400);
  10. path.close();
  11. canvas.drawPath(path, mPaint);

7.drawTextOnPath(@NonNull String text, @NonNull Path path, float hOffset,float vOffset, @NonNull Paint paint)
该方法可以沿着Path路径绘制文本,其中text指文本内容,hOffset参数指定水平偏移、vOffset指定垂直偏移

  1. //设置Path路径
  2. mPaint.setStyle(Paint.Style.STROKE);
  3. mPaint.setColor(Color.GREEN);
  4. mPaint.setStrokeWidth(3);
  5. Path path = new Path();
  6. path.moveTo(200, 100);
  7. path.lineTo(620, 80);
  8. path.lineTo(420, 200);
  9. path.lineTo(300, 400);
  10. path.close();
  11. mPaint.setTextSize(46);
  12. canvas.drawPath(path, mPaint);
  13. //drawTextOnPath(@NonNull String text, @NonNull Path path, float hOffset,float vOffset, @NonNull Paint paint)
  14. //该方法可以沿着Path路径绘制文本,其中text指文本内容,hOffset参数指定水平偏移、vOffset指定垂直偏移
  15. canvas.drawTextOnPath("7qiuwoeruowoqjifasdkfjksjfiojio23ur8950", path, -10, -10, mPaint);

8.drawPoint(float x, float y, Paint paint)
画点。
需要注意的是,需要设置将画笔设置下 paint.setStrokeWidth(xxx);
当然也可以给点加点特效: paint.setStrokeCap(Paint.Cap.ROUND);//或者paint.setStrokeCap(Paint.Cap.BUTT);
设置画笔的样式,来指定所画的点的样式,圆形还是方形

9. drawText(String text, float x, float y, Paint paint)

按照指定坐标 绘制文本。float x和 float y表示 其实点的xy坐标

  1. drawText(char[] text, int index, int count, float x, float y, Paint paint)
  2. canvas.drawText("零一二三四五六七八九十".toCharArray(),1,3,10,100,paint); 》》》 一二三
  3. drawText(CharSequence text, int start, int end, float x, float y, Paint paint)
  4. canvas.drawText("零一二三四五六七八九十",1,3,10,100,paint); 》》》 一二   含头不含尾

10.drawPicture(Picture picture, RectF dst) 和 drawBitmap(Bitmap bitmap, float left, float top, Paint paint)  (本部分借鉴)
区别 : drawPicture(矢量图) 和 drawBitmap(位图)
参照:http://blog.csdn.net/u014005316/article/details/54891400

在绘制图形的过程中,会需要对画布进行旋转,缩放,平移等操作,但对画布进行比如平移操作之后,会对以后画上去的内容也产生影响,有时,我们只希望这种平移或是旋转操作只是临时作用于画布上的某些内容,这个时候就可以使用save和restore方法,save和restore方法一般是配对使用.
例如:

  1. canvas.drawText("00000000", 0, 20, paint);
  2. canvas.translate(200, 200);//将画布从(0,0)移动一段距离到(200,200)
  3. canvas.drawText("——2223233———", 0, 20, paint);

  1. canvas.drawText("00000000", 0, 20, paint);
  2. canvas.save();
  3. canvas.translate(200, 200);
  4. canvas.restore();
  5. canvas.drawText("——2223233———", 0, 20, paint);
  6. }


save()在画布移动前调用和restore()方法在画布移动之后调用,这样 画布中的内容才不会跟随画布移动。

11。位置转换方法,canvas.rorate和canvas.translate: 这个是我找的,个人比较感兴趣奋斗

  1. @Override
  2. protected void onDraw(Canvas canvas) {
  3. Paint paint = new Paint();
  4. canvas.drawColor(Color.BLACK);
  5. paint.setColor(Color.YELLOW);
  6. paint.setStrokeJoin(Paint.Join.ROUND);
  7. paint.setStrokeCap(Paint.Cap.ROUND);
  8. paint.setStrokeWidth(3);
  9. paint.setAntiAlias(true);
  10. paint.setStyle(Paint.Style.STROKE);
  11. canvas.translate(500, 500); //将位置移动画纸的坐标点:150,150// 原点坐标 (500,500)
  12. canvas.drawCircle(0, 0, 200, paint); //画圆圈(半径200) 大圆
  13. //使用path绘制路径文字
  14. canvas.save();
  15. canvas.translate(-100, -165);
  16. Path path = new Path();
  17. // TODO: 2017/6/6
  18. path.addArc(new RectF(0,0,220,130), -210, 240);
  19. Paint citePaint = new Paint(paint);
  20. citePaint.setTextSize(40);
  21. citePaint.setStrokeWidth(1);
  22. //drawTextOnPath(@NonNull String text, @NonNull Path path, float hOffset,float vOffset, @NonNull Paint paint)
  23. //该方法可以沿着Path路径绘制文本,其中text指文本内容,hOffset参数指定水平偏移、vOffset指定垂直偏移
  24. canvas.drawTextOnPath("我爱学习Android", path, 28, 3, citePaint);
  25. canvas.restore();
  26. //刻度和数字
  27. Paint tmpPaint = new Paint(paint); //小刻度画笔对象
  28. tmpPaint.setTextSize(25);//1234 数字大小
  29. tmpPaint.setStrokeWidth(1);
  30. float y=200;//刻度圆半径
  31. int count = 60; //总刻度数
  32. for(int i=0 ; i <count ; i++){
  33. if(i%5 == 0){
  34. canvas.drawLine(0f, y, 0, y+18f, paint);//大刻度
  35. canvas.drawText(String.valueOf(i/5+1), -10f, y+44f, tmpPaint);//123456789 10 11 12
  36. }else{
  37. canvas.drawLine(0f, y, 0f, y +12f, tmpPaint);//小刻度
  38. }
  39. canvas.rotate(360/count,0f,0f); //旋转画纸
  40. }
  41. //绘制指针
  42. tmpPaint.setColor(Color.GRAY);
  43. tmpPaint.setStrokeWidth(4);
  44. canvas.drawCircle(0, 0, 10, tmpPaint);
  45. tmpPaint.setStyle(Paint.Style.FILL);
  46. tmpPaint.setColor(Color.RED);
  47. canvas.drawCircle(0, 0, 6, tmpPaint);
  48. canvas.drawLine(0, 20, 0, -150, paint);
  49. }





详细请参考:http://www.jcodecraeer.com/a/anzhuokaifa/androidkaifa/2012/1212/703.html

http://blog.csdn.net/sinat_26710701/article/details/70158696

http://www.cnblogs.com/yishujun/p/5559917.html

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/知新_RL/article/detail/711386
推荐阅读
相关标签
  

闽ICP备14008679号