1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: AccessibleParaManager.cxx,v $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_svx.hxx"
34 //------------------------------------------------------------------------
38 //------------------------------------------------------------------------
39 #include <com/sun/star/uno/Any.hxx>
40 #include <com/sun/star/uno/Reference.hxx>
41 #include <cppuhelper/weakref.hxx>
42 #include <com/sun/star/accessibility/XAccessible.hpp>
43 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
45 //------------------------------------------------------------------------
47 // Project-local header
49 //------------------------------------------------------------------------
51 #include "unoedhlp.hxx"
52 #include "unopracc.hxx"
53 #include <svx/unoedsrc.hxx>
54 #include "AccessibleParaManager.hxx"
55 #include "AccessibleEditableTextPara.hxx"
58 using namespace ::com::sun::star
;
59 using namespace ::com::sun::star::accessibility
;
63 namespace accessibility
65 AccessibleParaManager::AccessibleParaManager() :
73 AccessibleParaManager::~AccessibleParaManager()
75 // owner is responsible for possible child defuncs
78 void AccessibleParaManager::SetAdditionalChildStates( const VectorOfStates
& rChildStates
)
80 maChildStates
= rChildStates
;
83 const AccessibleParaManager::VectorOfStates
& AccessibleParaManager::GetAdditionalChildStates() const
88 void AccessibleParaManager::SetNum( sal_Int32 nNumParas
)
90 if( (size_t)nNumParas
< maChildren
.size() )
91 Release( nNumParas
, maChildren
.size() );
93 maChildren
.resize( nNumParas
);
95 if( mnFocusedChild
>= nNumParas
)
99 sal_uInt32
AccessibleParaManager::GetNum() const
101 return maChildren
.size();
104 AccessibleParaManager::VectorOfChildren::iterator
AccessibleParaManager::begin()
106 return maChildren
.begin();
109 AccessibleParaManager::VectorOfChildren::iterator
AccessibleParaManager::end()
111 return maChildren
.end();
114 AccessibleParaManager::VectorOfChildren::const_iterator
AccessibleParaManager::begin() const
116 return maChildren
.begin();
119 AccessibleParaManager::VectorOfChildren::const_iterator
AccessibleParaManager::end() const
121 return maChildren
.end();
124 void AccessibleParaManager::Release( sal_uInt32 nPara
)
126 DBG_ASSERT( maChildren
.size() > nPara
, "AccessibleParaManager::Release: invalid index" );
128 if( maChildren
.size() > nPara
)
130 ShutdownPara( GetChild( nPara
) );
132 // clear reference and rect
133 maChildren
[ nPara
] = WeakChild();
137 void AccessibleParaManager::FireEvent( sal_uInt32 nPara
,
138 const sal_Int16 nEventId
,
139 const uno::Any
& rNewValue
,
140 const uno::Any
& rOldValue
) const
142 DBG_ASSERT( maChildren
.size() > nPara
, "AccessibleParaManager::FireEvent: invalid index" );
144 if( maChildren
.size() > nPara
)
146 WeakPara::HardRefType
maChild( GetChild( nPara
).first
.get() );
148 maChild
->FireEvent( nEventId
, rNewValue
, rOldValue
);
152 sal_Bool
AccessibleParaManager::IsReferencable( WeakPara::HardRefType aChild
)
157 sal_Bool
AccessibleParaManager::IsReferencable( sal_uInt32 nChild
) const
159 DBG_ASSERT( maChildren
.size() > nChild
, "AccessibleParaManager::IsReferencable: invalid index" );
161 if( maChildren
.size() > nChild
)
163 // retrieve hard reference from weak one
164 return IsReferencable( GetChild( nChild
).first
.get() );
172 AccessibleParaManager::WeakChild
AccessibleParaManager::GetChild( sal_uInt32 nParagraphIndex
) const
174 DBG_ASSERT( maChildren
.size() > nParagraphIndex
, "AccessibleParaManager::GetChild: invalid index" );
176 if( maChildren
.size() > nParagraphIndex
)
178 return maChildren
[ nParagraphIndex
];
186 AccessibleParaManager::Child
AccessibleParaManager::CreateChild( sal_Int32 nChild
,
187 const uno::Reference
< XAccessible
>& xFrontEnd
,
188 SvxEditSourceAdapter
& rEditSource
,
189 sal_uInt32 nParagraphIndex
)
191 DBG_ASSERT( maChildren
.size() > nParagraphIndex
, "AccessibleParaManager::CreateChild: invalid index" );
193 if( maChildren
.size() > nParagraphIndex
)
195 // retrieve hard reference from weak one
196 WeakPara::HardRefType
aChild( GetChild( nParagraphIndex
).first
.get() );
198 if( !IsReferencable( nParagraphIndex
) )
200 // there is no hard reference available, create object then
201 // --> OD 2006-01-11 #i27138#
202 AccessibleEditableTextPara
* pChild
= new AccessibleEditableTextPara( xFrontEnd
, this );
204 uno::Reference
< XAccessible
> xChild( static_cast< ::cppu::OWeakObject
* > (pChild
), uno::UNO_QUERY
);
207 throw uno::RuntimeException(::rtl::OUString(RTL_CONSTASCII_USTRINGPARAM("Child creation failed")), xFrontEnd
);
209 aChild
= WeakPara::HardRefType( xChild
, pChild
);
211 InitChild( *aChild
, rEditSource
, nChild
, nParagraphIndex
);
213 maChildren
[ nParagraphIndex
] = WeakChild( aChild
, pChild
->getBounds() );
216 return Child( aChild
.getRef(), GetChild( nParagraphIndex
).second
);
224 void AccessibleParaManager::SetEEOffset( const Point
& rOffset
)
226 maEEOffset
= rOffset
;
228 MemFunAdapter
< const Point
& > aAdapter( &::accessibility::AccessibleEditableTextPara::SetEEOffset
, rOffset
);
229 ::std::for_each( begin(), end(), aAdapter
);
232 void AccessibleParaManager::SetActive( sal_Bool bActive
)
238 SetState( AccessibleStateType::ACTIVE
);
239 SetState( AccessibleStateType::EDITABLE
);
243 UnSetState( AccessibleStateType::ACTIVE
);
244 UnSetState( AccessibleStateType::EDITABLE
);
248 void AccessibleParaManager::SetFocus( sal_Int32 nChild
)
250 if( mnFocusedChild
!= -1 )
251 UnSetState( mnFocusedChild
, AccessibleStateType::FOCUSED
);
253 mnFocusedChild
= nChild
;
255 if( mnFocusedChild
!= -1 )
256 SetState( mnFocusedChild
, AccessibleStateType::FOCUSED
);
259 void AccessibleParaManager::InitChild( AccessibleEditableTextPara
& rChild
,
260 SvxEditSourceAdapter
& rEditSource
,
262 sal_uInt32 nParagraphIndex
) const
264 rChild
.SetEditSource( &rEditSource
);
265 rChild
.SetIndexInParent( nChild
);
266 rChild
.SetParagraphIndex( nParagraphIndex
);
268 rChild
.SetEEOffset( maEEOffset
);
272 rChild
.SetState( AccessibleStateType::ACTIVE
);
273 rChild
.SetState( AccessibleStateType::EDITABLE
);
276 if( mnFocusedChild
== static_cast<sal_Int32
>(nParagraphIndex
) )
277 rChild
.SetState( AccessibleStateType::FOCUSED
);
279 // add states passed from outside
280 for( VectorOfStates::const_iterator aIt
= maChildStates
.begin(), aEnd
= maChildStates
.end(); aIt
!= aEnd
; ++aIt
)
281 rChild
.SetState( *aIt
);
284 void AccessibleParaManager::SetState( sal_Int32 nChild
, const sal_Int16 nStateId
)
286 MemFunAdapter
< const sal_Int16
> aFunc( &AccessibleEditableTextPara::SetState
,
288 aFunc( GetChild(nChild
) );
291 void AccessibleParaManager::SetState( const sal_Int16 nStateId
)
293 ::std::for_each( begin(), end(),
294 MemFunAdapter
< const sal_Int16
>( &AccessibleEditableTextPara::SetState
,
298 void AccessibleParaManager::UnSetState( sal_Int32 nChild
, const sal_Int16 nStateId
)
300 MemFunAdapter
< const sal_Int16
> aFunc( &AccessibleEditableTextPara::UnSetState
,
302 aFunc( GetChild(nChild
) );
305 void AccessibleParaManager::UnSetState( const sal_Int16 nStateId
)
307 ::std::for_each( begin(), end(),
308 MemFunAdapter
< const sal_Int16
>( &AccessibleEditableTextPara::UnSetState
,
312 void AccessibleParaManager::SetEditSource( SvxEditSourceAdapter
* pEditSource
)
314 MemFunAdapter
< SvxEditSourceAdapter
* > aAdapter( &::accessibility::AccessibleEditableTextPara::SetEditSource
, pEditSource
);
315 ::std::for_each( begin(), end(), aAdapter
);
318 // not generic yet, no arguments...
319 class AccessibleParaManager_DisposeChildren
: public ::std::unary_function
< ::accessibility::AccessibleEditableTextPara
&, void >
322 AccessibleParaManager_DisposeChildren() {}
323 void operator()( ::accessibility::AccessibleEditableTextPara
& rPara
)
329 void AccessibleParaManager::Dispose()
331 AccessibleParaManager_DisposeChildren aFunctor
;
333 ::std::for_each( begin(), end(),
334 WeakChildAdapter
< AccessibleParaManager_DisposeChildren
> (aFunctor
) );
337 // not generic yet, too many method arguments...
338 class StateChangeEvent
: public ::std::unary_function
< ::accessibility::AccessibleEditableTextPara
&, void >
341 typedef void return_type
;
342 StateChangeEvent( const sal_Int16 nEventId
,
343 const uno::Any
& rNewValue
,
344 const uno::Any
& rOldValue
) :
345 mnEventId( nEventId
),
346 mrNewValue( rNewValue
),
347 mrOldValue( rOldValue
) {}
348 void operator()( ::accessibility::AccessibleEditableTextPara
& rPara
)
350 rPara
.FireEvent( mnEventId
, mrNewValue
, mrOldValue
);
354 const sal_Int16 mnEventId
;
355 const uno::Any
& mrNewValue
;
356 const uno::Any
& mrOldValue
;
359 void AccessibleParaManager::FireEvent( sal_uInt32 nStartPara
,
361 const sal_Int16 nEventId
,
362 const uno::Any
& rNewValue
,
363 const uno::Any
& rOldValue
) const
365 DBG_ASSERT( maChildren
.size() > nStartPara
&&
366 maChildren
.size() >= nEndPara
, "AccessibleParaManager::FireEvent: invalid index" );
368 if( maChildren
.size() > nStartPara
&&
369 maChildren
.size() >= nEndPara
)
371 VectorOfChildren::const_iterator front
= maChildren
.begin();
372 VectorOfChildren::const_iterator back
= front
;
374 ::std::advance( front
, nStartPara
);
375 ::std::advance( back
, nEndPara
);
377 StateChangeEvent
aFunctor( nEventId
, rNewValue
, rOldValue
);
379 ::std::for_each( front
, back
, AccessibleParaManager::WeakChildAdapter
< StateChangeEvent
>( aFunctor
) );
383 class ReleaseChild
: public ::std::unary_function
< const AccessibleParaManager::WeakChild
&, AccessibleParaManager::WeakChild
>
386 AccessibleParaManager::WeakChild
operator()( const AccessibleParaManager::WeakChild
& rPara
)
388 AccessibleParaManager::ShutdownPara( rPara
);
391 return AccessibleParaManager::WeakChild();
395 void AccessibleParaManager::Release( sal_uInt32 nStartPara
, sal_uInt32 nEndPara
)
397 DBG_ASSERT( maChildren
.size() > nStartPara
&&
398 maChildren
.size() >= nEndPara
, "AccessibleParaManager::Release: invalid index" );
400 if( maChildren
.size() > nStartPara
&&
401 maChildren
.size() >= nEndPara
)
403 VectorOfChildren::iterator front
= maChildren
.begin();
404 VectorOfChildren::iterator back
= front
;
406 ::std::advance( front
, nStartPara
);
407 ::std::advance( back
, nEndPara
);
409 ::std::transform( front
, back
, front
, ReleaseChild() );
413 void AccessibleParaManager::ShutdownPara( const WeakChild
& rChild
)
415 WeakPara::HardRefType
aChild( rChild
.first
.get() );
417 if( IsReferencable( aChild
) )
418 aChild
->SetEditSource( NULL
);
423 //------------------------------------------------------------------------