Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 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 | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "modules/accessibility/InspectorAccessibilityAgent.h" | 5 #include "modules/accessibility/InspectorAccessibilityAgent.h" |
| 6 | 6 |
| 7 #include "core/HTMLNames.h" | 7 #include "core/HTMLNames.h" |
| 8 #include "core/dom/AXObjectCache.h" | 8 #include "core/dom/AXObjectCache.h" |
| 9 #include "core/dom/DOMNodeIds.h" | 9 #include "core/dom/DOMNodeIds.h" |
| 10 #include "core/dom/Element.h" | 10 #include "core/dom/Element.h" |
| 11 #include "core/inspector/IdentifiersFactory.h" | |
| 11 #include "core/inspector/InspectorDOMAgent.h" | 12 #include "core/inspector/InspectorDOMAgent.h" |
| 12 #include "core/inspector/InspectorStyleSheet.h" | 13 #include "core/inspector/InspectorStyleSheet.h" |
| 13 #include "core/page/Page.h" | 14 #include "core/page/Page.h" |
| 14 #include "modules/accessibility/AXObject.h" | 15 #include "modules/accessibility/AXObject.h" |
| 15 #include "modules/accessibility/AXObjectCacheImpl.h" | 16 #include "modules/accessibility/AXObjectCacheImpl.h" |
| 16 #include "modules/accessibility/InspectorTypeBuilderHelper.h" | 17 #include "modules/accessibility/InspectorTypeBuilderHelper.h" |
| 17 #include <memory> | 18 #include <memory> |
| 18 | 19 |
| 19 namespace blink { | 20 namespace blink { |
| 20 | 21 |
| (...skipping 272 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 293 AtomicString roleName = AXObject::roleName(role); | 294 AtomicString roleName = AXObject::roleName(role); |
| 294 std::unique_ptr<AXValue> roleNameValue; | 295 std::unique_ptr<AXValue> roleNameValue; |
| 295 if (!roleName.isNull()) { | 296 if (!roleName.isNull()) { |
| 296 roleNameValue = createValue(roleName, AXValueTypeEnum::Role); | 297 roleNameValue = createValue(roleName, AXValueTypeEnum::Role); |
| 297 } else { | 298 } else { |
| 298 roleNameValue = createValue(AXObject::internalRoleName(role), AXValueTyp eEnum::InternalRole); | 299 roleNameValue = createValue(AXObject::internalRoleName(role), AXValueTyp eEnum::InternalRole); |
| 299 } | 300 } |
| 300 return roleNameValue; | 301 return roleNameValue; |
| 301 } | 302 } |
| 302 | 303 |
| 303 std::unique_ptr<AXNode> buildObjectForIgnoredNode(Node* node, AXObject* axObject , AXObjectCacheImpl* cacheImpl) | 304 std::unique_ptr<AXNode> buildObjectForIgnoredNode(Node* node, const AXObject* ax Object, AXObjectCacheImpl* cacheImpl) |
| 304 { | 305 { |
| 305 AXObject::IgnoredReasons ignoredReasons; | 306 AXObject::IgnoredReasons ignoredReasons; |
| 306 | 307 |
| 307 AXID axID = 0; | 308 AXID axID = 0; |
| 308 std::unique_ptr<AXNode> ignoredNodeObject = AXNode::create().setNodeId(Strin g::number(axID)).setIgnored(true).build(); | 309 std::unique_ptr<AXNode> ignoredNodeObject = AXNode::create().setNodeId(Strin g::number(axID)).setIgnored(true).build(); |
| 309 if (axObject) { | 310 if (axObject) { |
| 310 axObject->computeAccessibilityIsIgnored(&ignoredReasons); | 311 axObject->computeAccessibilityIsIgnored(&ignoredReasons); |
| 311 axID = axObject->axObjectID(); | 312 axID = axObject->axObjectID(); |
| 312 AccessibilityRole role = axObject->roleValue(); | 313 AccessibilityRole role = axObject->roleValue(); |
| 313 ignoredNodeObject->setRole(createRoleNameValue(role)); | 314 ignoredNodeObject->setRole(createRoleNameValue(role)); |
| 314 } else if (!node->layoutObject()) { | 315 } else if (node && !node->layoutObject()) { |
| 315 ignoredReasons.append(IgnoredReason(AXNotRendered)); | 316 ignoredReasons.append(IgnoredReason(AXNotRendered)); |
| 316 } | 317 } |
| 317 | 318 |
| 318 std::unique_ptr<protocol::Array<AXProperty>> ignoredReasonProperties = proto col::Array<AXProperty>::create(); | 319 std::unique_ptr<protocol::Array<AXProperty>> ignoredReasonProperties = proto col::Array<AXProperty>::create(); |
| 319 for (size_t i = 0; i < ignoredReasons.size(); i++) | 320 for (size_t i = 0; i < ignoredReasons.size(); i++) |
| 320 ignoredReasonProperties->addItem(createProperty(ignoredReasons[i])); | 321 ignoredReasonProperties->addItem(createProperty(ignoredReasons[i])); |
| 321 ignoredNodeObject->setIgnoredReasons(std::move(ignoredReasonProperties)); | 322 ignoredNodeObject->setIgnoredReasons(std::move(ignoredReasonProperties)); |
| 322 | 323 |
| 323 return ignoredNodeObject; | 324 return ignoredNodeObject; |
| 324 } | 325 } |
| 325 | 326 |
| 326 std::unique_ptr<AXNode> buildObjectForNode(Node* node, AXObject* axObject, AXObj ectCacheImpl* cacheImpl, std::unique_ptr<protocol::Array<AXProperty>> properties ) | 327 std::unique_ptr<AXNode> buildProtocolAXObject(AXObject* axObject, AXObjectCacheI mpl* cacheImpl) |
| 327 { | 328 { |
| 328 AccessibilityRole role = axObject->roleValue(); | 329 AccessibilityRole role = axObject->roleValue(); |
| 329 std::unique_ptr<AXNode> nodeObject = AXNode::create().setNodeId(String::numb er(axObject->axObjectID())).setIgnored(false).build(); | 330 std::unique_ptr<AXNode> nodeObject = AXNode::create().setNodeId(String::numb er(axObject->axObjectID())).setIgnored(false).build(); |
| 330 nodeObject->setRole(createRoleNameValue(role)); | 331 nodeObject->setRole(createRoleNameValue(role)); |
| 331 | 332 |
| 333 std::unique_ptr<protocol::Array<AXProperty>> properties = protocol::Array<AX Property>::create(); | |
| 334 fillLiveRegionProperties(axObject, properties.get()); | |
| 335 fillGlobalStates(axObject, properties.get()); | |
| 336 fillWidgetProperties(axObject, properties.get()); | |
| 337 fillWidgetStates(axObject, properties.get()); | |
| 338 fillRelationships(axObject, properties.get()); | |
| 339 | |
| 332 AXObject::NameSources nameSources; | 340 AXObject::NameSources nameSources; |
| 333 String computedName = axObject->name(&nameSources); | 341 String computedName = axObject->name(&nameSources); |
| 334 if (!nameSources.isEmpty()) { | 342 if (!nameSources.isEmpty()) { |
| 335 std::unique_ptr<AXValue> name = createValue(computedName, AXValueTypeEnu m::ComputedString); | 343 std::unique_ptr<AXValue> name = createValue(computedName, AXValueTypeEnu m::ComputedString); |
| 336 if (!nameSources.isEmpty()) { | 344 if (!nameSources.isEmpty()) { |
| 337 std::unique_ptr<protocol::Array<AXValueSource>> nameSourceProperties = protocol::Array<AXValueSource>::create(); | 345 std::unique_ptr<protocol::Array<AXValueSource>> nameSourceProperties = protocol::Array<AXValueSource>::create(); |
| 338 for (size_t i = 0; i < nameSources.size(); ++i) { | 346 for (size_t i = 0; i < nameSources.size(); ++i) { |
| 339 NameSource& nameSource = nameSources[i]; | 347 NameSource& nameSource = nameSources[i]; |
| 340 nameSourceProperties->addItem(createValueSource(nameSource)); | 348 nameSourceProperties->addItem(createValueSource(nameSource)); |
| 341 if (nameSource.text.isNull() || nameSource.superseded) | 349 if (nameSource.text.isNull() || nameSource.superseded) |
| (...skipping 15 matching lines...) Expand all Loading... | |
| 357 } | 365 } |
| 358 | 366 |
| 359 } // namespace | 367 } // namespace |
| 360 | 368 |
| 361 InspectorAccessibilityAgent::InspectorAccessibilityAgent(Page* page, InspectorDO MAgent* domAgent) | 369 InspectorAccessibilityAgent::InspectorAccessibilityAgent(Page* page, InspectorDO MAgent* domAgent) |
| 362 : m_page(page) | 370 : m_page(page) |
| 363 , m_domAgent(domAgent) | 371 , m_domAgent(domAgent) |
| 364 { | 372 { |
| 365 } | 373 } |
| 366 | 374 |
| 367 void InspectorAccessibilityAgent::getAXNode(ErrorString* errorString, int nodeId , Maybe<AXNode>* accessibilityNode) | 375 void InspectorAccessibilityAgent::getAXNodeForDOMNode(ErrorString* errorString, int domNodeId, bool fetchAncestors, Maybe<protocol::Array<protocol::Accessibilit y::AXNode>>* nodes) |
| 368 { | 376 { |
| 369 Frame* mainFrame = m_page->mainFrame(); | 377 discardFrontendBindings(); |
|
dgozman
2016/09/15 17:45:44
If the cache is not used in subsequent protocol ca
aboxhall
2016/09/15 20:30:08
It will be used in later changes, once I add getCh
| |
| 370 if (!mainFrame->isLocalFrame()) { | |
| 371 *errorString = "Can't inspect out of process frames yet"; | |
| 372 return; | |
| 373 } | |
| 374 | 378 |
| 375 if (!m_domAgent->enabled()) { | 379 if (!m_domAgent->enabled()) { |
| 376 *errorString = "DOM agent must be enabled"; | 380 *errorString = "DOM agent must be enabled"; |
| 377 return; | 381 return; |
| 378 } | 382 } |
| 379 Node* node = m_domAgent->assertNode(errorString, nodeId); | 383 Node* node = m_domAgent->assertNode(errorString, domNodeId); |
| 380 if (!node) | 384 if (!node) |
| 381 return; | 385 return; |
| 382 | 386 |
| 383 Document& document = node->document(); | 387 Document& document = node->document(); |
| 384 document.updateStyleAndLayoutIgnorePendingStylesheets(); | 388 document.updateStyleAndLayoutIgnorePendingStylesheets(); |
| 385 DocumentLifecycle::DisallowTransitionScope disallowTransition(document.lifec ycle()); | 389 DocumentLifecycle::DisallowTransitionScope disallowTransition(document.lifec ycle()); |
| 386 std::unique_ptr<ScopedAXObjectCache> cache = ScopedAXObjectCache::create(doc ument); | 390 LocalFrame* localFrame = document.frame(); |
| 387 AXObjectCacheImpl* cacheImpl = toAXObjectCacheImpl(cache->get()); | 391 if (!localFrame) { |
| 388 AXObject* axObject = cacheImpl->getOrCreate(node); | 392 *errorString = "Can't inspect out of process frames yet"; |
|
dgozman
2016/09/15 17:45:44
This actually means frame is detached. Out of proc
aboxhall
2016/09/15 20:30:08
Ah ok, changed error string.
| |
| 389 if (!axObject || axObject->accessibilityIsIgnored()) { | |
| 390 *accessibilityNode = buildObjectForIgnoredNode(node, axObject, cacheImpl ); | |
| 391 return; | 393 return; |
| 392 } | 394 } |
| 395 AXObjectCache* cache = nullptr; | |
| 396 String frameId = IdentifiersFactory::frameId(localFrame); | |
| 397 CacheMap::iterator it = m_frameToAXObjectCacheMap.find(frameId); | |
| 398 if (it != m_frameToAXObjectCacheMap.end()) { | |
| 399 cache = it->value; | |
| 400 } else { | |
| 401 cache = AXObjectCache::create(document); | |
| 402 m_frameToAXObjectCacheMap.set(frameId, cache); | |
| 403 } | |
| 393 | 404 |
| 394 std::unique_ptr<protocol::Array<AXProperty>> properties = protocol::Array<AX Property>::create(); | 405 AXObjectCacheImpl* cacheImpl = toAXObjectCacheImpl(cache); |
|
dgozman
2016/09/15 17:45:44
If we actually need an AXObjectCacheImpl, let's re
aboxhall
2016/09/15 20:30:08
Done.
| |
| 395 fillLiveRegionProperties(axObject, properties.get()); | 406 AXObject* axObject = cacheImpl->getOrCreate(node); |
| 396 fillGlobalStates(axObject, properties.get()); | 407 *nodes = protocol::Array<protocol::Accessibility::AXNode>::create(); |
|
dgozman
2016/09/15 17:45:44
Let's not create nodes if there was no axObject.
aboxhall
2016/09/15 20:30:08
I don't follow - either way an object gets added t
dgozman
2016/09/17 00:36:23
Then it should not be optional in protocol.
aboxhall
2016/09/17 01:12:34
Done.
| |
| 397 fillWidgetProperties(axObject, properties.get()); | 408 if (!axObject || axObject->accessibilityIsIgnored()) { |
| 398 fillWidgetStates(axObject, properties.get()); | 409 nodes->fromJust()->addItem(buildObjectForIgnoredNode(node, axObject, cac heImpl)); |
| 399 fillRelationships(axObject, properties.get()); | 410 } else { |
| 411 nodes->fromJust()->addItem(buildProtocolAXObject(axObject, cacheImpl)); | |
| 412 } | |
| 400 | 413 |
| 401 *accessibilityNode = buildObjectForNode(node, axObject, cacheImpl, std::move (properties)); | 414 if (fetchAncestors && axObject) { |
| 415 AXObject* parent = axObject->parentObjectUnignored(); | |
| 416 while (parent) { | |
| 417 nodes->fromJust()->addItem(buildProtocolAXObject(parent, cacheImpl)) ; | |
| 418 parent = parent->parentObjectUnignored(); | |
| 419 } | |
| 420 } | |
| 421 } | |
| 422 | |
| 423 void InspectorAccessibilityAgent::discardFrontendBindings() | |
| 424 { | |
| 425 m_frameToAXObjectCacheMap.clear(); | |
| 402 } | 426 } |
| 403 | 427 |
| 404 DEFINE_TRACE(InspectorAccessibilityAgent) | 428 DEFINE_TRACE(InspectorAccessibilityAgent) |
| 405 { | 429 { |
| 406 visitor->trace(m_page); | 430 visitor->trace(m_page); |
| 431 visitor->trace(m_frameToAXObjectCacheMap); | |
| 407 visitor->trace(m_domAgent); | 432 visitor->trace(m_domAgent); |
| 408 InspectorBaseAgent::trace(visitor); | 433 InspectorBaseAgent::trace(visitor); |
| 409 } | 434 } |
| 410 | 435 |
| 411 } // namespace blink | 436 } // namespace blink |
| OLD | NEW |