Monday, August 23, 2010

Android SurfaceView Drag an Image Wout External Thread Pump

I need to say that my laptop noise level serves me as a reliable profiling tool, so while following the series here: http://www.droidnova.com/playing-with-graphics-in-android-part-iii,176.html I just heard the fan complaining about around 50% of CPU being consumed. This time by android emulator and the idle app just waiting for me to tap into the screen. I guess there should be a better way waiting for this tap/drag, wout turning my device into an air heater.

The above mentioned tutorial is actually based on Lunar Lander sample, and the huge difference there is that they do the calculation every time before calling the view’s onDraw. Here, we are just idle!

So, here follows the code that uses postInvalidate:

package com.advaton.tasks.shellui;
 
import android.content.Context;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Color;
import android.util.Log;
import android.view.MotionEvent;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
 
public class SurfaceView2 extends SurfaceView
 implements SurfaceHolder.Callback {
    Bitmap _scratch;
    private int _x = 20;
    private int _y = 20;
 
    public SurfaceView2(Context context) {
        super(context);
        this.getHolder().addCallback(this);
        setFocusable(true);
        _scratch = BitmapFactory
                .decodeResource(getResources(), R.drawable.icon);
        
 
    }
 
    @Override
    protected void onDraw(Canvas canvas) {
        Log.d("surface", "inside onDraw");
            canvas.drawColor(Color.BLACK);
            canvas.drawBitmap(_scratch, _x - (_scratch.getWidth() / 2), _y
                    - (_scratch.getHeight() / 2), null);
    }
 
    @Override
    public boolean onTouchEvent(MotionEvent event) {
        Log.d("surface", "inside on touch");
        _x = (int) event.getX();
        _y = (int) event.getY();
        this.postInvalidate();
        return true;
    }
 
    public void surfaceChanged(SurfaceHolder holder, int format, int width,
            int height) {
 
    }
 
    public void surfaceCreated(SurfaceHolder holder) {
        Log.d("surface", "Surface created");
        setWillNotDraw(false);
    }
 
    public void surfaceDestroyed(SurfaceHolder holder) {
        Log.d("surface", "Surface destroyed");
    }
}

So here comes my draggable cpu/environment friendly android guy:

image

3 comments:

Praveen said...

Thank you so much for your code, It helpd in my project

taaki said...

Thank you.. even the blog is a old one, it has been very helpful.

taaki said...

Thank you.. even though the blog is old, it has been very helpful