HackSeven Canvas上的动画

当自定义View的时候,可以利用Canvas给View添加一些动画效果。

下面的例子,是在屏幕上绘制一个红色的小方块,这个小方块会在屏幕上面“乱跳”。


知识点

使用到的知识点:

(1) 在View的子类的draw()中调用invalidate(),可以让View对象一直保持重绘状态,从而可以使Canvas一直处于绘画过程中。

(2) Canvas的绘制功能,例如绘制Rect、Circle、Path等。

(3) 小方块碰撞屏幕边缘的算法。

实现

小方块视图。

继承View类,重写onDraw()方法,并提供一些setter和getter方法,用于设置小方块的属性。判断碰撞事件的逻辑在moveTo()方法中。代码如下:

  1 public class Rectangle extends View {
  2     public static final int MAX_SIZE = 40;
  3     private static final int ALPHA = 255;
  4     private int mCoordX = 0;
  5     private int mCoordY = 0;
  6     private int mRealSize = 40;
  7     private int mSpeedX = 3;
  8     private int mSpeedY = 3;
  9 
 10     private boolean goRight = true;
 11     private boolean goDown = true;
 12     private DrawView mDrawView;
 13 
 14     private Paint mInnerPaint;
 15     private RectF mDrawRect;
 16 
 17     public Rectangle(Context context, DrawView drawView) {
 18         super(context);
 19         mDrawView = drawView;
 20 
 21         mInnerPaint = new Paint();
 22 
 23         mDrawRect = new RectF();
 24 
 25         /* Red is default */
 26         mInnerPaint.setARGB(ALPHA, 255, 0, 0);
 27         mInnerPaint.setAntiAlias(true);
 28     }
 29 
 30     public void setARGB(int a, int r, int g, int b) {
 31         mInnerPaint.setARGB(a, r, g, b);
 32     }
 33 
 34     public void setX(int newValue) {
 35         mCoordX = newValue;
 36     }
 37 
 38     public float getX() {
 39         return mCoordX;
 40     }
 41 
 42     public void setY(int newValue) {
 43         mCoordY = newValue;
 44     }
 45 
 46     public float getY() {
 47         return mCoordY;
 48     }
 49 
 50     public void move() {
 51         moveTo(mSpeedX, mSpeedY);
 52     }
 53 
 54     private void moveTo(int goX, int goY) {
 55 
 56         // check the borders, and set the direction if a border has reached
 57         if (mCoordX > (mDrawView.width - MAX_SIZE)) {
 58             goRight = false;
 59         }
 60 
 61         if (mCoordX < 0) {
 62             goRight = true;
 63         }
 64 
 65         if (mCoordY > (mDrawView.height - MAX_SIZE)) {
 66             goDown = false;
 67         }
 68         if (mCoordY < 0) {
 69             goDown = true;
 70         }
 71 
 72         // move the x and y
 73         if (goRight) {
 74             mCoordX += goX;
 75         } else {
 76             mCoordX -= goX;
 77         }
 78         if (goDown) {
 79             mCoordY += goY;
 80         } else {
 81             mCoordY -= goY;
 82         }
 83 
 84     }
 85 
 86     public int getSpeedX() {
 87         return mSpeedX;
 88     }
 89 
 90     public void setSpeedX(int speedX) {
 91         mSpeedX = speedX;
 92     }
 93 
 94     public int getmSpeedY() {
 95         return mSpeedY;
 96     }
 97 
 98     public void setSpeedY(int speedY) {
 99         mSpeedY = speedY;
100     }
101 
102     @Override
103     protected void onDraw(Canvas canvas) {
104         super.onDraw(canvas);
105 
106         mDrawRect.set(mCoordX, mCoordY, mCoordX + mRealSize, mCoordY
107                 + mRealSize);
108         canvas.drawRoundRect(mDrawRect, 0, 0, mInnerPaint);
109 
110     }
111 
112     public void setSize(int newSize) {
113         mRealSize = newSize;
114     }
115 
116     public int getSize() {
117         return mRealSize;
118     }
119 }

外层视图。

小方块是一个独立的视图,这里不直接把小方块显示在Actiity中,在它的外面又“包”了一层。代码如下:

 1 public class DrawView extends View {
 2     private Rectangle mRectangle;
 3 
 4     public int width;
 5 
 6     public int height;
 7 
 8     public DrawView(Context context) {
 9         super(context);
10         mRectangle = new Rectangle(context, this);
11         mRectangle.setARGB(255, 255, 0, 0);
12         mRectangle.setSpeedX(3);
13         mRectangle.setSpeedY(3);
14 
15     }
16 
17     @SuppressLint("WrongCall")
18     @Override
19     protected void onDraw(Canvas canvas) {
20         super.onDraw(canvas);
21         invalidate();
22 
23         mRectangle.move();
24         mRectangle.onDraw(canvas);
25 
26     }
27 
28 }

主界面。

获取屏幕的尺寸,并把相应的尺寸赋值给DrawView对象。最后,显示DrawView对象。代码如下:

 1 public class MainActivity extends Activity {
 2 
 3     private DrawView mDrawView;
 4 
 5     @Override
 6     protected void onCreate(Bundle savedInstanceState) {
 7         super.onCreate(savedInstanceState);
 8 
 9         Display display = getWindowManager().getDefaultDisplay();
10         mDrawView = new DrawView(this);
11         mDrawView.height = display.getHeight();
12         mDrawView.width = display.getWidth();
13         setContentView(mDrawView);
14     }
15 
16 }

源码下载:

posted @ 2014-10-26 23:43  perfect亮  阅读(214)  评论(0编辑  收藏  举报