2011-10-22 42 views
20

在我的應用程序中,在MainActivity中,有一個工作正常的線程。但是當我調用另一個類從服務器獲取數據時,我無法在一個線程上運行。看下面的代碼示例。Android如何在其他類中運行OnUiThread?

class MainActivity extends Activity implements Runnable { 

    public void onCreate() { 
     new Thread(this).start(); 
    } 

    public void run() { 
     //here is code for download data from server after completion this and in handler i m call other class in setdata() method.... 
    } 

    public void setData() { 
     new CheckData(this); 
    } 
} 

class CheckData { 
    public CheckData(Context context) { 
     context.runUIonthread(){//cant call as runUIthread............ 
    } 
} 

回答

39

看到這篇文章Communicating with the UI Thread

Context的幫助下,您可以在任何課程中創建Handler。否則,您可以撥打Looper.getMainLooper(),無論哪種方式,您都可以獲得主UI線程。

例如:

class CheckData{ 
    private final Handler handler; 

    public Checkdata(Context context){ 
     handler = new Handler(context.getMainLooper()); 
    } 

    public void someMethod() { 
     // Do work 
     runOnUiThread(new Runnable() { 
      @Override 
      public void run() { 
       // Code to run on UI thread 
      } 
     }); 
    } 

    private void runOnUiThread(Runnable r) { 
     handler.post(r); 
    } 
} 
+0

處理程序如何在未初始化的情況下最終生效?:^) – Sipty

+0

@Sipty最終字段可以在構造函數中初始化,因爲它在我的示例中 –

+2

構造函數沒有返回值。 Java類名應以大寫字母BTW開頭。儘管有小錯誤,你的答案是有幫助的! – hgoebl

6

你可能想看看AsyncTask。儘管這不是最好的解決方案,但它會幫助你開始。

http://developer.android.com/reference/android/os/AsyncTask.html

編輯

我不明白爲什麼使用的AsyncTask是不適合你,但無論如何一個解決方案。您可以保存在UI線程中初始化的Handler類。然後使用此Handler,您可以以可運行的形式將消息回發到UI。因此,只需在UI線程中(在開始新線程之前)實例化新的Handler對象,然後與其他類共享該對象。完成後,可以使用該實例使用post方法將消息發送回UI線程。退房的處理程序類的文檔瞭解更多信息:

http://developer.android.com/reference/android/os/Handler.html

+0

沒有解不了爲什麼使用異步任務?我只使用線程..沒有其他....... –

+0

AsyncTask將分離的線程及其所有操作和實現封裝在其類中,使您可以更輕鬆地使用它。它是您需要的非常好的解決方案(從服務器下載數據)。你只實現一些回調方法,比如任務完成時,開始之前等等......然後你從你的onCreate方法開始。 – Jong

+0

@Jong我知道這很好,但我需要解決方案爲什麼我們不能調用runUIthread?所以仔細閱讀問題........ –

11
class MainActivity extends Activity implements Runnable{ 

    public void oncreate(){ 
     new Thread(this).start(); 
    } 

    public void run(){ 
     //here is code for download data from server after completion this and in handler i m call other class in setdata() method.... 
    } 

    public void setdata(); 
    { 
     new checkData(this,MainActivity.this); 
    } 
} 

class checkData{ 

    public void checkdata(Context context,MainActivity mainactivity){ 
     mainactivity.runUIonthread()..is works fine for me..... 
    } 

} 
+0

已經看到你的博客文章關於Twitter。有一個疑問。你能澄清一下嗎? – Apparatus

+0

傳遞上下文時傳遞活動是多餘的。請查看我在http://stackoverflow.com/a/28873148/2670370下分享的解決方案。 –

10

活動是擴展上下文的類。所以不需要傳遞上下文和活動。您可以通過活動爲背景,然後你可以使用上下文對UI線程上運行如下:小心的

((Activity) context).runOnUiThread(new Runnable() { 
     public void run() { 
      //Code goes here 
     } 
    }); 

字:只有當你確定這方面是一個活動環境中使用此,假設這不是一個好習慣。

+0

如果您已經通過了上下文,那麼這是最簡單的工作解決方案。 –

21

這裏的,如果你不想通過上下文的解決方案:

new Handler(Looper.getMainLooper()).post(new Runnable() { 
    public void run() { 
     // code goes here 
    } 
}); 
+0

爲我工作,謝謝 –

+0

它爲這種情況下一個簡單和有效的解決方案。謝謝。 – Al2x

0

如果有人尋找一個基於的Rx解決方案:

Observable.just(true) 
    .observeOn(AndroidSchedulers.mainThread()) 
    .subscribe(aBoolean -> { 
     // cool stuff comes here 
    }); 
相關問題