OLD | NEW |
---|---|
1 // Copyright (c) 2017 The Chromium Authors. All rights reserved. | 1 // Copyright (c) 2017 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 "content/browser/accessibility/browser_accessibility_com_win.h" | 5 #include "content/browser/accessibility/browser_accessibility_com_win.h" |
6 | 6 |
7 #include <UIAutomationClient.h> | 7 #include <UIAutomationClient.h> |
8 #include <UIAutomationCoreApi.h> | 8 #include <UIAutomationCoreApi.h> |
9 | 9 |
10 #include <algorithm> | 10 #include <algorithm> |
(...skipping 2914 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
2925 if (owner()->GetString16Attribute(ui::AX_ATTR_HTML_TAG, &tag)) | 2925 if (owner()->GetString16Attribute(ui::AX_ATTR_HTML_TAG, &tag)) |
2926 *node_name = SysAllocString(tag.c_str()); | 2926 *node_name = SysAllocString(tag.c_str()); |
2927 else | 2927 else |
2928 *node_name = nullptr; | 2928 *node_name = nullptr; |
2929 | 2929 |
2930 *name_space_id = 0; | 2930 *name_space_id = 0; |
2931 *node_value = SysAllocString(value().c_str()); | 2931 *node_value = SysAllocString(value().c_str()); |
2932 *num_children = owner()->PlatformChildCount(); | 2932 *num_children = owner()->PlatformChildCount(); |
2933 *unique_id = -owner()->unique_id(); | 2933 *unique_id = -owner()->unique_id(); |
2934 | 2934 |
2935 if (owner()->GetRole() == ui::AX_ROLE_ROOT_WEB_AREA || | 2935 if (IsDocument()) { |
2936 owner()->GetRole() == ui::AX_ROLE_WEB_AREA) { | |
2937 *node_type = NODETYPE_DOCUMENT; | 2936 *node_type = NODETYPE_DOCUMENT; |
2938 } else if (owner()->IsTextOnlyObject()) { | 2937 } else if (owner()->IsTextOnlyObject()) { |
2939 *node_type = NODETYPE_TEXT; | 2938 *node_type = NODETYPE_TEXT; |
2940 } else { | 2939 } else { |
2941 *node_type = NODETYPE_ELEMENT; | 2940 *node_type = NODETYPE_ELEMENT; |
2942 } | 2941 } |
2943 | 2942 |
2944 return S_OK; | 2943 return S_OK; |
2945 } | 2944 } |
2946 | 2945 |
(...skipping 823 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
3770 | 3769 |
3771 base::string16 value = owner()->GetValue(); | 3770 base::string16 value = owner()->GetValue(); |
3772 | 3771 |
3773 // Expose slider value. | 3772 // Expose slider value. |
3774 if (IsRangeValueSupported()) { | 3773 if (IsRangeValueSupported()) { |
3775 value = GetRangeValueText(); | 3774 value = GetRangeValueText(); |
3776 SanitizeStringAttributeForIA2(value, &value); | 3775 SanitizeStringAttributeForIA2(value, &value); |
3777 win_attributes_->ia2_attributes.push_back(L"valuetext:" + value); | 3776 win_attributes_->ia2_attributes.push_back(L"valuetext:" + value); |
3778 } else { | 3777 } else { |
3779 // On Windows, the value of a document should be its url. | 3778 // On Windows, the value of a document should be its url. |
3780 if (owner()->GetRole() == ui::AX_ROLE_ROOT_WEB_AREA || | 3779 if (IsDocument()) { |
3781 owner()->GetRole() == ui::AX_ROLE_WEB_AREA) { | |
3782 value = base::UTF8ToUTF16(Manager()->GetTreeData().url); | 3780 value = base::UTF8ToUTF16(Manager()->GetTreeData().url); |
3783 } | 3781 } |
3784 // If this doesn't have a value and is linked then set its value to the url | 3782 // If this doesn't have a value and is linked then set its value to the url |
3785 // attribute. This allows screen readers to read an empty link's | 3783 // attribute. This allows screen readers to read an empty link's |
3786 // destination. | 3784 // destination. |
3787 if (value.empty() && (ia_state() & STATE_SYSTEM_LINKED)) | 3785 if (value.empty() && (ia_state() & STATE_SYSTEM_LINKED)) |
3788 value = owner()->GetString16Attribute(ui::AX_ATTR_URL); | 3786 value = owner()->GetString16Attribute(ui::AX_ATTR_URL); |
3789 } | 3787 } |
3790 | 3788 |
3791 win_attributes_->value = value; | 3789 win_attributes_->value = value; |
(...skipping 503 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4295 | 4293 |
4296 void BrowserAccessibilityComWin::IntAttributeToIA2(ui::AXIntAttribute attribute, | 4294 void BrowserAccessibilityComWin::IntAttributeToIA2(ui::AXIntAttribute attribute, |
4297 const char* ia2_attr) { | 4295 const char* ia2_attr) { |
4298 int value; | 4296 int value; |
4299 if (owner()->GetIntAttribute(attribute, &value)) { | 4297 if (owner()->GetIntAttribute(attribute, &value)) { |
4300 win_attributes_->ia2_attributes.push_back( | 4298 win_attributes_->ia2_attributes.push_back( |
4301 base::ASCIIToUTF16(ia2_attr) + L":" + base::IntToString16(value)); | 4299 base::ASCIIToUTF16(ia2_attr) + L":" + base::IntToString16(value)); |
4302 } | 4300 } |
4303 } | 4301 } |
4304 | 4302 |
4303 bool BrowserAccessibilityComWin::IsDocument() const { | |
4304 return owner()->GetRole() == ui::AX_ROLE_ROOT_WEB_AREA || | |
4305 owner()->GetRole() == ui::AX_ROLE_WEB_AREA; | |
4306 } | |
4307 | |
4308 bool BrowserAccessibilityComWin::IsRootEditable() const { | |
4309 if (!owner()->HasState(ui::AX_STATE_EDITABLE)) | |
4310 return false; | |
4311 | |
4312 if (IsDocument()) | |
4313 return true; | |
4314 | |
4315 BrowserAccessibility* parent = owner()->PlatformGetParent(); | |
dougt
2017/06/23 18:27:18
I am confused by this.
GetParent() is just retur
aleventhal
2017/06/28 14:20:57
It does what I want, but maybe it needs a differen
| |
4316 return !parent || !parent->HasState(ui::AX_STATE_EDITABLE); | |
4317 } | |
4318 | |
4319 bool BrowserAccessibilityComWin::IsEditBoxRole() const { | |
4320 const int32_t role = owner()->GetRole(); | |
4321 return role == ui::AX_ROLE_TEXT_FIELD || role == ui::AX_ROLE_SEARCH_BOX; | |
4322 } | |
4323 | |
4305 bool BrowserAccessibilityComWin::IsHyperlink() const { | 4324 bool BrowserAccessibilityComWin::IsHyperlink() const { |
4306 int32_t hyperlink_index = -1; | 4325 int32_t hyperlink_index = -1; |
4307 auto* parent = owner()->PlatformGetParent(); | 4326 auto* parent = owner()->PlatformGetParent(); |
4308 if (parent) { | 4327 if (parent) { |
4309 hyperlink_index = | 4328 hyperlink_index = |
4310 ToBrowserAccessibilityComWin(parent)->GetHyperlinkIndexFromChild(*this); | 4329 ToBrowserAccessibilityComWin(parent)->GetHyperlinkIndexFromChild(*this); |
4311 } | 4330 } |
4312 | 4331 |
4313 if (hyperlink_index >= 0) | 4332 if (hyperlink_index >= 0) |
4314 return true; | 4333 return true; |
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
4356 return -1; | 4375 return -1; |
4357 } | 4376 } |
4358 | 4377 |
4359 int32_t BrowserAccessibilityComWin::GetHypertextOffsetFromChild( | 4378 int32_t BrowserAccessibilityComWin::GetHypertextOffsetFromChild( |
4360 BrowserAccessibilityComWin& child) { | 4379 BrowserAccessibilityComWin& child) { |
4361 DCHECK(child.owner()->PlatformGetParent() == owner()); | 4380 DCHECK(child.owner()->PlatformGetParent() == owner()); |
4362 | 4381 |
4363 // Handle the case when we are dealing with a direct text-only child. | 4382 // Handle the case when we are dealing with a direct text-only child. |
4364 // (Note that this object might be a platform leaf, e.g. an ARIA searchbox, | 4383 // (Note that this object might be a platform leaf, e.g. an ARIA searchbox, |
4365 // and so |owner()->InternalChild...| functions need to be used. Also, | 4384 // and so |owner()->InternalChild...| functions need to be used. Also, |
4366 // direct text-only children should not be present at tree roots and so no | 4385 // direct text-only children should not be present at tree s and so no |
dougt
2017/06/23 18:27:18
I don't think you want this change.
aleventhal
2017/06/28 14:20:57
Done.
| |
4367 // cross-tree traversal is necessary.) | 4386 // cross-tree traversal is necessary.) |
4368 if (child.owner()->IsTextOnlyObject()) { | 4387 if (child.owner()->IsTextOnlyObject()) { |
4369 int32_t hypertextOffset = 0; | 4388 int32_t hypertextOffset = 0; |
4370 int32_t index_in_parent = child.GetIndexInParent(); | 4389 int32_t index_in_parent = child.GetIndexInParent(); |
4371 DCHECK_GE(index_in_parent, 0); | 4390 DCHECK_GE(index_in_parent, 0); |
4372 DCHECK_LT(index_in_parent, | 4391 DCHECK_LT(index_in_parent, |
4373 static_cast<int32_t>(owner()->InternalChildCount())); | 4392 static_cast<int32_t>(owner()->InternalChildCount())); |
4374 for (uint32_t i = 0; i < static_cast<uint32_t>(index_in_parent); ++i) { | 4393 for (uint32_t i = 0; i < static_cast<uint32_t>(index_in_parent); ++i) { |
4375 const BrowserAccessibilityComWin* sibling = | 4394 const BrowserAccessibilityComWin* sibling = |
4376 ToBrowserAccessibilityComWin(owner()->InternalGetChild(i)); | 4395 ToBrowserAccessibilityComWin(owner()->InternalGetChild(i)); |
(...skipping 694 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5071 // Expose whether or not the mouse is over an element, but suppress | 5090 // Expose whether or not the mouse is over an element, but suppress |
5072 // this for tests because it can make the test results flaky depending | 5091 // this for tests because it can make the test results flaky depending |
5073 // on the position of the mouse. | 5092 // on the position of the mouse. |
5074 BrowserAccessibilityStateImpl* accessibility_state = | 5093 BrowserAccessibilityStateImpl* accessibility_state = |
5075 BrowserAccessibilityStateImpl::GetInstance(); | 5094 BrowserAccessibilityStateImpl::GetInstance(); |
5076 if (!accessibility_state->disable_hot_tracking_for_testing()) { | 5095 if (!accessibility_state->disable_hot_tracking_for_testing()) { |
5077 if (owner()->HasState(ui::AX_STATE_HOVERED)) | 5096 if (owner()->HasState(ui::AX_STATE_HOVERED)) |
5078 ia_state |= STATE_SYSTEM_HOTTRACKED; | 5097 ia_state |= STATE_SYSTEM_HOTTRACKED; |
5079 } | 5098 } |
5080 | 5099 |
5081 if (owner()->HasState(ui::AX_STATE_EDITABLE)) | 5100 const bool is_editable = owner()->HasState(ui::AX_STATE_EDITABLE); |
5101 if (is_editable) { | |
5082 ia2_state |= IA2_STATE_EDITABLE; | 5102 ia2_state |= IA2_STATE_EDITABLE; |
5103 } | |
dougt
2017/06/23 18:27:17
Since this is a one liner, you don't need the curl
aleventhal
2017/06/28 14:20:57
Done.
| |
5104 | |
5105 if (is_editable ? IsRootEditable() : IsEditBoxRole()) { | |
5106 // Support multi/single line states if root edtiable or appropriate role. | |
5107 // We support the edit box roles even if the area is not actually editable, | |
5108 // because it is technically feasible for JS to implement the edit box | |
5109 // by controlling selection. | |
5110 if (owner()->HasState(ui::AX_STATE_MULTILINE)) { | |
5111 ia2_state |= IA2_STATE_MULTI_LINE; | |
5112 } else { | |
5113 ia2_state |= IA2_STATE_SINGLE_LINE; | |
5114 } | |
5115 } | |
5083 | 5116 |
5084 if (!owner()->GetStringAttribute(ui::AX_ATTR_AUTO_COMPLETE).empty()) | 5117 if (!owner()->GetStringAttribute(ui::AX_ATTR_AUTO_COMPLETE).empty()) |
5085 ia2_state |= IA2_STATE_SUPPORTS_AUTOCOMPLETION; | 5118 ia2_state |= IA2_STATE_SUPPORTS_AUTOCOMPLETION; |
5086 | 5119 |
5087 if (owner()->GetBoolAttribute(ui::AX_ATTR_MODAL)) | 5120 if (owner()->GetBoolAttribute(ui::AX_ATTR_MODAL)) |
5088 ia2_state |= IA2_STATE_MODAL; | 5121 ia2_state |= IA2_STATE_MODAL; |
5089 | 5122 |
5090 base::string16 html_tag = owner()->GetString16Attribute(ui::AX_ATTR_HTML_TAG); | 5123 base::string16 html_tag = owner()->GetString16Attribute(ui::AX_ATTR_HTML_TAG); |
5091 switch (owner()->GetRole()) { | 5124 switch (owner()->GetRole()) { |
5092 case ui::AX_ROLE_ALERT: | 5125 case ui::AX_ROLE_ALERT: |
(...skipping 377 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5470 ia_role = ROLE_SYSTEM_LISTITEM; | 5503 ia_role = ROLE_SYSTEM_LISTITEM; |
5471 ia_state |= STATE_SYSTEM_READONLY; | 5504 ia_state |= STATE_SYSTEM_READONLY; |
5472 break; | 5505 break; |
5473 case ui::AX_ROLE_TOGGLE_BUTTON: | 5506 case ui::AX_ROLE_TOGGLE_BUTTON: |
5474 ia_role = ROLE_SYSTEM_PUSHBUTTON; | 5507 ia_role = ROLE_SYSTEM_PUSHBUTTON; |
5475 ia2_role = IA2_ROLE_TOGGLE_BUTTON; | 5508 ia2_role = IA2_ROLE_TOGGLE_BUTTON; |
5476 break; | 5509 break; |
5477 case ui::AX_ROLE_TEXT_FIELD: | 5510 case ui::AX_ROLE_TEXT_FIELD: |
5478 case ui::AX_ROLE_SEARCH_BOX: | 5511 case ui::AX_ROLE_SEARCH_BOX: |
5479 ia_role = ROLE_SYSTEM_TEXT; | 5512 ia_role = ROLE_SYSTEM_TEXT; |
5480 if (owner()->HasState(ui::AX_STATE_MULTILINE)) { | |
5481 ia2_state |= IA2_STATE_MULTI_LINE; | |
5482 } else { | |
5483 ia2_state |= IA2_STATE_SINGLE_LINE; | |
5484 } | |
5485 if (owner()->HasState(ui::AX_STATE_READ_ONLY)) | 5513 if (owner()->HasState(ui::AX_STATE_READ_ONLY)) |
5486 ia_state |= STATE_SYSTEM_READONLY; | 5514 ia_state |= STATE_SYSTEM_READONLY; |
5487 ia2_state |= IA2_STATE_SELECTABLE_TEXT; | 5515 ia2_state |= IA2_STATE_SELECTABLE_TEXT; |
5488 break; | 5516 break; |
5489 case ui::AX_ROLE_ABBR: | 5517 case ui::AX_ROLE_ABBR: |
5490 case ui::AX_ROLE_TIME: | 5518 case ui::AX_ROLE_TIME: |
5491 role_name = html_tag; | 5519 role_name = html_tag; |
5492 ia_role = ROLE_SYSTEM_TEXT; | 5520 ia_role = ROLE_SYSTEM_TEXT; |
5493 ia2_role = IA2_ROLE_TEXT_FRAME; | 5521 ia2_role = IA2_ROLE_TEXT_FRAME; |
5494 break; | 5522 break; |
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
5583 | 5611 |
5584 BrowserAccessibilityComWin* ToBrowserAccessibilityComWin( | 5612 BrowserAccessibilityComWin* ToBrowserAccessibilityComWin( |
5585 BrowserAccessibility* obj) { | 5613 BrowserAccessibility* obj) { |
5586 if (!obj || !obj->IsNative()) | 5614 if (!obj || !obj->IsNative()) |
5587 return nullptr; | 5615 return nullptr; |
5588 auto* result = static_cast<BrowserAccessibilityWin*>(obj)->GetCOM(); | 5616 auto* result = static_cast<BrowserAccessibilityWin*>(obj)->GetCOM(); |
5589 return result; | 5617 return result; |
5590 } | 5618 } |
5591 | 5619 |
5592 } // namespace content | 5620 } // namespace content |
OLD | NEW |