Java setFullScreenWindow() 保持在最顶层

13

我正在编写一个应用程序,旨在在双显示器设置上运行,在一个显示器上全屏显示“Display”JFrame,在另一个显示器上显示“Control”JFrame,并向“Display”发送指令。我尝试了两种不同的方法来设置“Display”全屏;每种方法的成功似乎取决于操作系统。

display.setUndecorated(true);
display.setExtendedState(JFrame.MAXIMIZED_BOTH);

在Windows中可以工作,但JFrame在OS X和Linux下会隐藏在Dock/面板下方。

我使用的另一种方法是:

GraphicsDevice.setFullScreenWindow(display);

在我尝试的三个操作系统中都能正常工作,但在 Windows 中,将控制窗口聚焦到另一台显示器上会导致显示窗口隐藏,并调用

display.setAlwaysOnTop(true);

这并没有解决问题。我偏爱使用GraphicsDevice方法,因为我不必处理在OS X或Linux中出现的问题,并且我希望Windows的问题可以简单解决。它可以吗?

2个回答

10

尝试这个...

适用于多屏幕

GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
GraphicsDevice[] gs = ge.getScreenDevices();


// Get size of each screen

for (int i=0; i<gs.length; i++) {
    DisplayMode dm = gs[i].getDisplayMode();
    int screenWidth = dm.getWidth();
    int screenHeight = dm.getHeight();
}

使用public final void setAlwaysOnTop(boolean alwaysOnTop)方法来使窗口置顶。如果该窗口可见,该方法会将窗口toFront并“固定”在最上方。


谢谢您的回答,但是我应该如何处理那个for循环中的宽度和高度值呢?我尝试使用setAlwaysOnTop(true);,但是当我尝试时它并没有起作用。我还需要一个小时左右才能访问Windows,但我注意到您说“如果窗口可见”,所以也许在设置窗口可见之前我已经调用了它?我会尽快尝试并接受您的答案,如果它有效的话。 - BitFiber
太晚了,无法编辑我的评论...但是在Windows中setAlwaysOnTop(true);仍然不起作用。然而,我发现一个解决方法是使用System.getProperty("os.name");来检查当前操作系统是否为Windows,这样我就可以使用setExtendedState方法代替。 - BitFiber
很抱歉它对你没有起作用,但感谢你提供的解决方法信息。 - Kumar Vivek Mitra
1
我在Windows上遇到了同样的问题,解决方案是什么?我尝试使用´setExtendedState(JFrame.MAXIMIZED_BOTH)´,但在某些情况下它不起作用,而且当它起作用时,图形没有更新。 - AngelAvila
1
这个回答与问题毫无关系。我不明白它怎么能被标记为正确并得到+10分。 - Newbie

4
我遇到了同样的问题。我的解决方法是重写jframe中的show()函数,并使用缓冲策略,从而永远不会退出show函数。因此可以像这样实现:
 @override
 public void show(){
        super.show();
        //Create a double buffering strategy
        createBufferStrategy(2);
        BufferStrategy bs = getBufferStrategy();
        while(true){
              //draw our frame
              Graphics g = bs.getGraphics();
              paint(g);
              //dispose of our graphics
              g.dispose();
              //Show our frame
              bs.show();
              try{
                  //Don't use all our cpu-power
                  Thread.sleep(10);
              }catch(Exception e){
                  //Do something (this probably will never happen)
              }
        }
 }

使用setVisible(boolean)代替show()会更好(show已经被弃用)。窗口不会总是置顶(你仍然可以将另一个窗口拖到它的上面),但是当你将焦点切换到另一个窗口时,它不会自动隐藏。我想这就是你想要的行为。

注意:不要在事件队列中调用show,因为这会使事件队列无效,并使jframe忽略所有事件。应该在一个新线程中调用show函数,这样所有事件仍将得到处理。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接