Android自定义控件(二 .1)Canvas的操作

Canvas的操作可以帮助我们更好的画图。
要学习Canvas的用法,可以访问Google官网,https://developer.android.google.cn/reference/android/graphics/Canvas.html
Canvas操作主要有以下几种:

操作 方法 备注
位移(translate) [translate](https://developer.android.google.cn/reference/android/graphics/Canvas.html#translate(float, float))(float dx, float dy) Preconcat the current matrix with the specified translation
缩放(scale) [scale](https://developer.android.google.cn/reference/android/graphics/Canvas.html#scale(float, float))(float sx, float sy)/[scale](https://developer.android.google.cn/reference/android/graphics/Canvas.html#scale(float, float, float, float))(float sx, float sy, float px, float py) Preconcat the current matrix with the specified scale.
旋转(rotate) rotate(float degrees)/[rotate](https://developer.android.google.cn/reference/android/graphics/Canvas.html#rotate(float, float, float))(float degrees, float px, float py) Preconcat the current matrix with the specified rotation.
斜切(skew) [skew](https://developer.android.google.cn/reference/android/graphics/Canvas.html#skew(float, float))(float sx, float sy) Preconcat the current matrix with the specified skew.
  1. translate是坐标系的移动,可以为图形绘制选择一个合适的坐标系。 请注意,位移是基于当前位置移动,而不是每次基于屏幕左上角的(0,0)点移动
 canvas.drawCircle(60,60,50,mPaint2);
 canvas.translate(200,200);
 canvas.drawCircle(60,60,50,mPaint2);
Android自定义控件(二 .1)Canvas的操作_第1张图片
Paste_Image.png

2.可以看到,缩放提供了来两个方法,这两个方法中前两个参数是相同的分别为x轴和y轴的缩放比例。而第二种方法比前一种多了两个参数,用来控制缩放中心位置的。

缩放比例(sx,sy)取值范围详解:

取值范围(n) 说明
[-∞, -1) 先根据缩放中心放大n倍,再根据中心轴进行翻转
-1 根据缩放中心轴进行翻转
(-1, 0) 先根据缩放中心缩小到n,再根据中心轴进行翻转
0 不会显示,若sx为0,则宽度为0,不会显示,sy同理
(0, 1) 根据缩放中心缩小到n
1 没有变化
(1, +∞) 根据缩放中心放大n倍
  • 通过缩放效果,可以看出,缩放的中心默认为坐标原点,而缩放中心轴就是坐标轴
 int width=getWidth();
 int height=getHeight();
 canvas.translate(width/2,height/2);  //将坐标移到中心
  RectF rectF=new RectF(0,-400,400,0);
  canvas.drawRect(rectF,mPaint1);
  canvas.scale(0.5f,0.5f);
   canvas.drawRect(rectF,mPaint1);
Android自定义控件(二 .1)Canvas的操作_第2张图片
scale.png
  • 我们使用第二种方法让缩放中心位置稍微改变一下,如下:
 int width=getWidth();
 int height=getHeight();
 canvas.translate(width/2,height/2);  //将坐标移到中心
 RectF rectF=new RectF(0,-400,400,0);
 canvas.drawRect(rectF,mPaint1);
 canvas.scale(0.5f,0.5f,200,0);
 canvas.drawRect(rectF,mPaint1);
Android自定义控件(二 .1)Canvas的操作_第3张图片
scale.png
  • 当缩放比例为负数的时候会根据缩放中心轴进行翻转,缩放还是在坐标原点
 int width=getWidth();
 int height=getHeight();
canvas.translate(width/2,height/2);  //将坐标移到中心
RectF rectF=new RectF(0,-400,400,0);
canvas.drawRect(rectF,mPaint1);
canvas.scale(-0.5f,-0.5f);
canvas.drawRect(rectF,mPaint1);
Android自定义控件(二 .1)Canvas的操作_第4张图片
scale.png
  • 如果这个时候在移动一下所放位置呢
int width=getWidth();
int height=getHeight();
canvas.translate(width/2,height/2);  //将坐标移到中心
RectF rectF=new RectF(0,-400,400,0);
canvas.drawRect(rectF,mPaint1);
canvas.scale(-0.5f,-0.5f,200,0);
canvas.drawRect(rectF,mPaint1);
Android自定义控件(二 .1)Canvas的操作_第5张图片
scale.png

PS:和位移(translate)一样,缩放也是可以叠加的。
canvas.scale(0.5f,0.5f);
canvas.scale(0.5f,0.1f);
调用两次缩放则 x轴实际缩放为0.5x0.5=0.25 y轴实际缩放为0.5x0.1=0.05
下面我们利用这一特性制作一个有趣的图形。

int width=getWidth();
int height=getHeight();
canvas.translate(width/2,height/2);  //将坐标移到中心
RectF rectF=new RectF(-400,-400,400,400);
canvas.drawRect(rectF,mPaint1);
  for (int i=0;i<20;i++){
     canvas.scale(0.9f,0.9f);
     canvas.drawRect(rectF,mPaint1);
    }
Android自定义控件(二 .1)Canvas的操作_第6张图片
scale.png
  • 旋转(rotate)
    旋转提供了两种方法:
    public void rotate (float degrees)
    public final void rotate (float degrees, float px, float py)
    和缩放一样,第二种方法多出来的两个参数依旧是控制旋转中心点的。
    默认的旋转中心依旧是坐标原点:
 int width=getWidth();
int height=getHeight();
canvas.translate(width/2,height/2);  //将坐标移到中心
RectF rectF=new RectF(0,-400,400,0);
canvas.drawRect(rectF,mPaint1);
canvas.rotate(180);
canvas.drawRect(rectF,mPaint1);
Android自定义控件(二 .1)Canvas的操作_第7张图片
rotate.png
  • 改变旋转中心位置:
int width=getWidth();
int height=getHeight();
canvas.translate(width/2,height/2);  //将坐标移到中心
RectF rectF=new RectF(0,-400,400,0);
canvas.drawRect(rectF,mPaint1);
canvas.rotate(180,200,0);
canvas.drawRect(rectF,mPaint1);
Android自定义控件(二 .1)Canvas的操作_第8张图片
rotate.png

当然,rotate也是可以叠加的,

int width=getWidth();
int height=getHeight();
canvas.translate(width/2,height/2);  //将坐标移到中心
RectF rectF=new RectF(0,-400,400,0);
canvas.drawRect(rectF,mPaint1);
canvas.rotate(180);
canvas.rotate(50);
canvas.drawRect(rectF,mPaint1);
Android自定义控件(二 .1)Canvas的操作_第9张图片
rotate.png
  • 斜切(skew)
    斜切只提供了一种方法:
    public void skew (float sx, float sy)
    参数含义:
    float sx:将画布在x方向上倾斜相应的角度,sx倾斜角度的tan值,
    float sy:将画布在y轴方向上倾斜相应的角度,sy为倾斜角度的tan值.
    变换后:
    X = x + sx * y
    Y = y+sy * x
 int width=getWidth();
int height=getHeight();
canvas.translate(width/2,height/2);  //将坐标移到中心
RectF rectF=new RectF(0,0,200,200);
canvas.drawRect(rectF,mPaint1);
canvas.skew(1,0);  //水平斜切45
canvas.drawRect(rectF,mPaint1);

你可能感兴趣的:(Android自定义控件(二 .1)Canvas的操作)