Android的绘制都是通过canvas来实现的,在canvas中提供了基本的旋转、平移等功能,但是在旋转时旋转的到底是什么,旋转之后的坐标系是否改变,一直存在疑虑,以上是在网上淘的一个例子,借此分析一下:
那么,由于是对canvas的操作,旋转了画布,第一个rect应该旋转了,然后画第二个rect,第二个rect应该没旋转,预估效果应该是下面第一个图(也就是第一个红方块旋转,第二个蓝方块不旋转)。而实际效果确是下面第二个图(第一个红方块不旋转,第二个蓝方块旋转),同时蓝色的方块的坐标与旋转之前不一样。
由此我们可以得出结论,canvas只是定义了绘制的规则,最终我们的绘制是绘制在屏幕上,绘制完成后进行旋转操作,并不能影响之前的绘制,只会对之后的绘制产生影响,同时坐标系随着旋转而旋转。
意思就是,画图,实际上是画在这个canvas定义的范围和规则下,但是显示在屏幕上,如下图:
蓝色的是手机屏幕边框,红色的是一个全屏的canvas
当canvas旋转30度之后,其实成了这个样子,但是你绘制的图形还是只能在canvas内,并且坐标是按照canvas旋转之前来的,也就是左上角坐标仍然是(0,0),右下角的坐标仍然是(width,height)。
也就是说,你按照(100,100,150,150)画出来的rect需要旋转30度之后,才是你看到的效果,这就是上面那个坐标看上去好像不对的原因。
那么save和restore的问题也就好解决了,save只是save了当前这个canvas的状态,和已经画出来的图形无关,restore就是取出最近一次save的canvas的状态,仍然不影响图形。
当我们对画布进行旋转,缩放,平移等操作的时候其实我们是想对特定的元素进行操作,比如图片,一个矩形等,但是当你用canvas的方法来进行这些操作的时候,其实是对整个画布进行了操作,那么之后在画布上的元素都会受到影响,所以我们在操作之前调用canvas.save()来保存画布当前的状态,当操作之后取出之前保存过的状态,这样就不会对其他的元素进行影响
对于
代码段1:
代码段2:
上面这两个代码片段中我们都假设有两张图片bmp1和bmp2,并且都画在画布上!
那么代码段1和代码段2的不同:
代码段1中我们进行画布缩放的之前保存了画布状态,做了缩放操作之后又取出之前保存的状态,这样做是为了保证bmp2正常画出来不受到缩放的影响!
代码段2里,画了bmp1后就执行了缩放操作,并且没有保存状态!紧接着画了bmp2,那么bmp2也会一样受到缩放的影响!!
所以我们如果单独处理一张图片的时候,而且不想影响其他部分的绘制,那么应该如下来做:
view plaincopy toclipboardprint?