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

Side by Side Diff: content/browser/accessibility/browser_accessibility_com_win.cc

Issue 2981073002: Move BrowserAccessibilityRelation code to the ui/accessibility/ (Closed)
Patch Set: Force tests to calculate relationships. Created 3 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
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 21 matching lines...) Expand all
32 #include "ui/base/win/accessibility_misc_utils.h" 32 #include "ui/base/win/accessibility_misc_utils.h"
33 #include "ui/base/win/atl_module.h" 33 #include "ui/base/win/atl_module.h"
34 34
35 // There is no easy way to decouple |kScreenReader| and |kHTML| accessibility 35 // There is no easy way to decouple |kScreenReader| and |kHTML| accessibility
36 // modes when Windows screen readers are used. For example, certain roles use 36 // modes when Windows screen readers are used. For example, certain roles use
37 // the HTML tag name. Input fields require their type attribute to be exposed. 37 // the HTML tag name. Input fields require their type attribute to be exposed.
38 const uint32_t kScreenReaderAndHTMLAccessibilityModes = 38 const uint32_t kScreenReaderAndHTMLAccessibilityModes =
39 content::AccessibilityMode::kScreenReader | 39 content::AccessibilityMode::kScreenReader |
40 content::AccessibilityMode::kHTML; 40 content::AccessibilityMode::kHTML;
41 41
42 const WCHAR* const IA2_RELATION_DETAILS = L"details";
43 const WCHAR* const IA2_RELATION_DETAILS_FOR = L"detailsFor";
44 const WCHAR* const IA2_RELATION_ERROR_MESSAGE = L"errorMessage";
45
46 namespace content { 42 namespace content {
47 43
48 using AXPlatformPositionInstance = AXPlatformPosition::AXPositionInstance; 44 using AXPlatformPositionInstance = AXPlatformPosition::AXPositionInstance;
49 using AXPlatformRange = ui::AXRange<AXPlatformPositionInstance::element_type>; 45 using AXPlatformRange = ui::AXRange<AXPlatformPositionInstance::element_type>;
50 46
51 // These nonstandard GUIDs are taken directly from the Mozilla sources 47 // These nonstandard GUIDs are taken directly from the Mozilla sources
52 // (accessible/src/msaa/nsAccessNodeWrap.cpp); some documentation is here: 48 // (accessible/src/msaa/nsAccessNodeWrap.cpp); some documentation is here:
53 // http://developer.mozilla.org/en/Accessibility/AT-APIs/ImplementationFeatures/ MSAA 49 // http://developer.mozilla.org/en/Accessibility/AT-APIs/ImplementationFeatures/ MSAA
54 const GUID GUID_ISimpleDOM = {0x0c539790, 50 const GUID GUID_ISimpleDOM = {0x0c539790,
55 0x12e4, 51 0x12e4,
56 0x11cf, 52 0x11cf,
57 {0xb6, 0x61, 0x00, 0xaa, 0x00, 0x4c, 0xd6, 0xd8}}; 53 {0xb6, 0x61, 0x00, 0xaa, 0x00, 0x4c, 0xd6, 0xd8}};
58 const GUID GUID_IAccessibleContentDocument = { 54 const GUID GUID_IAccessibleContentDocument = {
59 0xa5d8e1f3, 55 0xa5d8e1f3,
60 0x3571, 56 0x3571,
61 0x4d8f, 57 0x4d8f,
62 {0x95, 0x21, 0x07, 0xed, 0x28, 0xfb, 0x07, 0x2e}}; 58 {0x95, 0x21, 0x07, 0xed, 0x28, 0xfb, 0x07, 0x2e}};
63 59
64 const base::char16 BrowserAccessibilityComWin::kEmbeddedCharacter = L'\xfffc'; 60 const base::char16 BrowserAccessibilityComWin::kEmbeddedCharacter = L'\xfffc';
65 61
66 void AddAccessibilityModeFlags(AccessibilityMode mode_flags) { 62 void AddAccessibilityModeFlags(AccessibilityMode mode_flags) {
67 BrowserAccessibilityStateImpl::GetInstance()->AddAccessibilityModeFlags( 63 BrowserAccessibilityStateImpl::GetInstance()->AddAccessibilityModeFlags(
68 mode_flags); 64 mode_flags);
69 } 65 }
70 66
71 // 67 //
72 // BrowserAccessibilityRelation
73 //
74 // A simple implementation of IAccessibleRelation, used to represent
75 // a relationship between two accessible nodes in the tree.
76 //
77
78 class BrowserAccessibilityRelation
79 : public CComObjectRootEx<CComMultiThreadModel>,
80 public IAccessibleRelation {
81 BEGIN_COM_MAP(BrowserAccessibilityRelation)
82 COM_INTERFACE_ENTRY(IAccessibleRelation)
83 END_COM_MAP()
84
85 CONTENT_EXPORT BrowserAccessibilityRelation() {}
86 CONTENT_EXPORT virtual ~BrowserAccessibilityRelation() {}
87
88 CONTENT_EXPORT void Initialize(BrowserAccessibilityComWin* owner,
89 const base::string16& type);
90 CONTENT_EXPORT void AddTarget(int target_id);
91 CONTENT_EXPORT void RemoveTarget(int target_id);
92
93 // Accessors.
94 const base::string16& get_type() const { return type_; }
95 const std::vector<int>& get_target_ids() const { return target_ids_; }
96
97 // IAccessibleRelation methods.
98 CONTENT_EXPORT STDMETHODIMP get_relationType(BSTR* relation_type) override;
99 CONTENT_EXPORT STDMETHODIMP get_nTargets(long* n_targets) override;
100 CONTENT_EXPORT STDMETHODIMP get_target(long target_index,
101 IUnknown** target) override;
102 CONTENT_EXPORT STDMETHODIMP get_targets(long max_targets,
103 IUnknown** targets,
104 long* n_targets) override;
105
106 // IAccessibleRelation methods not implemented.
107 CONTENT_EXPORT STDMETHODIMP
108 get_localizedRelationType(BSTR* relation_type) override {
109 return E_NOTIMPL;
110 }
111
112 private:
113 base::string16 type_;
114 base::win::ScopedComPtr<BrowserAccessibilityComWin> owner_;
115 std::vector<int> target_ids_;
116 };
117
118 void BrowserAccessibilityRelation::Initialize(BrowserAccessibilityComWin* owner,
119 const base::string16& type) {
120 owner_ = owner;
121 type_ = type;
122 }
123
124 void BrowserAccessibilityRelation::AddTarget(int target_id) {
125 target_ids_.push_back(target_id);
126 }
127
128 void BrowserAccessibilityRelation::RemoveTarget(int target_id) {
129 target_ids_.erase(
130 std::remove(target_ids_.begin(), target_ids_.end(), target_id),
131 target_ids_.end());
132 }
133
134 STDMETHODIMP BrowserAccessibilityRelation::get_relationType(
135 BSTR* relation_type) {
136 if (!relation_type)
137 return E_INVALIDARG;
138
139 if (!owner_->owner())
140 return E_FAIL;
141
142 *relation_type = SysAllocString(type_.c_str());
143 DCHECK(*relation_type);
144 return S_OK;
145 }
146
147 STDMETHODIMP BrowserAccessibilityRelation::get_nTargets(long* n_targets) {
148 if (!n_targets)
149 return E_INVALIDARG;
150
151 if (!owner_->owner())
152 return E_FAIL;
153
154 *n_targets = static_cast<long>(target_ids_.size());
155
156 for (long i = *n_targets - 1; i >= 0; --i) {
157 BrowserAccessibilityComWin* result = owner_->GetFromID(target_ids_[i]);
158 if (!result || !result->owner()) {
159 *n_targets = 0;
160 break;
161 }
162 }
163 return S_OK;
164 }
165
166 STDMETHODIMP BrowserAccessibilityRelation::get_target(long target_index,
167 IUnknown** target) {
168 if (!target)
169 return E_INVALIDARG;
170
171 if (!owner_->owner())
172 return E_FAIL;
173
174 auto* manager = owner_->Manager();
175 if (!manager)
176 return E_FAIL;
177
178 if (target_index < 0 ||
179 target_index >= static_cast<long>(target_ids_.size())) {
180 return E_INVALIDARG;
181 }
182
183 BrowserAccessibility* result = manager->GetFromID(target_ids_[target_index]);
184 if (!result || !result->instance_active())
185 return E_FAIL;
186
187 *target = static_cast<IAccessible*>(
188 ToBrowserAccessibilityComWin(result)->NewReference());
189 return S_OK;
190 }
191
192 STDMETHODIMP BrowserAccessibilityRelation::get_targets(long max_targets,
193 IUnknown** targets,
194 long* n_targets) {
195 if (!targets || !n_targets)
196 return E_INVALIDARG;
197
198 if (!owner_->owner())
199 return E_FAIL;
200
201 long count = static_cast<long>(target_ids_.size());
202 if (count > max_targets)
203 count = max_targets;
204
205 *n_targets = count;
206 if (count == 0)
207 return S_FALSE;
208
209 for (long i = 0; i < count; ++i) {
210 HRESULT result = get_target(i, &targets[i]);
211 if (result != S_OK)
212 return result;
213 }
214
215 return S_OK;
216 }
217
218 //
219 // BrowserAccessibilityComWin::WinAttributes 68 // BrowserAccessibilityComWin::WinAttributes
220 // 69 //
221 70
222 BrowserAccessibilityComWin::WinAttributes::WinAttributes() 71 BrowserAccessibilityComWin::WinAttributes::WinAttributes()
223 : ia_role(0), ia_state(0), ia2_role(0), ia2_state(0) {} 72 : ia_role(0), ia_state(0), ia2_role(0), ia2_state(0) {}
224 73
225 BrowserAccessibilityComWin::WinAttributes::~WinAttributes() {} 74 BrowserAccessibilityComWin::WinAttributes::~WinAttributes() {}
226 75
227 // 76 //
228 // BrowserAccessibilityComWin 77 // BrowserAccessibilityComWin
229 // 78 //
230 BrowserAccessibilityComWin::BrowserAccessibilityComWin() 79 BrowserAccessibilityComWin::BrowserAccessibilityComWin()
231 : owner_(nullptr), 80 : owner_(nullptr),
232 win_attributes_(new WinAttributes()), 81 win_attributes_(new WinAttributes()),
233 previous_scroll_x_(0), 82 previous_scroll_x_(0),
234 previous_scroll_y_(0) {} 83 previous_scroll_y_(0) {}
235 84
236 BrowserAccessibilityComWin::~BrowserAccessibilityComWin() { 85 BrowserAccessibilityComWin::~BrowserAccessibilityComWin() {
237 for (BrowserAccessibilityRelation* relation : relations_)
238 relation->Release();
239 } 86 }
240 87
241 // 88 //
242 // IAccessible overrides: 89 // IAccessible overrides:
243 // 90 //
244 91
245 STDMETHODIMP BrowserAccessibilityComWin::get_accDefaultAction( 92 STDMETHODIMP BrowserAccessibilityComWin::get_accDefaultAction(
246 VARIANT var_id, 93 VARIANT var_id,
247 BSTR* def_action) { 94 BSTR* def_action) {
248 AddAccessibilityModeFlags(kScreenReaderAndHTMLAccessibilityModes); 95 AddAccessibilityModeFlags(kScreenReaderAndHTMLAccessibilityModes);
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
319 if (!index_in_parent) 166 if (!index_in_parent)
320 return E_INVALIDARG; 167 return E_INVALIDARG;
321 168
322 *index_in_parent = GetIndexInParent(); 169 *index_in_parent = GetIndexInParent();
323 return S_OK; 170 return S_OK;
324 } 171 }
325 172
326 STDMETHODIMP BrowserAccessibilityComWin::get_nRelations(LONG* n_relations) { 173 STDMETHODIMP BrowserAccessibilityComWin::get_nRelations(LONG* n_relations) {
327 WIN_ACCESSIBILITY_API_HISTOGRAM(UMA_API_GET_N_RELATIONS); 174 WIN_ACCESSIBILITY_API_HISTOGRAM(UMA_API_GET_N_RELATIONS);
328 AddAccessibilityModeFlags(kScreenReaderAndHTMLAccessibilityModes); 175 AddAccessibilityModeFlags(kScreenReaderAndHTMLAccessibilityModes);
329 if (!owner()) 176 return AXPlatformNodeWin::get_nRelations(n_relations);
330 return E_FAIL;
331
332 if (!n_relations)
333 return E_INVALIDARG;
334
335 *n_relations = relations_.size();
336 return S_OK;
337 } 177 }
338 178
339 STDMETHODIMP BrowserAccessibilityComWin::get_relation( 179 STDMETHODIMP BrowserAccessibilityComWin::get_relation(
340 LONG relation_index, 180 LONG relation_index,
341 IAccessibleRelation** relation) { 181 IAccessibleRelation** relation) {
342 WIN_ACCESSIBILITY_API_HISTOGRAM(UMA_API_GET_RELATION); 182 WIN_ACCESSIBILITY_API_HISTOGRAM(UMA_API_GET_RELATION);
343 AddAccessibilityModeFlags(kScreenReaderAndHTMLAccessibilityModes); 183 AddAccessibilityModeFlags(kScreenReaderAndHTMLAccessibilityModes);
344 if (!owner()) 184 return AXPlatformNodeWin::get_relation(relation_index, relation);
345 return E_FAIL;
346
347 if (relation_index < 0 ||
348 relation_index >= static_cast<long>(relations_.size())) {
349 return E_INVALIDARG;
350 }
351
352 if (!relation)
353 return E_INVALIDARG;
354
355 relations_[relation_index]->AddRef();
356 *relation = relations_[relation_index];
357 return S_OK;
358 } 185 }
359 186
360 STDMETHODIMP BrowserAccessibilityComWin::get_relations( 187 STDMETHODIMP BrowserAccessibilityComWin::get_relations(
361 LONG max_relations, 188 LONG max_relations,
362 IAccessibleRelation** relations, 189 IAccessibleRelation** relations,
363 LONG* n_relations) { 190 LONG* n_relations) {
364 WIN_ACCESSIBILITY_API_HISTOGRAM(UMA_API_GET_RELATIONS); 191 WIN_ACCESSIBILITY_API_HISTOGRAM(UMA_API_GET_RELATIONS);
365 AddAccessibilityModeFlags(kScreenReaderAndHTMLAccessibilityModes); 192 AddAccessibilityModeFlags(kScreenReaderAndHTMLAccessibilityModes);
366 if (!owner()) 193 return AXPlatformNodeWin::get_relations(max_relations, relations,
367 return E_FAIL; 194 n_relations);
368
369 if (!relations || !n_relations)
370 return E_INVALIDARG;
371
372 long count = static_cast<long>(relations_.size());
373 *n_relations = count;
374 if (count == 0)
375 return S_FALSE;
376
377 for (long i = 0; i < count; ++i) {
378 relations_[i]->AddRef();
379 relations[i] = relations_[i];
380 }
381
382 return S_OK;
383 } 195 }
384 196
385 STDMETHODIMP BrowserAccessibilityComWin::scrollTo(IA2ScrollType scroll_type) { 197 STDMETHODIMP BrowserAccessibilityComWin::scrollTo(IA2ScrollType scroll_type) {
386 WIN_ACCESSIBILITY_API_HISTOGRAM(UMA_API_IA2_SCROLL_TO); 198 WIN_ACCESSIBILITY_API_HISTOGRAM(UMA_API_IA2_SCROLL_TO);
387 if (!owner()) 199 if (!owner())
388 return E_FAIL; 200 return E_FAIL;
389 201
390 auto* manager = Manager(); 202 auto* manager = Manager();
391 203
392 if (!manager) 204 if (!manager)
(...skipping 2240 matching lines...) Expand 10 before | Expand all | Expand 10 after
2633 value = base::UTF8ToUTF16(Manager()->GetTreeData().url); 2445 value = base::UTF8ToUTF16(Manager()->GetTreeData().url);
2634 } 2446 }
2635 // If this doesn't have a value and is linked then set its value to the url 2447 // If this doesn't have a value and is linked then set its value to the url
2636 // attribute. This allows screen readers to read an empty link's 2448 // attribute. This allows screen readers to read an empty link's
2637 // destination. 2449 // destination.
2638 if (value.empty() && (MSAAState() & STATE_SYSTEM_LINKED)) 2450 if (value.empty() && (MSAAState() & STATE_SYSTEM_LINKED))
2639 value = owner()->GetString16Attribute(ui::AX_ATTR_URL); 2451 value = owner()->GetString16Attribute(ui::AX_ATTR_URL);
2640 2452
2641 win_attributes_->value = value; 2453 win_attributes_->value = value;
2642 2454
2643 ClearOwnRelations(); 2455 CalculateRelationships();
2644 AddBidirectionalRelations(IA2_RELATION_CONTROLLER_FOR,
2645 IA2_RELATION_CONTROLLED_BY,
2646 ui::AX_ATTR_CONTROLS_IDS);
2647 AddBidirectionalRelations(IA2_RELATION_DESCRIBED_BY,
2648 IA2_RELATION_DESCRIPTION_FOR,
2649 ui::AX_ATTR_DESCRIBEDBY_IDS);
2650 AddBidirectionalRelations(IA2_RELATION_FLOWS_TO, IA2_RELATION_FLOWS_FROM,
2651 ui::AX_ATTR_FLOWTO_IDS);
2652 AddBidirectionalRelations(IA2_RELATION_LABELLED_BY, IA2_RELATION_LABEL_FOR,
2653 ui::AX_ATTR_LABELLEDBY_IDS);
2654
2655 int32_t details_id;
2656 if (GetIntAttribute(ui::AX_ATTR_DETAILS_ID, &details_id)) {
2657 std::vector<int32_t> details_ids;
2658 details_ids.push_back(details_id);
2659 AddBidirectionalRelations(IA2_RELATION_DETAILS, IA2_RELATION_DETAILS_FOR,
2660 details_ids);
2661 }
2662
2663 int member_of_id;
2664 if (owner()->GetIntAttribute(ui::AX_ATTR_MEMBER_OF_ID, &member_of_id))
2665 AddRelation(IA2_RELATION_MEMBER_OF, member_of_id);
2666
2667 int error_message_id;
2668 if (owner()->GetIntAttribute(ui::AX_ATTR_ERRORMESSAGE_ID, &error_message_id))
2669 AddRelation(IA2_RELATION_ERROR_MESSAGE, error_message_id);
2670 } 2456 }
2671 2457
2672 void BrowserAccessibilityComWin::UpdateStep2ComputeHypertext() { 2458 void BrowserAccessibilityComWin::UpdateStep2ComputeHypertext() {
2673 if (owner()->IsSimpleTextControl()) { 2459 if (owner()->IsSimpleTextControl()) {
2674 win_attributes_->hypertext = value(); 2460 win_attributes_->hypertext = value();
2675 return; 2461 return;
2676 } 2462 }
2677 2463
2678 if (!owner()->PlatformChildCount()) { 2464 if (!owner()->PlatformChildCount()) {
2679 if (owner()->IsRichTextControl()) { 2465 if (owner()->IsRichTextControl()) {
(...skipping 911 matching lines...) Expand 10 before | Expand all | Expand 10 after
3591 } 3377 }
3592 3378
3593 if (role == ui::AX_ROLE_MENU_LIST_OPTION && 3379 if (role == ui::AX_ROLE_MENU_LIST_OPTION &&
3594 parent_role == ui::AX_ROLE_MENU_LIST_POPUP) { 3380 parent_role == ui::AX_ROLE_MENU_LIST_POPUP) {
3595 return true; 3381 return true;
3596 } 3382 }
3597 3383
3598 return false; 3384 return false;
3599 } 3385 }
3600 3386
3601 void BrowserAccessibilityComWin::AddRelation(
3602 const base::string16& relation_type,
3603 int target_id) {
3604 // Reflexive relations don't need to be exposed through IA2.
3605 if (target_id == owner()->GetId())
3606 return;
3607
3608 CComObject<BrowserAccessibilityRelation>* relation;
3609 HRESULT hr =
3610 CComObject<BrowserAccessibilityRelation>::CreateInstance(&relation);
3611 DCHECK(SUCCEEDED(hr));
3612 relation->AddRef();
3613 relation->Initialize(this, relation_type);
3614 relation->AddTarget(target_id);
3615 relations_.push_back(relation);
3616 }
3617
3618 void BrowserAccessibilityComWin::AddBidirectionalRelations(
3619 const base::string16& relation_type,
3620 const base::string16& reverse_relation_type,
3621 ui::AXIntListAttribute attribute) {
3622 if (!owner()->HasIntListAttribute(attribute))
3623 return;
3624
3625 const std::vector<int32_t>& target_ids =
3626 owner()->GetIntListAttribute(attribute);
3627 AddBidirectionalRelations(relation_type, reverse_relation_type, target_ids);
3628 }
3629
3630 void BrowserAccessibilityComWin::AddBidirectionalRelations(
3631 const base::string16& relation_type,
3632 const base::string16& reverse_relation_type,
3633 const std::vector<int32_t>& target_ids) {
3634 // Reflexive relations don't need to be exposed through IA2.
3635 std::vector<int32_t> filtered_target_ids;
3636 int32_t current_id = owner()->GetId();
3637 std::copy_if(target_ids.begin(), target_ids.end(),
3638 std::back_inserter(filtered_target_ids),
3639 [current_id](int32_t id) { return id != current_id; });
3640 if (filtered_target_ids.empty())
3641 return;
3642
3643 CComObject<BrowserAccessibilityRelation>* relation;
3644 HRESULT hr =
3645 CComObject<BrowserAccessibilityRelation>::CreateInstance(&relation);
3646 DCHECK(SUCCEEDED(hr));
3647 relation->AddRef();
3648 relation->Initialize(this, relation_type);
3649
3650 for (int target_id : filtered_target_ids) {
3651 BrowserAccessibilityComWin* target =
3652 GetFromID(static_cast<int32_t>(target_id));
3653 if (!target || !target->owner())
3654 continue;
3655 relation->AddTarget(target_id);
3656 target->AddRelation(reverse_relation_type, owner()->GetId());
3657 }
3658
3659 relations_.push_back(relation);
3660 }
3661
3662 // Clears all the forward relations from this object to any other object and the
3663 // associated reverse relations on the other objects, but leaves any reverse
3664 // relations on this object alone.
3665 void BrowserAccessibilityComWin::ClearOwnRelations() {
3666 RemoveBidirectionalRelationsOfType(IA2_RELATION_CONTROLLER_FOR,
3667 IA2_RELATION_CONTROLLED_BY);
3668 RemoveBidirectionalRelationsOfType(IA2_RELATION_DESCRIBED_BY,
3669 IA2_RELATION_DESCRIPTION_FOR);
3670 RemoveBidirectionalRelationsOfType(IA2_RELATION_FLOWS_TO,
3671 IA2_RELATION_FLOWS_FROM);
3672 RemoveBidirectionalRelationsOfType(IA2_RELATION_LABELLED_BY,
3673 IA2_RELATION_LABEL_FOR);
3674
3675 relations_.erase(
3676 std::remove_if(relations_.begin(), relations_.end(),
3677 [](BrowserAccessibilityRelation* relation) {
3678 if (relation->get_type() == IA2_RELATION_MEMBER_OF) {
3679 relation->Release();
3680 return true;
3681 }
3682 return false;
3683 }),
3684 relations_.end());
3685 }
3686
3687 void BrowserAccessibilityComWin::RemoveBidirectionalRelationsOfType(
3688 const base::string16& relation_type,
3689 const base::string16& reverse_relation_type) {
3690 for (auto iter = relations_.begin(); iter != relations_.end();) {
3691 BrowserAccessibilityRelation* relation = *iter;
3692 DCHECK(relation);
3693 if (relation->get_type() == relation_type) {
3694 for (int target_id : relation->get_target_ids()) {
3695 BrowserAccessibilityComWin* target =
3696 GetFromID(static_cast<int32_t>(target_id));
3697 if (!target || !target->owner())
3698 continue;
3699 DCHECK_NE(target, this);
3700 target->RemoveTargetFromRelation(reverse_relation_type,
3701 owner()->GetId());
3702 }
3703 iter = relations_.erase(iter);
3704 relation->Release();
3705 } else {
3706 ++iter;
3707 }
3708 }
3709 }
3710
3711 void BrowserAccessibilityComWin::RemoveTargetFromRelation(
3712 const base::string16& relation_type,
3713 int target_id) {
3714 for (auto iter = relations_.begin(); iter != relations_.end();) {
3715 BrowserAccessibilityRelation* relation = *iter;
3716 DCHECK(relation);
3717 if (relation->get_type() == relation_type) {
3718 // If |target_id| is not present, |RemoveTarget| will do nothing.
3719 relation->RemoveTarget(target_id);
3720 }
3721 if (relation->get_target_ids().empty()) {
3722 iter = relations_.erase(iter);
3723 relation->Release();
3724 } else {
3725 ++iter;
3726 }
3727 }
3728 }
3729
3730 void BrowserAccessibilityComWin::FireNativeEvent(LONG win_event_type) const { 3387 void BrowserAccessibilityComWin::FireNativeEvent(LONG win_event_type) const {
3731 (new BrowserAccessibilityEventWin(BrowserAccessibilityEvent::FromTreeChange, 3388 (new BrowserAccessibilityEventWin(BrowserAccessibilityEvent::FromTreeChange,
3732 ui::AX_EVENT_NONE, win_event_type, owner())) 3389 ui::AX_EVENT_NONE, win_event_type, owner()))
3733 ->Fire(); 3390 ->Fire();
3734 } 3391 }
3735 3392
3736 BrowserAccessibilityComWin* ToBrowserAccessibilityComWin( 3393 BrowserAccessibilityComWin* ToBrowserAccessibilityComWin(
3737 BrowserAccessibility* obj) { 3394 BrowserAccessibility* obj) {
3738 if (!obj || !obj->IsNative()) 3395 if (!obj || !obj->IsNative())
3739 return nullptr; 3396 return nullptr;
3740 auto* result = static_cast<BrowserAccessibilityWin*>(obj)->GetCOM(); 3397 auto* result = static_cast<BrowserAccessibilityWin*>(obj)->GetCOM();
3741 return result; 3398 return result;
3742 } 3399 }
3743 3400
3744 } // namespace content 3401 } // namespace content
OLDNEW
« no previous file with comments | « content/browser/accessibility/browser_accessibility_com_win.h ('k') | ui/accessibility/platform/ax_platform_node_win.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698