2015-08-09 52 views
-2

我想在Java中製作卡拉OK機,但我不知道如何在GUI中延遲程序。我已經搜索了這個網站上的大量主題,但我仍然沒有找到適用於此的解決方案。Java:如何在GUI中等待1秒

import javax.swing.*; 
import java.awt.event.*; 
public class KaraokeMachine extends JFrame implements ActionListener 
{ 
    ClassLoader Idr = this.getClass().getClassLoader(); 
    JLabel lbl1 = new JLabel(""); 
    JLabel lbl2 = new JLabel(""); 
    JLabel lbl3 = new JLabel(""); 
    JLabel lbl4 = new JLabel(""); 
    JButton btn = new JButton("Play"); 
    int x = 0; 
    int y = 0; 
    int z = 0; 
    JPanel pnl = new JPanel(); 

    public KaraokeMachine() 
    { 
     super("Karaoke"); 
     setSize(520, 280); 
     setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 
     pnl.add(lbl1); 
     pnl.add(lbl2); 
     pnl.add(lbl3); 
     pnl.add(lbl4); 
     pnl.add(btn); 
     btn.addActionListener(this); 
     add(pnl); setVisible(true); 
    } 

    public void actionPerformed(ActionEvent event) 
    { 
     if(event.getSource() == btn) 
     { 
      // 
     } 
    } 
    public static void main(String[] args) throws InterruptedException 
    { 
     KaraokeMachine karaoke = new KaraokeMachine(); 
    } 
} 

我想讓標籤在1秒後改變文字。我已經在catch語句中試過Thread.sleep,但沒有//,但沒有,編譯器說這是一個錯誤,並且只有一個,程序只是延遲幾秒鐘,並在最後顯示結果,但沒有的結果在中間。有人可以告訴我我怎樣才能讓lbl1說「一切」,然後一秒鐘後「一切都是」,然後在那之後的另一秒「一切都很棒!」?謝謝。

+0

瞭解Java線程。你可以使用單線程來完成這個任務,並且你可以睡覺()或等待()來完成這個任務。 –

+0

輸出文本的代碼片段在哪裏** Everything is Awesome ** ?? – CrakC

+0

您能否提供一個能告訴我的鏈接? – DalekCaan99

回答

3

你不應該在你的GUI線程中調用sleep()方法,否則所有的界面都會凍結。您應該使用單獨的線程,並與您的GUI線程通信以告訴他何時更新界面。

在Swing應用程序中使用線程的最佳方式是使用SwingWorker對象。特別是,它提供了兩種鉤子方法,分別是processdone,它們直接在您的gui線程中調用,並且是發佈工作線程完成進度的強大方法。在你的情況,你應該做這樣的事情:

SwingWorker<Void, String> worker = new SwingWorker<Void, String>(){ 

     @Override 
     protected Void doInBackground() throws Exception { 
      this.publish("Everything"); 
      Thread.sleep(1000); 
      this.publish("Everything is"); 
      Thread.sleep(1000); 
      this.publish("Everything is Awesome!"); 
      return null; 
     } 

     @Override 
     protected void process(List<String> res){ 
      for(String text : res){ 
       label.setText(text); 
      } 
     } 

    }; 

    worker.execute(); 

P.S:你可以一個工人對象上調用​​方法只有一次。如果你想多次調用它,你必須實例化新的對象。

+0

對不起,我很困惑。我在哪裏擺放SwingWorker? – DalekCaan99

+0

在調用worker.execute()之前,可以在任何地方完成工作對象的實例化。並且應該調用execute()方法在哪裏開始執行任務。 – SimoV8

+0

但是,我在代碼中放哪? – DalekCaan99

2

你可以用javax.swing.Timer來做到這一點。它應該足以用您的代碼替換//

 final AtomicInteger frame = new AtomicInteger(0); 
     final String[] text = { 
       "Everything", 
       "Everything is", 
       "Everything is Awesome!" 
     }; 
     final Timer timer = new Timer(1000, null); 
     timer.addActionListener((e) -> { 
      lbl1.setText(text[frame.getAndIncrement()]); 
      if (frame.get() >= text.length) { 
       timer.stop(); 
      } 
     }); 
     timer.start();