Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(43)

Side by Side Diff: content/shell/renderer/test_runner/WebAXObjectProxy.cpp

Issue 172263002: Move WebAXObjectProxy and AccessibleController from CppBoundClass to gin::Wrappable (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: (rebasing) Created 6 years, 9 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "content/shell/renderer/test_runner/WebAXObjectProxy.h"
6
7 #include "content/shell/renderer/test_runner/TestCommon.h"
8 #include "third_party/WebKit/public/platform/WebCString.h"
9 #include "third_party/WebKit/public/platform/WebPoint.h"
10 #include "third_party/WebKit/public/platform/WebRect.h"
11 #include "third_party/WebKit/public/platform/WebString.h"
12
13 using namespace blink;
14 using namespace std;
15
16 namespace WebTestRunner {
17
18 namespace {
19
20 // Map role value to string, matching Safari/Mac platform implementation to
21 // avoid rebaselining layout tests.
22 string roleToString(WebAXRole role)
23 {
24 string result = "AXRole: AX";
25 switch (role) {
26 case WebAXRoleAlertDialog:
27 return result.append("AlertDialog");
28 case WebAXRoleAlert:
29 return result.append("Alert");
30 case WebAXRoleAnnotation:
31 return result.append("Annotation");
32 case WebAXRoleApplication:
33 return result.append("Application");
34 case WebAXRoleArticle:
35 return result.append("Article");
36 case WebAXRoleBanner:
37 return result.append("Banner");
38 case WebAXRoleBrowser:
39 return result.append("Browser");
40 case WebAXRoleBusyIndicator:
41 return result.append("BusyIndicator");
42 case WebAXRoleButton:
43 return result.append("Button");
44 case WebAXRoleCanvas:
45 return result.append("Canvas");
46 case WebAXRoleCell:
47 return result.append("Cell");
48 case WebAXRoleCheckBox:
49 return result.append("CheckBox");
50 case WebAXRoleColorWell:
51 return result.append("ColorWell");
52 case WebAXRoleColumnHeader:
53 return result.append("ColumnHeader");
54 case WebAXRoleColumn:
55 return result.append("Column");
56 case WebAXRoleComboBox:
57 return result.append("ComboBox");
58 case WebAXRoleComplementary:
59 return result.append("Complementary");
60 case WebAXRoleContentInfo:
61 return result.append("ContentInfo");
62 case WebAXRoleDefinition:
63 return result.append("Definition");
64 case WebAXRoleDescriptionListDetail:
65 return result.append("DescriptionListDetail");
66 case WebAXRoleDescriptionListTerm:
67 return result.append("DescriptionListTerm");
68 case WebAXRoleDialog:
69 return result.append("Dialog");
70 case WebAXRoleDirectory:
71 return result.append("Directory");
72 case WebAXRoleDisclosureTriangle:
73 return result.append("DisclosureTriangle");
74 case WebAXRoleDiv:
75 return result.append("Div");
76 case WebAXRoleDocument:
77 return result.append("Document");
78 case WebAXRoleDrawer:
79 return result.append("Drawer");
80 case WebAXRoleEditableText:
81 return result.append("EditableText");
82 case WebAXRoleFooter:
83 return result.append("Footer");
84 case WebAXRoleForm:
85 return result.append("Form");
86 case WebAXRoleGrid:
87 return result.append("Grid");
88 case WebAXRoleGroup:
89 return result.append("Group");
90 case WebAXRoleGrowArea:
91 return result.append("GrowArea");
92 case WebAXRoleHeading:
93 return result.append("Heading");
94 case WebAXRoleHelpTag:
95 return result.append("HelpTag");
96 case WebAXRoleHorizontalRule:
97 return result.append("HorizontalRule");
98 case WebAXRoleIgnored:
99 return result.append("Ignored");
100 case WebAXRoleImageMapLink:
101 return result.append("ImageMapLink");
102 case WebAXRoleImageMap:
103 return result.append("ImageMap");
104 case WebAXRoleImage:
105 return result.append("Image");
106 case WebAXRoleIncrementor:
107 return result.append("Incrementor");
108 case WebAXRoleInlineTextBox:
109 return result.append("InlineTextBox");
110 case WebAXRoleLabel:
111 return result.append("Label");
112 case WebAXRoleLegend:
113 return result.append("Legend");
114 case WebAXRoleLink:
115 return result.append("Link");
116 case WebAXRoleListBoxOption:
117 return result.append("ListBoxOption");
118 case WebAXRoleListBox:
119 return result.append("ListBox");
120 case WebAXRoleListItem:
121 return result.append("ListItem");
122 case WebAXRoleListMarker:
123 return result.append("ListMarker");
124 case WebAXRoleList:
125 return result.append("List");
126 case WebAXRoleLog:
127 return result.append("Log");
128 case WebAXRoleMain:
129 return result.append("Main");
130 case WebAXRoleMarquee:
131 return result.append("Marquee");
132 case WebAXRoleMathElement:
133 return result.append("MathElement");
134 case WebAXRoleMath:
135 return result.append("Math");
136 case WebAXRoleMatte:
137 return result.append("Matte");
138 case WebAXRoleMenuBar:
139 return result.append("MenuBar");
140 case WebAXRoleMenuButton:
141 return result.append("MenuButton");
142 case WebAXRoleMenuItem:
143 return result.append("MenuItem");
144 case WebAXRoleMenuListOption:
145 return result.append("MenuListOption");
146 case WebAXRoleMenuListPopup:
147 return result.append("MenuListPopup");
148 case WebAXRoleMenu:
149 return result.append("Menu");
150 case WebAXRoleNavigation:
151 return result.append("Navigation");
152 case WebAXRoleNote:
153 return result.append("Note");
154 case WebAXRoleOutline:
155 return result.append("Outline");
156 case WebAXRoleParagraph:
157 return result.append("Paragraph");
158 case WebAXRolePopUpButton:
159 return result.append("PopUpButton");
160 case WebAXRolePresentational:
161 return result.append("Presentational");
162 case WebAXRoleProgressIndicator:
163 return result.append("ProgressIndicator");
164 case WebAXRoleRadioButton:
165 return result.append("RadioButton");
166 case WebAXRoleRadioGroup:
167 return result.append("RadioGroup");
168 case WebAXRoleRegion:
169 return result.append("Region");
170 case WebAXRoleRootWebArea:
171 return result.append("RootWebArea");
172 case WebAXRoleRowHeader:
173 return result.append("RowHeader");
174 case WebAXRoleRow:
175 return result.append("Row");
176 case WebAXRoleRulerMarker:
177 return result.append("RulerMarker");
178 case WebAXRoleRuler:
179 return result.append("Ruler");
180 case WebAXRoleSVGRoot:
181 return result.append("SVGRoot");
182 case WebAXRoleScrollArea:
183 return result.append("ScrollArea");
184 case WebAXRoleScrollBar:
185 return result.append("ScrollBar");
186 case WebAXRoleSeamlessWebArea:
187 return result.append("SeamlessWebArea");
188 case WebAXRoleSearch:
189 return result.append("Search");
190 case WebAXRoleSheet:
191 return result.append("Sheet");
192 case WebAXRoleSlider:
193 return result.append("Slider");
194 case WebAXRoleSliderThumb:
195 return result.append("SliderThumb");
196 case WebAXRoleSpinButtonPart:
197 return result.append("SpinButtonPart");
198 case WebAXRoleSpinButton:
199 return result.append("SpinButton");
200 case WebAXRoleSplitGroup:
201 return result.append("SplitGroup");
202 case WebAXRoleSplitter:
203 return result.append("Splitter");
204 case WebAXRoleStaticText:
205 return result.append("StaticText");
206 case WebAXRoleStatus:
207 return result.append("Status");
208 case WebAXRoleSystemWide:
209 return result.append("SystemWide");
210 case WebAXRoleTabGroup:
211 return result.append("TabGroup");
212 case WebAXRoleTabList:
213 return result.append("TabList");
214 case WebAXRoleTabPanel:
215 return result.append("TabPanel");
216 case WebAXRoleTab:
217 return result.append("Tab");
218 case WebAXRoleTableHeaderContainer:
219 return result.append("TableHeaderContainer");
220 case WebAXRoleTable:
221 return result.append("Table");
222 case WebAXRoleTextArea:
223 return result.append("TextArea");
224 case WebAXRoleTextField:
225 return result.append("TextField");
226 case WebAXRoleTimer:
227 return result.append("Timer");
228 case WebAXRoleToggleButton:
229 return result.append("ToggleButton");
230 case WebAXRoleToolbar:
231 return result.append("Toolbar");
232 case WebAXRoleTreeGrid:
233 return result.append("TreeGrid");
234 case WebAXRoleTreeItem:
235 return result.append("TreeItem");
236 case WebAXRoleTree:
237 return result.append("Tree");
238 case WebAXRoleUnknown:
239 return result.append("Unknown");
240 case WebAXRoleUserInterfaceTooltip:
241 return result.append("UserInterfaceTooltip");
242 case WebAXRoleValueIndicator:
243 return result.append("ValueIndicator");
244 case WebAXRoleWebArea:
245 return result.append("WebArea");
246 case WebAXRoleWindow:
247 return result.append("Window");
248 default:
249 return result.append("Unknown");
250 }
251 }
252
253 string getDescription(const WebAXObject& object)
254 {
255 string description = object.accessibilityDescription().utf8();
256 return description.insert(0, "AXDescription: ");
257 }
258
259 string getHelpText(const WebAXObject& object)
260 {
261 string helpText = object.helpText().utf8();
262 return helpText.insert(0, "AXHelp: ");
263 }
264
265 string getStringValue(const WebAXObject& object)
266 {
267 string value;
268 if (object.role() == WebAXRoleColorWell) {
269 int r, g, b;
270 char buffer[100];
271 object.colorValue(r, g, b);
272 snprintf(buffer, sizeof(buffer), "rgb %7.5f %7.5f %7.5f 1", r / 255., g / 255., b / 255.);
273 value = buffer;
274 } else {
275 value = object.stringValue().utf8();
276 }
277 return value.insert(0, "AXValue: ");
278 }
279
280 string getRole(const WebAXObject& object)
281 {
282 string roleString = roleToString(object.role());
283
284 // Special-case canvas with fallback content because Chromium wants to
285 // treat this as essentially a separate role that it can map differently dep ending
286 // on the platform.
287 if (object.role() == WebAXRoleCanvas && object.canvasHasFallbackContent())
288 roleString += "WithFallbackContent";
289
290 return roleString;
291 }
292
293 string getTitle(const WebAXObject& object)
294 {
295 string title = object.title().utf8();
296 return title.insert(0, "AXTitle: ");
297 }
298
299 string getOrientation(const WebAXObject& object)
300 {
301 if (object.isVertical())
302 return "AXOrientation: AXVerticalOrientation";
303
304 return "AXOrientation: AXHorizontalOrientation";
305 }
306
307 string getValueDescription(const WebAXObject& object)
308 {
309 string valueDescription = object.valueDescription().utf8();
310 return valueDescription.insert(0, "AXValueDescription: ");
311 }
312
313 string getAttributes(const WebAXObject& object)
314 {
315 // FIXME: Concatenate all attributes of the AXObject.
316 string attributes(getTitle(object));
317 attributes.append("\n");
318 attributes.append(getRole(object));
319 attributes.append("\n");
320 attributes.append(getDescription(object));
321 return attributes;
322 }
323
324 WebRect boundsForCharacter(const WebAXObject& object, int characterIndex)
325 {
326 BLINK_ASSERT(object.role() == WebAXRoleStaticText);
327 int end = 0;
328 for (unsigned i = 0; i < object.childCount(); i++) {
329 WebAXObject inlineTextBox = object.childAt(i);
330 BLINK_ASSERT(inlineTextBox.role() == WebAXRoleInlineTextBox);
331 int start = end;
332 end += inlineTextBox.stringValue().length();
333 if (end <= characterIndex)
334 continue;
335 WebRect inlineTextBoxRect = inlineTextBox.boundingBoxRect();
336 int localIndex = characterIndex - start;
337 WebVector<int> characterOffsets;
338 inlineTextBox.characterOffsets(characterOffsets);
339 BLINK_ASSERT(characterOffsets.size() > 0 && characterOffsets.size() == i nlineTextBox.stringValue().length());
340 switch (inlineTextBox.textDirection()) {
341 case WebAXTextDirectionLR: {
342 if (localIndex) {
343 int left = inlineTextBoxRect.x + characterOffsets[localIndex - 1 ];
344 int width = characterOffsets[localIndex] - characterOffsets[loca lIndex - 1];
345 return WebRect(left, inlineTextBoxRect.y, width, inlineTextBoxRe ct.height);
346 }
347 return WebRect(inlineTextBoxRect.x, inlineTextBoxRect.y, characterOf fsets[0], inlineTextBoxRect.height);
348 }
349 case WebAXTextDirectionRL: {
350 int right = inlineTextBoxRect.x + inlineTextBoxRect.width;
351
352 if (localIndex) {
353 int left = right - characterOffsets[localIndex];
354 int width = characterOffsets[localIndex] - characterOffsets[loca lIndex - 1];
355 return WebRect(left, inlineTextBoxRect.y, width, inlineTextBoxRe ct.height);
356 }
357 int left = right - characterOffsets[0];
358 return WebRect(left, inlineTextBoxRect.y, characterOffsets[0], inlin eTextBoxRect.height);
359 }
360 case WebAXTextDirectionTB: {
361 if (localIndex) {
362 int top = inlineTextBoxRect.y + characterOffsets[localIndex - 1] ;
363 int height = characterOffsets[localIndex] - characterOffsets[loc alIndex - 1];
364 return WebRect(inlineTextBoxRect.x, top, inlineTextBoxRect.width , height);
365 }
366 return WebRect(inlineTextBoxRect.x, inlineTextBoxRect.y, inlineTextB oxRect.width, characterOffsets[0]);
367 }
368 case WebAXTextDirectionBT: {
369 int bottom = inlineTextBoxRect.y + inlineTextBoxRect.height;
370
371 if (localIndex) {
372 int top = bottom - characterOffsets[localIndex];
373 int height = characterOffsets[localIndex] - characterOffsets[loc alIndex - 1];
374 return WebRect(inlineTextBoxRect.x, top, inlineTextBoxRect.width , height);
375 }
376 int top = bottom - characterOffsets[0];
377 return WebRect(inlineTextBoxRect.x, top, inlineTextBoxRect.width, ch aracterOffsets[0]);
378 }
379 }
380 }
381
382 BLINK_ASSERT(false);
383 return WebRect();
384 }
385
386 void getBoundariesForOneWord(const WebAXObject& object, int characterIndex, int& wordStart, int& wordEnd)
387 {
388 int end = 0;
389 for (unsigned i = 0; i < object.childCount(); i++) {
390 WebAXObject inlineTextBox = object.childAt(i);
391 BLINK_ASSERT(inlineTextBox.role() == WebAXRoleInlineTextBox);
392 int start = end;
393 end += inlineTextBox.stringValue().length();
394 if (end <= characterIndex)
395 continue;
396 int localIndex = characterIndex - start;
397
398 WebVector<int> starts;
399 WebVector<int> ends;
400 inlineTextBox.wordBoundaries(starts, ends);
401 size_t wordCount = starts.size();
402 BLINK_ASSERT(ends.size() == wordCount);
403
404 // If there are no words, use the InlineTextBox boundaries.
405 if (!wordCount) {
406 wordStart = start;
407 wordEnd = end;
408 return;
409 }
410
411 // Look for a character within any word other than the last.
412 for (size_t j = 0; j < wordCount - 1; j++) {
413 if (localIndex <= ends[j]) {
414 wordStart = start + starts[j];
415 wordEnd = start + ends[j];
416 return;
417 }
418 }
419
420 // Return the last word by default.
421 wordStart = start + starts[wordCount - 1];
422 wordEnd = start + ends[wordCount - 1];
423 return;
424 }
425 }
426
427 // Collects attributes into a string, delimited by dashes. Used by all methods
428 // that output lists of attributes: attributesOfLinkedUIElementsCallback,
429 // AttributesOfChildrenCallback, etc.
430 class AttributesCollector {
431 public:
432 void collectAttributes(const WebAXObject& object)
433 {
434 m_attributes.append("\n------------\n");
435 m_attributes.append(getAttributes(object));
436 }
437
438 string attributes() const { return m_attributes; }
439
440 private:
441 string m_attributes;
442 };
443
444 }
445
446 WebAXObjectProxy::WebAXObjectProxy(const WebAXObject& object, Factory* factory)
447 : m_accessibilityObject(object)
448 , m_factory(factory)
449 {
450
451 BLINK_ASSERT(factory);
452
453 //
454 // Properties
455 //
456
457 bindProperty("role", &WebAXObjectProxy::roleGetterCallback);
458 bindProperty("title", &WebAXObjectProxy::titleGetterCallback);
459 bindProperty("description", &WebAXObjectProxy::descriptionGetterCallback);
460 bindProperty("helpText", &WebAXObjectProxy::helpTextGetterCallback);
461 bindProperty("stringValue", &WebAXObjectProxy::stringValueGetterCallback);
462 bindProperty("x", &WebAXObjectProxy::xGetterCallback);
463 bindProperty("y", &WebAXObjectProxy::yGetterCallback);
464 bindProperty("width", &WebAXObjectProxy::widthGetterCallback);
465 bindProperty("height", &WebAXObjectProxy::heightGetterCallback);
466 bindProperty("intValue", &WebAXObjectProxy::intValueGetterCallback);
467 bindProperty("minValue", &WebAXObjectProxy::minValueGetterCallback);
468 bindProperty("maxValue", &WebAXObjectProxy::maxValueGetterCallback);
469 bindProperty("valueDescription", &WebAXObjectProxy::valueDescriptionGetterCa llback);
470 bindProperty("childrenCount", &WebAXObjectProxy::childrenCountGetterCallback );
471 bindProperty("insertionPointLineNumber", &WebAXObjectProxy::insertionPointLi neNumberGetterCallback);
472 bindProperty("selectedTextRange", &WebAXObjectProxy::selectedTextRangeGetter Callback);
473 bindProperty("isEnabled", &WebAXObjectProxy::isEnabledGetterCallback);
474 bindProperty("isRequired", &WebAXObjectProxy::isRequiredGetterCallback);
475 bindProperty("isFocused", &WebAXObjectProxy::isFocusedGetterCallback);
476 bindProperty("isFocusable", &WebAXObjectProxy::isFocusableGetterCallback);
477 bindProperty("isSelected", &WebAXObjectProxy::isSelectedGetterCallback);
478 bindProperty("isSelectable", &WebAXObjectProxy::isSelectableGetterCallback);
479 bindProperty("isMultiSelectable", &WebAXObjectProxy::isMultiSelectableGetter Callback);
480 bindProperty("isSelectedOptionActive", &WebAXObjectProxy::isSelectedOptionAc tiveGetterCallback);
481 bindProperty("isExpanded", &WebAXObjectProxy::isExpandedGetterCallback);
482 bindProperty("isChecked", &WebAXObjectProxy::isCheckedGetterCallback);
483 bindProperty("isVisible", &WebAXObjectProxy::isVisibleGetterCallback);
484 bindProperty("isOffScreen", &WebAXObjectProxy::isOffScreenGetterCallback);
485 bindProperty("isCollapsed", &WebAXObjectProxy::isCollapsedGetterCallback);
486 bindProperty("hasPopup", &WebAXObjectProxy::hasPopupGetterCallback);
487 bindProperty("isValid", &WebAXObjectProxy::isValidGetterCallback);
488 bindProperty("isReadOnly", &WebAXObjectProxy::isReadOnlyGetterCallback);
489 bindProperty("orientation", &WebAXObjectProxy::orientationGetterCallback);
490 bindProperty("clickPointX", &WebAXObjectProxy::clickPointXGetterCallback);
491 bindProperty("clickPointY", &WebAXObjectProxy::clickPointYGetterCallback);
492 bindProperty("rowCount", &WebAXObjectProxy::rowCountGetterCallback);
493 bindProperty("columnCount", &WebAXObjectProxy::columnCountGetterCallback);
494 bindProperty("isClickable", &WebAXObjectProxy::isClickableGetterCallback);
495
496 //
497 // Methods
498 //
499
500 bindMethod("allAttributes", &WebAXObjectProxy::allAttributesCallback);
501 bindMethod("attributesOfChildren", &WebAXObjectProxy::attributesOfChildrenCa llback);
502 bindMethod("lineForIndex", &WebAXObjectProxy::lineForIndexCallback);
503 bindMethod("boundsForRange", &WebAXObjectProxy::boundsForRangeCallback);
504 bindMethod("childAtIndex", &WebAXObjectProxy::childAtIndexCallback);
505 bindMethod("elementAtPoint", &WebAXObjectProxy::elementAtPointCallback);
506 bindMethod("tableHeader", &WebAXObjectProxy::tableHeaderCallback);
507 bindMethod("rowIndexRange", &WebAXObjectProxy::rowIndexRangeCallback);
508 bindMethod("columnIndexRange", &WebAXObjectProxy::columnIndexRangeCallback);
509 bindMethod("cellForColumnAndRow", &WebAXObjectProxy::cellForColumnAndRowCall back);
510 bindMethod("titleUIElement", &WebAXObjectProxy::titleUIElementCallback);
511 bindMethod("setSelectedTextRange", &WebAXObjectProxy::setSelectedTextRangeCa llback);
512 bindMethod("isAttributeSettable", &WebAXObjectProxy::isAttributeSettableCall back);
513 bindMethod("isPressActionSupported", &WebAXObjectProxy::isPressActionSupport edCallback);
514 bindMethod("isIncrementActionSupported", &WebAXObjectProxy::isIncrementActio nSupportedCallback);
515 bindMethod("isDecrementActionSupported", &WebAXObjectProxy::isDecrementActio nSupportedCallback);
516 bindMethod("parentElement", &WebAXObjectProxy::parentElementCallback);
517 bindMethod("increment", &WebAXObjectProxy::incrementCallback);
518 bindMethod("decrement", &WebAXObjectProxy::decrementCallback);
519 bindMethod("showMenu", &WebAXObjectProxy::showMenuCallback);
520 bindMethod("press", &WebAXObjectProxy::pressCallback);
521 bindMethod("isEqual", &WebAXObjectProxy::isEqualCallback);
522 bindMethod("addNotificationListener", &WebAXObjectProxy::addNotificationList enerCallback);
523 bindMethod("removeNotificationListener", &WebAXObjectProxy::removeNotificati onListenerCallback);
524 bindMethod("takeFocus", &WebAXObjectProxy::takeFocusCallback);
525 bindMethod("scrollToMakeVisible", &WebAXObjectProxy::scrollToMakeVisibleCall back);
526 bindMethod("scrollToMakeVisibleWithSubFocus", &WebAXObjectProxy::scrollToMak eVisibleWithSubFocusCallback);
527 bindMethod("scrollToGlobalPoint", &WebAXObjectProxy::scrollToGlobalPointCall back);
528 bindMethod("wordStart", &WebAXObjectProxy::wordStartCallback);
529 bindMethod("wordEnd", &WebAXObjectProxy::wordEndCallback);
530
531 bindFallbackMethod(&WebAXObjectProxy::fallbackCallback);
532 }
533
534 WebAXObjectProxy::~WebAXObjectProxy()
535 {
536 }
537
538 WebAXObjectProxy* WebAXObjectProxy::getChildAtIndex(unsigned index)
539 {
540 return m_factory->getOrCreate(accessibilityObject().childAt(index));
541 }
542
543 bool WebAXObjectProxy::isRoot() const
544 {
545 return false;
546 }
547
548 bool WebAXObjectProxy::isEqual(const blink::WebAXObject& other)
549 {
550 return accessibilityObject().equals(other);
551 }
552
553 void WebAXObjectProxy::notificationReceived(const char* notificationName)
554 {
555 size_t callbackCount = m_notificationCallbacks.size();
556 for (size_t i = 0; i < callbackCount; i++) {
557 CppVariant notificationNameArgument;
558 notificationNameArgument.set(notificationName);
559 CppVariant invokeResult;
560 m_notificationCallbacks[i].invokeDefault(&notificationNameArgument, 1, i nvokeResult);
561 }
562 }
563
564 //
565 // Properties
566 //
567
568 void WebAXObjectProxy::roleGetterCallback(CppVariant* result)
569 {
570 result->set(getRole(accessibilityObject()));
571 }
572
573 void WebAXObjectProxy::titleGetterCallback(CppVariant* result)
574 {
575 result->set(getTitle(accessibilityObject()));
576 }
577
578 void WebAXObjectProxy::descriptionGetterCallback(CppVariant* result)
579 {
580 result->set(getDescription(accessibilityObject()));
581 }
582
583 void WebAXObjectProxy::helpTextGetterCallback(CppVariant* result)
584 {
585 result->set(getHelpText(accessibilityObject()));
586 }
587
588 void WebAXObjectProxy::stringValueGetterCallback(CppVariant* result)
589 {
590 result->set(getStringValue(accessibilityObject()));
591 }
592
593 void WebAXObjectProxy::xGetterCallback(CppVariant* result)
594 {
595 result->set(accessibilityObject().boundingBoxRect().x);
596 }
597
598 void WebAXObjectProxy::yGetterCallback(CppVariant* result)
599 {
600 result->set(accessibilityObject().boundingBoxRect().y);
601 }
602
603 void WebAXObjectProxy::widthGetterCallback(CppVariant* result)
604 {
605 result->set(accessibilityObject().boundingBoxRect().width);
606 }
607
608 void WebAXObjectProxy::heightGetterCallback(CppVariant* result)
609 {
610 result->set(accessibilityObject().boundingBoxRect().height);
611 }
612
613 void WebAXObjectProxy::intValueGetterCallback(CppVariant* result)
614 {
615 if (accessibilityObject().supportsRangeValue())
616 result->set(accessibilityObject().valueForRange());
617 else if (accessibilityObject().role() == WebAXRoleHeading)
618 result->set(accessibilityObject().headingLevel());
619 else
620 result->set(atoi(accessibilityObject().stringValue().utf8().data()));
621 }
622
623 void WebAXObjectProxy::minValueGetterCallback(CppVariant* result)
624 {
625 result->set(accessibilityObject().minValueForRange());
626 }
627
628 void WebAXObjectProxy::maxValueGetterCallback(CppVariant* result)
629 {
630 result->set(accessibilityObject().maxValueForRange());
631 }
632
633 void WebAXObjectProxy::valueDescriptionGetterCallback(CppVariant* result)
634 {
635 result->set(getValueDescription(accessibilityObject()));
636 }
637
638 void WebAXObjectProxy::childrenCountGetterCallback(CppVariant* result)
639 {
640 int count = 1; // Root object always has only one child, the WebView.
641 if (!isRoot())
642 count = accessibilityObject().childCount();
643 result->set(count);
644 }
645
646 void WebAXObjectProxy::insertionPointLineNumberGetterCallback(CppVariant* result )
647 {
648 if (!accessibilityObject().isFocused()) {
649 result->set(-1);
650 return;
651 }
652
653 int lineNumber = accessibilityObject().selectionEndLineNumber();
654 result->set(lineNumber);
655 }
656
657 void WebAXObjectProxy::selectedTextRangeGetterCallback(CppVariant* result)
658 {
659 unsigned selectionStart = accessibilityObject().selectionStart();
660 unsigned selectionEnd = accessibilityObject().selectionEnd();
661 char buffer[100];
662 snprintf(buffer, sizeof(buffer), "{%d, %d}", selectionStart, selectionEnd - selectionStart);
663
664 result->set(std::string(buffer));
665 }
666
667 void WebAXObjectProxy::isEnabledGetterCallback(CppVariant* result)
668 {
669 result->set(accessibilityObject().isEnabled());
670 }
671
672 void WebAXObjectProxy::isRequiredGetterCallback(CppVariant* result)
673 {
674 result->set(accessibilityObject().isRequired());
675 }
676
677 void WebAXObjectProxy::isFocusedGetterCallback(CppVariant* result)
678 {
679 result->set(accessibilityObject().isFocused());
680 }
681
682 void WebAXObjectProxy::isFocusableGetterCallback(CppVariant* result)
683 {
684 result->set(accessibilityObject().canSetFocusAttribute());
685 }
686
687 void WebAXObjectProxy::isSelectedGetterCallback(CppVariant* result)
688 {
689 result->set(accessibilityObject().isSelected());
690 }
691
692 void WebAXObjectProxy::isSelectableGetterCallback(CppVariant* result)
693 {
694 result->set(accessibilityObject().canSetSelectedAttribute());
695 }
696
697 void WebAXObjectProxy::isMultiSelectableGetterCallback(CppVariant* result)
698 {
699 result->set(accessibilityObject().isMultiSelectable());
700 }
701
702 void WebAXObjectProxy::isSelectedOptionActiveGetterCallback(CppVariant* result)
703 {
704 result->set(accessibilityObject().isSelectedOptionActive());
705 }
706
707 void WebAXObjectProxy::isExpandedGetterCallback(CppVariant* result)
708 {
709 result->set(!accessibilityObject().isCollapsed());
710 }
711
712 void WebAXObjectProxy::isCheckedGetterCallback(CppVariant* result)
713 {
714 result->set(accessibilityObject().isChecked());
715 }
716
717 void WebAXObjectProxy::isVisibleGetterCallback(CppVariant* result)
718 {
719 result->set(accessibilityObject().isVisible());
720 }
721
722 void WebAXObjectProxy::isOffScreenGetterCallback(CppVariant* result)
723 {
724 result->set(accessibilityObject().isOffScreen());
725 }
726
727 void WebAXObjectProxy::isCollapsedGetterCallback(CppVariant* result)
728 {
729 result->set(accessibilityObject().isCollapsed());
730 }
731
732 void WebAXObjectProxy::hasPopupGetterCallback(CppVariant* result)
733 {
734 result->set(accessibilityObject().ariaHasPopup());
735 }
736
737 void WebAXObjectProxy::isValidGetterCallback(CppVariant* result)
738 {
739 result->set(!accessibilityObject().isDetached());
740 }
741
742 void WebAXObjectProxy::isReadOnlyGetterCallback(CppVariant* result)
743 {
744 result->set(accessibilityObject().isReadOnly());
745 }
746
747 void WebAXObjectProxy::orientationGetterCallback(CppVariant* result)
748 {
749 result->set(getOrientation(accessibilityObject()));
750 }
751
752 void WebAXObjectProxy::clickPointXGetterCallback(CppVariant* result)
753 {
754 result->set(accessibilityObject().clickPoint().x);
755 }
756
757 void WebAXObjectProxy::clickPointYGetterCallback(CppVariant* result)
758 {
759 result->set(accessibilityObject().clickPoint().y);
760 }
761
762 void WebAXObjectProxy::rowCountGetterCallback(CppVariant* result)
763 {
764 result->set(static_cast<int32_t>(accessibilityObject().rowCount()));
765 }
766
767 void WebAXObjectProxy::columnCountGetterCallback(CppVariant* result)
768 {
769 result->set(static_cast<int32_t>(accessibilityObject().columnCount()));
770 }
771
772 void WebAXObjectProxy::isClickableGetterCallback(CppVariant* result)
773 {
774 result->set(accessibilityObject().isClickable());
775 }
776
777 //
778 // Methods
779 //
780
781 void WebAXObjectProxy::allAttributesCallback(const CppArgumentList&, CppVariant* result)
782 {
783 result->set(getAttributes(accessibilityObject()));
784 }
785
786 void WebAXObjectProxy::attributesOfChildrenCallback(const CppArgumentList& argum ents, CppVariant* result)
787 {
788 AttributesCollector collector;
789 unsigned size = accessibilityObject().childCount();
790 for (unsigned i = 0; i < size; ++i)
791 collector.collectAttributes(accessibilityObject().childAt(i));
792 result->set(collector.attributes());
793 }
794
795 void WebAXObjectProxy::lineForIndexCallback(const CppArgumentList& arguments, Cp pVariant* result)
796 {
797 if (!arguments.size() || !arguments[0].isNumber()) {
798 result->setNull();
799 return;
800 }
801
802 int index = arguments[0].toInt32();
803
804 WebVector<int> lineBreaks;
805 accessibilityObject().lineBreaks(lineBreaks);
806 int line = 0;
807 int vectorSize = static_cast<int>(lineBreaks.size());
808 while (line < vectorSize && lineBreaks[line] <= index)
809 line++;
810 result->set(line);
811 }
812
813 void WebAXObjectProxy::boundsForRangeCallback(const CppArgumentList& arguments, CppVariant* result)
814 {
815 result->setNull();
816
817 if (arguments.size() != 2 || !arguments[0].isNumber() || !arguments[1].isNum ber())
818 return;
819
820 if (accessibilityObject().role() != WebAXRoleStaticText)
821 return;
822
823 int start = arguments[0].toInt32();
824 int end = arguments[1].toInt32();
825 int len = end - start;
826
827 // Get the bounds for each character and union them into one large rectangle .
828 // This is just for testing so it doesn't need to be efficient.
829 WebRect bounds = boundsForCharacter(accessibilityObject(), start);
830 for (int i = 1; i < len; i++) {
831 WebRect next = boundsForCharacter(accessibilityObject(), start + i);
832 int right = std::max(bounds.x + bounds.width, next.x + next.width);
833 int bottom = std::max(bounds.y + bounds.height, next.y + next.height);
834 bounds.x = std::min(bounds.x, next.x);
835 bounds.y = std::min(bounds.y, next.y);
836 bounds.width = right - bounds.x;
837 bounds.height = bottom - bounds.y;
838 }
839
840 char buffer[100];
841 snprintf(buffer, sizeof(buffer), "{x: %d, y: %d, width: %d, height: %d}", bo unds.x, bounds.y, bounds.width, bounds.height);
842 result->set(string(buffer));
843 }
844
845 void WebAXObjectProxy::childAtIndexCallback(const CppArgumentList& arguments, Cp pVariant* result)
846 {
847 if (!arguments.size() || !arguments[0].isNumber()) {
848 result->setNull();
849 return;
850 }
851
852 WebAXObjectProxy* child = getChildAtIndex(arguments[0].toInt32());
853 if (!child) {
854 result->setNull();
855 return;
856 }
857
858 result->set(*(child->getAsCppVariant()));
859 }
860
861 void WebAXObjectProxy::elementAtPointCallback(const CppArgumentList& arguments, CppVariant* result)
862 {
863 result->setNull();
864
865 if (arguments.size() != 2 || !arguments[0].isNumber() || !arguments[1].isNum ber())
866 return;
867
868 int x = arguments[0].toInt32();
869 int y = arguments[1].toInt32();
870 WebPoint point(x, y);
871 WebAXObject obj = accessibilityObject().hitTest(point);
872 if (obj.isNull())
873 return;
874
875 result->set(*(m_factory->getOrCreate(obj)->getAsCppVariant()));
876 }
877
878 void WebAXObjectProxy::tableHeaderCallback(const CppArgumentList&, CppVariant* r esult)
879 {
880 WebAXObject obj = accessibilityObject().headerContainerObject();
881 if (obj.isNull()) {
882 result->setNull();
883 return;
884 }
885
886 result->set(*(m_factory->getOrCreate(obj)->getAsCppVariant()));
887 }
888
889 void WebAXObjectProxy::rowIndexRangeCallback(const CppArgumentList&, CppVariant* result)
890 {
891 unsigned rowIndex = accessibilityObject().cellRowIndex();
892 unsigned rowSpan = accessibilityObject().cellRowSpan();
893 char buffer[100];
894 snprintf(buffer, sizeof(buffer), "{%d, %d}", rowIndex, rowSpan);
895 string value = buffer;
896 result->set(std::string(buffer));
897 }
898
899 void WebAXObjectProxy::columnIndexRangeCallback(const CppArgumentList&, CppVaria nt* result)
900 {
901 unsigned columnIndex = accessibilityObject().cellColumnIndex();
902 unsigned columnSpan = accessibilityObject().cellColumnSpan();
903 char buffer[100];
904 snprintf(buffer, sizeof(buffer), "{%d, %d}", columnIndex, columnSpan);
905 result->set(std::string(buffer));
906 }
907
908 void WebAXObjectProxy::cellForColumnAndRowCallback(const CppArgumentList& argume nts, CppVariant* result)
909 {
910 if (arguments.size() != 2 || !arguments[0].isNumber() || !arguments[1].isNum ber())
911 return;
912
913 int column = arguments[0].toInt32();
914 int row = arguments[1].toInt32();
915 WebAXObject obj = accessibilityObject().cellForColumnAndRow(column, row);
916 if (obj.isNull()) {
917 result->setNull();
918 return;
919 }
920
921 result->set(*(m_factory->getOrCreate(obj)->getAsCppVariant()));
922 }
923
924 void WebAXObjectProxy::titleUIElementCallback(const CppArgumentList&, CppVariant * result)
925 {
926 WebAXObject obj = accessibilityObject().titleUIElement();
927 if (obj.isNull()) {
928 result->setNull();
929 return;
930 }
931
932 result->set(*(m_factory->getOrCreate(obj)->getAsCppVariant()));
933 }
934
935 void WebAXObjectProxy::setSelectedTextRangeCallback(const CppArgumentList&argume nts, CppVariant* result)
936 {
937 result->setNull();
938 if (arguments.size() != 2 || !arguments[0].isNumber() || !arguments[1].isNum ber())
939 return;
940
941 int selectionStart = arguments[0].toInt32();
942 int selectionEnd = selectionStart + arguments[1].toInt32();
943 accessibilityObject().setSelectedTextRange(selectionStart, selectionEnd);
944 }
945
946 void WebAXObjectProxy::isAttributeSettableCallback(const CppArgumentList& argume nts, CppVariant* result)
947 {
948 if (arguments.size() < 1 && !arguments[0].isString()) {
949 result->setNull();
950 return;
951 }
952
953 string attribute = arguments[0].toString();
954 bool settable = false;
955 if (attribute == "AXValue")
956 settable = accessibilityObject().canSetValueAttribute();
957 result->set(settable);
958 }
959
960 void WebAXObjectProxy::isPressActionSupportedCallback(const CppArgumentList&, Cp pVariant* result)
961 {
962 result->set(accessibilityObject().canPress());
963 }
964
965 void WebAXObjectProxy::isIncrementActionSupportedCallback(const CppArgumentList& , CppVariant* result)
966 {
967 result->set(accessibilityObject().canIncrement());
968 }
969
970 void WebAXObjectProxy::isDecrementActionSupportedCallback(const CppArgumentList& , CppVariant* result)
971 {
972 result->set(accessibilityObject().canDecrement());
973 }
974
975 void WebAXObjectProxy::parentElementCallback(const CppArgumentList&, CppVariant* result)
976 {
977 WebAXObject parentObject = accessibilityObject().parentObject();
978 while (parentObject.accessibilityIsIgnored())
979 parentObject = parentObject.parentObject();
980 WebAXObjectProxy* parent = m_factory->getOrCreate(parentObject);
981 if (!parent) {
982 result->setNull();
983 return;
984 }
985
986 result->set(*(parent->getAsCppVariant()));
987 }
988
989 void WebAXObjectProxy::incrementCallback(const CppArgumentList&, CppVariant* res ult)
990 {
991 accessibilityObject().increment();
992 result->setNull();
993 }
994
995 void WebAXObjectProxy::decrementCallback(const CppArgumentList&, CppVariant* res ult)
996 {
997 accessibilityObject().decrement();
998 result->setNull();
999 }
1000
1001 void WebAXObjectProxy::showMenuCallback(const CppArgumentList&, CppVariant* resu lt)
1002 {
1003 result->setNull();
1004 }
1005
1006 void WebAXObjectProxy::pressCallback(const CppArgumentList&, CppVariant* result)
1007 {
1008 accessibilityObject().press();
1009 result->setNull();
1010 }
1011
1012 void WebAXObjectProxy::isEqualCallback(const CppArgumentList& arguments, CppVari ant* result)
1013 {
1014 if (arguments.size() < 1 || !arguments[0].isObject()) {
1015 result->setNull();
1016 return;
1017 }
1018
1019 result->set(arguments[0].isEqual(*getAsCppVariant()));
1020 }
1021
1022 void WebAXObjectProxy::addNotificationListenerCallback(const CppArgumentList& ar guments, CppVariant* result)
1023 {
1024 if (arguments.size() < 1 || !arguments[0].isObject()) {
1025 result->setNull();
1026 return;
1027 }
1028
1029 m_notificationCallbacks.push_back(arguments[0]);
1030 result->setNull();
1031 }
1032
1033 void WebAXObjectProxy::removeNotificationListenerCallback(const CppArgumentList& , CppVariant* result)
1034 {
1035 // FIXME: Implement this.
1036 result->setNull();
1037 }
1038
1039 void WebAXObjectProxy::takeFocusCallback(const CppArgumentList&, CppVariant* res ult)
1040 {
1041 accessibilityObject().setFocused(true);
1042 result->setNull();
1043 }
1044
1045 void WebAXObjectProxy::scrollToMakeVisibleCallback(const CppArgumentList&, CppVa riant* result)
1046 {
1047 accessibilityObject().scrollToMakeVisible();
1048 result->setNull();
1049 }
1050
1051 void WebAXObjectProxy::scrollToMakeVisibleWithSubFocusCallback(const CppArgument List& arguments, CppVariant* result)
1052 {
1053 result->setNull();
1054
1055 if (arguments.size() != 4
1056 || !arguments[0].isNumber()
1057 || !arguments[1].isNumber()
1058 || !arguments[2].isNumber()
1059 || !arguments[3].isNumber())
1060 return;
1061
1062 int x = arguments[0].toInt32();
1063 int y = arguments[1].toInt32();
1064 int width = arguments[2].toInt32();
1065 int height = arguments[3].toInt32();
1066 accessibilityObject().scrollToMakeVisibleWithSubFocus(WebRect(x, y, width, h eight));
1067 result->setNull();
1068 }
1069
1070 void WebAXObjectProxy::scrollToGlobalPointCallback(const CppArgumentList& argume nts, CppVariant* result)
1071 {
1072 result->setNull();
1073
1074 if (arguments.size() != 2
1075 || !arguments[0].isNumber()
1076 || !arguments[1].isNumber())
1077 return;
1078
1079 int x = arguments[0].toInt32();
1080 int y = arguments[1].toInt32();
1081
1082 accessibilityObject().scrollToGlobalPoint(WebPoint(x, y));
1083 result->setNull();
1084 }
1085
1086 void WebAXObjectProxy::wordStartCallback(const CppArgumentList& arguments, CppVa riant* result)
1087 {
1088 result->setNull();
1089
1090 if (arguments.size() != 1 || !arguments[0].isNumber())
1091 return;
1092
1093 if (accessibilityObject().role() != WebAXRoleStaticText)
1094 return;
1095
1096 int characterIndex = arguments[0].toInt32();
1097 int wordStart, wordEnd;
1098 getBoundariesForOneWord(accessibilityObject(), characterIndex, wordStart, wo rdEnd);
1099 result->set(wordStart);
1100 }
1101
1102 void WebAXObjectProxy::wordEndCallback(const CppArgumentList& arguments, CppVari ant* result)
1103 {
1104 result->setNull();
1105
1106 if (arguments.size() != 1 || !arguments[0].isNumber())
1107 return;
1108
1109 if (accessibilityObject().role() != WebAXRoleStaticText)
1110 return;
1111
1112 int characterIndex = arguments[0].toInt32();
1113 int wordStart, wordEnd;
1114 getBoundariesForOneWord(accessibilityObject(), characterIndex, wordStart, wo rdEnd);
1115 result->set(wordEnd);
1116 }
1117
1118 void WebAXObjectProxy::fallbackCallback(const CppArgumentList &, CppVariant* res ult)
1119 {
1120 result->setNull();
1121 }
1122
1123 RootWebAXObjectProxy::RootWebAXObjectProxy(const WebAXObject &object, Factory *f actory)
1124 : WebAXObjectProxy(object, factory) { }
1125
1126 WebAXObjectProxy* RootWebAXObjectProxy::getChildAtIndex(unsigned index)
1127 {
1128 if (index)
1129 return 0;
1130
1131 return factory()->getOrCreate(accessibilityObject());
1132 }
1133
1134 bool RootWebAXObjectProxy::isRoot() const
1135 {
1136 return true;
1137 }
1138
1139 WebAXObjectProxyList::WebAXObjectProxyList()
1140 {
1141 }
1142
1143 WebAXObjectProxyList::~WebAXObjectProxyList()
1144 {
1145 clear();
1146 }
1147
1148 void WebAXObjectProxyList::clear()
1149 {
1150 for (ElementList::iterator i = m_elements.begin(); i != m_elements.end(); ++ i)
1151 delete (*i);
1152 m_elements.clear();
1153 }
1154
1155 WebAXObjectProxy* WebAXObjectProxyList::getOrCreate(const WebAXObject& object)
1156 {
1157 if (object.isNull())
1158 return 0;
1159
1160 size_t elementCount = m_elements.size();
1161 for (size_t i = 0; i < elementCount; i++) {
1162 if (m_elements[i]->isEqual(object))
1163 return m_elements[i];
1164 }
1165
1166 WebAXObjectProxy* element = new WebAXObjectProxy(object, this);
1167 m_elements.push_back(element);
1168 return element;
1169 }
1170
1171 WebAXObjectProxy* WebAXObjectProxyList::createRoot(const WebAXObject& object)
1172 {
1173 WebAXObjectProxy* element = new RootWebAXObjectProxy(object, this);
1174 m_elements.push_back(element);
1175 return element;
1176 }
1177
1178 }
OLDNEW
« no previous file with comments | « content/shell/renderer/test_runner/WebAXObjectProxy.h ('k') | content/shell/renderer/test_runner/WebTestProxy.cpp » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698