blob: 7d215316fafd88abcf8620512919f172f54edbf5 [file] [log] [blame]
duke6e45e102007-12-01 00:00:00 +00001/*
2 * Copyright 2007 Sun Microsystems, Inc. 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 Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
20 * CA 95054 USA or visit www.sun.com if you need additional information or
21 * have any questions.
22 */
23
24/*
25 @test
26 @bug 4811096
27 @summary Tests whether opaque and non-opaque components mix correctly
28 @author anthony.petrov@...: area=awt.mixing
29 @library ../regtesthelpers
30 @build Util
31 @run main OpaqueTest
32*/
33
34
35/**
36 * OpaqueTest.java
37 *
38 * summary: OpaqueTest
39 */
40
41import java.awt.*;
42import java.awt.event.*;
43import javax.swing.*;
44import test.java.awt.regtesthelpers.Util;
anthony421dab82009-02-04 11:58:13 +030045import com.sun.awt.AWTUtilities;
duke6e45e102007-12-01 00:00:00 +000046
47
48
49public class OpaqueTest
50{
51
52 //*** test-writer defined static variables go here ***
53
54 static String testSeq = new String("");
55 final static String checkSeq = new String("010000101");
56
57 private static void init()
58 {
59 //*** Create instructions for the user here ***
60
61 String[] instructions =
62 {
63 "This is an AUTOMATIC test, simply wait until it is done.",
64 "The result (passed or failed) will be shown in the",
65 "message window below."
66 };
67 Sysout.createDialog( );
68 Sysout.printInstructions( instructions );
69
70
71 // Create components
72 final Frame f = new Frame("Button-JButton mix test");
73 final Panel p = new Panel();
74 final Button heavy = new Button(" Heavyweight Button ");
75 final JButton light = new JButton(" LW Button ");
76
77 // Actions for the buttons add appropriate number to the test sequence
78 heavy.addActionListener(new java.awt.event.ActionListener()
79 {
80 public void actionPerformed(java.awt.event.ActionEvent e) {
81 p.setComponentZOrder(light, 0);
anthony421dab82009-02-04 11:58:13 +030082 f.validate();
duke6e45e102007-12-01 00:00:00 +000083 testSeq = testSeq + "0";
84 }
85 }
86 );
87
88 light.addActionListener(new java.awt.event.ActionListener()
89 {
90 public void actionPerformed(java.awt.event.ActionEvent e) {
91 p.setComponentZOrder(heavy, 0);
anthony421dab82009-02-04 11:58:13 +030092 f.validate();
duke6e45e102007-12-01 00:00:00 +000093 testSeq = testSeq + "1";
94 }
95 }
96 );
97
98 // Overlap the buttons
99 heavy.setBounds(30, 30, 200, 200);
100 light.setBounds(10, 10, 50, 50);
101
102 // Put the components into the frame
103 p.setLayout(null);
104 p.add(heavy);
105 p.add(light);
106 f.add(p);
107 f.setBounds(50, 50, 400, 400);
108 f.show();
109
110
111 Robot robot = Util.createRobot();
112 robot.setAutoDelay(20);
113
114 Util.waitForIdle(robot);
115
116 // Move the mouse pointer to the position where both
117 // buttons overlap
118 Point heavyLoc = heavy.getLocationOnScreen();
119 robot.mouseMove(heavyLoc.x + 5, heavyLoc.y + 5);
120
121 // Now perform the click at this point for 9 times
122 // In the middle of the process toggle the opaque
123 // flag value.
124 for (int i = 0; i < 9; ++i) {
125 if (i == 3) {
anthony421dab82009-02-04 11:58:13 +0300126 AWTUtilities.setComponentMixingCutoutShape(light,
127 new Rectangle());
duke6e45e102007-12-01 00:00:00 +0000128 }
129 if (i == 6) {
anthony421dab82009-02-04 11:58:13 +0300130 AWTUtilities.setComponentMixingCutoutShape(light,
131 null);
duke6e45e102007-12-01 00:00:00 +0000132 }
133
134 robot.mousePress(InputEvent.BUTTON1_MASK);
135 robot.mouseRelease(InputEvent.BUTTON1_MASK);
136 Util.waitForIdle(robot);
137 }
138
139 Util.waitForIdle(robot);
140
141 // If the buttons are correctly mixed, the test sequence
142 // is equal to the check sequence.
143 if (testSeq.equals(checkSeq)) {
144 OpaqueTest.pass();
145 } else {
146 OpaqueTest.fail("The components changed their visible Z-order in a wrong sequence: '" + testSeq + "' instead of '" + checkSeq + "'");
147 }
148 }//End init()
149
150
151
152 /*****************************************************
153 * Standard Test Machinery Section
154 * DO NOT modify anything in this section -- it's a
155 * standard chunk of code which has all of the
156 * synchronisation necessary for the test harness.
157 * By keeping it the same in all tests, it is easier
158 * to read and understand someone else's test, as
159 * well as insuring that all tests behave correctly
160 * with the test harness.
161 * There is a section following this for test-
162 * classes
163 ******************************************************/
164 private static boolean theTestPassed = false;
165 private static boolean testGeneratedInterrupt = false;
166 private static String failureMessage = "";
167
168 private static Thread mainThread = null;
169
170 private static int sleepTime = 300000;
171
172 // Not sure about what happens if multiple of this test are
173 // instantiated in the same VM. Being static (and using
174 // static vars), it aint gonna work. Not worrying about
175 // it for now.
176 public static void main( String args[] ) throws InterruptedException
177 {
178 mainThread = Thread.currentThread();
179 try
180 {
181 init();
182 }
183 catch( TestPassedException e )
184 {
185 //The test passed, so just return from main and harness will
186 // interepret this return as a pass
187 return;
188 }
189 //At this point, neither test pass nor test fail has been
190 // called -- either would have thrown an exception and ended the
191 // test, so we know we have multiple threads.
192
193 //Test involves other threads, so sleep and wait for them to
194 // called pass() or fail()
195 try
196 {
197 Thread.sleep( sleepTime );
198 //Timed out, so fail the test
199 throw new RuntimeException( "Timed out after " + sleepTime/1000 + " seconds" );
200 }
201 catch (InterruptedException e)
202 {
203 //The test harness may have interrupted the test. If so, rethrow the exception
204 // so that the harness gets it and deals with it.
205 if( ! testGeneratedInterrupt ) throw e;
206
207 //reset flag in case hit this code more than once for some reason (just safety)
208 testGeneratedInterrupt = false;
209
210 if ( theTestPassed == false )
211 {
212 throw new RuntimeException( failureMessage );
213 }
214 }
215
216 }//main
217
218 public static synchronized void setTimeoutTo( int seconds )
219 {
220 sleepTime = seconds * 1000;
221 }
222
223 public static synchronized void pass()
224 {
225 Sysout.println( "The test passed." );
226 Sysout.println( "The test is over, hit Ctl-C to stop Java VM" );
227 //first check if this is executing in main thread
228 if ( mainThread == Thread.currentThread() )
229 {
230 //Still in the main thread, so set the flag just for kicks,
231 // and throw a test passed exception which will be caught
232 // and end the test.
233 theTestPassed = true;
234 throw new TestPassedException();
235 }
236 theTestPassed = true;
237 testGeneratedInterrupt = true;
238 mainThread.interrupt();
239 }//pass()
240
241 public static synchronized void fail()
242 {
243 //test writer didn't specify why test failed, so give generic
244 fail( "it just plain failed! :-)" );
245 }
246
247 public static synchronized void fail( String whyFailed )
248 {
249 Sysout.println( "The test failed: " + whyFailed );
250 Sysout.println( "The test is over, hit Ctl-C to stop Java VM" );
251 //check if this called from main thread
252 if ( mainThread == Thread.currentThread() )
253 {
254 //If main thread, fail now 'cause not sleeping
255 throw new RuntimeException( whyFailed );
256 }
257 theTestPassed = false;
258 testGeneratedInterrupt = true;
259 failureMessage = whyFailed;
260 mainThread.interrupt();
261 }//fail()
262
263}// class OpaqueTest
264
265//This exception is used to exit from any level of call nesting
266// when it's determined that the test has passed, and immediately
267// end the test.
268class TestPassedException extends RuntimeException
269{
270}
271
272//*********** End Standard Test Machinery Section **********
273
274
275//************ Begin classes defined for the test ****************
276
277// if want to make listeners, here is the recommended place for them, then instantiate
278// them in init()
279
280/* Example of a class which may be written as part of a test
281class NewClass implements anInterface
282 {
283 static int newVar = 0;
284
285 public void eventDispatched(AWTEvent e)
286 {
287 //Counting events to see if we get enough
288 eventCount++;
289
290 if( eventCount == 20 )
291 {
292 //got enough events, so pass
293
294 OpaqueTest.pass();
295 }
296 else if( tries == 20 )
297 {
298 //tried too many times without getting enough events so fail
299
300 OpaqueTest.fail();
301 }
302
303 }// eventDispatched()
304
305 }// NewClass class
306
307*/
308
309
310//************** End classes defined for the test *******************
311
312
313
314
315/****************************************************
316 Standard Test Machinery
317 DO NOT modify anything below -- it's a standard
318 chunk of code whose purpose is to make user
319 interaction uniform, and thereby make it simpler
320 to read and understand someone else's test.
321 ****************************************************/
322
323/**
324 This is part of the standard test machinery.
325 It creates a dialog (with the instructions), and is the interface
326 for sending text messages to the user.
327 To print the instructions, send an array of strings to Sysout.createDialog
328 WithInstructions method. Put one line of instructions per array entry.
329 To display a message for the tester to see, simply call Sysout.println
330 with the string to be displayed.
331 This mimics System.out.println but works within the test harness as well
332 as standalone.
333 */
334
335class Sysout
336{
337 private static TestDialog dialog;
338
339 public static void createDialogWithInstructions( String[] instructions )
340 {
341 dialog = new TestDialog( new Frame(), "Instructions" );
342 dialog.printInstructions( instructions );
343 dialog.setVisible(true);
344 println( "Any messages for the tester will display here." );
345 }
346
347 public static void createDialog( )
348 {
349 dialog = new TestDialog( new Frame(), "Instructions" );
350 String[] defInstr = { "Instructions will appear here. ", "" } ;
351 dialog.printInstructions( defInstr );
352 dialog.setVisible(true);
353 println( "Any messages for the tester will display here." );
354 }
355
356
357 public static void printInstructions( String[] instructions )
358 {
359 dialog.printInstructions( instructions );
360 }
361
362
363 public static void println( String messageIn )
364 {
365 dialog.displayMessage( messageIn );
366 System.out.println(messageIn);
367 }
368
369}// Sysout class
370
371/**
372 This is part of the standard test machinery. It provides a place for the
373 test instructions to be displayed, and a place for interactive messages
374 to the user to be displayed.
375 To have the test instructions displayed, see Sysout.
376 To have a message to the user be displayed, see Sysout.
377 Do not call anything in this dialog directly.
378 */
379class TestDialog extends Dialog
380{
381
382 TextArea instructionsText;
383 TextArea messageText;
384 int maxStringLength = 80;
385
386 //DO NOT call this directly, go through Sysout
387 public TestDialog( Frame frame, String name )
388 {
389 super( frame, name );
390 int scrollBoth = TextArea.SCROLLBARS_BOTH;
391 instructionsText = new TextArea( "", 15, maxStringLength, scrollBoth );
392 add( "North", instructionsText );
393
394 messageText = new TextArea( "", 5, maxStringLength, scrollBoth );
395 add("Center", messageText);
396
397 pack();
398
399 setVisible(true);
400 }// TestDialog()
401
402 //DO NOT call this directly, go through Sysout
403 public void printInstructions( String[] instructions )
404 {
405 //Clear out any current instructions
406 instructionsText.setText( "" );
407
408 //Go down array of instruction strings
409
410 String printStr, remainingStr;
411 for( int i=0; i < instructions.length; i++ )
412 {
413 //chop up each into pieces maxSringLength long
414 remainingStr = instructions[ i ];
415 while( remainingStr.length() > 0 )
416 {
417 //if longer than max then chop off first max chars to print
418 if( remainingStr.length() >= maxStringLength )
419 {
420 //Try to chop on a word boundary
421 int posOfSpace = remainingStr.
422 lastIndexOf( ' ', maxStringLength - 1 );
423
424 if( posOfSpace <= 0 ) posOfSpace = maxStringLength - 1;
425
426 printStr = remainingStr.substring( 0, posOfSpace + 1 );
427 remainingStr = remainingStr.substring( posOfSpace + 1 );
428 }
429 //else just print
430 else
431 {
432 printStr = remainingStr;
433 remainingStr = "";
434 }
435
436 instructionsText.append( printStr + "\n" );
437
438 }// while
439
440 }// for
441
442 }//printInstructions()
443
444 //DO NOT call this directly, go through Sysout
445 public void displayMessage( String messageIn )
446 {
447 messageText.append( messageIn + "\n" );
448 System.out.println(messageIn);
449 }
450
451}// TestDialog class