2012-05-08 89 views
0

下面是一個SwingWorker實例,它沒有像我期望的那樣更新Java GUI。使用SwingWorker更新Java Gui

SwingWorker在一個按鈕的動作偵聽器中實現。定義循環的minmax都是動作偵聽器本地的「final int」。

SwingWorker應該在每次迭代中調用NQueens對象的go()方法,它遞歸地找到n皇后的所有解決方案。然後調用NQueens對象的toString()後發佈字符串,以便process()方法將更新jProgressBarjTextArea。但是,按下按鈕時不會發生任何事情。我應該如何實現與GUI組件更新結合的密集過程?

new SwingWorker <Void,String>() 
{  
    private int totalPercent; 
    @Override 
    protected Void doInBackground() 
    { 
     int diff = max - min + 1; 
     int percent = 100; 
     if(diff != 0) 
     { 
       percent = 100/diff; 
     } 
     totalPercent = 0; 
     NQueens queens = new NQueens(min); 
     for(int j = min; j <= max; j++) 
     { 
       queens.go(); 
       totalPercent += percent; 
       String newText = queens.toString(); 
       publish(newText); 
       queens.nextSet(); 
     } 

     isCalced = true; 

     return null; 
     } 

     protected void process(String results) 
     { 
      jTextArea2.append(results); 
      jProgressBar1.setValue(totalPercent); 
      jProgressBar1.repaint(); 
     }         
    }.execute(); 
+0

[如何使用進度條(http://docs.oracle.com/javase/tutorial/uiswing/components/progress.html) – oers

+0

看起來沒給我。你知道它是否在調用進程()嗎?也許添加一些簡單的System.out調試?也可以嘗試重寫done()並在其中調用get(),它將使doInBackground()過程中發生的任何異常「重新拋出」。 – Jim

回答

0

原因可能是您沒有實施正確的過程方法?我相信過程的正確簽名是

process(List<String> results) { 
    for(String result : results) { 
    jTextArea2.append(result); 
    } 
} 

關於更新進度條; doInBackground方法在單獨的線程中運行,而process方法在您調用worker的線程上運行。您不應該從doInBackground寫入totalPercent變量並從process()中讀取它。有關詳細信息,請參閱thread visibility。相反,創建一個類似於名爲ProgressUpdateEvent的類可以保存百分比值和消息。這樣一來,你可以做如下:

new SwingWorker <Void,ProgressUpdateEvent>() { 

    protected Void doInBackground() { 
    for (int i = 0; i <= 100; i++) { 
     publish(new ProgressUpdateEvent("At " + i + "% right now", i); 
    } 
    } 

    protected void process(List<ProgressUpdateEvent> events) { 
    for (ProgressUpdateEvent event : events) { 
     jTextArea2.append(event.getMessage()); 
     jProgressBar1.setValue(event.getPercent()); 
    } 
    } 
}