| 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 91 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 102 AXObjectCacheImpl::~AXObjectCacheImpl() { | 102 AXObjectCacheImpl::~AXObjectCacheImpl() { |
| 103 #if DCHECK_IS_ON() | 103 #if DCHECK_IS_ON() |
| 104 DCHECK(has_been_disposed_); | 104 DCHECK(has_been_disposed_); |
| 105 #endif | 105 #endif |
| 106 } | 106 } |
| 107 | 107 |
| 108 void AXObjectCacheImpl::Dispose() { | 108 void AXObjectCacheImpl::Dispose() { |
| 109 notification_post_timer_.Stop(); | 109 notification_post_timer_.Stop(); |
| 110 | 110 |
| 111 for (auto& entry : objects_) { | 111 for (auto& entry : objects_) { |
| 112 AXObjectImpl* obj = entry.value; | 112 AXObject* obj = entry.value; |
| 113 obj->Detach(); | 113 obj->Detach(); |
| 114 RemoveAXID(obj); | 114 RemoveAXID(obj); |
| 115 } | 115 } |
| 116 | 116 |
| 117 #if DCHECK_IS_ON() | 117 #if DCHECK_IS_ON() |
| 118 has_been_disposed_ = true; | 118 has_been_disposed_ = true; |
| 119 #endif | 119 #endif |
| 120 } | 120 } |
| 121 | 121 |
| 122 AXObjectImpl* AXObjectCacheImpl::Root() { | 122 AXObject* AXObjectCacheImpl::Root() { |
| 123 return GetOrCreate(document_); | 123 return GetOrCreate(document_); |
| 124 } | 124 } |
| 125 | 125 |
| 126 AXObjectImpl* AXObjectCacheImpl::FocusedImageMapUIElement( | 126 AXObject* AXObjectCacheImpl::FocusedImageMapUIElement( |
| 127 HTMLAreaElement* area_element) { | 127 HTMLAreaElement* area_element) { |
| 128 // Find the corresponding accessibility object for the HTMLAreaElement. This | 128 // Find the corresponding accessibility object for the HTMLAreaElement. This |
| 129 // should be in the list of children for its corresponding image. | 129 // should be in the list of children for its corresponding image. |
| 130 if (!area_element) | 130 if (!area_element) |
| 131 return 0; | 131 return 0; |
| 132 | 132 |
| 133 HTMLImageElement* image_element = area_element->ImageElement(); | 133 HTMLImageElement* image_element = area_element->ImageElement(); |
| 134 if (!image_element) | 134 if (!image_element) |
| 135 return 0; | 135 return 0; |
| 136 | 136 |
| 137 AXObjectImpl* ax_layout_image = GetOrCreate(image_element); | 137 AXObject* ax_layout_image = GetOrCreate(image_element); |
| 138 if (!ax_layout_image) | 138 if (!ax_layout_image) |
| 139 return 0; | 139 return 0; |
| 140 | 140 |
| 141 const AXObjectImpl::AXObjectVector& image_children = | 141 const AXObject::AXObjectVector& image_children = ax_layout_image->Children(); |
| 142 ax_layout_image->Children(); | |
| 143 unsigned count = image_children.size(); | 142 unsigned count = image_children.size(); |
| 144 for (unsigned k = 0; k < count; ++k) { | 143 for (unsigned k = 0; k < count; ++k) { |
| 145 AXObjectImpl* child = image_children[k]; | 144 AXObject* child = image_children[k]; |
| 146 if (!child->IsImageMapLink()) | 145 if (!child->IsImageMapLink()) |
| 147 continue; | 146 continue; |
| 148 | 147 |
| 149 if (ToAXImageMapLink(child)->AreaElement() == area_element) | 148 if (ToAXImageMapLink(child)->AreaElement() == area_element) |
| 150 return child; | 149 return child; |
| 151 } | 150 } |
| 152 | 151 |
| 153 return 0; | 152 return 0; |
| 154 } | 153 } |
| 155 | 154 |
| 156 AXObjectImpl* AXObjectCacheImpl::FocusedObject() { | 155 AXObject* AXObjectCacheImpl::FocusedObject() { |
| 157 if (!AccessibilityEnabled()) | 156 if (!AccessibilityEnabled()) |
| 158 return nullptr; | 157 return nullptr; |
| 159 | 158 |
| 160 Node* focused_node = document_->FocusedElement(); | 159 Node* focused_node = document_->FocusedElement(); |
| 161 if (!focused_node) | 160 if (!focused_node) |
| 162 focused_node = document_; | 161 focused_node = document_; |
| 163 | 162 |
| 164 // If it's an image map, get the focused link within the image map. | 163 // If it's an image map, get the focused link within the image map. |
| 165 if (isHTMLAreaElement(focused_node)) | 164 if (isHTMLAreaElement(focused_node)) |
| 166 return FocusedImageMapUIElement(toHTMLAreaElement(focused_node)); | 165 return FocusedImageMapUIElement(toHTMLAreaElement(focused_node)); |
| 167 | 166 |
| 168 // See if there's a page popup, for example a calendar picker. | 167 // See if there's a page popup, for example a calendar picker. |
| 169 Element* adjusted_focused_element = document_->AdjustedFocusedElement(); | 168 Element* adjusted_focused_element = document_->AdjustedFocusedElement(); |
| 170 if (isHTMLInputElement(adjusted_focused_element)) { | 169 if (isHTMLInputElement(adjusted_focused_element)) { |
| 171 if (AXObjectImpl* ax_popup = | 170 if (AXObject* ax_popup = |
| 172 toHTMLInputElement(adjusted_focused_element)->PopupRootAXObject()) { | 171 toHTMLInputElement(adjusted_focused_element)->PopupRootAXObject()) { |
| 173 if (Element* focused_element_in_popup = | 172 if (Element* focused_element_in_popup = |
| 174 ax_popup->GetDocument()->FocusedElement()) | 173 ax_popup->GetDocument()->FocusedElement()) |
| 175 focused_node = focused_element_in_popup; | 174 focused_node = focused_element_in_popup; |
| 176 } | 175 } |
| 177 } | 176 } |
| 178 | 177 |
| 179 AXObjectImpl* obj = GetOrCreate(focused_node); | 178 AXObject* obj = GetOrCreate(focused_node); |
| 180 if (!obj) | 179 if (!obj) |
| 181 return nullptr; | 180 return nullptr; |
| 182 | 181 |
| 183 // the HTML element, for example, is focusable but has an AX object that is | 182 // the HTML element, for example, is focusable but has an AX object that is |
| 184 // ignored | 183 // ignored |
| 185 if (obj->AccessibilityIsIgnored()) | 184 if (obj->AccessibilityIsIgnored()) |
| 186 obj = obj->ParentObjectUnignored(); | 185 obj = obj->ParentObjectUnignored(); |
| 187 | 186 |
| 188 return obj; | 187 return obj; |
| 189 } | 188 } |
| 190 | 189 |
| 191 AXObjectImpl* AXObjectCacheImpl::Get(LayoutObject* layout_object) { | 190 AXObject* AXObjectCacheImpl::Get(LayoutObject* layout_object) { |
| 192 if (!layout_object) | 191 if (!layout_object) |
| 193 return 0; | 192 return 0; |
| 194 | 193 |
| 195 AXID ax_id = layout_object_mapping_.at(layout_object); | 194 AXID ax_id = layout_object_mapping_.at(layout_object); |
| 196 DCHECK(!HashTraits<AXID>::IsDeletedValue(ax_id)); | 195 DCHECK(!HashTraits<AXID>::IsDeletedValue(ax_id)); |
| 197 if (!ax_id) | 196 if (!ax_id) |
| 198 return 0; | 197 return 0; |
| 199 | 198 |
| 200 return objects_.at(ax_id); | 199 return objects_.at(ax_id); |
| 201 } | 200 } |
| 202 | 201 |
| 203 // Returns true if |node| is an <option> element and its parent <select> | 202 // Returns true if |node| is an <option> element and its parent <select> |
| 204 // is a menu list (not a list box). | 203 // is a menu list (not a list box). |
| 205 static bool IsMenuListOption(Node* node) { | 204 static bool IsMenuListOption(Node* node) { |
| 206 if (!isHTMLOptionElement(node)) | 205 if (!isHTMLOptionElement(node)) |
| 207 return false; | 206 return false; |
| 208 HTMLSelectElement* select = toHTMLOptionElement(node)->OwnerSelectElement(); | 207 HTMLSelectElement* select = toHTMLOptionElement(node)->OwnerSelectElement(); |
| 209 if (!select) | 208 if (!select) |
| 210 return false; | 209 return false; |
| 211 LayoutObject* layout_object = select->GetLayoutObject(); | 210 LayoutObject* layout_object = select->GetLayoutObject(); |
| 212 return layout_object && layout_object->IsMenuList(); | 211 return layout_object && layout_object->IsMenuList(); |
| 213 } | 212 } |
| 214 | 213 |
| 215 AXObjectImpl* AXObjectCacheImpl::Get(Node* node) { | 214 AXObject* AXObjectCacheImpl::Get(Node* node) { |
| 216 if (!node) | 215 if (!node) |
| 217 return 0; | 216 return 0; |
| 218 | 217 |
| 219 // Menu list option and HTML area elements are indexed by DOM node, never by | 218 // Menu list option and HTML area elements are indexed by DOM node, never by |
| 220 // layout object. | 219 // layout object. |
| 221 LayoutObject* layout_object = node->GetLayoutObject(); | 220 LayoutObject* layout_object = node->GetLayoutObject(); |
| 222 if (IsMenuListOption(node) || isHTMLAreaElement(node)) | 221 if (IsMenuListOption(node) || isHTMLAreaElement(node)) |
| 223 layout_object = nullptr; | 222 layout_object = nullptr; |
| 224 | 223 |
| 225 AXID layout_id = layout_object ? layout_object_mapping_.at(layout_object) : 0; | 224 AXID layout_id = layout_object ? layout_object_mapping_.at(layout_object) : 0; |
| (...skipping 12 matching lines...) Expand all Loading... |
| 238 | 237 |
| 239 if (layout_id) | 238 if (layout_id) |
| 240 return objects_.at(layout_id); | 239 return objects_.at(layout_id); |
| 241 | 240 |
| 242 if (!node_id) | 241 if (!node_id) |
| 243 return 0; | 242 return 0; |
| 244 | 243 |
| 245 return objects_.at(node_id); | 244 return objects_.at(node_id); |
| 246 } | 245 } |
| 247 | 246 |
| 248 AXObjectImpl* AXObjectCacheImpl::Get(AbstractInlineTextBox* inline_text_box) { | 247 AXObject* AXObjectCacheImpl::Get(AbstractInlineTextBox* inline_text_box) { |
| 249 if (!inline_text_box) | 248 if (!inline_text_box) |
| 250 return 0; | 249 return 0; |
| 251 | 250 |
| 252 AXID ax_id = inline_text_box_object_mapping_.at(inline_text_box); | 251 AXID ax_id = inline_text_box_object_mapping_.at(inline_text_box); |
| 253 DCHECK(!HashTraits<AXID>::IsDeletedValue(ax_id)); | 252 DCHECK(!HashTraits<AXID>::IsDeletedValue(ax_id)); |
| 254 if (!ax_id) | 253 if (!ax_id) |
| 255 return 0; | 254 return 0; |
| 256 | 255 |
| 257 return objects_.at(ax_id); | 256 return objects_.at(ax_id); |
| 258 } | 257 } |
| 259 | 258 |
| 260 // FIXME: This probably belongs on Node. | 259 // FIXME: This probably belongs on Node. |
| 261 // FIXME: This should take a const char*, but one caller passes nullAtom. | 260 // FIXME: This should take a const char*, but one caller passes nullAtom. |
| 262 bool NodeHasRole(Node* node, const String& role) { | 261 bool NodeHasRole(Node* node, const String& role) { |
| 263 if (!node || !node->IsElementNode()) | 262 if (!node || !node->IsElementNode()) |
| 264 return false; | 263 return false; |
| 265 | 264 |
| 266 return EqualIgnoringASCIICase(ToElement(node)->getAttribute(roleAttr), role); | 265 return EqualIgnoringASCIICase(ToElement(node)->getAttribute(roleAttr), role); |
| 267 } | 266 } |
| 268 | 267 |
| 269 AXObjectImpl* AXObjectCacheImpl::CreateFromRenderer( | 268 AXObject* AXObjectCacheImpl::CreateFromRenderer(LayoutObject* layout_object) { |
| 270 LayoutObject* layout_object) { | |
| 271 // FIXME: How could layoutObject->node() ever not be an Element? | 269 // FIXME: How could layoutObject->node() ever not be an Element? |
| 272 Node* node = layout_object->GetNode(); | 270 Node* node = layout_object->GetNode(); |
| 273 | 271 |
| 274 // If the node is aria role="list" or the aria role is empty and its a | 272 // If the node is aria role="list" or the aria role is empty and its a |
| 275 // ul/ol/dl type (it shouldn't be a list if aria says otherwise). | 273 // ul/ol/dl type (it shouldn't be a list if aria says otherwise). |
| 276 if (NodeHasRole(node, "list") || NodeHasRole(node, "directory") || | 274 if (NodeHasRole(node, "list") || NodeHasRole(node, "directory") || |
| 277 (NodeHasRole(node, g_null_atom) && | 275 (NodeHasRole(node, g_null_atom) && |
| 278 (isHTMLUListElement(node) || isHTMLOListElement(node) || | 276 (isHTMLUListElement(node) || isHTMLOListElement(node) || |
| 279 isHTMLDListElement(node)))) | 277 isHTMLDListElement(node)))) |
| 280 return AXList::Create(layout_object, *this); | 278 return AXList::Create(layout_object, *this); |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 322 return AXProgressIndicator::Create(ToLayoutProgress(css_box), *this); | 320 return AXProgressIndicator::Create(ToLayoutProgress(css_box), *this); |
| 323 | 321 |
| 324 // input type=range | 322 // input type=range |
| 325 if (css_box->IsSlider()) | 323 if (css_box->IsSlider()) |
| 326 return AXSlider::Create(ToLayoutSlider(css_box), *this); | 324 return AXSlider::Create(ToLayoutSlider(css_box), *this); |
| 327 } | 325 } |
| 328 | 326 |
| 329 return AXLayoutObject::Create(layout_object, *this); | 327 return AXLayoutObject::Create(layout_object, *this); |
| 330 } | 328 } |
| 331 | 329 |
| 332 AXObjectImpl* AXObjectCacheImpl::CreateFromNode(Node* node) { | 330 AXObject* AXObjectCacheImpl::CreateFromNode(Node* node) { |
| 333 if (IsMenuListOption(node)) | 331 if (IsMenuListOption(node)) |
| 334 return AXMenuListOption::Create(toHTMLOptionElement(node), *this); | 332 return AXMenuListOption::Create(toHTMLOptionElement(node), *this); |
| 335 | 333 |
| 336 if (isHTMLAreaElement(node)) | 334 if (isHTMLAreaElement(node)) |
| 337 return AXImageMapLink::Create(toHTMLAreaElement(node), *this); | 335 return AXImageMapLink::Create(toHTMLAreaElement(node), *this); |
| 338 | 336 |
| 339 return AXNodeObject::Create(node, *this); | 337 return AXNodeObject::Create(node, *this); |
| 340 } | 338 } |
| 341 | 339 |
| 342 AXObjectImpl* AXObjectCacheImpl::CreateFromInlineTextBox( | 340 AXObject* AXObjectCacheImpl::CreateFromInlineTextBox( |
| 343 AbstractInlineTextBox* inline_text_box) { | 341 AbstractInlineTextBox* inline_text_box) { |
| 344 return AXInlineTextBox::Create(inline_text_box, *this); | 342 return AXInlineTextBox::Create(inline_text_box, *this); |
| 345 } | 343 } |
| 346 | 344 |
| 347 AXObjectImpl* AXObjectCacheImpl::GetOrCreate(Node* node) { | 345 AXObject* AXObjectCacheImpl::GetOrCreate(Node* node) { |
| 348 if (!node) | 346 if (!node) |
| 349 return 0; | 347 return 0; |
| 350 | 348 |
| 351 if (AXObjectImpl* obj = Get(node)) | 349 if (AXObject* obj = Get(node)) |
| 352 return obj; | 350 return obj; |
| 353 | 351 |
| 354 // If the node has a layout object, prefer using that as the primary key for | 352 // If the node has a layout object, prefer using that as the primary key for |
| 355 // the AXObjectImpl, with the exception of an HTMLAreaElement, which is | 353 // the AXObject, with the exception of an HTMLAreaElement, which is created |
| 356 // created based on its node. | 354 // based on its node. |
| 357 if (node->GetLayoutObject() && !isHTMLAreaElement(node)) | 355 if (node->GetLayoutObject() && !isHTMLAreaElement(node)) |
| 358 return GetOrCreate(node->GetLayoutObject()); | 356 return GetOrCreate(node->GetLayoutObject()); |
| 359 | 357 |
| 360 if (!node->parentElement()) | 358 if (!node->parentElement()) |
| 361 return 0; | 359 return 0; |
| 362 | 360 |
| 363 if (isHTMLHeadElement(node)) | 361 if (isHTMLHeadElement(node)) |
| 364 return 0; | 362 return 0; |
| 365 | 363 |
| 366 AXObjectImpl* new_obj = CreateFromNode(node); | 364 AXObject* new_obj = CreateFromNode(node); |
| 367 | 365 |
| 368 // Will crash later if we have two objects for the same node. | 366 // Will crash later if we have two objects for the same node. |
| 369 DCHECK(!Get(node)); | 367 DCHECK(!Get(node)); |
| 370 | 368 |
| 371 const AXID ax_id = GetOrCreateAXID(new_obj); | 369 const AXID ax_id = GetOrCreateAXID(new_obj); |
| 372 | 370 |
| 373 node_object_mapping_.Set(node, ax_id); | 371 node_object_mapping_.Set(node, ax_id); |
| 374 new_obj->Init(); | 372 new_obj->Init(); |
| 375 new_obj->SetLastKnownIsIgnoredValue(new_obj->AccessibilityIsIgnored()); | 373 new_obj->SetLastKnownIsIgnoredValue(new_obj->AccessibilityIsIgnored()); |
| 376 | 374 |
| 377 if (node->IsElementNode()) | 375 if (node->IsElementNode()) |
| 378 UpdateTreeIfElementIdIsAriaOwned(ToElement(node)); | 376 UpdateTreeIfElementIdIsAriaOwned(ToElement(node)); |
| 379 | 377 |
| 380 return new_obj; | 378 return new_obj; |
| 381 } | 379 } |
| 382 | 380 |
| 383 AXObjectImpl* AXObjectCacheImpl::GetOrCreate(LayoutObject* layout_object) { | 381 AXObject* AXObjectCacheImpl::GetOrCreate(LayoutObject* layout_object) { |
| 384 if (!layout_object) | 382 if (!layout_object) |
| 385 return 0; | 383 return 0; |
| 386 | 384 |
| 387 if (AXObjectImpl* obj = Get(layout_object)) | 385 if (AXObject* obj = Get(layout_object)) |
| 388 return obj; | 386 return obj; |
| 389 | 387 |
| 390 AXObjectImpl* new_obj = CreateFromRenderer(layout_object); | 388 AXObject* new_obj = CreateFromRenderer(layout_object); |
| 391 | 389 |
| 392 // Will crash later if we have two objects for the same layoutObject. | 390 // Will crash later if we have two objects for the same layoutObject. |
| 393 DCHECK(!Get(layout_object)); | 391 DCHECK(!Get(layout_object)); |
| 394 | 392 |
| 395 const AXID axid = GetOrCreateAXID(new_obj); | 393 const AXID axid = GetOrCreateAXID(new_obj); |
| 396 | 394 |
| 397 layout_object_mapping_.Set(layout_object, axid); | 395 layout_object_mapping_.Set(layout_object, axid); |
| 398 new_obj->Init(); | 396 new_obj->Init(); |
| 399 new_obj->SetLastKnownIsIgnoredValue(new_obj->AccessibilityIsIgnored()); | 397 new_obj->SetLastKnownIsIgnoredValue(new_obj->AccessibilityIsIgnored()); |
| 400 | 398 |
| 401 return new_obj; | 399 return new_obj; |
| 402 } | 400 } |
| 403 | 401 |
| 404 AXObjectImpl* AXObjectCacheImpl::GetOrCreate( | 402 AXObject* AXObjectCacheImpl::GetOrCreate( |
| 405 AbstractInlineTextBox* inline_text_box) { | 403 AbstractInlineTextBox* inline_text_box) { |
| 406 if (!inline_text_box) | 404 if (!inline_text_box) |
| 407 return 0; | 405 return 0; |
| 408 | 406 |
| 409 if (AXObjectImpl* obj = Get(inline_text_box)) | 407 if (AXObject* obj = Get(inline_text_box)) |
| 410 return obj; | 408 return obj; |
| 411 | 409 |
| 412 AXObjectImpl* new_obj = CreateFromInlineTextBox(inline_text_box); | 410 AXObject* new_obj = CreateFromInlineTextBox(inline_text_box); |
| 413 | 411 |
| 414 // Will crash later if we have two objects for the same inlineTextBox. | 412 // Will crash later if we have two objects for the same inlineTextBox. |
| 415 DCHECK(!Get(inline_text_box)); | 413 DCHECK(!Get(inline_text_box)); |
| 416 | 414 |
| 417 const AXID axid = GetOrCreateAXID(new_obj); | 415 const AXID axid = GetOrCreateAXID(new_obj); |
| 418 | 416 |
| 419 inline_text_box_object_mapping_.Set(inline_text_box, axid); | 417 inline_text_box_object_mapping_.Set(inline_text_box, axid); |
| 420 new_obj->Init(); | 418 new_obj->Init(); |
| 421 new_obj->SetLastKnownIsIgnoredValue(new_obj->AccessibilityIsIgnored()); | 419 new_obj->SetLastKnownIsIgnoredValue(new_obj->AccessibilityIsIgnored()); |
| 422 | 420 |
| 423 return new_obj; | 421 return new_obj; |
| 424 } | 422 } |
| 425 | 423 |
| 426 AXObjectImpl* AXObjectCacheImpl::GetOrCreate(AccessibilityRole role) { | 424 AXObject* AXObjectCacheImpl::GetOrCreate(AccessibilityRole role) { |
| 427 AXObjectImpl* obj = nullptr; | 425 AXObject* obj = nullptr; |
| 428 | 426 |
| 429 // will be filled in... | 427 // will be filled in... |
| 430 switch (role) { | 428 switch (role) { |
| 431 case kColumnRole: | 429 case kColumnRole: |
| 432 obj = AXTableColumn::Create(*this); | 430 obj = AXTableColumn::Create(*this); |
| 433 break; | 431 break; |
| 434 case kTableHeaderContainerRole: | 432 case kTableHeaderContainerRole: |
| 435 obj = AXTableHeaderContainer::Create(*this); | 433 obj = AXTableHeaderContainer::Create(*this); |
| 436 break; | 434 break; |
| 437 case kSliderThumbRole: | 435 case kSliderThumbRole: |
| (...skipping 19 matching lines...) Expand all Loading... |
| 457 | 455 |
| 458 obj->Init(); | 456 obj->Init(); |
| 459 return obj; | 457 return obj; |
| 460 } | 458 } |
| 461 | 459 |
| 462 void AXObjectCacheImpl::Remove(AXID ax_id) { | 460 void AXObjectCacheImpl::Remove(AXID ax_id) { |
| 463 if (!ax_id) | 461 if (!ax_id) |
| 464 return; | 462 return; |
| 465 | 463 |
| 466 // first fetch object to operate some cleanup functions on it | 464 // first fetch object to operate some cleanup functions on it |
| 467 AXObjectImpl* obj = objects_.at(ax_id); | 465 AXObject* obj = objects_.at(ax_id); |
| 468 if (!obj) | 466 if (!obj) |
| 469 return; | 467 return; |
| 470 | 468 |
| 471 obj->Detach(); | 469 obj->Detach(); |
| 472 RemoveAXID(obj); | 470 RemoveAXID(obj); |
| 473 | 471 |
| 474 // finally remove the object | 472 // finally remove the object |
| 475 if (!objects_.Take(ax_id)) | 473 if (!objects_.Take(ax_id)) |
| 476 return; | 474 return; |
| 477 | 475 |
| (...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 519 do { | 517 do { |
| 520 ++obj_id; | 518 ++obj_id; |
| 521 } while (!obj_id || HashTraits<AXID>::IsDeletedValue(obj_id) || | 519 } while (!obj_id || HashTraits<AXID>::IsDeletedValue(obj_id) || |
| 522 ids_in_use_.Contains(obj_id)); | 520 ids_in_use_.Contains(obj_id)); |
| 523 | 521 |
| 524 last_used_id = obj_id; | 522 last_used_id = obj_id; |
| 525 | 523 |
| 526 return obj_id; | 524 return obj_id; |
| 527 } | 525 } |
| 528 | 526 |
| 529 AXID AXObjectCacheImpl::GetOrCreateAXID(AXObjectImpl* obj) { | 527 AXID AXObjectCacheImpl::GetOrCreateAXID(AXObject* obj) { |
| 530 // check for already-assigned ID | 528 // check for already-assigned ID |
| 531 const AXID existing_axid = obj->AxObjectID(); | 529 const AXID existing_axid = obj->AxObjectID(); |
| 532 if (existing_axid) { | 530 if (existing_axid) { |
| 533 DCHECK(ids_in_use_.Contains(existing_axid)); | 531 DCHECK(ids_in_use_.Contains(existing_axid)); |
| 534 return existing_axid; | 532 return existing_axid; |
| 535 } | 533 } |
| 536 | 534 |
| 537 const AXID new_axid = GenerateAXID(); | 535 const AXID new_axid = GenerateAXID(); |
| 538 | 536 |
| 539 ids_in_use_.insert(new_axid); | 537 ids_in_use_.insert(new_axid); |
| 540 obj->SetAXObjectID(new_axid); | 538 obj->SetAXObjectID(new_axid); |
| 541 objects_.Set(new_axid, obj); | 539 objects_.Set(new_axid, obj); |
| 542 | 540 |
| 543 return new_axid; | 541 return new_axid; |
| 544 } | 542 } |
| 545 | 543 |
| 546 void AXObjectCacheImpl::RemoveAXID(AXObjectImpl* object) { | 544 void AXObjectCacheImpl::RemoveAXID(AXObject* object) { |
| 547 if (!object) | 545 if (!object) |
| 548 return; | 546 return; |
| 549 | 547 |
| 550 AXID obj_id = object->AxObjectID(); | 548 AXID obj_id = object->AxObjectID(); |
| 551 if (!obj_id) | 549 if (!obj_id) |
| 552 return; | 550 return; |
| 553 DCHECK(!HashTraits<AXID>::IsDeletedValue(obj_id)); | 551 DCHECK(!HashTraits<AXID>::IsDeletedValue(obj_id)); |
| 554 DCHECK(ids_in_use_.Contains(obj_id)); | 552 DCHECK(ids_in_use_.Contains(obj_id)); |
| 555 object->SetAXObjectID(0); | 553 object->SetAXObjectID(0); |
| 556 ids_in_use_.erase(obj_id); | 554 ids_in_use_.erase(obj_id); |
| 557 | 555 |
| 558 if (aria_owner_to_children_mapping_.Contains(obj_id)) { | 556 if (aria_owner_to_children_mapping_.Contains(obj_id)) { |
| 559 Vector<AXID> child_axi_ds = aria_owner_to_children_mapping_.at(obj_id); | 557 Vector<AXID> child_axi_ds = aria_owner_to_children_mapping_.at(obj_id); |
| 560 for (size_t i = 0; i < child_axi_ds.size(); ++i) | 558 for (size_t i = 0; i < child_axi_ds.size(); ++i) |
| 561 aria_owned_child_to_owner_mapping_.erase(child_axi_ds[i]); | 559 aria_owned_child_to_owner_mapping_.erase(child_axi_ds[i]); |
| 562 aria_owner_to_children_mapping_.erase(obj_id); | 560 aria_owner_to_children_mapping_.erase(obj_id); |
| 563 } | 561 } |
| 564 aria_owned_child_to_owner_mapping_.erase(obj_id); | 562 aria_owned_child_to_owner_mapping_.erase(obj_id); |
| 565 aria_owned_child_to_real_parent_mapping_.erase(obj_id); | 563 aria_owned_child_to_real_parent_mapping_.erase(obj_id); |
| 566 aria_owner_to_ids_mapping_.erase(obj_id); | 564 aria_owner_to_ids_mapping_.erase(obj_id); |
| 567 } | 565 } |
| 568 | 566 |
| 569 void AXObjectCacheImpl::SelectionChanged(Node* node) { | 567 void AXObjectCacheImpl::SelectionChanged(Node* node) { |
| 570 // Find the nearest ancestor that already has an accessibility object, since | 568 // Find the nearest ancestor that already has an accessibility object, since |
| 571 // we might be in the middle of a layout. | 569 // we might be in the middle of a layout. |
| 572 while (node) { | 570 while (node) { |
| 573 if (AXObjectImpl* obj = Get(node)) { | 571 if (AXObject* obj = Get(node)) { |
| 574 obj->SelectionChanged(); | 572 obj->SelectionChanged(); |
| 575 return; | 573 return; |
| 576 } | 574 } |
| 577 node = node->parentNode(); | 575 node = node->parentNode(); |
| 578 } | 576 } |
| 579 } | 577 } |
| 580 | 578 |
| 581 void AXObjectCacheImpl::TextChanged(Node* node) { | 579 void AXObjectCacheImpl::TextChanged(Node* node) { |
| 582 TextChanged(GetOrCreate(node)); | 580 TextChanged(GetOrCreate(node)); |
| 583 } | 581 } |
| 584 | 582 |
| 585 void AXObjectCacheImpl::TextChanged(LayoutObject* layout_object) { | 583 void AXObjectCacheImpl::TextChanged(LayoutObject* layout_object) { |
| 586 TextChanged(GetOrCreate(layout_object)); | 584 TextChanged(GetOrCreate(layout_object)); |
| 587 } | 585 } |
| 588 | 586 |
| 589 void AXObjectCacheImpl::TextChanged(AXObjectImpl* obj) { | 587 void AXObjectCacheImpl::TextChanged(AXObject* obj) { |
| 590 if (!obj) | 588 if (!obj) |
| 591 return; | 589 return; |
| 592 | 590 |
| 593 bool parent_already_exists = obj->ParentObjectIfExists(); | 591 bool parent_already_exists = obj->ParentObjectIfExists(); |
| 594 obj->TextChanged(); | 592 obj->TextChanged(); |
| 595 PostNotification(obj, AXObjectCacheImpl::kAXTextChanged); | 593 PostNotification(obj, AXObjectCacheImpl::kAXTextChanged); |
| 596 if (parent_already_exists) | 594 if (parent_already_exists) |
| 597 obj->NotifyIfIgnoredValueChanged(); | 595 obj->NotifyIfIgnoredValueChanged(); |
| 598 } | 596 } |
| 599 | 597 |
| 600 void AXObjectCacheImpl::UpdateCacheAfterNodeIsAttached(Node* node) { | 598 void AXObjectCacheImpl::UpdateCacheAfterNodeIsAttached(Node* node) { |
| 601 // Calling get() will update the AX object if we had an AXNodeObject but now | 599 // Calling get() will update the AX object if we had an AXNodeObject but now |
| 602 // we need an AXLayoutObject, because it was reparented to a location outside | 600 // we need an AXLayoutObject, because it was reparented to a location outside |
| 603 // of a canvas. | 601 // of a canvas. |
| 604 Get(node); | 602 Get(node); |
| 605 if (node->IsElementNode()) | 603 if (node->IsElementNode()) |
| 606 UpdateTreeIfElementIdIsAriaOwned(ToElement(node)); | 604 UpdateTreeIfElementIdIsAriaOwned(ToElement(node)); |
| 607 } | 605 } |
| 608 | 606 |
| 609 void AXObjectCacheImpl::ChildrenChanged(Node* node) { | 607 void AXObjectCacheImpl::ChildrenChanged(Node* node) { |
| 610 ChildrenChanged(Get(node)); | 608 ChildrenChanged(Get(node)); |
| 611 } | 609 } |
| 612 | 610 |
| 613 void AXObjectCacheImpl::ChildrenChanged(LayoutObject* layout_object) { | 611 void AXObjectCacheImpl::ChildrenChanged(LayoutObject* layout_object) { |
| 614 ChildrenChanged(Get(layout_object)); | 612 ChildrenChanged(Get(layout_object)); |
| 615 } | 613 } |
| 616 | 614 |
| 617 void AXObjectCacheImpl::ChildrenChanged(AXObjectImpl* obj) { | 615 void AXObjectCacheImpl::ChildrenChanged(AXObject* obj) { |
| 618 if (!obj) | 616 if (!obj) |
| 619 return; | 617 return; |
| 620 | 618 |
| 621 obj->ChildrenChanged(); | 619 obj->ChildrenChanged(); |
| 622 } | 620 } |
| 623 | 621 |
| 624 void AXObjectCacheImpl::NotificationPostTimerFired(TimerBase*) { | 622 void AXObjectCacheImpl::NotificationPostTimerFired(TimerBase*) { |
| 625 notification_post_timer_.Stop(); | 623 notification_post_timer_.Stop(); |
| 626 | 624 |
| 627 unsigned i = 0, count = notifications_to_post_.size(); | 625 unsigned i = 0, count = notifications_to_post_.size(); |
| 628 for (i = 0; i < count; ++i) { | 626 for (i = 0; i < count; ++i) { |
| 629 AXObjectImpl* obj = notifications_to_post_[i].first; | 627 AXObject* obj = notifications_to_post_[i].first; |
| 630 | 628 |
| 631 if (!obj->AxObjectID()) | 629 if (!obj->AxObjectID()) |
| 632 continue; | 630 continue; |
| 633 | 631 |
| 634 if (obj->IsDetached()) | 632 if (obj->IsDetached()) |
| 635 continue; | 633 continue; |
| 636 | 634 |
| 637 #if DCHECK_IS_ON() | 635 #if DCHECK_IS_ON() |
| 638 // Make sure none of the layout views are in the process of being layed out. | 636 // Make sure none of the layout views are in the process of being layed out. |
| 639 // Notifications should only be sent after the layoutObject has finished | 637 // Notifications should only be sent after the layoutObject has finished |
| (...skipping 23 matching lines...) Expand all Loading... |
| 663 PostNotification(Get(layout_object), notification); | 661 PostNotification(Get(layout_object), notification); |
| 664 } | 662 } |
| 665 | 663 |
| 666 void AXObjectCacheImpl::PostNotification(Node* node, | 664 void AXObjectCacheImpl::PostNotification(Node* node, |
| 667 AXNotification notification) { | 665 AXNotification notification) { |
| 668 if (!node) | 666 if (!node) |
| 669 return; | 667 return; |
| 670 PostNotification(Get(node), notification); | 668 PostNotification(Get(node), notification); |
| 671 } | 669 } |
| 672 | 670 |
| 673 void AXObjectCacheImpl::PostNotification(AXObjectImpl* object, | 671 void AXObjectCacheImpl::PostNotification(AXObject* object, |
| 674 AXNotification notification) { | 672 AXNotification notification) { |
| 675 if (!object) | 673 if (!object) |
| 676 return; | 674 return; |
| 677 | 675 |
| 678 modification_count_++; | 676 modification_count_++; |
| 679 notifications_to_post_.push_back(std::make_pair(object, notification)); | 677 notifications_to_post_.push_back(std::make_pair(object, notification)); |
| 680 if (!notification_post_timer_.IsActive()) | 678 if (!notification_post_timer_.IsActive()) |
| 681 notification_post_timer_.StartOneShot(0, BLINK_FROM_HERE); | 679 notification_post_timer_.StartOneShot(0, BLINK_FROM_HERE); |
| 682 } | 680 } |
| 683 | 681 |
| 684 bool AXObjectCacheImpl::IsAriaOwned(const AXObjectImpl* child) const { | 682 bool AXObjectCacheImpl::IsAriaOwned(const AXObject* child) const { |
| 685 return aria_owned_child_to_owner_mapping_.Contains(child->AxObjectID()); | 683 return aria_owned_child_to_owner_mapping_.Contains(child->AxObjectID()); |
| 686 } | 684 } |
| 687 | 685 |
| 688 AXObjectImpl* AXObjectCacheImpl::GetAriaOwnedParent( | 686 AXObject* AXObjectCacheImpl::GetAriaOwnedParent(const AXObject* child) const { |
| 689 const AXObjectImpl* child) const { | |
| 690 return ObjectFromAXID( | 687 return ObjectFromAXID( |
| 691 aria_owned_child_to_owner_mapping_.at(child->AxObjectID())); | 688 aria_owned_child_to_owner_mapping_.at(child->AxObjectID())); |
| 692 } | 689 } |
| 693 | 690 |
| 694 void AXObjectCacheImpl::UpdateAriaOwns( | 691 void AXObjectCacheImpl::UpdateAriaOwns( |
| 695 const AXObjectImpl* owner, | 692 const AXObject* owner, |
| 696 const Vector<String>& id_vector, | 693 const Vector<String>& id_vector, |
| 697 HeapVector<Member<AXObjectImpl>>& owned_children) { | 694 HeapVector<Member<AXObject>>& owned_children) { |
| 698 // | 695 // |
| 699 // Update the map from the AXID of this element to the ids of the owned | 696 // Update the map from the AXID of this element to the ids of the owned |
| 700 // children, and the reverse map from ids to possible AXID owners. | 697 // children, and the reverse map from ids to possible AXID owners. |
| 701 // | 698 // |
| 702 | 699 |
| 703 HashSet<String> current_ids = | 700 HashSet<String> current_ids = |
| 704 aria_owner_to_ids_mapping_.at(owner->AxObjectID()); | 701 aria_owner_to_ids_mapping_.at(owner->AxObjectID()); |
| 705 HashSet<String> new_ids; | 702 HashSet<String> new_ids; |
| 706 bool ids_changed = false; | 703 bool ids_changed = false; |
| 707 for (const String& id : id_vector) { | 704 for (const String& id : id_vector) { |
| (...skipping 29 matching lines...) Expand all Loading... |
| 737 // | 734 // |
| 738 | 735 |
| 739 // Figure out the children that are owned by this object and are in the tree. | 736 // Figure out the children that are owned by this object and are in the tree. |
| 740 TreeScope& scope = owner->GetNode()->GetTreeScope(); | 737 TreeScope& scope = owner->GetNode()->GetTreeScope(); |
| 741 Vector<AXID> new_child_axi_ds; | 738 Vector<AXID> new_child_axi_ds; |
| 742 for (const String& id_name : id_vector) { | 739 for (const String& id_name : id_vector) { |
| 743 Element* element = scope.getElementById(AtomicString(id_name)); | 740 Element* element = scope.getElementById(AtomicString(id_name)); |
| 744 if (!element) | 741 if (!element) |
| 745 continue; | 742 continue; |
| 746 | 743 |
| 747 AXObjectImpl* child = GetOrCreate(element); | 744 AXObject* child = GetOrCreate(element); |
| 748 if (!child) | 745 if (!child) |
| 749 continue; | 746 continue; |
| 750 | 747 |
| 751 // If this child is already aria-owned by a different owner, continue. | 748 // If this child is already aria-owned by a different owner, continue. |
| 752 // It's an author error if this happens and we don't worry about which of | 749 // It's an author error if this happens and we don't worry about which of |
| 753 // the two owners wins ownership of the child, as long as only one of them | 750 // the two owners wins ownership of the child, as long as only one of them |
| 754 // does. | 751 // does. |
| 755 if (IsAriaOwned(child) && GetAriaOwnedParent(child) != owner) | 752 if (IsAriaOwned(child) && GetAriaOwnedParent(child) != owner) |
| 756 continue; | 753 continue; |
| 757 | 754 |
| 758 // You can't own yourself! | 755 // You can't own yourself! |
| 759 if (child == owner) | 756 if (child == owner) |
| 760 continue; | 757 continue; |
| 761 | 758 |
| 762 // Walk up the parents of the owner object, make sure that this child | 759 // Walk up the parents of the owner object, make sure that this child |
| 763 // doesn't appear there, as that would create a cycle. | 760 // doesn't appear there, as that would create a cycle. |
| 764 bool found_cycle = false; | 761 bool found_cycle = false; |
| 765 for (AXObjectImpl* parent = owner->ParentObject(); parent && !found_cycle; | 762 for (AXObject* parent = owner->ParentObject(); parent && !found_cycle; |
| 766 parent = parent->ParentObject()) { | 763 parent = parent->ParentObject()) { |
| 767 if (parent == child) | 764 if (parent == child) |
| 768 found_cycle = true; | 765 found_cycle = true; |
| 769 } | 766 } |
| 770 if (found_cycle) | 767 if (found_cycle) |
| 771 continue; | 768 continue; |
| 772 | 769 |
| 773 new_child_axi_ds.push_back(child->AxObjectID()); | 770 new_child_axi_ds.push_back(child->AxObjectID()); |
| 774 owned_children.push_back(child); | 771 owned_children.push_back(child); |
| 775 } | 772 } |
| (...skipping 11 matching lines...) Expand all Loading... |
| 787 same = false; | 784 same = false; |
| 788 } | 785 } |
| 789 } | 786 } |
| 790 if (same) | 787 if (same) |
| 791 return; | 788 return; |
| 792 | 789 |
| 793 // The list of owned children has changed. Even if they were just reordered, | 790 // The list of owned children has changed. Even if they were just reordered, |
| 794 // to be safe and handle all cases we remove all of the current owned children | 791 // to be safe and handle all cases we remove all of the current owned children |
| 795 // and add the new list of owned children. | 792 // and add the new list of owned children. |
| 796 for (size_t i = 0; i < current_child_axi_ds.size(); ++i) { | 793 for (size_t i = 0; i < current_child_axi_ds.size(); ++i) { |
| 797 // Find the AXObjectImpl for the child that this owner no longer owns. | 794 // Find the AXObject for the child that this owner no longer owns. |
| 798 AXID removed_child_id = current_child_axi_ds[i]; | 795 AXID removed_child_id = current_child_axi_ds[i]; |
| 799 AXObjectImpl* removed_child = ObjectFromAXID(removed_child_id); | 796 AXObject* removed_child = ObjectFromAXID(removed_child_id); |
| 800 | 797 |
| 801 // It's possible that this child has already been owned by some other owner, | 798 // It's possible that this child has already been owned by some other owner, |
| 802 // in which case we don't need to do anything. | 799 // in which case we don't need to do anything. |
| 803 if (removed_child && GetAriaOwnedParent(removed_child) != owner) | 800 if (removed_child && GetAriaOwnedParent(removed_child) != owner) |
| 804 continue; | 801 continue; |
| 805 | 802 |
| 806 // Remove it from the child -> owner mapping so it's not owned by this owner | 803 // Remove it from the child -> owner mapping so it's not owned by this owner |
| 807 // anymore. | 804 // anymore. |
| 808 aria_owned_child_to_owner_mapping_.erase(removed_child_id); | 805 aria_owned_child_to_owner_mapping_.erase(removed_child_id); |
| 809 | 806 |
| 810 if (removed_child) { | 807 if (removed_child) { |
| 811 // If the child still exists, find its "real" parent, and reparent it back | 808 // If the child still exists, find its "real" parent, and reparent it back |
| 812 // to its real parent in the tree by detaching it from its current parent | 809 // to its real parent in the tree by detaching it from its current parent |
| 813 // and calling childrenChanged on its real parent. | 810 // and calling childrenChanged on its real parent. |
| 814 removed_child->DetachFromParent(); | 811 removed_child->DetachFromParent(); |
| 815 AXID real_parent_id = | 812 AXID real_parent_id = |
| 816 aria_owned_child_to_real_parent_mapping_.at(removed_child_id); | 813 aria_owned_child_to_real_parent_mapping_.at(removed_child_id); |
| 817 AXObjectImpl* real_parent = ObjectFromAXID(real_parent_id); | 814 AXObject* real_parent = ObjectFromAXID(real_parent_id); |
| 818 ChildrenChanged(real_parent); | 815 ChildrenChanged(real_parent); |
| 819 } | 816 } |
| 820 | 817 |
| 821 // Remove the child -> original parent mapping too since this object has now | 818 // Remove the child -> original parent mapping too since this object has now |
| 822 // been reparented back to its original parent. | 819 // been reparented back to its original parent. |
| 823 aria_owned_child_to_real_parent_mapping_.erase(removed_child_id); | 820 aria_owned_child_to_real_parent_mapping_.erase(removed_child_id); |
| 824 } | 821 } |
| 825 | 822 |
| 826 for (size_t i = 0; i < new_child_axi_ds.size(); ++i) { | 823 for (size_t i = 0; i < new_child_axi_ds.size(); ++i) { |
| 827 // Find the AXObjectImpl for the child that will now be a child of this | 824 // Find the AXObject for the child that will now be a child of this owner. |
| 828 // owner. | |
| 829 AXID added_child_id = new_child_axi_ds[i]; | 825 AXID added_child_id = new_child_axi_ds[i]; |
| 830 AXObjectImpl* added_child = ObjectFromAXID(added_child_id); | 826 AXObject* added_child = ObjectFromAXID(added_child_id); |
| 831 | 827 |
| 832 // Add this child to the mapping from child to owner. | 828 // Add this child to the mapping from child to owner. |
| 833 aria_owned_child_to_owner_mapping_.Set(added_child_id, owner->AxObjectID()); | 829 aria_owned_child_to_owner_mapping_.Set(added_child_id, owner->AxObjectID()); |
| 834 | 830 |
| 835 // Add its parent object to a mapping from child to real parent. If later | 831 // Add its parent object to a mapping from child to real parent. If later |
| 836 // this owner doesn't own this child anymore, we need to return it to its | 832 // this owner doesn't own this child anymore, we need to return it to its |
| 837 // original parent. | 833 // original parent. |
| 838 AXObjectImpl* original_parent = added_child->ParentObject(); | 834 AXObject* original_parent = added_child->ParentObject(); |
| 839 aria_owned_child_to_real_parent_mapping_.Set(added_child_id, | 835 aria_owned_child_to_real_parent_mapping_.Set(added_child_id, |
| 840 original_parent->AxObjectID()); | 836 original_parent->AxObjectID()); |
| 841 | 837 |
| 842 // Now detach the object from its original parent and call childrenChanged | 838 // Now detach the object from its original parent and call childrenChanged |
| 843 // on the original parent so that it can recompute its list of children. | 839 // on the original parent so that it can recompute its list of children. |
| 844 added_child->DetachFromParent(); | 840 added_child->DetachFromParent(); |
| 845 ChildrenChanged(original_parent); | 841 ChildrenChanged(original_parent); |
| 846 } | 842 } |
| 847 | 843 |
| 848 // Finally, update the mapping from the owner to the list of child IDs. | 844 // Finally, update the mapping from the owner to the list of child IDs. |
| 849 aria_owner_to_children_mapping_.Set(owner->AxObjectID(), new_child_axi_ds); | 845 aria_owner_to_children_mapping_.Set(owner->AxObjectID(), new_child_axi_ds); |
| 850 } | 846 } |
| 851 | 847 |
| 852 void AXObjectCacheImpl::UpdateTreeIfElementIdIsAriaOwned(Element* element) { | 848 void AXObjectCacheImpl::UpdateTreeIfElementIdIsAriaOwned(Element* element) { |
| 853 if (!element->HasID()) | 849 if (!element->HasID()) |
| 854 return; | 850 return; |
| 855 | 851 |
| 856 String id = element->GetIdAttribute(); | 852 String id = element->GetIdAttribute(); |
| 857 HashSet<AXID>* owners = id_to_aria_owners_mapping_.at(id); | 853 HashSet<AXID>* owners = id_to_aria_owners_mapping_.at(id); |
| 858 if (!owners) | 854 if (!owners) |
| 859 return; | 855 return; |
| 860 | 856 |
| 861 AXObjectImpl* ax_element = GetOrCreate(element); | 857 AXObject* ax_element = GetOrCreate(element); |
| 862 if (!ax_element) | 858 if (!ax_element) |
| 863 return; | 859 return; |
| 864 | 860 |
| 865 // If it's already owned, call childrenChanged on the owner to make sure it's | 861 // If it's already owned, call childrenChanged on the owner to make sure it's |
| 866 // still an owner. | 862 // still an owner. |
| 867 if (IsAriaOwned(ax_element)) { | 863 if (IsAriaOwned(ax_element)) { |
| 868 AXObjectImpl* owned_parent = GetAriaOwnedParent(ax_element); | 864 AXObject* owned_parent = GetAriaOwnedParent(ax_element); |
| 869 DCHECK(owned_parent); | 865 DCHECK(owned_parent); |
| 870 ChildrenChanged(owned_parent); | 866 ChildrenChanged(owned_parent); |
| 871 return; | 867 return; |
| 872 } | 868 } |
| 873 | 869 |
| 874 // If it's not already owned, check the possible owners based on our mapping | 870 // If it's not already owned, check the possible owners based on our mapping |
| 875 // from ids to elements that have that id listed in their aria-owns attribute. | 871 // from ids to elements that have that id listed in their aria-owns attribute. |
| 876 for (const auto& ax_id : *owners) { | 872 for (const auto& ax_id : *owners) { |
| 877 AXObjectImpl* owner = ObjectFromAXID(ax_id); | 873 AXObject* owner = ObjectFromAXID(ax_id); |
| 878 if (owner) | 874 if (owner) |
| 879 ChildrenChanged(owner); | 875 ChildrenChanged(owner); |
| 880 } | 876 } |
| 881 } | 877 } |
| 882 | 878 |
| 883 void AXObjectCacheImpl::CheckedStateChanged(Node* node) { | 879 void AXObjectCacheImpl::CheckedStateChanged(Node* node) { |
| 884 PostNotification(node, AXObjectCacheImpl::kAXCheckedStateChanged); | 880 PostNotification(node, AXObjectCacheImpl::kAXCheckedStateChanged); |
| 885 } | 881 } |
| 886 | 882 |
| 887 void AXObjectCacheImpl::ListboxOptionStateChanged(HTMLOptionElement* option) { | 883 void AXObjectCacheImpl::ListboxOptionStateChanged(HTMLOptionElement* option) { |
| 888 PostNotification(option, kAXCheckedStateChanged); | 884 PostNotification(option, kAXCheckedStateChanged); |
| 889 } | 885 } |
| 890 | 886 |
| 891 void AXObjectCacheImpl::ListboxSelectedChildrenChanged( | 887 void AXObjectCacheImpl::ListboxSelectedChildrenChanged( |
| 892 HTMLSelectElement* select) { | 888 HTMLSelectElement* select) { |
| 893 PostNotification(select, kAXSelectedChildrenChanged); | 889 PostNotification(select, kAXSelectedChildrenChanged); |
| 894 } | 890 } |
| 895 | 891 |
| 896 void AXObjectCacheImpl::ListboxActiveIndexChanged(HTMLSelectElement* select) { | 892 void AXObjectCacheImpl::ListboxActiveIndexChanged(HTMLSelectElement* select) { |
| 897 AXObjectImpl* obj = Get(select); | 893 AXObject* obj = Get(select); |
| 898 if (!obj || !obj->IsAXListBox()) | 894 if (!obj || !obj->IsAXListBox()) |
| 899 return; | 895 return; |
| 900 | 896 |
| 901 ToAXListBox(obj)->ActiveIndexChanged(); | 897 ToAXListBox(obj)->ActiveIndexChanged(); |
| 902 } | 898 } |
| 903 | 899 |
| 904 void AXObjectCacheImpl::RadiobuttonRemovedFromGroup( | 900 void AXObjectCacheImpl::RadiobuttonRemovedFromGroup( |
| 905 HTMLInputElement* group_member) { | 901 HTMLInputElement* group_member) { |
| 906 AXObjectImpl* obj = Get(group_member); | 902 AXObject* obj = Get(group_member); |
| 907 if (!obj || !obj->IsAXRadioInput()) | 903 if (!obj || !obj->IsAXRadioInput()) |
| 908 return; | 904 return; |
| 909 | 905 |
| 910 // The 'posInSet' and 'setSize' attributes should be updated from the first | 906 // The 'posInSet' and 'setSize' attributes should be updated from the first |
| 911 // node, as the removed node is already detached from tree. | 907 // node, as the removed node is already detached from tree. |
| 912 HTMLInputElement* first_radio = | 908 HTMLInputElement* first_radio = |
| 913 ToAXRadioInput(obj)->FindFirstRadioButtonInGroup(group_member); | 909 ToAXRadioInput(obj)->FindFirstRadioButtonInGroup(group_member); |
| 914 AXObjectImpl* first_obj = Get(first_radio); | 910 AXObject* first_obj = Get(first_radio); |
| 915 if (!first_obj || !first_obj->IsAXRadioInput()) | 911 if (!first_obj || !first_obj->IsAXRadioInput()) |
| 916 return; | 912 return; |
| 917 | 913 |
| 918 ToAXRadioInput(first_obj)->UpdatePosAndSetSize(1); | 914 ToAXRadioInput(first_obj)->UpdatePosAndSetSize(1); |
| 919 PostNotification(first_obj, kAXAriaAttributeChanged); | 915 PostNotification(first_obj, kAXAriaAttributeChanged); |
| 920 ToAXRadioInput(first_obj)->RequestUpdateToNextNode(true); | 916 ToAXRadioInput(first_obj)->RequestUpdateToNextNode(true); |
| 921 } | 917 } |
| 922 | 918 |
| 923 void AXObjectCacheImpl::HandleLayoutComplete(LayoutObject* layout_object) { | 919 void AXObjectCacheImpl::HandleLayoutComplete(LayoutObject* layout_object) { |
| 924 if (!layout_object) | 920 if (!layout_object) |
| 925 return; | 921 return; |
| 926 | 922 |
| 927 modification_count_++; | 923 modification_count_++; |
| 928 | 924 |
| 929 // Create the AXObjectImpl if it didn't yet exist - that's always safe at the | 925 // Create the AXObject if it didn't yet exist - that's always safe at the end |
| 930 // end of a layout, and it allows an AX notification to be sent when a page | 926 // of a layout, and it allows an AX notification to be sent when a page has |
| 931 // has its first layout, rather than when the document first loads. | 927 // its first layout, rather than when the document first loads. |
| 932 if (AXObjectImpl* obj = GetOrCreate(layout_object)) | 928 if (AXObject* obj = GetOrCreate(layout_object)) |
| 933 PostNotification(obj, kAXLayoutComplete); | 929 PostNotification(obj, kAXLayoutComplete); |
| 934 } | 930 } |
| 935 | 931 |
| 936 void AXObjectCacheImpl::HandleClicked(Node* node) { | 932 void AXObjectCacheImpl::HandleClicked(Node* node) { |
| 937 if (AXObjectImpl* obj = GetOrCreate(node)) | 933 if (AXObject* obj = GetOrCreate(node)) |
| 938 PostNotification(obj, kAXClicked); | 934 PostNotification(obj, kAXClicked); |
| 939 } | 935 } |
| 940 | 936 |
| 941 void AXObjectCacheImpl::HandleAriaExpandedChange(Node* node) { | 937 void AXObjectCacheImpl::HandleAriaExpandedChange(Node* node) { |
| 942 if (AXObjectImpl* obj = GetOrCreate(node)) | 938 if (AXObject* obj = GetOrCreate(node)) |
| 943 obj->HandleAriaExpandedChanged(); | 939 obj->HandleAriaExpandedChanged(); |
| 944 } | 940 } |
| 945 | 941 |
| 946 void AXObjectCacheImpl::HandleAriaSelectedChanged(Node* node) { | 942 void AXObjectCacheImpl::HandleAriaSelectedChanged(Node* node) { |
| 947 AXObjectImpl* obj = Get(node); | 943 AXObject* obj = Get(node); |
| 948 if (!obj) | 944 if (!obj) |
| 949 return; | 945 return; |
| 950 | 946 |
| 951 PostNotification(obj, kAXCheckedStateChanged); | 947 PostNotification(obj, kAXCheckedStateChanged); |
| 952 | 948 |
| 953 AXObjectImpl* listbox = obj->ParentObjectUnignored(); | 949 AXObject* listbox = obj->ParentObjectUnignored(); |
| 954 if (listbox && listbox->RoleValue() == kListBoxRole) | 950 if (listbox && listbox->RoleValue() == kListBoxRole) |
| 955 PostNotification(listbox, kAXSelectedChildrenChanged); | 951 PostNotification(listbox, kAXSelectedChildrenChanged); |
| 956 } | 952 } |
| 957 | 953 |
| 958 void AXObjectCacheImpl::HandleActiveDescendantChanged(Node* node) { | 954 void AXObjectCacheImpl::HandleActiveDescendantChanged(Node* node) { |
| 959 // Changing the active descendant should trigger recomputing all | 955 // Changing the active descendant should trigger recomputing all |
| 960 // cached values even if it doesn't result in a notification, because | 956 // cached values even if it doesn't result in a notification, because |
| 961 // it can affect what's focusable or not. | 957 // it can affect what's focusable or not. |
| 962 modification_count_++; | 958 modification_count_++; |
| 963 | 959 |
| 964 if (AXObjectImpl* obj = GetOrCreate(node)) | 960 if (AXObject* obj = GetOrCreate(node)) |
| 965 obj->HandleActiveDescendantChanged(); | 961 obj->HandleActiveDescendantChanged(); |
| 966 } | 962 } |
| 967 | 963 |
| 968 void AXObjectCacheImpl::HandleAriaRoleChanged(Node* node) { | 964 void AXObjectCacheImpl::HandleAriaRoleChanged(Node* node) { |
| 969 if (AXObjectImpl* obj = GetOrCreate(node)) { | 965 if (AXObject* obj = GetOrCreate(node)) { |
| 970 obj->UpdateAccessibilityRole(); | 966 obj->UpdateAccessibilityRole(); |
| 971 modification_count_++; | 967 modification_count_++; |
| 972 obj->NotifyIfIgnoredValueChanged(); | 968 obj->NotifyIfIgnoredValueChanged(); |
| 973 } | 969 } |
| 974 } | 970 } |
| 975 | 971 |
| 976 void AXObjectCacheImpl::HandleAttributeChanged(const QualifiedName& attr_name, | 972 void AXObjectCacheImpl::HandleAttributeChanged(const QualifiedName& attr_name, |
| 977 Element* element) { | 973 Element* element) { |
| 978 if (attr_name == roleAttr) | 974 if (attr_name == roleAttr) |
| 979 HandleAriaRoleChanged(element); | 975 HandleAriaRoleChanged(element); |
| (...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1017 void AXObjectCacheImpl::InlineTextBoxesUpdated( | 1013 void AXObjectCacheImpl::InlineTextBoxesUpdated( |
| 1018 LineLayoutItem line_layout_item) { | 1014 LineLayoutItem line_layout_item) { |
| 1019 if (!InlineTextBoxAccessibilityEnabled()) | 1015 if (!InlineTextBoxAccessibilityEnabled()) |
| 1020 return; | 1016 return; |
| 1021 | 1017 |
| 1022 LayoutObject* layout_object = | 1018 LayoutObject* layout_object = |
| 1023 LineLayoutAPIShim::LayoutObjectFrom(line_layout_item); | 1019 LineLayoutAPIShim::LayoutObjectFrom(line_layout_item); |
| 1024 | 1020 |
| 1025 // Only update if the accessibility object already exists and it's | 1021 // Only update if the accessibility object already exists and it's |
| 1026 // not already marked as dirty. | 1022 // not already marked as dirty. |
| 1027 if (AXObjectImpl* obj = Get(layout_object)) { | 1023 if (AXObject* obj = Get(layout_object)) { |
| 1028 if (!obj->NeedsToUpdateChildren()) { | 1024 if (!obj->NeedsToUpdateChildren()) { |
| 1029 obj->SetNeedsToUpdateChildren(); | 1025 obj->SetNeedsToUpdateChildren(); |
| 1030 PostNotification(layout_object, kAXChildrenChanged); | 1026 PostNotification(layout_object, kAXChildrenChanged); |
| 1031 } | 1027 } |
| 1032 } | 1028 } |
| 1033 } | 1029 } |
| 1034 | 1030 |
| 1035 Settings* AXObjectCacheImpl::GetSettings() { | 1031 Settings* AXObjectCacheImpl::GetSettings() { |
| 1036 return document_->GetSettings(); | 1032 return document_->GetSettings(); |
| 1037 } | 1033 } |
| (...skipping 18 matching lines...) Expand all Loading... |
| 1056 node->IsElementNode() ? ToElement(node) : node->parentElement(); | 1052 node->IsElementNode() ? ToElement(node) : node->parentElement(); |
| 1057 | 1053 |
| 1058 for (; element; element = element->parentElement()) { | 1054 for (; element; element = element->parentElement()) { |
| 1059 if (NodeIsTextControl(element)) | 1055 if (NodeIsTextControl(element)) |
| 1060 result = element; | 1056 result = element; |
| 1061 } | 1057 } |
| 1062 | 1058 |
| 1063 return result; | 1059 return result; |
| 1064 } | 1060 } |
| 1065 | 1061 |
| 1066 AXObjectImpl* AXObjectCacheImpl::FirstAccessibleObjectFromNode( | 1062 AXObject* AXObjectCacheImpl::FirstAccessibleObjectFromNode(const Node* node) { |
| 1067 const Node* node) { | |
| 1068 if (!node) | 1063 if (!node) |
| 1069 return 0; | 1064 return 0; |
| 1070 | 1065 |
| 1071 AXObjectImpl* accessible_object = GetOrCreate(node->GetLayoutObject()); | 1066 AXObject* accessible_object = GetOrCreate(node->GetLayoutObject()); |
| 1072 while (accessible_object && accessible_object->AccessibilityIsIgnored()) { | 1067 while (accessible_object && accessible_object->AccessibilityIsIgnored()) { |
| 1073 node = NodeTraversal::Next(*node); | 1068 node = NodeTraversal::Next(*node); |
| 1074 | 1069 |
| 1075 while (node && !node->GetLayoutObject()) | 1070 while (node && !node->GetLayoutObject()) |
| 1076 node = NodeTraversal::NextSkippingChildren(*node); | 1071 node = NodeTraversal::NextSkippingChildren(*node); |
| 1077 | 1072 |
| 1078 if (!node) | 1073 if (!node) |
| 1079 return 0; | 1074 return 0; |
| 1080 | 1075 |
| 1081 accessible_object = GetOrCreate(node->GetLayoutObject()); | 1076 accessible_object = GetOrCreate(node->GetLayoutObject()); |
| 1082 } | 1077 } |
| 1083 | 1078 |
| 1084 return accessible_object; | 1079 return accessible_object; |
| 1085 } | 1080 } |
| 1086 | 1081 |
| 1087 bool AXObjectCacheImpl::NodeIsTextControl(const Node* node) { | 1082 bool AXObjectCacheImpl::NodeIsTextControl(const Node* node) { |
| 1088 if (!node) | 1083 if (!node) |
| 1089 return false; | 1084 return false; |
| 1090 | 1085 |
| 1091 const AXObjectImpl* ax_object = GetOrCreate(const_cast<Node*>(node)); | 1086 const AXObject* ax_object = GetOrCreate(const_cast<Node*>(node)); |
| 1092 return ax_object && ax_object->IsTextControl(); | 1087 return ax_object && ax_object->IsTextControl(); |
| 1093 } | 1088 } |
| 1094 | 1089 |
| 1095 bool IsNodeAriaVisible(Node* node) { | 1090 bool IsNodeAriaVisible(Node* node) { |
| 1096 if (!node) | 1091 if (!node) |
| 1097 return false; | 1092 return false; |
| 1098 | 1093 |
| 1099 if (!node->IsElementNode()) | 1094 if (!node->IsElementNode()) |
| 1100 return false; | 1095 return false; |
| 1101 | 1096 |
| 1102 return EqualIgnoringASCIICase(ToElement(node)->getAttribute(aria_hiddenAttr), | 1097 return EqualIgnoringASCIICase(ToElement(node)->getAttribute(aria_hiddenAttr), |
| 1103 "false"); | 1098 "false"); |
| 1104 } | 1099 } |
| 1105 | 1100 |
| 1106 void AXObjectCacheImpl::PostPlatformNotification(AXObjectImpl* obj, | 1101 void AXObjectCacheImpl::PostPlatformNotification(AXObject* obj, |
| 1107 AXNotification notification) { | 1102 AXNotification notification) { |
| 1108 if (!obj || !obj->GetDocument() || !obj->DocumentFrameView() || | 1103 if (!obj || !obj->GetDocument() || !obj->DocumentFrameView() || |
| 1109 !obj->DocumentFrameView()->GetFrame().GetPage()) | 1104 !obj->DocumentFrameView()->GetFrame().GetPage()) |
| 1110 return; | 1105 return; |
| 1111 | 1106 |
| 1112 ChromeClient& client = | 1107 ChromeClient& client = |
| 1113 obj->GetDocument()->AxObjectCacheOwner().GetPage()->GetChromeClient(); | 1108 obj->GetDocument()->AxObjectCacheOwner().GetPage()->GetChromeClient(); |
| 1114 client.PostAccessibilityNotification(obj, notification); | 1109 client.PostAccessibilityNotification(obj, notification); |
| 1115 } | 1110 } |
| 1116 | 1111 |
| 1117 void AXObjectCacheImpl::HandleFocusedUIElementChanged(Node* old_focused_node, | 1112 void AXObjectCacheImpl::HandleFocusedUIElementChanged(Node* old_focused_node, |
| 1118 Node* new_focused_node) { | 1113 Node* new_focused_node) { |
| 1119 if (!new_focused_node) | 1114 if (!new_focused_node) |
| 1120 return; | 1115 return; |
| 1121 | 1116 |
| 1122 Page* page = new_focused_node->GetDocument().GetPage(); | 1117 Page* page = new_focused_node->GetDocument().GetPage(); |
| 1123 if (!page) | 1118 if (!page) |
| 1124 return; | 1119 return; |
| 1125 | 1120 |
| 1126 AXObjectImpl* focused_object = this->FocusedObject(); | 1121 AXObject* focused_object = this->FocusedObject(); |
| 1127 if (!focused_object) | 1122 if (!focused_object) |
| 1128 return; | 1123 return; |
| 1129 | 1124 |
| 1130 AXObjectImpl* old_focused_object = Get(old_focused_node); | 1125 AXObject* old_focused_object = Get(old_focused_node); |
| 1131 | 1126 |
| 1132 PostPlatformNotification(old_focused_object, kAXBlur); | 1127 PostPlatformNotification(old_focused_object, kAXBlur); |
| 1133 PostPlatformNotification(focused_object, kAXFocusedUIElementChanged); | 1128 PostPlatformNotification(focused_object, kAXFocusedUIElementChanged); |
| 1134 } | 1129 } |
| 1135 | 1130 |
| 1136 void AXObjectCacheImpl::HandleInitialFocus() { | 1131 void AXObjectCacheImpl::HandleInitialFocus() { |
| 1137 PostNotification(document_, AXObjectCache::kAXFocusedUIElementChanged); | 1132 PostNotification(document_, AXObjectCache::kAXFocusedUIElementChanged); |
| 1138 } | 1133 } |
| 1139 | 1134 |
| 1140 void AXObjectCacheImpl::HandleEditableTextContentChanged(Node* node) { | 1135 void AXObjectCacheImpl::HandleEditableTextContentChanged(Node* node) { |
| 1141 AXObjectImpl* obj = Get(node); | 1136 AXObject* obj = Get(node); |
| 1142 while (obj && !obj->IsNativeTextControl() && !obj->IsNonNativeTextControl()) | 1137 while (obj && !obj->IsNativeTextControl() && !obj->IsNonNativeTextControl()) |
| 1143 obj = obj->ParentObject(); | 1138 obj = obj->ParentObject(); |
| 1144 PostNotification(obj, AXObjectCache::kAXValueChanged); | 1139 PostNotification(obj, AXObjectCache::kAXValueChanged); |
| 1145 } | 1140 } |
| 1146 | 1141 |
| 1147 void AXObjectCacheImpl::HandleTextFormControlChanged(Node* node) { | 1142 void AXObjectCacheImpl::HandleTextFormControlChanged(Node* node) { |
| 1148 HandleEditableTextContentChanged(node); | 1143 HandleEditableTextContentChanged(node); |
| 1149 } | 1144 } |
| 1150 | 1145 |
| 1151 void AXObjectCacheImpl::HandleValueChanged(Node* node) { | 1146 void AXObjectCacheImpl::HandleValueChanged(Node* node) { |
| 1152 PostNotification(node, AXObjectCache::kAXValueChanged); | 1147 PostNotification(node, AXObjectCache::kAXValueChanged); |
| 1153 } | 1148 } |
| 1154 | 1149 |
| 1155 void AXObjectCacheImpl::HandleUpdateActiveMenuOption(LayoutMenuList* menu_list, | 1150 void AXObjectCacheImpl::HandleUpdateActiveMenuOption(LayoutMenuList* menu_list, |
| 1156 int option_index) { | 1151 int option_index) { |
| 1157 AXObjectImpl* obj = Get(menu_list); | 1152 AXObject* obj = Get(menu_list); |
| 1158 if (!obj || !obj->IsMenuList()) | 1153 if (!obj || !obj->IsMenuList()) |
| 1159 return; | 1154 return; |
| 1160 | 1155 |
| 1161 ToAXMenuList(obj)->DidUpdateActiveOption(option_index); | 1156 ToAXMenuList(obj)->DidUpdateActiveOption(option_index); |
| 1162 } | 1157 } |
| 1163 | 1158 |
| 1164 void AXObjectCacheImpl::DidShowMenuListPopup(LayoutMenuList* menu_list) { | 1159 void AXObjectCacheImpl::DidShowMenuListPopup(LayoutMenuList* menu_list) { |
| 1165 AXObjectImpl* obj = Get(menu_list); | 1160 AXObject* obj = Get(menu_list); |
| 1166 if (!obj || !obj->IsMenuList()) | 1161 if (!obj || !obj->IsMenuList()) |
| 1167 return; | 1162 return; |
| 1168 | 1163 |
| 1169 ToAXMenuList(obj)->DidShowPopup(); | 1164 ToAXMenuList(obj)->DidShowPopup(); |
| 1170 } | 1165 } |
| 1171 | 1166 |
| 1172 void AXObjectCacheImpl::DidHideMenuListPopup(LayoutMenuList* menu_list) { | 1167 void AXObjectCacheImpl::DidHideMenuListPopup(LayoutMenuList* menu_list) { |
| 1173 AXObjectImpl* obj = Get(menu_list); | 1168 AXObject* obj = Get(menu_list); |
| 1174 if (!obj || !obj->IsMenuList()) | 1169 if (!obj || !obj->IsMenuList()) |
| 1175 return; | 1170 return; |
| 1176 | 1171 |
| 1177 ToAXMenuList(obj)->DidHidePopup(); | 1172 ToAXMenuList(obj)->DidHidePopup(); |
| 1178 } | 1173 } |
| 1179 | 1174 |
| 1180 void AXObjectCacheImpl::HandleLoadComplete(Document* document) { | 1175 void AXObjectCacheImpl::HandleLoadComplete(Document* document) { |
| 1181 PostNotification(GetOrCreate(document), AXObjectCache::kAXLoadComplete); | 1176 PostNotification(GetOrCreate(document), AXObjectCache::kAXLoadComplete); |
| 1182 } | 1177 } |
| 1183 | 1178 |
| 1184 void AXObjectCacheImpl::HandleLayoutComplete(Document* document) { | 1179 void AXObjectCacheImpl::HandleLayoutComplete(Document* document) { |
| 1185 PostNotification(GetOrCreate(document), AXObjectCache::kAXLayoutComplete); | 1180 PostNotification(GetOrCreate(document), AXObjectCache::kAXLayoutComplete); |
| 1186 } | 1181 } |
| 1187 | 1182 |
| 1188 void AXObjectCacheImpl::HandleScrolledToAnchor(const Node* anchor_node) { | 1183 void AXObjectCacheImpl::HandleScrolledToAnchor(const Node* anchor_node) { |
| 1189 if (!anchor_node) | 1184 if (!anchor_node) |
| 1190 return; | 1185 return; |
| 1191 AXObjectImpl* obj = GetOrCreate(anchor_node->GetLayoutObject()); | 1186 AXObject* obj = GetOrCreate(anchor_node->GetLayoutObject()); |
| 1192 if (!obj) | 1187 if (!obj) |
| 1193 return; | 1188 return; |
| 1194 if (obj->AccessibilityIsIgnored()) | 1189 if (obj->AccessibilityIsIgnored()) |
| 1195 obj = obj->ParentObjectUnignored(); | 1190 obj = obj->ParentObjectUnignored(); |
| 1196 PostPlatformNotification(obj, kAXScrolledToAnchor); | 1191 PostPlatformNotification(obj, kAXScrolledToAnchor); |
| 1197 } | 1192 } |
| 1198 | 1193 |
| 1199 void AXObjectCacheImpl::HandleScrollPositionChanged(FrameView* frame_view) { | 1194 void AXObjectCacheImpl::HandleScrollPositionChanged(FrameView* frame_view) { |
| 1200 AXObjectImpl* target_ax_object = | 1195 AXObject* target_ax_object = |
| 1201 GetOrCreate(frame_view->GetFrame().GetDocument()); | 1196 GetOrCreate(frame_view->GetFrame().GetDocument()); |
| 1202 PostPlatformNotification(target_ax_object, kAXScrollPositionChanged); | 1197 PostPlatformNotification(target_ax_object, kAXScrollPositionChanged); |
| 1203 } | 1198 } |
| 1204 | 1199 |
| 1205 void AXObjectCacheImpl::HandleScrollPositionChanged( | 1200 void AXObjectCacheImpl::HandleScrollPositionChanged( |
| 1206 LayoutObject* layout_object) { | 1201 LayoutObject* layout_object) { |
| 1207 PostPlatformNotification(GetOrCreate(layout_object), | 1202 PostPlatformNotification(GetOrCreate(layout_object), |
| 1208 kAXScrollPositionChanged); | 1203 kAXScrollPositionChanged); |
| 1209 } | 1204 } |
| 1210 | 1205 |
| 1211 const AtomicString& AXObjectCacheImpl::ComputedRoleForNode(Node* node) { | 1206 const AtomicString& AXObjectCacheImpl::ComputedRoleForNode(Node* node) { |
| 1212 AXObjectImpl* obj = GetOrCreate(node); | 1207 AXObject* obj = GetOrCreate(node); |
| 1213 if (!obj) | 1208 if (!obj) |
| 1214 return AXObjectImpl::RoleName(kUnknownRole); | 1209 return AXObject::RoleName(kUnknownRole); |
| 1215 return AXObjectImpl::RoleName(obj->RoleValue()); | 1210 return AXObject::RoleName(obj->RoleValue()); |
| 1216 } | 1211 } |
| 1217 | 1212 |
| 1218 String AXObjectCacheImpl::ComputedNameForNode(Node* node) { | 1213 String AXObjectCacheImpl::ComputedNameForNode(Node* node) { |
| 1219 AXObjectImpl* obj = GetOrCreate(node); | 1214 AXObject* obj = GetOrCreate(node); |
| 1220 if (!obj) | 1215 if (!obj) |
| 1221 return ""; | 1216 return ""; |
| 1222 | 1217 |
| 1223 return obj->ComputedName(); | 1218 return obj->ComputedName(); |
| 1224 } | 1219 } |
| 1225 | 1220 |
| 1226 void AXObjectCacheImpl::OnTouchAccessibilityHover(const IntPoint& location) { | 1221 void AXObjectCacheImpl::OnTouchAccessibilityHover(const IntPoint& location) { |
| 1227 AXObjectImpl* hit = Root()->AccessibilityHitTest(location); | 1222 AXObject* hit = Root()->AccessibilityHitTest(location); |
| 1228 if (hit) { | 1223 if (hit) { |
| 1229 // Ignore events on a frame or plug-in, because the touch events | 1224 // Ignore events on a frame or plug-in, because the touch events |
| 1230 // will be re-targeted there and we don't want to fire duplicate | 1225 // will be re-targeted there and we don't want to fire duplicate |
| 1231 // accessibility events. | 1226 // accessibility events. |
| 1232 if (hit->GetLayoutObject() && hit->GetLayoutObject()->IsLayoutPart()) | 1227 if (hit->GetLayoutObject() && hit->GetLayoutObject()->IsLayoutPart()) |
| 1233 return; | 1228 return; |
| 1234 | 1229 |
| 1235 PostPlatformNotification(hit, kAXHover); | 1230 PostPlatformNotification(hit, kAXHover); |
| 1236 } | 1231 } |
| 1237 } | 1232 } |
| 1238 | 1233 |
| 1239 void AXObjectCacheImpl::SetCanvasObjectBounds(HTMLCanvasElement* canvas, | 1234 void AXObjectCacheImpl::SetCanvasObjectBounds(HTMLCanvasElement* canvas, |
| 1240 Element* element, | 1235 Element* element, |
| 1241 const LayoutRect& rect) { | 1236 const LayoutRect& rect) { |
| 1242 AXObjectImpl* obj = GetOrCreate(element); | 1237 AXObject* obj = GetOrCreate(element); |
| 1243 if (!obj) | 1238 if (!obj) |
| 1244 return; | 1239 return; |
| 1245 | 1240 |
| 1246 AXObjectImpl* ax_canvas = GetOrCreate(canvas); | 1241 AXObject* ax_canvas = GetOrCreate(canvas); |
| 1247 if (!ax_canvas) | 1242 if (!ax_canvas) |
| 1248 return; | 1243 return; |
| 1249 | 1244 |
| 1250 obj->SetElementRect(rect, ax_canvas); | 1245 obj->SetElementRect(rect, ax_canvas); |
| 1251 } | 1246 } |
| 1252 | 1247 |
| 1253 DEFINE_TRACE(AXObjectCacheImpl) { | 1248 DEFINE_TRACE(AXObjectCacheImpl) { |
| 1254 visitor->Trace(document_); | 1249 visitor->Trace(document_); |
| 1255 visitor->Trace(node_object_mapping_); | 1250 visitor->Trace(node_object_mapping_); |
| 1256 | 1251 |
| 1257 visitor->Trace(objects_); | 1252 visitor->Trace(objects_); |
| 1258 visitor->Trace(notifications_to_post_); | 1253 visitor->Trace(notifications_to_post_); |
| 1259 | 1254 |
| 1260 AXObjectCache::Trace(visitor); | 1255 AXObjectCache::Trace(visitor); |
| 1261 } | 1256 } |
| 1262 | 1257 |
| 1263 } // namespace blink | 1258 } // namespace blink |
| OLD | NEW |