2009-09-24 3 views
1

UI가 JFrame 안에 내장되어 있습니다. 버튼 중 하나는 (같은 자바 프로세스 내에서) 장시간 실행되는 호출을 시작하고 실행 중에는 UI가 고정됩니다.강제로 JFrame을 새로 고칩니다.

상황이 여전히 실행 중임을 분명히하기 위해 팝업 창에 진행률 표시 줄을 표시하여 사용자가 프로그램의 현재 상태를 최신 상태로 유지할 수 있도록했습니다.

그래서 새로운 JDialog를 만들고, JProgressBar를 추가하고, 상황에 따라 업데이트합니다. 문제는 대화 상자의 콘텐츠가 업데이트되지 않는다는 것입니다. 내가 직접 만든 제목의 변경 사항과 콘솔에 출력 한 내용은 모두 표시되지만 UI 자체는 변경되지 않습니다.

강제로 다시 칠할 수있는 명령이 있습니까? 우리가 진행으로

killWindow = new JDialog(); 
    killWindow.setUndecorated(true); 
    killWindow.setTitle("stopping tests - 0 of " + numActive); 
    killProgress = new JProgressBar(0, numActive); 
    killWindow.add(killProgress); 
    killProgress.setStringPainted(true); 
    killWindow.pack(); 
    killWindow.setLocationRelativeTo(frame); 
    killWindow.setVisible(true); 

..., 그런 :

다음은이 섹션의 핵심이다 내가 무엇을 놓치고

killProgress.setValue(++killedTests);     // not seen! 
    killProgress.setString("Killing test on " + nickname()); // not seen! 
    log("Killed another test, " + killedTests + " so far"); // visible in real time 
    killWindow.setTitle("stopping tests - " + killedTests + 
         " of " + killProgress.getMaximum()); // visible in real time 

? 나는 인터넷 검색을 시도 했으므로 여기를 검색해 보았고 아무 것도 분명히 보지 못했습니까?

답변

3

다른 스레드에서 장기 실행 작업을 수행해야합니다.

UI 구성 요소의 업데이트를 담당하는 "AWT Event Dispatch Thread"라는 스레드가 있습니다. 장기 실행 작업을 수행하는 중 바쁜 경우 UI를 업데이트하거나 대화 상자를 새로 고치지 않습니다.

SwingUtilities 또는 SwingWorker을 사용하는 것이 좋습니다. SwingWorker를 documentation에서

여기, 당신이 반응하는 UI를 보여주기 위해 AWT 이벤트 발송 쓰레드를 허용하고 다른 스레드에서 오래 작업을 실행하여 샘플을

final JLabel label; 
class MeaningOfLifeFinder extends SwingWorker<String, Object> { 
    @Override 
    public String doInBackground() { 
     return findTheMeaningOfLife(); 
    } 

    @Override 
    protected void done() { 
     try { 
      label.setText(get()); 
     } catch (Exception ignore) { 
     } 
    } 
} 

(new MeaningOfLifeFinder()).execute(); 

을합니다.

이러한 개념을 더 잘 이해하려면이 "Lesson from the Java tutorial"을 살펴보십시오.

관련 문제