ViewGroup を継承したクラスを自作する(2)

前回は、ViewGroup.addView(View, int, ViewGroup.LayoutParams)をオーバーライドすれば動作を変更できそうという調査まで行った。今回は、実際にオーバーライドして動作を確認してみた。

public class HogeViewGroup extends FrameLayout {
    private SparseArray<SparseArray<Object>> children = new SparseArray<SparseArray<Object>>();

    // FrameLayout と同じ引数でコンストラクターを作成

    @Override
    public void addView(View child, int index, ViewGroup.LayoutParams params) {
        Log.d(Consts.LOG_TAG, "addView(View, int, ViewGroup.LayoutParams), " + "(" + child.getClass().getCanonicalName() + ", " + index + ")");

        SparseArray<Object> sa = new SparseArray<Object>(3);
        sa.put(0, child);
        sa.put(1, index);
        sa.put(2, params);

        children.put(child.getId(), sa);
    }

    public void attach(int id) {
        Log.d(Consts.LOG_TAG, "attach(" + id + ")" + this.getChildCount());

        removeAllViews();

        SparseArray<Object> sa = children.get(id);
        super.addView((View) sa.get(0), (Integer) sa.get(1), (LayoutParams) sa.get(2));
    }
}

Android のフレームワークが addView(View, int, ViewGroup.LayoutParams) メソッドを呼び出したときは SparseArray に格納する。SparseArray への格納方法はもうちょっとスマートに行う必要があると思うが、実験中なのでちょっと適当だ。attach(int)を呼び出すと、表示したい View を実際に addView(View, int, ViewGroup.LayoutParams) するようにしてみた。attach(int)メソッドの引数は、R.id.mainView など、レイアウト XML で指定した ID になる。

動かしてみても特に問題はないので、このまま使えそうな気もするのだが、問題点が2つあった。

  1. HogeViewGroup のインスタンスを Activity が保持していないと attach(int) メソッドを任意の場所から呼び出せない(もしくは想定していない動きになる)
  2. attach(int) メソッドを呼び出したときに removeAllViews() メソッドを呼び出すので、子の View で SurfaceView を利用していると遅い

1の方はなんとか回避する方法があるにしても、2の方は「ViewGroup を継承したクラスを自作する」理由が Activity の切り替え速度が気になったことが理由だけに致命的だ。もう少し調整が必要になりそう・・・ちなみに、SurfaceView を利用していないときは、速度はほとんど気になりませんでした。


ViewGroup を継承したクラスを自作する(2)」への1件のフィードバック

  1. dsl 投稿作成者

    最終形になるか分からないけど、現在のところ、addView() メソッドで View を追加する際に、enable を false、visibility を INVISIBLE に、attach() にあたるメソッドで、enable を true にして visibility を VISIBLE にしている。

コメントを残す

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です

Time limit is exhausted. Please reload CAPTCHA.