1 /*
2  * Copyright (c) 2007, 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  * @bug 6497426
27  * @summary Tests that pressing of Ctrl+ascii mostly fires KEY_TYPED with a Unicode control symbols
28  * @author Yuri.Nesterenko@... area=awt.keyboard
29  * @run applet CtrlASCII.html
30  */
31 
32 // Note there is no @ in front of test above.  This is so that the
33 //  harness will not mistake this file as a test file.  It should
34 //  only see the html file as a test file. (the harness runs all
35 //  valid test files, so it would run this test twice if this file
36 //  were valid as well as the html file.)
37 // Also, note the area= after Your Name in the author tag.  Here, you
38 //  should put which functional area the test falls in.  See the
39 //  AWT-core home page -> test areas and/or -> AWT team  for a list of
40 //  areas.
41 // Note also the 'RobotLWTest.html' in the run tag.  This should
42 //  be changed to the name of the test.
43 
44 
45 /**
46  * CtrlASCII.java
47  *
48  * @summary Tests that pressing of Ctrl+ascii mostly fires KEY_TYPED with a Unicode control symbols
49  */
50 
51 import java.applet.Applet;
52 import java.awt.*;
53 import java.awt.event.*;
54 import java.util.*;
55 
56 
57 //
58 // In this test, a key listener for KEY_TYPED checks if a character typed has
59 // a correspondent keycode in an initially filled hashtable.
60 // If it does not, test fails. If character was produced by
61 // pressing a wrong key still listed in the hashtable, test cannot detect it.
62 // Under MS Windows, unlike X Window, some Ctrl+Ascii keystrokes don't
63 // produce a unicode character, so there will be no KEY_TYPED and no problem.
64 // Test doesn't try to verify Ctrl+deadkey behavior.
65 //
66 
67 public class CtrlASCII extends Applet implements KeyListener
68 {
69     // Declare things used in the test, like buttons and labels here
70     static Hashtable<Character, Integer> keycharHash = new Hashtable<Character, Integer>();
71     static boolean testFailed = false;
72     //Frame frame;
73     TextField tf;
74     Robot robot;
75 
fillHash( boolean isMSWindows )76     static void fillHash( boolean isMSWindows ) {
77         keycharHash.put(    (char)0x20         , KeyEvent.VK_SPACE        );                      /*32,x20*/ /*' ' */
78         keycharHash.put(    (char)0x21         , KeyEvent.VK_EXCLAMATION_MARK        );           /*33,x21*/ /*'!' fr*/
79         keycharHash.put(    (char)0x22         , KeyEvent.VK_QUOTEDBL        );                   /*34,x22*/ /*'"' fr*/
80         keycharHash.put(    (char)0x23         , KeyEvent.VK_NUMBER_SIGN        );                /*35,x23*/ /*'#' de*/
81         keycharHash.put(    (char)0x24         , KeyEvent.VK_DOLLAR        );                      /*36,x24*/ /*'$', de_CH*/
82         //keycharHash.put('%',                                  (char)0x25        );                                  /*37,x25*/ /*no VK, cannot test*/
83         keycharHash.put(    (char)0x26    , KeyEvent.VK_AMPERSAND        );                  /*38,x26*/ /*'&', fr*/
84         keycharHash.put(    (char)0x27    , KeyEvent.VK_QUOTE        );                      /*39,x27*/ /*''', fr*/
85         keycharHash.put(    (char)0x28    , KeyEvent.VK_LEFT_PARENTHESIS        );           /*40,x28*/ /*'(', fr*/
86         keycharHash.put(    (char)0x29    , KeyEvent.VK_RIGHT_PARENTHESIS        );           /*41,x29*/ /*')', fr*/
87         keycharHash.put(    (char)0x2a    , KeyEvent.VK_ASTERISK        );                    /*42,x2a*/ /*'*', fr*/
88         keycharHash.put(    (char)0x2b    , KeyEvent.VK_PLUS        );                        /*43,x2b*/ /*'+', de*/
89         keycharHash.put(    (char)0x2c    , KeyEvent.VK_COMMA        );                       /*44,x2c*/  /*','*/
90         keycharHash.put(    (char)0x2d    , KeyEvent.VK_MINUS        );                       /*45,x2d*/ /*'-'*/
91         keycharHash.put(    (char)0x2e    , KeyEvent.VK_PERIOD        );                      /*46,x2e*/ /*'.'*/
92         keycharHash.put(    (char)0x2f    , KeyEvent.VK_SLASH        );                       /*47,x2f*/ /*'/'*/
93         keycharHash.put(    (char)0x30    , KeyEvent.VK_0        );                           /*48,x30*/
94         keycharHash.put(    (char)0x31    , KeyEvent.VK_1        );                           /*49,x31*/
95         keycharHash.put(    (char)0x32    , KeyEvent.VK_2        );                           /*50,x32*/
96         keycharHash.put(    (char)0x33    , KeyEvent.VK_3        );                           /*51,x33*/
97         keycharHash.put(    (char)0x34    , KeyEvent.VK_4        );                           /*52,x34*/
98         keycharHash.put(    (char)0x35    , KeyEvent.VK_5        );                           /*53,x35*/
99         keycharHash.put(    (char)0x36    , KeyEvent.VK_6        );                           /*54,x36*/
100         keycharHash.put(    (char)0x37    , KeyEvent.VK_7        );                           /*55,x37*/
101         keycharHash.put(    (char)0x38    , KeyEvent.VK_8        );                           /*56,x38*/
102         keycharHash.put(    (char)0x39    , KeyEvent.VK_9        );                           /*57,x39*/
103         keycharHash.put(    (char)0x3a    , KeyEvent.VK_COLON        );                       /*58,x3a*/ /*':', fr*/
104         keycharHash.put(    (char)0x3b    , KeyEvent.VK_SEMICOLON        );                   /*59,x3b*/ /*';'*/
105         keycharHash.put(    (char)0x3c    , KeyEvent.VK_LESS        );                        /*60,x3c*/ /*'<' us 102*/
106         keycharHash.put(    (char)0x3d    , KeyEvent.VK_EQUALS        );                      /*61,x3d*/
107         keycharHash.put(    (char)0x3e    , KeyEvent.VK_GREATER        );                     /*62,x3e*/ /*'>' ?????? where???*/
108             // Javadoc says: "there is no keycode for the question mark because
109             // there is no keyboard for which it appears on the primary layer."
110             // Well, it's Lithuanian standard.
111         //keycharHash.put('?',                                 (char)0x3f        );                                   /*63,x3f*/ /*no VK, cannot test*/
112         keycharHash.put(    (char)0x40   , KeyEvent.VK_AT        );                          /*64,x40*/ /*'@' ?????? where???*/
113         keycharHash.put(    (char)0x1    , KeyEvent.VK_A        );                             /*65,x41*/
114         keycharHash.put(    (char)0x2    , KeyEvent.VK_B        );                            /*66,x42*/
115         keycharHash.put(    (char)0x3    , KeyEvent.VK_C        );                            /*67,x43*/
116         keycharHash.put(    (char)0x4    , KeyEvent.VK_D        );                            /*68,x44*/
117         keycharHash.put(    (char)0x5    , KeyEvent.VK_E        );                            /*69,x45*/
118         keycharHash.put(    (char)0x6    , KeyEvent.VK_F        );                            /*70,x46*/
119         keycharHash.put(    (char)0x7    , KeyEvent.VK_G        );                            /*71,x47*/
120         keycharHash.put(    (char)0x8    , KeyEvent.VK_H        );                            /*72,x48*/
121         keycharHash.put(    (char)0x9    , KeyEvent.VK_I        );                            /*73,x49*/
122         keycharHash.put(    (char)0xa    , KeyEvent.VK_J        );                            /*74,x4a*/
123         keycharHash.put(    (char)0xb    , KeyEvent.VK_K        );                            /*75,x4b*/
124         keycharHash.put(    (char)0xc    , KeyEvent.VK_L        );                            /*76,x4c*/
125         keycharHash.put(    (char)0xd    , KeyEvent.VK_M        );                            /*77,x4d*/
126         keycharHash.put(    (char)0xe    , KeyEvent.VK_N        );                            /*78,x4e*/
127         keycharHash.put(    (char)0xf    , KeyEvent.VK_O        );                            /*79,x4f*/
128         keycharHash.put(    (char)0x10   , KeyEvent.VK_P        );                           /*80,x50*/
129         keycharHash.put(    (char)0x11   , KeyEvent.VK_Q        );                           /*81,x51*/
130         keycharHash.put(    (char)0x12   , KeyEvent.VK_R        );                           /*82,x52*/
131         keycharHash.put(    (char)0x13   , KeyEvent.VK_S        );                           /*83,x53*/
132         keycharHash.put(    (char)0x14   , KeyEvent.VK_T        );                           /*84,x54*/
133         keycharHash.put(    (char)0x15   , KeyEvent.VK_U        );                           /*85,x55*/
134         keycharHash.put(    (char)0x16   , KeyEvent.VK_V        );                           /*86,x56*/
135         keycharHash.put(    (char)0x17   , KeyEvent.VK_W        );                           /*87,x57*/
136         keycharHash.put(    (char)0x18   , KeyEvent.VK_X        );                           /*88,x58*/
137         keycharHash.put(    (char)0x19   , KeyEvent.VK_Y        );                           /*89,x59*/
138         keycharHash.put(    (char)0x1a   , KeyEvent.VK_Z        );                           /*90,x5a*/
139 
140         keycharHash.put(    (char)0x1b   , KeyEvent.VK_OPEN_BRACKET        );             /*91,x5b*/ /*'['*/
141         keycharHash.put(    (char)0x1c   , KeyEvent.VK_BACK_SLASH        );               /*92,x5c*/ /*'\'*/
142         keycharHash.put(    (char)0x1d   , KeyEvent.VK_CLOSE_BRACKET        );            /*93,x5d*/ /*']'*/
143         keycharHash.put(    (char)0x5e   , KeyEvent.VK_CIRCUMFLEX        );               /*94,x5e*/  /*'^' ?? nodead fr, de??*/
144         keycharHash.put(    (char)0x1f   , KeyEvent.VK_UNDERSCORE        );               /*95,x5f*/  /*'_' fr*/
145         keycharHash.put(    (char)0x60   , KeyEvent.VK_BACK_QUOTE        );               /*96,x60*/
146         /********* Same as uppercase*/
147         //keycharHash.put(  (char)0x1         , KeyEvent.VK_a        );/*97,x61*/
148         //keycharHash.put(  (char)0x2         , KeyEvent.VK_b        );/*98,x62*/
149         //keycharHash.put(  (char)0x3         , KeyEvent.VK_c        );/*99,x63*/
150         //keycharHash.put(  (char)0x4         , KeyEvent.VK_d        );/*100,x64*/
151         //keycharHash.put(  (char)0x5         , KeyEvent.VK_e        );/*101,x65*/
152         //keycharHash.put(  (char)0x6         , KeyEvent.VK_f        );/*102,x66*/
153         //keycharHash.put(  (char)0x7         , KeyEvent.VK_g        );/*103,x67*/
154         //keycharHash.put(  (char)0x8         , KeyEvent.VK_h        );/*104,x68*/
155         //keycharHash.put(  (char)0x9         , KeyEvent.VK_i        );/*105,x69*/
156         //keycharHash.put(  (char)0xa         , KeyEvent.VK_j        );/*106,x6a*/
157         //keycharHash.put(  (char)0xb         , KeyEvent.VK_k        );/*107,x6b*/
158         //keycharHash.put(  (char)0xc         , KeyEvent.VK_l        );/*108,x6c*/
159         //keycharHash.put(  (char)0xd         , KeyEvent.VK_m        );/*109,x6d*/
160         //keycharHash.put(  (char)0xe         , KeyEvent.VK_n        );/*110,x6e*/
161         //keycharHash.put(  (char)0xf         , KeyEvent.VK_o        );/*111,x6f*/
162         //keycharHash.put(  (char)0x10        , KeyEvent.VK_p        );/*112,x70*/
163         //keycharHash.put(  (char)0x11        , KeyEvent.VK_q        );/*113,x71*/
164         //keycharHash.put(  (char)0x12        , KeyEvent.VK_r        );/*114,x72*/
165         //keycharHash.put(  (char)0x13        , KeyEvent.VK_s        );/*115,x73*/
166         //keycharHash.put(  (char)0x14        , KeyEvent.VK_t        );/*116,x74*/
167         //keycharHash.put(  (char)0x15        , KeyEvent.VK_u        );/*117,x75*/
168         //keycharHash.put(  (char)0x16        , KeyEvent.VK_v        );/*118,x76*/
169         //keycharHash.put(  (char)0x17        , KeyEvent.VK_w        );/*119,x77*/
170         //keycharHash.put(  (char)0x18        , KeyEvent.VK_x        );/*120,x78*/
171         //keycharHash.put(  (char)0x19        , KeyEvent.VK_y        );/*121,x79*/
172         //keycharHash.put(  (char)0x1a        , KeyEvent.VK_z        );/*122,x7a*/
173 
174         keycharHash.put(    (char)0x7b      , KeyEvent.VK_BRACELEFT        );             /*123,x7b*/ /*'{' la (Latin American)*/
175         //keycharHash.put(  (char)0x1c        , KeyEvent.VK_|        );                   /*124,x7c*/ /* no VK, cannot test*/
176         keycharHash.put(    (char)0x7d      , KeyEvent.VK_BRACERIGHT        );            /*125,x7d*/ /*'}' la */
177         //keycharHash.put(  (char)0x1e        , KeyEvent.VK_~        );                   /*126,x7e*/ /* no VK, cannot test*/
178 
179 
180     }
main(String[] args)181     public static void main(String[] args) {
182         CtrlASCII test = new CtrlASCII();
183         test.init();
184         test.start();
185     }
186 
init()187     public void init()
188     {
189         //Create instructions for the user here, as well as set up
190         // the environment -- set the layout manager, add buttons,
191         // etc.
192         // XXX test for MS Windows
193         fillHash( false );
194         this.setLayout (new BorderLayout ());
195 
196         String[] instructions =
197         {
198             "This is an AUTOMATIC test",
199             "simply wait until it is done"
200         };
201         Sysout.createDialog( );
202         Sysout.printInstructions( instructions );
203 
204     }//End  init()
205 
start()206     public void start ()
207     {
208         //Get things going.  Request focus, set size, et cetera
209 
210         setSize(400,300);
211         setVisible(true);
212 
213         //What would normally go into main() will probably go here.
214         //Use System.out.println for diagnostic messages that you want
215         //to read after the test is done.
216         //Use Sysout.println for messages you want the tester to read.
217 
218         String original = "0123456789";
219         tf = new TextField(original, 20);
220         this.add(tf);
221         tf.addKeyListener(this);
222         validate();
223 
224         try {
225             robot = new Robot();
226             robot.setAutoWaitForIdle(true);
227             robot.setAutoDelay(100);
228 
229             robot.waitForIdle();
230 
231             // wait for focus, etc.  (Hack.)
232             robot.delay(2000);
233             this.requestFocus();
234             tf.requestFocusInWindow();
235 
236             Point pt = getLocationOnScreen();
237             robot.mouseMove( pt.x+100, pt.y+100 );
238             robot.delay(2000);
239             robot.mousePress( InputEvent.BUTTON1_MASK );
240             robot.mouseRelease( InputEvent.BUTTON1_MASK );
241             Enumeration<Integer> enuElem = keycharHash.elements();
242 
243             int kc;
244             while( enuElem.hasMoreElements()) {
245                 kc = enuElem.nextElement();
246                 punchCtrlKey( robot, kc );
247             }
248             robot.delay(500);
249         } catch (Exception e) {
250             throw new RuntimeException("The test was not completed.\n\n" + e);
251         }
252         if( testFailed ) {
253             throw new RuntimeException("The test failed.\n\n");
254         }
255         Sysout.println("Success\n");
256 
257     }// start()
punchCtrlKey( Robot ro, int keyCode )258     public void punchCtrlKey( Robot ro, int keyCode ) {
259         ro.keyPress(KeyEvent.VK_CONTROL);
260         ro.keyPress(keyCode);
261         ro.keyRelease(keyCode);
262         ro.keyRelease(KeyEvent.VK_CONTROL);
263         ro.delay(200);
264     }
keyPressed(KeyEvent evt)265     public void keyPressed(KeyEvent evt)
266     {
267         //printKey(evt);
268     }
269 
keyTyped(KeyEvent evt)270     public void keyTyped(KeyEvent evt)
271     {
272         printKey(evt);
273         char keych = evt.getKeyChar();
274         if( !keycharHash.containsKey( keych ) ) {
275             System.out.println("Unexpected keychar: "+keych);
276             Sysout.println("Unexpected keychar: "+keych);
277             testFailed = true;
278         }
279     }
280 
keyReleased(KeyEvent evt)281     public void keyReleased(KeyEvent evt)
282     {
283         //printKey(evt);
284     }
285 
printKey(KeyEvent evt)286     protected void printKey(KeyEvent evt)
287     {
288         switch(evt.getID())
289         {
290           case KeyEvent.KEY_TYPED:
291           case KeyEvent.KEY_PRESSED:
292           case KeyEvent.KEY_RELEASED:
293             break;
294           default:
295             System.out.println("Other Event ");
296             Sysout.println("Other Event ");
297             return;
298         }
299         System.out.print(" 0x"+ Integer.toHexString(evt.getKeyChar()));
300         Sysout.println    (" 0x"+ Integer.toHexString(evt.getKeyChar()));
301     }
302 
303 }// class CtrlASCII
304 
305 
306 /****************************************************
307  Standard Test Machinery
308  DO NOT modify anything below -- it's a standard
309   chunk of code whose purpose is to make user
310   interaction uniform, and thereby make it simpler
311   to read and understand someone else's test.
312  ****************************************************/
313 
314 /**
315  This is part of the standard test machinery.
316  It creates a dialog (with the instructions), and is the interface
317   for sending text messages to the user.
318  To print the instructions, send an array of strings to Sysout.createDialog
319   WithInstructions method.  Put one line of instructions per array entry.
320  To display a message for the tester to see, simply call Sysout.println
321   with the string to be displayed.
322  This mimics System.out.println but works within the test harness as well
323   as standalone.
324  */
325 
326 class Sysout
327  {
328    private static TestDialog dialog;
329 
createDialogWithInstructions( String[] instructions )330    public static void createDialogWithInstructions( String[] instructions )
331     {
332       dialog = new TestDialog( new Frame(), "Instructions" );
333       dialog.printInstructions( instructions );
334       dialog.show();
335       println( "Any messages for the tester will display here." );
336     }
337 
createDialog( )338    public static void createDialog( )
339     {
340       dialog = new TestDialog( new Frame(), "Instructions" );
341       String[] defInstr = { "Instructions will appear here. ", "" } ;
342       dialog.printInstructions( defInstr );
343       dialog.show();
344       println( "Any messages for the tester will display here." );
345     }
346 
347 
printInstructions( String[] instructions )348    public static void printInstructions( String[] instructions )
349     {
350       dialog.printInstructions( instructions );
351     }
352 
353 
println( String messageIn )354    public static void println( String messageIn )
355     {
356       dialog.displayMessage( messageIn );
357     }
358 
359  }// Sysout  class
360 
361 /**
362   This is part of the standard test machinery.  It provides a place for the
363    test instructions to be displayed, and a place for interactive messages
364    to the user to be displayed.
365   To have the test instructions displayed, see Sysout.
366   To have a message to the user be displayed, see Sysout.
367   Do not call anything in this dialog directly.
368   */
369 class TestDialog extends Dialog
370  {
371 
372    TextArea instructionsText;
373    TextArea messageText;
374    int maxStringLength = 80;
375 
376    //DO NOT call this directly, go through Sysout
TestDialog( Frame frame, String name )377    public TestDialog( Frame frame, String name )
378     {
379       super( frame, name );
380       int scrollBoth = TextArea.SCROLLBARS_BOTH;
381       instructionsText = new TextArea( "", 15, maxStringLength, scrollBoth );
382       add( "North", instructionsText );
383 
384       messageText = new TextArea( "", 5, maxStringLength, scrollBoth );
385       add("South", messageText);
386 
387       pack();
388 
389       show();
390     }// TestDialog()
391 
392    //DO NOT call this directly, go through Sysout
printInstructions( String[] instructions )393    public void printInstructions( String[] instructions )
394     {
395       //Clear out any current instructions
396       instructionsText.setText( "" );
397 
398       //Go down array of instruction strings
399 
400       String printStr, remainingStr;
401       for( int i=0; i < instructions.length; i++ )
402        {
403          //chop up each into pieces maxSringLength long
404          remainingStr = instructions[ i ];
405          while( remainingStr.length() > 0 )
406           {
407             //if longer than max then chop off first max chars to print
408             if( remainingStr.length() >= maxStringLength )
409              {
410                //Try to chop on a word boundary
411                int posOfSpace = remainingStr.
412                   lastIndexOf( ' ', maxStringLength - 1 );
413 
414                if( posOfSpace <= 0 ) posOfSpace = maxStringLength - 1;
415 
416                printStr = remainingStr.substring( 0, posOfSpace + 1 );
417                remainingStr = remainingStr.substring( posOfSpace + 1 );
418              }
419             //else just print
420             else
421              {
422                printStr = remainingStr;
423                remainingStr = "";
424              }
425 
426             instructionsText.append( printStr + "\n" );
427 
428           }// while
429 
430        }// for
431 
432     }//printInstructions()
433 
434    //DO NOT call this directly, go through Sysout
displayMessage( String messageIn )435    public void displayMessage( String messageIn )
436     {
437       messageText.append( messageIn + "\n" );
438     }
439 
440  }// TestDialog  class
441