Java - 摆轮定时器在WHILE中,带启用/禁用按钮
在这里搜索了三天,发现了一些答案,但无法理解如何实现解决方案。于是,我将代码恢复到第一个版本,并决定询问。Java - 摆轮定时器在WHILE中,带启用/禁用按钮
我的代码有两个问题,并且读取线程和协议并没有解释如何多次使用swing定时器,如何启动和停止定时器INSIDE LOOP,以及如何在定时器启动时禁用按钮,以及何时重新启用停止。
当你点击按钮,它会滚死,定时器必须做它的序列号的时候停止,但如果骰子数为6它必须再次启动,在
“做{计时圈}而(模具== 6);”
在我的代码按钮不会被禁用。如果6滚动,计时器立即熄灭而不等待完成先前的移动,并且在完成所有事情之前可以单击按钮,使JLabel移动更加混乱。
有人请告诉我如何使这项工作?我有更多这样的东西来写,需要看这个例子,并从中学习。
请。
在此先感谢您的理解。
下面的代码:
import java.awt.EventQueue;
import java.awt.Toolkit;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import static java.lang.Math.random;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JButton;
import javax.swing.Timer;
public class RunPhysics extends JFrame {
private final int waits = 200;
private JLabel blackBoard = new JLabel();
private JLabel label = new JLabel("a=F/m -> O");
private JButton roll = new JButton("Roll");
private int labelX = 10;
private int labelY = 60;
private int die;
private Timer timer;
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
new RunPhysics();
}
});
}
public RunPhysics() {
setSize(1000, 200);
setTitle("Running Physics");
setLayout(null);
setDefaultCloseOperation(DISPOSE_ON_CLOSE);
setVisible(true);
getContentPane().add(blackBoard);
blackBoard.setBounds(10, 10, 980, 280);
blackBoard.add(label);
blackBoard.add(roll);
label.setBounds(30, 50, 100, 20);
roll.setBounds(10, 10, 60, 30);
roll.addActionListener(new ActionListener() {
@Override
public void actionPerformed(ActionEvent roller) {
do {labelX = 10;
die = (int)(random()*6+1);
roll.setEnabled(false);
System.out.println(die + " was rolled.");
timer = new Timer(waits, new ActionListener() {
@Override
public void actionPerformed(ActionEvent mover) {
Toolkit.getDefaultToolkit().beep();
label.setLocation(labelX, labelY);
if (labelX >= 900) {((Timer)mover.getSource()).stop();}
else { labelX+=36; }
}
});
timer.start();
} while (die == 6); // “Dice” is the plural form of the singular noun “Die”.
roll.setEnabled(true);
System.out.println("~~~~~~~~~~~~~~~~~~~~");
}
});
}
}
该按钮的ActionListener的负责启动动画。所以你所做的就是设置组件的属性,然后开始动画。因此,它可能看起来像:
roll.addActionListener(new ActionListener()
{
@Override
public void actionPerformed(ActionEvent roller)
{
// disable the roll button
// set the labelX to its start value
// set the label location
// start the timer
}
});
定时器的ActionListener然后负责:
- 原创动漫
- 确定何时停止动画
- 重新启动动画取决于卷骰子
所以代码应该在你的构造函数中定义类(而不是在按钮的ActionListener),并可能看起来像:
timer = new Timer(waits, new ActionListener()
{
@Override
public void actionPerformed(ActionEvent mover)
{
// do the basic animation
// 1. increment the labelX value
// 2. set the location of the label
// determine when to stop the animation
if (your stop condition is satisfied)
{
// stop the timeer
// enable the roll button
int die = (int)(random()*6+1);
System.out.println(die + " was rolled.");
// auto restart the animation
if (die > 4) // make it easier to test auto repeat
{
// Reset the component properties and restart the timer.
// The code here is the same as the code for the roll button
// that is why I suggested you create a method
}
}
}
});
同样这个答案的角度来理解的
- 用户分离开始某种处理
- 定时器负责其动画并知道何时停止/重新开始动画。
它可能不是你想要的,但应该给你一个更好的结构来实现你的确切要求的基础知识。
谢谢。我正在试验这个,并花了我时间去更好地理解它。要想从根本上改变思维方式,20岁的分步构建只是一种负担。 Timer根据我们自己的指示循环,在我们指导它时动态分支,并在我们放置它们时循环下一个任务。 – Sinisa
'阅读有关线程和协议并没有解释如何多次使用摆动计时器,如何启动和停止计时器INSIDE LOOP' - 这是因为定时器'REPLACES'循环。摆脱循环。计时器将在您指定的时间段内生成一个事件。 – camickr
是的,计时器是循环移动JLabel一步一步。它取代了原来的FOR循环。现在,如何把它放在另一个可以取代WHILE的计时器中? – Sinisa
你不需要while循环!当某些事件发生时,您停止定时器。也许用户点击一个按钮或键入一个特定的键。 – camickr