1 /**************************************************************
2  *
3  * Licensed to the Apache Software Foundation (ASF) under one
4  * or more contributor license agreements.  See the NOTICE file
5  * distributed with this work for additional information
6  * regarding copyright ownership.  The ASF licenses this file
7  * to you under the Apache License, Version 2.0 (the
8  * "License"); you may not use this file except in compliance
9  * with the License.  You may obtain a copy of the License at
10  *
11  *   http://www.apache.org/licenses/LICENSE-2.0
12  *
13  * Unless required by applicable law or agreed to in writing,
14  * software distributed under the License is distributed on an
15  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16  * KIND, either express or implied.  See the License for the
17  * specific language governing permissions and limitations
18  * under the License.
19  *
20  *************************************************************/
21 
22 
23 
24 
25 #ifndef ACCESSIBILITY_EXT_ACCESSIBLEGRIDCONTROLBASE_HXX
26 #define ACCESSIBILITY_EXT_ACCESSIBLEGRIDCONTROLBASE_HXX
27 
28 #include <svtools/accessibletable.hxx>
29 #include <tools/debug.hxx>
30 #include <rtl/ustring.hxx>
31 #include <tools/gen.hxx>
32 #include <vcl/svapp.hxx>
33 #include <cppuhelper/compbase4.hxx>
34 #include <comphelper/broadcasthelper.hxx>
35 #include <unotools/accessiblestatesethelper.hxx>
36 #include <toolkit/helper/convert.hxx>
37 #include <com/sun/star/lang/XServiceInfo.hpp>
38 #include <com/sun/star/lang/DisposedException.hpp>
39 #include <com/sun/star/awt/XWindow.hpp>
40 #include <com/sun/star/accessibility/XAccessible.hpp>
41 #include <com/sun/star/accessibility/XAccessibleContext.hpp>
42 #include <com/sun/star/accessibility/XAccessibleComponent.hpp>
43 #include <com/sun/star/accessibility/XAccessibleEventBroadcaster.hpp>
44 #include <com/sun/star/accessibility/AccessibleRole.hpp>
45 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
46 #include <comphelper/accessibleeventnotifier.hxx>
47 #include <comphelper/uno3.hxx>
48 
49 // ============================================================================
50 
51 class Window;
52 
53 namespace utl {
54     class AccessibleStateSetHelper;
55 }
56 
57 // ============================================================================
58 
59 namespace accessibility {
60 
61 // ============================================================================
62 
63 /** Aquire the solar mutex. */
64 class TCSolarGuard : public ::vos::OGuard
65 {
66 public:
TCSolarGuard()67     inline TCSolarGuard() : ::vos::OGuard( Application::GetSolarMutex() ) {}
68 };
69 
70 // ============================================================================
71 
72 typedef ::cppu::WeakAggComponentImplHelper4<
73             ::com::sun::star::accessibility::XAccessibleContext,
74             ::com::sun::star::accessibility::XAccessibleComponent,
75             ::com::sun::star::accessibility::XAccessibleEventBroadcaster,
76             ::com::sun::star::lang::XServiceInfo >
77         AccessibleGridControlImplHelper;
78 
79 /** The GridControl accessible objects inherit from this base class. It
80     implements basic functionality for various Accessibility interfaces and
81     the event broadcaster and contains the ::osl::Mutex. */
82 class AccessibleGridControlBase :
83     public ::comphelper::OBaseMutex,
84     public AccessibleGridControlImplHelper
85 {
86 public:
87     /** Constructor sets specified name and description.
88         @param rxParent  XAccessible interface of the parent object.
89         @param rTable  The Table control.
90         @param eNameText  The constant for the name text.
91         @param eDescrText  The constant for the description text. */
92     AccessibleGridControlBase(
93         const ::com::sun::star::uno::Reference<
94             	::com::sun::star::accessibility::XAccessible >& rxParent,
95 		::svt::table::IAccessibleTable& rTable,
96 		::svt::table::AccessibleTableControlObjType  eObjType );
97 
98 protected:
99     virtual ~AccessibleGridControlBase();
100 
101     /** Commits DeFunc event to listeners and cleans up members. */
102     virtual void SAL_CALL disposing();
103 
104 public:
105     // XAccessibleContext -----------------------------------------------------
106 
107     /** @return  A reference to the parent accessible object. */
108     virtual ::com::sun::star::uno::Reference<
109         ::com::sun::star::accessibility::XAccessible > SAL_CALL
110     getAccessibleParent()
111         throw ( ::com::sun::star::uno::RuntimeException );
112 
113     /** @return  The index of this object among the parent's children. */
114     virtual sal_Int32 SAL_CALL getAccessibleIndexInParent()
115         throw ( ::com::sun::star::uno::RuntimeException );
116 
117     /** @return
118 			The description of this object.
119 	*/
120     virtual ::rtl::OUString SAL_CALL getAccessibleDescription()
121         throw ( ::com::sun::star::uno::RuntimeException );
122 
123     /** @return
124 			The name of this object.
125 	*/
126     virtual ::rtl::OUString SAL_CALL getAccessibleName()
127         throw ( ::com::sun::star::uno::RuntimeException );
128 
129     /** @return
130 			The relation set (the GridControl does not have one).
131 	*/
132 	virtual ::com::sun::star::uno::Reference<
133 	::com::sun::star::accessibility::XAccessibleRelationSet > SAL_CALL
134 		getAccessibleRelationSet()
135         throw ( ::com::sun::star::uno::RuntimeException );
136 
137     /** @return  The set of current states. */
138 	virtual ::com::sun::star::uno::Reference<
139         ::com::sun::star::accessibility::XAccessibleStateSet > SAL_CALL
140 		getAccessibleStateSet()
141         throw ( ::com::sun::star::uno::RuntimeException );
142 
143     /** @return  The parent's locale. */
144     virtual ::com::sun::star::lang::Locale SAL_CALL getLocale()
145         throw ( ::com::sun::star::accessibility::IllegalAccessibleComponentStateException,
146                 ::com::sun::star::uno::RuntimeException );
147 
148 	/** @return
149 			The role of this object. Panel, ROWHEADER, COLUMNHEADER, TABLE, TABLE_CELL are supported.
150 	*/
151     virtual sal_Int16 SAL_CALL getAccessibleRole()
152         throw ( ::com::sun::star::uno::RuntimeException );
153 
154     /*  Derived classes have to implement:
155         -   getAccessibleChildCount,
156         -   getAccessibleChild,
157         -   getAccessibleRole.
158         Derived classes may overwrite getAccessibleIndexInParent to increase
159         performance. */
160 
161     // XAccessibleComponent ---------------------------------------------------
162 
163     /** @return
164         <TRUE/>, if the point lies within the bounding box of this object. */
165     virtual sal_Bool SAL_CALL containsPoint( const ::com::sun::star::awt::Point& rPoint )
166         throw ( ::com::sun::star::uno::RuntimeException );
167 
168     /** @return  The bounding box of this object. */
169     virtual ::com::sun::star::awt::Rectangle SAL_CALL getBounds()
170         throw ( ::com::sun::star::uno::RuntimeException );
171 
172     /** @return
173         The upper left corner of the bounding box relative to the parent. */
174     virtual ::com::sun::star::awt::Point SAL_CALL getLocation()
175         throw ( ::com::sun::star::uno::RuntimeException );
176 
177     /** @return
178         The upper left corner of the bounding box in screen coordinates. */
179     virtual ::com::sun::star::awt::Point SAL_CALL getLocationOnScreen()
180         throw ( ::com::sun::star::uno::RuntimeException );
181 
182     /** @return  The size of the bounding box. */
183     virtual ::com::sun::star::awt::Size SAL_CALL getSize()
184         throw ( ::com::sun::star::uno::RuntimeException );
185 
186     /** @return  <TRUE/>, if the object is showing. */
187     virtual sal_Bool SAL_CALL isShowing()
188         throw ( ::com::sun::star::uno::RuntimeException );
189 
190     /** @return  <TRUE/>, if the object is visible. */
191     virtual sal_Bool SAL_CALL isVisible()
192         throw ( ::com::sun::star::uno::RuntimeException );
193 
194     /** @return  <TRUE/>, if the object can accept the focus. */
195     virtual sal_Bool SAL_CALL isFocusTraversable()
196         throw ( ::com::sun::star::uno::RuntimeException );
197 
198 	virtual sal_Int32 SAL_CALL getForeground(  ) throw (::com::sun::star::uno::RuntimeException);
199 	virtual sal_Int32 SAL_CALL getBackground(  ) throw (::com::sun::star::uno::RuntimeException);
200 
201 
202     /*  Derived classes have to implement:
203         -   getAccessibleAt,
204         -   grabFocus,
205         -   getAccessibleKeyBinding. */
206 
207 	/** @return
208 		No key bindings supported by default.
209 	*/
210     virtual ::com::sun::star::uno::Any SAL_CALL getAccessibleKeyBinding()
211         throw ( ::com::sun::star::uno::RuntimeException );
212 	/** @return
213 			The accessible child rendered under the given point.
214 	*/
215     virtual ::com::sun::star::uno::Reference<
216         ::com::sun::star::accessibility::XAccessible > SAL_CALL
217     getAccessibleAtPoint( const ::com::sun::star::awt::Point& rPoint )
218         throw ( ::com::sun::star::uno::RuntimeException );
219 
220     // XAccessibleEventBroadcaster --------------------------------------------
221 
222     /** Adds a new event listener */
223     using cppu::WeakAggComponentImplHelperBase::addEventListener;
224     virtual void SAL_CALL addEventListener(
225             const ::com::sun::star::uno::Reference<
226                 ::com::sun::star::accessibility::XAccessibleEventListener>& rxListener )
227         throw ( ::com::sun::star::uno::RuntimeException );
228 
229     /** Removes an event listener. */
230     using cppu::WeakAggComponentImplHelperBase::removeEventListener;
231     virtual void SAL_CALL removeEventListener(
232 			const ::com::sun::star::uno::Reference<
233                 ::com::sun::star::accessibility::XAccessibleEventListener>& rxListener )
234         throw ( ::com::sun::star::uno::RuntimeException );
235 
236     // XTypeProvider ----------------------------------------------------------
237 
238     /** @return  An unique implementation ID. */
239     virtual ::com::sun::star::uno::Sequence< sal_Int8 > SAL_CALL getImplementationId()
240         throw ( ::com::sun::star::uno::RuntimeException );
241 
242     // XServiceInfo -----------------------------------------------------------
243 
244     /** @return  Whether the specified service is supported by this class. */
245     virtual sal_Bool SAL_CALL supportsService( const ::rtl::OUString& rServiceName )
246         throw ( ::com::sun::star::uno::RuntimeException );
247 
248     /** @return  A list of all supported services. */
249     virtual ::com::sun::star::uno::Sequence< ::rtl::OUString > SAL_CALL
250     getSupportedServiceNames()
251         throw ( ::com::sun::star::uno::RuntimeException );
252 
253     /*  Derived classes have to implement:
254         -   getImplementationName. */
255 
256     // helper methods ---------------------------------------------------------
257 
258     /** @return  The GridControl object type. */
259 	inline ::svt::table::AccessibleTableControlObjType getType() const;
260 
261 	/** Commits an event to all listeners. */
262     void commitEvent(
263             sal_Int16 nEventId,
264             const ::com::sun::star::uno::Any& rNewValue,
265 
266     const ::com::sun::star::uno::Any& rOldValue );
267     /** @return  <TRUE/>, if the object is not disposed or disposing. */
268     sal_Bool isAlive() const;
269 
270 protected:
271     // internal virtual methods -----------------------------------------------
272 
273     /** Determines whether the Grid control is really showing inside of
274         its parent accessible window. Derived classes may implement different
275         behaviour.
276         @attention  This method requires locked mutex's and a living object.
277         @return  <TRUE/>, if the object is really showing. */
278     virtual sal_Bool implIsShowing();
279 
280     /** Derived classes return the bounding box relative to the parent window.
281         @attention  This method requires locked mutex's and a living object.
282         @return  The bounding box (VCL rect.) relative to the parent window. */
283     virtual Rectangle implGetBoundingBox() = 0;
284     ///** Derived classes return the bounding box in screen coordinates.
285     //    @attention  This method requires locked mutex's and a living object.
286     //    @return  The bounding box (VCL rect.) in screen coordinates. */
287     virtual Rectangle implGetBoundingBoxOnScreen() = 0;
288 
289     /** Creates a new AccessibleStateSetHelper and fills it with states of the
290         current object. This method calls FillStateSet at the GridControl which
291         fills it with more states depending on the object type. Derived classes
292         may overwrite this method and add more states.
293         @attention  This method requires locked mutex's.
294         @return  A filled AccessibleStateSetHelper. */
295     virtual ::utl::AccessibleStateSetHelper* implCreateStateSetHelper();
296 
297     // internal helper methods ------------------------------------------------
298 
299     /** @throws <type>DisposedException</type>  If the object is not alive. */
300     void ensureIsAlive() const
301         throw ( ::com::sun::star::lang::DisposedException );
302 
303     /** @return  The ::osl::Mutex member provided by the class OBaseMutex. */
304     inline ::osl::Mutex& getOslMutex();
305     /** @return  Pointer to the global ::osl::Mutex. */
306     static inline ::osl::Mutex* getOslGlobalMutex();
307 
308     /** Changes the name of the object (flat assignment, no notify).
309         @attention  This method requires a locked mutex. */
310     inline void implSetName( const ::rtl::OUString& rName );
311     /** Changes the description of the object (flat assignment, no notify).
312         @attention  This method requires a locked mutex. */
313     inline void implSetDescription( const ::rtl::OUString& rDescription );
314 
315     /** Locks all mutex's and calculates the bounding box relative to the
316         parent window.
317         @return  The bounding box (VCL rect.) relative to the parent object. */
318     Rectangle getBoundingBox()
319         throw ( ::com::sun::star::lang::DisposedException );
320     ///** Locks all mutex's and calculates the bounding box in screen
321     //    coordinates.
322     //    @return  The bounding box (VCL rect.) in screen coordinates. */
323     Rectangle getBoundingBoxOnScreen()
324         throw ( ::com::sun::star::lang::DisposedException );
325 
326     /** Creates a new UUID, if rId is empty.
327         @attention  This method requires locked global mutex to prevent double
328                     creation of an UUID. */
329     static void implCreateUuid( ::com::sun::star::uno::Sequence< sal_Int8 >& rId );
330 
getClientId() const331 	::comphelper::AccessibleEventNotifier::TClientId getClientId() const { return m_aClientId; }
setClientId(::comphelper::AccessibleEventNotifier::TClientId _aNewClientId)332 	void setClientId(::comphelper::AccessibleEventNotifier::TClientId _aNewClientId) { m_aClientId = _aNewClientId; }
333 
334 public:
335 	// public versions of internal helper methods, with access control
TC_AccessControlaccessibility::AccessibleGridControlBase::TC_AccessControl336 	struct TC_AccessControl { friend class TC_SolarMethodGuard; private: TC_AccessControl() { } };
337 
getMutex(const TC_AccessControl &)338 	inline ::osl::Mutex&	getMutex( const TC_AccessControl& ) { return getOslMutex(); }
ensureIsAlive(const TC_AccessControl &)339 	inline void             ensureIsAlive( const TC_AccessControl& ) { ensureIsAlive(); }
340 
341 protected:
342     // members ----------------------------------------------------------------
343 
344     /** The parent accessible object. */
345     ::com::sun::star::uno::Reference<
346         ::com::sun::star::accessibility::XAccessible > m_xParent;
347     /** The SVT Table control. */
348 	::svt::table::IAccessibleTable& m_aTable;
349 	/** The type of this object (for names, descriptions, state sets, ...). */
350 	::svt::table::AccessibleTableControlObjType m_eObjType;
351 
352 private:
353     /** Localized name. */
354     ::rtl::OUString m_aName;
355     /** Localized description text. */
356     ::rtl::OUString m_aDescription;
357 	::comphelper::AccessibleEventNotifier::TClientId	m_aClientId;
358 };
359 
360 // ============================================================================
361 // a version of AccessibleGridControlBase which implements not only the XAccessibleContext,
362 // but also the XAccessible
363 
364 typedef ::cppu::ImplHelper1	<	::com::sun::star::accessibility::XAccessible
365 							>	GridControlAccessibleElement_Base;
366 
367 class GridControlAccessibleElement
368 			:public AccessibleGridControlBase
369 			,public GridControlAccessibleElement_Base
370 {
371 protected:
372     /** Constructor sets specified name and description.
373 
374 		@param rxParent  XAccessible interface of the parent object.
375         @param rTable  The Table control.
376         @param eNameText  The constant for the name text.
377         @param eDescrText  The constant for the description text.
378 	*/
379     GridControlAccessibleElement(
380         const ::com::sun::star::uno::Reference<
381             ::com::sun::star::accessibility::XAccessible >& rxParent,
382 			::svt::table::IAccessibleTable& rTable,
383 		::svt::table::AccessibleTableControlObjType  eObjType );
384 
385 public:
386 	// XInterface
387 	DECLARE_XINTERFACE( )
388 	// XTypeProvider
389 	DECLARE_XTYPEPROVIDER( )
390 
391 protected:
392     virtual ~GridControlAccessibleElement();
393 
394 protected:
395 	// XAccessible ------------------------------------------------------------
396 
397 	/** @return  The XAccessibleContext interface of this object. */
398 	virtual ::com::sun::star::uno::Reference<
399 		::com::sun::star::accessibility::XAccessibleContext > SAL_CALL
400 	getAccessibleContext()
401 		throw ( ::com::sun::star::uno::RuntimeException );
402 
403 private:
404 	GridControlAccessibleElement();												// never implemented
405 	GridControlAccessibleElement( const GridControlAccessibleElement& );		// never implemented
406 	GridControlAccessibleElement& operator=( const GridControlAccessibleElement& );	// never implemented
407 };
408 
409 // ============================================================================
410 // a helper class for protecting methods which need to lock the solar mutex in addition to the own mutex
411 
412 typedef ::osl::MutexGuard OslMutexGuard;
413 
414 class TC_SolarMethodGuard : public TCSolarGuard, public OslMutexGuard
415 {
416 public:
TC_SolarMethodGuard(AccessibleGridControlBase & _rOwner,bool _bEnsureAlive=true)417 	inline TC_SolarMethodGuard( AccessibleGridControlBase& _rOwner, bool _bEnsureAlive = true )
418 		:TCSolarGuard( )
419 		,OslMutexGuard( _rOwner.getMutex( AccessibleGridControlBase::TC_AccessControl() ) )
420 	{
421 		if ( _bEnsureAlive )
422 			_rOwner.ensureIsAlive( AccessibleGridControlBase::TC_AccessControl() );
423 	}
424 };
425 
426 // inlines --------------------------------------------------------------------
427 
getType() const428 inline ::svt::table::AccessibleTableControlObjType AccessibleGridControlBase::getType() const
429 {
430     return m_eObjType;
431 }
432 
getOslMutex()433 inline ::osl::Mutex& AccessibleGridControlBase::getOslMutex()
434 {
435     return m_aMutex;
436 }
437 
getOslGlobalMutex()438 inline ::osl::Mutex* AccessibleGridControlBase::getOslGlobalMutex()
439 {
440     return ::osl::Mutex::getGlobalMutex();
441 }
442 
implSetName(const::rtl::OUString & rName)443 inline void AccessibleGridControlBase::implSetName(
444         const ::rtl::OUString& rName )
445 {
446     m_aName = rName;
447 }
448 
implSetDescription(const::rtl::OUString & rDescription)449 inline void AccessibleGridControlBase::implSetDescription(
450         const ::rtl::OUString& rDescription )
451 {
452     m_aDescription = rDescription;
453 }
454 
455 // ============================================================================
456 
457 } // namespace accessibility
458 
459 // ============================================================================
460 
461 #endif // ACCESSIBILITY_EXT_ACCESSIBILEGRIDCONTROLBASE_HXX
462 
463