GWT PopupPanel没有在合适的时间显示

时间:2014-03-11 16:54:31

标签: javascript gwt

我有一个函数,只需单击一个按钮即可调用它,并且需要很长时间才能创建一个元素并将其附加到DOM,因此我希望在函数完成时显示一个带有“loading”图标的PopupPanel它必须这样做。请注意,我的函数不会调用服务器,它只会在UI中创建一些需要很长时间才能计算的元素,所以我没有onSuccess()事件或回调函数可以使用。

所以我有我的PopupPanel:

pp = new PopupPanel();
pp.setTitle("loading....");
pp.setGlassEnabled(true);

然后在点击处理程序上,我有以下代码:

public void onClick(ClickEvent event) {
  pp.show();
  functionWhichTakesaLongTimeToExecute();               
  pp.hide();
}

由于JavaScript是单线程的,我期待PopUp出现,然后执行functionWhichTakesaLongTimeToExecute()然后隐藏PopUp,但是发生的事情是functionWhichTakesaLongTimeToExecute()首先执行,需要很长时间才能将元素追加到DOM,只有在完成其工作后才显示PopUp然后隐藏。 就像代码一样:

functionWhichTakesaLongTimeToExecute(); 
pp.show();                  
pp.hide();

更令我困扰的是,如果我在pp.show()之后添加一个Window.alert(“test”),这将打破流程,直到警告中的OK按钮被按下,这导致PopUp出现之前警告和之前调用functionWhichTakesaLongTimeToExecute()。 因此,以下代码按预期工作:

pp.show();
Window.alert("test");
functionWhichTakesaLongTimeToExecute();                 
pp.hide(); 

有人可以向我解释为什么在调用functionWhichTakesaLongTimeToExecute()之前不显示PopUp,而是“等待”functionWhichTakesaLongTimeToExecute()执行,之后才会显示它以及添加Window.alert的原因(“测试”)使其正确显示?
PS:我已经测试了IE8和Chrome中的代码,行为是一样的。

2 个答案:

答案 0 :(得分:4)

这是你可以做到的:

pp.show();
Scheduler.get().scheduleDeferred(new ScheduledCommand() {

    @Override
    public void execute() {
        functionWhichTakesaLongTimeToExecute();
        pp.hide();
    }
});

我在这里解释一下:GWT: Timer and Scheduler Classes

答案 1 :(得分:0)

我在使用setGlassEnabled时遇到了一些问题。您可以通过从代码中删除setGlassEnabled(true)行来查看它是否有效吗?

我还要注意的另一件事是,你没有向PopupPanel添加任何小部件。在PopupPanel的源代码中,提到在调用show之前必须将子窗口小部件附加到PopupPanel对象。 http://code.google.com/p/google-web-toolkit/source/browse/trunk/user/src/com/google/gwt/user/client/ui/PopupPanel.java

请尝试这两种方法,如果其中任何一种有效,请告诉我。