/* * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * This code is free software; you can redistribute it and/or modify it * under the terms of the GNU General Public License version 2 only, as * published by the Free Software Foundation. * * This code is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License * version 2 for more details (a copy is included in the LICENSE file that * accompanied this code). * * You should have received a copy of the GNU General Public License version * 2 along with this work; if not, write to the Free Software Foundation, * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. * * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA * or visit www.oracle.com if you need additional information or have any * questions. */ import java.awt.*; import java.util.ArrayList; import javax.swing.*; /* @test @summary Toplevel should be correctly positioned as relative to a component: so that their centers coincide or, if the component is hidden, centered on the screen. @bug 8036915 @library ../../../../lib/testlibrary @build ExtendedRobot @run main/timeout=1200 SetLocationRelativeToTest @key randomness */ public class SetLocationRelativeToTest { private static int delay = 500; private static boolean testEverything = false;// NB: change this to true to test everything java.util.List awtToplevels = new ArrayList(); java.util.List swingToplevels = new ArrayList(); java.util.List allToplevels = new ArrayList(); java.util.List awtComponents = new ArrayList(); java.util.List swingComponents = new ArrayList(); java.util.List allComponents = new ArrayList(); Label placeholder = new Label(); JLabel jplaceholder = new JLabel(); JFrame jcontainer; public SetLocationRelativeToTest() { Frame frame = new Frame("Frame"); frame.setSize(200,100); Frame uframe = new Frame("U.Frame"); uframe.setUndecorated(true); uframe.setSize(200,100); Window window = new Window(frame); window.setSize(200,100); Dialog dialog = new Dialog(frame, "Dialog"); dialog.setSize(200,100); awtToplevels.add(frame); awtToplevels.add(uframe); awtToplevels.add(window); awtToplevels.add(dialog); awtComponents.add(new TextArea("Am a TextArea")); awtComponents.add(new TextField("Am a TextField")); awtComponents.add(new Button("Press")); awtComponents.add(new Label("Label")); Choice aChoice = new Choice(); aChoice.add("One"); aChoice.add("Two"); awtComponents.add(aChoice); awtComponents.add(new Canvas()); awtComponents.add(new List(4)); awtComponents.add(new Checkbox("Me CheckBox")); awtComponents.add(new Scrollbar()); swingComponents.add(new JTextArea("Am a JTextArea")); swingComponents.add(new JTextField("Am a JTextField")); swingComponents.add(new JButton("Press")); swingComponents.add(new JLabel("JLabel")); JComboBox jcombo = new JComboBox(); swingComponents.add(jcombo); swingComponents.add(new JPanel()); swingComponents.add(new JList()); swingComponents.add(new JCheckBox("Me JCheckBox")); swingComponents.add(new JScrollBar()); } public static void main(String args[]) { SetLocationRelativeToTest test = new SetLocationRelativeToTest(); test.doAWTTest(true); test.doAWTTest(false); try { test.doSwingTest(true); test.doSwingTest(false); }catch(InterruptedException ie) { ie.printStackTrace(); }catch(java.lang.reflect.InvocationTargetException ite) { ite.printStackTrace(); throw new RuntimeException("InvocationTarget?"); } return; } // In regular testing, we select just few components to test // randomly. If full testing required, select many ("all"). void selectObjectsToTest(boolean doSwing) { allToplevels.clear(); allComponents.clear(); if(testEverything) { allToplevels.addAll(0, awtToplevels); allComponents.addAll(0, awtComponents); if(doSwing) { allToplevels.addAll(allToplevels.size(), swingToplevels); allComponents.addAll(allComponents.size(), swingComponents); } }else{ //select a random of each int i = (int)(java.lang.Math.random()*awtToplevels.size()); allToplevels.add(awtToplevels.get(i)); i = (int)(java.lang.Math.random()*awtComponents.size()); allComponents.add(awtComponents.get(i)); if(doSwing) { i = (int)(java.lang.Math.random()*swingToplevels.size()); allToplevels.add(swingToplevels.get(i)); i = (int)(java.lang.Math.random()*swingComponents.size()); allComponents.add(swingComponents.get(i)); } } } // create Frame, add an AWT component to it, // hide it (or not) and position a new toplevel // relativeTo void doAWTTest(boolean isHidden) { boolean res; ExtendedRobot robot; try { robot = new ExtendedRobot(); }catch(Exception ex) { ex.printStackTrace(); throw new RuntimeException("Failed: "+ex.getMessage()); } Frame container = new Frame("Frame"); container.setBounds(100,100,300,300); container.setLayout(new GridLayout(3,1)); container.add(placeholder); container.setVisible(true); selectObjectsToTest(false); for(Component c: allComponents) { placeholder.setText((isHidden ? "Hidden: " : "Below is ")+ c.getClass().getName()); c.setVisible(true); container.add(c); container.doLayout(); if(isHidden) { c.setVisible(false); } robot.waitForIdle(delay); for(Window w: allToplevels) { w.setLocationRelativeTo(c); w.setVisible(true); robot.waitForIdle(delay); res = compareLocations(w, c, robot); System.out.println(c.getClass().getName()+" \t: "+w.getClass().getName()+ ((w instanceof Frame) && (((Frame)w).isUndecorated()) ? " undec\t\t:" : "\t\t:")+" "+ (res ? "" : "Failed")); if(!res) { throw new RuntimeException("Test failed."); } w.dispose(); } container.remove(c); robot.waitForIdle(delay); } container.dispose(); } // Create JFrame, add an AWT or Swing component to it, // hide it (or not) and position a new toplevel // relativeTo void doSwingTest(boolean isHidden) throws InterruptedException, java.lang.reflect.InvocationTargetException { boolean res; ExtendedRobot robot; try { robot = new ExtendedRobot(); }catch(Exception ex) { ex.printStackTrace(); throw new RuntimeException("Failed: "+ex.getMessage()); } EventQueue.invokeAndWait( () -> { JFrame jframe = new JFrame("jframe"); jframe.setSize(200,100); swingToplevels.add(jframe); JFrame ujframe = new JFrame("ujframe"); ujframe.setSize(200,100); ujframe.setUndecorated(true); swingToplevels.add(ujframe); JWindow jwin = new JWindow(); jwin.setSize(200,100); swingToplevels.add(jwin); JDialog jdia = new JDialog((Frame)null, "JDialog"); jdia.setSize(200,100); swingToplevels.add(jdia); jcontainer = new JFrame("JFrame"); jcontainer.setBounds(100,100,300,300); jcontainer.setLayout(new GridLayout(3,1)); jcontainer.add(jplaceholder); jcontainer.setVisible(true); selectObjectsToTest(true); }); robot.waitForIdle(delay); for(Component c: allComponents) { EventQueue.invokeAndWait( () -> { jplaceholder.setText((isHidden ? "Hidden: " : "Below is: ")+ c.getClass().getName()); c.setVisible(true); jcontainer.add(c); jcontainer.doLayout(); if(isHidden) { c.setVisible(false); } }); robot.waitForIdle(delay); for(Window w: allToplevels) { EventQueue.invokeAndWait( () -> { w.setLocationRelativeTo(c); w.setVisible(true); }); robot.waitForIdle(delay); res = compareLocations(w, c, robot); System.out.println(c.getClass().getName()+" \t: "+w.getClass().getName()+ ((w instanceof Frame) && (((Frame)w).isUndecorated()) ? " undec\t\t:" : "\t\t:")+" "+ (res ? "" : "Failed")); EventQueue.invokeAndWait( () -> { w.dispose(); }); robot.waitForIdle(); if(!res) { throw new RuntimeException("Test failed."); } } EventQueue.invokeAndWait( () -> { jcontainer.remove(c); }); robot.waitForIdle(delay); } EventQueue.invokeAndWait( () -> { jcontainer.dispose(); }); } // Check, finally, if w either is concentric with c // or sits in the center of the screen (if c is hidden) boolean compareLocations(final Window w, final Component c, ExtendedRobot robot) { final Point pc = new Point(); final Point pw = new Point(); try { EventQueue.invokeAndWait( () -> { pw.setLocation(w.getLocationOnScreen()); pw.translate(w.getWidth()/2, w.getHeight()/2); if(!c.isVisible()) { Rectangle screenRect = w.getGraphicsConfiguration().getBounds(); pc.setLocation(screenRect.x+screenRect.width/2, screenRect.y+screenRect.height/2); }else{ pc.setLocation(c.getLocationOnScreen()); pc.translate(c.getWidth()/2, c.getHeight()/2); } }); } catch(InterruptedException ie) { throw new RuntimeException("Interrupted"); } catch(java.lang.reflect.InvocationTargetException ite) { ite.printStackTrace(); throw new RuntimeException("InvocationTarget?"); } robot.waitForIdle(delay); // Compare with 1 tolerance to forgive possible rounding errors if(pc.x - pw.x > 1 || pc.x - pw.x < -1 || pc.y - pw.y > 1 || pc.y - pw.y < -1 ) { System.out.println("Center of "+(c.isVisible() ? "Component:" : "screen:")+pc); System.out.println("Center of Window:"+pw); System.out.println("Centers of "+w+" and "+c+" do not coincide"); return false; } return true; } }