1

我有一个名为 GameUpdater 的 java 类,它扩展了 JInternalFrame。当我将类作为程序单独运行时,它曾经扩展 JFrame,但我将其更改为 JInternalFrame 以成为更大应用程序的一部分 - 现在可以通过菜单按钮访问。

当我按下这个菜单按钮时调用的函数如下:

private void update(){

    GameUpdater gu = new GameUpdater();
    desktop.add(gu); //add to JDesktopPane
    gu.setSize(400, 300);
    gu.setVisible(true);

    gu.readMatches();//this function takes ages

    gu.setMatch("Updating database...");//this is some output to the user, displays info in the internal frame
    //try and insert into database
    for(Match m : gu.getMatches()){
        db.insertMatch(m);
    }
    gu.setMatch("DONE"); //now it shows the frame, way too late
}

gu.readMatches() 方法执行需要很长时间,因此它会定期更新 JInternalFrame 中的内容以显示其进度。但是,在此更新功能完成之前,不会显示框架!

就像 setVisible(true) 一直等到函数结束......

当它是 JFrame 时,它​​工作得非常好。JInternalFrame 是否有任何奇怪的属性会导致这种情况?

干杯

4

2 回答 2

2

听起来您正在事件调度线程(EDT)中执行一个耗时的过程,这将防止事件队列处理(除其他外)重绘请求。

这将使您的程序看起来好像它已“挂起”。

您需要将此任务卸载到后台线程。

阅读Swing 中的 Concurrency,尤其是关于Worker Threads 和 SwingWorker的部分

于 2012-09-17T19:39:37.737 回答
2

问题是您正在阻止您的EDT,这可以通过简单地创建一个新的Thread/ Runnablethar 调用 gu.readMatches();该方法来解决:

SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
gu.readMatches(); //gu will have to be declared `final`

gu.setMatch("Updating database...");//this is some output to the user, displays info in the internal frame
//try and insert into database
for(Match m : gu.getMatches()){
    db.insertMatch(m);
}
}
});

当然,尽管您可能想要实现 aJProgressBar以便用户可以跟踪读数的距离。

于 2012-09-17T19:40:25.283 回答