1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include "accessibility/extended/accessiblelistboxentry.hxx"
21 #include <svtools/treelistbox.hxx>
22 #include <svtools/stringtransfer.hxx>
23 #include <svtools/svlbitm.hxx>
24 #include <com/sun/star/awt/Point.hpp>
25 #include <com/sun/star/awt/Rectangle.hpp>
26 #include <com/sun/star/awt/Size.hpp>
27 #include <com/sun/star/accessibility/AccessibleEventId.hpp>
28 #include <com/sun/star/accessibility/AccessibleRelationType.hpp>
29 #include <com/sun/star/accessibility/AccessibleRole.hpp>
30 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
31 #include <vcl/svapp.hxx>
32 #include <vcl/controllayout.hxx>
33 #include <vcl/settings.hxx>
34 #include <toolkit/awt/vclxwindow.hxx>
35 #include <toolkit/helper/convert.hxx>
36 #include <unotools/accessiblestatesethelper.hxx>
37 #include <unotools/accessiblerelationsethelper.hxx>
38 #include <cppuhelper/supportsservice.hxx>
39 #include <cppuhelper/typeprovider.hxx>
40 #include <comphelper/sequence.hxx>
41 #include <comphelper/accessibleeventnotifier.hxx>
42 #include <toolkit/helper/vclunohelper.hxx>
43 #include <accessibility/helper/accresmgr.hxx>
44 #include <accessibility/helper/accessiblestrings.hrc>
45 #include <com/sun/star/accessibility/XAccessibleValue.hpp>
46 #define ACCESSIBLE_ACTION_COUNT 1
50 void checkActionIndex_Impl( sal_Int32 _nIndex
) throw (::com::sun::star::lang::IndexOutOfBoundsException
)
52 if ( _nIndex
< 0 || _nIndex
>= ACCESSIBLE_ACTION_COUNT
)
54 throw ::com::sun::star::lang::IndexOutOfBoundsException();
59 namespace accessibility
61 // class AccessibleListBoxEntry -----------------------------------------------------
63 using namespace ::com::sun::star::accessibility
;
64 using namespace ::com::sun::star::uno
;
65 using namespace ::com::sun::star::lang
;
66 using namespace ::com::sun::star
;
67 using namespace ::comphelper
;
72 AccessibleListBoxEntry::AccessibleListBoxEntry( SvTreeListBox
& _rListBox
,
73 SvTreeListEntry
* _pEntry
,
74 const Reference
< XAccessible
>& _xParent
) :
76 AccessibleListBoxEntry_BASE ( m_aMutex
),
77 ListBoxAccessibleBase( _rListBox
),
79 m_pSvLBoxEntry ( _pEntry
),
81 m_aParent ( _xParent
)
84 _rListBox
.FillEntryPath( _pEntry
, m_aEntryPath
);
87 AccessibleListBoxEntry::~AccessibleListBoxEntry()
91 // increment ref count to prevent double call of Dtor
92 osl_atomic_increment( &m_refCount
);
97 void AccessibleListBoxEntry::NotifyAccessibleEvent( sal_Int16 _nEventId
,
98 const ::com::sun::star::uno::Any
& _aOldValue
,
99 const ::com::sun::star::uno::Any
& _aNewValue
)
101 Reference
< uno::XInterface
> xSource( *this );
102 AccessibleEventObject
aEventObj( xSource
, _nEventId
, _aNewValue
, _aOldValue
);
105 comphelper::AccessibleEventNotifier::addEvent( m_nClientId
, aEventObj
);
110 Rectangle
AccessibleListBoxEntry::GetBoundingBox_Impl() const
113 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
116 aRect
= getListBox()->GetBoundingRect( pEntry
);
117 SvTreeListEntry
* pParent
= getListBox()->GetParent( pEntry
);
120 // position relative to parent entry
121 Point aTopLeft
= aRect
.TopLeft();
122 aTopLeft
-= getListBox()->GetBoundingRect( pParent
).TopLeft();
123 aRect
= Rectangle( aTopLeft
, aRect
.GetSize() );
130 Rectangle
AccessibleListBoxEntry::GetBoundingBoxOnScreen_Impl() const
133 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
136 aRect
= getListBox()->GetBoundingRect( pEntry
);
137 Point aTopLeft
= aRect
.TopLeft();
138 aTopLeft
+= getListBox()->GetWindowExtentsRelative( NULL
).TopLeft();
139 aRect
= Rectangle( aTopLeft
, aRect
.GetSize() );
145 bool AccessibleListBoxEntry::IsAlive_Impl() const
147 return ( !rBHelper
.bDisposed
&& !rBHelper
.bInDispose
&& isAlive() );
150 bool AccessibleListBoxEntry::IsShowing_Impl() const
152 Reference
< XAccessible
> xParent
= implGetParentAccessible( );
154 bool bShowing
= false;
155 Reference
< XAccessibleContext
> m_xParentContext
=
156 xParent
.is() ? xParent
->getAccessibleContext() : Reference
< XAccessibleContext
>();
157 if( m_xParentContext
.is() )
159 Reference
< XAccessibleComponent
> xParentComp( m_xParentContext
, uno::UNO_QUERY
);
160 if( xParentComp
.is() )
161 bShowing
= GetBoundingBox_Impl().IsOver( VCLRectangle( xParentComp
->getBounds() ) );
167 Rectangle
AccessibleListBoxEntry::GetBoundingBox()
168 throw (lang::DisposedException
, uno::RuntimeException
)
170 SolarMutexGuard aSolarGuard
;
171 ::osl::MutexGuard
aGuard( m_aMutex
);
174 return GetBoundingBox_Impl();
177 Rectangle
AccessibleListBoxEntry::GetBoundingBoxOnScreen()
178 throw (lang::DisposedException
, uno::RuntimeException
)
180 SolarMutexGuard aSolarGuard
;
181 ::osl::MutexGuard
aGuard( m_aMutex
);
184 return GetBoundingBoxOnScreen_Impl();
187 void AccessibleListBoxEntry::EnsureIsAlive() const throw ( lang::DisposedException
)
189 if ( !IsAlive_Impl() )
190 throw lang::DisposedException();
193 OUString
AccessibleListBoxEntry::implGetText()
196 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
198 sRet
= getListBox()->SearchEntryTextWithHeadTitle( pEntry
);
202 Locale
AccessibleListBoxEntry::implGetLocale()
205 aLocale
= Application::GetSettings().GetUILanguageTag().getLocale();
209 void AccessibleListBoxEntry::implGetSelection( sal_Int32
& nStartIndex
, sal_Int32
& nEndIndex
)
218 Sequence
< sal_Int8
> AccessibleListBoxEntry::getImplementationId() throw (RuntimeException
, std::exception
)
220 return css::uno::Sequence
<sal_Int8
>();
224 // XComponent/ListBoxAccessibleBase
226 void SAL_CALL
AccessibleListBoxEntry::dispose() throw ( uno::RuntimeException
, std::exception
)
228 AccessibleListBoxEntry_BASE::dispose();
234 void SAL_CALL
AccessibleListBoxEntry::disposing()
237 ::osl::MutexGuard
aGuard( m_aMutex
);
239 Reference
< XAccessible
> xKeepAlive( this );
241 // Send a disposing to all listeners.
244 ::comphelper::AccessibleEventNotifier::TClientId nId
= m_nClientId
;
246 ::comphelper::AccessibleEventNotifier::revokeClientNotifyDisposing( nId
, *this );
252 ListBoxAccessibleBase::disposing();
254 m_aParent
= WeakReference
< XAccessible
>();
259 OUString SAL_CALL
AccessibleListBoxEntry::getImplementationName() throw(RuntimeException
, std::exception
)
261 return getImplementationName_Static();
264 Sequence
< OUString
> SAL_CALL
AccessibleListBoxEntry::getSupportedServiceNames() throw(RuntimeException
, std::exception
)
266 return getSupportedServiceNames_Static();
269 sal_Bool SAL_CALL
AccessibleListBoxEntry::supportsService( const OUString
& _rServiceName
) throw (RuntimeException
, std::exception
)
271 return cppu::supportsService(this, _rServiceName
);
274 // XServiceInfo - static methods
276 Sequence
< OUString
> AccessibleListBoxEntry::getSupportedServiceNames_Static() throw( RuntimeException
)
278 Sequence
< OUString
> aSupported(3);
279 aSupported
[0] = "com.sun.star.accessibility.AccessibleContext";
280 aSupported
[1] = "com.sun.star.accessibility.AccessibleComponent";
281 aSupported
[2] = "com.sun.star.awt.AccessibleTreeListBoxEntry";
285 OUString
AccessibleListBoxEntry::getImplementationName_Static() throw( RuntimeException
)
287 return OUString( "com.sun.star.comp.svtools.AccessibleTreeListBoxEntry" );
292 Reference
< XAccessibleContext
> SAL_CALL
AccessibleListBoxEntry::getAccessibleContext( ) throw (RuntimeException
, std::exception
)
298 // XAccessibleContext
300 sal_Int32 SAL_CALL
AccessibleListBoxEntry::getAccessibleChildCount( ) throw (RuntimeException
, std::exception
)
302 SolarMutexGuard aSolarGuard
;
303 ::osl::MutexGuard
aGuard( m_aMutex
);
306 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
307 sal_Int32 nCount
= 0;
309 nCount
= getListBox()->GetLevelChildCount( pEntry
);
314 Reference
< XAccessible
> SAL_CALL
AccessibleListBoxEntry::getAccessibleChild( sal_Int32 i
) throw (IndexOutOfBoundsException
,RuntimeException
, std::exception
)
316 SolarMutexGuard aSolarGuard
;
317 ::osl::MutexGuard
aGuard( m_aMutex
);
320 SvTreeListEntry
* pEntry
= GetRealChild(i
);
322 throw IndexOutOfBoundsException();
324 return new AccessibleListBoxEntry( *getListBox(), pEntry
, this );
328 Reference
< XAccessible
> AccessibleListBoxEntry::implGetParentAccessible( ) const
330 Reference
< XAccessible
> xParent(m_aParent
);
333 OSL_ENSURE( m_aEntryPath
.size(), "AccessibleListBoxEntry::getAccessibleParent: invalid path!" );
334 if ( 1 == m_aEntryPath
.size() )
335 { // we're a top level entry
336 // -> our parent is the tree listbox itself
338 xParent
= getListBox()->GetAccessible( );
341 { // we have a entry as parent -> get its accessible
343 // shorten our access path by one
344 ::std::deque
< sal_Int32
> aParentPath( m_aEntryPath
);
345 aParentPath
.pop_back();
347 // get the entry for this shortened access path
348 SvTreeListEntry
* pParentEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
349 OSL_ENSURE( pParentEntry
, "AccessibleListBoxEntry::implGetParentAccessible: could not obtain a parent entry!" );
352 pParentEntry
= getListBox()->GetParent(pParentEntry
);
354 xParent
= new AccessibleListBoxEntry( *getListBox(), pParentEntry
, NULL
);
355 // note that we pass NULL here as parent-accessible:
356 // this is allowed, as the AccessibleListBoxEntry class will create its parent
365 Reference
< XAccessible
> SAL_CALL
AccessibleListBoxEntry::getAccessibleParent( ) throw (RuntimeException
, std::exception
)
367 SolarMutexGuard aSolarGuard
;
368 ::osl::MutexGuard
aGuard( m_aMutex
);
371 return implGetParentAccessible( );
374 sal_Int32 SAL_CALL
AccessibleListBoxEntry::getAccessibleIndexInParent( ) throw (RuntimeException
, std::exception
)
376 ::osl::MutexGuard
aGuard( m_aMutex
);
378 OSL_ENSURE( !m_aEntryPath
.empty(), "empty path" );
379 return m_aEntryPath
.empty() ? -1 : m_aEntryPath
.back();
382 sal_Int32
AccessibleListBoxEntry::GetRoleType()
385 SvTreeListEntry
* pEntry
= getListBox()->GetEntry(0);
388 if( pEntry
->HasChildrenOnDemand() || getListBox()->GetChildCount(pEntry
) > 0 )
395 bool bHasButtons
= (getListBox()->GetStyle() & WB_HASBUTTONS
)!=0;
396 if( !(getListBox()->GetTreeFlags() & SvTreeFlags::CHKBTN
) )
411 sal_Int16 SAL_CALL
AccessibleListBoxEntry::getAccessibleRole( ) throw (RuntimeException
, std::exception
)
413 SolarMutexGuard aSolarGuard
;
414 ::osl::MutexGuard
aGuard( m_aMutex
);
416 SvTreeListBox
* pBox
= getListBox();
419 SvTreeAccRoleType nType
= pBox
->GetAllEntriesAccessibleRoleType();
420 if( nType
== SvTreeAccRoleType::TREE
)
421 return AccessibleRole::TREE_ITEM
;
422 else if( nType
== SvTreeAccRoleType::LIST
)
423 return AccessibleRole::LIST_ITEM
;
425 SvTreeFlags treeFlag
= pBox
->GetTreeFlags();
426 if(treeFlag
& SvTreeFlags::CHKBTN
)
428 SvTreeListEntry
* pEntry
= pBox
->GetEntryFromPath( m_aEntryPath
);
429 SvButtonState eState
= pBox
->GetCheckButtonState( pEntry
);
432 case SV_BUTTON_CHECKED
:
433 case SV_BUTTON_UNCHECKED
:
434 return AccessibleRole::CHECK_BOX
;
435 case SV_BUTTON_TRISTATE
:
437 return AccessibleRole::LABEL
;
440 if (GetRoleType() == 0)
441 return AccessibleRole::LIST_ITEM
;
443 //o is: return AccessibleRole::LABEL;
444 return AccessibleRole::TREE_ITEM
;
446 return AccessibleRole::UNKNOWN
;
449 OUString SAL_CALL
AccessibleListBoxEntry::getAccessibleDescription( ) throw (RuntimeException
, std::exception
)
451 SolarMutexGuard aSolarGuard
;
452 ::osl::MutexGuard
aGuard( m_aMutex
);
454 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
455 if( getAccessibleRole() == AccessibleRole::TREE_ITEM
)
457 return getListBox()->GetEntryLongDescription( pEntry
);
459 //want to cout the real column nubmer in the list box.
460 sal_uInt16 iRealItemCount
= 0;
461 sal_uInt16 iCount
= 0;
462 sal_uInt16 iTotleItemCount
= pEntry
->ItemCount();
463 while( iCount
< iTotleItemCount
)
465 const SvLBoxItem
* pItem
= pEntry
->GetItem( iCount
);
466 if ( pItem
->GetType() == SV_ITEM_ID_LBOXSTRING
&&
467 !static_cast<const SvLBoxString
*>( pItem
)->GetText().isEmpty() )
473 if(iRealItemCount
<=1 )
479 return getListBox()->SearchEntryTextWithHeadTitle( pEntry
);
483 OUString SAL_CALL
AccessibleListBoxEntry::getAccessibleName( ) throw (RuntimeException
, std::exception
)
485 ::osl::MutexGuard
aGuard( m_aMutex
);
489 OUString
sRet(implGetText());
491 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
493 OUString altText
= getListBox()->GetEntryAltText( pEntry
);
494 if (!altText
.isEmpty())
503 Reference
< XAccessibleRelationSet
> SAL_CALL
AccessibleListBoxEntry::getAccessibleRelationSet( ) throw (RuntimeException
, std::exception
)
505 Reference
< XAccessibleRelationSet
> xRelSet
;
506 Reference
< XAccessible
> xParent
;
507 if ( m_aEntryPath
.size() > 1 ) // not a root entry
508 xParent
= implGetParentAccessible();
511 utl::AccessibleRelationSetHelper
* pRelationSetHelper
= new utl::AccessibleRelationSetHelper
;
512 Sequence
< Reference
< XInterface
> > aSequence(1);
513 aSequence
[0] = xParent
;
514 pRelationSetHelper
->AddRelation(
515 AccessibleRelation( AccessibleRelationType::NODE_CHILD_OF
, aSequence
) );
516 xRelSet
= pRelationSetHelper
;
521 Reference
< XAccessibleStateSet
> SAL_CALL
AccessibleListBoxEntry::getAccessibleStateSet( ) throw (RuntimeException
, std::exception
)
523 ::osl::MutexGuard
aGuard( m_aMutex
);
525 utl::AccessibleStateSetHelper
* pStateSetHelper
= new utl::AccessibleStateSetHelper
;
526 Reference
< XAccessibleStateSet
> xStateSet
= pStateSetHelper
;
528 if ( IsAlive_Impl() )
530 switch(getAccessibleRole())
532 case AccessibleRole::LABEL
:
533 pStateSetHelper
->AddState( AccessibleStateType::TRANSIENT
);
534 pStateSetHelper
->AddState( AccessibleStateType::SELECTABLE
);
535 pStateSetHelper
->AddState( AccessibleStateType::ENABLED
);
536 if (getListBox()->IsInplaceEditingEnabled())
537 pStateSetHelper
->AddState( AccessibleStateType::EDITABLE
);
538 if (IsShowing_Impl())
539 pStateSetHelper
->AddState( AccessibleStateType::SHOWING
);
541 case AccessibleRole::CHECK_BOX
:
542 pStateSetHelper
->AddState( AccessibleStateType::TRANSIENT
);
543 pStateSetHelper
->AddState( AccessibleStateType::SELECTABLE
);
544 pStateSetHelper
->AddState( AccessibleStateType::ENABLED
);
545 if (IsShowing_Impl())
546 pStateSetHelper
->AddState( AccessibleStateType::SHOWING
);
549 SvTreeListEntry
*pEntry
= getListBox()->GetEntryFromPath(m_aEntryPath
);
551 getListBox()->FillAccessibleEntryStateSet(pEntry
, *pStateSetHelper
);
554 pStateSetHelper
->AddState( AccessibleStateType::DEFUNC
);
559 Locale SAL_CALL
AccessibleListBoxEntry::getLocale( ) throw (IllegalAccessibleComponentStateException
, RuntimeException
, std::exception
)
561 SolarMutexGuard aSolarGuard
;
562 ::osl::MutexGuard
aGuard( m_aMutex
);
564 return implGetLocale();
567 // XAccessibleComponent
569 sal_Bool SAL_CALL
AccessibleListBoxEntry::containsPoint( const awt::Point
& rPoint
) throw (RuntimeException
, std::exception
)
571 return Rectangle( Point(), GetBoundingBox().GetSize() ).IsInside( VCLPoint( rPoint
) );
574 Reference
< XAccessible
> SAL_CALL
AccessibleListBoxEntry::getAccessibleAtPoint( const awt::Point
& _aPoint
) throw (RuntimeException
, std::exception
)
576 SolarMutexGuard aSolarGuard
;
577 ::osl::MutexGuard
aGuard( m_aMutex
);
580 SvTreeListEntry
* pEntry
= getListBox()->GetEntry( VCLPoint( _aPoint
) );
582 throw RuntimeException();
584 Reference
< XAccessible
> xAcc
;
585 AccessibleListBoxEntry
* pAccEntry
= new AccessibleListBoxEntry( *getListBox(), pEntry
, this );
586 Rectangle aRect
= pAccEntry
->GetBoundingBox_Impl();
587 if ( aRect
.IsInside( VCLPoint( _aPoint
) ) )
592 awt::Rectangle SAL_CALL
AccessibleListBoxEntry::getBounds( ) throw (RuntimeException
, std::exception
)
594 return AWTRectangle( GetBoundingBox() );
597 awt::Point SAL_CALL
AccessibleListBoxEntry::getLocation( ) throw (RuntimeException
, std::exception
)
599 return AWTPoint( GetBoundingBox().TopLeft() );
602 awt::Point SAL_CALL
AccessibleListBoxEntry::getLocationOnScreen( ) throw (RuntimeException
, std::exception
)
604 return AWTPoint( GetBoundingBoxOnScreen().TopLeft() );
607 awt::Size SAL_CALL
AccessibleListBoxEntry::getSize( ) throw (RuntimeException
, std::exception
)
609 return AWTSize( GetBoundingBox().GetSize() );
612 void SAL_CALL
AccessibleListBoxEntry::grabFocus( ) throw (RuntimeException
, std::exception
)
614 // do nothing, because no focus for each item
617 sal_Int32
AccessibleListBoxEntry::getForeground( ) throw (RuntimeException
, std::exception
)
619 SolarMutexGuard aSolarGuard
;
620 ::osl::MutexGuard
aGuard( m_aMutex
);
622 sal_Int32 nColor
= 0;
623 Reference
< XAccessible
> xParent
= getAccessibleParent();
626 Reference
< XAccessibleComponent
> xParentComp( xParent
->getAccessibleContext(), UNO_QUERY
);
627 if ( xParentComp
.is() )
628 nColor
= xParentComp
->getForeground();
634 sal_Int32
AccessibleListBoxEntry::getBackground( ) throw (RuntimeException
, std::exception
)
636 SolarMutexGuard aSolarGuard
;
637 ::osl::MutexGuard
aGuard( m_aMutex
);
639 sal_Int32 nColor
= 0;
640 Reference
< XAccessible
> xParent
= getAccessibleParent();
643 Reference
< XAccessibleComponent
> xParentComp( xParent
->getAccessibleContext(), UNO_QUERY
);
644 if ( xParentComp
.is() )
645 nColor
= xParentComp
->getBackground();
654 awt::Rectangle SAL_CALL
AccessibleListBoxEntry::getCharacterBounds( sal_Int32 nIndex
) throw (IndexOutOfBoundsException
, RuntimeException
, std::exception
)
656 SolarMutexGuard aSolarGuard
;
657 ::osl::MutexGuard
aGuard( m_aMutex
);
661 if ( !implIsValidIndex( nIndex
, implGetText().getLength() ) )
662 throw IndexOutOfBoundsException();
664 awt::Rectangle
aBounds( 0, 0, 0, 0 );
665 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
668 vcl::ControlLayoutData aLayoutData
;
669 Rectangle aItemRect
= GetBoundingBox();
670 getListBox()->RecordLayoutData( &aLayoutData
, aItemRect
);
671 Rectangle aCharRect
= aLayoutData
.GetCharacterBounds( nIndex
);
672 aCharRect
.Move( -aItemRect
.Left(), -aItemRect
.Top() );
673 aBounds
= AWTRectangle( aCharRect
);
679 sal_Int32 SAL_CALL
AccessibleListBoxEntry::getIndexAtPoint( const awt::Point
& aPoint
) throw (RuntimeException
, std::exception
)
681 SolarMutexGuard aSolarGuard
;
682 ::osl::MutexGuard
aGuard( m_aMutex
);
684 if(aPoint
.X
==0 && aPoint
.Y
==0) return 0;
686 sal_Int32 nIndex
= -1;
687 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
690 vcl::ControlLayoutData aLayoutData
;
691 Rectangle aItemRect
= GetBoundingBox();
692 getListBox()->RecordLayoutData( &aLayoutData
, aItemRect
);
693 Point
aPnt( VCLPoint( aPoint
) );
694 aPnt
+= aItemRect
.TopLeft();
695 nIndex
= aLayoutData
.GetIndexForPoint( aPnt
);
701 sal_Bool SAL_CALL
AccessibleListBoxEntry::copyText( sal_Int32 nStartIndex
, sal_Int32 nEndIndex
) throw (IndexOutOfBoundsException
, RuntimeException
, std::exception
)
703 SolarMutexGuard aSolarGuard
;
704 ::osl::MutexGuard
aGuard( m_aMutex
);
707 OUString sText
= getText();
708 if ( ( 0 > nStartIndex
) || ( sText
.getLength() <= nStartIndex
)
709 || ( 0 > nEndIndex
) || ( sText
.getLength() <= nEndIndex
) )
710 throw IndexOutOfBoundsException();
712 sal_Int32 nLen
= nEndIndex
- nStartIndex
+ 1;
713 ::svt::OStringTransfer::CopyString( sText
.copy( nStartIndex
, nLen
), getListBox() );
718 // XAccessibleEventBroadcaster
720 void SAL_CALL
AccessibleListBoxEntry::addAccessibleEventListener( const Reference
< XAccessibleEventListener
>& xListener
) throw (RuntimeException
, std::exception
)
724 ::osl::MutexGuard
aGuard( m_aMutex
);
726 m_nClientId
= comphelper::AccessibleEventNotifier::registerClient( );
727 comphelper::AccessibleEventNotifier::addEventListener( m_nClientId
, xListener
);
731 void SAL_CALL
AccessibleListBoxEntry::removeAccessibleEventListener( const Reference
< XAccessibleEventListener
>& xListener
) throw (RuntimeException
, std::exception
)
735 ::osl::MutexGuard
aGuard( m_aMutex
);
737 sal_Int32 nListenerCount
= comphelper::AccessibleEventNotifier::removeEventListener( m_nClientId
, xListener
);
738 if ( !nListenerCount
)
740 // no listeners anymore
741 // -> revoke ourself. This may lead to the notifier thread dying (if we were the last client),
742 // and at least to us not firing any events anymore, in case somebody calls
743 // NotifyAccessibleEvent, again
744 sal_Int32 nId
= m_nClientId
;
746 comphelper::AccessibleEventNotifier::revokeClient( nId
);
754 sal_Int32 SAL_CALL
AccessibleListBoxEntry::getAccessibleActionCount( ) throw (RuntimeException
, std::exception
)
756 ::osl::MutexGuard
aGuard( m_aMutex
);
758 // three actions supported
759 SvTreeListBox
* pBox
= getListBox();
760 SvTreeFlags treeFlag
= pBox
->GetTreeFlags();
761 bool bHasButtons
= (getListBox()->GetStyle() & WB_HASBUTTONS
)!=0;
762 if( (treeFlag
& SvTreeFlags::CHKBTN
) && !bHasButtons
)
764 sal_Int16 role
= getAccessibleRole();
765 if ( role
== AccessibleRole::CHECK_BOX
)
767 else if ( role
== AccessibleRole::LABEL
)
771 return ACCESSIBLE_ACTION_COUNT
;
775 sal_Bool SAL_CALL
AccessibleListBoxEntry::doAccessibleAction( sal_Int32 nIndex
) throw (IndexOutOfBoundsException
, RuntimeException
, std::exception
)
777 SolarMutexGuard aSolarGuard
;
778 ::osl::MutexGuard
aGuard( m_aMutex
);
781 checkActionIndex_Impl( nIndex
);
784 SvTreeFlags treeFlag
= getListBox()->GetTreeFlags();
785 if( nIndex
== 0 && (treeFlag
& SvTreeFlags::CHKBTN
) )
787 if(getAccessibleRole() == AccessibleRole::CHECK_BOX
)
789 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
790 SvButtonState state
= getListBox()->GetCheckButtonState( pEntry
);
791 if ( state
== SV_BUTTON_CHECKED
)
792 getListBox()->SetCheckButtonState(pEntry
, SV_BUTTON_UNCHECKED
);
793 else if (state
== SV_BUTTON_UNCHECKED
)
794 getListBox()->SetCheckButtonState(pEntry
, SV_BUTTON_CHECKED
);
797 else if( (nIndex
== 1 && (treeFlag
& SvTreeFlags::CHKBTN
) ) || (nIndex
== 0) )
799 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
802 if ( getListBox()->IsExpanded( pEntry
) )
803 getListBox()->Collapse( pEntry
);
805 getListBox()->Expand( pEntry
);
813 OUString SAL_CALL
AccessibleListBoxEntry::getAccessibleActionDescription( sal_Int32 nIndex
) throw (IndexOutOfBoundsException
, RuntimeException
, std::exception
)
815 SolarMutexGuard aSolarGuard
;
816 ::osl::MutexGuard
aGuard( m_aMutex
);
818 checkActionIndex_Impl( nIndex
);
821 static const char sActionDesc1
[] = "Check";
822 static const char sActionDesc2
[] = "UnCheck";
823 // sal_Bool bHasButtons = (getListBox()->GetStyle() & WB_HASBUTTONS)!=0;
824 SvTreeListEntry
* pEntry
= getListBox()->GetEntryFromPath( m_aEntryPath
);
825 SvButtonState state
= getListBox()->GetCheckButtonState( pEntry
);
826 SvTreeFlags treeFlag
= getListBox()->GetTreeFlags();
827 if(nIndex
== 0 && (treeFlag
& SvTreeFlags::CHKBTN
))
829 if(getAccessibleRole() == AccessibleRole::CHECK_BOX
)
831 if ( state
== SV_BUTTON_CHECKED
)
832 return OUString(sActionDesc2
);
833 else if (state
== SV_BUTTON_UNCHECKED
)
834 return OUString(sActionDesc1
);
838 //Sometimes, a List or Tree may have both checkbox and label at the same time
841 }else if( (nIndex
== 1 && (treeFlag
& SvTreeFlags::CHKBTN
)) || nIndex
== 0 )
843 if( pEntry
->HasChildren() || pEntry
->HasChildrenOnDemand() )
844 return getListBox()->IsExpanded( pEntry
) ? \
845 OUString(TK_RES_STRING(STR_SVT_ACC_ACTION_COLLAPSE
)) :
846 OUString(TK_RES_STRING(STR_SVT_ACC_ACTION_EXPAND
));
850 throw IndexOutOfBoundsException();
853 Reference
< XAccessibleKeyBinding
> AccessibleListBoxEntry::getAccessibleActionKeyBinding( sal_Int32 nIndex
) throw (IndexOutOfBoundsException
, RuntimeException
, std::exception
)
855 ::osl::MutexGuard
aGuard( m_aMutex
);
857 Reference
< XAccessibleKeyBinding
> xRet
;
858 checkActionIndex_Impl( nIndex
);
863 // XAccessibleSelection
865 void SAL_CALL
AccessibleListBoxEntry::selectAccessibleChild( sal_Int32 nChildIndex
) throw (IndexOutOfBoundsException
, RuntimeException
, std::exception
)
867 SolarMutexGuard aSolarGuard
;
868 ::osl::MutexGuard
aGuard( m_aMutex
);
872 SvTreeListEntry
* pEntry
= GetRealChild(nChildIndex
);
874 throw IndexOutOfBoundsException();
876 getListBox()->Select( pEntry
, true );
879 sal_Bool SAL_CALL
AccessibleListBoxEntry::isAccessibleChildSelected( sal_Int32 nChildIndex
) throw (IndexOutOfBoundsException
, RuntimeException
, std::exception
)
881 SolarMutexGuard aSolarGuard
;
882 ::osl::MutexGuard
aGuard( m_aMutex
);
886 SvTreeListEntry
* pParent
= getListBox()->GetEntryFromPath( m_aEntryPath
);
887 SvTreeListEntry
* pEntry
= getListBox()->GetEntry( pParent
, nChildIndex
);
889 throw IndexOutOfBoundsException();
891 return getListBox()->IsSelected( pEntry
);
894 void SAL_CALL
AccessibleListBoxEntry::clearAccessibleSelection( ) throw (RuntimeException
, std::exception
)
896 SolarMutexGuard aSolarGuard
;
897 ::osl::MutexGuard
aGuard( m_aMutex
);
901 SvTreeListEntry
* pParent
= getListBox()->GetEntryFromPath( m_aEntryPath
);
903 throw RuntimeException();
904 sal_Int32 nCount
= getListBox()->GetLevelChildCount( pParent
);
905 for ( sal_Int32 i
= 0; i
< nCount
; ++i
)
907 SvTreeListEntry
* pEntry
= getListBox()->GetEntry( pParent
, i
);
908 if ( getListBox()->IsSelected( pEntry
) )
909 getListBox()->Select( pEntry
, false );
913 void SAL_CALL
AccessibleListBoxEntry::selectAllAccessibleChildren( ) throw (RuntimeException
, std::exception
)
915 SolarMutexGuard aSolarGuard
;
916 ::osl::MutexGuard
aGuard( m_aMutex
);
920 SvTreeListEntry
* pParent
= getListBox()->GetEntryFromPath( m_aEntryPath
);
922 throw RuntimeException();
923 sal_Int32 nCount
= getListBox()->GetLevelChildCount( pParent
);
924 for ( sal_Int32 i
= 0; i
< nCount
; ++i
)
926 SvTreeListEntry
* pEntry
= getListBox()->GetEntry( pParent
, i
);
927 if ( !getListBox()->IsSelected( pEntry
) )
928 getListBox()->Select( pEntry
, true );
932 sal_Int32 SAL_CALL
AccessibleListBoxEntry::getSelectedAccessibleChildCount( ) throw (RuntimeException
, std::exception
)
934 SolarMutexGuard aSolarGuard
;
935 ::osl::MutexGuard
aGuard( m_aMutex
);
939 sal_Int32 i
, nSelCount
= 0, nCount
= 0;
941 SvTreeListEntry
* pParent
= getListBox()->GetEntryFromPath( m_aEntryPath
);
943 throw RuntimeException();
944 nCount
= getListBox()->GetLevelChildCount( pParent
);
945 for ( i
= 0; i
< nCount
; ++i
)
947 SvTreeListEntry
* pEntry
= getListBox()->GetEntry( pParent
, i
);
948 if ( getListBox()->IsSelected( pEntry
) )
955 Reference
< XAccessible
> SAL_CALL
AccessibleListBoxEntry::getSelectedAccessibleChild( sal_Int32 nSelectedChildIndex
) throw (IndexOutOfBoundsException
, RuntimeException
, std::exception
)
957 SolarMutexGuard aSolarGuard
;
958 ::osl::MutexGuard
aGuard( m_aMutex
);
962 if ( nSelectedChildIndex
< 0 || nSelectedChildIndex
>= getSelectedAccessibleChildCount() )
963 throw IndexOutOfBoundsException();
965 Reference
< XAccessible
> xChild
;
966 sal_Int32 i
, nSelCount
= 0, nCount
= 0;
968 SvTreeListEntry
* pParent
= getListBox()->GetEntryFromPath( m_aEntryPath
);
970 throw RuntimeException();
971 nCount
= getListBox()->GetLevelChildCount( pParent
);
972 for ( i
= 0; i
< nCount
; ++i
)
974 SvTreeListEntry
* pEntry
= getListBox()->GetEntry( pParent
, i
);
975 if ( getListBox()->IsSelected( pEntry
) )
978 if ( nSelCount
== ( nSelectedChildIndex
+ 1 ) )
980 xChild
= new AccessibleListBoxEntry( *getListBox(), pEntry
, this );
988 void SAL_CALL
AccessibleListBoxEntry::deselectAccessibleChild( sal_Int32 nSelectedChildIndex
) throw (IndexOutOfBoundsException
, RuntimeException
, std::exception
)
990 SolarMutexGuard aSolarGuard
;
991 ::osl::MutexGuard
aGuard( m_aMutex
);
995 SvTreeListEntry
* pParent
= getListBox()->GetEntryFromPath( m_aEntryPath
);
996 SvTreeListEntry
* pEntry
= getListBox()->GetEntry( pParent
, nSelectedChildIndex
);
998 throw IndexOutOfBoundsException();
1000 getListBox()->Select( pEntry
, false );
1002 sal_Int32 SAL_CALL
AccessibleListBoxEntry::getCaretPosition( ) throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1006 sal_Bool SAL_CALL
AccessibleListBoxEntry::setCaretPosition ( sal_Int32 nIndex
) throw (::com::sun::star::lang::IndexOutOfBoundsException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1008 SolarMutexGuard aSolarGuard
;
1009 ::osl::MutexGuard
aGuard( m_aMutex
);
1012 if ( !implIsValidRange( nIndex
, nIndex
, implGetText().getLength() ) )
1013 throw IndexOutOfBoundsException();
1017 sal_Unicode SAL_CALL
AccessibleListBoxEntry::getCharacter( sal_Int32 nIndex
) throw (::com::sun::star::lang::IndexOutOfBoundsException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1019 SolarMutexGuard aSolarGuard
;
1020 ::osl::MutexGuard
aGuard( m_aMutex
);
1022 return OCommonAccessibleText::getCharacter( nIndex
);
1024 ::com::sun::star::uno::Sequence
< ::com::sun::star::beans::PropertyValue
> SAL_CALL
AccessibleListBoxEntry::getCharacterAttributes( sal_Int32 nIndex
, const ::com::sun::star::uno::Sequence
< OUString
>& ) throw (::com::sun::star::lang::IndexOutOfBoundsException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1026 SolarMutexGuard aSolarGuard
;
1027 ::osl::MutexGuard
aGuard( m_aMutex
);
1030 OUString
sText( implGetText() );
1032 if ( !implIsValidIndex( nIndex
, sText
.getLength() ) )
1033 throw IndexOutOfBoundsException();
1035 return ::com::sun::star::uno::Sequence
< ::com::sun::star::beans::PropertyValue
>();
1037 sal_Int32 SAL_CALL
AccessibleListBoxEntry::getCharacterCount( ) throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1039 SolarMutexGuard aSolarGuard
;
1040 ::osl::MutexGuard
aGuard( m_aMutex
);
1042 return OCommonAccessibleText::getCharacterCount( );
1045 OUString SAL_CALL
AccessibleListBoxEntry::getSelectedText( ) throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1047 SolarMutexGuard aSolarGuard
;
1048 ::osl::MutexGuard
aGuard( m_aMutex
);
1050 return OCommonAccessibleText::getSelectedText( );
1052 sal_Int32 SAL_CALL
AccessibleListBoxEntry::getSelectionStart( ) throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1054 SolarMutexGuard aSolarGuard
;
1055 ::osl::MutexGuard
aGuard( m_aMutex
);
1057 return OCommonAccessibleText::getSelectionStart( );
1059 sal_Int32 SAL_CALL
AccessibleListBoxEntry::getSelectionEnd( ) throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1061 SolarMutexGuard aSolarGuard
;
1062 ::osl::MutexGuard
aGuard( m_aMutex
);
1064 return OCommonAccessibleText::getSelectionEnd( );
1066 sal_Bool SAL_CALL
AccessibleListBoxEntry::setSelection( sal_Int32 nStartIndex
, sal_Int32 nEndIndex
) throw (::com::sun::star::lang::IndexOutOfBoundsException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1068 SolarMutexGuard aSolarGuard
;
1069 ::osl::MutexGuard
aGuard( m_aMutex
);
1072 if ( !implIsValidRange( nStartIndex
, nEndIndex
, implGetText().getLength() ) )
1073 throw IndexOutOfBoundsException();
1077 OUString SAL_CALL
AccessibleListBoxEntry::getText( ) throw (::com::sun::star::uno::RuntimeException
, std::exception
)
1079 SolarMutexGuard aSolarGuard
;
1080 ::osl::MutexGuard
aGuard( m_aMutex
);
1082 return OCommonAccessibleText::getText( );
1084 OUString SAL_CALL
AccessibleListBoxEntry::getTextRange( sal_Int32 nStartIndex
, sal_Int32 nEndIndex
) throw (::com::sun::star::lang::IndexOutOfBoundsException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1086 SolarMutexGuard aSolarGuard
;
1087 ::osl::MutexGuard
aGuard( m_aMutex
);
1089 return OCommonAccessibleText::getTextRange( nStartIndex
, nEndIndex
);
1091 ::com::sun::star::accessibility::TextSegment SAL_CALL
AccessibleListBoxEntry::getTextAtIndex( sal_Int32 nIndex
, sal_Int16 aTextType
) throw (::com::sun::star::lang::IndexOutOfBoundsException
, ::com::sun::star::lang::IllegalArgumentException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1093 SolarMutexGuard aSolarGuard
;
1094 ::osl::MutexGuard
aGuard( m_aMutex
);
1096 return OCommonAccessibleText::getTextAtIndex( nIndex
,aTextType
);
1098 ::com::sun::star::accessibility::TextSegment SAL_CALL
AccessibleListBoxEntry::getTextBeforeIndex( sal_Int32 nIndex
, sal_Int16 aTextType
) throw (::com::sun::star::lang::IndexOutOfBoundsException
, ::com::sun::star::lang::IllegalArgumentException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1100 SolarMutexGuard aSolarGuard
;
1101 ::osl::MutexGuard
aGuard( m_aMutex
);
1103 return OCommonAccessibleText::getTextBeforeIndex( nIndex
,aTextType
);
1105 ::com::sun::star::accessibility::TextSegment SAL_CALL
AccessibleListBoxEntry::getTextBehindIndex( sal_Int32 nIndex
, sal_Int16 aTextType
) throw (::com::sun::star::lang::IndexOutOfBoundsException
, ::com::sun::star::lang::IllegalArgumentException
, ::com::sun::star::uno::RuntimeException
, std::exception
)
1107 SolarMutexGuard aSolarGuard
;
1108 ::osl::MutexGuard
aGuard( m_aMutex
);
1111 return OCommonAccessibleText::getTextBehindIndex( nIndex
,aTextType
);
1117 Any
AccessibleListBoxEntry::getCurrentValue( ) throw (RuntimeException
, std::exception
)
1119 ::osl::MutexGuard
aGuard( m_aMutex
);
1121 sal_Int32 level
= ((sal_Int32
) m_aEntryPath
.size() - 1);
1122 level
= level
< 0 ? 0: level
;
1129 sal_Bool
AccessibleListBoxEntry::setCurrentValue( const Any
& aNumber
) throw (RuntimeException
, std::exception
)
1131 ::osl::MutexGuard
aGuard( m_aMutex
);
1134 bool bReturn
= false;
1135 SvTreeListBox
* pBox
= getListBox();
1136 if(getAccessibleRole() == AccessibleRole::CHECK_BOX
)
1138 SvTreeListEntry
* pEntry
= pBox
->GetEntryFromPath( m_aEntryPath
);
1141 sal_Int32
nValue(0), nValueMin(0), nValueMax(0);
1143 getMinimumValue() >>= nValueMin
;
1144 getMaximumValue() >>= nValueMax
;
1146 if ( nValue
< nValueMin
)
1148 else if ( nValue
> nValueMax
)
1151 pBox
->SetCheckButtonState(pEntry
, (SvButtonState
) nValue
);
1161 Any
AccessibleListBoxEntry::getMaximumValue( ) throw (RuntimeException
, std::exception
)
1163 ::osl::MutexGuard
aGuard( m_aMutex
);
1166 // SvTreeListBox* pBox = getListBox();
1167 switch(getAccessibleRole())
1169 case AccessibleRole::CHECK_BOX
:
1170 aValue
<<= (sal_Int32
)1;
1172 case AccessibleRole::LABEL
:
1182 Any
AccessibleListBoxEntry::getMinimumValue( ) throw (RuntimeException
, std::exception
)
1184 ::osl::MutexGuard
aGuard( m_aMutex
);
1187 // SvTreeListBox* pBox = getListBox();
1188 switch(getAccessibleRole())
1190 case AccessibleRole::CHECK_BOX
:
1191 aValue
<<= (sal_Int32
)0;
1193 case AccessibleRole::LABEL
:
1203 SvTreeListEntry
* AccessibleListBoxEntry::GetRealChild(sal_Int32 nIndex
)
1205 SvTreeListEntry
* pEntry
= NULL
;
1206 SvTreeListEntry
* pParent
= getListBox()->GetEntryFromPath( m_aEntryPath
);
1209 pEntry
= getListBox()->GetEntry( pParent
, nIndex
);
1210 if ( !pEntry
&& getAccessibleChildCount() > 0 )
1212 getListBox()->RequestingChildren(pParent
);
1213 pEntry
= getListBox()->GetEntry( pParent
, nIndex
);
1219 }// namespace accessibility
1222 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */