2011-09-15 24 views
2

SMACKを使用してXMPPクライアントを作成しています。Android runOnUiThread - アクティビティを渡す方法

私はcontactListを更新したいとき、ListAdapter.notifyDataSetChangedはUIスレッドで実行する必要がありますが、明らかにSMACKライ​​ブラリはRosterListener(実際には良いことです)でマルチスレッドを使用します。しかし、ここに問題があります:s.thを実行する。 UIスレッドでは、有効なコンテキストが必要です。

しかし、どうすれば入手できますか?アクティビティのコンテキストをRosterListenerのレジスタ関数に渡すことが頭に浮かんだ最初のものでしたが、レジスタ関数に到達する前に別のクラスの関数がいくつかあります。それが最終的にその目的地に到達するまで何度も何度も何度も繰り返し使用されます。

私はこの問題に遭遇した唯一の人ではないと思いますので、どうすれば解決できますか?

これを保存するだけのシングルトンかもしれないコンテキスト(私の意見では、あまり好ましくないアイデア...) または、おそらく私のデザイン全体に欠陥がありますか? どこからでもUIスレッドを取得する可能性はありますか?

ボトムライン:現時点では、複数の機能を介してコンテキストを引数として渡していますが、それを行うより良い方法があります。

ありがとうございました。

答えて

1

サービスにXMPPコードを入力し、ブロードキャストを送信します。関心のある活動は、単にそれらの放送に登録することができます。そうすれば、UIスレッドとアクティビティコンテキストの可用性についてもう一度心配する必要はありません。

+0

チャットクライアントの場合は特に素晴らしいアイデアです。バックグラウンドサービスは非常に便利で、私の問題も解決します。ありがとう;-) –

+0

あなたはこの答えを受け入れることをお勧めしますか? –

0

私はあなたがやろう正確に何を得ることはありませんが、あなたは、いくつかのスレッドであり、あなたが戻ってUIThreadに

ルーパーよりshitchしたい場合は、あなたのソリューションは、私が得る、あなたを読む http://developer.android.com/reference/android/os/Looper.html

0

ですあなたがコールバックで作業しているような気分です。 Smackなど、ワーカースレッドからコールバックしている場合は、そのときにメインのUIスレッドに投稿します。

私の経験では、コールバックは、コールバックを登録するときに渡すカスタムデータに常に関連付けることができ、実際にコールバックされたときに受け取ることができます。

あなたの文脈では、私が悪いのデザインであると考えて二つのアプローチがあります:グローバルブツのいずれかの種類を使用して

  • は、あなたが
  • を好きなら、あなたのモデルに期待しましょうと(を返すシングルトンそれを呼び出しますAndroidとUI固有)コンテキスト

代わりに、私はアクティビティによって実装されたモデルを作成し、モデルがこのインタフェースのインスタンスを受け入れ、そうするために、登録までさまざまなレイヤーに渡します。

このインターフェイスによって公開されるメソッドは、非同期に呼び出され、適切に文書化してrunOnUiThread()などを使用する必要があることを示します。

このようにして、コンテキスト(プラットフォームとUIの詳細)を場所とモデルに正確に渡すわけではありません。さらに、グローバル/静的データを避けることで、さまざまな問題、競合およびその他のメモリリークを引き起こします。

1

私はそれをより洗練されたやり方で行うことができました。このためには、Application Contextを定義する必要があります。いったんそれを持っていれば、Activityへの参照の混乱なしに、任意のクラスライブラリからRunOnUIThreadを呼び出すことができます。どこでもあなたのクラスライブラリの呼び出し内から

Handler handler = new Handler(Application.Context.MainLooper); 
handler.Post(() => doStuff()); 

私はMonoDroidを使用すると、これはC#で書かれていることを心に留めておいてください、私はそれは、Javaと非常によく似ていると信じています。 ApplicationContextの作成方法についてはこちらthread

関連する問題