【移动开发】在Canvas上显示动画

本文翻译自《50 android hacks》


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

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

【移动开发】在Canvas上显示动画_第1张图片

知识点

使用到的知识点:

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

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

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

实现

小方块视图。

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

public class Rectangle extends View {
  public static final int MAX_SIZE = 40;
  private static final int ALPHA = 255;
  private int mCoordX = 0;
  private int mCoordY = 0;
  private int mRealSize = 40;
  private int mSpeedX = 3;
  private int mSpeedY = 3;

  private boolean goRight = true;
  private boolean goDown = true;
  private DrawView mDrawView;

  private Paint mInnerPaint;
  private RectF mDrawRect;

  public Rectangle(Context context, DrawView drawView) {
    super(context);
    mDrawView = drawView;

    mInnerPaint = new Paint();

    mDrawRect = new RectF();

    /* Red is default */
    mInnerPaint.setARGB(ALPHA, 255, 0, 0);
    mInnerPaint.setAntiAlias(true);
  }

  public void setARGB(int a, int r, int g, int b) {
    mInnerPaint.setARGB(a, r, g, b);
  }

  public void setX(int newValue) {
    mCoordX = newValue;
  }

  public int getX() {
    return mCoordX;
  }

  public void setY(int newValue) {
    mCoordY = newValue;
  }

  public int getY() {
    return mCoordY;
  }

  public void move() {
    moveTo(mSpeedX, mSpeedY);
  }

  private void moveTo(int goX, int goY) {

    // check the borders, and set the direction if a border has reached
    if (mCoordX > (mDrawView.width - MAX_SIZE)) {
      goRight = false;
    }

    if (mCoordX < 0) {
      goRight = true;
    }

    if (mCoordY > (mDrawView.height - MAX_SIZE)) {
      goDown = false;
    }
    if (mCoordY < 0) {
      goDown = true;
    }

    // move the x and y
    if (goRight) {
      mCoordX += goX;
    } else {
      mCoordX -= goX;
    }
    if (goDown) {
      mCoordY += goY;
    } else {
      mCoordY -= goY;
    }

  }

  public int getSpeedX() {
    return mSpeedX;
  }

  public void setSpeedX(int speedX) {
    mSpeedX = speedX;
  }

  public int getmSpeedY() {
    return mSpeedY;
  }

  public void setSpeedY(int speedY) {
    mSpeedY = speedY;
  }

  @Override
  protected void onDraw(Canvas canvas) {
    super.onDraw(canvas);

    mDrawRect.set(mCoordX, mCoordY, mCoordX + mRealSize, mCoordY
        + mRealSize);
    canvas.drawRoundRect(mDrawRect, 0, 0, mInnerPaint);

  }

  public void setSize(int newSize) {
    mRealSize = newSize;
  }

  public int getSize() {
    return mRealSize;
  }
}

外层视图。

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

public class DrawView extends View {
  private Rectangle mRectangle;
  public int width;
  public int height;

  public DrawView(Context context) {
    super(context);

    mRectangle = new Rectangle(context, this);
    mRectangle.setARGB(255, 255, 0, 0);
    mRectangle.setSpeedX(3);
    mRectangle.setSpeedY(3);
  }

  @Override
  protected void onDraw(Canvas canvas) {
    invalidate();

    mRectangle.move();
    mRectangle.onDraw(canvas);
  }

}

主界面。

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

public class MainActivity extends Activity {

  private DrawView mDrawView;

  @Override
  public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);

    Display display = getWindowManager().getDefaultDisplay();
    mDrawView = new DrawView(this);
    mDrawView.height = display.getHeight();
    mDrawView.width = display.getWidth();

    setContentView(mDrawView);
  }
}


参考资料

http://developer.android.com/reference/android/graphics/Canvas.html

http://developer.android.com/guide/topics/graphics/2d-graphics.html

你可能感兴趣的:(【移动开发】在Canvas上显示动画)