Canvas 画布,用于在位图上进行绘制,内部关联一个mutable Bitmap, canvas在一系列操作后,展现在该Bitmap上。


什么时候有Canvas?

1. 自定义view时, onDraw、dispatchDraw

2.SurfaceHolder.lockCanvas(); 操作SurfaceView时需要用到Canvas

3. 自行创建。

Canvas c = new Canvas(bitmap);//要求参数bitmap为一个可变的Bitmap

或Canvas c = new Canvas();c.setBitmap(b);


API

canvas.drawPoint(100, 200, paint); //画像素点

canvas.drawPoints(new float[]{100,200, 100,220}, paint); //一组点每两个元素表示x,y

canvas.drawLine(50, 200, 80, 300, paint); //直线两点x,y x1,y1确定

canvas.drawLines(new float[]{50, 220, 100, 330, 115, 138, 459, 388}, paint); //一组直线

canvas.drawRect(rect, paint); //画矩形

canvas.drawRoundRect(new RectF(200, 10, 400, 80), 10, 80,paint); //圆角矩形 10x方向圆角半径 80:y方向圆角半径

canvas.drawCircle(300, 700, 180, paint); //圆形 圆心xy和半径值

canvas.drawArc(new RectF(100,700,400,1000), 180, 90,false,paint);//以矩形为边界,绘制弧形。顺时针绘制。0度在中心点到右水平线。true表示会连接到中心点,false不会连接,只会连接起始点和终点

canvas.drawOval(new RectF(100,700,200,900), p); //以矩形为边界,绘制椭圆。 如果矩形为正方形,那绘制的就是圆形

canvas.drawText(…) // 绘制文本

canvas.drawPath(path, p); //绘制出路径 路径内包含一些图形

canvas.drawTextOnPath(text, path, h, v, p); //沿着路径的图形绘制文本。h表示距离绘制的起点位置 v表示距离路径的位置。 当顺时针时v=0,文本紧贴图形外部;v<0离在图形外越来越远。逆时针时v=0,文本在图形内部;v>0文本离图形边越来越远

canvas.setDrawFilter(new PaintFlagsDrawFilter(0, Paint.ANTI_ALIAS_FLAG | Paint.FILTER_BITMAP_FLAG)); // 抗锯齿

canvas.drawBitmap(bmp, 0, 0, paint);

canvas.drawBitmap(bmp, matrix, paint);


多边形绘制

Path path = new Path();

path.moveTo(x, y); //起始点
path.lineTo(x, y); //到某点画直线
。。。
path.lineTo(x, y);
path.close();

canvas.drawPath(path, paint);


位移、旋转、缩放、扭曲(倾斜)

canvas.translate(dx, dy); 位移 即将(0,0)原点移到 (dx,dy)

canvas.rotate(float degrees); 默认以view的(0,0)原点 旋转

canvas.rotate(float degrees, float px, float py);

内部会先translate(px,py); 再rotate(degrees);再translate(-px,-py);

旋转后,x、y轴的指向也就改变了

canvas.scale(float sx, float sy); 以view的(0,0)为缩放中心

scale(float sx, float sy, float px, float py) ;
内部: translate(px, py);
scale(sx, sy);
translate(-px, -py); 这时平移的坐标相对于原来的坐标比例为: -px*sx, -py*sy

paint.setColor(Color.BLACK);canvas.drawLine(0,0,100,500,paint);        canvas.translate(50, 50);        canvas.scale(0.5f,0.5f);        paint.setColor(Color.BLUE);        canvas.drawLine(0,0,100,500,paint);        canvas.translate(-50, -50);//        canvas.scale(0.5f, 0.5f, 50, 50);        paint.setColor(Color.CYAN);        canvas.drawLine(0,0,100,500,paint);

上例先绘制一条从(0,0)开始的 到 (100,500) 的 黑色线段;

平移(50,50),xy缩小0.5倍。 这时绘制的起始点(0,0) 即是平移后的(50,50)这个位置, 结束点(100,500)即变为(50,250),蓝色线段;

最后再平移(-50,-50),即只移动(-50*0.5,-50*0.5)=> (-25,-25), 以其为(0,0),绘制结束点为(50,250)的 青色线段

如下图:



canvas.skew(float sx, float sy);sx或sy为倾斜角度的tan值


save和restore

save就是保存当前的; restore 恢复、回退到上次save之前的状态。

可以多次save,再restoreToCount(int count);回退到某次save后。

int count = save(); 每save一次都返回一个count ; 或 int count =getSaveCount();

save(); Saves the current matrix and clip onto a private stack. 对应的flag:MATRIX_SAVE_FLAG | CLIP_SAVE_FLAG

saveLayer(); 不含alpha; 图层需要一个矩形的限定区和paint画笔; 可以指定其它flag

saveLayerAlpha(); 含alpha;图层需要一个矩形的限定区和paint画笔; 可以指定其它flag.(保存成一个透明度为a的,大小为矩形r的图层)

Canvas.MATRIX_SAVE_FLAG | Canvas.CLIP_SAVE_FLAG
| Canvas.HAS_ALPHA_LAYER_SAVE_FLAG | Canvas.FULL_COLOR_LAYER_SAVE_FLAG
| Canvas.CLIP_TO_LAYER_SAVE_FLAG; //Canvas.ALL_SAVE_FLAG 含所有5种flag


clip

clipRect(rect,...);

clipPath(path,...);

clipRegion(...); //已过时,类似操作推荐用 clipRect

canvas.save();Region region = new Region();region.set(new Rect(150, 0, 600, 700));region.op(new Rect(0,0, 200, 300), Region.Op.UNION);canvas.clipRegion(region); //裁剪范围canvas.drawColor(Color.RED);//将bitmap绘制到相应的regioncanvas.restore();

public enum Op {
DIFFERENCE(0), //区别上一个,即去掉上一个图形所占区域
INTERSECT(1), //交集
UNION(2), //并集
XOR(3), //去掉交集的部份
REVERSE_DIFFERENCE(4), //反转,即区别下一个,即去掉当前图形所占区域
REPLACE(5); //替换; 只保留当前图形
}


在执行了canvas的裁剪、平移、缩放、扭曲(skew)等操作,将影响其后执行的绘制draw的动作

所以一般在执行类似操作时 需要一对 save和restore


更多相关文章

  1. Android(安卓)RecyclerView —— 自定义分割线
  2. Android实现全屏截图或长截屏功能
  3. android百度地图:在地图上绘制点、线、多边形、圆形和文字
  4. Android的冷启动优化
  5. Android(安卓)ApiDemos示例解析(73):Graphics->Points
  6. android 里面的 Drawable 和 ConstantState
  7. Android(安卓)shape中的padding无效
  8. Android(安卓)GUI Architecture
  9. Android绘图系列(五)——绘制文本

随机推荐

  1. 修改android wifi热点默认网关
  2. android布局属性详解
  3. Failed to sync vcpu reg
  4. android 数据库 备份还原
  5. android自带的drawable图标ico名称对应表
  6. Cocos2d-3.x Android环境搭建
  7. Android(安卓)RelativeLayout 实现顶部左
  8. 2013.05.16——— android 关于listview
  9. Android中获取屏幕信息DisplayMetrics的
  10. android添加外部按键