我正在尝试从JTextField中读取System.in InputStream。
我需要做的是,一旦用户在带有字符串的JTextField中按下Enter键,就允许.read()
继续进行。
问题是我不知道何时会调用.read(),并且我希望它在不冻结主线程的情况下进行阻塞,直到用户在JTextField中按下enter为止,它将在该位置通知线程等待。
到目前为止,我尝试了以下方法:
public class InputStreamHandlerThread extends Thread {
private JTextField txt;
public InputStreamHandlerThread(JTextField txt) {
this.txt = txt;
start();
}
@Override
public void run() {
System.setIn(new FakeInputStream());
}
class FakeInputStream extends InputStream {
private int indx = 0;
@Override
public int read() throws IOException {
if (indx == txt.getText().length()) {
indx = 0;
try {
synchronized (this) {
wait();
}
} catch (InterruptedException e) {
e.printStackTrace();
}
}
int byt = txt.getText().getBytes()[indx];
indx++;
return byt;
}
}
}
它由GUI线程初始化和启动。
因此,一旦GUI加载,它就会创建此类的实例并保留一个指针,以便在JTextField中的键盘上按下enter键时,它会被通知从中读取。
in = new JTextField();
in.addKeyListener(new KeyAdapter() {
@Override
public void keyTyped(KeyEvent a) {
if (a.getKeyChar() == '\n') {
inputStreamHandler.notify();
}
}
});
因此,目前有三个线程:
1.运行GUI的主线程
2. InputStream处理程序线程(请参见上面的^)
3.从System.in读取的线程
问题是,一旦我调用
inputStreamHandler.notify();
,它就会抛出一个java.lang.IllegalMonitorStateException
,根据文档,如果线程不是锁的持有者,则会抛出该ojit_code。我该如何解决?
谢谢 :-)
最佳答案
String text;
...
in.addActionListener(new ActionListener(){
public void actionPerformed(ActionEvent e){
text = in.getText();
}
});
确保在两个字段中都输入文本。