1 /* 2 * Copyright (c) 2006, 2016, 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 6359129 28 @summary REGRESSION: Popup menus dont respond to selections when extend outside Applet 29 @author oleg.sukhodolsky area=awt.grab 30 @library ../../regtesthelpers 31 @build Util 32 @run main EmbeddedFrameTest1 33 */ 34 35 /** 36 * EmbeddedFrameTest1.java 37 * 38 * summary: REGRESSION: Popup menus dont respond to selections when extend outside Applet 39 */ 40 41 import java.awt.BorderLayout; 42 import java.awt.Dialog; 43 import java.awt.Frame; 44 import java.awt.Panel; 45 import java.awt.Robot; 46 import java.awt.TextArea; 47 import java.awt.Toolkit; 48 49 import java.awt.event.ActionEvent; 50 import java.awt.event.ActionListener; 51 52 import javax.swing.JButton; 53 import javax.swing.JPopupMenu; 54 55 import sun.awt.SunToolkit; 56 57 import test.java.awt.regtesthelpers.Util; 58 59 public class EmbeddedFrameTest1 60 { 61 private static void init() 62 { 63 //*** Create instructions for the user here *** 64 65 String[] instructions = { 66 "This is an AUTOMATIC test, simply wait until it is done.", 67 "The result (passed or failed) will be shown in the", 68 "message window below." 69 }; 70 71 Sysout.createDialog( ); 72 Sysout.printInstructions( instructions ); 73 74 SunToolkit tk = (SunToolkit) Toolkit.getDefaultToolkit(); 75 if ("sun.awt.motif.MToolkit".equals(tk.getClass().getName())) { 76 System.out.println("We shouldn't test MToolkit."); 77 EmbeddedFrameTest1.pass(); 78 return; 79 } 80 81 try { 82 final Frame frame = new Frame("AWT Frame"); 83 frame.pack(); 84 frame.setSize(200,200); 85 86 final Frame embedded_frame = Util.createEmbeddedFrame(frame); 87 embedded_frame.setSize(200, 200); 88 Sysout.println("embedded_frame = " + embedded_frame); 89 90 final JPopupMenu menu = new JPopupMenu(); 91 JButton item = new JButton("A button in popup"); 92 item.addActionListener(new ActionListener() { 93 public void actionPerformed(ActionEvent e) { 94 System.out.println("Button pressed"); 95 } 96 }); 97 98 menu.add(item); 99 100 final JButton btn = new JButton("Press me to see popup"); 101 btn.addActionListener(new ActionListener() { 102 public void actionPerformed(ActionEvent e) { 103 menu.show(btn, 0, btn.getHeight()); 104 } 105 }); 106 final Panel p = new Panel(); 107 p.setLayout(new BorderLayout()); 108 embedded_frame.add(p,BorderLayout.CENTER); 109 embedded_frame.validate(); 110 p.add(btn); 111 p.validate(); 112 frame.setVisible(true); 113 Robot robot = new Robot(); 114 tk.realSync(); 115 Util.clickOnComp(btn, robot); 116 tk.realSync(); 117 118 Util.clickOnComp(item, robot); 119 tk.realSync(); 120 if (item.getMousePosition() == null) { 121 throw new RuntimeException("Popup was not closed (mouse above it)"); 122 } 123 embedded_frame.remove(p); 124 embedded_frame.dispose(); 125 frame.dispose(); 126 } catch (Throwable thr) { 127 thr.printStackTrace(); 128 EmbeddedFrameTest1.fail("TEST FAILED: " + thr); 129 } 130 EmbeddedFrameTest1.pass(); 131 }//End init() 132 133 /***************************************************** 134 * Standard Test Machinery Section 135 * DO NOT modify anything in this section -- it's a 136 * standard chunk of code which has all of the 137 * synchronisation necessary for the test harness. 138 * By keeping it the same in all tests, it is easier 139 * to read and understand someone else's test, as 140 * well as insuring that all tests behave correctly 141 * with the test harness. 142 * There is a section following this for test- 143 * classes 144 ******************************************************/ 145 private static boolean theTestPassed = false; 146 private static boolean testGeneratedInterrupt = false; 147 private static String failureMessage = ""; 148 149 private static Thread mainThread = null; 150 151 private static int sleepTime = 300000; 152 153 // Not sure about what happens if multiple of this test are 154 // instantiated in the same VM. Being static (and using 155 // static vars), it aint gonna work. Not worrying about 156 // it for now. 157 public static void main( String args[] ) throws InterruptedException 158 { 159 mainThread = Thread.currentThread(); 160 try 161 { 162 init(); 163 } 164 catch( TestPassedException e ) 165 { 166 //The test passed, so just return from main and harness will 167 // interepret this return as a pass 168 return; 169 } 170 //At this point, neither test pass nor test fail has been 171 // called -- either would have thrown an exception and ended the 172 // test, so we know we have multiple threads. 173 174 //Test involves other threads, so sleep and wait for them to 175 // called pass() or fail() 176 try 177 { 178 Thread.sleep( sleepTime ); 179 //Timed out, so fail the test 180 throw new RuntimeException( "Timed out after " + sleepTime/1000 + " seconds" ); 181 } 182 catch (InterruptedException e) 183 { 184 //The test harness may have interrupted the test. If so, rethrow the exception 185 // so that the harness gets it and deals with it. 186 if( ! testGeneratedInterrupt ) throw e; 187 188 //reset flag in case hit this code more than once for some reason (just safety) 189 testGeneratedInterrupt = false; 190 191 if ( theTestPassed == false ) 192 { 193 throw new RuntimeException( failureMessage ); 194 } 195 } 196 197 }//main 198 199 public static synchronized void setTimeoutTo( int seconds ) 200 { 201 sleepTime = seconds * 1000; 202 } 203 204 public static synchronized void pass() 205 { 206 Sysout.println( "The test passed." ); 207 Sysout.println( "The test is over, hit Ctl-C to stop Java VM" ); 208 //first check if this is executing in main thread 209 if ( mainThread == Thread.currentThread() ) 210 { 211 //Still in the main thread, so set the flag just for kicks, 212 // and throw a test passed exception which will be caught 213 // and end the test. 214 theTestPassed = true; 215 throw new TestPassedException(); 216 } 217 theTestPassed = true; 218 testGeneratedInterrupt = true; 219 mainThread.interrupt(); 220 }//pass() 221 222 public static synchronized void fail() 223 { 224 //test writer didn't specify why test failed, so give generic 225 fail( "it just plain failed! :-)" ); 226 } 227 228 public static synchronized void fail( String whyFailed ) 229 { 230 Sysout.println( "The test failed: " + whyFailed ); 231 Sysout.println( "The test is over, hit Ctl-C to stop Java VM" ); 232 //check if this called from main thread 233 if ( mainThread == Thread.currentThread() ) 234 { 235 //If main thread, fail now 'cause not sleeping 236 throw new RuntimeException( whyFailed ); 237 } 238 theTestPassed = false; 239 testGeneratedInterrupt = true; 240 failureMessage = whyFailed; 241 mainThread.interrupt(); 242 }//fail() 243 244 }// class EmbeddedFrameTest1 245 246 //This exception is used to exit from any level of call nesting 247 // when it's determined that the test has passed, and immediately 248 // end the test. 249 class TestPassedException extends RuntimeException 250 { 251 } 252 253 //*********** End Standard Test Machinery Section ********** 254 255 256 /**************************************************** 257 Standard Test Machinery 258 DO NOT modify anything below -- it's a standard 259 chunk of code whose purpose is to make user 260 interaction uniform, and thereby make it simpler 261 to read and understand someone else's test. 262 ****************************************************/ 263 264 /** 265 This is part of the standard test machinery. 266 It creates a dialog (with the instructions), and is the interface 267 for sending text messages to the user. 268 To print the instructions, send an array of strings to Sysout.createDialog 269 WithInstructions method. Put one line of instructions per array entry. 270 To display a message for the tester to see, simply call Sysout.println 271 with the string to be displayed. 272 This mimics System.out.println but works within the test harness as well 273 as standalone. 274 */ 275 276 class Sysout 277 { 278 private static TestDialog dialog; 279 280 public static void createDialogWithInstructions( String[] instructions ) 281 { 282 dialog = new TestDialog( new Frame(), "Instructions" ); 283 dialog.printInstructions( instructions ); 284 dialog.setVisible(true); 285 println( "Any messages for the tester will display here." ); 286 } 287 288 public static void createDialog( ) 289 { 290 dialog = new TestDialog( new Frame(), "Instructions" ); 291 String[] defInstr = { "Instructions will appear here. ", "" } ; 292 dialog.printInstructions( defInstr ); 293 dialog.setVisible(true); 294 println( "Any messages for the tester will display here." ); 295 } 296 297 298 public static void printInstructions( String[] instructions ) 299 { 300 dialog.printInstructions( instructions ); 301 } 302 303 304 public static void println( String messageIn ) 305 { 306 dialog.displayMessage( messageIn ); 307 System.out.println(messageIn); 308 } 309 310 }// Sysout class 311 312 /** 313 This is part of the standard test machinery. It provides a place for the 314 test instructions to be displayed, and a place for interactive messages 315 to the user to be displayed. 316 To have the test instructions displayed, see Sysout. 317 To have a message to the user be displayed, see Sysout. 318 Do not call anything in this dialog directly. 319 */ 320 class TestDialog extends Dialog 321 { 322 323 TextArea instructionsText; 324 TextArea messageText; 325 int maxStringLength = 80; 326 327 //DO NOT call this directly, go through Sysout 328 public TestDialog( Frame frame, String name ) 329 { 330 super( frame, name ); 331 int scrollBoth = TextArea.SCROLLBARS_BOTH; 332 instructionsText = new TextArea( "", 15, maxStringLength, scrollBoth ); 333 add( "North", instructionsText ); 334 335 messageText = new TextArea( "", 5, maxStringLength, scrollBoth ); 336 add("Center", messageText); 337 338 pack(); 339 340 setVisible(true); 341 }// TestDialog() 342 343 //DO NOT call this directly, go through Sysout 344 public void printInstructions( String[] instructions ) 345 { 346 //Clear out any current instructions 347 instructionsText.setText( "" ); 348 349 //Go down array of instruction strings 350 351 String printStr, remainingStr; 352 for( int i=0; i < instructions.length; i++ ) 353 { 354 //chop up each into pieces maxSringLength long 355 remainingStr = instructions[ i ]; 356 while( remainingStr.length() > 0 ) 357 { 358 //if longer than max then chop off first max chars to print 359 if( remainingStr.length() >= maxStringLength ) 360 { 361 //Try to chop on a word boundary 362 int posOfSpace = remainingStr. 363 lastIndexOf( ' ', maxStringLength - 1 ); 364 365 if( posOfSpace <= 0 ) posOfSpace = maxStringLength - 1; 366 367 printStr = remainingStr.substring( 0, posOfSpace + 1 ); 368 remainingStr = remainingStr.substring( posOfSpace + 1 ); 369 } 370 //else just print 371 else 372 { 373 printStr = remainingStr; 374 remainingStr = ""; 375 } 376 377 instructionsText.append( printStr + "\n" ); 378 379 }// while 380 381 }// for 382 383 }//printInstructions() 384 385 //DO NOT call this directly, go through Sysout 386 public void displayMessage( String messageIn ) 387 { 388 messageText.append( messageIn + "\n" ); 389 System.out.println(messageIn); 390 } 391 392 }// TestDialog class