1 /*
   2  * Copyright (c) 2007, 2017, 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. Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle in the LICENSE file that accompanied this code.
  10  *
  11  * This code is distributed in the hope that it will be useful, but WITHOUT
  12  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  13  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  14  * version 2 for more details (a copy is included in the LICENSE file that
  15  * accompanied this code).
  16  *
  17  * You should have received a copy of the GNU General Public License version
  18  * 2 along with this work; if not, write to the Free Software Foundation,
  19  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  20  *
  21  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any
  23  * questions.
  24  */
  25 package org.jemmy.input.awt;
  26 
  27 
  28 import java.awt.AWTException;
  29 import java.awt.BorderLayout;
  30 import java.awt.Button;
  31 import java.awt.EventQueue;
  32 import java.awt.Frame;
  33 import java.awt.Robot;
  34 import java.awt.event.InputEvent;
  35 import java.awt.event.KeyAdapter;
  36 import java.awt.event.KeyEvent;
  37 import java.awt.event.MouseAdapter;
  38 import java.awt.event.MouseEvent;
  39 import java.io.File;
  40 import java.lang.reflect.InvocationTargetException;
  41 import java.util.HashMap;
  42 import java.util.HashSet;
  43 import java.util.Queue;
  44 import java.util.Random;
  45 import java.util.concurrent.ConcurrentLinkedQueue;
  46 import org.jemmy.Point;
  47 import org.jemmy.control.Wrap;
  48 import org.jemmy.env.Environment;
  49 import org.jemmy.env.Timeout;
  50 import org.jemmy.image.awt.AWTImage;
  51 import org.jemmy.input.awt.AWTMap;
  52 import org.jemmy.input.awt.RobotDriver;
  53 import org.jemmy.input.awt.RobotExecutor;
  54 import org.jemmy.interfaces.Keyboard.KeyboardButton;
  55 import org.jemmy.interfaces.Modifier;
  56 import org.jemmy.interfaces.Mouse.MouseButton;
  57 import org.jemmy.interfaces.Mouse.MouseButtons;
  58 import org.jemmy.timing.State;
  59 import org.jemmy.timing.Waiter;
  60 import org.testng.annotations.AfterClass;
  61 import org.testng.annotations.AfterMethod;
  62 import org.testng.annotations.BeforeClass;
  63 import org.testng.annotations.BeforeMethod;
  64 import org.testng.annotations.Test;
  65 
  66 
  67 /**
  68  *
  69  * @author Alexander Kouznetsov <mrkam@mail.ru>
  70  */
  71 public class RobotDriver2Test {
  72 
  73     final static Timeout TIMEOUT = new Timeout("Wait for state to be reached", 10000);
  74     final static Timeout DELTA_TIMEOUT = new Timeout("Delta timeout of wait for state to be reached", 1000);
  75 
  76     public RobotDriver2Test() {
  77     }
  78 
  79     @BeforeClass
  80     public static void setUpClass() throws Exception {
  81         File workdir = new File(System.getProperty("user.dir") + File.separator +
  82                 "build" + File.separator +
  83                 "test" + File.separator +
  84                 "results");
  85         workdir.mkdirs();
  86         AWTImage.setImageRoot(workdir);
  87     }
  88 
  89     @AfterClass
  90     public static void tearDownClass() throws Exception {
  91         RobotDriver.exit();
  92     }
  93 
  94     Frame frm;
  95     Button btn;
  96     Wrap<Object> area;
  97     RobotDriver instance;
  98     Robot rb;
  99     Queue<InputEvent> queue = new ConcurrentLinkedQueue<InputEvent>();
 100     static Random r = new Random();
 101 
 102     @BeforeMethod
 103     public void setUp() throws InterruptedException, AWTException, InvocationTargetException {
 104         EventQueue.invokeAndWait(new Runnable() {
 105 
 106             public void run() {
 107                 frm = new Frame("some frame");
 108                 frm.setSize(100, 100);
 109                 frm.setLocation(100, 100);
 110                 btn = new Button("some button");
 111                 MouseAdapter m = new MouseAdapter() {
 112 
 113                     @Override
 114                     public void mousePressed(MouseEvent e) {
 115                         System.out.println("mousePressed event triggered: " + e);
 116                         System.out.flush();
 117                         queue.add(e);
 118                     }
 119 
 120                     @Override
 121                     public void mouseReleased(MouseEvent e) {
 122                         System.out.println("mouseReleased event triggered: " + e);
 123                         System.out.flush();
 124                         queue.add(e);
 125                     }
 126 
 127                     @Override
 128                     public void mouseMoved(MouseEvent e) {
 129                         System.out.println("mouseMoved event triggered: " + e);
 130                         System.out.flush();
 131                         queue.add(e);
 132                     }
 133 
 134                     @Override
 135                     public void mouseClicked(MouseEvent e) {
 136                         System.out.println("mouseClicked event triggered: " + e);
 137                         System.out.flush();
 138                         queue.add(e);
 139                     }
 140 
 141                     @Override
 142                     public void mouseDragged(MouseEvent e) {
 143                         System.out.println("mouseDragged event triggered: " + e);
 144                         System.out.flush();
 145                         queue.add(e);
 146                     }
 147 
 148                 };
 149                 btn.addMouseListener(m);
 150                 btn.addMouseMotionListener(m);
 151                 btn.addKeyListener(new KeyAdapter() {
 152 
 153                     @Override
 154                     public void keyPressed(KeyEvent e) {
 155                         System.out.println("keyPressed event triggered: " + e);
 156                         System.out.flush();
 157                         queue.add(e);
 158                     }
 159 
 160                     @Override
 161                     public void keyReleased(KeyEvent e) {
 162                         System.out.println("keyReleased event triggered: " + e);
 163                         System.out.flush();
 164                         queue.add(e);
 165                     }
 166 
 167                 });
 168                 frm.add(btn, BorderLayout.SOUTH);
 169                 frm.doLayout();
 170                 instance = new RobotDriver(Environment.getEnvironment());
 171                 frm.setVisible(true);
 172                 btn.requestFocusInWindow();
 173             }
 174         });
 175 
 176         rb = new Robot();
 177         rb.waitForIdle();
 178 
 179         RobotExecutor.get().setRunInOtherJVM(true);
 180 
 181     }
 182 
 183     @AfterMethod
 184     public void tearDown() throws InterruptedException, InvocationTargetException {
 185         EventQueue.invokeAndWait(new Runnable() {
 186 
 187             public void run() {
 188                 frm.setVisible(false);
 189             }
 190         });
 191     }
 192 
 193 //    /**
 194 //     * Test of createScreenCapture method, of class RobotDriver.
 195 //     */
 196 //    @Test
 197 //    public void testCreateScreenCaptureLocally() throws AWTException, InterruptedException {
 198 //        System.out.println("testCreateScreenCaptureLocally");
 199 //        Thread.sleep(3000);
 200 //        Rectangle screenRect = new Rectangle(100, 100, 100, 100);
 201 //        RobotExecutor.get().setRunInOtherJVM(false);
 202 //        Image expResult = new AWTImage(new Robot().createScreenCapture(new java.awt.Rectangle(100, 100, 100, 100)));
 203 //        Image result = RobotDriver.createScreenCapture(screenRect);
 204 //        Image diff = expResult.compareTo(result);
 205 //        if (diff != null) {
 206 //            diff.save("testCreateScreenCaptureLocally.png");
 207 //            fail();
 208 //        }
 209 //    }
 210 //
 211 //    /**
 212 //     * Test of createScreenCapture method, of class RobotDriver.
 213 //     */
 214 //    @Test
 215 //    public void testCreateScreenCaptureRemotely() throws AWTException, InterruptedException {
 216 //        System.out.println("testCreateScreenCaptureRemotely");
 217 //        Thread.sleep(3000);
 218 //        Rectangle screenRect = new Rectangle(100, 100, 100, 100);
 219 //        RobotExecutor.get().setRunInOtherJVM(true);
 220 //        Image expResult = new AWTImage(new Robot().createScreenCapture(new java.awt.Rectangle(100, 100, 100, 100)));
 221 //        Image result = RobotDriver.createScreenCapture(screenRect);
 222 //        RobotDriver.createScreenCapture(screenRect);
 223 //        Image diff = expResult.compareTo(result);
 224 //        if (diff != null) {
 225 //            diff.save("testCreateScreenCaptureRemotely.png");
 226 //            fail();
 227 //        }
 228 //    }
 229 //
 230 //    /**
 231 //     * Test of createScreenCapture method, of class RobotDriver.
 232 //     */
 233 //    @Test
 234 //    public void testCreateScreenCaptureRemotely2() throws AWTException, InterruptedException {
 235 //        System.out.println("testCreateScreenCaptureRemotely2");
 236 //        Thread.sleep(3000);
 237 //        Rectangle screenRect = new Rectangle(100, 100, 100, 100);
 238 //        RobotExecutor.get().setRunInOtherJVM(true);
 239 //        Image expResult = new AWTImage(new Robot().createScreenCapture(new java.awt.Rectangle(100, 100, 100, 100)));
 240 //        Image result = RobotDriver.createScreenCapture(screenRect);
 241 //        Image diff = expResult.compareTo(result);
 242 //        if (diff != null) {
 243 //            diff.save("testCreateScreenCaptureRemotely2.png");
 244 //            fail();
 245 //        }
 246 //    }
 247 
 248     /**
 249      * Test of all RobotDriver methods invoked multiple times
 250      * @throws InterruptedException
 251      */
 252 //    @Test
 253     public void testAll() throws InterruptedException {
 254         for(int i = 0; i < 10; i++) {
 255             testPressMouse();
 256         }
 257     }
 258 
 259     public void test() throws InterruptedException {
 260 //        testPressMouse();
 261         testPressKey();
 262     }
 263 
 264     @Test
 265     public void test0() throws InterruptedException {
 266         test();
 267     }
 268 
 269     @Test
 270     public void test1() throws InterruptedException {
 271         test();
 272     }
 273 
 274     @Test
 275     public void test2() throws InterruptedException {
 276         test();
 277     }
 278 
 279     @Test
 280     public void test3() throws InterruptedException {
 281         test();
 282     }
 283 
 284     @Test
 285     public void test4() throws InterruptedException {
 286         test();
 287     }
 288 
 289     @Test
 290     public void test5() throws InterruptedException {
 291         test();
 292     }
 293 
 294     @Test
 295     public void test6() throws InterruptedException {
 296         test();
 297     }
 298 
 299     @Test
 300     public void test7() throws InterruptedException {
 301         test();
 302     }
 303 
 304     @Test
 305     public void test8() throws InterruptedException {
 306         test();
 307     }
 308 
 309     @Test
 310     public void test9() throws InterruptedException {
 311         test();
 312     }
 313 
 314     protected static final int[] MODIFIERS = new int[] {
 315             InputEvent.SHIFT_DOWN_MASK,
 316             InputEvent.CTRL_DOWN_MASK,
 317             InputEvent.ALT_DOWN_MASK,
 318             InputEvent.SHIFT_MASK,
 319             InputEvent.CTRL_MASK,
 320             InputEvent.ALT_MASK,
 321 //            MouseEvent.ALT_GRAPH_DOWN_MASK,
 322 //            MouseEvent.META_DOWN_MASK
 323         };
 324 
 325     public static int getModifiers() {
 326         int modifiersMask = r.nextInt(1 << MODIFIERS.length/2);
 327         int m = 0;
 328         System.out.print("Modifiers:");
 329         for (int i = 0; i < MODIFIERS.length/2; i++) {
 330             if ((modifiersMask & (1 << i)) != 0 ) {
 331                 m |= MODIFIERS[i];
 332                 System.out.print(" " + i);
 333             }
 334         }
 335         System.out.println("");
 336         return m;
 337     }
 338 
 339     protected static HashMap<Integer, Integer> normalizeMap =  new HashMap<Integer, Integer>();
 340     static {
 341         normalizeMap.put(InputEvent.SHIFT_MASK,InputEvent.SHIFT_DOWN_MASK);
 342         normalizeMap.put(InputEvent.CTRL_MASK,InputEvent.CTRL_DOWN_MASK);
 343         normalizeMap.put(InputEvent.ALT_MASK,InputEvent.ALT_DOWN_MASK);
 344         normalizeMap.put(InputEvent.META_MASK,InputEvent.META_DOWN_MASK);
 345     }
 346 
 347     protected static HashSet<Integer> normalize(HashSet<Integer> modifiers) {
 348         HashSet<Integer> normalized = new HashSet<Integer>();
 349         for (Integer mod : modifiers) {
 350             Integer n = normalizeMap.get(mod);
 351             if (n != null) {
 352                 normalized.add(n);
 353             } else {
 354                 normalized.add(mod);
 355             }
 356         }
 357         return normalized;
 358     }
 359 
 360     protected static HashSet<Integer> modifiers2Set(int mods) {
 361         HashSet<Integer> set = new HashSet<Integer>();
 362         for (int i = 0; i < MODIFIERS.length; i++) {
 363             if ((mods & MODIFIERS[i]) > 0) {
 364                 set.add(MODIFIERS[i]);
 365             }
 366         }
 367         return set;
 368    }
 369 
 370     protected static boolean compareModifiers(int m1, int m2) {
 371         return normalize(modifiers2Set(m1)).equals(normalize(modifiers2Set(m2)));
 372     }
 373     /**
 374      * Test of pressMouse method, of class RobotDriver.
 375      */
 376     public void testPressMouse() throws InterruptedException {
 377         System.out.println("pressMouse");
 378         Thread.sleep(3000);
 379         final int[] MOUSE_BUTTONS_1 = new int[] {
 380             MouseEvent.BUTTON1_MASK,
 381             MouseEvent.BUTTON2_MASK,
 382             MouseEvent.BUTTON3_MASK
 383         };
 384         final int[] MOUSE_BUTTONS_2 = new int[] {
 385             MouseEvent.BUTTON1,
 386             MouseEvent.BUTTON2,
 387             MouseEvent.BUTTON3
 388         };
 389         int bIndex = r.nextInt(MOUSE_BUTTONS_1.length);
 390         final int mouseButton1 = MOUSE_BUTTONS_1[bIndex];
 391         final int mouseButton2 = MOUSE_BUTTONS_2[bIndex];
 392         System.out.print("Button: " + bIndex + " Modifier:");
 393         final int modifiers = getModifiers();
 394         queue.clear();
 395         java.awt.Point locationOnScreen = btn.getLocationOnScreen();
 396         System.out.println("Pressing mouse");
 397         instance.moveMouse(new Point(locationOnScreen.x + btn.getWidth() / 2, locationOnScreen.y + btn.getHeight() / 2));
 398         AWTMap map = new AWTMap();
 399         MouseButton button = map.convertMouseButton(mouseButton1);
 400         Modifier[] converted_modifiers = map.convertModifiers(modifiers);
 401         instance.pressMouse(button, converted_modifiers);
 402         instance.releaseMouse(button, converted_modifiers);
 403 
 404         rb.waitForIdle();
 405         new Waiter(TIMEOUT, DELTA_TIMEOUT).ensureState(new State<Boolean>(){
 406 
 407             public Boolean reached() {
 408                 while(true) {
 409                     InputEvent e = queue.poll();
 410                     if (e != null) {
 411                         if (e instanceof MouseEvent) {
 412                             MouseEvent me = (MouseEvent) e;
 413                             if (me.getID() == MouseEvent.MOUSE_PRESSED && me.getButton() == mouseButton2 && (compareModifiers(me.getModifiers(), modifiers))) {
 414                                 return true;
 415                             }
 416                             if (me.getID() == MouseEvent.MOUSE_PRESSED) {
 417                                 System.out.println("Wrong combination of button and modifiers triggered:");
 418                                 System.out.println("me.getModifiers() = " + Integer.toString(me.getModifiers(), 2)  + ", modifiers = " + Integer.toString(modifiers, 2));
 419                                 System.out.println("expected: " + new MouseEvent(
 420                                         me.getComponent(), MouseEvent.MOUSE_PRESSED,
 421                                         me.getWhen(), modifiers, me.getX(), me.getY(), me.getClickCount(), me.isPopupTrigger(), mouseButton2));
 422                                 System.out.println("     got: " + me);
 423                             }
 424                         }
 425                     } else {
 426                         break;
 427                     }
 428                 }
 429                 return null;
 430             }
 431 
 432         });
 433 
 434         System.out.println("PASSED");
 435 
 436     }
 437 
 438 //    /**
 439 //     * Test of releaseMouse method, of class RobotDriver.
 440 //     */
 441 //    @Test
 442 //    public void testReleaseMouse() throws InterruptedException {
 443 //        System.out.println("releaseMouse");
 444 //        Thread.sleep(3000);
 445 //        int mouseButton = MouseEvent.BUTTON2_MASK;
 446 //        int modifiers = MouseEvent.CTRL_DOWN_MASK;
 447 //        mouseReleased = false;
 448 //        java.awt.Point locationOnScreen = btn.getLocationOnScreen();
 449 //        instance.moveMouse(new Point(locationOnScreen.x + btn.getWidth() / 2, locationOnScreen.y + btn.getHeight() / 2));
 450 //        System.out.println("Pressing mouse");
 451 //        instance.pressMouse(mouseButton, modifiers);
 452 //        System.out.println("Releasing mouse");
 453 //        instance.releaseMouse(mouseButton, modifiers);
 454 //
 455 //        rb.waitForIdle();
 456 //        new Waiter(TIMEOUT, DELTA_TIMEOUT).ensureState(new State<Boolean>(){
 457 //
 458 //            public Boolean reached() {
 459 //                return mouseReleased ? true: null;
 460 //            }
 461 //
 462 //        });
 463 //        assertTrue(mouseReleased);
 464 //    }
 465 //
 466 //    /**
 467 //     * Test of moveMouse method, of class RobotDriver.
 468 //     */
 469 //    @Test
 470 //    public void testMoveMouse() throws InterruptedException {
 471 //        System.out.println("moveMouse");
 472 //        Thread.sleep(3000);
 473 //        mouseMoved = false;
 474 //        java.awt.Point locationOnScreen = btn.getLocationOnScreen();
 475 //        System.out.println("Moving mouse");
 476 //        Point startPoint = new Point(locationOnScreen.x, locationOnScreen.y);
 477 //        Point endPoint = new Point(locationOnScreen.x + btn.getWidth(), locationOnScreen.y + btn.getHeight());
 478 //        double steps = 5; //Math.max(btn.getWidth(), btn.getHeight());
 479 //        double dx = (endPoint.x - startPoint.x) / steps;
 480 //        double dy = (endPoint.y - startPoint.y) / steps;
 481 //        for(int i = 0; i < steps; i++) {
 482 //            Point point = new Point(startPoint.x + dx * i, startPoint.y + dy * i);
 483 //            instance.moveMouse(point);
 484 //            Thread.sleep(100);
 485 //        }
 486 //
 487 //        rb.waitForIdle();
 488 //        new Waiter(TIMEOUT, DELTA_TIMEOUT).ensureState(new State<Boolean>(){
 489 //
 490 //            public Boolean reached() {
 491 //                return mouseMoved ? true: null;
 492 //            }
 493 //
 494 //        });
 495 //        assertTrue(mouseMoved);
 496 //    }
 497 //
 498 //    /**
 499 //     * Test of clickMouse method, of class RobotDriver.
 500 //     */
 501 //    @Test
 502 //    public void testClickMouse() throws InterruptedException {
 503 //        System.out.println("clickMouse");
 504 //        Thread.sleep(3000);
 505 //        mouseClicked = false;
 506 //        java.awt.Point locationOnScreen = btn.getLocationOnScreen();
 507 //        Point point = new Point(locationOnScreen.x + btn.getWidth() / 2, locationOnScreen.y + btn.getHeight() / 2);
 508 //        int clickCount = 1;
 509 //        int mouseButton = MouseEvent.BUTTON3_MASK;
 510 //        int modifiers = InputEvent.ALT_DOWN_MASK;
 511 //        Timeout mouseClick = new Timeout("mouseClick", 100);
 512 //        System.out.println("Clicking mouse");
 513 //        instance.clickMouse(point, clickCount, mouseButton, modifiers, mouseClick);
 514 //
 515 //        rb.waitForIdle();
 516 //        new Waiter(TIMEOUT, DELTA_TIMEOUT).ensureState(new State<Boolean>(){
 517 //
 518 //            public Boolean reached() {
 519 //                return mouseClicked ? true: null;
 520 //            }
 521 //
 522 //        });
 523 //        assertTrue(mouseClicked);
 524 //    }
 525 //
 526 //    /**
 527 //     * Test of dragNDrop method, of class RobotDriver.
 528 //     */
 529 //    @Test
 530 //    public void testDragNDrop() throws InterruptedException {
 531 //        System.out.println("dragNDrop");
 532 //        java.awt.Point locationOnScreen = btn.getLocationOnScreen();
 533 //        Point startPoint = new Point(locationOnScreen.x + btn.getWidth() / 2, locationOnScreen.y + btn.getHeight() / 2);
 534 //        Point endPoint = new Point(frm.getLocationOnScreen().x + frm.getWidth() / 2, frm.getLocationOnScreen().y + frm.getHeight() / 2);
 535 //        int mouseButton = MouseEvent.BUTTON2_MASK;
 536 //        int modifiers = 0;
 537 //        Timeout before = new Timeout("before", 500);
 538 //        Timeout after = new Timeout("after", 500);
 539 //        mouseDragged = false;
 540 //        instance.dragNDrop(startPoint, endPoint, mouseButton, modifiers, before, after);
 541 //
 542 //        rb.waitForIdle();
 543 //        new Waiter(TIMEOUT, DELTA_TIMEOUT).ensureState(new State<Boolean>(){
 544 //
 545 //            public Boolean reached() {
 546 //                return mouseDragged ? true: null;
 547 //            }
 548 //
 549 //        });
 550 //        assertTrue(mouseDragged);
 551 //    }
 552 
 553     /**
 554      * Test of pressKey method, of class RobotDriver.
 555      */
 556     public void testPressKey() throws InterruptedException {
 557         System.out.println("pressKey");
 558         Thread.sleep(3000);
 559 
 560         final int keyCode = KeyEvent.VK_A;
 561         final int modifiers = getModifiers();
 562         AWTMap map = new AWTMap();
 563         KeyboardButton button = map.convertKeyboardButton(keyCode);
 564         Modifier[] converted_modifiers = map.convertModifiers(modifiers);
 565 
 566         queue.clear();
 567 
 568         java.awt.Point locationOnScreen = btn.getLocationOnScreen();
 569         instance.clickMouse(new Point(locationOnScreen.x + btn.getWidth() / 2, locationOnScreen.y + btn.getHeight() / 2), 1,
 570                 MouseButtons.BUTTON1, DELTA_TIMEOUT);
 571 
 572         rb.waitForIdle();
 573 
 574         instance.pressKey(button, converted_modifiers);
 575         instance.releaseKey(button, converted_modifiers);
 576 
 577         rb.waitForIdle();
 578         new Waiter(TIMEOUT, DELTA_TIMEOUT).ensureState(new State<Boolean>(){
 579 
 580             public Boolean reached() {
 581                 while(true) {
 582                     InputEvent e = queue.poll();
 583                     if (e != null) {
 584                         if (e instanceof KeyEvent) {
 585                             KeyEvent ke = (KeyEvent) e;
 586                             if (ke.getID() == KeyEvent.KEY_PRESSED && ke.getKeyCode() == keyCode && compareModifiers(ke.getModifiers(), modifiers)) {
 587                                 return true;
 588                             }
 589                             if (ke.getID() == KeyEvent.KEY_PRESSED) {
 590                                 System.out.println("Wrong combination of button and modifiers triggered:");
 591                                 System.out.println("ke.getModifiers() = " + Integer.toString(ke.getModifiers(), 2)  + ", modifiers = " + Integer.toString(modifiers, 2));
 592                                 System.out.println("expected: " + new KeyEvent(ke.getComponent(), KeyEvent.KEY_PRESSED, ke.getWhen(), modifiers, keyCode, KeyEvent.CHAR_UNDEFINED));
 593                                 System.out.println("     got: " + ke);
 594                             }
 595                         }
 596                     } else {
 597                         break;
 598                     }
 599                 }
 600                 return null;
 601             }
 602 
 603         });
 604 
 605         System.out.println("PASSED");
 606     }
 607 
 608 //    /**
 609 //     * Test of releaseKey method, of class RobotDriver.
 610 //     */
 611 //    @Test
 612 //    public void testReleaseKey() throws InterruptedException {
 613 //        System.out.println("releaseKey");
 614 //        int keyCode = KeyEvent.VK_B;
 615 //        int modifiers = 0;
 616 //        keyReleased = false;
 617 //        instance.pressKey(keyCode, modifiers);
 618 //        instance.releaseKey(keyCode, modifiers);
 619 //
 620 //        rb.waitForIdle();
 621 //        new Waiter(TIMEOUT, DELTA_TIMEOUT).ensureState(new State<Boolean>(){
 622 //
 623 //            public Boolean reached() {
 624 //                return keyReleased ? true: null;
 625 //            }
 626 //
 627 //        });
 628 //        assertTrue(keyReleased);
 629 //    }
 630 
 631 }