xref: /AOO41X/main/accessibility/source/standard/accessiblemenubasecomponent.cxx (revision ffad8df045fe8db79e3e50f731c1fa6ab6501c83)
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 // MARKER(update_precomp.py): autogen include statement, do not remove
25 #include "precompiled_accessibility.hxx"
26 
27 // includes --------------------------------------------------------------
28 #include <accessibility/standard/accessiblemenubasecomponent.hxx>
29 #include <accessibility/standard/vclxaccessiblemenu.hxx>
30 #include <accessibility/standard/vclxaccessiblemenuitem.hxx>
31 #include <accessibility/standard/vclxaccessiblemenuseparator.hxx>
32 #include <toolkit/helper/externallock.hxx>
33 #include <toolkit/helper/convert.hxx>
34 
35 #include <com/sun/star/accessibility/AccessibleEventId.hpp>
36 #include <com/sun/star/accessibility/AccessibleRole.hpp>
37 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
38 
39 #include <unotools/accessiblestatesethelper.hxx>
40 #include <vcl/svapp.hxx>
41 #include <vcl/window.hxx>
42 #include <vcl/menu.hxx>
43 #include <tools/debug.hxx>
44 
45 using namespace ::com::sun::star;
46 using namespace ::com::sun::star::lang;
47 using namespace ::com::sun::star::uno;
48 using namespace ::com::sun::star::accessibility;
49 using namespace ::comphelper;
50 
51 
52 // -----------------------------------------------------------------------------
53 // OAccessibleMenuBaseComponent
54 // -----------------------------------------------------------------------------
55 
OAccessibleMenuBaseComponent(Menu * pMenu)56 OAccessibleMenuBaseComponent::OAccessibleMenuBaseComponent( Menu* pMenu )
57     :AccessibleExtendedComponentHelper_BASE( new VCLExternalSolarLock() )
58     ,m_pMenu( pMenu )
59     ,m_bEnabled( sal_False )
60     ,m_bFocused( sal_False )
61     ,m_bVisible( sal_False )
62     ,m_bSelected( sal_False )
63     ,m_bChecked( sal_False )
64 {
65     m_pExternalLock = static_cast< VCLExternalSolarLock* >( getExternalLock() );
66 
67     if ( m_pMenu )
68     {
69         m_aAccessibleChildren.assign( m_pMenu->GetItemCount(), Reference< XAccessible >() );
70         m_pMenu->AddEventListener( LINK( this, OAccessibleMenuBaseComponent, MenuEventListener ) );
71     }
72 }
73 
74 // -----------------------------------------------------------------------------
75 
~OAccessibleMenuBaseComponent()76 OAccessibleMenuBaseComponent::~OAccessibleMenuBaseComponent()
77 {
78     if ( m_pMenu )
79         m_pMenu->RemoveEventListener( LINK( this, OAccessibleMenuBaseComponent, MenuEventListener ) );
80 
81     delete m_pExternalLock;
82     m_pExternalLock = NULL;
83 }
84 
85 // -----------------------------------------------------------------------------
86 
IsEnabled()87 sal_Bool OAccessibleMenuBaseComponent::IsEnabled()
88 {
89     return sal_False;
90 }
91 
92 // -----------------------------------------------------------------------------
93 
IsFocused()94 sal_Bool OAccessibleMenuBaseComponent::IsFocused()
95 {
96     return sal_False;
97 }
98 
99 // -----------------------------------------------------------------------------
100 
IsVisible()101 sal_Bool OAccessibleMenuBaseComponent::IsVisible()
102 {
103     return sal_False;
104 }
105 
106 // -----------------------------------------------------------------------------
107 
IsSelected()108 sal_Bool OAccessibleMenuBaseComponent::IsSelected()
109 {
110     return sal_False;
111 }
112 
113 // -----------------------------------------------------------------------------
114 
IsChecked()115 sal_Bool OAccessibleMenuBaseComponent::IsChecked()
116 {
117     return sal_False;
118 }
119 
120 // -----------------------------------------------------------------------------
121 
SetStates()122 void OAccessibleMenuBaseComponent::SetStates()
123 {
124     m_bEnabled = IsEnabled();
125     m_bFocused = IsFocused();
126     m_bVisible = IsVisible();
127     m_bSelected = IsSelected();
128     m_bChecked = IsChecked();
129 }
130 
131 // -----------------------------------------------------------------------------
132 
SetEnabled(sal_Bool bEnabled)133 void OAccessibleMenuBaseComponent::SetEnabled( sal_Bool bEnabled )
134 {
135     if ( m_bEnabled != bEnabled )
136     {
137         sal_Int16 nStateType=AccessibleStateType::ENABLED;
138         if (IsMenuHideDisabledEntries())
139         {
140             nStateType = AccessibleStateType::VISIBLE;
141         }
142         Any aOldValue[2], aNewValue[2];
143         if ( m_bEnabled )
144         {
145             aOldValue[0] <<= AccessibleStateType::SENSITIVE;
146             aOldValue[1] <<= nStateType;
147         }
148         else
149         {
150             aNewValue[0] <<= nStateType;
151             aNewValue[1] <<= AccessibleStateType::SENSITIVE;
152         }
153         m_bEnabled = bEnabled;
154         NotifyAccessibleEvent( AccessibleEventId::STATE_CHANGED, aOldValue[0], aNewValue[0] );
155         NotifyAccessibleEvent( AccessibleEventId::STATE_CHANGED, aOldValue[1], aNewValue[1] );
156     }
157 }
158 
159 // -----------------------------------------------------------------------------
160 
SetFocused(sal_Bool bFocused)161 void OAccessibleMenuBaseComponent::SetFocused( sal_Bool bFocused )
162 {
163     if ( m_bFocused != bFocused )
164     {
165         Any aOldValue, aNewValue;
166         if ( m_bFocused )
167             aOldValue <<= AccessibleStateType::FOCUSED;
168         else
169             aNewValue <<= AccessibleStateType::FOCUSED;
170         m_bFocused = bFocused;
171         NotifyAccessibleEvent( AccessibleEventId::STATE_CHANGED, aOldValue, aNewValue );
172     }
173 }
174 
175 // -----------------------------------------------------------------------------
176 
SetVisible(sal_Bool bVisible)177 void OAccessibleMenuBaseComponent::SetVisible( sal_Bool bVisible )
178 {
179     if ( m_bVisible != bVisible )
180     {
181         Any aOldValue, aNewValue;
182         if ( m_bVisible )
183             aOldValue <<= AccessibleStateType::VISIBLE;
184         else
185             aNewValue <<= AccessibleStateType::VISIBLE;
186         m_bVisible = bVisible;
187         NotifyAccessibleEvent( AccessibleEventId::STATE_CHANGED, aOldValue, aNewValue );
188     }
189 }
190 
191 // -----------------------------------------------------------------------------
192 
SetSelected(sal_Bool bSelected)193 void OAccessibleMenuBaseComponent::SetSelected( sal_Bool bSelected )
194 {
195     if ( m_bSelected != bSelected )
196     {
197         Any aOldValue, aNewValue;
198         if ( m_bSelected )
199             aOldValue <<= AccessibleStateType::SELECTED;
200         else
201             aNewValue <<= AccessibleStateType::SELECTED;
202         m_bSelected = bSelected;
203         NotifyAccessibleEvent( AccessibleEventId::STATE_CHANGED, aOldValue, aNewValue );
204     }
205 }
206 
207 // -----------------------------------------------------------------------------
208 
SetChecked(sal_Bool bChecked)209 void OAccessibleMenuBaseComponent::SetChecked( sal_Bool bChecked )
210 {
211     if ( m_bChecked != bChecked )
212     {
213         Any aOldValue, aNewValue;
214         if ( m_bChecked )
215             aOldValue <<= AccessibleStateType::CHECKED;
216         else
217             aNewValue <<= AccessibleStateType::CHECKED;
218         m_bChecked = bChecked;
219         NotifyAccessibleEvent( AccessibleEventId::STATE_CHANGED, aOldValue, aNewValue );
220     }
221 }
222 
223 // -----------------------------------------------------------------------------
224 
UpdateEnabled(sal_Int32 i,sal_Bool bEnabled)225 void OAccessibleMenuBaseComponent::UpdateEnabled( sal_Int32 i, sal_Bool bEnabled )
226 {
227     if ( i >= 0 && i < (sal_Int32)m_aAccessibleChildren.size() )
228     {
229         Reference< XAccessible > xChild( m_aAccessibleChildren[i] );
230         if ( xChild.is() )
231         {
232             OAccessibleMenuBaseComponent* pComp = static_cast< OAccessibleMenuBaseComponent* >( xChild.get() );
233             if ( pComp )
234                 pComp->SetEnabled( bEnabled );
235         }
236     }
237 }
238 
239 // -----------------------------------------------------------------------------
240 
UpdateFocused(sal_Int32 i,sal_Bool bFocused)241 void OAccessibleMenuBaseComponent::UpdateFocused( sal_Int32 i, sal_Bool bFocused )
242 {
243     if ( i >= 0 && i < (sal_Int32)m_aAccessibleChildren.size() )
244     {
245         Reference< XAccessible > xChild( m_aAccessibleChildren[i] );
246         if ( xChild.is() )
247         {
248             OAccessibleMenuBaseComponent* pComp = static_cast< OAccessibleMenuBaseComponent* >( xChild.get() );
249             if ( pComp )
250                 pComp->SetFocused( bFocused );
251         }
252     }
253 }
254 
255 // -----------------------------------------------------------------------------
256 
UpdateVisible()257 void OAccessibleMenuBaseComponent::UpdateVisible()
258 {
259     SetVisible( IsVisible() );
260     for ( sal_uInt32 i = 0; i < m_aAccessibleChildren.size(); ++i )
261     {
262         Reference< XAccessible > xChild( m_aAccessibleChildren[i] );
263         if ( xChild.is() )
264         {
265             OAccessibleMenuBaseComponent* pComp = static_cast< OAccessibleMenuBaseComponent* >( xChild.get() );
266             if ( pComp )
267                 pComp->SetVisible( pComp->IsVisible() );
268         }
269     }
270 }
271 
272 // -----------------------------------------------------------------------------
273 
UpdateSelected(sal_Int32 i,sal_Bool bSelected)274 void OAccessibleMenuBaseComponent::UpdateSelected( sal_Int32 i, sal_Bool bSelected )
275 {
276     NotifyAccessibleEvent( AccessibleEventId::SELECTION_CHANGED, Any(), Any() );
277 
278     if ( i >= 0 && i < (sal_Int32)m_aAccessibleChildren.size() )
279     {
280         Reference< XAccessible > xChild( m_aAccessibleChildren[i] );
281         if ( xChild.is() )
282         {
283             OAccessibleMenuBaseComponent* pComp = static_cast< OAccessibleMenuBaseComponent* >( xChild.get() );
284             if ( pComp )
285                 pComp->SetSelected( bSelected );
286         }
287     }
288 }
289 
290 // -----------------------------------------------------------------------------
291 
UpdateChecked(sal_Int32 i,sal_Bool bChecked)292 void OAccessibleMenuBaseComponent::UpdateChecked( sal_Int32 i, sal_Bool bChecked )
293 {
294     if ( i >= 0 && i < (sal_Int32)m_aAccessibleChildren.size() )
295     {
296         Reference< XAccessible > xChild( m_aAccessibleChildren[i] );
297         if ( xChild.is() )
298         {
299             OAccessibleMenuBaseComponent* pComp = static_cast< OAccessibleMenuBaseComponent* >( xChild.get() );
300             if ( pComp )
301                 pComp->SetChecked( bChecked );
302         }
303     }
304 }
305 
306 // -----------------------------------------------------------------------------
307 
UpdateAccessibleName(sal_Int32 i)308 void OAccessibleMenuBaseComponent::UpdateAccessibleName( sal_Int32 i )
309 {
310     if ( i >= 0 && i < (sal_Int32)m_aAccessibleChildren.size() )
311     {
312         Reference< XAccessible > xChild( m_aAccessibleChildren[i] );
313         if ( xChild.is() )
314         {
315             OAccessibleMenuItemComponent* pComp = static_cast< OAccessibleMenuItemComponent* >( xChild.get() );
316             if ( pComp )
317                 pComp->SetAccessibleName( pComp->GetAccessibleName() );
318         }
319     }
320 }
321 
322 // -----------------------------------------------------------------------------
323 
UpdateItemText(sal_Int32 i)324 void OAccessibleMenuBaseComponent::UpdateItemText( sal_Int32 i )
325 {
326     if ( i >= 0 && i < (sal_Int32)m_aAccessibleChildren.size() )
327     {
328         Reference< XAccessible > xChild( m_aAccessibleChildren[i] );
329         if ( xChild.is() )
330         {
331             OAccessibleMenuItemComponent* pComp = static_cast< OAccessibleMenuItemComponent* >( xChild.get() );
332             if ( pComp )
333                 pComp->SetItemText( pComp->GetItemText() );
334         }
335     }
336 }
337 
338 // -----------------------------------------------------------------------------
339 
GetChildCount()340 sal_Int32 OAccessibleMenuBaseComponent::GetChildCount()
341 {
342     return m_aAccessibleChildren.size();
343 }
344 
345 // -----------------------------------------------------------------------------
346 
GetChild(sal_Int32 i)347 Reference< XAccessible > OAccessibleMenuBaseComponent::GetChild( sal_Int32 i )
348 {
349     Reference< XAccessible > xChild = m_aAccessibleChildren[i];
350     if ( !xChild.is() )
351     {
352         if ( m_pMenu )
353         {
354             // create a new child
355             OAccessibleMenuBaseComponent* pChild;
356 
357             if ( m_pMenu->GetItemType( (sal_uInt16)i ) == MENUITEM_SEPARATOR )
358             {
359                 pChild = new VCLXAccessibleMenuSeparator( m_pMenu, (sal_uInt16)i );
360             }
361             else
362             {
363                 PopupMenu* pPopupMenu = m_pMenu->GetPopupMenu( m_pMenu->GetItemId( (sal_uInt16)i ) );
364                 if ( pPopupMenu )
365                 {
366                     pChild = new VCLXAccessibleMenu( m_pMenu, (sal_uInt16)i, pPopupMenu );
367                     pPopupMenu->SetAccessible( pChild );
368                 }
369                 else
370                 {
371                     pChild = new VCLXAccessibleMenuItem( m_pMenu, (sal_uInt16)i );
372                 }
373             }
374 
375             // set states
376             pChild->SetStates();
377 
378             xChild = pChild;
379 
380             // insert into menu item list
381             m_aAccessibleChildren[i] = xChild;
382         }
383     }
384 
385     return xChild;
386 }
387 
388 // -----------------------------------------------------------------------------
389 
GetChildAt(const awt::Point & rPoint)390 Reference< XAccessible > OAccessibleMenuBaseComponent::GetChildAt( const awt::Point& rPoint )
391 {
392     Reference< XAccessible > xChild;
393     for ( sal_uInt32 i = 0, nCount = getAccessibleChildCount(); i < nCount; ++i )
394     {
395         Reference< XAccessible > xAcc = getAccessibleChild( i );
396         if ( xAcc.is() )
397         {
398             Reference< XAccessibleComponent > xComp( xAcc->getAccessibleContext(), UNO_QUERY );
399             if ( xComp.is() )
400             {
401                 Rectangle aRect = VCLRectangle( xComp->getBounds() );
402                 Point aPos = VCLPoint( rPoint );
403                 if ( aRect.IsInside( aPos ) )
404                 {
405                     xChild = xAcc;
406                     break;
407                 }
408             }
409         }
410     }
411 
412     return xChild;
413 }
414 
415 // -----------------------------------------------------------------------------
416 
InsertChild(sal_Int32 i)417 void OAccessibleMenuBaseComponent::InsertChild( sal_Int32 i )
418 {
419     if ( i > (sal_Int32)m_aAccessibleChildren.size() )
420         i = m_aAccessibleChildren.size();
421 
422     if ( i >= 0 )
423     {
424         // insert entry in child list
425         m_aAccessibleChildren.insert( m_aAccessibleChildren.begin() + i, Reference< XAccessible >() );
426 
427         // update item position of accessible children
428         for ( sal_uInt32 j = i, nCount = m_aAccessibleChildren.size(); j < nCount; ++j )
429         {
430             Reference< XAccessible > xAcc( m_aAccessibleChildren[j] );
431             if ( xAcc.is() )
432             {
433                 OAccessibleMenuItemComponent* pComp = static_cast< OAccessibleMenuItemComponent* >( xAcc.get() );
434                 if ( pComp )
435                     pComp->SetItemPos( (sal_uInt16)j );
436             }
437         }
438 
439         // send accessible child event
440         Reference< XAccessible > xChild( GetChild( i ) );
441         if ( xChild.is() )
442         {
443             Any aOldValue, aNewValue;
444             aNewValue <<= xChild;
445             NotifyAccessibleEvent( AccessibleEventId::CHILD, aOldValue, aNewValue );
446         }
447     }
448 }
449 
450 // -----------------------------------------------------------------------------
451 
RemoveChild(sal_Int32 i)452 void OAccessibleMenuBaseComponent::RemoveChild( sal_Int32 i )
453 {
454     if ( i >= 0 && i < (sal_Int32)m_aAccessibleChildren.size() )
455     {
456         // keep the accessible of the removed item
457         Reference< XAccessible > xChild( m_aAccessibleChildren[i] );
458 
459         // remove entry in child list
460         m_aAccessibleChildren.erase( m_aAccessibleChildren.begin() + i );
461 
462         // update item position of accessible children
463         for ( sal_uInt32 j = i, nCount = m_aAccessibleChildren.size(); j < nCount; ++j )
464         {
465             Reference< XAccessible > xAcc( m_aAccessibleChildren[j] );
466             if ( xAcc.is() )
467             {
468                 OAccessibleMenuItemComponent* pComp = static_cast< OAccessibleMenuItemComponent* >( xAcc.get() );
469                 if ( pComp )
470                     pComp->SetItemPos( (sal_uInt16)j );
471             }
472         }
473 
474         // send accessible child event
475         if ( xChild.is() )
476         {
477             Any aOldValue, aNewValue;
478             aOldValue <<= xChild;
479             NotifyAccessibleEvent( AccessibleEventId::CHILD, aOldValue, aNewValue );
480 
481             Reference< XComponent > xComponent( xChild, UNO_QUERY );
482             if ( xComponent.is() )
483                 xComponent->dispose();
484         }
485     }
486 }
487 
488 // -----------------------------------------------------------------------------
489 
IsHighlighted()490 sal_Bool OAccessibleMenuBaseComponent::IsHighlighted()
491 {
492     return sal_False;
493 }
494 
495 // -----------------------------------------------------------------------------
496 
IsChildHighlighted()497 sal_Bool OAccessibleMenuBaseComponent::IsChildHighlighted()
498 {
499     sal_Bool bChildHighlighted = sal_False;
500 
501     for ( sal_uInt32 i = 0; i < m_aAccessibleChildren.size(); ++i )
502     {
503         Reference< XAccessible > xChild( m_aAccessibleChildren[i] );
504         if ( xChild.is() )
505         {
506             OAccessibleMenuBaseComponent* pComp = static_cast< OAccessibleMenuBaseComponent* >( xChild.get() );
507             if ( pComp && pComp->IsHighlighted() )
508             {
509                 bChildHighlighted = sal_True;
510                 break;
511             }
512         }
513     }
514 
515     return bChildHighlighted;
516 }
517 
518 // -----------------------------------------------------------------------------
519 
SelectChild(sal_Int32 i)520 void OAccessibleMenuBaseComponent::SelectChild( sal_Int32 i )
521 {
522     // open the menu
523     if ( getAccessibleRole() == AccessibleRole::MENU && !IsPopupMenuOpen() )
524         Click();
525 
526     // highlight the child
527     if ( m_pMenu )
528         m_pMenu->HighlightItem( (sal_uInt16)i );
529 }
530 
531 // -----------------------------------------------------------------------------
532 
DeSelectAll()533 void OAccessibleMenuBaseComponent::DeSelectAll()
534 {
535     if ( m_pMenu )
536         m_pMenu->DeHighlight();
537 }
538 
539 // -----------------------------------------------------------------------------
540 
IsChildSelected(sal_Int32 i)541 sal_Bool OAccessibleMenuBaseComponent::IsChildSelected( sal_Int32 i )
542 {
543     sal_Bool bSelected = sal_False;
544 
545     if ( m_pMenu && m_pMenu->IsHighlighted( (sal_uInt16)i ) )
546         bSelected = sal_True;
547 
548     return bSelected;
549 }
550 
551 // -----------------------------------------------------------------------------
552 
Select()553 void OAccessibleMenuBaseComponent::Select()
554 {
555 }
556 
557 // -----------------------------------------------------------------------------
558 
DeSelect()559 void OAccessibleMenuBaseComponent::DeSelect()
560 {
561 }
562 
563 // -----------------------------------------------------------------------------
564 
Click()565 void OAccessibleMenuBaseComponent::Click()
566 {
567 }
568 
569 // -----------------------------------------------------------------------------
570 
IsPopupMenuOpen()571 sal_Bool OAccessibleMenuBaseComponent::IsPopupMenuOpen()
572 {
573     return sal_False;
574 }
575 
576 // -----------------------------------------------------------------------------
577 
IMPL_LINK(OAccessibleMenuBaseComponent,MenuEventListener,VclSimpleEvent *,pEvent)578 IMPL_LINK( OAccessibleMenuBaseComponent, MenuEventListener, VclSimpleEvent*, pEvent )
579 {
580     DBG_ASSERT( pEvent && pEvent->ISA( VclMenuEvent ), "OAccessibleMenuBaseComponent - Unknown MenuEvent!" );
581     if ( pEvent && pEvent->ISA( VclMenuEvent ) )
582     {
583         DBG_ASSERT( ((VclMenuEvent*)pEvent)->GetMenu(), "OAccessibleMenuBaseComponent - Menu?" );
584         ProcessMenuEvent( *(VclMenuEvent*)pEvent );
585     }
586     return 0;
587 }
588 
589 // -----------------------------------------------------------------------------
590 
ProcessMenuEvent(const VclMenuEvent & rVclMenuEvent)591 void OAccessibleMenuBaseComponent::ProcessMenuEvent( const VclMenuEvent& rVclMenuEvent )
592 {
593     sal_uInt16 nItemPos = rVclMenuEvent.GetItemPos();
594 
595     switch ( rVclMenuEvent.GetId() )
596     {
597         case VCLEVENT_MENU_SHOW:
598         case VCLEVENT_MENU_HIDE:
599         {
600             UpdateVisible();
601         }
602         break;
603         case VCLEVENT_MENU_HIGHLIGHT:
604         {
605             SetFocused( sal_False );
606             UpdateFocused( nItemPos, sal_True );
607             UpdateSelected( nItemPos, sal_True );
608         }
609         break;
610         case VCLEVENT_MENU_DEHIGHLIGHT:
611         {
612             UpdateFocused( nItemPos, sal_False );
613             UpdateSelected( nItemPos, sal_False );
614         }
615         break;
616         case VCLEVENT_MENU_SUBMENUACTIVATE:
617         {
618         }
619         break;
620         case VCLEVENT_MENU_SUBMENUDEACTIVATE:
621         {
622             UpdateFocused( nItemPos, sal_True );
623         }
624         break;
625         case VCLEVENT_MENU_ENABLE:
626         {
627             UpdateEnabled( nItemPos, sal_True );
628         }
629         break;
630         case VCLEVENT_MENU_DISABLE:
631         {
632             UpdateEnabled( nItemPos, sal_False );
633         }
634         break;
635         case VCLEVENT_MENU_SUBMENUCHANGED:
636         {
637             RemoveChild( nItemPos );
638             InsertChild( nItemPos );
639         }
640         break;
641         case VCLEVENT_MENU_INSERTITEM:
642         {
643             InsertChild( nItemPos );
644         }
645         break;
646         case VCLEVENT_MENU_REMOVEITEM:
647         {
648             RemoveChild( nItemPos );
649         }
650         break;
651         case VCLEVENT_MENU_ACCESSIBLENAMECHANGED:
652         {
653             UpdateAccessibleName( nItemPos );
654         }
655         break;
656         case VCLEVENT_MENU_ITEMTEXTCHANGED:
657         {
658             UpdateAccessibleName( nItemPos );
659             UpdateItemText( nItemPos );
660         }
661         break;
662         case VCLEVENT_MENU_ITEMCHECKED:
663         {
664             UpdateChecked( nItemPos, sal_True );
665         }
666         break;
667         case VCLEVENT_MENU_ITEMUNCHECKED:
668         {
669             UpdateChecked( nItemPos, sal_False );
670         }
671         break;
672         case VCLEVENT_OBJECT_DYING:
673         {
674             if ( m_pMenu )
675             {
676                 m_pMenu->RemoveEventListener( LINK( this, OAccessibleMenuBaseComponent, MenuEventListener ) );
677 
678                 m_pMenu = NULL;
679 
680                 // dispose all menu items
681                 for ( sal_uInt32 i = 0; i < m_aAccessibleChildren.size(); ++i )
682                 {
683                     Reference< XComponent > xComponent( m_aAccessibleChildren[i], UNO_QUERY );
684                     if ( xComponent.is() )
685                         xComponent->dispose();
686                 }
687                 m_aAccessibleChildren.clear();
688             }
689         }
690         break;
691         default:
692         {
693         }
694         break;
695     }
696 }
697 
698 // -----------------------------------------------------------------------------
699 // XInterface
700 // -----------------------------------------------------------------------------
701 
IMPLEMENT_FORWARD_XINTERFACE2(OAccessibleMenuBaseComponent,AccessibleExtendedComponentHelper_BASE,OAccessibleMenuBaseComponent_BASE)702 IMPLEMENT_FORWARD_XINTERFACE2( OAccessibleMenuBaseComponent, AccessibleExtendedComponentHelper_BASE, OAccessibleMenuBaseComponent_BASE )
703 
704 // -----------------------------------------------------------------------------
705 // XTypeProvider
706 // -----------------------------------------------------------------------------
707 
708 IMPLEMENT_FORWARD_XTYPEPROVIDER2( OAccessibleMenuBaseComponent, AccessibleExtendedComponentHelper_BASE, OAccessibleMenuBaseComponent_BASE )
709 
710 // -----------------------------------------------------------------------------
711 // XComponent
712 // -----------------------------------------------------------------------------
713 
714 void OAccessibleMenuBaseComponent::disposing()
715 {
716     AccessibleExtendedComponentHelper_BASE::disposing();
717 
718     if ( m_pMenu )
719     {
720         m_pMenu->RemoveEventListener( LINK( this, OAccessibleMenuBaseComponent, MenuEventListener ) );
721 
722         m_pMenu = NULL;
723 
724         // dispose all menu items
725         for ( sal_uInt32 i = 0; i < m_aAccessibleChildren.size(); ++i )
726         {
727             Reference< XComponent > xComponent( m_aAccessibleChildren[i], UNO_QUERY );
728             if ( xComponent.is() )
729                 xComponent->dispose();
730         }
731         m_aAccessibleChildren.clear();
732     }
733 }
734 
735 // -----------------------------------------------------------------------------
736 // XServiceInfo
737 // -----------------------------------------------------------------------------
738 
supportsService(const::rtl::OUString & rServiceName)739 sal_Bool OAccessibleMenuBaseComponent::supportsService( const ::rtl::OUString& rServiceName ) throw (RuntimeException)
740 {
741     Sequence< ::rtl::OUString > aNames( getSupportedServiceNames() );
742     const ::rtl::OUString* pNames = aNames.getConstArray();
743     const ::rtl::OUString* pEnd = pNames + aNames.getLength();
744     for ( ; pNames != pEnd && !pNames->equals( rServiceName ); ++pNames )
745         ;
746 
747     return pNames != pEnd;
748 }
749 
750 // -----------------------------------------------------------------------------
751 // XAccessible
752 // -----------------------------------------------------------------------------
753 
getAccessibleContext()754 Reference< XAccessibleContext > OAccessibleMenuBaseComponent::getAccessibleContext(  ) throw (RuntimeException)
755 {
756     OExternalLockGuard aGuard( this );
757 
758     return this;
759 }
760 
761 // -----------------------------------------------------------------------------
762 // XAccessibleContext
763 // -----------------------------------------------------------------------------
764 
getAccessibleStateSet()765 Reference< XAccessibleStateSet > OAccessibleMenuBaseComponent::getAccessibleStateSet(  ) throw (RuntimeException)
766 {
767     OExternalLockGuard aGuard( this );
768 
769     utl::AccessibleStateSetHelper* pStateSetHelper = new utl::AccessibleStateSetHelper;
770     Reference< XAccessibleStateSet > xSet = pStateSetHelper;
771 
772     if ( !rBHelper.bDisposed && !rBHelper.bInDispose )
773     {
774         FillAccessibleStateSet( *pStateSetHelper );
775     }
776     else
777     {
778         pStateSetHelper->AddState( AccessibleStateType::DEFUNC );
779     }
780 
781     return xSet;
782 }
783 
784 // -----------------------------------------------------------------------------
785 
IsMenuHideDisabledEntries()786 sal_Bool OAccessibleMenuBaseComponent::IsMenuHideDisabledEntries()
787 {
788     return sal_False;
789 }
790 
791