サービスで実行されているスレッドがいくつかあります。スレッドは UI / アクティビティにメッセージを投稿する必要があります
Handler 参照をスレッドに渡すにはどうすればよいですか? 状態の変更を Activity に投稿できるようにするには?
または、このようにハンドラー ref をグローバルに公開する方法はありますか?
Handler getUIHandler();
前もって感謝します ;)
サービスで実行されているスレッドがいくつかあります。スレッドは UI / アクティビティにメッセージを投稿する必要があります
Handler 参照をスレッドに渡すにはどうすればよいですか? 状態の変更を Activity に投稿できるようにするには?
または、このようにハンドラー ref をグローバルに公開する方法はありますか?
Handler getUIHandler();
前もって感謝します ;)
UIスレッドにHandlerオブジェクトを作成します。必要に応じて、インスタンス化時に作成できます。アクティビティから起動されたスレッドはすべて、そのハンドラーにメッセージまたは実行可能ファイルを投稿できます。他のアクティビティ、サービス、またはその他から起動されたスレッドは、アクティビティが実行されているという保証がないため、機能しません。(実際には、アクティビティの実行中に機能するかどうかを確認するのは楽しい実験かもしれませんが、この手法に基づいて実際のアプリを作成することはできません。)
実際、ハンドラーを作成する必要はありません。すべてのViewオブジェクトには独自のハンドラーが含まれているため、ランナブルをビューに簡単に投稿できます。
または、電話することもできますrunOnUiThread()
ハンドラーに関する私のメモから:
使用パターン:
パターン1、ハンドラーとランナブル:
// Main thread
private Handler handler = new Handler()
...
// Some other thread
handler.post(new Runnable() {
public void run() {
Log.d(TAG, "this is being run in the main thread");
}
});
パターン2、ハンドラーとメッセージ:
// Main thread
private Handler handler = new Handler() {
public void handleMessage(Message msg) {
Log.d(TAG, "dealing with message: " + msg.what);
}
};
...
// Some other thread
Message msg = handler.obtainMessage(what);
handler.sendMessage(msg);
パターン3、runOnUiThread()を呼び出します。
// Some other thread
runOnUiThread(new Runnable() { // Only available in Activity
public void run() {
// perform action in ui thread
}
});
パターン4、ビューの組み込みハンドラーを使用します。
// Some other thread
myView.post(new Runnable() {
public void run() {
// perform action in ui thread, presumably involving this view
}
});
OK、基本的な問題に戻るべきかもしれません。サービスからのアクティビティで UI を更新しようとしていますか? これには2つのアプローチがあります。
まず、サービスは特別なインテントをアクティビティに送り返すことができます。「singleTask」の起動モードでアクティビティを宣言し、サービスからインテントを受け取る onNewIntent() を実装します。次に、関連情報をインテントにパックし、処理するアクティビティに送信します。
もう少し複雑ですが、より良い方法は、アクティビティからサービスをバインドすることです。そうすれば、バインダーを介して簡単に相互に通信できます。サービスとアクティビティが両方とも同じアプリケーションの一部であり、両方が同じプロセスで実行されている場合、これははるかに簡単になります。
繰り返しますが、私のメモから:
Binder を拡張し、サービスのインスタンスを返す getService() などのメソッドを含む、たとえば "LocalBinder" という名前の内部クラスを宣言します。
public class MyService extends Service
{
public class LocalBinder extends Binder {
MyService getService() {
return MyService.this;
}
}
private final IBinder binder = new LocalBinder();
public IBinder onBind(Intent intent) {
return binder;
}
}
アクティビティには次のようなコードが含まれています。
// Subclass of ServiceConnection used to manage connect/disconnect
class MyConnection extends ServiceConnection {
public void onServiceConnected(ComponentName name, IBinder svc) {
myService = ((MyService.LocalBinder)svc).getService();
// we are now connected
}
public void onServiceDisconnected(ComponentName name) {
// we are now disconnected
myService = null;
}
}
private MyService myService;
private MyConnection connection = new MyConnection();
/**
* Bind to the service
*/
void doBind() {
bindService(new Intent(MyClient.this, MyService.class),
connection, Context.BIND_AUTO_CREATE);
}
/**
* Unbind from the service
*/
void doUnbind() {
if (connection != null) {
unbindService(connection);
}
}
サービスのエラーをアクティビティに報告する方法について、同様の質問に回答しました。
Android Service でのエラー処理のベスト プラクティスを確認してください。これにより、使用できるアプローチとコード例が得られます。
よろしく。