简体   繁体   English

Java计时器不增加

[英]java timer not incrementing

I tried creating a timer in Java that displays in a JFrame window but I'm having no luck! 我试图用Java创建一个计时器,该计时器显示在JFrame窗口中,但是我没有运气!

The timer always remains at 0. Would appreciate if anyone can see where I am going wrong :( 计时器始终保持为0。如果有人可以看到我要去哪里,将不胜感激:(

import javax.swing.*;
import java.awt.*;
import java.awt.event.*;

class Globals 
{
    public static int seconds = 0;
}

class main
{
    public static void main(String Args[])
    {

        JFrame testing = new JFrame();
        testing.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        testing.setSize(1000,1000);
        testing.setVisible(true);

        Countdown timer = new Countdown();
        Timer countdown = new Timer(5000, timer);
        countdown.start();

        JLabel firstline = new JLabel();
        firstline.setText("Time is:" + Globals.seconds);
        testing.add(firstline);

    }
}

class Countdown implements ActionListener
{
    public void actionPerformed(ActionEvent e)
    {
    Globals.seconds++;

    }
}

You set the JLabel's text here: 您可以在此处设置JLabel的文本:

JLabel firstline = new JLabel();
firstline.setText("Time is:" + Globals.seconds);

But once set that's it, you never change it. 但是一旦设置成功,就永远不会改变它。

All the timer does is change the state of a variable. 计时器所做的只是更改变量的状态。 It does nothing to the GUI, such as tell the JLabel to use the new value. 它对GUI无任何作用,例如告诉JLabel使用新值。 Please understand that a JLabel is not going to magically track any variable used to create its text String. 请理解,JLabel不会神奇地跟踪用于创建其文本String的任何变量。 All it knows is that it has been set with an immutable String, and that's it. 它所知道的就是它已经设置了一个不可变的String,仅此而已。

Your Timer should instead call setText(...) on the JLabel to update its text, or better, use a reference to the class holding the JLabel, and call a public method of that class to change the JLabel's state. 相反,您的Timer应该在JLabel上调用setText(...)来更新其文本,或者更好地,使用对持有JLabel的类的引用,并调用该类的公共方法来更改JLabel的状态。

For example: 例如:

import java.awt.Dimension;
import java.awt.event.*;
import javax.swing.*;

public class TimerTest {
   private static final int TIMER_DELAY = 20;

   private static void createAndShowGui() {
      MyGui myGui = new MyGui();
      TimerListener timerListener = new TimerListener(myGui, 2 * 60 * 1000);
      new Timer(TIMER_DELAY, timerListener).start();
      JFrame frame = new JFrame("TimerTest");
      frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
      frame.getContentPane().add(myGui.getMainComponent());
      frame.pack();
      frame.setLocationRelativeTo(null);
      frame.setVisible(true);
   }

   public static void main(String[] args) {
      SwingUtilities.invokeLater(new Runnable() {
         public void run() {
            createAndShowGui();
         }
      });
   }
}

class MyGui {
   private static final int PREF_W = 200;
   private static final int PREF_H = 80;
   private JPanel mainPanel = new JPanel() {
      public Dimension getPreferredSize() {
         return MyGui.this.getPreferredSize();
      };
   };
   private JLabel statusLabel = new JLabel();

   public MyGui() {
      mainPanel.add(statusLabel);
   }

   public Dimension getPreferredSize() {
      return new Dimension(PREF_W, PREF_H);
   }

   public JComponent getMainComponent() {
      return mainPanel;
   }

   public void setStatus(String text) {
      statusLabel.setText(text);
   }
}

class TimerListener implements ActionListener {
   private static final String FORMAT = "Count Down: %02d:%02d:%03d";
   private static final int MS_PER_SEC = 1000;
   private static final int SEC_PER_MIN = 60;
   private MyGui myGui;
   private long countDownTime;
   private long startTime;

   public TimerListener(MyGui myGui, long countDownTime) {
      this.myGui = myGui;
      this.countDownTime = countDownTime;
      startTime = System.currentTimeMillis();
   }

   @Override
   public void actionPerformed(ActionEvent evt) {
      long currentTime = System.currentTimeMillis();
      long deltaTime = countDownTime - (currentTime - startTime);
      if (deltaTime < 0) {
         ((Timer) evt.getSource()).stop();
         deltaTime = 0;
      }
      int minutes = (int) (deltaTime / (MS_PER_SEC * SEC_PER_MIN));
      deltaTime = deltaTime % (MS_PER_SEC * SEC_PER_MIN);
      int seconds = (int) (deltaTime / MS_PER_SEC);
      deltaTime = deltaTime % MS_PER_SEC;
      int msecs = (int) deltaTime;
      String text = String.format(FORMAT, minutes, seconds, msecs);
      myGui.setStatus(text);
   }
}

The timer starts, waiting for 5 seconds. 计时器启动,等待5秒钟。

During this 5 seconds, it runs this code: 在这5秒钟内,它将运行以下代码:

JLabel firstline = new JLabel();
firstline.setText("Time is:" + Globals.seconds);
testing.add(firstline);

Then it increments your value. 然后,它将增加您的价值。

Since the above code isn't in a loop or anything, it never runs it again. 由于上面的代码不是循环的,所以它再也不会运行了。

Perhaps try putting the JLabel update in the timer itself: 也许尝试将JLabel更新放入计时器本身:

class Countdown implements ActionListener
{
    public void actionPerformed(ActionEvent e)
    {
        Globals.seconds++;
        main.firstline.setText("Time is:" + Globals.seconds);
    }
}

Obviously you need to have access to the JLabel here, I'll leave figuring that out to you. 显然,您需要在这里访问JLabel ,我将为您解决这个问题。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM