ホームへ戻る

5.2 別スレッドからUIを操作する


 Androidでは別スレッドからUIを操作することができません。
そこで、Handlerを使ってUIを扱うことが出来るようにすると言いました。
この仕組みについて少し説明します。

UIスレッドの根底となる部分に、Looperがいます。
ここでグルグル処理が回っています。



UIの処理はLooperが実質的に行うので、同じスレッドで行うのは問題ありません。



しかし、別スレッドからこのループに入ろうと思っても入りようがありません。



そこで、別スレッドからは、Looperが定期的に見る「queue」に仕事を積み、
Looperは自分のタイミングで仕事をすることができるようになっています。



このqueueに積む処理をHandlerによって実現することができるのです。

それでは、下のようなお待ちくださいダイアログを表示してみようと思います。
通信中やレンダリング中など、時間がかかる処理の時にこんなダイアログをみかけますね。



このダイアログ中のマークはグルグル回るので、定期的に更新する必要がありますが(自分でするわけではありません)、
レンダリング等の重い処理は途中でやめられません。
そんな時は、別のスレッドで重い処理をやりたいですね。

また、ダイアログは
.show();
で表示開始、
.dismiss();
で表示終了です。
ダイアログの表示開始はUIスレッドで行えばいいですが、
レンダリング終了のタイミングはレンダリングを行ったスレッドでなければ分かりません。
そこで、レンダリング終了をHandlerによって通知させるプログラムを書いてみます。


public class AndroidsCastleActivity extends Activity implements Runnable {
        private ProgressDialog _progressDialog;

        @Override
        public void onCreate(Bundle savedInstanceState) {
                super.onCreate(savedInstanceState);

                _progressDialog = new ProgressDialog(this);
                _progressDialog.setTitle("レンダリング中");
                _progressDialog.setMessage("しばらくお待ちください...");
                _progressDialog.setIndeterminate(true); //進捗が分からないことを示す
                _progressDialog.setProgressStyle(ProgressDialog.STYLE_SPINNER);//クルクル回るタイプのダイアログ
                _progressDialog.show();  //表示開始

                Thread thread = new Thread(this);
                thread.start();
        }

        public void run() {
                try {
                        Thread.sleep(5000);
                } catch (InterruptedException e) {}
                
                //ここに時間のかかる処理を記述

                handler.sendEmptyMessage(0);
        }

        private Handler handler = new Handler() {
                public void handleMessage(Message msg) {
                        //終了処理を記述
                        _progressDialog.dismiss();       //ダイアログの終了
                }
        };
}


runメソッド内に重い処理を記述します。
本来なら、runの終了時に、_progressDialog.dismiss()を呼びたいところですが、そこで呼ぶと例外になります。
そこで、handlerを使ってMessageを投げてhandleMessageを呼び出します。
この中はUIスレッドなので、UIに関する設定を変更しても大丈夫になります。

→分からないことがあれば掲示板で質問して下さい


Portions of this page are modifications based on work created and shared by Google and used according to terms described in the Creative Commons 3.0 Attribution License.

- Remical Soft -