在双监视器configuration的特定屏幕中显示JFrame
我有一个双显示器configuration,我想运行我的graphics用户界面在特定的显示器,如果它被发现。 我试图创build我的JFrame
窗口,通过我的屏幕设备的GraphicConfiguration
对象,但它不起作用,帧仍然显示在主屏幕上。
我怎样才能设置我的框架必须显示的屏幕?
public static void showOnScreen( int screen, JFrame frame ) { GraphicsEnvironment ge = GraphicsEnvironment .getLocalGraphicsEnvironment(); GraphicsDevice[] gs = ge.getScreenDevices(); if( screen > -1 && screen < gs.length ) { gs[screen].setFullScreenWindow( frame ); } else if( gs.length > 0 ) { gs[0].setFullScreenWindow( frame ); } else { throw new RuntimeException( "No Screens Found" ); } }
我修改了@ Joseph-gordon的答案,以便在不强制全屏的情况下实现这一点:
public static void showOnScreen( int screen, JFrame frame ) { GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment(); GraphicsDevice[] gd = ge.getScreenDevices(); if( screen > -1 && screen < gd.length ) { frame.setLocation(gd[screen].getDefaultConfiguration().getBounds().x, frame.getY()); } else if( gd.length > 0 ) { frame.setLocation(gd[0].getDefaultConfiguration().getBounds().x, frame.getY()); } else { throw new RuntimeException( "No Screens Found" ); } }
在这个代码中,我假设getDefaultConfiguration()
永远不会返回null。 如果情况不是这样,那么请有人纠正我。 但是,这段代码的作品将您的JFrame
移动到所需的屏幕。
请参考GraphicsDevice API,你有一个很好的例子。
我的经验是将桌面扩展到多个显示器,而将显示器configuration为单独的(X11)显示器。 如果这不是你想要做的,这将不适用。
我的解决scheme是一个黑客:我叫Toolkit.getScreenSize()
,确定如果我在一个多显示器的情况下(通过比较高度和宽度,并假设宽度>两倍的高度表示多显示器),然后设置框架的初始X和Y位置。
阅读屏幕2上的JFrame.setLocationRelativeTo Display的文档后,获得更干净的解决scheme
public void moveToScreen() { setVisible(false); GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment(); GraphicsDevice[] screens = ge.getScreenDevices(); int n = screens.length; for (int i = 0; i < n; i++) { if (screens[i].getIDstring().contentEquals(settings.getScreen())) { JFrame dummy = new JFrame(screens[i].getDefaultConfiguration()); setLocationRelativeTo(dummy); dummy.dispose(); } } setVisible(true); }
这个function可以用来在屏幕之间切换应用程序窗口
对我来说也工作得很好(假设左侧显示器尺寸为1920×1200):
A)在左侧显示器上设置确切的位置:
newFrame.setBounds(200,100,400,200)
B)在正确的位置上设置显示器:
newFrame.setBounds(2000,100,200,100)
C)设置在左侧显示器上最大化:
newFrame.setBounds(200,100,400,200)
newFrame.setExtendedState(JFrame.MAXIMIZED_BOTH)
D)设置在正确的显示器上最大化
newFrame.setBounds(2000,100,200,100)
newFrame.setExtendedState(JFrame.MAXIMIZED_BOTH)
这里的许多解决scheme适用于扩展显示器。 如果使用单独的显示器,只需将所需graphics设备的graphicsconfiguration对象传递给jframe或jdialog的构造函数。
Vickys答案包含正确的指针。 它是新的JFrame(GraphicsConfiguration gc)。
你可以这样做:
GraphicsDevice otherScreen = getOtherScreen(this); JFrame frameOnOtherScreen = new JFrame(otherScreen.getDefaultConfiguration()); private GraphicsDevice getOtherScreen(Component component) { GraphicsEnvironment graphicsEnvironment = GraphicsEnvironment.getLocalGraphicsEnvironment(); if (graphicsEnvironment.getScreenDevices().length == 1) { // if there is only one screen, return that one return graphicsEnvironment.getScreenDevices()[0]; } GraphicsDevice theWrongOne = component.getGraphicsConfiguration().getDevice(); for (GraphicsDevice dev : graphicsEnvironment.getScreenDevices()) { if (dev != theWrongOne) { return dev; } } return null; }
如果你想把它设置在左边屏幕的中心:
int halfScreen = (int)(screenSize.width/2); frame.setLocation((halfScreen - frame.getSize().width)/2, (screenSize.height - frame.getSize().height)/2);
如果你想将它设置为右侧屏幕的中心:
int halfScreen = (int)(screenSize.width/2); frame.setLocation((halfScreen - frame.getSize().width)/2 + halfScreen, (screenSize.height - frame.getSize().height)/2);
我修改了@ Joseph-gordon和@ryvantage答案,以便在不强制全屏,固定屏幕configuration位置的情况下实现此目的,并将其居中在select屏幕上:
public void showOnScreen(int screen, JFrame frame ) { GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment(); GraphicsDevice[] gd = ge.getScreenDevices(); int width = 0, height = 0; if( screen > -1 && screen < gd.length ) { width = gd[screen].getDefaultConfiguration().getBounds().width; height = gd[screen].getDefaultConfiguration().getBounds().height; frame.setLocation( ((width / 2) - (frame.getSize().width / 2)) + gd[screen].getDefaultConfiguration().getBounds().x, ((height / 2) - (frame.getSize().height / 2)) + gd[screen].getDefaultConfiguration().getBounds().y ); frame.setVisible(true); } else { throw new RuntimeException( "No Screens Found" ); } }
随着每个人都根据其他口味进行自己口味的调配, 我添加了我的,因为其他人将您locking在所选屏幕上的窗口位置上。
这是最好的。 它允许您在另一个屏幕上设置位置。
public void setLocation( int screen, double x, double y ) { GraphicsEnvironment g = GraphicsEnvironment.getLocalGraphicsEnvironment(); GraphicsDevice[] d = g.getScreenDevices(); if ( screen >= d.length ) { screen = d.length - 1; } Rectangle bounds = d[screen].getDefaultConfiguration().getBounds(); // Is double? if ( x == Math.floor(x) && !Double.isInfinite(x) ) { x *= bounds.x; // Decimal -> percentage } if ( y == Math.floor(y) && !Double.isInfinite(y) ) { y *= bounds.y; // Decimal -> percentage } x = bounds.x + x; y = jframe.getY() + y; if ( x > bounds.x) x = bounds.x; if ( y > bounds.y) y = bounds.y; // If double we do want to floor the value either way jframe.setLocation((int)x, (int)y); }
例:
setLocation(2, 200, 200);
甚至可以让你通过屏幕位置的百分比!
setLocation(2, 0.5, 0); // Place on right edge from the top down if combined with setSize(50%, 100%);
屏幕必须大于0,我相信这是一个强硬的要求!
要放在最后,只需使用Integer.MAX_VALUE调用。**