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

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

Issue 8775059: Relanding http://codereview.chromium.org/8416034 (Closed) Base URL: http://git.chromium.org/git/chromium.git@trunk
Patch Set: Windows mucking up line endings for Mac file. Created 9 years 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 | Annotate | Revision Log
« no previous file with comments | « content/browser/accessibility/browser_accessibility_win.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2011 The Chromium Authors. All rights reserved. 1 // Copyright (c) 2011 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_win.h" 5 #include "content/browser/accessibility/browser_accessibility_win.h"
6 6
7 #include "base/string_number_conversions.h" 7 #include "base/string_number_conversions.h"
8 #include "base/string_util.h" 8 #include "base/string_util.h"
9 #include "base/utf_string_conversions.h" 9 #include "base/utf_string_conversions.h"
10 #include "base/win/scoped_comptr.h" 10 #include "base/win/scoped_comptr.h"
11 #include "content/browser/accessibility/browser_accessibility_manager_win.h" 11 #include "content/browser/accessibility/browser_accessibility_manager_win.h"
12 #include "content/common/view_messages.h" 12 #include "content/common/view_messages.h"
13 #include "net/base/escape.h" 13 #include "net/base/escape.h"
14 #include "ui/base/accessibility/accessible_text_utils.h" 14 #include "ui/base/accessibility/accessible_text_utils.h"
15 15
16 using webkit_glue::WebAccessibility; 16 using webkit_glue::WebAccessibility;
17 17
18 // The GUID for the ISimpleDOM service is not defined in the IDL files. 18 // The GUID for the ISimpleDOM service is not defined in the IDL files.
19 // This is taken directly from the Mozilla sources 19 // This is taken directly from the Mozilla sources
20 // (accessible/src/msaa/nsAccessNodeWrap.cpp) and it's also documented at: 20 // (accessible/src/msaa/nsAccessNodeWrap.cpp) and it's also documented at:
21 // http://developer.mozilla.org/en/Accessibility/AT-APIs/ImplementationFeatures/ MSAA 21 // http://developer.mozilla.org/en/Accessibility/AT-APIs/ImplementationFeatures/ MSAA
22 22
23 const GUID GUID_ISimpleDOM = { 23 const GUID GUID_ISimpleDOM = {
24 0x0c539790, 0x12e4, 0x11cf, 24 0x0c539790, 0x12e4, 0x11cf,
25 0xb6, 0x61, 0x00, 0xaa, 0x00, 0x4c, 0xd6, 0xd8}; 25 0xb6, 0x61, 0x00, 0xaa, 0x00, 0x4c, 0xd6, 0xd8};
26 26
27 const char16 BrowserAccessibilityWin::kEmbeddedCharacter[] = L"\xfffc";
28
27 // 29 //
28 // BrowserAccessibilityRelation 30 // BrowserAccessibilityRelation
29 // 31 //
30 // A simple implementation of IAccessibleRelation, used to represent 32 // A simple implementation of IAccessibleRelation, used to represent
31 // a relationship between two accessible nodes in the tree. 33 // a relationship between two accessible nodes in the tree.
32 // 34 //
33 35
34 class BrowserAccessibilityRelation 36 class BrowserAccessibilityRelation
35 : public CComObjectRootEx<CComMultiThreadModel>, 37 : public CComObjectRootEx<CComMultiThreadModel>,
36 public IAccessibleRelation { 38 public IAccessibleRelation {
(...skipping 1557 matching lines...) Expand 10 before | Expand all | Expand 10 after
1594 // IAccessibleText methods. 1596 // IAccessibleText methods.
1595 // 1597 //
1596 1598
1597 STDMETHODIMP BrowserAccessibilityWin::get_nCharacters(LONG* n_characters) { 1599 STDMETHODIMP BrowserAccessibilityWin::get_nCharacters(LONG* n_characters) {
1598 if (!instance_active_) 1600 if (!instance_active_)
1599 return E_FAIL; 1601 return E_FAIL;
1600 1602
1601 if (!n_characters) 1603 if (!n_characters)
1602 return E_INVALIDARG; 1604 return E_INVALIDARG;
1603 1605
1604 if (role_ == WebAccessibility::ROLE_TEXT_FIELD || 1606 *n_characters = TextForIAccessibleText().length();
1605 role_ == WebAccessibility::ROLE_TEXTAREA) {
1606 *n_characters = value_.length();
1607 } else {
1608 *n_characters = name_.length();
1609 }
1610
1611 return S_OK; 1607 return S_OK;
1612 } 1608 }
1613 1609
1614 STDMETHODIMP BrowserAccessibilityWin::get_caretOffset(LONG* offset) { 1610 STDMETHODIMP BrowserAccessibilityWin::get_caretOffset(LONG* offset) {
1615 if (!instance_active_) 1611 if (!instance_active_)
1616 return E_FAIL; 1612 return E_FAIL;
1617 1613
1618 if (!offset) 1614 if (!offset)
1619 return E_INVALIDARG; 1615 return E_INVALIDARG;
1620 1616
(...skipping 226 matching lines...) Expand 10 before | Expand all | Expand 10 after
1847 return E_INVALIDARG; 1843 return E_INVALIDARG;
1848 1844
1849 // TODO(dmazzoni): implement this. We're returning S_OK for now so that 1845 // TODO(dmazzoni): implement this. We're returning S_OK for now so that
1850 // screen readers still return partially accurate results rather than 1846 // screen readers still return partially accurate results rather than
1851 // completely failing. 1847 // completely failing.
1852 *offset = 0; 1848 *offset = 0;
1853 return S_OK; 1849 return S_OK;
1854 } 1850 }
1855 1851
1856 // 1852 //
1853 // IAccessibleHypertext methods.
1854 //
1855
1856 STDMETHODIMP BrowserAccessibilityWin::get_nHyperlinks(long* hyperlink_count) {
1857 if (!instance_active_)
1858 return E_FAIL;
1859
1860 if (!hyperlink_count)
1861 return E_INVALIDARG;
1862
1863 *hyperlink_count = hyperlink_offset_to_index_.size();
1864 return S_OK;
1865 }
1866
1867 STDMETHODIMP BrowserAccessibilityWin::get_hyperlink(
1868 long index,
1869 IAccessibleHyperlink** hyperlink) {
1870 if (!instance_active_)
1871 return E_FAIL;
1872
1873 if (!hyperlink ||
1874 index < 0 ||
1875 index >= static_cast<long>(hyperlinks_.size())) {
1876 return E_INVALIDARG;
1877 }
1878
1879 BrowserAccessibilityWin* child =
1880 children_[hyperlinks_[index]]->toBrowserAccessibilityWin();
1881 *hyperlink = static_cast<IAccessibleHyperlink*>(child->NewReference());
1882 return S_OK;
1883 }
1884
1885 STDMETHODIMP BrowserAccessibilityWin::get_hyperlinkIndex(
1886 long char_index,
1887 long* hyperlink_index) {
1888 if (!instance_active_)
1889 return E_FAIL;
1890
1891 if (!hyperlink_index)
1892 return E_INVALIDARG;
1893
1894 *hyperlink_index = -1;
1895
1896 if (char_index < 0 || char_index >= static_cast<long>(hypertext_.size()))
1897 return E_INVALIDARG;
1898
1899 std::map<int32, int32>::iterator it =
1900 hyperlink_offset_to_index_.find(char_index);
1901 if (it == hyperlink_offset_to_index_.end())
1902 return E_FAIL;
1903
1904 *hyperlink_index = it->second;
1905 return S_OK;
1906 }
1907
1908 //
1857 // IAccessibleValue methods. 1909 // IAccessibleValue methods.
1858 // 1910 //
1859 1911
1860 STDMETHODIMP BrowserAccessibilityWin::get_currentValue(VARIANT* value) { 1912 STDMETHODIMP BrowserAccessibilityWin::get_currentValue(VARIANT* value) {
1861 if (!instance_active_) 1913 if (!instance_active_)
1862 return E_FAIL; 1914 return E_FAIL;
1863 1915
1864 if (!value) 1916 if (!value)
1865 return E_INVALIDARG; 1917 return E_INVALIDARG;
1866 1918
(...skipping 373 matching lines...) Expand 10 before | Expand all | Expand 10 after
2240 // IServiceProvider methods. 2292 // IServiceProvider methods.
2241 // 2293 //
2242 2294
2243 STDMETHODIMP BrowserAccessibilityWin::QueryService( 2295 STDMETHODIMP BrowserAccessibilityWin::QueryService(
2244 REFGUID guidService, REFIID riid, void** object) { 2296 REFGUID guidService, REFIID riid, void** object) {
2245 if (!instance_active_) 2297 if (!instance_active_)
2246 return E_FAIL; 2298 return E_FAIL;
2247 2299
2248 if (guidService == IID_IAccessible || 2300 if (guidService == IID_IAccessible ||
2249 guidService == IID_IAccessible2 || 2301 guidService == IID_IAccessible2 ||
2302 guidService == IID_IAccessibleAction ||
2303 guidService == IID_IAccessibleHyperlink ||
2304 guidService == IID_IAccessibleHypertext ||
2250 guidService == IID_IAccessibleImage || 2305 guidService == IID_IAccessibleImage ||
2251 guidService == IID_IAccessibleTable || 2306 guidService == IID_IAccessibleTable ||
2252 guidService == IID_IAccessibleTable2 || 2307 guidService == IID_IAccessibleTable2 ||
2253 guidService == IID_IAccessibleTableCell || 2308 guidService == IID_IAccessibleTableCell ||
2254 guidService == IID_IAccessibleText || 2309 guidService == IID_IAccessibleText ||
2255 guidService == IID_IAccessibleValue || 2310 guidService == IID_IAccessibleValue ||
2256 guidService == IID_ISimpleDOMDocument || 2311 guidService == IID_ISimpleDOMDocument ||
2257 guidService == IID_ISimpleDOMNode || 2312 guidService == IID_ISimpleDOMNode ||
2258 guidService == IID_ISimpleDOMText || 2313 guidService == IID_ISimpleDOMText ||
2259 guidService == GUID_ISimpleDOM) { 2314 guidService == GUID_ISimpleDOM) {
2260 return QueryInterface(riid, object); 2315 return QueryInterface(riid, object);
2261 } 2316 }
2262 2317
2263 *object = NULL; 2318 *object = NULL;
2264 return E_FAIL; 2319 return E_FAIL;
2265 } 2320 }
2266 2321
2267 // 2322 //
2268 // CComObjectRootEx methods. 2323 // CComObjectRootEx methods.
2269 // 2324 //
2270 2325
2271 HRESULT WINAPI BrowserAccessibilityWin::InternalQueryInterface( 2326 HRESULT WINAPI BrowserAccessibilityWin::InternalQueryInterface(
2272 void* this_ptr, 2327 void* this_ptr,
2273 const _ATL_INTMAP_ENTRY* entries, 2328 const _ATL_INTMAP_ENTRY* entries,
2274 REFIID iid, 2329 REFIID iid,
2275 void** object) { 2330 void** object) {
2276 if (iid == IID_IAccessibleText) { 2331 if (iid == IID_IAccessibleImage) {
2277 if (ia_role_ != ROLE_SYSTEM_LINK && ia_role_ != ROLE_SYSTEM_TEXT) {
2278 *object = NULL;
2279 return E_NOINTERFACE;
2280 }
2281 } else if (iid == IID_IAccessibleImage) {
2282 if (ia_role_ != ROLE_SYSTEM_GRAPHIC) { 2332 if (ia_role_ != ROLE_SYSTEM_GRAPHIC) {
2283 *object = NULL; 2333 *object = NULL;
2284 return E_NOINTERFACE; 2334 return E_NOINTERFACE;
2285 } 2335 }
2286 } else if (iid == IID_IAccessibleTable || iid == IID_IAccessibleTable2) { 2336 } else if (iid == IID_IAccessibleTable || iid == IID_IAccessibleTable2) {
2287 if (ia_role_ != ROLE_SYSTEM_TABLE) { 2337 if (ia_role_ != ROLE_SYSTEM_TABLE) {
2288 *object = NULL; 2338 *object = NULL;
2289 return E_NOINTERFACE; 2339 return E_NOINTERFACE;
2290 } 2340 }
2291 } else if (iid == IID_IAccessibleTableCell) { 2341 } else if (iid == IID_IAccessibleTableCell) {
(...skipping 17 matching lines...) Expand all
2309 2359
2310 return CComObjectRootBase::InternalQueryInterface( 2360 return CComObjectRootBase::InternalQueryInterface(
2311 this_ptr, entries, iid, object); 2361 this_ptr, entries, iid, object);
2312 } 2362 }
2313 2363
2314 // 2364 //
2315 // Private methods. 2365 // Private methods.
2316 // 2366 //
2317 2367
2318 // Initialize this object and mark it as active. 2368 // Initialize this object and mark it as active.
2319 void BrowserAccessibilityWin::Initialize() { 2369 void BrowserAccessibilityWin::PreInitialize() {
2320 BrowserAccessibility::Initialize(); 2370 BrowserAccessibility::PreInitialize();
2321 2371
2322 InitRoleAndState(); 2372 InitRoleAndState();
2323 2373
2324 // Expose headings levels with the "level" attribute. 2374 // Expose headings levels with the "level" attribute.
2325 if (role_ == WebAccessibility::ROLE_HEADING && role_name_.size() == 2 && 2375 if (role_ == WebAccessibility::ROLE_HEADING && role_name_.size() == 2 &&
2326 IsAsciiDigit(role_name_[1])) { 2376 IsAsciiDigit(role_name_[1])) {
2327 ia2_attributes_.push_back(string16(L"level:") + role_name_.substr(1)); 2377 ia2_attributes_.push_back(string16(L"level:") + role_name_.substr(1));
2328 } 2378 }
2329 2379
2330 // Expose the "display" and "tag" attributes. 2380 // Expose the "display" and "tag" attributes.
(...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after
2417 HRESULT hr = CComObject<BrowserAccessibilityRelation>::CreateInstance( 2467 HRESULT hr = CComObject<BrowserAccessibilityRelation>::CreateInstance(
2418 &relation); 2468 &relation);
2419 DCHECK(SUCCEEDED(hr)); 2469 DCHECK(SUCCEEDED(hr));
2420 relation->AddRef(); 2470 relation->AddRef();
2421 relation->Initialize(this, IA2_RELATION_LABELLED_BY); 2471 relation->Initialize(this, IA2_RELATION_LABELLED_BY);
2422 relation->AddTarget(title_elem_id); 2472 relation->AddTarget(title_elem_id);
2423 relations_.push_back(relation); 2473 relations_.push_back(relation);
2424 } 2474 }
2425 } 2475 }
2426 2476
2427 void BrowserAccessibilityWin::SendNodeUpdateEvents() { 2477 void BrowserAccessibilityWin::PostInitialize() {
2478 BrowserAccessibility::PostInitialize();
2479
2480 // Construct the hypertext for this node.
2481 hyperlink_offset_to_index_.clear();
2482 hyperlinks_.clear();
2483 hypertext_.clear();
2484 for (unsigned int i = 0; i < children().size(); ++i) {
2485 BrowserAccessibility* child = children()[i];
2486 if (child->role() == WebAccessibility::ROLE_STATIC_TEXT) {
2487 hypertext_ += child->name();
2488 } else {
2489 hyperlink_offset_to_index_[hypertext_.size()] = hyperlinks_.size();
2490 hypertext_ += kEmbeddedCharacter;
2491 hyperlinks_.push_back(i);
2492 }
2493 }
2494 DCHECK_EQ(hyperlink_offset_to_index_.size(), hyperlinks_.size());
2495
2428 // Fire an event when an alert first appears. 2496 // Fire an event when an alert first appears.
2429 if (role_ == WebAccessibility::ROLE_ALERT && first_time_) 2497 if (role_ == WebAccessibility::ROLE_ALERT && first_time_)
2430 manager_->NotifyAccessibilityEvent(ViewHostMsg_AccEvent::ALERT, this); 2498 manager_->NotifyAccessibilityEvent(ViewHostMsg_AccEvent::ALERT, this);
2431 2499
2432 // Fire events if text has changed. 2500 // Fire events if text has changed.
2433 string16 text = TextForIAccessibleText(); 2501 string16 text = TextForIAccessibleText();
2434 if (previous_text_ != text) { 2502 if (previous_text_ != text) {
2435 if (!previous_text_.empty() && !text.empty()) { 2503 if (!previous_text_.empty() && !text.empty()) {
2436 manager_->NotifyAccessibilityEvent( 2504 manager_->NotifyAccessibilityEvent(
2437 ViewHostMsg_AccEvent::OBJECT_SHOW, this); 2505 ViewHostMsg_AccEvent::OBJECT_SHOW, this);
(...skipping 76 matching lines...) Expand 10 before | Expand all | Expand 10 after
2514 base::IntToString16(value)); 2582 base::IntToString16(value));
2515 } 2583 }
2516 2584
2517 string16 BrowserAccessibilityWin::Escape(const string16& str) { 2585 string16 BrowserAccessibilityWin::Escape(const string16& str) {
2518 return net::EscapeQueryParamValueUTF8(str, false); 2586 return net::EscapeQueryParamValueUTF8(str, false);
2519 } 2587 }
2520 2588
2521 const string16& BrowserAccessibilityWin::TextForIAccessibleText() { 2589 const string16& BrowserAccessibilityWin::TextForIAccessibleText() {
2522 if (IsEditableText()) { 2590 if (IsEditableText()) {
2523 return value_; 2591 return value_;
2592 } else if (role_ == WebAccessibility::ROLE_STATIC_TEXT) {
2593 return name_;
2524 } else { 2594 } else {
2525 return name_; 2595 return hypertext_;
2526 } 2596 }
2527 } 2597 }
2528 2598
2529 void BrowserAccessibilityWin::HandleSpecialTextOffset( 2599 void BrowserAccessibilityWin::HandleSpecialTextOffset(
2530 const string16& text, LONG* offset) { 2600 const string16& text, LONG* offset) {
2531 if (*offset == IA2_TEXT_OFFSET_LENGTH) { 2601 if (*offset == IA2_TEXT_OFFSET_LENGTH) {
2532 *offset = static_cast<LONG>(text.size()); 2602 *offset = static_cast<LONG>(text.size());
2533 } else if (*offset == IA2_TEXT_OFFSET_CARET) { 2603 } else if (*offset == IA2_TEXT_OFFSET_CARET) {
2534 get_caretOffset(offset); 2604 get_caretOffset(offset);
2535 } 2605 }
(...skipping 430 matching lines...) Expand 10 before | Expand all | Expand 10 after
2966 } 3036 }
2967 3037
2968 // The role should always be set. 3038 // The role should always be set.
2969 DCHECK(!role_name_.empty() || ia_role_); 3039 DCHECK(!role_name_.empty() || ia_role_);
2970 3040
2971 // If we didn't explicitly set the IAccessible2 role, make it the same 3041 // If we didn't explicitly set the IAccessible2 role, make it the same
2972 // as the MSAA role. 3042 // as the MSAA role.
2973 if (!ia2_role_) 3043 if (!ia2_role_)
2974 ia2_role_ = ia_role_; 3044 ia2_role_ = ia_role_;
2975 } 3045 }
OLDNEW
« no previous file with comments | « content/browser/accessibility/browser_accessibility_win.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698