2011-08-12 10 views
3

私は最後の数時間をここで答えを探すのに費やしましたが、何もわかりません。Activity.onCreate()からスレッドを作成しないで死ぬこと

ここに私の問題があります:私はメインメニューを持つ簡単なアプリを持っています。オプションの1つは、PHPサーバーからコメントのリストを取得し、データベースを更新してListViewを表示します。

すべてが正しく機能します。今度は、私が戻って活動を再開するたびに、新しいスレッドが開始されます。私は50以上の待機スレッドに到達することができました。 EclipseのDDMSタブを使ってトレッドを監視しています。

Looper.getLooper().quit()またはLooper.myLooper().quit()に電話すると、「メインスレッドは終了できません」というエラーが表示されます。

私は間違って何をしていますか、スレッドをどこで止めるべきですか?ここで

はコードです:

public class RequestActivity extends Activity { 

    ProgressDialog pDialog; 
    DatabaseHelper db; 
    int userId; 
    myCursorAdapter adapter; 
    Thread runner = null; 
    ListView list; 

    @Override 
    public void onCreate(Bundle savedInstanceState) { 
     super.onCreate(savedInstanceState); 
     userId = myApplication.getInstance().getSession().getUserId(); 
     setContentView(R.layout.request_list); 

     db = new myProvider.DatabaseHelper(this); 
     Cursor cursor = db.getRequests(userId); 
     startManagingCursor(cursor); 
     adapter = new myCursorAdapter(RequestActivity.this, cursor); 
     list = (ListView) findViewById(R.id.list); 
     list.setVisibility(View.INVISIBLE); 
     list.setAdapter(adapter); 

     pDialog = ProgressDialog.show(RequestActivity.this, "", "Loading ...", true, false); 

     runner = new Thread() { 
      Handler handler = new Handler() { 
       @Override 
       public void handleMessage(Message msg) { 
        adapter.getCursor().requery(); 
       } 
      }; 

      public void run() { 
       Looper.prepare(); 
       // ... setup HttpGet 
       try { 
        // ... get HTTP GET response 
        if (response != null) { 
         // ... update database 
         handler.sendEmptyMessage(0); 
        } 
       } catch(Exception e) { 
        // .. log exception 
       } 
       Looper.loop(); 
      } 
     }; 
     runner.start(); 
    } 

    private static class ViewHolder { 
     // .. view objects 
    } 

    private class myCursorAdapter extends CursorAdapter { 
     private LayoutInflater inflater; 
     public myCursorAdapter(Context context, Cursor c) { 
      super(context, c); 
      inflater = LayoutInflater.from(context); 
     } 

     @Override 
     public void bindView(View view, Context context, Cursor cursor) { 
      // .. bind data 
      if (cursor.isLast()) { 
       pDialog.dismiss(); 
       list.setVisibility(View.VISIBLE); 
      } 
     } 

     @Override 
     public View newView(Context context, Cursor cursor, ViewGroup parent) { 
      View view = inflater.inflate(R.layout.request_list_item, parent, false); 
      ViewHolder holder = new ViewHolder(); 
      // .. set holder View objects 
      view.setTag(holder); 
      return view; 
     } 
    } 

} 

答えて

1

あなたのonDestroyメソッドでスレッドを停止するための呼び出しを行いますか?

public void onDestroy() 
{ 
    Thread moribund = runner; 
    runner = null 
    moribund.interrupt(); 

} 
+0

ジャック、私はそれを行っているが、スレッドがまだ生きている、とisInterruptedを()はfalseを返します。 –

+0

私がやることは、スレッドクラスにrequestedStopブール値を追加することです。 requestStop()メソッドを作成してtrueに設定します。私は私のループにconditionalを追加するだけですが、IFを続けると言います。requestedStop – Jack

+0

http://stackoverflow.com/questions/6673687/specifics-on-using-looper-prepare-in-android – Jack

1

あなたが許可されていない、あなたのメイン(UI)スレッド内Looper.quit()メソッドを呼び出しています。 Looper.quit()を呼び出すスレッド内のハンドラにRunnableを投稿してみてください。これにより、スレッドコンテキスト内のLooperが終了します。

2

メインスレッドのルーパーでquit()を呼び出しています。スレッドのルーパーではありません。

これを試すことができます。 Threadを拡張する別のプライベート内部クラスを作成します。 run()メソッドで、Looper.myLooper()を呼び出してスレッドのLooperインスタンスをクラスに保存します。その後、そのルーパーを終了するコールを終了するメソッドがあります。

例:

private class LooperThread extends Thread{ 
    private Looper threadLooper; 

    @Override 
    public void run(){ 
     Looper.prepare(); 
     threadLooper = Looper.myLooper(); 
     Looper.loop(); 
    } 

    public void stopLooper(){ 
     if(threadLooper != null) 
      threadLooper.quit(); 
    } 
} 
+0

それはそれです! アクティビティの 'Looper'に対して' quit() 'を呼び出せないことは知っていましたが、**スレッド**ルーパ_inisde_' run() 'を得ることは決してありませんでした。 もう一度おねがいします! –

関連する問題