2013/01/07 このエントリーをはてなブックマークに追加 はてなブックマーク - 【Android】イベントリスナー実装のベストプラクティスはなんだろう(the best coding  to use EventListener for Android )

【Android】イベントリスナー実装のベストプラクティスはなんだろう(the best coding to use EventListener for Android )





前々から気になっていたこのテーマ。


Androidにおけるイベントリスナーの実装はどのようにすべきか。考えてみたいと思う。
同じようなエントリは少しはあったのだけれども、僕にとっては不十分に感じたので、書いてみたい。



イベントリスナーとはボタンウィジェットのOnClickListenerとか
アラートダイアログのDialogInterface.OnClickListener(であってるかな・・?)とか
そういった類のものである。
実装方法は僕の思いつく限りでは4つある。




  1. インナークラスを作る
  2. Activityにリスナーインターフェースを実装させる(implements)
  3. Activity内に別クラスを作る
  4. publicな別クラスを作る




1と2あたりがやっぱり主流な感じだろうか。
以下で、それぞれ考えていく。











1.インナークラスを作る




これはこんな感じ


public void onCreate(Bundle savedInstanceState){
 
    Button button = (Button) findById(R.id.button);
    botton.setOnClickListener(new OnClickListener(){
        public void onClick(View view){
            //処理
        }
    });
}



メリット

  • 簡単な(ステップ数が少ないという意味で)処理が書きやすい
  • 実装が直感的に分かりやすい



  • デメリット

  • メソッド内の処理が膨らむ
  • →onCreateの肥大化の恐れ
    (大体の人がonCreateで記述するのではないだろうか)
  • 同じ処理を実装する場合、無駄な記述が増える。
  • (共通化が図れる)
  • 記述形式が初級者には分かりにくいかも(上から順に実行されるプログラムではないため)










  • 2.Activity自身にリスナーインターフェースを実装させる(implements)





    これはこういった形。



    public class SampleActivity extends Activity implements OnClickListener{
        ...
    
        public void onCreate(Bundle savedInstanceState){
            Button button = (Button) findById(R.id.button);
            // 自インスタンスをリスナーとしてセット
            botton.setOnClickListener(new OnClickListener(this);
        }
    
        @Override
        public void onClick(View v){
            //処理
        }
    }






    メリット

    ・実装忘れが防止できる(実装しないとコンパイルエラーになるので)


    デメリット

  • ボタン単位でのメソッドの分類が出来ない
  • →同一メソッド内(例ではonClick)での部品ID(v.getId())などでどのボタン処理か
    判別するなどの処理が必要になる。









    3.Activity内に別クラスを作る




    内部に別のクラスを作っちゃうって方法






    public class SampleActivity extends Activity {
    
        public void onCreate(Bundle savedInstanceState){
            Button button = (Button) findById(R.id.button);
            botton.setOnClickListener(new ButtonAction());
        }
    
        ...(略)...
    }
    
    class ButtonAction implements OnClickListener{
    
        @Override
        public void onClick(View v){
            //処理
        }
    }
    
    

    メリット

    ・ボタンごとの処理が書きやすい ・処理タイミングが視覚的に理解しやすい

    デメリット

    ・クラス外部から参照できず、汎用性が無い ・単純な処理には不向き






    4.publicな別クラスを作る



    これは3と実装自体はほぼ同じ




    public class SampleActivity extends Activity{
    
        public void onCreate(Bundle savedInstanceState){
    
            Button button = (Button) findById(R.id.button);
            botton.setOnClickListener(new ButtonAction());
        }
    
        ...(略)...
    
    }
    
    
    public class ButtonAction implements OnClickListener{
    
            @Override
            public void onClick(View v){
                //処理
            }
    }


    メリット



    ・複数のActivityから利用でき、再利用性が高い(と思う)

    デメリット

    ・Activity内のフィールド、Contextなどのパラメータ渡しが面倒。 →コンストラクタで渡すのか、Factoryクラスを介して渡すのかみたいな話になる。
    ・Activityクラスで無意識に呼び出せていたContextやActivityのメソッドの呼び出し がやや面倒になる。 ex)Toast、AlertDialog、Intentなどなど
    ・クラスが機能単位分増え、デバッグなどが難しくなる
    実は、個人的に1の手法から4の方法に切り替えようと
    最近リファクタリングしていたのだが、地味にめんどくさい。





    まとめ





    4つの実装方法のメリット・デメリットを上げる形で書いてみたが、
    結論として、どれがベストということもないと思う。
    実装方針として検討するのであれば、以下のような点が重要に
    なってくるのではないだろうか。


  • イベント内の処理の複雑さ
  • →例えばonClick内でのAlertDialog呼び出しなどの場合、
    1のインナークラス方式で書くとソースがネストして可読性が下がる。
  • Activity内でのButton数
  • →1つしかButtonが無い場合は1や2などが楽である
  • 実装者の書きやすさ
  • →スピード重視の場合、慣れた形式での実装が手っ取り早い。結局。
    ただ、僕の書いた4パターンぐらいは実装出来ても損はないかなと思う。
    Javaを使う人としては。

    どの規模のアンドロイドアプリを制作するかに尽きる。
    個人で制作するなら自分に合った方法を。
    チームで制作する場合は規約化して統一感あるものに仕上げると、
    後々のバージョンアップやバグフィックスも捗るのではないかと思います。





    0 件のコメント:

    コメントを投稿