1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=2 et sw=2 tw=80: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4  * License, v. 2.0. If a copy of the MPL was not distributed with this
5  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 
7 #ifndef mozilla_a11y_AccessibleWrap_h_
8 #define mozilla_a11y_AccessibleWrap_h_
9 
10 #include "nsCOMPtr.h"
11 #include "LocalAccessible.h"
12 #include "MsaaAccessible.h"
13 #include "mozilla/a11y/AccessibleHandler.h"
14 #include "mozilla/a11y/RemoteAccessible.h"
15 #include "mozilla/Attributes.h"
16 #include "mozilla/mscom/Utils.h"
17 #include "mozilla/StaticPrefs_accessibility.h"
18 #include "mozilla/StaticPtr.h"
19 #include "nsXULAppAPI.h"
20 #include "Units.h"
21 
22 namespace mozilla {
23 namespace a11y {
24 class DocRemoteAccessibleWrap;
25 
26 class AccessibleWrap : public LocalAccessible {
27  public:  // construction, destruction
28   AccessibleWrap(nsIContent* aContent, DocAccessible* aDoc);
29 
30   // nsISupports
31   NS_DECL_ISUPPORTS_INHERITED
32 
33  public:
34   // LocalAccessible
35   virtual nsresult HandleAccEvent(AccEvent* aEvent) override;
36   virtual void Shutdown() override;
37 
38   // Helper methods
39   /**
40    * System caret support: update the Windows caret position.
41    * The system caret works more universally than the MSAA caret
42    * For example, Window-Eyes, JAWS, ZoomText and Windows Tablet Edition use it
43    * We will use an invisible system caret.
44    * Gecko is still responsible for drawing its own caret
45    */
46   void UpdateSystemCaretFor(LocalAccessible* aAccessible);
47   static void UpdateSystemCaretFor(RemoteAccessible* aProxy,
48                                    const LayoutDeviceIntRect& aCaretRect);
49 
50  private:
51   static void UpdateSystemCaretFor(HWND aCaretWnd,
52                                    const LayoutDeviceIntRect& aCaretRect);
53 
54  public:
55   /**
56    * Determine whether this is the root accessible for its HWND.
57    */
58   bool IsRootForHWND();
59 
60   MsaaAccessible* GetMsaa();
61   virtual void GetNativeInterface(void** aOutAccessible) override;
62 
63   static void SetHandlerControl(DWORD aPid, RefPtr<IHandlerControl> aCtrl);
64 
65   static void InvalidateHandlers();
66 
67   bool DispatchTextChangeToHandler(bool aIsInsert, const nsString& aText,
68                                    int32_t aStart, uint32_t aLen);
69 
70  protected:
71   virtual ~AccessibleWrap() = default;
72 
73   RefPtr<MsaaAccessible> mMsaa;
74 
75   struct HandlerControllerData final {
HandlerControllerDatafinal76     HandlerControllerData(DWORD aPid, RefPtr<IHandlerControl>&& aCtrl)
77         : mPid(aPid), mCtrl(std::move(aCtrl)) {
78       mIsProxy = mozilla::mscom::IsProxy(mCtrl);
79     }
80 
HandlerControllerDatafinal81     HandlerControllerData(HandlerControllerData&& aOther)
82         : mPid(aOther.mPid),
83           mIsProxy(aOther.mIsProxy),
84           mCtrl(std::move(aOther.mCtrl)) {}
85 
86     bool operator==(const HandlerControllerData& aOther) const {
87       return mPid == aOther.mPid;
88     }
89 
90     bool operator==(const DWORD& aPid) const { return mPid == aPid; }
91 
92     DWORD mPid;
93     bool mIsProxy;
94     RefPtr<IHandlerControl> mCtrl;
95   };
96 
97   static StaticAutoPtr<nsTArray<HandlerControllerData>> sHandlerControllers;
98 };
99 
WrapperFor(const RemoteAccessible * aProxy)100 static inline AccessibleWrap* WrapperFor(const RemoteAccessible* aProxy) {
101   MOZ_ASSERT(!StaticPrefs::accessibility_cache_enabled_AtStartup());
102   return reinterpret_cast<AccessibleWrap*>(aProxy->GetWrapper());
103 }
104 
105 }  // namespace a11y
106 }  // namespace mozilla
107 
108 #endif
109