1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 23 24 package complex.toolkit.accessibility; 25 26 import com.sun.star.awt.Point; 27 import com.sun.star.awt.Rectangle; 28 import com.sun.star.awt.Size; 29 import com.sun.star.uno.UnoRuntime; 30 import com.sun.star.accessibility.XAccessible; 31 import com.sun.star.accessibility.XAccessibleComponent; 32 import com.sun.star.accessibility.XAccessibleContext; 33 import com.sun.star.uno.XInterface; 34 import java.util.Vector; 35 36 /** 37 * Testing <code>com.sun.star.accessibility.XAccessibleComponent</code> 38 * interface methods : 39 * <ul> 40 * <li><code> containsPoint()</code></li> 41 * <li><code> getAccessibleAtPoint()</code></li> 42 * <li><code> getBounds()</code></li> 43 * <li><code> getLocation()</code></li> 44 * <li><code> getLocationOnScreen()</code></li> 45 * <li><code> getSize()</code></li> 46 * <li><code> grabFocus()</code></li> 47 * <li><code> getAccessibleKeyBinding()</code></li> 48 * </ul> <p> 49 * 50 * @see com.sun.star.accessibility.XAccessibleComponent 51 */ 52 public class _XAccessibleComponent { 53 54 // private LogWriter log; 55 56 public XAccessibleComponent oObj = null; 57 58 private Rectangle bounds = null ; 59 60 private static final String className = 61 "com.sun.star.accessibility.XAccessibleComponent"; 62 63 /** 64 * Constructor 65 * @param object 66 */ _XAccessibleComponent(XInterface object )67 public _XAccessibleComponent(XInterface object/*, LogWriter log*/) { 68 oObj = UnoRuntime.queryInterface( 69 XAccessibleComponent.class, object); 70 // this.log = log; 71 } 72 73 /** 74 * First checks 4 inner bounds (upper, lower, left and right) 75 * of component bounding box to contain 76 * at least one point of the component. Second 4 outer bounds 77 * are checked to not contain any component points.<p> 78 * 79 * Has <b> OK </b> status if inner bounds contain component points 80 * and outer bounds don't contain any component points. <p> 81 * 82 * The following method tests are to be completed successfully before : 83 * <ul> 84 * <li> <code> getBounds() </code> : to have size of a component.</li> 85 * </ul> 86 * @return 87 */ _containsPoint()88 public boolean _containsPoint() { 89 90 boolean result = true ; 91 92 int curX = 0; 93 //while (!oObj.containsPoint(new Point(curX, bounds.Y)) && curX < bounds.Width+bounds.X) { 94 while (!oObj.containsPoint(new Point(curX, 0)) && curX < bounds.Width) { 95 curX++; 96 } 97 //if ((bounds.X <= curX) && (curX < bounds.Width+bounds.X)) { 98 if (curX < bounds.Width) { 99 System.out.println("Upper bound of box contains point (" 100 + curX + ",0) - OK"); 101 } else { 102 System.out.println 103 ("Upper bound of box contains no component points - FAILED"); 104 result = false; 105 } 106 107 curX = 0; 108 //while (!oObj.containsPoint(new Point(curX, bounds.Y+bounds.Height - 1)) 109 while (!oObj.containsPoint(new Point(curX, bounds.Height - 1)) 110 && curX < bounds.Width) { 111 112 System.out.println("Contains returns false for ("+curX+","+bounds.Height+")"); 113 curX++; 114 } 115 //if ((bounds.X <= curX) && (curX < bounds.Width+bounds.X)) { 116 if (curX < bounds.Width) { 117 System.out.println("Lower bound of box contains point (" 118 + curX + "," + (bounds.Height - 1) + ") - OK"); 119 } else { 120 System.out.println 121 ("Lower bound of box contains no component points - FAILED"); 122 result = false; 123 } 124 125 int curY = 0; 126 //while (!oObj.containsPoint(new Point(bounds.X, curY)) && curY < bounds.Height+bounds.Y) { 127 while (!oObj.containsPoint(new Point(0, curY)) && curY < bounds.Height) { 128 curY++; 129 } 130 //if ((bounds.Y <= curY) && (curY < bounds.Height+bounds.Y)) { 131 if (curY < bounds.Height) { 132 System.out.println("Left bound of box contains point (0," 133 + curY + ") - OK"); 134 } else { 135 System.out.println 136 ("Left bound of box contains no component points - FAILED"); 137 result = false; 138 } 139 140 curY = 0; 141 //while (!oObj.containsPoint(new Point(bounds.X+bounds.Width - 1, curY)) 142 // && curY < bounds.Height+bounds.Y) { 143 while (!oObj.containsPoint(new Point(bounds.Width - 1, curY)) && curY < bounds.Height) { 144 curY++; 145 } 146 //if ((bounds.Y <= curY) && (curY < bounds.Height + bounds.Y)) { 147 if (curY < bounds.Height) { 148 System.out.println("Right bound of box contains point (" 149 + (bounds.Width - 1) + "," + curY + ") - OK"); 150 } else { 151 System.out.println 152 ("Right bound of box contains no component points - FAILED"); 153 result = false; 154 } 155 156 boolean locRes = true; 157 for (int x = -1; x <= bounds.Width; x++) { 158 locRes &= !oObj.containsPoint(new Point(x, -1)); 159 locRes &= !oObj.containsPoint(new Point(x, bounds.Height+bounds.Y)); 160 } 161 if (locRes) { 162 System.out.println("Outer upper and lower bounds contain no component " 163 + "points - OK"); 164 } else { 165 System.out.println("Outer upper and lower bounds CONTAIN some component " 166 + "points - FAILED"); 167 result = false; 168 } 169 170 locRes = true; 171 for (int y = -1; y <= bounds.Height; y++) { 172 locRes &= !oObj.containsPoint(new Point(-1, y)); 173 locRes &= !oObj.containsPoint(new Point(bounds.X+bounds.Width, y)); 174 } 175 if (locRes) { 176 System.out.println("Outer left and right bounds contain no component " 177 + "points - OK"); 178 } else { 179 System.out.println("Outer left and right bounds CONTAIN some component " 180 + "points - FAILED"); 181 result = false; 182 } 183 184 return result; 185 } 186 187 /** 188 * Iterates through all children which implement 189 * <code>XAccessibleComponent</code> (if they exist) determines their 190 * boundaries and tries to get each child by <code>getAccessibleAtPoint</code> 191 * passing point which belongs to the child. 192 * Also the point is checked which doesn't belong to child boundary 193 * box. <p> 194 * 195 * Has <b> OK </b> status if in the first cases the right children 196 * are returned, and in the second <code>null</code> or 197 * another child is returned. 198 * @return 199 */ _getAccessibleAtPoint()200 public boolean _getAccessibleAtPoint() { 201 202 boolean result = true ; 203 XAccessibleComponent[] children = getChildrenComponents(); 204 205 if (children.length > 0) { 206 for (int i = 0; i < children.length; i++) { 207 Rectangle chBnd = children[i].getBounds(); 208 if (chBnd.X == -1) 209 { 210 continue; 211 } 212 System.out.println("Checking child with bounds " + 213 "(" + chBnd.X + "," + chBnd.Y + "),(" 214 + chBnd.Width + "," + chBnd.Height + "): " 215 + util.AccessibilityTools.accessibleToString(children[i])); 216 217 System.out.println("finding the point which lies on the component"); 218 int curX = 0; 219 int curY = 0; 220 while (!children[i].containsPoint(new Point(curX, curY)) 221 && curX < chBnd.Width) { 222 curX++; 223 curY++; 224 } 225 226 if (curX==chBnd.Width) { 227 System.out.println("Couldn't find a point with contains"); 228 continue; 229 } 230 231 // trying the point laying on child 232 XAccessible xAcc = oObj.getAccessibleAtPoint 233 (new Point(chBnd.X , chBnd.Y)); 234 if (xAcc == null) { 235 System.out.println("The child not found at point (" 236 + (chBnd.X ) + "," + chBnd.Y + ") - FAILED"); 237 result = false; 238 } else { 239 XAccessible xAccCh = UnoRuntime.queryInterface 240 (XAccessible.class, children[i]); 241 System.out.println("Child found at point (" 242 + (chBnd.X ) + "," + chBnd.Y + ") - OK"); 243 boolean res = util.AccessibilityTools.equals(xAccCh, xAcc); 244 if (!res) { 245 int expIndex = xAccCh.getAccessibleContext().getAccessibleIndexInParent(); 246 int gotIndex = xAcc.getAccessibleContext().getAccessibleIndexInParent(); 247 if (expIndex < gotIndex) { 248 System.out.println("The children found is not the same"); 249 System.out.println("The expected child " + 250 xAccCh.getAccessibleContext().getAccessibleName()); 251 System.out.println("is hidden behind the found Child "); 252 System.out.println(xAcc.getAccessibleContext().getAccessibleName()+" - OK"); 253 } else { 254 System.out.println("The children found is not the same - FAILED"); 255 System.out.println("Expected: " 256 +xAccCh.getAccessibleContext().getAccessibleName()); 257 System.out.println("Found: " 258 +xAcc.getAccessibleContext().getAccessibleName()); 259 result = false ; 260 } 261 } 262 } 263 264 // trying the point NOT laying on child 265 xAcc = oObj.getAccessibleAtPoint 266 (new Point(chBnd.X - 1, chBnd.Y - 1)); 267 if (xAcc == null) { 268 System.out.println("No children found at point (" 269 + (chBnd.X - 1) + "," + (chBnd.Y - 1) + ") - OK"); 270 result &= true; 271 } else { 272 XAccessible xAccCh = UnoRuntime.queryInterface(XAccessible.class, children[i]); 273 boolean res = util.AccessibilityTools.equals(xAccCh, xAcc); 274 if (res) { 275 System.out.println("The same child found outside " 276 + "its bounds - FAILED"); 277 result = false ; 278 } 279 } 280 } 281 } else { 282 System.out.println("There are no children supporting " 283 + "XAccessibleComponent"); 284 } 285 286 return result; 287 } 288 289 /** 290 * Retrieves the component bounds and stores it. <p> 291 * 292 * Has <b> OK </b> status if boundary position (x,y) is not negative 293 * and size (Width, Height) is greater than 0. 294 * @return 295 */ _getBounds()296 public boolean _getBounds() { 297 boolean result = true ; 298 299 bounds = oObj.getBounds() ; 300 result &= bounds != null 301 && bounds.X >=0 && bounds.Y >=0 302 && bounds.Width >0 && bounds.Height >0; 303 304 System.out.println("Bounds = " + (bounds != null 305 ? "(" + bounds.X + "," + bounds.Y + "),(" 306 + bounds.Width + "," + bounds.Height + ")" : "null")); 307 308 return result; 309 } 310 311 /** 312 * Gets the location. <p> 313 * 314 * Has <b> OK </b> status if the location is the same as location 315 * of boundary obtained by <code>getBounds()</code> method. 316 * 317 * The following method tests are to be completed successfully before : 318 * <ul> 319 * <li> <code> getBounds() </code> : to have bounds </li> 320 * </ul> 321 * @return 322 */ _getLocation()323 public boolean _getLocation() { 324 325 boolean result = true ; 326 Point loc = oObj.getLocation() ; 327 328 result &= loc.X == bounds.X && loc.Y == bounds.Y ; 329 330 return result; 331 } 332 333 /** 334 * Get the screen location of the component and its parent 335 * (if it exists and supports <code>XAccessibleComponent</code>). <p> 336 * 337 * Has <b> OK </b> status if component screen location equals 338 * to screen location of its parent plus location of the component 339 * relative to the parent. <p> 340 * 341 * The following method tests are to be completed successfully before : 342 * <ul> 343 * <li> <code> getBounds() </code> : to have location of the component 344 * relative to its parent</li> 345 * </ul> 346 * @return 347 */ _getLocationOnScreen()348 public boolean _getLocationOnScreen() { 349 350 XAccessibleComponent parent = getParentComponent(); 351 352 boolean result = true ; 353 Point loc = oObj.getLocationOnScreen(); 354 System.out.println("Location is (" + loc.X + "," + loc.Y + ")"); 355 356 if (parent != null) { 357 Point parLoc = parent.getLocationOnScreen(); 358 System.out.println("Parent location is (" 359 + parLoc.X + "," + parLoc.Y + ")"); 360 361 result &= parLoc.X + bounds.X == loc.X; 362 result &= parLoc.Y + bounds.Y == loc.Y; 363 } 364 365 return result; 366 } 367 368 /** 369 * Obtains the size of the component. <p> 370 * 371 * Has <b> OK </b> status if the size is the same as in bounds. <p> 372 * 373 * The following method tests are to be completed successfully before : 374 * <ul> 375 * <li> <code> getBounds() </code> </li> 376 * </ul> 377 * @return 378 */ _getSize()379 public boolean _getSize() { 380 381 boolean result = true ; 382 Size size = oObj.getSize() ; 383 384 result &= size.Width == bounds.Width; 385 result &= size.Height == bounds.Height; 386 387 return result; 388 } 389 390 /** 391 * Just calls the method. <p> 392 * 393 * Has <b> OK </b> status if no runtime exceptions occurred. 394 * @return 395 */ _grabFocus()396 public boolean _grabFocus() { 397 398 boolean result = true ; 399 oObj.grabFocus() ; 400 401 return result ; 402 } 403 404 /** 405 * Retrieves all children (not more than 50) of the current 406 * component which support <code>XAccessibleComponent</code>. 407 * 408 * @return The array of children. Empty array returned if 409 * such children were not found or some error occurred. 410 */ getChildrenComponents()411 private XAccessibleComponent[] getChildrenComponents() { 412 XAccessible xAcc = UnoRuntime.queryInterface(XAccessible.class, oObj) ; 413 if (xAcc == null) { 414 System.out.println("Component doesn't support XAccessible."); 415 return new XAccessibleComponent[0]; 416 } 417 XAccessibleContext xAccCon = xAcc.getAccessibleContext(); 418 int cnt = xAccCon.getAccessibleChildCount(); 419 420 // for cases when too many children exist checking only first 50 421 if (cnt > 50) 422 { 423 cnt = 50; 424 } 425 426 Vector childComp = new Vector(); 427 for (int i = 0; i < cnt; i++) { 428 try { 429 XAccessible child = xAccCon.getAccessibleChild(i); 430 XAccessibleContext xAccConCh = child.getAccessibleContext(); 431 XAccessibleComponent xChAccComp = UnoRuntime.queryInterface(XAccessibleComponent.class, xAccConCh); 432 if (xChAccComp != null) { 433 childComp.add(xChAccComp) ; 434 } 435 } catch (com.sun.star.lang.IndexOutOfBoundsException e) {} 436 } 437 438 return (XAccessibleComponent[]) childComp.toArray 439 (new XAccessibleComponent[childComp.size()]); 440 } 441 442 /** 443 * Gets the parent of the current component which support 444 * <code>XAccessibleComponent</code>. 445 * 446 * @return The parent or <code>null</code> if the component 447 * has no parent or some errors occurred. 448 */ getParentComponent()449 private XAccessibleComponent getParentComponent() { 450 XAccessible xAcc = UnoRuntime.queryInterface(XAccessible.class, oObj) ; 451 if (xAcc == null) { 452 System.out.println("Component doesn't support XAccessible."); 453 return null; 454 } 455 456 XAccessibleContext xAccCon = xAcc.getAccessibleContext(); 457 XAccessible xAccPar = xAccCon.getAccessibleParent(); 458 459 if (xAccPar == null) { 460 System.out.println("Component has no accessible parent."); 461 return null; 462 } 463 XAccessibleContext xAccConPar = xAccPar.getAccessibleContext(); 464 XAccessibleComponent parent = UnoRuntime.queryInterface(XAccessibleComponent.class, xAccConPar); 465 if (parent == null) { 466 System.out.println 467 ("Accessible parent doesn't support XAccessibleComponent"); 468 return null; 469 } 470 471 return parent; 472 } 473 474 /** 475 * Just calls the method. 476 * @return 477 */ _getForeground()478 public boolean _getForeground() { 479 int forColor = oObj.getForeground(); 480 System.out.println("getForeground(): " + forColor); 481 return true; 482 } 483 484 /** 485 * Just calls the method. 486 * @return 487 */ _getBackground()488 public boolean _getBackground() { 489 int backColor = oObj.getBackground(); 490 System.out.println("getBackground(): " + backColor); 491 return true; 492 } 493 494 } 495