所以我一直在尝试使用这篇文章中的代码在JTextArea中创建控制台窗口。这段代码似乎可以在我的代码中运行,但是我遇到了一个奇怪的问题。
我的程序:我基本上是在为我最近做的命令行工具构建一个快速而肮脏的gui。gui包含的唯一东西是一个按钮,上面写着"启动自动化引擎",然后它有一个JTextArea
,应该显示我的程序发送到System.out.println()
的任何文本。
此时它什么也不显示,尽管程序本身正在运行和工作(并且应该显示输出结果)。我注意到,当我点击gui上的按钮时,该按钮在程序运行时保持压抑状态。这使我相信JFrame
在程序运行时没有更新,因此JTextArea
作为它的子程序,没有更新。这不是很好……
有没有办法让JTextArea
更新,而程序在后台运行?
JFrame
的代码,顺便说一句,如果你想看看它更好地了解我在说什么。它主要是在Eclipse中的WindowBuilder中构建的。我所做的唯一一件事就是向startAutmoatorEngineButton
添加一个按钮侦听器,然后添加initalize()
方法的最后几行,将JTextArea
(engineOutput
)设置为System.out
。
public class EngineGUI {
private JFrame frmAutomatorEngine;
private File logPath = new File("<redacted>", "<redacted>");
private File masterFile = new File("<redacted>", "<redacted>");
/**
* Launch the application.
*/
public static void main(String[] args) {
EventQueue.invokeLater(new Runnable() {
public void run() {
try {
EngineGUI window = new EngineGUI();
window.frmAutomatorEngine.setVisible(true);
} catch (Exception e) {
e.printStackTrace();
}
}
});
}
/**
* Create the application.
*/
public EngineGUI() {
initialize();
}
/**
* Initialize the contents of the frame.
*/
private void initialize() {
frmAutomatorEngine = new JFrame();
frmAutomatorEngine.setType(Type.UTILITY);
frmAutomatorEngine.setResizable(false);
frmAutomatorEngine.setTitle("Automator Engine");
frmAutomatorEngine.setBounds(100, 100, 636, 335);
frmAutomatorEngine.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JMenuBar menuBar = new JMenuBar();
frmAutomatorEngine.setJMenuBar(menuBar);
JMenu mnEngine = new JMenu("Engine");
menuBar.add(mnEngine);
JMenuItem mntmLoadMasterFile = new JMenuItem("Load Master File...");
mnEngine.add(mntmLoadMasterFile);
JMenuItem mntmExit = new JMenuItem("Exit");
mnEngine.add(mntmExit);
frmAutomatorEngine.getContentPane().setLayout(null);
JTextArea engineOutput = new JTextArea();
engineOutput.setBounds(10, 48, 600, 217);
frmAutomatorEngine.getContentPane().add(engineOutput);
JButton startAutomatorEngineButton = new JButton("Start Automator Engine");
startAutomatorEngineButton.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
MasterFile master = null;
try {
master = new MasterFile(masterFile, logPath);
} catch (FileNotFoundException e1) {
// TODO Auto-generated catch block
e1.printStackTrace();
}
AutomationLoop theLoop = new AutomationLoop(master);
theLoop.startLoop();
}
});
startAutomatorEngineButton.setBounds(441, 11, 169, 23);
frmAutomatorEngine.getContentPane().add(startAutomatorEngineButton);
//Set up textArea to be used as output stream for program
TextAreaOutputStream outputStream = new TextAreaOutputStream(engineOutput);
PrintStream printStream = new PrintStream(outputStream);
System.setOut(printStream);
//System.setErr(printStream);
}
}
很难确定,因为我不知道你的AutomationLoop和TextAreaOutputStream类做什么,但它听起来像一个线程问题。
所有Swing代码都需要在事件分派线程中执行。如果您有一个长时间运行的代码,没有更新GUI,那么您可能希望它运行另一个线程,否则GUI没有机会更新。从您的行为来看,loop . startloop()似乎在事件调度线程中运行,因此GUI永远没有机会更新自己。
loop . startloop()是否启动一个新线程?如果没有,它可能应该;否则,直到代码完成执行,您的GUI才会更新。