OLD | NEW |
1 /* | 1 /* |
2 * Copyright (C) 2014, Google Inc. All rights reserved. | 2 * Copyright (C) 2014, Google Inc. All rights reserved. |
3 * | 3 * |
4 * Redistribution and use in source and binary forms, with or without | 4 * Redistribution and use in source and binary forms, with or without |
5 * modification, are permitted provided that the following conditions | 5 * modification, are permitted provided that the following conditions |
6 * are met: | 6 * are met: |
7 * | 7 * |
8 * 1. Redistributions of source code must retain the above copyright | 8 * 1. Redistributions of source code must retain the above copyright |
9 * notice, this list of conditions and the following disclaimer. | 9 * notice, this list of conditions and the following disclaimer. |
10 * 2. Redistributions in binary form must reproduce the above copyright | 10 * 2. Redistributions in binary form must reproduce the above copyright |
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
59 #include "modules/accessibility/AXLayoutObject.h" | 59 #include "modules/accessibility/AXLayoutObject.h" |
60 #include "modules/accessibility/AXList.h" | 60 #include "modules/accessibility/AXList.h" |
61 #include "modules/accessibility/AXListBox.h" | 61 #include "modules/accessibility/AXListBox.h" |
62 #include "modules/accessibility/AXListBoxOption.h" | 62 #include "modules/accessibility/AXListBoxOption.h" |
63 #include "modules/accessibility/AXMediaControls.h" | 63 #include "modules/accessibility/AXMediaControls.h" |
64 #include "modules/accessibility/AXMenuList.h" | 64 #include "modules/accessibility/AXMenuList.h" |
65 #include "modules/accessibility/AXMenuListOption.h" | 65 #include "modules/accessibility/AXMenuListOption.h" |
66 #include "modules/accessibility/AXMenuListPopup.h" | 66 #include "modules/accessibility/AXMenuListPopup.h" |
67 #include "modules/accessibility/AXProgressIndicator.h" | 67 #include "modules/accessibility/AXProgressIndicator.h" |
68 #include "modules/accessibility/AXSVGRoot.h" | 68 #include "modules/accessibility/AXSVGRoot.h" |
69 #include "modules/accessibility/AXScrollView.h" | |
70 #include "modules/accessibility/AXScrollbar.h" | |
71 #include "modules/accessibility/AXSlider.h" | 69 #include "modules/accessibility/AXSlider.h" |
72 #include "modules/accessibility/AXSpinButton.h" | 70 #include "modules/accessibility/AXSpinButton.h" |
73 #include "modules/accessibility/AXTable.h" | 71 #include "modules/accessibility/AXTable.h" |
74 #include "modules/accessibility/AXTableCell.h" | 72 #include "modules/accessibility/AXTableCell.h" |
75 #include "modules/accessibility/AXTableColumn.h" | 73 #include "modules/accessibility/AXTableColumn.h" |
76 #include "modules/accessibility/AXTableHeaderContainer.h" | 74 #include "modules/accessibility/AXTableHeaderContainer.h" |
77 #include "modules/accessibility/AXTableRow.h" | 75 #include "modules/accessibility/AXTableRow.h" |
78 #include "wtf/PassRefPtr.h" | 76 #include "wtf/PassRefPtr.h" |
79 | 77 |
80 namespace blink { | 78 namespace blink { |
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
178 obj = descendant; | 176 obj = descendant; |
179 } | 177 } |
180 | 178 |
181 // the HTML element, for example, is focusable but has an AX object that is
ignored | 179 // the HTML element, for example, is focusable but has an AX object that is
ignored |
182 if (obj->accessibilityIsIgnored()) | 180 if (obj->accessibilityIsIgnored()) |
183 obj = obj->parentObjectUnignored(); | 181 obj = obj->parentObjectUnignored(); |
184 | 182 |
185 return obj; | 183 return obj; |
186 } | 184 } |
187 | 185 |
188 AXObject* AXObjectCacheImpl::get(Widget* widget) | |
189 { | |
190 if (!widget) | |
191 return 0; | |
192 | |
193 AXID axID = m_widgetObjectMapping.get(widget); | |
194 ASSERT(!HashTraits<AXID>::isDeletedValue(axID)); | |
195 if (!axID) | |
196 return 0; | |
197 | |
198 return m_objects.get(axID); | |
199 } | |
200 | |
201 AXObject* AXObjectCacheImpl::get(LayoutObject* layoutObject) | 186 AXObject* AXObjectCacheImpl::get(LayoutObject* layoutObject) |
202 { | 187 { |
203 if (!layoutObject) | 188 if (!layoutObject) |
204 return 0; | 189 return 0; |
205 | 190 |
206 AXID axID = m_layoutObjectMapping.get(layoutObject); | 191 AXID axID = m_layoutObjectMapping.get(layoutObject); |
207 ASSERT(!HashTraits<AXID>::isDeletedValue(axID)); | 192 ASSERT(!HashTraits<AXID>::isDeletedValue(axID)); |
208 if (!axID) | 193 if (!axID) |
209 return 0; | 194 return 0; |
210 | 195 |
(...skipping 134 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
345 return AXImageMapLink::create(toHTMLAreaElement(node), *this); | 330 return AXImageMapLink::create(toHTMLAreaElement(node), *this); |
346 | 331 |
347 return AXNodeObject::create(node, *this); | 332 return AXNodeObject::create(node, *this); |
348 } | 333 } |
349 | 334 |
350 AXObject* AXObjectCacheImpl::createFromInlineTextBox(AbstractInlineTextBox* inli
neTextBox) | 335 AXObject* AXObjectCacheImpl::createFromInlineTextBox(AbstractInlineTextBox* inli
neTextBox) |
351 { | 336 { |
352 return AXInlineTextBox::create(inlineTextBox, *this); | 337 return AXInlineTextBox::create(inlineTextBox, *this); |
353 } | 338 } |
354 | 339 |
355 AXObject* AXObjectCacheImpl::getOrCreate(Widget* widget) | |
356 { | |
357 if (!widget) | |
358 return 0; | |
359 | |
360 if (AXObject* obj = get(widget)) | |
361 return obj; | |
362 | |
363 AXObject* newObj = nullptr; | |
364 if (widget->isFrameView()) { | |
365 FrameView* frameView = toFrameView(widget); | |
366 | |
367 // Don't create an AXScrollView for a FrameView that isn't attached to a
frame, | |
368 // for example if it's in the process of being disposed. | |
369 if (frameView->frame().view() != frameView || !frameView->layoutView()) | |
370 return 0; | |
371 | |
372 newObj = AXScrollView::create(toFrameView(widget), *this); | |
373 } else if (widget->isScrollbar()) { | |
374 newObj = AXScrollbar::create(toScrollbar(widget), *this); | |
375 } | |
376 | |
377 // Will crash later if we have two objects for the same widget. | |
378 ASSERT(!get(widget)); | |
379 | |
380 // Catch the case if an (unsupported) widget type is used. Only FrameView an
d ScrollBar are supported now. | |
381 ASSERT(newObj); | |
382 if (!newObj) | |
383 return 0; | |
384 | |
385 getAXID(newObj); | |
386 | |
387 m_widgetObjectMapping.set(widget, newObj->axObjectID()); | |
388 m_objects.set(newObj->axObjectID(), newObj); | |
389 newObj->init(); | |
390 return newObj; | |
391 } | |
392 | |
393 AXObject* AXObjectCacheImpl::getOrCreate(Node* node) | 340 AXObject* AXObjectCacheImpl::getOrCreate(Node* node) |
394 { | 341 { |
395 if (!node) | 342 if (!node) |
396 return 0; | 343 return 0; |
397 | 344 |
398 if (AXObject* obj = get(node)) | 345 if (AXObject* obj = get(node)) |
399 return obj; | 346 return obj; |
400 | 347 |
401 // If the node has a layout object, prefer using that as the primary key for
the AXObject, | 348 // If the node has a layout object, prefer using that as the primary key for
the AXObject, |
402 // with the exception of an HTMLAreaElement, which is created based on its n
ode. | 349 // with the exception of an HTMLAreaElement, which is created based on its n
ode. |
(...skipping 68 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
471 newObj->setLastKnownIsIgnoredValue(newObj->accessibilityIsIgnored()); | 418 newObj->setLastKnownIsIgnoredValue(newObj->accessibilityIsIgnored()); |
472 | 419 |
473 return newObj; | 420 return newObj; |
474 } | 421 } |
475 | 422 |
476 AXObject* AXObjectCacheImpl::rootObject() | 423 AXObject* AXObjectCacheImpl::rootObject() |
477 { | 424 { |
478 if (!accessibilityEnabled()) | 425 if (!accessibilityEnabled()) |
479 return 0; | 426 return 0; |
480 | 427 |
481 return getOrCreate(m_document->view()); | 428 return getOrCreate(m_document); |
482 } | 429 } |
483 | 430 |
484 AXObject* AXObjectCacheImpl::getOrCreate(AccessibilityRole role) | 431 AXObject* AXObjectCacheImpl::getOrCreate(AccessibilityRole role) |
485 { | 432 { |
486 AXObject* obj = nullptr; | 433 AXObject* obj = nullptr; |
487 | 434 |
488 // will be filled in... | 435 // will be filled in... |
489 switch (role) { | 436 switch (role) { |
490 case ColumnRole: | 437 case ColumnRole: |
491 obj = AXTableColumn::create(*this); | 438 obj = AXTableColumn::create(*this); |
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
558 AXID axID = m_nodeObjectMapping.get(node); | 505 AXID axID = m_nodeObjectMapping.get(node); |
559 remove(axID); | 506 remove(axID); |
560 m_nodeObjectMapping.remove(node); | 507 m_nodeObjectMapping.remove(node); |
561 | 508 |
562 if (node->layoutObject()) { | 509 if (node->layoutObject()) { |
563 remove(node->layoutObject()); | 510 remove(node->layoutObject()); |
564 return; | 511 return; |
565 } | 512 } |
566 } | 513 } |
567 | 514 |
568 void AXObjectCacheImpl::remove(Widget* view) | |
569 { | |
570 if (!view) | |
571 return; | |
572 | |
573 AXID axID = m_widgetObjectMapping.get(view); | |
574 remove(axID); | |
575 m_widgetObjectMapping.remove(view); | |
576 } | |
577 | |
578 void AXObjectCacheImpl::remove(AbstractInlineTextBox* inlineTextBox) | 515 void AXObjectCacheImpl::remove(AbstractInlineTextBox* inlineTextBox) |
579 { | 516 { |
580 if (!inlineTextBox) | 517 if (!inlineTextBox) |
581 return; | 518 return; |
582 | 519 |
583 AXID axID = m_inlineTextBoxObjectMapping.get(inlineTextBox); | 520 AXID axID = m_inlineTextBoxObjectMapping.get(inlineTextBox); |
584 remove(axID); | 521 remove(axID); |
585 m_inlineTextBoxObjectMapping.remove(inlineTextBox); | 522 m_inlineTextBoxObjectMapping.remove(inlineTextBox); |
586 } | 523 } |
587 | 524 |
(...skipping 376 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
964 | 901 |
965 void AXObjectCacheImpl::listboxActiveIndexChanged(HTMLSelectElement* select) | 902 void AXObjectCacheImpl::listboxActiveIndexChanged(HTMLSelectElement* select) |
966 { | 903 { |
967 AXObject* obj = get(select); | 904 AXObject* obj = get(select); |
968 if (!obj || !obj->isAXListBox()) | 905 if (!obj || !obj->isAXListBox()) |
969 return; | 906 return; |
970 | 907 |
971 toAXListBox(obj)->activeIndexChanged(); | 908 toAXListBox(obj)->activeIndexChanged(); |
972 } | 909 } |
973 | 910 |
974 void AXObjectCacheImpl::handleScrollbarUpdate(FrameView* view) | |
975 { | |
976 if (!view) | |
977 return; | |
978 | |
979 // We don't want to create a scroll view from this method, only update an ex
isting one. | |
980 if (AXObject* scrollViewObject = get(view)) { | |
981 m_modificationCount++; | |
982 scrollViewObject->updateChildrenIfNecessary(); | |
983 } | |
984 } | |
985 | |
986 void AXObjectCacheImpl::handleLayoutComplete(LayoutObject* layoutObject) | 911 void AXObjectCacheImpl::handleLayoutComplete(LayoutObject* layoutObject) |
987 { | 912 { |
988 if (!layoutObject) | 913 if (!layoutObject) |
989 return; | 914 return; |
990 | 915 |
991 m_modificationCount++; | 916 m_modificationCount++; |
992 | 917 |
993 // Create the AXObject if it didn't yet exist - that's always safe at the en
d of a layout, and it | 918 // Create the AXObject if it didn't yet exist - that's always safe at the en
d of a layout, and it |
994 // allows an AX notification to be sent when a page has its first layout, ra
ther than when the | 919 // allows an AX notification to be sent when a page has its first layout, ra
ther than when the |
995 // document first loads. | 920 // document first loads. |
(...skipping 161 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1157 return false; | 1082 return false; |
1158 | 1083 |
1159 if (!node->isElementNode()) | 1084 if (!node->isElementNode()) |
1160 return false; | 1085 return false; |
1161 | 1086 |
1162 return equalIgnoringCase(toElement(node)->getAttribute(aria_hiddenAttr), "fa
lse"); | 1087 return equalIgnoringCase(toElement(node)->getAttribute(aria_hiddenAttr), "fa
lse"); |
1163 } | 1088 } |
1164 | 1089 |
1165 void AXObjectCacheImpl::postPlatformNotification(AXObject* obj, AXNotification n
otification) | 1090 void AXObjectCacheImpl::postPlatformNotification(AXObject* obj, AXNotification n
otification) |
1166 { | 1091 { |
1167 if (obj && obj->isAXScrollbar() && notification == AXValueChanged) { | |
1168 // Send document value changed on scrollbar value changed notification. | |
1169 Scrollbar* scrollBar = toAXScrollbar(obj)->scrollbar(); | |
1170 if (!scrollBar || !scrollBar->parent() || !scrollBar->parent()->isFrameV
iew()) | |
1171 return; | |
1172 Document* document = toFrameView(scrollBar->parent())->frame().document(
); | |
1173 if (document != document->topDocument()) | |
1174 return; | |
1175 obj = get(document->layoutView()); | |
1176 } | |
1177 | |
1178 if (!obj || !obj->document() || !obj->documentFrameView() || !obj->documentF
rameView()->frame().page()) | 1092 if (!obj || !obj->document() || !obj->documentFrameView() || !obj->documentF
rameView()->frame().page()) |
1179 return; | 1093 return; |
1180 | 1094 |
1181 ChromeClient& client = obj->document()->axObjectCacheOwner().page()->chromeC
lient(); | 1095 ChromeClient& client = obj->document()->axObjectCacheOwner().page()->chromeC
lient(); |
1182 | 1096 |
1183 if (notification == AXActiveDescendantChanged | 1097 if (notification == AXActiveDescendantChanged |
1184 && obj->document()->focusedElement() | 1098 && obj->document()->focusedElement() |
1185 && obj->node() == obj->document()->focusedElement()) { | 1099 && obj->node() == obj->document()->focusedElement()) { |
1186 // Calling handleFocusedUIElementChanged will focus the new active | 1100 // Calling handleFocusedUIElementChanged will focus the new active |
1187 // descendant and send the AXFocusedUIElementChanged notification. | 1101 // descendant and send the AXFocusedUIElementChanged notification. |
(...skipping 84 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1272 | 1186 |
1273 void AXObjectCacheImpl::handleScrolledToAnchor(const Node* anchorNode) | 1187 void AXObjectCacheImpl::handleScrolledToAnchor(const Node* anchorNode) |
1274 { | 1188 { |
1275 // The anchor node may not be accessible. Post the notification for the | 1189 // The anchor node may not be accessible. Post the notification for the |
1276 // first accessible object. | 1190 // first accessible object. |
1277 postPlatformNotification(firstAccessibleObjectFromNode(anchorNode), AXScroll
edToAnchor); | 1191 postPlatformNotification(firstAccessibleObjectFromNode(anchorNode), AXScroll
edToAnchor); |
1278 } | 1192 } |
1279 | 1193 |
1280 void AXObjectCacheImpl::handleScrollPositionChanged(FrameView* frameView) | 1194 void AXObjectCacheImpl::handleScrollPositionChanged(FrameView* frameView) |
1281 { | 1195 { |
1282 // Prefer to fire the scroll position changed event on the frame view's chil
d web area, if possible. | 1196 AXObject* targetAXObject = getOrCreate(frameView->frame().document()); |
1283 AXObject* targetAXObject = getOrCreate(frameView); | |
1284 if (targetAXObject && !targetAXObject->children().isEmpty()) | |
1285 targetAXObject = targetAXObject->children()[0].get(); | |
1286 postPlatformNotification(targetAXObject, AXScrollPositionChanged); | 1197 postPlatformNotification(targetAXObject, AXScrollPositionChanged); |
1287 } | 1198 } |
1288 | 1199 |
1289 void AXObjectCacheImpl::handleScrollPositionChanged(LayoutObject* layoutObject) | 1200 void AXObjectCacheImpl::handleScrollPositionChanged(LayoutObject* layoutObject) |
1290 { | 1201 { |
1291 postPlatformNotification(getOrCreate(layoutObject), AXScrollPositionChanged)
; | 1202 postPlatformNotification(getOrCreate(layoutObject), AXScrollPositionChanged)
; |
1292 } | 1203 } |
1293 | 1204 |
1294 const AtomicString& AXObjectCacheImpl::computedRoleForNode(Node* node) | 1205 const AtomicString& AXObjectCacheImpl::computedRoleForNode(Node* node) |
1295 { | 1206 { |
(...skipping 25 matching lines...) Expand all Loading... |
1321 if (!obj) | 1232 if (!obj) |
1322 return; | 1233 return; |
1323 | 1234 |
1324 obj->setElementRect(rect); | 1235 obj->setElementRect(rect); |
1325 } | 1236 } |
1326 | 1237 |
1327 DEFINE_TRACE(AXObjectCacheImpl) | 1238 DEFINE_TRACE(AXObjectCacheImpl) |
1328 { | 1239 { |
1329 #if ENABLE(OILPAN) | 1240 #if ENABLE(OILPAN) |
1330 visitor->trace(m_document); | 1241 visitor->trace(m_document); |
1331 visitor->trace(m_widgetObjectMapping); | |
1332 visitor->trace(m_nodeObjectMapping); | 1242 visitor->trace(m_nodeObjectMapping); |
1333 #endif | 1243 #endif |
1334 | 1244 |
1335 visitor->trace(m_objects); | 1245 visitor->trace(m_objects); |
1336 visitor->trace(m_notificationsToPost); | 1246 visitor->trace(m_notificationsToPost); |
1337 | 1247 |
1338 AXObjectCache::trace(visitor); | 1248 AXObjectCache::trace(visitor); |
1339 } | 1249 } |
1340 | 1250 |
1341 } // namespace blink | 1251 } // namespace blink |
OLD | NEW |