ひつじのにっき

mhidakaのにっきです。たまに長文、気が向いたとき更新。

画像をドラッグできるViewの作り方

画面サイズを超える画像を、縮小せずに表示する方法です。
Viewを拡張した独自実装になっています。意外に需要ありそうなので公開します。

1280x960px image.jpg Androidで拡大表示

図の通り、アンドロイドで拡大表示して、タッチでドラッグできます。
# GoogleMapのようなイメージの分割ロードではないのです。
# 期待しちゃった方、申し訳ない。


ソースコードScrollViewDemo.src.zipです。
自由にご利用ください。
お絵かきアプリや、画像処理アプリでは使えるかもしれません。


以下、簡単なソースコード解説です。


今回はViewをベースに作成しました。
onSizeChangedで画像を読み込みます。

    protected void onSizeChanged(int w, int h, int oldw, int oldh){
        Log.v("View", "onSizeChanged Width:" + w + ",Height:" + h );
        //表示用Viewの設定
        mViewWidth  = w;
        mViewHeight = h;

        mViewBitmap = Bitmap.createBitmap(mSrcBitmap, mViewPointX, mViewPointY, mViewWidth, mViewHeight);
    }

Bitmap.createBitmapで、読み込む範囲を指定すればOK。
mViewWidth, mViewHeightは画面サイズ、
mViewPointX, mViewPointY:は描画開始位置です。現在の表示位置に応じて更新します。

    private void touch_start(float x, float y) {
        Log.v("View", "touch_start");
        mX = x;
        mY = y;
    }
    private void touch_move(float x, float y) {
        Log.d("View", "touch_move");
        float dx = Math.abs(x - mX);
        float dy = Math.abs(y - mY);
        if (dx >= TOUCH_TOLERANCE || dy >= TOUCH_TOLERANCE) {
        	translateBitmap((int)(mX - x), (int)(mY - y), 1.0f);
            mX = x;
            mY = y;
        }
    }

タッチイベントに反応してmViewPointX, mViewPointYを更新しています。
MotionEvent.ACTION_DOWからMotionEvent.ACTION_MOVEまでの移動量を計算、
再描画すれば表示範囲=タッチでの移動量と同じ分だけ移動します。
TOUCH_TOLERANCEは移動量の下限値です。
負荷を気にしなければ、0で良いかと。


画像の回転なども同様の手法で簡単に実装できますね。
計算や処理負荷を考えるとSurfaceViewで描画したほうがいいかもしれません。