Android Gauge Animation Question

Mark Manickaraj picture Mark Manickaraj · May 27, 2011 · Viewed 13.7k times · Source

Okay so i've been trying to do this for a couple of days and i am getting no where. So i have the following two images:

The First is a RPM Gauge

RPM Gauge

The Second image is a full white graphic representing rpm gauge being full:

Full Gauge

I want to do the following:

  1. ask the user for an RPM input, if for example they enter 1.2 the gauge will fill up as follows:

output

I have the user input working i need help with the animation. Here is what i have tried:

  1. I have tried using PorterDuff but it also clips the gauge in the background not just the white bar
  2. I've tried splitting the image into little bitmaps and store them into arrays so that i can recall parts but this was slow and often crashed
  3. I made some progress by applying the Gauge first to the canvas then saving the canvas: canvas.save(); then clipping a path on the white image then restoring the canvas. However i do not know how to clip in a circular fashion starting from bottom left to a 180 degress to the bottom right (CW). Is this the best way?

I know there is probably an easier or more efficient way of doing this i just don't have a clue. Anyone with any good ideas?

*Note all images are PNG's

Thanks in advance!

Answer

Ludevik picture Ludevik · May 27, 2011

As you already found, i would use clip:

  • draw background image
  • set clip
  • draw foreground image

I would use

Canvas.clipPath()

with path looking like pie slice starting in the center of circle, like this:

Clip path

To create clip path use something like:

public class PieView extends View {

    private int width = 200;
    private int angleStart = 135;
    private int sweep = 270;

    private Path p;

    private Paint paint = new Paint();

    public PieView(Context context, AttributeSet attrs) {
    super(context, attrs);
        p = new Path();
        //move into center of the circle
        p.setLastPoint(width/2, width/2);
        //add line from the center to arc at specified angle
        p.lineTo(width/2+(float)Math.cos(Math.toRadians(angleStart))*(width/2), 
                 width/2+(float)Math.sin(Math.toRadians(angleStart))*(width/2));
        //add arc from start angle with specified sweep
        p.addArc(new RectF(0, 0, width, width), angleStart, sweep);
        //from end of arc return to the center of circle
        p.lineTo(width/2, width/2);

        paint.setColor(Color.RED);
        paint.setStrokeWidth(1);
        paint.setStyle(Style.STROKE);
    }

    @Override
    protected void onDraw(Canvas canvas) {
        super.onDraw(canvas);
        canvas.drawRect(0,0,width,width, paint);
        canvas.drawPath(p,paint);
    }
}