1/*
2 * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 */
23
24/**
25 * @test
26 * @key headful
27 * @bug 8027628
28 * @author Oleg Pekhovskiy
29 * @summary JWindow jumps to (0, 0) after mouse clicked
30 * @run main TopLevelLocation
31 */
32
33import java.awt.Color;
34import java.awt.Dimension;
35import java.awt.EventQueue;
36import java.awt.Point;
37import java.awt.Robot;
38import java.awt.event.MouseAdapter;
39import java.awt.event.MouseEvent;
40import javax.swing.JFrame;
41import javax.swing.JWindow;
42
43public class TopLevelLocation {
44
45    private static JFrame frame;
46    private static JWindow window;
47    private static boolean passed = true;
48
49    public static void main(String[] args) throws Exception {
50        EventQueue.invokeAndWait(() -> {
51            frame = new JFrame();
52            frame.getContentPane().setBackground(Color.PINK);
53            frame.setBounds(100, 100, 500, 400);
54            frame.setUndecorated(true);
55            frame.setVisible(true);
56            window = new JWindow(frame);
57            window.setBackground(Color.BLUE);
58            window.setAlwaysOnTop(true);
59            window.setBounds(200, 200, 200, 200);
60            window.addMouseListener(new MouseAdapter() {
61                private Point dragOrigin = null;
62                private Dimension origSize = null;
63                private Point origLoc = null;
64                private Point lastLoc = null;
65                private boolean left = false;
66                private boolean top = false;
67                private boolean bottom = false;
68                private boolean right = false;
69
70                @Override
71                public void mousePressed(MouseEvent e) {
72                    System.out.println("mousePressed");
73                    dragOrigin = e.getLocationOnScreen();
74                    origSize = window.getSize();
75                    origLoc = window.getLocationOnScreen();
76                    if (lastLoc != null) {
77                        System.out.println("SET LOCATION: " + lastLoc);
78                        System.out.println("CURRENT LOCATION: " + origLoc);
79                        if (lastLoc.x != origLoc.x || lastLoc.y != origLoc.y) {
80                            passed = false;
81                        }
82                    }
83                    right = (origLoc.x + window.getWidth() - dragOrigin.x) < 5;
84                    left = !right && dragOrigin.x - origLoc.x < 5;
85                    bottom = (origLoc.y + window.getHeight() - dragOrigin.y) < 5;
86                    top = !bottom && dragOrigin.y - origLoc.y < 5;
87                }
88
89                @Override
90                public void mouseDragged(MouseEvent e) {
91                    System.out.println("mouseDragged");
92                    resize(e);
93                }
94
95                @Override
96                public void mouseReleased(MouseEvent e) {
97                    System.out.println("mouseReleased");
98                    resize(e);
99                }
100
101                void resize(MouseEvent e) {
102                    Point dragDelta = e.getLocationOnScreen();
103                    dragDelta.translate(-dragOrigin.x, -dragOrigin.y);
104                    Point newLoc = new Point(origLoc);
105                    newLoc.translate(dragDelta.x, dragDelta.y);
106                    Dimension newSize = new Dimension(origSize);
107                    if (left || right) {
108                        newSize.width += right ? dragDelta.x : -dragDelta.x;
109                    }
110                    if (top || bottom) {
111                        newSize.height += bottom ? dragDelta.y : -dragDelta.y;
112                    }
113                    if (right || (top || bottom) && !left) {
114                        newLoc.x = origLoc.x;
115                    }
116                    if (bottom || (left || right) && !top) {
117                        newLoc.y = origLoc.y;
118                    }
119                    window.setBounds(newLoc.x, newLoc.y, newSize.width, newSize.height);
120                    lastLoc = newLoc;
121                }
122            });
123            window.setVisible(true);
124        });
125        Thread.sleep(500);
126        Dimension size = window.getSize();
127        Point location = window.getLocation();
128        Robot robot = new Robot();
129        robot.setAutoDelay(200);
130        robot.setAutoWaitForIdle(true);
131        robot.waitForIdle();
132        robot.mouseMove(location.x + size.height - 2, location.y + size.width - 2);
133        robot.mousePress(MouseEvent.BUTTON1_DOWN_MASK);
134        robot.mouseMove(location.x + size.height, location.y + size.width);
135        robot.mouseRelease(MouseEvent.BUTTON1_DOWN_MASK);
136        robot.mousePress(MouseEvent.BUTTON1_DOWN_MASK);
137        robot.mouseMove(location.x + size.height + 2, location.y + size.width + 2);
138        robot.mouseRelease(MouseEvent.BUTTON1_DOWN_MASK);
139        Thread.sleep(500);
140        frame.dispose();
141        if (!passed) {
142            throw new RuntimeException("TEST FAILED: Location doesn't match!");
143        }
144        System.out.println("TEST PASSED!");
145    }
146}
147
148