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 #include <cassert>
23
24 #include <com/sun/star/accessibility/XAccessibleEventBroadcaster.hpp>
25 #include <com/sun/star/accessibility/XAccessibleEventListener.hpp>
26 #include <com/sun/star/accessibility/XAccessibleComponent.hpp>
27 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
28
29 #include <oleacc.h>
30 #ifndef _SV_AccObjectWinManager_HXX
31 #include "AccObjectWinManager.hxx"
32 #endif
33 #include "AccEventListener.hxx"
34 #include "AccComponentEventListener.hxx"
35 #include "AccContainerEventListener.hxx"
36 #include "AccDialogEventListener.hxx"
37 #include "AccWindowEventListener.hxx"
38 #include "AccFrameEventListener.hxx"
39 #include "AccMenuEventListener.hxx"
40 #include "AccObjectContainerEventListener.hxx"
41 #include "AccParagraphEventListener.hxx"
42 #include "AccTextComponentEventListener.hxx"
43 #include "AccListEventListener.hxx"
44 #include "AccTreeEventListener.hxx"
45 #include "AccTableEventListener.hxx"
46 #include "AccObject.hxx"
47 #include "unomsaaevent.hxx"
48 #include "checkmt.hxx"
49
50 #define CHILDID_SELF 0
51
52
53 using namespace std;
54 using namespace com::sun::star::accessibility;
55 using namespace com::sun::star::uno;
56
57 AccObjectWinManager* g_acc_manager = NULL;
58 AccObjectWinManager* AccObjectWinManager::me = NULL;
59
60 /**
61 * Implementation of interface XMSAAService's method getAccObjectPtr() that return the
62 * corresponding com interface with the MS event.
63 *
64 * @param
65 * @return Com interface.
66 */
GetMSComPtr(long hWnd,long lParam,long wParam)67 long GetMSComPtr(long hWnd, long lParam, long wParam)
68 {
69 if( g_acc_manager )
70 return (long)g_acc_manager->Get_ToATInterface(HWND((void*)hWnd),lParam,wParam );
71 return NULL;
72 }
73
74 /**
75 * constructor
76 * @param Agent The agent kept in all listeners,it's the sole interface by which
77 * listener communicate with windows manager.
78 * pEventAccObj The present event accobject.
79 * oldFocus Last focused object.
80 * isSelectionChanged flag that identifies if there is selection changed.
81 * selectionChildObj Selected object.
82 * dChildID Chile resource ID.
83 * hAcc TopWindowHWND
84 * @return
85 */
AccObjectWinManager(AccObjectManagerAgent * Agent)86 AccObjectWinManager::AccObjectWinManager( AccObjectManagerAgent* Agent ):
87 pAgent( Agent ),
88 oldFocus( NULL )
89 {
90 }
91
92 /**
93 * Public method to produce manager
94 * @param Agent The agent kept in all listeners,it's the sole interface by which
95 * listener communicate with windows manager.
96 * @return
97 */
CreateAccObjectWinManagerInstance(AccObjectManagerAgent * Agent)98 AccObjectWinManager* AccObjectWinManager::CreateAccObjectWinManagerInstance( AccObjectManagerAgent* Agent )
99 {
100 if( me == NULL )
101 {
102 me = new AccObjectWinManager( Agent );
103 g_acc_manager = me;
104 return me;
105 }
106
107 return me;
108 }
109
110
111 /**
112 * Destructor,clear all resource.
113 * @param
114 * @return
115 */
~AccObjectWinManager()116 AccObjectWinManager::~AccObjectWinManager()
117 {
118 XIdAccList.clear();
119 HwndXAcc.clear();
120 XResIdAccList.clear();
121 XHWNDDocList.clear();
122 #ifdef ACC_DEBUG
123
124 fclose( pFile );
125 #endif
126 }
127
128
129 /**
130 * Get valid com object interface when notifying some MSAA event
131 * @param pWND The top window handle that contains that event control.
132 * @param wParam Windows system interface.
133 * @return Com interface with event.
134 */
135
Get_ToATInterface(HWND hWnd,long lParam,long wParam)136 long AccObjectWinManager::Get_ToATInterface( HWND hWnd, long lParam, long wParam)
137 {
138 vos::OGuard localGuard(maATInterfaceMutex);//
139
140 IMAccessible* pRetIMAcc = NULL;
141
142 if(lParam == OBJID_CLIENT )
143 {
144 AccObject* topWindowAccObj = GetTopWindowAccObj(hWnd);
145 if(topWindowAccObj)
146 {
147 pRetIMAcc = topWindowAccObj->GetIMAccessible();
148 if(pRetIMAcc)
149 pRetIMAcc->AddRef();//increase COM reference count
150 }
151 }
152
153 if ( pRetIMAcc && lParam == OBJID_CLIENT )
154 {
155 IAccessible* pTemp = dynamic_cast<IAccessible*>( pRetIMAcc );
156 HRESULT result = LresultFromObject(IID_IAccessible, wParam, pTemp);
157 pTemp->Release();
158 return result;
159 }
160 return 0;
161 }
162
163 /**
164 * Search AccObject by XAccessible pointer from our container.
165 * @param pXAcc XAccessible interface.
166 * @return Pointer of accObject that is found.
167 */
GetAccObjByXAcc(XAccessible * pXAcc)168 AccObject* AccObjectWinManager::GetAccObjByXAcc( XAccessible* pXAcc)
169 {
170 if( pXAcc == NULL)
171 return NULL;
172
173 XIdToAccObjHash::iterator pIndTemp = XIdAccList.find( (void*)pXAcc );
174 if ( pIndTemp == XIdAccList.end() )
175 return NULL;
176
177 return &(pIndTemp->second);
178 }
179
180 /**
181 * Search XAccessible by AccObject pointer from our container.
182 * @param pAccObj AccObject pointer.
183 * @return Pointer of XAccessible Interface.
184 */
GetXAccByAccObj(AccObject * pAccObj)185 XAccessible* AccObjectWinManager::GetXAccByAccObj(AccObject* pAccObj)
186 {
187 XIdToAccObjHash::iterator iter = XIdAccList.begin();
188 while(iter!=XIdAccList.end())
189 {
190 AccObject* tmp = &(iter->second);
191 if(tmp== pAccObj)
192 return (XAccessible*)(iter->first);
193 iter++;
194 }
195 return NULL;
196 }
197
198 /**
199 * get acc object of top window by its handle
200 * @param hWnd, top window handle
201 * @return pointer to AccObject
202 */
GetTopWindowAccObj(HWND hWnd)203 AccObject* AccObjectWinManager::GetTopWindowAccObj(HWND hWnd)
204 {
205 XHWNDToXAccHash::iterator iterResult =HwndXAcc.find(hWnd);
206 if(iterResult == HwndXAcc.end())
207 return NULL;
208 XAccessible* pXAcc = (XAccessible*)(iterResult->second);
209 return GetAccObjByXAcc(pXAcc);
210 }
211
212 /**
213 * Simulate MSAA event via XAccessible interface and event type.
214 * @param pXAcc XAccessible interface.
215 * @param state Customize Interface
216 * @return The terminate result that identifies if the call is successful.
217 */
NotifyAccEvent(XAccessible * pXAcc,short state)218 sal_Bool AccObjectWinManager::NotifyAccEvent(XAccessible* pXAcc,short state)
219 {
220 vos::OGuard aGuard(aNotifyMutex);
221
222 if (!IsInMainThread())
223 {
224 return sal_False;
225 }
226
227 Reference< XAccessibleContext > pRContext;
228
229 if( pXAcc == NULL)
230 return sal_False;
231
232
233 pRContext = pXAcc->getAccessibleContext();
234 if( !pRContext.is() )
235 return sal_False;
236
237
238 AccObject* selfAccObj= GetAccObjByXAcc(pXAcc);
239
240 if(selfAccObj==NULL)
241 return sal_False;
242
243 int selectNum =0;
244
245 long dChildID = selfAccObj->GetResID();
246 HWND hAcc = selfAccObj->GetParentHWND();
247
248 switch(state)
249 {
250 case UM_EVENT_STATE_FOCUSED:
251 {
252 UpdateAccFocus(pXAcc);
253 if( selfAccObj )
254 selfAccObj->UpdateDefaultAction( );
255 UpdateValue(pXAcc);
256 NotifyWinEvent( EVENT_OBJECT_FOCUS,hAcc, OBJID_CLIENT,dChildID );
257 break;
258 }
259 case UM_EVENT_STATE_BUSY:
260 NotifyWinEvent( EVENT_OBJECT_STATECHANGE,hAcc, OBJID_CLIENT,dChildID );
261 break;
262 case UM_EVENT_STATE_CHECKED:
263 NotifyWinEvent( EVENT_OBJECT_STATECHANGE,hAcc, OBJID_CLIENT,dChildID );
264 break;
265 case UM_EVENT_STATE_PRESSED:
266 NotifyWinEvent( EVENT_OBJECT_STATECHANGE,hAcc, OBJID_CLIENT,dChildID );
267 break;
268
269 //Removed fire out selected event
270 //case UM_EVENT_STATE_SELECTED:
271 // NotifyWinEvent( EVENT_OBJECT_STATECHANGE,hAcc, OBJID_CLIENT,dChildID );
272 // break;
273 case UM_EVENT_STATE_ARMED:
274 UpdateAccFocus(pXAcc);
275 NotifyWinEvent( EVENT_OBJECT_FOCUS,hAcc, OBJID_CLIENT,dChildID );
276 break;
277 case UM_EVENT_MENU_START:
278 NotifyWinEvent( EVENT_SYSTEM_MENUSTART,hAcc, OBJID_CLIENT,dChildID );
279 break;
280 case UM_EVENT_MENU_END:
281 NotifyWinEvent( EVENT_SYSTEM_MENUEND,hAcc, OBJID_CLIENT,dChildID );
282 break;
283 case UM_EVENT_MENUPOPUPSTART:
284 NotifyWinEvent( EVENT_SYSTEM_MENUPOPUPSTART,hAcc, OBJID_CLIENT,dChildID );
285 break;
286 case UM_EVENT_MENUPOPUPEND:
287 NotifyWinEvent( EVENT_SYSTEM_MENUPOPUPEND,hAcc, OBJID_CLIENT,dChildID );
288 break;
289 case UM_EVENT_SELECTION_CHANGED:
290 NotifyWinEvent( EVENT_OBJECT_SELECTION,hAcc, OBJID_CLIENT,dChildID );
291 break;
292 case UM_EVENT_SELECTION_CHANGED_ADD:
293 NotifyWinEvent( EVENT_OBJECT_SELECTIONADD,hAcc, OBJID_CLIENT,dChildID );
294 break;
295 case UM_EVENT_SELECTION_CHANGED_REMOVE:
296 NotifyWinEvent( EVENT_OBJECT_SELECTIONREMOVE,hAcc, OBJID_CLIENT,dChildID );
297 break;
298 case UM_EVENT_SELECTION_CHANGED_WITHIN:
299 NotifyWinEvent( EVENT_OBJECT_SELECTIONWITHIN,hAcc, OBJID_CLIENT,dChildID );
300 break;
301 case UM_EVENT_OBJECT_VALUECHANGE:
302 UpdateValue(pXAcc);
303 NotifyWinEvent( EVENT_OBJECT_VALUECHANGE,hAcc, OBJID_CLIENT,dChildID );
304 break;
305 case UM_EVENT_OBJECT_NAMECHANGE:
306 NotifyWinEvent( EVENT_OBJECT_NAMECHANGE,hAcc, OBJID_CLIENT,dChildID );
307 break;
308 case UM_EVENT_OBJECT_DESCRIPTIONCHANGE:
309 NotifyWinEvent( EVENT_OBJECT_DESCRIPTIONCHANGE,hAcc, OBJID_CLIENT,dChildID );
310 break;
311 case UM_EVENT_OBJECT_DEFACTIONCHANGE:
312 NotifyWinEvent( IA2_EVENT_ACTION_CHANGED,hAcc, OBJID_CLIENT,dChildID );
313 break;
314 case UM_EVENT_OBJECT_CARETCHANGE:
315 NotifyWinEvent( IA2_EVENT_TEXT_CARET_MOVED,hAcc, OBJID_CLIENT,dChildID );
316 break;
317 case UM_EVENT_OBJECT_TEXTCHANGE:
318 NotifyWinEvent( IA2_EVENT_TEXT_CHANGED,hAcc, OBJID_CLIENT,dChildID );
319 break;
320 case UM_EVENT_ACTIVE_DESCENDANT_CHANGED:
321 UpdateAccFocus(pXAcc);
322 NotifyWinEvent( EVENT_OBJECT_FOCUS,hAcc, OBJID_CLIENT,dChildID );
323 break;
324 case UM_EVENT_BOUNDRECT_CHANGED:
325 NotifyWinEvent( EVENT_OBJECT_LOCATIONCHANGE,hAcc, OBJID_CLIENT,dChildID );
326 break;
327 case UM_EVENT_VISIBLE_DATA_CHANGED:
328 NotifyWinEvent( IA2_EVENT_VISIBLE_DATA_CHANGED,hAcc, OBJID_CLIENT,dChildID );
329 break;
330 case UM_EVENT_SHOW :
331 NotifyWinEvent( EVENT_OBJECT_SHOW,hAcc, OBJID_CLIENT,dChildID );
332 NotifyWinEvent( EVENT_SYSTEM_FOREGROUND,hAcc, OBJID_CLIENT,dChildID );
333 break;
334 case UM_EVENT_TABLE_CAPTION_CHANGED:
335 NotifyWinEvent( IA2_EVENT_TABLE_CAPTION_CHANGED,hAcc, OBJID_CLIENT,dChildID );
336 break;
337 case UM_EVENT_TABLE_COLUMN_DESCRIPTION_CHANGED:
338 NotifyWinEvent( IA2_EVENT_TABLE_COLUMN_DESCRIPTION_CHANGED,hAcc, OBJID_CLIENT,dChildID );
339 break;
340 case UM_EVENT_TABLE_COLUMN_HEADER_CHANGED:
341 NotifyWinEvent( IA2_EVENT_TABLE_COLUMN_HEADER_CHANGED,hAcc, OBJID_CLIENT,dChildID );
342 break;
343 case UM_EVENT_TABLE_MODEL_CHANGED:
344 NotifyWinEvent( IA2_EVENT_TABLE_MODEL_CHANGED,hAcc, OBJID_CLIENT,dChildID );
345 break;
346 case UM_EVENT_TABLE_ROW_HEADER_CHANGED:
347 NotifyWinEvent( IA2_EVENT_TABLE_ROW_HEADER_CHANGED,hAcc, OBJID_CLIENT,dChildID );
348 break;
349 case UM_EVENT_TABLE_SUMMARY_CHANGED:
350 NotifyWinEvent( IA2_EVENT_TABLE_SUMMARY_CHANGED,hAcc, OBJID_CLIENT,dChildID );
351 break;
352 case UM_EVENT_TABLE_ROW_DESCRIPTION_CHANGED:
353 NotifyWinEvent( IA2_EVENT_TABLE_ROW_DESCRIPTION_CHANGED,hAcc, OBJID_CLIENT,dChildID );
354 break;
355 case UM_EVENT_OBJECT_REORDER:
356 NotifyWinEvent( EVENT_OBJECT_REORDER,hAcc, OBJID_CLIENT,dChildID );
357 break;
358 case UM_EVENT_PAGE_CHANGED:
359 NotifyWinEvent( IA2_EVENT_PAGE_CHANGED,hAcc, OBJID_CLIENT,dChildID );
360 break;
361 case UM_EVENT_CHILD_REMOVED:
362 NotifyWinEvent( EVENT_OBJECT_DESTROY,hAcc, OBJID_CLIENT,dChildID );
363 break;
364 case UM_EVENT_CHILD_ADDED:
365 NotifyWinEvent( EVENT_OBJECT_CREATE ,hAcc, OBJID_CLIENT,dChildID );
366 break;
367 case UM_EVENT_OBJECT_PAGECHANGED:
368 NotifyWinEvent( IA2_EVENT_PAGE_CHANGED ,hAcc, OBJID_CLIENT,dChildID );
369 break;
370 case UM_EVENT_TEXT_SELECTION_CHANGED:
371 NotifyWinEvent( IA2_EVENT_TEXT_SELECTION_CHANGED ,hAcc, OBJID_CLIENT,dChildID );
372 break;
373 case UM_EVENT_SECTION_CHANGED:
374 NotifyWinEvent( IA2_EVENT_SECTION_CHANGED ,hAcc, OBJID_CLIENT,dChildID );
375 break;
376 case UM_EVENT_COLUMN_CHANGED:
377 NotifyWinEvent( IA2_EVENT_TEXT_COLUMN_CHANGED ,hAcc, OBJID_CLIENT,dChildID );
378 break;
379 default:
380 break;
381 }
382
383 return sal_True;
384 }
385
386 /**
387 * Get Parent XAccessible interface by XAccessible interface.
388 * @param pXAcc XAccessible interface.
389 * @return Parent XAccessible interface.
390 */
GetParentXAccessible(XAccessible * pXAcc)391 XAccessible* AccObjectWinManager::GetParentXAccessible( XAccessible* pXAcc )
392 {
393 AccObject* pObj= GetAccObjByXAcc(pXAcc);
394 if( pObj ==NULL )
395 return NULL;
396 if(pObj->GetParentObj())
397 {
398 pObj = pObj->GetParentObj();
399 return pObj->GetXAccessible().get();
400 }
401 return NULL;
402 }
403
404 /**
405 * Get Parent role by XAccessible interface.
406 * @param pXAcc XAccessible interface.
407 * @return Parent role.
408 */
GetParentRole(XAccessible * pXAcc)409 short AccObjectWinManager::GetParentRole( XAccessible* pXAcc )
410 {
411 AccObject* pObj= GetAccObjByXAcc(pXAcc);
412 if( pObj ==NULL )
413 return -1;
414 if(pObj->GetParentObj())
415 {
416 pObj = pObj->GetParentObj();
417 if(pObj->GetXAccessible().is())
418 {
419 XAccessible* pXAcc = pObj->GetXAccessible().get();
420 Reference< XAccessibleContext > pRContext = pXAcc->getAccessibleContext();
421 if(pRContext.is())
422 return pRContext->getAccessibleRole();
423 }
424 }
425 return -1;
426 }
427
428 /**
429 * Update focus objcet by new focused XAccessible interface.
430 * @param newFocus New XAccessible interface that gets focus.
431 * @return
432 */
UpdateAccFocus(XAccessible * newFocus)433 void AccObjectWinManager::UpdateAccFocus(XAccessible* newFocus)
434 {
435 AccObject* pAccObjNew = GetAccObjByXAcc(newFocus);
436 if(pAccObjNew)
437 {
438 AccObject* pAccObjOld = GetAccObjByXAcc(oldFocus);
439 oldFocus = newFocus;
440 pAccObjNew->setFocus();
441 //if old == new, the pAccObjNew will be without focused state
442 if (pAccObjOld && pAccObjOld != pAccObjNew)
443 pAccObjOld->unsetFocus();
444 }
445 }
446
447 /**
448 * Update selected objcet by new focused XAccessible interface.
449 * @param pXAcc XAccessible interface that has selected child changed.
450 * @return Selected children count.
451 */
UpdateAccSelection(XAccessible * pXAcc)452 int AccObjectWinManager::UpdateAccSelection(XAccessible* pXAcc)
453 {
454 XAccessibleSelection* pSelection = NULL;
455 Reference< XAccessibleContext > pRContext;
456
457 if( pXAcc == NULL)
458 return sal_False;
459
460 pRContext = pXAcc->getAccessibleContext();
461 if( !pRContext.is() )
462 return sal_False;
463
464 Reference< XAccessibleSelection > pRSelection(pRContext,UNO_QUERY);
465 if( !pRSelection.is() )
466 return sal_False;
467
468 AccObject* pAccObj = GetAccObjByXAcc(pXAcc);
469 if(pAccObj==NULL)
470 return sal_False;
471
472 Reference<XAccessible> pRChild = NULL;
473 AccObject* pAccChildObj = NULL;
474 int selectNum= pRSelection->getSelectedAccessibleChildCount();
475
476 IAccSelectionList oldSelection = pAccObj->GetSelection();
477
478 if(selectNum > 4)//for selected.
479 return selectNum;
480 if(selectNum == 1 && oldSelection.size() == 0)
481 return 1;
482
483 for (int i=0;i<selectNum;i++)
484 {
485 pRChild = pRSelection->getSelectedAccessibleChild(i);
486 if(!pRChild.is())
487 {
488 continue;
489 }
490 Reference<XAccessibleContext> pRChildContext = pRChild->getAccessibleContext();
491 if(!pRChildContext.is())
492 {
493 continue;
494 }
495 long index = pRChildContext->getAccessibleIndexInParent();
496 IAccSelectionList::iterator temp = oldSelection.find(index);
497 if ( temp != oldSelection.end() )
498 {
499 oldSelection.erase(index);
500 continue;
501 }
502
503 pAccChildObj = NULL;
504 pAccChildObj = GetAccObjByXAcc(pRChild.get());
505 if(!pAccChildObj)
506 {
507 InsertAccObj(pRChild.get(), pXAcc,pAccObj->GetParentHWND());
508 pAccChildObj = GetAccObjByXAcc(pRChild.get());
509 }
510
511 pAccObj->AddSelect(index, pAccChildObj);
512
513 if(pAccChildObj != NULL)
514 NotifyWinEvent(EVENT_OBJECT_SELECTIONADD,pAccObj->GetParentHWND(), OBJID_CLIENT,pAccChildObj->GetResID());
515 }
516
517 IAccSelectionList::iterator iter = oldSelection.begin();
518 while(iter!=oldSelection.end())
519 {
520 pAccObj->GetSelection().erase(iter->first);
521 pAccChildObj = (AccObject*)(iter->second);
522 if(pAccChildObj != NULL)
523 NotifyWinEvent(EVENT_OBJECT_SELECTIONREMOVE,pAccObj->GetParentHWND(), OBJID_CLIENT,pAccChildObj->GetResID());
524 iter++;
525 }
526 return 0;
527
528 }
529
530 /**
531 * Delete child element from children list.
532 * @param pObj Child element that should be removed from parant child list.
533 * @return
534 */
DeleteAccChildNode(AccObject * pObj)535 void AccObjectWinManager::DeleteAccChildNode( AccObject* pObj )
536 {
537 AccObject *parentAccObj = pObj->GetParentObj();
538 if( parentAccObj )
539 parentAccObj->DeleteChild( pObj );
540 }
541
542 /**
543 * Delete XAccessible items in top window handle hashtable
544 * @param pXAcc XAccessible interface.
545 * @return
546 */
DeleteFromHwndXAcc(XAccessible * pXAcc)547 void AccObjectWinManager::DeleteFromHwndXAcc(XAccessible* pXAcc )
548 {
549 XHWNDToXAccHash::iterator iter = HwndXAcc.begin();
550 while(iter!=HwndXAcc.end())
551 {
552 if(iter->second == pXAcc )
553 {
554 HwndXAcc.erase(iter);
555 return;
556 }
557 iter++;
558 }
559 }
560
561 /**
562 * Delete Delete all children with the tree root of XAccessible pointer
563 * @param pXAcc Tree root XAccessible interface.
564 * @return
565 */
DeleteChildrenAccObj(XAccessible * pXAcc)566 void AccObjectWinManager::DeleteChildrenAccObj(XAccessible* pXAcc)
567 {
568 vos::OGuard aGuard( aDeleteMutex );
569 AccObject* currentObj=NULL;
570 AccObject* childObj=NULL;
571 XAccessible* pTmpXAcc=NULL;
572
573 currentObj = GetAccObjByXAcc( pXAcc);
574 if(currentObj)
575 {
576 childObj = currentObj->NextChild();
577 while(childObj)
578 {
579 pTmpXAcc = GetXAccByAccObj(childObj);
580 if(pTmpXAcc)
581 {
582 DeleteChildrenAccObj(pTmpXAcc);
583 DeleteAccObj(pTmpXAcc);
584 }
585 childObj = currentObj->NextChild();
586 }
587 }
588 }
589
590 /**
591 * Delete Delete Acc object self.
592 * @param pXAcc The XAccessible interface.
593 * @return
594 */
DeleteAccObj(XAccessible * pXAcc)595 void AccObjectWinManager::DeleteAccObj( XAccessible* pXAcc )
596 {
597 vos::OGuard aGuard( aDeleteMutex );
598 if( pXAcc == NULL )
599 return;
600 XIdToAccObjHash::iterator temp = XIdAccList.find(pXAcc);
601 if( temp != XIdAccList.end() )
602 {
603 ResIdGen.SetSub( temp->second.GetResID() );
604 }
605 else
606 {
607 return;
608 }
609
610 AccObject& accObj = temp->second;
611 DeleteAccChildNode( &accObj );
612 DeleteAccListener( &accObj );
613 if( accObj.GetIMAccessible() )
614 {
615 accObj.GetIMAccessible()->Release();
616 }
617 XIdAccList.erase( pXAcc );
618 XResIdAccList.erase( accObj.GetResID() );
619 DeleteFromHwndXAcc(pXAcc);
620 }
621
622 /**
623 * Delete listener that inspects some XAccessible object
624 * @param pAccObj Accobject pointer.
625 * @return
626 */
DeleteAccListener(AccObject * pAccObj)627 void AccObjectWinManager::DeleteAccListener( AccObject* pAccObj )
628 {
629 AccEventListener* listener = pAccObj->getListener();
630 if( listener==NULL )
631 return;
632 listener->removeMeFromBroadcaster();
633 pAccObj->SetListener(NULL);
634 }
635
636 /**
637 * Generate a child ID, which is used for AT
638 * @param
639 * @return New resource ID.
640 */
ImpleGenerateResID()641 inline long AccObjectWinManager::ImpleGenerateResID()
642 {
643 return ResIdGen.GenerateNewResID();
644 }
645
646 /**
647 * Insert all children of the current acc object
648 * @param pXAcc XAccessible interface
649 * @param pWnd Top Window handle
650 * @return The calling result.
651 */
InsertChildrenAccObj(com::sun::star::accessibility::XAccessible * pXAcc,HWND pWnd)652 sal_Bool AccObjectWinManager::InsertChildrenAccObj( com::sun::star::accessibility::XAccessible* pXAcc,
653 HWND pWnd)
654 {
655 if(!IsContainer(pXAcc))
656 return sal_False;
657
658 Reference< XAccessibleContext > pRContext;
659
660 if( pXAcc == NULL)
661 return sal_False;
662 pRContext = pXAcc->getAccessibleContext();
663 if( !pRContext.is() )
664 return sal_False;
665
666 short role = pRContext->getAccessibleRole();
667
668 if(com::sun::star::accessibility::AccessibleRole::DOCUMENT == role )
669 {
670 if(IsStateManageDescendant(pXAcc))
671 {
672 return sal_True;
673 }
674 }
675
676 int count = pRContext->getAccessibleChildCount();
677 for (int i=0;i<count;i++)
678 {
679 Reference<XAccessible> mxAccessible
680 = pRContext->getAccessibleChild(i);
681 XAccessible* mpAccessible = mxAccessible.get();
682 if(mpAccessible != NULL)
683 {
684 InsertAccObj( mpAccessible,pXAcc,pWnd );
685 InsertChildrenAccObj(mpAccessible,pWnd);
686 }
687 }
688
689 return sal_True;
690 }
691
692 /**
693 * Insert child object.
694 * @param pCurObj The child object
695 * @param pParentObj The parant object
696 * @param pWnd Top window handle.
697 * @return
698 */
InsertAccChildNode(AccObject * pCurObj,AccObject * pParentObj,HWND)699 void AccObjectWinManager::InsertAccChildNode( AccObject* pCurObj, AccObject* pParentObj, HWND /* pWnd */ )
700 {
701 if(pCurObj)
702 {
703 if(pParentObj)
704 {
705 pParentObj->InsertChild(pCurObj);
706 }
707 else
708 {
709 pCurObj->UpdateValidWindow();
710 }
711 }
712 }
713
714 /**
715 * Insert child object.
716 * @param pCurObj The child object
717 * @param pParentObj The parant object
718 * @param pWnd Top window handle.
719 * @return
720 */
InsertAccObj(XAccessible * pXAcc,XAccessible * pParentXAcc,HWND pWnd)721 sal_Bool AccObjectWinManager::InsertAccObj( XAccessible* pXAcc,XAccessible* pParentXAcc,HWND pWnd )
722 {
723 XIdToAccObjHash::iterator itXacc = XIdAccList.find( (void*)pXAcc );
724 if (itXacc != XIdAccList.end() )
725 {
726 short nCurRole =GetRole(pXAcc);
727 if (AccessibleRole::SHAPE == nCurRole)
728 {
729 AccObject &objXacc = itXacc->second;
730 AccObject *pObjParent = objXacc.GetParentObj();
731 if (pObjParent &&
732 pObjParent->GetXAccessible().is() &&
733 pObjParent->GetXAccessible().get() != pParentXAcc)
734 {
735 XIdToAccObjHash::iterator itXaccParent = XIdAccList.find( (void*)pParentXAcc );
736 if(itXaccParent != XIdAccList.end())
737 {
738 objXacc.SetParentObj(&(itXaccParent->second));
739 }
740 }
741 }
742 return sal_False;
743 }
744
745
746 Reference< XAccessibleContext > pRContext;
747
748 if( pXAcc == NULL)
749 return sal_False;
750
751 pRContext = pXAcc->getAccessibleContext();
752 if( !pRContext.is() )
753 return sal_False;
754
755 if( pWnd == NULL )
756 {
757 if(pParentXAcc)
758 {
759 AccObject* pObj = GetAccObjByXAcc(pParentXAcc);
760 if(pObj)
761 pWnd = pObj->GetParentHWND();
762 }
763 if( pWnd == NULL )
764 return sal_False;
765 }
766
767 AccObject pObj( pXAcc,pAgent );
768 if( pObj.GetIMAccessible() == NULL )
769 return sal_False;
770 pObj.SetResID( this->ImpleGenerateResID());
771 pObj.SetParentHWND( pWnd );
772
773 //for file name support
774 if ( pObj.GetRole() == DOCUMENT )
775 {
776 XHWNDToDocumentHash::iterator aIter = XHWNDDocList.find( (long)pWnd );
777 if ( aIter != XHWNDDocList.end() )
778 {
779 XHWNDDocList.erase( aIter );
780 }
781 XHWNDDocList.insert( XHWNDToDocumentHash::value_type( (long)pWnd, pXAcc ) );
782
783 }
784 //end of file name
785
786 AccEventListener* listener = createAccEventListener(pXAcc, pAgent);
787 if(listener==NULL)
788 return sal_False;
789 Reference<XAccessibleComponent> xComponent(pRContext,UNO_QUERY);
790 Reference<XAccessibleEventBroadcaster> broadcaster(xComponent,UNO_QUERY);
791 if (broadcaster.is())
792 {
793 Reference <XAccessibleEventListener> pp (
794 static_cast< XAccessibleEventListener* >(listener),UNO_QUERY );
795 if(pp.is())
796 {
797 broadcaster->addEventListener(pp);
798 }
799 else
800 {
801 delete listener;
802 return sal_False;
803 }
804 }
805 else
806 return sal_False;
807
808 XIdAccList.insert( XIdToAccObjHash::value_type( (void*)pXAcc, pObj ));
809 XIdToAccObjHash::iterator pIndTemp = XIdAccList.find( (void*)pXAcc );
810 XResIdAccList.insert(XResIdToAccObjHash::value_type(pObj.GetResID(),&(pIndTemp->second)));
811
812 AccObject* pCurObj = GetAccObjByXAcc(pXAcc);
813 if( pCurObj )
814 {
815 pCurObj->SetListener( listener );
816 if(listener != NULL)
817 listener->acquire();
818 }
819
820 AccObject* pParentObj = GetAccObjByXAcc(pParentXAcc);
821 InsertAccChildNode(pCurObj,pParentObj,pWnd);
822 if( pCurObj )
823 pCurObj->UpdateAccessibleInfoFromUnoToMSAA();
824 return sal_True;
825 }
826
827
828 /**
829 * save the pair <topwindowhandle, XAccessible>
830 * @param hWnd, top window handle
831 * @param pXAcc XAccessible interface for top window
832 * @return void
833 */
SaveTopWindowHandle(HWND hWnd,com::sun::star::accessibility::XAccessible * pXAcc)834 void AccObjectWinManager::SaveTopWindowHandle(HWND hWnd, com::sun::star::accessibility::XAccessible* pXAcc)
835 {
836 HwndXAcc.insert( XHWNDToXAccHash::value_type( hWnd,(void*)pXAcc ) );
837 }
838
839
840 /**
841 * create the corresponding listener.
842 * @param pXAcc XAccessible interface.
843 * @param Agent The agent kept in all listeners,it's the sole interface by which
844 * listener communicate with windows manager.
845 * @return
846 */
createAccEventListener(XAccessible * pXAcc,AccObjectManagerAgent *)847 AccEventListener* AccObjectWinManager::createAccEventListener(XAccessible* pXAcc, AccObjectManagerAgent* /* Agent */ )
848 {
849 AccEventListener* listener = NULL;
850 Reference<XAccessibleContext> xContext(pXAcc->getAccessibleContext(),UNO_QUERY);
851 if(xContext.is())
852 {
853 switch( xContext->getAccessibleRole() )
854 {
855 case /*AccessibleRole::*/DIALOG:
856 listener = new AccDialogEventListener(pXAcc,pAgent);
857 break;
858 case /*AccessibleRole::*/FRAME:
859 listener = new AccFrameEventListener(pXAcc,pAgent);
860 break;
861 case /*AccessibleRole::*/WINDOW:
862 listener = new AccWindowEventListener(pXAcc,pAgent);
863 break;
864 case /*AccessibleRole::*/ROOT_PANE:
865 listener = new AccFrameEventListener(pXAcc,pAgent);
866 break;
867 //Container
868 case /*AccessibleRole::*/CANVAS:
869 case /*AccessibleRole::*/COMBO_BOX:
870 case /*AccessibleRole::*/DOCUMENT:
871 case /*AccessibleRole::*/END_NOTE:
872 case /*AccessibleRole::*/FILLER:
873 case /*AccessibleRole::*/FOOTNOTE:
874 case /*AccessibleRole::*/FOOTER:
875 case /*AccessibleRole::*/HEADER:
876 case /*AccessibleRole::*/LAYERED_PANE:
877 case /*AccessibleRole::*/MENU_BAR:
878 case /*AccessibleRole::*/POPUP_MENU:
879 case /*AccessibleRole::*/OPTION_PANE:
880 case /*AccessibleRole::*/PAGE_TAB:
881 case /*AccessibleRole::*/PAGE_TAB_LIST:
882 case /*AccessibleRole::*/PANEL:
883 case /*AccessibleRole::*/SCROLL_PANE:
884 case /*AccessibleRole::*/SPLIT_PANE:
885 case /*AccessibleRole::*/STATUS_BAR:
886 case /*AccessibleRole::*/TABLE_CELL:
887 case /*AccessibleRole::*/TOOL_BAR:
888 case /*AccessibleRole::*/VIEW_PORT:
889 listener = new AccContainerEventListener(pXAcc,pAgent);
890 break;
891 case /*AccessibleRole::*/PARAGRAPH:
892 case /*AccessibleRole::*/HEADING:
893 listener = new AccParagraphEventListener(pXAcc,pAgent);
894 break;
895 //Component
896 case /*AccessibleRole::*/CHECK_BOX:
897 case /*AccessibleRole::*/ICON:
898 case /*AccessibleRole::*/LABEL:
899 case /*AccessibleRole::*/MENU_ITEM:
900 case /*AccessibleRole::*/CHECK_MENU_ITEM:
901 case /*AccessibleRole::*/RADIO_MENU_ITEM:
902 case /*AccessibleRole::*/PUSH_BUTTON:
903 case /*AccessibleRole::*/RADIO_BUTTON:
904 case /*AccessibleRole::*/SCROLL_BAR:
905 case /*AccessibleRole::*/SEPARATOR:
906 case /*AccessibleRole::*/TOGGLE_BUTTON:
907 case /*AccessibleRole::*/BUTTON_DROPDOWN:
908 case /*AccessibleRole::*/TOOL_TIP:
909 case /*AccessibleRole::*/SPIN_BOX:
910 case DATE_EDITOR:
911 listener = new AccComponentEventListener(pXAcc,pAgent);
912 break;
913 //text component
914 case /*AccessibleRole::*/TEXT:
915 listener = new AccTextComponentEventListener(pXAcc,pAgent);
916 break;
917 //menu
918 case /*AccessibleRole::*/MENU:
919 listener = new AccMenuEventListener(pXAcc,pAgent);
920 break;
921 //object container
922 case /*AccessibleRole::*/SHAPE:
923
924 case /*AccessibleRole::*/EMBEDDED_OBJECT:
925 case /*AccessibleRole::*/GRAPHIC:
926 case /*AccessibleRole::*/TEXT_FRAME:
927 listener = new AccObjectContainerEventListener(pXAcc,pAgent);
928 break;
929 //descendmanager
930 case /*AccessibleRole::*/LIST:
931 listener = new AccListEventListener(pXAcc,pAgent);
932 break;
933 case /*AccessibleRole::*/TREE:
934 listener = new AccTreeEventListener(pXAcc,pAgent);
935 break;
936 //special
937 case /*AccessibleRole::*/COLUMN_HEADER:
938 case /*AccessibleRole::*/TABLE:
939 listener = new AccTableEventListener(pXAcc,pAgent);
940 break;
941 default:
942 listener = new AccContainerEventListener(pXAcc,pAgent);
943 break;
944 }
945 }
946
947 return listener;
948 }
949
950 /**
951 * state is a combination integer, each bit of which represents a single state,
952 * such as focused,1 for the state on,0 for the state off. Here call COM interface
953 * to modify the state value, including DecreaseState.
954 * @param pXAcc XAccessible interface.
955 * @param pState Changed state.
956 * @return
957 */
DecreaseState(XAccessible * pXAcc,unsigned short pState)958 void AccObjectWinManager::DecreaseState( XAccessible* pXAcc,unsigned short pState )
959 {
960 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
961 if( pAccObj )
962 pAccObj->DecreaseState( pState );
963 }
964
965 /**
966 * state is a combination integer, each bit of which represents a single state,such as focused,1 for
967 * the state on,0 for the state off. Here call COM interface to modify the state value, including
968 * IncreaseState.
969 * @param pXAcc XAccessible interface.
970 * @param pState Changed state.
971 * @return
972 */
IncreaseState(XAccessible * pXAcc,unsigned short pState)973 void AccObjectWinManager::IncreaseState( XAccessible* pXAcc,unsigned short pState )
974 {
975 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
976 if( pAccObj )
977 pAccObj->IncreaseState( pState );
978 }
979
UpdateState(com::sun::star::accessibility::XAccessible * pXAcc)980 void AccObjectWinManager::UpdateState( com::sun::star::accessibility::XAccessible* pXAcc )
981 {
982 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
983 if( pAccObj )
984 pAccObj->UpdateState( );
985 }
986
987 /**
988 * Set corresponding com object's accessible name via XAccessilbe interface and new
989 * name
990 * @param pXAcc XAccessible interface.
991 * @return
992 */
UpdateAccName(XAccessible * pXAcc)993 void AccObjectWinManager::UpdateAccName( XAccessible* pXAcc )
994 {
995 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
996 if( pAccObj )
997 pAccObj->UpdateName();
998 }
999
UpdateAction(XAccessible * pXAcc)1000 void AccObjectWinManager::UpdateAction( XAccessible* pXAcc )
1001 {
1002 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
1003 if( pAccObj )
1004 pAccObj->UpdateAction();
1005 }
1006
UpdateDescription(XAccessible * pXAcc)1007 void AccObjectWinManager::UpdateDescription( XAccessible* pXAcc )
1008 {
1009 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
1010 if ( pAccObj )
1011 pAccObj->UpdateDescription();
1012 }
1013
1014 /**
1015 * Set corresponding com object's accessible location via XAccessilbe interface and new
1016 * location.
1017 * @param pXAcc XAccessible interface.
1018 * @return
1019 */
SetLocation(XAccessible * pXAcc,long,long,long,long)1020 void AccObjectWinManager::SetLocation( XAccessible* pXAcc, long /*top*/, long /*left*/, long /*width*/, long /*height*/ )
1021 {
1022 AccObject* pObj = GetAccObjByXAcc( pXAcc );
1023 //get the location from XComponent.
1024 Reference< XAccessibleContext > pRContext = pXAcc->getAccessibleContext();
1025 if( pObj )
1026 pObj->UpdateLocation();
1027 }
1028
1029 /**
1030 * Set corresponding com object's value via XAccessilbe interface and new value.
1031 * @param pXAcc XAccessible interface.
1032 * @param pAny new value.
1033 * @return
1034 */
SetValue(XAccessible * pXAcc,Any pAny)1035 void AccObjectWinManager::SetValue( XAccessible* pXAcc, Any pAny )
1036 {
1037 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
1038 if( pAccObj )
1039 pAccObj->SetValue( pAny );
1040 }
1041
1042 /**
1043 * Set corresponding com object's value via XAccessilbe interface.
1044 * @param pXAcc XAccessible interface.
1045 * @return
1046 */
UpdateValue(XAccessible * pXAcc)1047 void AccObjectWinManager::UpdateValue( XAccessible* pXAcc )
1048 {
1049 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
1050 if( pAccObj )
1051 pAccObj->UpdateValue();
1052 }
1053
1054 /**
1055 * Set corresponding com object's name via XAccessilbe interface and new name.
1056 * @param pXAcc XAccessible interface.
1057 * @param newName new name
1058 * @return
1059 */
SetAccName(XAccessible * pXAcc,Any newName)1060 void AccObjectWinManager::SetAccName( XAccessible* pXAcc, Any newName)
1061 {
1062 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
1063 if( pAccObj )
1064 pAccObj->SetName( newName );
1065 }
1066
1067 /**
1068 * Set corresponding com object's description via XAccessilbe interface and new description.
1069 * @param pXAcc XAccessible interface.
1070 * @param newDesc new description
1071 * @return
1072 */
SetDescription(XAccessible * pXAcc,Any newDesc)1073 void AccObjectWinManager::SetDescription( XAccessible* pXAcc, Any newDesc )
1074 {
1075 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
1076 if( pAccObj )
1077 pAccObj->SetDescription( newDesc );
1078 }
1079
1080 /**
1081 * Set corresponding com object's role via XAccessilbe interface and new role.
1082 * @param pXAcc XAccessible interface.
1083 * @param Role new role
1084 * @return
1085 */
SetRole(XAccessible * pXAcc,long Role)1086 void AccObjectWinManager::SetRole( XAccessible* pXAcc, long Role )
1087 {
1088 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
1089 if( pAccObj )
1090 pAccObj->SetRole( (short)Role );
1091 }
1092
1093 /**
1094 * Judge if a XAccessible object is a container object.
1095 * @param pAccessible XAccessible interface.
1096 * @return If XAccessible object is container.
1097 */
IsContainer(XAccessible * pAccessible)1098 sal_Bool AccObjectWinManager::IsContainer(XAccessible* pAccessible)
1099 {
1100 try
1101 {
1102 if(pAccessible)
1103 {
1104 Reference<XAccessibleContext> xContext(pAccessible->getAccessibleContext(),UNO_QUERY);
1105 if(xContext.is())
1106 {
1107 switch( xContext->getAccessibleRole() )
1108 {
1109 case /*AccessibleRole::*/DIALOG:
1110 case /*AccessibleRole::*/FRAME:
1111 case /*AccessibleRole::*/WINDOW:
1112 case /*AccessibleRole::*/ROOT_PANE:
1113 case /*AccessibleRole::*/CANVAS:
1114 case /*AccessibleRole::*/COMBO_BOX:
1115 case /*AccessibleRole::*/DOCUMENT:
1116 case /*AccessibleRole::*/EMBEDDED_OBJECT:
1117 case /*AccessibleRole::*/END_NOTE:
1118 case /*AccessibleRole::*/FILLER:
1119 case /*AccessibleRole::*/FOOTNOTE:
1120 case /*AccessibleRole::*/FOOTER:
1121 case /*AccessibleRole::*/GRAPHIC:
1122 case /*AccessibleRole::*/GROUP_BOX:
1123 case /*AccessibleRole::*/HEADER:
1124 case /*AccessibleRole::*/LAYERED_PANE:
1125 case /*AccessibleRole::*/MENU_BAR:
1126 case /*AccessibleRole::*/POPUP_MENU:
1127 case /*AccessibleRole::*/OPTION_PANE:
1128 case /*AccessibleRole::*/PAGE_TAB:
1129 case /*AccessibleRole::*/PAGE_TAB_LIST:
1130 case /*AccessibleRole::*/PANEL:
1131 case /*AccessibleRole::*/SCROLL_PANE:
1132 case /*AccessibleRole::*/SPLIT_PANE:
1133 case /*AccessibleRole::*/STATUS_BAR:
1134 case /*AccessibleRole::*/TABLE_CELL:
1135 case /*AccessibleRole::*/TEXT_FRAME:
1136 case /*AccessibleRole::*/TOOL_BAR:
1137 case /*AccessibleRole::*/VIEW_PORT:
1138 case /*AccessibleRole::*/SHAPE:
1139 return sal_True;
1140 break;
1141 case /*AccessibleRole::*/COLUMN_HEADER:
1142 case /*AccessibleRole::*/TABLE:
1143 if(!IsStateManageDescendant(pAccessible))
1144 return sal_True;
1145 break;
1146 case /*AccessibleRole::*/MENU:
1147 return sal_True;
1148 break;
1149 default:
1150 return sal_False;
1151 }
1152 }
1153 }
1154 }
1155 catch(...)
1156 {
1157 return sal_False;
1158 }
1159 return sal_False;
1160 }
1161
1162 /**
1163 * Judge if a XAccessible object has ManageDescendant event.
1164 * @param pAccessible XAccessible interface.
1165 * @return If XAccessible object is managedescendant.
1166 */
IsStateManageDescendant(XAccessible * pAccessible)1167 bool AccObjectWinManager::IsStateManageDescendant(XAccessible* pAccessible)
1168 {
1169 if(pAccessible)
1170 {
1171 Reference<XAccessibleContext> xContext(pAccessible->getAccessibleContext(),UNO_QUERY);
1172 if(xContext.is())
1173 {
1174 Reference< XAccessibleStateSet > pRState = xContext->getAccessibleStateSet();
1175 if( !pRState.is() )
1176 return sal_False;
1177
1178 Sequence<short> pStates = pRState->getStates();
1179 int count = pStates.getLength();
1180 for( int iIndex = 0;iIndex < count;iIndex++ )
1181 {
1182 if(pStates[iIndex] == /*AccessibleStateType::*/MANAGES_DESCENDANTS)
1183 return sal_True;
1184 }
1185 }
1186 }
1187 return sal_False;
1188 }
1189
1190 /**
1191 * Query and get IAccessible interface by XAccessible interface from list.
1192 * @param pXAcc XAccessible interface.
1193 * @return Com accobject interface.
1194 */
GetIMAccByXAcc(XAccessible * pXAcc)1195 IMAccessible* AccObjectWinManager::GetIMAccByXAcc(XAccessible* pXAcc)
1196 {
1197 AccObject* pAccObj = GetAccObjByXAcc(pXAcc);
1198 if(pAccObj)
1199 {
1200 return pAccObj->GetIMAccessible();
1201 }
1202 else
1203 {
1204 return NULL;
1205 }
1206 }
1207
1208 /**
1209 * Query and get IAccessible interface by child id from list.
1210 * @param resID, childID.
1211 * @return Com accobject interface.
1212 */
GetIAccessibleFromResID(long resID)1213 IMAccessible * AccObjectWinManager::GetIAccessibleFromResID(long resID)
1214 {
1215 XResIdToAccObjHash::iterator pIndTemp = XResIdAccList.find( resID );
1216 if ( pIndTemp == XResIdAccList.end() )
1217 return NULL;
1218
1219 AccObject* pObj = pIndTemp->second;
1220
1221 if(pObj->GetIMAccessible())
1222 return pObj->GetIMAccessible();
1223 return NULL;
1224 }
1225 /**
1226 * Notify some object will be destroyed.
1227 * @param pXAcc XAccessible interface.
1228 * @return Com accobject interface.
1229 */
NotifyDestroy(XAccessible * pXAcc)1230 void AccObjectWinManager::NotifyDestroy(XAccessible* pXAcc)
1231 {
1232 AccObject* accObj = GetAccObjByXAcc(pXAcc);
1233 if(accObj)
1234 {
1235 accObj->NotifyDestroy(sal_True);
1236 }
1237 }
1238
1239
UpdateChildState(com::sun::star::accessibility::XAccessible * pAccSubMenu)1240 void AccObjectWinManager::UpdateChildState(com::sun::star::accessibility::XAccessible* pAccSubMenu)
1241 {
1242 Reference<com::sun::star::accessibility::XAccessibleContext> xContext(pAccSubMenu,UNO_QUERY);
1243 if (!xContext.is())
1244 {
1245 return;
1246 }
1247 sal_Int32 nCount = xContext->getAccessibleChildCount();
1248 for (sal_Int32 i = 0 ; i < nCount ; ++i)
1249 {
1250 Reference<com::sun::star::accessibility::XAccessible> xChild = xContext->getAccessibleChild(i);
1251 if (xChild.is())
1252 {
1253 AccObject *pObj = GetAccObjByXAcc(xChild.get());
1254 if (pObj)
1255 {
1256 pObj->UpdateState();
1257 }
1258 }
1259 }
1260 }
1261
1262
IsSpecialToolboItem(com::sun::star::accessibility::XAccessible * pXAcc)1263 bool AccObjectWinManager::IsSpecialToolboItem(com::sun::star::accessibility::XAccessible* pXAcc)
1264 {
1265 if (pXAcc && oldFocus != pXAcc)
1266 {
1267 if(GetParentRole(pXAcc) == TOOL_BAR)
1268 {
1269 Reference< XAccessibleContext > pRContext(pXAcc->getAccessibleContext());
1270 if (pRContext.is())
1271 {
1272 if(pRContext->getAccessibleRole() == TOGGLE_BUTTON)
1273 {
1274 return true;
1275 }
1276 }
1277 }
1278 }
1279 return false;
1280 }
1281
GetRole(com::sun::star::accessibility::XAccessible * pXAcc)1282 short AccObjectWinManager::GetRole(com::sun::star::accessibility::XAccessible* pXAcc)
1283 {
1284 assert(pXAcc != NULL);
1285 Reference<com::sun::star::accessibility::XAccessibleContext> xContext(pXAcc->getAccessibleContext(),UNO_QUERY);
1286 if(xContext.is())
1287 {
1288 return xContext->getAccessibleRole();
1289 }
1290 return -1;
1291 }
1292
GetAccDocByHWND(long pWnd)1293 XAccessible* AccObjectWinManager::GetAccDocByHWND( long pWnd )
1294 {
1295 XHWNDToDocumentHash::iterator aIter;
1296 aIter = XHWNDDocList.find( pWnd );
1297 if ( aIter != XHWNDDocList.end() )
1298 {
1299 return aIter->second;
1300 }
1301
1302 return NULL;
1303 }
1304
GetAccDocByAccTopWin(XAccessible * pXAcc)1305 XAccessible* AccObjectWinManager::GetAccDocByAccTopWin( XAccessible* pXAcc )
1306 {
1307 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
1308 long pWnd = (long)( pAccObj->GetParentHWND() );
1309 return GetAccDocByHWND( pWnd );
1310 }
1311
IsTopWinAcc(com::sun::star::accessibility::XAccessible * pXAcc)1312 bool AccObjectWinManager::IsTopWinAcc( com::sun::star::accessibility::XAccessible* pXAcc )
1313 {
1314 bool bRet = false;
1315 AccObject* pAccObj = GetAccObjByXAcc( pXAcc );
1316 if ( pAccObj )
1317 {
1318 bRet = ( pAccObj->GetParentObj() == NULL );
1319 }
1320 return bRet;
1321 }