高速な描画処理(SurfaceView)

TOP > Androidアプリ開発日誌 >  高速な描画処理(SurfaceView)
このエントリーをはてなブックマークに追加

SurfaceViewとは?

SurfaceViewはゲームなど高速描画が必要なときに使用します。Viewクラスを継承しており別スレッドで直接GUI操作をおこなう事もできます。 使用する端末の性能にもよりますが、FPS(1秒間のフレーム数)で違いを見ると、通常のViewは5fps程度、Surfaceview は30fps超といった具合に描画に関しては大きな性能差があります。
java.lang.Object
 ↳ android.view.View
  ↳ android.view.SurfaceView

SurfaceViewに関連する主なクラスとメソッド
SurfaceView
SurfaceHolder getHolder()SurfaceHolderを取得
SurfaceHolder
void addCallback(SurfaceHolder.Callback)コールバックを設定
removeCallback(SurfaceHolder.Callback)コールバックを解除
Canvas lockCanvas()描画を開始
void unlockCanvasAndPost(Canvas)描画を終了
Canvas
int save()状態を保存
void restore()状態を復元
Paint
setAntiAlias(boolean)アンチエイリアスを設定

通常 SurfaceView を利用する場合は、SurfaceViewを継承したサブクラスを作成し利用します。 常に描画し続ける場合は Thred を用いループさせます。逆にタッチなどのイベント時のみ描画する場合は SurfaceHolderにコールバックを設定し描画を行います。

SurfaceViewを用いた高速描画のサンプルソース

下記のソースは常に描画し続けるタイプのシンプルなSurfaceView を使用した雛形ソースです。
package jp.mediawing.android.test2;

import android.app.Activity;
import android.content.Context;
import android.graphics.BitmapFactory;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.graphics.drawable.BitmapDrawable;
import android.os.Bundle;
import android.view.SurfaceHolder;
import android.view.SurfaceView;

public class MainActivity extends Activity {
	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);

		//レイアウトファイルでなく カスタムクラスを使用。
		//setContentView(R.layout.main);
		setContentView(new SurfaceTestView(this));
	}

	// SurfaceViewをextends したカスタムクラス
	class SurfaceTestView extends SurfaceView implements Runnable {
		private Thread thread;

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

			// スレッドの作成と実行
			thread = new Thread(this);
			thread.start();
		}


		public void run() {
			// ループ処理
			while (thread != null) {
				draw() ;
			}
		}

		// 描画処理
		public void draw() {
			Canvas canvas = getHolder().lockCanvas();
			if ( canvas != null)
			{
				// 描画処理を以下に記述
				// ~
				getHolder().unlockCanvasAndPost(canvas);
			}
		}
	}
}