protected void onDraw(Canvas canvas) {
super.onDraw(canvas);
}
@Override
protected void dispatchDraw(Canvas canvas) {
super.dispatchDraw(canvas);
}
可以看到,onDraw()、dispatchDraw()函数在传入的参数中都有一个Canvas对象,这个Canvas对象是View中的Canvas对象,利用这个Canvas对象绘图,效果会直接反映在View中。
这两个函数的区别如下:
-
onDraw()函数用于绘制视图自身
-
dispatchDraw()函数用于绘制子视图
无论是View还是ViewGroup,对这两个函数的调用顺序都是 onDraw() --> dispatchDraw()
但在ViewGroup中,当它有背景的时候,会跳过onDraw()函数,直接调用dispatchDraw()函数,所以在ViewGroup中绘图,则往往会重写dispatchDraw()函数。
在View中,onDraw和dispatchDraw方法都会调用,所以我们把绘制代码放在哪个函数中都会执行。但由于dispatchDraw函数用于绘制子视图,所以,从原则上来讲,在绘制View控件时,我们会重写onDraw()函数。
方法二:使用Bitmap创建
1、构建方法,使用:
Canvas c = new Canvas(bitmap);
或
Canvas c = new Canvas();
c.setBitmap(bitmap);
其中Bitmap可以从图片中加载,也可以自行创建:
//方法一,新建空白bitmap
Bitmap bitmap = Bitmap.createBitmap(width,height,Bitmap.Config.ARGB_8888);
//方法二,从图片中加载
Bitmap bitmap = BitmapFactory.decodeResource(getResources(), R.drawable.XXX,nu;😉;
2、在onDraw函数中使用
如果我们用Bitmap构造了一个Canvas,那么在这个Canvas上绘制的图像也都会保存在这个Bitmap上,而不会画在View上。如果想画在View上,就必须使用onDraw(Canvas canvas)函数中传入的Canvas画一遍bitmap。
比如我们自己 构造了一个Canvas为bmpCanvas(mBitmap),然后在onDraw中我们在这个bmpCanvas上进行绘制,但是应用最后却没有将该bmpCanvas上的东西显示出来!?
这就说明,其实我们没有最终将自己新建的画布 画在 最终的画布上。 我们给bmpCanvas进行的绘制,绘制的内容只是在mBitmap上而已。
方法三、调用SurfaceHolder.lockCanvas()函数
在使用SurfaceView时,当调用SurfaceHolder.lockCanvas()函数时,也会创建Canvas对象,有关SurfaceView的知识可以参考第十章。
前面讲过Canvas的save()和restore()函数,除了这两个函数以外,还有其他一些函数用来保存和回复画布状态。
saveLayer()函数
saveLayer有两个构造函数:
public int saveLayer(RectF bounds,Paint paint,int saveFlags)
public int saveLayer(float left,float top,