在按下Button1时的以下代码行中,Jframe变得无响应,直到encode()方法的执行完成。但是我需要在Jframe中更新显示进度的进度条。
private void Button1ActionPerformed(java.awt.event.ActionEvent evt) {
try {
if (flagState == 0) {
WavFile.decode(readWavFile, msg.getText(), key.getText().hashCode());
} else if (flagState == 1) {
WavFile.encode(readWavFile, msg.getText(), key.getText().hashCode());
}
} catch (WavFileException | IOException e) {
notes.setText(e.getMessage());
}
}
我想过这样做
private void Button1ActionPerformed(java.awt.event.ActionEvent evt) {
try {
if (flagState == 0) {
Thread t = new Thread(new Runnable() {
public void run() {
WavFile.decode(readWavFile, msg.getText(), key.getText().hashCode());
}
};)
t.start();
} else if (flagState == 1) {
Thread t = new Thread(new Runnable() {
public void run() {
WavFile.encode(readWavFile, msg.getText(), key.getText().hashCode());
}
};)
t.start();
}
} catch (WavFileException | IOException e) {
notes.setText(e.getMessage());
}
}
并从encode()方法更新进度条。
但我明白,这将是模块之间的强大耦合,我不希望这样。
我也不认为每次调用一个新线程都是个好主意(想到ExecutorService但不知道如何使用它)。
我该怎么做才能把它变成一个体面的片段代码?
答案 0 :(得分:1)
在按下Button1时,以下代码行,Jframe变得无响应,直到encode()方法的执行完成。但是我需要在Jframe中更新显示进度的进度条。
您遇到Concurency in Swing的问题,block the EDT导致无法响应的GUI,直到代码结束
使用已实施的setEnabled()代替if (flagState == 0) {
答案 1 :(得分:1)
线程绝对是你必须在这里介绍的东西。任何需要花费大量时间才能完成的事情都不应该在awt事件线程中运行。
每次单击按钮时生成一个新线程本身并不是问题。但是,您应该考虑,即使在第一次完成之前,也可能会生成许多执行相同操作的线程。如果需要,可以使用Executor,但可能没有必要。
至于跟踪进度,我会添加另一个线程,定期查询其他线程并根据需要更新进度条。以下是我将如何构建它:
private void Button1ActionPerformed(java.awt.event.ActionEvent evt) {
disableButton1();
final Thread t;
if (flagState == 0) {
t = new Thread(new Runnable() {
public void run() {
try {
WavFile.decode(readWavFile, msg.getText(), key.getText().hashCode());
} catch (WavFileException | IOException e) {
notes.setText(e.getMessage());
}
}
});
} else if (flagState == 1) {
t = new Thread(new Runnable() {
public void run() {
try {
WavFile.encode(readWavFile, msg.getText(), key.getText().hashCode());
} catch (WavFileException | IOException e) {
notes.setText(e.getMessage());
}
}
});
}
Thread monitor = new Thread(new Runnable() {
public void run() {
try {
while (notComplete(t)) {
setProgressBar(getProgress(t));
Thread.sleep(SLEEP_TIME);
}
t.join();
} finally {
enableButton1();
}
}
});
t.start();
monitor.start();
}
答案 2 :(得分:0)
多线程是你需要的,没有其他好的方法我可以想到不要担心调用新线程,这就是它们的用途,jvm有一个线程池可供使用,这种事情运行非常好用线程,试一试!
创建一个扩展Runnable的类,实现run方法或让它调用当前方法,这应该就足够了。
此外,您可以让它短时间睡眠并在每次睡眠时间结束时检查状态,如果过程结束,您可以继续,如果没有,则再次进入睡眠状态,这样您就不会我不得不问过很多次。
我希望它有所帮助。