2011-05-20 30 views
1

美好的一天! 我開發程序客戶端服務器,遇到了一個問題,我真的不知道如何解決它。無法立即在Java中繪製數字

所以,我有幾個按鈕。當按鈕點擊後,信息發送到服務器,服務器做一些工作併發送結果。按鈕的監聽器接收到,然後調用必須在屏幕上畫出結果的其他類的方法。

所以,這裏是問題。服務器向我發送很少的結果,程序必須立即繪製它。但它不這樣做!它等待,直到所有消息都會出現,然後才畫出結果。

所以我想知道如何在屏幕上瞬間畫出結果!

代碼: 監聽巴頓:

public class ShowFrame extends JFrame 
{ 
    startButton.addActionListener(new ActionListener() { 
     public void actionPerformed(ActionEvent e) 
     { 
      try 
      { 
       messageToServer.println("Start"); 

       while(true) 
       { 
        fserver = answerOfServer.readLine(); //Get result from server 

        if (fserver.equals("Finish")) 
        { 
         break; 
        } 
        if(fserver.equals("Busy 1")) 
        { 
         ShowFrame.this.stuff.setBusy(1); 
        } 
        if(fserver.equals("Busy 2")) 
        { 
         ShowFrame.this.stuff.setBusy(2); 
        } 
        //...Same code 


       } 
      } catch (IOException ex) { 
       Logger.getLogger(ShowFrame.class.getName()).log(Level.SEVERE, null, ex); 
     } 

    DrawStuff stuff = new DrawStuff(); 
    //... 
} 

類繪製導致在屏幕上:

public class DrawStuff extends JComponent 
{ 

public DrawStuff() 
{ 
    s1 = false; 
    s2 = false; 
    s3 = false; 
    s4_1 = false; 
    s4_2 = false; 
    s4_3 = false; 
} 

@Override 
public void paintComponent(Graphics g) 
{ 
    Graphics2D g2 = (Graphics2D) g; 
    //... 
     if (s1)      
     { 
       g2.draw(line1_of_P1); 
       g2.draw(line2_of_P1); 
     } 
     //... 
} 

public void setBusy(int i) //If such id found then figure will be drawn by prog. 
{ 
    if  (i == 1) 
    { 
     s1 = true; 
    } 
    else if (i == 2) 
    { 
     s2 = true; 
    } 
    else if (i == 3) 
    { 
     s3 = true; 
    } 
    else if (i == 4) 
    { 
     s4_1 = true; 
    } 
    else if (i == 5) 
    { 
     s4_2 = true; 
    } 
    else if (i == 6) 
    { 
     s4_3 = true; 
    } 
    this.repaint(); //DOESN'T WORK AS IT MUST! 

} 
//... 
} 

回答

1

您需要在單獨的線程中執行實際操作,以便事件分派線程可以繼續運行(需要運行它才能繪製屏幕)。您可以創建並啓動使用以下內容運行的新線程:

Thread newThread = new Thread(new Runnable() { 

    @Override 
    public void run() { 
     // put your actions to perform in here 
    }}); 

    newThread.start(); 

在您的動作偵聽器中調用此函數。

+0

還要記住,您必須創建一個新的Runnable,並將其返回到創建的線程*中的事件分派線程(SwingUtilities.invokeLater(Runnable r))*以再次修改UI狀態。 – 2011-05-20 20:11:35

+0

@Chris:我不確定你是否確定。既然你希望它在EDT上運行,這有點特別,你可以調用一個方法來使用SwingUtilities.invokeLater()更新UI狀態。這確實需要你創建一個Runnable對象,但是你可以實時創建它。 – jwir3 2011-05-20 20:13:40

+0

當您在作爲分派機制一部分的EDT上運行的runnable內執行新線程時,新創建的runnable不再在EDT上執行,而是在單獨的線程中執行。這就是我的意思:) – 2011-05-20 20:14:12