xref: /trunk/main/sw/source/core/access/accmap.cxx (revision 440e7076)
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_sw.hxx"
26 
27 
28 #include <vos/ref.hxx>
29 #include <cppuhelper/weakref.hxx>
30 #include <vcl/window.hxx>
31 #include <svx/svdmodel.hxx>
32 #include <svx/unomod.hxx>
33 #include <tools/debug.hxx>
34 
35 #include <map>
36 #include <list>
37 #include <vector>
38 #include <accmap.hxx>
39 #include <acccontext.hxx>
40 #include <accdoc.hxx>
41 #include <accpreview.hxx>
42 #include <accpage.hxx>
43 #include <accpara.hxx>
44 #include <accheaderfooter.hxx>
45 #include <accfootnote.hxx>
46 #include <acctextframe.hxx>
47 #include <accgraphic.hxx>
48 #include <accembedded.hxx>
49 #include <acccell.hxx>
50 #include <acctable.hxx>
51 #include <fesh.hxx>
52 #include <rootfrm.hxx>
53 #include <txtfrm.hxx>
54 #include <hffrm.hxx>
55 #include <ftnfrm.hxx>
56 #include <cellfrm.hxx>
57 #include <tabfrm.hxx>
58 #include <pagefrm.hxx>
59 #include <flyfrm.hxx>
60 #include <ndtyp.hxx>
61 #include <IDocumentDrawModelAccess.hxx>
62 #include <svx/ShapeTypeHandler.hxx>
63 #include <vcl/svapp.hxx>
64 //IAccessibility2 Implementation 2009-----
65 #ifndef _SVX_ACCESSIBILITY_SHAPE_TYPE_HANDLER_HXX
66 #include <svx/ShapeTypeHandler.hxx>
67 #endif
68 #ifndef _SVX_ACCESSIBILITY_SVX_SHAPE_TYPES_HXX
69 #include <svx/SvxShapeTypes.hxx>
70 #endif
71 #ifndef _SVDPAGE_HXX
72 #include <svx/svdpage.hxx>
73 #endif
74 #include <com/sun/star/accessibility/AccessibleRelationType.hpp>
75 #include <com/sun/star/accessibility/AccessibleEventId.hpp>
76 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
77 #include <com/sun/star/accessibility/AccessibleRole.hpp>
78 #include <cppuhelper/implbase1.hxx>
79 #include <pagepreviewlayout.hxx>
80 #include <dcontact.hxx>
81 #include <svx/unoapi.hxx>
82 #include <svx/svdmark.hxx>
83 #include <doc.hxx>
84 #include <pam.hxx>
85 #include <ndtxt.hxx>
86 #include <dflyobj.hxx>
87 #include <prevwpage.hxx>
88 #include <switerator.hxx>
89 
90 using namespace ::com::sun::star;
91 using namespace ::com::sun::star::accessibility;
92 using ::rtl::OUString;
93 using namespace ::sw::access;
94 
95 struct SwFrmFunc
96 {
97 	sal_Bool operator()( const SwFrm * p1,
98 				    	 const SwFrm * p2) const
99 	{
100 		return p1 < p2;
101 	}
102 };
103 
104 typedef ::std::map < const SwFrm *, uno::WeakReference < XAccessible >, SwFrmFunc > _SwAccessibleContextMap_Impl;
105 
106 class SwAccessibleContextMap_Impl: public _SwAccessibleContextMap_Impl
107 {
108 public:
109 
110 #ifdef DBG_UTIL
111 	sal_Bool mbLocked;
112 #endif
113 
114 	SwAccessibleContextMap_Impl()
115 #ifdef DBG_UTIL
116 		: mbLocked( sal_False )
117 #endif
118 	{}
119 
120 };
121 
122 //------------------------------------------------------------------------------
123 class SwDrawModellListener_Impl : public SfxListener,
124 	public ::cppu::WeakImplHelper1< document::XEventBroadcaster >
125 {
126 	mutable ::osl::Mutex maListenerMutex;
127 	::cppu::OInterfaceContainerHelper maEventListeners;
128 	SdrModel *mpDrawModel;
129 protected:
130 	virtual ~SwDrawModellListener_Impl();
131 public:
132 
133 	SwDrawModellListener_Impl( SdrModel *pDrawModel );
134 
135 
136     virtual void SAL_CALL addEventListener( const uno::Reference< document::XEventListener >& xListener ) throw (uno::RuntimeException);
137     virtual void SAL_CALL removeEventListener( const uno::Reference< document::XEventListener >& xListener ) throw (uno::RuntimeException);
138 
139 	virtual void		Notify( SfxBroadcaster& rBC, const SfxHint& rHint );
140 	void Dispose();
141 };
142 
143 SwDrawModellListener_Impl::SwDrawModellListener_Impl( SdrModel *pDrawModel ) :
144 	maEventListeners( maListenerMutex ),
145 	mpDrawModel( pDrawModel )
146 {
147 	StartListening( *mpDrawModel );
148 }
149 
150 SwDrawModellListener_Impl::~SwDrawModellListener_Impl()
151 {
152 	EndListening( *mpDrawModel );
153 }
154 
155 void SAL_CALL SwDrawModellListener_Impl::addEventListener( const uno::Reference< document::XEventListener >& xListener ) throw (uno::RuntimeException)
156 {
157 	maEventListeners.addInterface( xListener );
158 }
159 
160 void SAL_CALL SwDrawModellListener_Impl::removeEventListener( const uno::Reference< document::XEventListener >& xListener ) throw (uno::RuntimeException)
161 {
162 	maEventListeners.removeInterface( xListener );
163 }
164 
165 void SwDrawModellListener_Impl::Notify( SfxBroadcaster& /*rBC*/,
166 		const SfxHint& rHint )
167 {
168 	// do not broadcast notifications for writer fly frames, because there
169 	// are no shapes that need to know about them.
170     // OD 01.07.2003 #110554# - correct condition in order not to broadcast
171     // notifications for writer fly frames.
172     // OD 01.07.2003 #110554# - do not broadcast notifications for plane
173     // <SdrObject>objects
174 	const SdrHint *pSdrHint = PTR_CAST( SdrHint, &rHint );
175     if ( !pSdrHint ||
176          ( pSdrHint->GetObject() &&
177            ( pSdrHint->GetObject()->ISA(SwFlyDrawObj) ||
178              pSdrHint->GetObject()->ISA(SwVirtFlyDrawObj) ||
179              IS_TYPE(SdrObject,pSdrHint->GetObject()) ) ) )
180     {
181         return;
182     }
183 
184 	ASSERT( mpDrawModel, "draw model listener is disposed" );
185 	if( !mpDrawModel )
186 		return;
187 
188 	document::EventObject aEvent;
189 	if( !SvxUnoDrawMSFactory::createEvent( mpDrawModel, pSdrHint, aEvent ) )
190 		return;
191 
192 	::cppu::OInterfaceIteratorHelper aIter( maEventListeners );
193 	while( aIter.hasMoreElements() )
194 	{
195 		uno::Reference < document::XEventListener > xListener( aIter.next(),
196 												uno::UNO_QUERY );
197 		try
198 		{
199 			xListener->notifyEvent( aEvent );
200 		}
201 		catch( uno::RuntimeException const & r )
202 		{
203             (void)r;
204 #if OSL_DEBUG_LEVEL > 1
205 			ByteString aError( "Runtime exception caught while notifying shape.:\n" );
206 			aError += ByteString( String( r.Message), RTL_TEXTENCODING_ASCII_US );
207 			DBG_ERROR( aError.GetBuffer() );
208 #endif
209 		}
210 	}
211 }
212 
213 void SwDrawModellListener_Impl::Dispose()
214 {
215 	mpDrawModel = 0;
216 }
217 
218 //------------------------------------------------------------------------------
219 struct SwShapeFunc
220 {
221 	sal_Bool operator()( const SdrObject * p1,
222 				    	 const SdrObject * p2) const
223 	{
224 		return p1 < p2;
225 	}
226 };
227 typedef ::std::map < const SdrObject *, uno::WeakReference < XAccessible >, SwShapeFunc > _SwAccessibleShapeMap_Impl;
228 typedef ::std::pair < const SdrObject *, ::vos::ORef < ::accessibility::AccessibleShape > > SwAccessibleObjShape_Impl;
229 
230 class SwAccessibleShapeMap_Impl: public _SwAccessibleShapeMap_Impl
231 
232 {
233 	::accessibility::AccessibleShapeTreeInfo maInfo;
234 
235 public:
236 
237 #ifdef DBG_UTIL
238 	sal_Bool mbLocked;
239 #endif
240 	SwAccessibleShapeMap_Impl( SwAccessibleMap *pMap )
241 #ifdef DBG_UTIL
242 		: mbLocked( sal_False )
243 #endif
244 	{
245 		maInfo.SetSdrView( pMap->GetShell()->GetDrawView() );
246 		maInfo.SetWindow( pMap->GetShell()->GetWin() );
247 		maInfo.SetViewForwarder( pMap );
248         // --> OD 2005-08-08 #i52858# - method name changed
249 		uno::Reference < document::XEventBroadcaster > xModelBroadcaster =
250 			new SwDrawModellListener_Impl(
251                     pMap->GetShell()->getIDocumentDrawModelAccess()->GetOrCreateDrawModel() );
252         // <--
253 		maInfo.SetControllerBroadcaster( xModelBroadcaster );
254 	}
255 
256 	~SwAccessibleShapeMap_Impl();
257 
258 	const ::accessibility::AccessibleShapeTreeInfo& GetInfo() const { return maInfo; }
259 
260 	SwAccessibleObjShape_Impl *Copy( size_t& rSize,
261 		const SwFEShell *pFESh = 0,
262 		SwAccessibleObjShape_Impl  **pSelShape = 0 ) const;
263 };
264 
265 SwAccessibleShapeMap_Impl::~SwAccessibleShapeMap_Impl()
266 {
267 	uno::Reference < document::XEventBroadcaster > xBrd( maInfo.GetControllerBroadcaster() );
268 	if( xBrd.is() )
269 		static_cast < SwDrawModellListener_Impl * >( xBrd.get() )->Dispose();
270 }
271 
272 SwAccessibleObjShape_Impl
273 	*SwAccessibleShapeMap_Impl::Copy(
274 			size_t& rSize, const SwFEShell *pFESh,
275 			SwAccessibleObjShape_Impl **pSelStart ) const
276 {
277 	SwAccessibleObjShape_Impl *pShapes = 0;
278 	SwAccessibleObjShape_Impl *pSelShape = 0;
279 
280 	sal_uInt16 nSelShapes = pFESh ? pFESh->IsObjSelected() : 0;
281 	rSize = size();
282 
283 	if( rSize > 0 )
284 	{
285 		pShapes =
286 			new SwAccessibleObjShape_Impl[rSize];
287 
288 		const_iterator aIter = begin();
289 		const_iterator aEndIter = end();
290 
291 		SwAccessibleObjShape_Impl *pShape = pShapes;
292 		pSelShape = &(pShapes[rSize]);
293 		while( aIter != aEndIter )
294 		{
295 			const SdrObject *pObj = (*aIter).first;
296 			uno::Reference < XAccessible > xAcc( (*aIter).second );
297 			//IAccessibility2 Implementation 2009-----
298 			if( nSelShapes && pFESh &&pFESh->IsObjSelected( *pObj ) )
299 			//-----IAccessibility2 Implementation 2009
300 			{
301 				// selected objects are inserted from the back
302 				--pSelShape;
303 				pSelShape->first = pObj;
304 				pSelShape->second =
305 					static_cast < ::accessibility::AccessibleShape* >(
306 													xAcc.get() );
307 				--nSelShapes;
308 			}
309 			else
310 			{
311 				pShape->first = pObj;
312 				pShape->second =
313 					static_cast < ::accessibility::AccessibleShape* >(
314 													xAcc.get() );
315 				++pShape;
316 			}
317 			++aIter;
318 		}
319 		ASSERT( pSelShape == pShape, "copying shapes went wrong!" );
320 	}
321 
322 	if( pSelStart )
323 		*pSelStart = pSelShape;
324 
325 	return pShapes;
326 }
327 
328 //------------------------------------------------------------------------------
329 struct SwAccessibleEvent_Impl
330 {
331 public:
332     enum EventType { CARET_OR_STATES,
333                      INVALID_CONTENT,
334                      POS_CHANGED,
335                      CHILD_POS_CHANGED,
336                      SHAPE_SELECTION,
337                      DISPOSE,
338                      INVALID_ATTR };
339 
340 private:
341 	SwRect		maOldBox;				// the old bounds for CHILD_POS_CHANGED
342 										// and POS_CHANGED
343 	uno::WeakReference < XAccessible > mxAcc;	// The object that fires the event
344     SwAccessibleChild   maFrmOrObj;             // the child for CHILD_POS_CHANGED and
345 										// the same as xAcc for any other
346 										// event type
347 	EventType 	meType;					// The event type
348     // --> OD 2005-12-12 #i27301# - use new type definition for <mnStates>
349     tAccessibleStates mnStates;         // check states or update caret pos
350     // <--
351 
352 	SwAccessibleEvent_Impl& operator==( const SwAccessibleEvent_Impl& );
353 
354 public:
355 	//IAccessibility2 Implementation 2009-----
356 	const SwFrm* mpParentFrm;	// The object that fires the event
357 	sal_Bool IsNoXaccParentFrm() const
358 	{
359 		return CHILD_POS_CHANGED == meType && mpParentFrm != 0;
360 	}
361 	uno::WeakReference < XAccessible > GetxAcc() const { return mxAcc;}
362 	//-----IAccessibility2 Implementation 2009
363 public:
364     SwAccessibleEvent_Impl( EventType eT,
365                             SwAccessibleContext *pA,
366                             const SwAccessibleChild& rFrmOrObj )
367         : mxAcc( pA ),
368           maFrmOrObj( rFrmOrObj ),
369           meType( eT ),
370           mnStates( 0 ),
371           mpParentFrm( 0 )
372 	{}
373 
374     SwAccessibleEvent_Impl( EventType eT,
375                             const SwAccessibleChild& rFrmOrObj )
376         : maFrmOrObj( rFrmOrObj ),
377           meType( eT ),
378           mnStates( 0 ),
379           mpParentFrm( 0 )
380 	{
381 		ASSERT( SwAccessibleEvent_Impl::DISPOSE == meType,
382 				"wrong event constructor, DISPOSE only" );
383 	}
384 
385     SwAccessibleEvent_Impl( EventType eT )
386         : meType( eT ),
387           mnStates( 0 ),
388           mpParentFrm( 0 )
389 	{
390         ASSERT( SwAccessibleEvent_Impl::SHAPE_SELECTION == meType,
391 				"wrong event constructor, SHAPE_SELECTION only" );
392 	}
393 
394     SwAccessibleEvent_Impl( EventType eT,
395                             SwAccessibleContext *pA,
396                             const SwAccessibleChild& rFrmOrObj,
397                             const SwRect& rR )
398         : maOldBox( rR ),
399           mxAcc( pA ),
400           maFrmOrObj( rFrmOrObj ),
401           meType( eT ),
402           mnStates( 0 ),
403           mpParentFrm( 0 )
404 	{
405 		ASSERT( SwAccessibleEvent_Impl::CHILD_POS_CHANGED == meType ||
406 				SwAccessibleEvent_Impl::POS_CHANGED == meType,
407 				"wrong event constructor, (CHILD_)POS_CHANGED only" );
408 	}
409 
410     // --> OD 2005-12-12 #i27301# - use new type definition for parameter <_nStates>
411     SwAccessibleEvent_Impl( EventType eT,
412                             SwAccessibleContext *pA,
413                             const SwAccessibleChild& rFrmOrObj,
414                             const tAccessibleStates _nStates )
415         : mxAcc( pA ),
416           maFrmOrObj( rFrmOrObj ),
417           meType( eT ),
418           mnStates( _nStates ),
419           mpParentFrm( 0 )
420 	{
421 		ASSERT( SwAccessibleEvent_Impl::CARET_OR_STATES == meType,
422 				"wrong event constructor, CARET_OR_STATES only" );
423 	}
424 
425 	//IAccessibility2 Implementation 2009-----
426 	SwAccessibleEvent_Impl( EventType eT,
427                                 const SwFrm *pParentFrm,
428 				const SwAccessibleChild& rFrmOrObj,
429                                 const SwRect& rR ) :
430 		maOldBox( rR ),
431                 maFrmOrObj( rFrmOrObj ),
432                 meType( eT ),
433 		mnStates( 0 ),
434                 mpParentFrm( pParentFrm )
435 	{
436 		OSL_ENSURE( SwAccessibleEvent_Impl::CHILD_POS_CHANGED == meType,
437 			"wrong event constructor, CHILD_POS_CHANGED only" );
438 	}
439 	//-----IAccessibility2 Implementation 2009
440     // <SetType(..)> only used in method <SwAccessibleMap::AppendEvent(..)>
441     inline void SetType( EventType eT )
442     {
443         meType = eT;
444     }
445     inline EventType GetType() const
446     {
447         return meType;
448     }
449 
450     inline ::vos::ORef < SwAccessibleContext > GetContext() const
451     {
452         uno::Reference < XAccessible > xTmp( mxAcc );
453         ::vos::ORef < SwAccessibleContext > xAccImpl(
454                             static_cast<SwAccessibleContext*>( xTmp.get() ) );
455 
456         return xAccImpl;
457     }
458 
459     inline const SwRect& GetOldBox() const
460     {
461         return maOldBox;
462     }
463     // <SetOldBox(..)> only used in method <SwAccessibleMap::AppendEvent(..)>
464     inline void SetOldBox( const SwRect& rOldBox )
465     {
466         maOldBox = rOldBox;
467     }
468 
469     inline const SwAccessibleChild& GetFrmOrObj() const
470     {
471         return maFrmOrObj;
472     }
473 
474     // <SetStates(..)> only used in method <SwAccessibleMap::AppendEvent(..)>
475     // --> OD 2005-12-12 #i27301# - use new type definition for parameter <_nStates>
476     inline void SetStates( tAccessibleStates _nStates )
477     {
478         mnStates |= _nStates;
479     }
480     // <--
481 
482     inline sal_Bool IsUpdateCursorPos() const
483     {
484         return (mnStates & ACC_STATE_CARET) != 0;
485     }
486     inline sal_Bool IsInvalidateStates() const
487     {
488         return (mnStates & ACC_STATE_MASK) != 0;
489     }
490     inline sal_Bool IsInvalidateRelation() const
491     {
492         return (mnStates & ACC_STATE_RELATION_MASK) != 0;
493     }
494     // --> OD 2005-12-12 #i27301# - new event TEXT_SELECTION_CHANGED
495     inline sal_Bool IsInvalidateTextSelection() const
496     {
497         return ( mnStates & ACC_STATE_TEXT_SELECTION_CHANGED ) != 0;
498     }
499     // <--
500     // --> OD 2009-01-07 #i88069# - new event TEXT_ATTRIBUTE_CHANGED
501     inline sal_Bool IsInvalidateTextAttrs() const
502     {
503         return ( mnStates & ACC_STATE_TEXT_ATTRIBUTE_CHANGED ) != 0;
504     }
505     // <--
506     // --> OD 2005-12-12 #i27301# - use new type definition <tAccessibleStates>
507     // for return value
508     inline tAccessibleStates GetStates() const
509     {
510         return mnStates & ACC_STATE_MASK;
511     }
512     // <--
513     // --> OD 2005-12-12 #i27301# - use new type definition <tAccessibleStates>
514     // for return value
515     inline tAccessibleStates GetAllStates() const
516     {
517         return mnStates;
518     }
519     // <--
520 };
521 
522 //------------------------------------------------------------------------------
523 typedef ::std::list < SwAccessibleEvent_Impl > _SwAccessibleEventList_Impl;
524 
525 class SwAccessibleEventList_Impl: public _SwAccessibleEventList_Impl
526 {
527 	sal_Bool mbFiring;
528 
529 public:
530 
531     SwAccessibleEventList_Impl()
532         : mbFiring( sal_False )
533     {}
534 
535     inline void SetFiring()
536     {
537         mbFiring = sal_True;
538     }
539     inline sal_Bool IsFiring() const
540     {
541         return mbFiring;
542     }
543 	//IAccessibility2 Implementation 2009-----
544 	struct XAccisNULL
545 	{
546 		bool operator()(const SwAccessibleEvent_Impl& e)
547 		{
548 			return e.IsNoXaccParentFrm();
549 		}
550 	};
551 	void MoveInvalidXAccToEnd();
552 	//-----IAccessibility2 Implementation 2009
553 };
554 
555 //IAccessibility2 Implementation 2009-----
556 void SwAccessibleEventList_Impl::MoveInvalidXAccToEnd()
557 {
558 	int nSize = size();
559 	if (nSize < 2 )
560 	{
561 		return;
562 	}
563 	SwAccessibleEventList_Impl lstEvent;
564 	iterator li = begin();
565 	for ( ;li != end();)
566 	{
567 		SwAccessibleEvent_Impl e = *li;
568 		if (e.IsNoXaccParentFrm())
569 		{
570 			iterator liNext = li;
571 			++liNext;
572 			erase(li);
573 			li = liNext;
574 			lstEvent.insert(lstEvent.end(),e);
575 		}
576 		else
577 			++li;
578 	}
579 	OSL_ENSURE(size() + lstEvent.size() == nSize ,"");
580 	insert(end(),lstEvent.begin(),lstEvent.end());
581 	OSL_ENSURE(size() == nSize ,"");
582 }
583 //-----IAccessibility2 Implementation 2009
584 //------------------------------------------------------------------------------
585 // The shape list is filled if an accessible shape is destroyed. It
586 // simply keeps a reference to the accessible shape's XShape. These
587 // references are destroyed within the EndAction when firing events,
588 // There are twp reason for this. First of all, a new accessible shape
589 // for the XShape might be created soon. It's then cheaper if the XShape
590 // still exists. The other reason are situations where an accessible shape
591 // is destroyed within an SwFrmFmt::Modify. In this case, destryoing
592 // the XShape at the same time (indirectly by destroying the accessible
593 // shape) leads to an assert, because a client of the Modify is destroyed
594 // within a Modify call.
595 
596 typedef ::std::list < uno::Reference < drawing::XShape > > _SwShapeList_Impl;
597 
598 class SwShapeList_Impl: public _SwShapeList_Impl
599 {
600 public:
601 
602 	SwShapeList_Impl() {}
603 };
604 
605 
606 //------------------------------------------------------------------------------
607 struct SwAccessibleChildFunc
608 {
609     sal_Bool operator()( const SwAccessibleChild& r1,
610                          const SwAccessibleChild& r2 ) const
611 	{
612 		const void *p1 = r1.GetSwFrm()
613                          ? static_cast < const void * >( r1.GetSwFrm())
614                          : ( r1.GetDrawObject()
615                              ? static_cast < const void * >( r1.GetDrawObject() )
616                              : static_cast < const void * >( r1.GetWindow() ) );
617 		const void *p2 = r2.GetSwFrm()
618                          ? static_cast < const void * >( r2.GetSwFrm())
619                          : ( r2.GetDrawObject()
620                              ? static_cast < const void * >( r2.GetDrawObject() )
621                              : static_cast < const void * >( r2.GetWindow() ) );
622 		return p1 < p2;
623 	}
624 };
625 typedef ::std::map < SwAccessibleChild, SwAccessibleEventList_Impl::iterator,
626                      SwAccessibleChildFunc > _SwAccessibleEventMap_Impl;
627 
628 class SwAccessibleEventMap_Impl: public _SwAccessibleEventMap_Impl
629 {
630 };
631 
632 //------------------------------------------------------------------------------
633 // --> OD 2005-12-13 #i27301# - map containing the accessible paragraph, which
634 // have a selection. Needed to keep this information to submit corresponding
635 // TEXT_SELECTION_CHANGED events.
636 struct SwAccessibleParaSelection
637 {
638     xub_StrLen nStartOfSelection;
639     xub_StrLen nEndOfSelection;
640 
641     SwAccessibleParaSelection( const xub_StrLen _nStartOfSelection,
642                                const xub_StrLen _nEndOfSelection )
643         : nStartOfSelection( _nStartOfSelection ),
644           nEndOfSelection( _nEndOfSelection )
645     {}
646 };
647 
648 struct SwXAccWeakRefComp
649 {
650     sal_Bool operator()( const uno::WeakReference<XAccessible>& _rXAccWeakRef1,
651                          const uno::WeakReference<XAccessible>& _rXAccWeakRef2 ) const
652     {
653         return _rXAccWeakRef1.get() < _rXAccWeakRef2.get();
654     }
655 };
656 
657 typedef ::std::map< uno::WeakReference < XAccessible >,
658                     SwAccessibleParaSelection,
659                     SwXAccWeakRefComp > _SwAccessibleSelectedParas_Impl;
660 
661 class SwAccessibleSelectedParas_Impl: public _SwAccessibleSelectedParas_Impl
662 {};
663 // <--
664 
665 // helper class that stores preview data
666 class SwAccPreviewData
667 {
668     typedef std::vector<Rectangle> Rectangles;
669     Rectangles maPreviewRects;
670     Rectangles maLogicRects;
671 
672     SwRect maVisArea;
673     Fraction maScale;
674 
675     const SwPageFrm *mpSelPage;
676 
677     /** adjust logic page retangle to its visible part
678 
679         OD 17.01.2003 #103492#
680 
681         @author OD
682 
683         @param _iorLogicPgSwRect
684         input/output parameter - reference to the logic page rectangle, which
685         has to be adjusted.
686 
687         @param _rPrevwPgSwRect
688         input parameter - constant reference to the corresponding preview page
689         rectangle; needed to determine the visible part of the logic page rectangle.
690 
691         @param _rPrevwWinSize
692         input paramter - constant reference to the preview window size in TWIP;
693         needed to determine the visible part of the logic page rectangle
694     */
695     void AdjustLogicPgRectToVisibleArea( SwRect&         _iorLogicPgSwRect,
696                                          const SwRect&   _rPrevwPgSwRect,
697                                          const Size&     _rPrevwWinSize );
698 
699 public:
700     SwAccPreviewData();
701     ~SwAccPreviewData();
702 
703     // OD 14.01.2003 #103492# - complete re-factoring of method due to new
704     // page/print preview functionality.
705     void Update( const SwAccessibleMap& rAccMap,
706                  const std::vector<PrevwPage*>& _rPrevwPages,
707                  const Fraction&  _rScale,
708                  const SwPageFrm* _pSelectedPageFrm,
709                  const Size&      _rPrevwWinSize );
710 
711     // OD 14.01.2003 #103492# - complete re-factoring of method due to new
712     // page/print preview functionality.
713     void InvalidateSelection( const SwPageFrm* _pSelectedPageFrm );
714 
715     const SwRect& GetVisArea() const;
716 
717     MapMode GetMapModeForPreview( ) const;
718 
719     /** Adjust the MapMode so that the preview page appears at the
720      * proper position. rPoint identifies the page for which the
721      * MapMode should be adjusted. If bFromPreview is true, rPoint is
722      * a preview coordinate; else it's a document coordinate. */
723     // OD 17.01.2003 #103492# - delete unused 3rd parameter.
724     void AdjustMapMode( MapMode& rMapMode,
725                         const Point& rPoint ) const;
726 
727     inline const SwPageFrm *GetSelPage() const { return mpSelPage; }
728 
729     void DisposePage(const SwPageFrm *pPageFrm );
730 };
731 
732 SwAccPreviewData::SwAccPreviewData() :
733     mpSelPage( 0 )
734 {
735 }
736 
737 SwAccPreviewData::~SwAccPreviewData()
738 {
739 }
740 
741 // OD 13.01.2003 #103492# - complete re-factoring of method due to new page/print
742 // preview functionality.
743 void SwAccPreviewData::Update( const SwAccessibleMap& rAccMap,
744                                const std::vector<PrevwPage*>& _rPrevwPages,
745                                const Fraction&  _rScale,
746                                const SwPageFrm* _pSelectedPageFrm,
747                                const Size&      _rPrevwWinSize )
748 {
749     // store preview scaling, maximal preview page size and selected page
750     maScale = _rScale;
751     mpSelPage = _pSelectedPageFrm;
752 
753     // prepare loop on preview pages
754     maPreviewRects.clear();
755     maLogicRects.clear();
756     SwAccessibleChild aPage;
757     maVisArea.Clear();
758 
759     // loop on preview pages to calculate <maPreviewRects>, <maLogicRects> and
760     // <maVisArea>
761     for ( std::vector<PrevwPage*>::const_iterator aPageIter = _rPrevwPages.begin();
762           aPageIter != _rPrevwPages.end();
763           ++aPageIter )
764     {
765         aPage = (*aPageIter)->pPage;
766 
767         // add preview page rectangle to <maPreviewRects>
768         Rectangle aPrevwPgRect( (*aPageIter)->aPrevwWinPos, (*aPageIter)->aPageSize );
769         maPreviewRects.push_back( aPrevwPgRect );
770 
771         // add logic page rectangle to <maLogicRects>
772         SwRect aLogicPgSwRect( aPage.GetBox( rAccMap ) );
773         Rectangle aLogicPgRect( aLogicPgSwRect.SVRect() );
774         maLogicRects.push_back( aLogicPgRect );
775         // union visible area with visible part of logic page rectangle
776         if ( (*aPageIter)->bVisible )
777         {
778             if ( !(*aPageIter)->pPage->IsEmptyPage() )
779             {
780                 AdjustLogicPgRectToVisibleArea( aLogicPgSwRect,
781                                                 SwRect( aPrevwPgRect ),
782                                                 _rPrevwWinSize );
783             }
784             if ( maVisArea.IsEmpty() )
785                 maVisArea = aLogicPgSwRect;
786             else
787                 maVisArea.Union( aLogicPgSwRect );
788         }
789     }
790 }
791 
792 // OD 16.01.2003 #103492# - complete re-factoring of method due to new page/print
793 // preview functionality.
794 void SwAccPreviewData::InvalidateSelection( const SwPageFrm* _pSelectedPageFrm )
795 {
796     mpSelPage = _pSelectedPageFrm;
797     ASSERT( mpSelPage, "selected page not found" );
798 }
799 
800 struct ContainsPredicate
801 {
802     const Point& mrPoint;
803     ContainsPredicate( const Point& rPoint ) : mrPoint(rPoint) {}
804     bool operator() ( const Rectangle& rRect ) const
805     {
806         return rRect.IsInside( mrPoint ) ? true : false;
807     }
808 };
809 
810 const SwRect& SwAccPreviewData::GetVisArea() const
811 {
812     return maVisArea;
813 }
814 
815 void SwAccPreviewData::AdjustMapMode( MapMode& rMapMode,
816                                       const Point& rPoint ) const
817 {
818     // adjust scale
819     rMapMode.SetScaleX( maScale );
820     rMapMode.SetScaleY( maScale );
821 
822     // find proper rectangle
823     Rectangles::const_iterator aBegin = maLogicRects.begin();
824     Rectangles::const_iterator aEnd = maLogicRects.end();
825     Rectangles::const_iterator aFound = ::std::find_if( aBegin, aEnd,
826                                                  ContainsPredicate( rPoint ) );
827 
828     if( aFound != aEnd )
829     {
830         // found! set new origin
831         Point aPoint = (maPreviewRects.begin() + (aFound - aBegin))->TopLeft();
832         aPoint -= (maLogicRects.begin() + (aFound-aBegin))->TopLeft();
833         rMapMode.SetOrigin( aPoint );
834     }
835     // else: don't adjust MapMode
836 }
837 
838 void SwAccPreviewData::DisposePage(const SwPageFrm *pPageFrm )
839 {
840     if( mpSelPage == pPageFrm )
841         mpSelPage = 0;
842 }
843 
844 /** adjust logic page retangle to its visible part
845 
846     OD 17.01.2003 #103492#
847 
848     @author OD
849 */
850 void SwAccPreviewData::AdjustLogicPgRectToVisibleArea(
851                             SwRect&         _iorLogicPgSwRect,
852                             const SwRect&   _rPrevwPgSwRect,
853                             const Size&     _rPrevwWinSize )
854 {
855     // determine preview window rectangle
856     const SwRect aPrevwWinSwRect( Point( 0, 0 ), _rPrevwWinSize );
857     // calculate visible preview page rectangle
858     SwRect aVisPrevwPgSwRect( _rPrevwPgSwRect );
859     aVisPrevwPgSwRect.Intersection( aPrevwWinSwRect );
860     // adjust logic page rectangle
861     SwTwips nTmpDiff;
862     // left
863     nTmpDiff = aVisPrevwPgSwRect.Left() - _rPrevwPgSwRect.Left();
864     if ( nTmpDiff > 0 )
865         _iorLogicPgSwRect.Left( _iorLogicPgSwRect.Left() + nTmpDiff );
866     // top
867     nTmpDiff = aVisPrevwPgSwRect.Top() - _rPrevwPgSwRect.Top();
868     if ( nTmpDiff > 0 )
869         _iorLogicPgSwRect.Top( _iorLogicPgSwRect.Top() + nTmpDiff );
870     // right
871     nTmpDiff = _rPrevwPgSwRect.Right() - aVisPrevwPgSwRect.Right();
872     if ( nTmpDiff > 0 )
873         _iorLogicPgSwRect.Right( _iorLogicPgSwRect.Right() - nTmpDiff );
874     // bottom
875     nTmpDiff = _rPrevwPgSwRect.Bottom() - aVisPrevwPgSwRect.Bottom();
876     if ( nTmpDiff > 0 )
877         _iorLogicPgSwRect.Bottom( _iorLogicPgSwRect.Bottom() - nTmpDiff );
878 }
879 
880 //------------------------------------------------------------------------------
881 static sal_Bool AreInSameTable( const uno::Reference< XAccessible >& rAcc,
882 					  		    const SwFrm *pFrm )
883 {
884 	sal_Bool bRet = sal_False;
885 
886 	if( pFrm && pFrm->IsCellFrm() && rAcc.is() )
887 	{
888 		// Is it in the same table? We check that
889 		// by comparing the last table frame in the
890 		// follow chain, because that's cheaper than
891 		// searching the first one.
892 		SwAccessibleContext *pAccImpl =
893 			static_cast< SwAccessibleContext *>( rAcc.get() );
894 		if( pAccImpl->GetFrm()->IsCellFrm() )
895 		{
896 			const SwTabFrm *pTabFrm1 = pAccImpl->GetFrm()->FindTabFrm();
897 			while( pTabFrm1->GetFollow() )
898 				   pTabFrm1 = pTabFrm1->GetFollow();
899 
900 			const SwTabFrm *pTabFrm2 = pFrm->FindTabFrm();
901 			while( pTabFrm2->GetFollow() )
902 				   pTabFrm2 = pTabFrm2->GetFollow();
903 
904 			bRet = (pTabFrm1 == pTabFrm2);
905 		}
906 	}
907 
908 	return bRet;
909 }
910 
911 void SwAccessibleMap::FireEvent( const SwAccessibleEvent_Impl& rEvent )
912 {
913 	::vos::ORef < SwAccessibleContext > xAccImpl( rEvent.GetContext() );
914 	//IAccessibility2 Implementation 2009-----
915 	if (!xAccImpl.isValid() && rEvent.mpParentFrm != 0 )
916 	{
917 		SwAccessibleContextMap_Impl::iterator aIter =
918 			mpFrmMap->find( rEvent.mpParentFrm );
919 		if( aIter != mpFrmMap->end() )
920 		{
921 			uno::Reference < XAccessible > xAcc( (*aIter).second );
922 			if (xAcc.is())
923 			{
924 				uno::Reference < XAccessibleContext >  xContext(xAcc,uno::UNO_QUERY);
925 				if (xContext.is() && xContext->getAccessibleRole() == AccessibleRole::PARAGRAPH)
926 				{
927 					xAccImpl = static_cast< SwAccessibleContext *>( xAcc.get() );
928 				}
929 			}
930 		}
931 	}
932 	//-----IAccessibility2 Implementation 2009
933 	if( SwAccessibleEvent_Impl::SHAPE_SELECTION == rEvent.GetType() )
934 	{
935 		DoInvalidateShapeSelection();
936 	}
937 	else if( xAccImpl.isValid() && xAccImpl->GetFrm() )
938 	{
939         // --> OD 2009-01-07 #i88069#
940         if ( rEvent.GetType() != SwAccessibleEvent_Impl::DISPOSE &&
941              rEvent.IsInvalidateTextAttrs() )
942         {
943             xAccImpl->InvalidateAttr();
944         }
945         // <--
946 		switch( rEvent.GetType() )
947 		{
948 		case SwAccessibleEvent_Impl::INVALID_CONTENT:
949 			xAccImpl->InvalidateContent();
950 			break;
951 		case SwAccessibleEvent_Impl::POS_CHANGED:
952 			xAccImpl->InvalidatePosOrSize( rEvent.GetOldBox() );
953 			break;
954 		case SwAccessibleEvent_Impl::CHILD_POS_CHANGED:
955 			xAccImpl->InvalidateChildPosOrSize( rEvent.GetFrmOrObj(),
956 									   rEvent.GetOldBox() );
957 			break;
958 		case SwAccessibleEvent_Impl::DISPOSE:
959 			ASSERT( xAccImpl.isValid(),
960 					"dispose event has been stored" );
961 			break;
962         // --> OD 2009-01-06 #i88069#
963         case SwAccessibleEvent_Impl::INVALID_ATTR:
964             // nothing to do here - handled above
965             break;
966         // <--
967 		default:
968 			break;
969 		}
970 		if( SwAccessibleEvent_Impl::DISPOSE != rEvent.GetType() )
971 		{
972 			if( rEvent.IsUpdateCursorPos() )
973 				xAccImpl->InvalidateCursorPos();
974 			if( rEvent.IsInvalidateStates() )
975 				xAccImpl->InvalidateStates( rEvent.GetStates() );
976             if( rEvent.IsInvalidateRelation() )
977             {
978                 // --> OD 2005-12-01 #i27138#
979                 // both events CONTENT_FLOWS_FROM_RELATION_CHANGED and
980                 // CONTENT_FLOWS_TO_RELATION_CHANGED are possible
981                 if ( rEvent.GetAllStates() & ACC_STATE_RELATION_FROM )
982                 {
983                     xAccImpl->InvalidateRelation(
984                         AccessibleEventId::CONTENT_FLOWS_FROM_RELATION_CHANGED );
985                 }
986                 if ( rEvent.GetAllStates() & ACC_STATE_RELATION_TO )
987                 {
988                     xAccImpl->InvalidateRelation(
989                         AccessibleEventId::CONTENT_FLOWS_TO_RELATION_CHANGED );
990                 }
991                 // <--
992             }
993             // --> OD 2005-12-12 #i27301# - submit event TEXT_SELECTION_CHANGED
994             if ( rEvent.IsInvalidateTextSelection() )
995             {
996                 xAccImpl->InvalidateTextSelection();
997             }
998             // <--
999 		}
1000 	}
1001 }
1002 
1003 void SwAccessibleMap::AppendEvent( const SwAccessibleEvent_Impl& rEvent )
1004 {
1005 	vos::OGuard aGuard( maEventMutex );
1006 
1007 	if( !mpEvents )
1008 		mpEvents = new SwAccessibleEventList_Impl;
1009 	if( !mpEventMap )
1010 		mpEventMap = new SwAccessibleEventMap_Impl;
1011 
1012 	if( mpEvents->IsFiring() )
1013 	{
1014 		// While events are fired new ones are generated. They have to be fired
1015 		// now. This does not work for DISPOSE events!
1016 		ASSERT( rEvent.GetType() != SwAccessibleEvent_Impl::DISPOSE,
1017 				"dispose event while firing events" );
1018 		FireEvent( rEvent );
1019 	}
1020 	else
1021 	{
1022 
1023 		SwAccessibleEventMap_Impl::iterator aIter =
1024                                         mpEventMap->find( rEvent.GetFrmOrObj() );
1025 		if( aIter != mpEventMap->end() )
1026 		{
1027 			SwAccessibleEvent_Impl aEvent( *(*aIter).second );
1028 			ASSERT( aEvent.GetType() != SwAccessibleEvent_Impl::DISPOSE,
1029 					"dispose events should not be stored" );
1030 			sal_Bool bAppendEvent = sal_True;
1031 			switch( rEvent.GetType() )
1032 			{
1033 			case SwAccessibleEvent_Impl::CARET_OR_STATES:
1034 				// A CARET_OR_STATES event is added to any other
1035 				// event only. It is broadcasted after any other event, so the
1036 				// event should be put to the back.
1037                 ASSERT( aEvent.GetType() != SwAccessibleEvent_Impl::CHILD_POS_CHANGED,
1038 						"invalid event combination" );
1039 				aEvent.SetStates( rEvent.GetAllStates() );
1040 				break;
1041 			case SwAccessibleEvent_Impl::INVALID_CONTENT:
1042 				// An INVALID_CONTENT event overwrites a CARET_OR_STATES
1043 				// event (but keeps its flags) and it is contained in a
1044 				// POS_CHANGED event.
1045 				// Therefor, the event's type has to be adapted and the event
1046 				// has to be put at the end.
1047                 ASSERT( aEvent.GetType() != SwAccessibleEvent_Impl::CHILD_POS_CHANGED,
1048 						"invalid event combination" );
1049                 if( aEvent.GetType() == SwAccessibleEvent_Impl::CARET_OR_STATES )
1050 					aEvent.SetType( SwAccessibleEvent_Impl::INVALID_CONTENT );
1051 				break;
1052 			case SwAccessibleEvent_Impl::POS_CHANGED:
1053 				// A pos changed event overwrites CARET_STATES (keeping its
1054 				// flags) as well as INVALID_CONTENT. The old box position
1055 				// has to be stored however if the old event is not a
1056 				// POS_CHANGED itself.
1057                 ASSERT( aEvent.GetType() != SwAccessibleEvent_Impl::CHILD_POS_CHANGED,
1058 						"invalid event combination" );
1059 				if( aEvent.GetType() != SwAccessibleEvent_Impl::POS_CHANGED )
1060 					aEvent.SetOldBox( rEvent.GetOldBox() );
1061 				aEvent.SetType( SwAccessibleEvent_Impl::POS_CHANGED );
1062 				break;
1063 			case SwAccessibleEvent_Impl::CHILD_POS_CHANGED:
1064 				// CHILD_POS_CHANGED events can only follow CHILD_POS_CHANGED
1065 				// events. The only action that needs to be done again is
1066 				// to put the old event to the back. The new one cannot be used,
1067 				// because we are interested in the old frame bounds.
1068                 ASSERT( aEvent.GetType() == SwAccessibleEvent_Impl::CHILD_POS_CHANGED,
1069 						"invalid event combination" );
1070 				break;
1071 			case SwAccessibleEvent_Impl::SHAPE_SELECTION:
1072                 ASSERT( aEvent.GetType() == SwAccessibleEvent_Impl::SHAPE_SELECTION,
1073 						"invalid event combination" );
1074 				break;
1075 			case SwAccessibleEvent_Impl::DISPOSE:
1076 				// DISPOSE events overwrite all others. They are not stored
1077 				// but executed immediatly to avoid broadcasting of
1078 				// defunctional objects. So what needs to be done here is to
1079 				// remove all events for the frame in question.
1080 				bAppendEvent = sal_False;
1081 				break;
1082             // --> OD 2009-01-06 #i88069#
1083             case SwAccessibleEvent_Impl::INVALID_ATTR:
1084                 ASSERT( aEvent.GetType() == SwAccessibleEvent_Impl::INVALID_ATTR,
1085                         "invalid event combination" );
1086                 break;
1087             // <--
1088 			}
1089 			if( bAppendEvent )
1090 			{
1091 				mpEvents->erase( (*aIter).second );
1092 				(*aIter).second = mpEvents->insert( mpEvents->end(), aEvent );
1093 			}
1094 			else
1095 			{
1096 				mpEvents->erase( (*aIter).second );
1097 				mpEventMap->erase( aIter );
1098 			}
1099 		}
1100 		else if( SwAccessibleEvent_Impl::DISPOSE != rEvent.GetType() )
1101 		{
1102 			SwAccessibleEventMap_Impl::value_type aEntry( rEvent.GetFrmOrObj(),
1103 					mpEvents->insert( mpEvents->end(), rEvent ) );
1104 			mpEventMap->insert( aEntry );
1105 		}
1106 	}
1107 }
1108 
1109 void SwAccessibleMap::InvalidateCursorPosition(
1110 		const uno::Reference< XAccessible >& rAcc )
1111 {
1112 	SwAccessibleContext *pAccImpl =
1113 		static_cast< SwAccessibleContext *>( rAcc.get() );
1114 	ASSERT( pAccImpl, "no caret context" );
1115 	ASSERT( pAccImpl->GetFrm(), "caret context is disposed" );
1116 	if( GetShell()->ActionPend() )
1117 	{
1118         SwAccessibleEvent_Impl aEvent( SwAccessibleEvent_Impl::CARET_OR_STATES,
1119                                        pAccImpl,
1120                                        SwAccessibleChild(pAccImpl->GetFrm()),
1121                                        ACC_STATE_CARET );
1122 		AppendEvent( aEvent );
1123 	}
1124 	else
1125 	{
1126 		FireEvents();
1127 		// While firing events the current frame might have
1128 		// been disposed because it moved out of the vis area.
1129 		// Setting the cursor for such frames is useless and even
1130 		// causes asserts.
1131 		if( pAccImpl->GetFrm() )
1132 			pAccImpl->InvalidateCursorPos();
1133 	}
1134 }
1135 
1136 void SwAccessibleMap::InvalidateShapeSelection()
1137 {
1138 	if( GetShell()->ActionPend() )
1139 	{
1140 		SwAccessibleEvent_Impl aEvent(
1141 			SwAccessibleEvent_Impl::SHAPE_SELECTION );
1142 		AppendEvent( aEvent );
1143 	}
1144 	else
1145 	{
1146 		FireEvents();
1147 		DoInvalidateShapeSelection();
1148 	}
1149 }
1150 //IAccessibility2 Implementation 2009-----
1151 //This method should implement the following functions:
1152 //1.find the shape objects and set the selected state.
1153 //2.find the Swframe objects and set the selected state.
1154 //3.find the paragraph objects and set the selected state.
1155 void SwAccessibleMap::InvalidateShapeInParaSelection()
1156 {
1157 	SwAccessibleObjShape_Impl *pShapes = 0;
1158 	SwAccessibleObjShape_Impl *pSelShape = 0;
1159 	size_t nShapes = 0;
1160 
1161 	const ViewShell *pVSh = GetShell();
1162 	const SwFEShell *pFESh = pVSh->ISA( SwFEShell ) ?
1163 							static_cast< const SwFEShell * >( pVSh ) : 0;
1164 	SwPaM* pCrsr = pFESh ? pFESh->GetCrsr( sal_False /* ??? */ ) : NULL;//IAccessibility2 Implementation 2009
1165 
1166 	//sal_uInt16 nSelShapes = pFESh ? pFESh->IsObjSelected() : 0;
1167 
1168 	{
1169 		vos::OGuard aGuard( maMutex );
1170 		if( mpShapeMap )
1171 			pShapes = mpShapeMap->Copy( nShapes, pFESh, &pSelShape );
1172 	}
1173 
1174 	sal_Bool bIsSelAll =IsDocumentSelAll();
1175 
1176 	if( mpShapeMap )
1177 	{
1178 		//Checked for shapes.
1179 		_SwAccessibleShapeMap_Impl::const_iterator aIter = mpShapeMap->begin();
1180 		_SwAccessibleShapeMap_Impl::const_iterator aEndIter = mpShapeMap->end();
1181 		::vos::ORef< SwAccessibleContext > xParentAccImpl;
1182 
1183 		if( bIsSelAll)
1184 		{
1185 			while( aIter != aEndIter )
1186 			{
1187 				uno::Reference < XAccessible > xAcc( (*aIter).second );
1188 				if( xAcc.is() )
1189 					(static_cast < ::accessibility::AccessibleShape* >(xAcc.get()))->SetState( AccessibleStateType::SELECTED );
1190 
1191 				++aIter;
1192 			}
1193 		}
1194 		else
1195 		{
1196 			while( aIter != aEndIter )
1197 			{
1198 				sal_Bool bChanged = sal_False;
1199 				sal_Bool bMarked = sal_False;
1200 				SwAccessibleChild pFrm( (*aIter).first );
1201 
1202 				const SwFrmFmt *pFrmFmt = (*aIter).first ? ::FindFrmFmt( (*aIter).first ) : 0;
1203 				if( !pFrmFmt ) { ++aIter; continue; }
1204 				const SwFmtAnchor& pAnchor = pFrmFmt->GetAnchor();
1205 				const SwPosition *pPos = pAnchor.GetCntntAnchor();
1206 
1207 				if(pAnchor.GetAnchorId() == FLY_AT_PAGE)
1208 				{
1209 					uno::Reference < XAccessible > xAcc( (*aIter).second );
1210 					if(xAcc.is())
1211 						(static_cast < ::accessibility::AccessibleShape* >(xAcc.get()))->ResetState( AccessibleStateType::SELECTED );
1212 
1213 					++aIter; continue;
1214 				}
1215 
1216 				if( !pPos ) { ++aIter; continue; }
1217 				if( pPos->nNode.GetNode().GetTxtNode() )
1218 				{
1219 					int pIndex = pPos->nContent.GetIndex();
1220 					SwPaM* pTmpCrsr = pCrsr;
1221 					if( pTmpCrsr != NULL )
1222 					{
1223 						const SwTxtNode* pNode = pPos->nNode.GetNode().GetTxtNode();
1224 						sal_uLong nHere = pNode->GetIndex();
1225 
1226 						do
1227 						{
1228 							// ignore, if no mark
1229 							if( pTmpCrsr->HasMark() )
1230 							{
1231 								bMarked = sal_True;
1232 								// check whether nHere is 'inside' pCrsr
1233 								SwPosition* pStart = pTmpCrsr->Start();
1234 								sal_uLong nStartIndex = pStart->nNode.GetIndex();
1235 								SwPosition* pEnd = pTmpCrsr->End();
1236 								sal_uLong nEndIndex = pEnd->nNode.GetIndex();
1237 								if( ( nHere >= nStartIndex ) && (nHere <= nEndIndex)  )
1238 								{
1239 									if( pAnchor.GetAnchorId() == FLY_AS_CHAR )
1240 									{
1241 										if( ( (nHere == nStartIndex) && (pIndex >= pStart->nContent.GetIndex()) || (nHere > nStartIndex) )
1242 											&&( (nHere == nEndIndex) && (pIndex < pEnd->nContent.GetIndex()) || (nHere < nEndIndex) ) )
1243 										{
1244 											uno::Reference < XAccessible > xAcc( (*aIter).second );
1245 											if( xAcc.is() )
1246 												bChanged = (static_cast < ::accessibility::AccessibleShape* >(xAcc.get()))->SetState( AccessibleStateType::SELECTED );
1247 										}
1248 										else
1249 										{
1250 											uno::Reference < XAccessible > xAcc( (*aIter).second );
1251 											if( xAcc.is() )
1252 												bChanged = (static_cast < ::accessibility::AccessibleShape* >(xAcc.get()))->ResetState( AccessibleStateType::SELECTED );
1253 										}
1254 									}
1255 									else if( pAnchor.GetAnchorId() == FLY_AT_PARA )
1256 									{
1257 										if( ((nHere > nStartIndex) || pStart->nContent.GetIndex() ==0 )
1258 											&& (nHere < nEndIndex ) )
1259 										{
1260 											uno::Reference < XAccessible > xAcc( (*aIter).second );
1261 											if( xAcc.is() )
1262 												bChanged = (static_cast < ::accessibility::AccessibleShape* >(xAcc.get()))->SetState( AccessibleStateType::SELECTED );
1263 										}
1264 										else
1265 										{
1266 											uno::Reference < XAccessible > xAcc( (*aIter).second );
1267 											if(xAcc.is())
1268 												bChanged = (static_cast < ::accessibility::AccessibleShape* >(xAcc.get()))->ResetState( AccessibleStateType::SELECTED );
1269 										}
1270 									}
1271 								}
1272 							}
1273 							// next PaM in ring
1274 							pTmpCrsr = static_cast<SwPaM*>( pTmpCrsr->GetNext() );
1275 						}
1276 						while( pTmpCrsr != pCrsr );
1277 					}
1278 					if( !bMarked )
1279 					{
1280 						SwAccessibleObjShape_Impl  *pShape = pShapes;
1281 						size_t nNumShapes = nShapes;
1282 						while( nNumShapes )
1283 						{
1284 							if( pShape < pSelShape && (pShape->first==(*aIter).first) )
1285 							{
1286 								uno::Reference < XAccessible > xAcc( (*aIter).second );
1287 								if(xAcc.is())
1288 									bChanged = (static_cast < ::accessibility::AccessibleShape* >(xAcc.get()))->ResetState( AccessibleStateType::SELECTED );
1289 							}
1290 							--nNumShapes;
1291 							++pShape;
1292 						}
1293 					}
1294 				}
1295 				++aIter;
1296 			}//while( aIter != aEndIter )
1297 		}//else
1298 	}
1299 
1300 	//Checked for FlyFrm
1301 	SwAccessibleContextMap_Impl::iterator aIter = mpFrmMap->begin();
1302 	while( aIter != mpFrmMap->end() )
1303 	{
1304 		const SwFrm *pFrm = (*aIter).first;
1305 		if(pFrm->IsFlyFrm())
1306 		{
1307 			sal_Bool bFrmChanged = sal_False;
1308 			uno::Reference < XAccessible > xAcc = (*aIter).second;
1309 
1310 			if(xAcc.is())
1311 			{
1312 				SwAccessibleFrameBase *pAccFrame = (static_cast< SwAccessibleFrameBase * >(xAcc.get()));
1313 				bFrmChanged = pAccFrame->SetSelectedState( sal_True );
1314 				if (bFrmChanged)
1315 				{
1316 					const SwFlyFrm *pFlyFrm = static_cast< const SwFlyFrm * >( pFrm );
1317 					const SwFrmFmt *pFrmFmt = pFlyFrm->GetFmt();
1318 					if (pFrmFmt)
1319 					{
1320 						const SwFmtAnchor& pAnchor = pFrmFmt->GetAnchor();
1321 						if( pAnchor.GetAnchorId() == FLY_AS_CHAR )
1322 						{
1323 							uno::Reference< XAccessible > xAccParent = pAccFrame->getAccessibleParent();
1324 							if (xAccParent.is())
1325 							{
1326 								uno::Reference< XAccessibleContext > xAccContext = xAccParent->getAccessibleContext();
1327 								if(xAccContext.is() && xAccContext->getAccessibleRole() == AccessibleRole::PARAGRAPH)
1328 								{
1329 									SwAccessibleParagraph* pAccPara = static_cast< SwAccessibleParagraph *>(xAccContext.get());
1330 									if(pAccFrame->IsSeletedInDoc())
1331 									{
1332 										m_setParaAdd.insert(pAccPara);
1333 									}
1334 									else if(m_setParaAdd.count(pAccPara) == 0)
1335 									{
1336 										m_setParaRemove.insert(pAccPara);
1337 									}
1338 								}
1339 							}
1340 						}
1341 					}
1342                 }
1343 			}
1344 		}
1345 		++aIter;
1346 	}
1347 	typedef std::vector< SwAccessibleContext* > VEC_PARA;
1348 	VEC_PARA vecAdd;
1349 	VEC_PARA vecRemove;
1350 	//Checked for Paras.
1351 	SwPaM* pTmpCrsr = pCrsr;
1352 	sal_Bool bMarkChanged = sal_False;
1353 	SwAccessibleContextMap_Impl mapTemp;
1354 	if( pTmpCrsr != NULL )
1355 	{
1356 		do
1357 		{
1358 			if( pTmpCrsr->HasMark() )
1359 			{
1360 				SwNodeIndex nStartIndex( pTmpCrsr->Start()->nNode );
1361 				SwNodeIndex nEndIndex( pTmpCrsr->End()->nNode );
1362 				while(nStartIndex <= nEndIndex)
1363 				{
1364 					SwFrm *pFrm = NULL;
1365 					if(nStartIndex.GetNode().IsCntntNode())
1366 					{
1367 						SwCntntNode* pCNd = (SwCntntNode*)&(nStartIndex.GetNode());
1368 						SwClientIter aClientIter( *pCNd );
1369 						pFrm = (SwFrm*)aClientIter.First( TYPE(SwFrm));
1370 					}
1371 					else if( nStartIndex.GetNode().IsTableNode() )
1372 					{
1373 						SwTableNode * pTable= (SwTableNode *)&(nStartIndex.GetNode());
1374 						SwFrmFmt* pFmt = const_cast<SwFrmFmt*>(pTable->GetTable().GetFrmFmt());
1375 						SwClientIter aClientIter( *pFmt );
1376 						pFrm = (SwFrm*)aClientIter.First( TYPE(SwFrm));
1377 					}
1378 
1379                     if( pFrm && mpFrmMap)
1380 					{
1381 						aIter = mpFrmMap->find( pFrm );
1382 						if( aIter != mpFrmMap->end() )
1383 						{
1384 							uno::Reference < XAccessible > xAcc = (*aIter).second;
1385 							sal_Bool isChanged = sal_False;
1386 							if( xAcc.is() )
1387 							{
1388 								isChanged = (static_cast< SwAccessibleContext * >(xAcc.get()))->SetSelectedState( sal_True );
1389 							}
1390 							if(!isChanged)
1391 							{
1392 								SwAccessibleContextMap_Impl::iterator aEraseIter = mpSeletedFrmMap->find( pFrm );
1393 								if(aEraseIter != mpSeletedFrmMap->end())
1394 									mpSeletedFrmMap->erase(aEraseIter);
1395 							}
1396 							else
1397 							{
1398 								bMarkChanged = sal_True;
1399 								vecAdd.push_back(static_cast< SwAccessibleContext * >(xAcc.get()));
1400 							}
1401 
1402 							mapTemp.insert( SwAccessibleContextMap_Impl::value_type( pFrm, xAcc ) );
1403 						}
1404 					}
1405 					nStartIndex++;
1406 				}
1407 			}
1408 			pTmpCrsr = static_cast<SwPaM*>( pTmpCrsr->GetNext() );
1409 		}
1410 		while( pTmpCrsr != pCrsr );
1411 	}
1412 	if( !mpSeletedFrmMap )
1413 		mpSeletedFrmMap = new SwAccessibleContextMap_Impl;
1414 	if( !mpSeletedFrmMap->empty() )
1415 	{
1416 		aIter = mpSeletedFrmMap->begin();
1417 		while( aIter != mpSeletedFrmMap->end() )
1418 		{
1419 			uno::Reference < XAccessible > xAcc = (*aIter).second;
1420 			if(xAcc.is())
1421 				(static_cast< SwAccessibleContext * >(xAcc.get()))->SetSelectedState( sal_False );
1422 			++aIter;
1423 			vecRemove.push_back(static_cast< SwAccessibleContext * >(xAcc.get()));
1424 		}
1425 		bMarkChanged = sal_True;
1426 		mpSeletedFrmMap->clear();
1427 	}
1428 
1429 	if( !mapTemp.empty() )
1430 	{
1431 		aIter = mapTemp.begin();
1432 		while( aIter != mapTemp.end() )
1433 		{
1434 			mpSeletedFrmMap->insert( SwAccessibleContextMap_Impl::value_type( (*aIter).first, (*aIter).second ) );
1435 			++aIter;
1436 		}
1437 		mapTemp.clear();
1438 	}
1439 	if( bMarkChanged && mpFrmMap)
1440 	{
1441 		VEC_PARA::iterator vi = vecAdd.begin();
1442 		for (; vi != vecAdd.end() ; ++vi)
1443 		{
1444 			AccessibleEventObject aEvent;
1445 			aEvent.EventId = AccessibleEventId::SELECTION_CHANGED;
1446 			SwAccessibleContext* pAccPara = *vi;
1447 			if (pAccPara)
1448 			{
1449 				pAccPara->FireAccessibleEvent( aEvent );
1450 			}
1451 		}
1452 		vi = vecRemove.begin();
1453 		for (; vi != vecRemove.end() ; ++vi)
1454 		{
1455 			AccessibleEventObject aEvent;
1456 			aEvent.EventId = AccessibleEventId::SELECTION_CHANGED_REMOVE;
1457 			SwAccessibleContext* pAccPara = *vi;
1458 			if (pAccPara)
1459 			{
1460 				pAccPara->FireAccessibleEvent( aEvent );
1461 			}
1462 		}
1463 	}
1464 }
1465 
1466 //Marge with DoInvalidateShapeFocus
1467 void SwAccessibleMap::DoInvalidateShapeSelection(sal_Bool bInvalidateFocusMode /*=sal_False*/)
1468 {
1469 	SwAccessibleObjShape_Impl *pShapes = 0;
1470 	SwAccessibleObjShape_Impl *pSelShape = 0;
1471 	size_t nShapes = 0;
1472 
1473 	const ViewShell *pVSh = GetShell();
1474 	const SwFEShell *pFESh = pVSh->ISA( SwFEShell ) ?
1475 							static_cast< const SwFEShell * >( pVSh ) : 0;
1476 	sal_uInt16 nSelShapes = pFESh ? pFESh->IsObjSelected() : 0;
1477 
1478 
1479 	//when InvalidateFocus Call this function ,and the current selected shape count is not 1 ,
1480 	//return
1481 	if (bInvalidateFocusMode && nSelShapes != 1)
1482 	{
1483 		return;
1484 	}
1485 	{
1486 		vos::OGuard aGuard( maMutex );
1487 		if( mpShapeMap )
1488 			pShapes = mpShapeMap->Copy( nShapes, pFESh, &pSelShape );
1489 	}
1490 
1491 	if( pShapes )
1492 	{
1493 		typedef std::vector< ::vos::ORef < ::accessibility::AccessibleShape >  >  VEC_SHAPE;
1494 		VEC_SHAPE vecxShapeAdd;
1495 		VEC_SHAPE vecxShapeRemove;
1496 		int nCountSelectedShape=0;
1497 
1498 		Window *pWin = GetShell()->GetWin();
1499 		sal_Bool bFocused = pWin && pWin->HasFocus();
1500 		SwAccessibleObjShape_Impl *pShape = pShapes;
1501 		int nShapeCount = nShapes;
1502 		while( nShapeCount )
1503 		{
1504 			//if( pShape->second.isValid() )
1505 			if (pShape->second.isValid() && IsInSameLevel(pShape->first, pFESh))
1506 				{
1507 				if( pShape < pSelShape )
1508 				{
1509 					if(pShape->second->ResetState( AccessibleStateType::SELECTED ))
1510 					{
1511 						vecxShapeRemove.push_back(pShape->second);
1512 					}
1513 					pShape->second->ResetState( AccessibleStateType::FOCUSED );
1514 				}
1515 			}
1516 			--nShapeCount;
1517 			++pShape;
1518 		}
1519 
1520 		VEC_SHAPE::iterator vi =vecxShapeRemove.begin();
1521 		for (; vi != vecxShapeRemove.end(); ++vi)
1522 		{
1523 			::accessibility::AccessibleShape *pAccShape = static_cast< ::accessibility::AccessibleShape * >(vi->getBodyPtr());
1524 			if (pAccShape)
1525 			{
1526 				pAccShape->CommitChange(AccessibleEventId::SELECTION_CHANGED_REMOVE, uno::Any(), uno::Any());
1527 			}
1528 		}
1529 
1530 		pShape = pShapes;
1531 		while( nShapes )
1532 		{
1533 			//if( pShape->second.isValid() )
1534 			if (pShape->second.isValid() && IsInSameLevel(pShape->first, pFESh))
1535 			{
1536 				// IA2 - why?
1537 				// sal_Bool bChanged;
1538 				if( pShape >= pSelShape )
1539 				{
1540 					// IA2: first fire focus event
1541 					// bChanged = pShape->second->SetState( AccessibleStateType::SELECTED );
1542 
1543 					//first fire focus event
1544 					if( bFocused && 1 == nSelShapes )
1545 						pShape->second->SetState( AccessibleStateType::FOCUSED );
1546 					else
1547 						pShape->second->ResetState( AccessibleStateType::FOCUSED );
1548 
1549 					// IA2 CWS:
1550 					if(pShape->second->SetState( AccessibleStateType::SELECTED ))
1551 					{
1552 						vecxShapeAdd.push_back(pShape->second);
1553 					}
1554 					++nCountSelectedShape;
1555 				}
1556 				/* MT: This still was in DEV300m80, but was removed in IA2 CWS.
1557 				   Someone needs to check what should happen here, see original diff CWS oo31ia2 vs. OOO310M11
1558 				else
1559 				{
1560 					bChanged =
1561 						pShape->second->ResetState( AccessibleStateType::SELECTED );
1562 					pShape->second->ResetState( AccessibleStateType::FOCUSED );
1563 				}
1564 				if( bChanged )
1565 				{
1566                     const SwFrm* pParent = SwAccessibleFrame::GetParent(
1567                                                     SwAccessibleChild( pShape->first ),
1568                                                     GetShell()->IsPreView() );
1569                     aParents.push_back( pParent );
1570 				}
1571 				*/
1572 			}
1573 
1574 			--nShapes;
1575 			++pShape;
1576 		}
1577 
1578 		const unsigned int SELECTION_WITH_NUM = 10;
1579 		if (vecxShapeAdd.size() > SELECTION_WITH_NUM )
1580 		{
1581 			uno::Reference< XAccessible > xDoc = GetDocumentView( );
1582 			 SwAccessibleContext * pCont = static_cast<SwAccessibleContext *>(xDoc.get());
1583 			 if (pCont)
1584 			 {
1585 				 AccessibleEventObject aEvent;
1586 				 aEvent.EventId = AccessibleEventId::SELECTION_CHANGED_WITHIN;
1587 				 pCont->FireAccessibleEvent(aEvent);
1588 			 }
1589 		}
1590 		else
1591 		{
1592 			short nEventID = AccessibleEventId::SELECTION_CHANGED_ADD;
1593 			if (nCountSelectedShape <= 1 && vecxShapeAdd.size() == 1 )
1594 			{
1595 				nEventID = AccessibleEventId::SELECTION_CHANGED;
1596 			}
1597 			vi = vecxShapeAdd.begin();
1598 			for (; vi != vecxShapeAdd.end(); ++vi)
1599 			{
1600 				::accessibility::AccessibleShape *pAccShape = static_cast< ::accessibility::AccessibleShape * >(vi->getBodyPtr());
1601 				if (pAccShape)
1602 				{
1603 					pAccShape->CommitChange(nEventID, uno::Any(), uno::Any());
1604 				}
1605 			}
1606 		}
1607 
1608 		vi = vecxShapeAdd.begin();
1609 		for (; vi != vecxShapeAdd.end(); ++vi)
1610 		{
1611 			::accessibility::AccessibleShape *pAccShape = static_cast< ::accessibility::AccessibleShape * >(vi->getBodyPtr());
1612 			if (pAccShape)
1613 			{
1614 				SdrObject *pObj = GetSdrObjectFromXShape(pAccShape->GetXShape());
1615 				SwFrmFmt *pFrmFmt = pObj ? FindFrmFmt( pObj ) : NULL;
1616 				if (pFrmFmt)
1617 				{
1618 					const SwFmtAnchor& pAnchor = pFrmFmt->GetAnchor();
1619 					if( pAnchor.GetAnchorId() == FLY_AS_CHAR )
1620 					{
1621 						uno::Reference< XAccessible > xPara = pAccShape->getAccessibleParent();
1622 						if (xPara.is())
1623 						{
1624 							uno::Reference< XAccessibleContext > xParaContext = xPara->getAccessibleContext();
1625 							if (xParaContext.is() && xParaContext->getAccessibleRole() == AccessibleRole::PARAGRAPH)
1626 							{
1627 								SwAccessibleParagraph* pAccPara = static_cast< SwAccessibleParagraph *>(xPara.get());
1628 								if (pAccPara)
1629 								{
1630 									m_setParaAdd.insert(pAccPara);
1631 								}
1632 							}
1633 						}
1634 					}
1635 				}
1636 			}
1637 		}
1638 		vi = vecxShapeRemove.begin();
1639 		for (; vi != vecxShapeRemove.end(); ++vi)
1640 		{
1641 			::accessibility::AccessibleShape *pAccShape = static_cast< ::accessibility::AccessibleShape * >(vi->getBodyPtr());
1642 			if (pAccShape)
1643 			{
1644 				uno::Reference< XAccessible > xPara = pAccShape->getAccessibleParent();
1645 				uno::Reference< XAccessibleContext > xParaContext = xPara->getAccessibleContext();
1646 				if (xParaContext.is() && xParaContext->getAccessibleRole() == AccessibleRole::PARAGRAPH)
1647 				{
1648 					SwAccessibleParagraph* pAccPara = static_cast< SwAccessibleParagraph *>(xPara.get());
1649 					if (m_setParaAdd.count(pAccPara) == 0 )
1650 					{
1651 						m_setParaRemove.insert(pAccPara);
1652 					}
1653 				}
1654 			}
1655 		}
1656 		delete[] pShapes;
1657 	}
1658 }
1659 
1660 //Marge with DoInvalidateShapeSelection
1661 /*
1662 void SwAccessibleMap::DoInvalidateShapeFocus()
1663 {
1664 	const ViewShell *pVSh = GetShell();
1665 	const SwFEShell *pFESh = pVSh->ISA( SwFEShell ) ?
1666 							static_cast< const SwFEShell * >( pVSh ) : 0;
1667 	sal_uInt16 nSelShapes = pFESh ? pFESh->IsObjSelected() : 0;
1668 
1669 	if( nSelShapes != 1 )
1670 		return;
1671 
1672 	SwAccessibleObjShape_Impl *pShapes = 0;
1673 	SwAccessibleObjShape_Impl *pSelShape = 0;
1674 	size_t nShapes = 0;
1675 
1676 
1677 	{
1678 		vos::OGuard aGuard( maMutex );
1679 		if( mpShapeMap )
1680 			pShapes = mpShapeMap->Copy( nShapes, pFESh, &pSelShape );
1681 	}
1682 
1683 	if( pShapes )
1684 	{
1685 		Window *pWin = GetShell()->GetWin();
1686 		sal_Bool bFocused = pWin && pWin->HasFocus();
1687 		SwAccessibleObjShape_Impl  *pShape = pShapes;
1688 		while( nShapes )
1689 		{
1690 			if( pShape->second.isValid() )
1691 			{
1692 				if( bFocused && pShape >= pSelShape )
1693 					pShape->second->SetState( AccessibleStateType::FOCUSED );
1694 				else
1695 					pShape->second->ResetState( AccessibleStateType::FOCUSED );
1696 			}
1697 
1698 			--nShapes;
1699 			++pShape;
1700 		}
1701 
1702 		delete[] pShapes;
1703 	}
1704 }
1705 */
1706 //-----IAccessibility2 Implementation 2009
1707 
1708 SwAccessibleMap::SwAccessibleMap( ViewShell *pSh ) :
1709 	mpFrmMap( 0  ),
1710 	mpShapeMap( 0  ),
1711 	mpShapes( 0  ),
1712 	mpEvents( 0  ),
1713 	mpEventMap( 0  ),
1714     // --> OD 2005-12-13 #i27301#
1715     mpSelectedParas( 0 ),
1716     // <--
1717 	mpVSh( pSh ),
1718     	mpPreview( 0 ),
1719 	mnPara( 1 ),
1720 	mnFootnote( 1 ),
1721 	mnEndnote( 1 ),
1722 	mbShapeSelected( sal_False ),
1723 	mpSeletedFrmMap(NULL)//IAccessibility2 Implementation 2009
1724 {
1725 	pSh->GetLayout()->AddAccessibleShell();
1726 }
1727 
1728 SwAccessibleMap::~SwAccessibleMap()
1729 {
1730 	uno::Reference < XAccessible > xAcc;
1731 	{
1732 		vos::OGuard aGuard( maMutex );
1733 		if( mpFrmMap )
1734 		{
1735 			const SwRootFrm *pRootFrm = GetShell()->GetLayout();
1736 			SwAccessibleContextMap_Impl::iterator aIter = mpFrmMap->find( pRootFrm );
1737 			if( aIter != mpFrmMap->end() )
1738 				xAcc = (*aIter).second;
1739 			if( !xAcc.is() )
1740 				xAcc = new SwAccessibleDocument( this );
1741 		}
1742 	}
1743 
1744 	//IAccessibility2 Implementation 2009-----
1745 	if(xAcc.is())
1746 	{
1747 	SwAccessibleDocument *pAcc =
1748 		static_cast< SwAccessibleDocument * >( xAcc.get() );
1749 	pAcc->Dispose( sal_True );
1750 	}
1751 	if( mpFrmMap )
1752 	{
1753 		SwAccessibleContextMap_Impl::iterator aIter = mpFrmMap->begin();
1754 		while( aIter != mpFrmMap->end() )
1755 		{
1756 			uno::Reference < XAccessible > xTmp = (*aIter).second;
1757 			if( xTmp.is() )
1758 			{
1759 				SwAccessibleContext *pTmp = static_cast< SwAccessibleContext * >( xTmp.get() );
1760 				pTmp->SetMap(NULL);
1761 			}
1762 			++aIter;
1763 		}
1764 	}
1765 	//-----IAccessibility2 Implementation 2009
1766 	{
1767 		vos::OGuard aGuard( maMutex );
1768 #ifdef DBG_UTIL
1769 		ASSERT( !mpFrmMap || mpFrmMap->empty(),
1770 				"Frame map should be empty after disposing the root frame" );
1771 		if( mpFrmMap )
1772 		{
1773 			SwAccessibleContextMap_Impl::iterator aIter = mpFrmMap->begin();
1774 			while( aIter != mpFrmMap->end() )
1775 			{
1776 				uno::Reference < XAccessible > xTmp = (*aIter).second;
1777 				if( xTmp.is() )
1778 				{
1779 					SwAccessibleContext *pTmp =
1780 						static_cast< SwAccessibleContext * >( xTmp.get() );
1781 					(void) pTmp;
1782 				}
1783 				++aIter;
1784 			}
1785 		}
1786 		ASSERT( !mpShapeMap || mpShapeMap->empty(),
1787 				"Object map should be empty after disposing the root frame" );
1788 		if( mpShapeMap )
1789 		{
1790 			SwAccessibleShapeMap_Impl::iterator aIter = mpShapeMap->begin();
1791 			while( aIter != mpShapeMap->end() )
1792 			{
1793 				uno::Reference < XAccessible > xTmp = (*aIter).second;
1794 				if( xTmp.is() )
1795 				{
1796 					::accessibility::AccessibleShape *pTmp =
1797 						static_cast< ::accessibility::AccessibleShape* >( xTmp.get() );
1798 					(void) pTmp;
1799 				}
1800 				++aIter;
1801 			}
1802 		}
1803 #endif
1804 		delete mpFrmMap;
1805 		mpFrmMap = 0;
1806 		delete mpShapeMap;
1807 		mpShapeMap = 0;
1808 		delete mpShapes;
1809 		mpShapes = 0;
1810         // --> OD 2005-12-13 #i27301#
1811         delete mpSelectedParas;
1812         mpSelectedParas = 0;
1813         // <--
1814 	}
1815 
1816 	delete mpPreview;
1817 	mpPreview = NULL;
1818 
1819     {
1820 		vos::OGuard aGuard( maEventMutex );
1821 #ifdef DBG_UTIL
1822 		ASSERT( !(mpEvents || mpEventMap), "pending events" );
1823 		if( mpEvents )
1824 		{
1825 			SwAccessibleEventList_Impl::iterator aIter = mpEvents->begin();
1826 			while( aIter != mpEvents->end() )
1827 			{
1828 				++aIter;
1829 			}
1830 		}
1831 		if( mpEventMap )
1832 		{
1833 			SwAccessibleEventMap_Impl::iterator aIter = mpEventMap->begin();
1834 			while( aIter != mpEventMap->end() )
1835 			{
1836 				++aIter;
1837 			}
1838 		}
1839 #endif
1840 		delete mpEventMap;
1841 		mpEventMap = 0;
1842 		delete mpEvents;
1843 		mpEvents = 0;
1844 	}
1845 	mpVSh->GetLayout()->RemoveAccessibleShell();
1846 	delete mpSeletedFrmMap;//IAccessibility2 Implementation 2009
1847 }
1848 
1849 uno::Reference< XAccessible > SwAccessibleMap::_GetDocumentView(
1850     sal_Bool bPagePreview )
1851 {
1852 	uno::Reference < XAccessible > xAcc;
1853 	sal_Bool bSetVisArea = sal_False;
1854 
1855 	{
1856 		vos::OGuard aGuard( maMutex );
1857 
1858 		if( !mpFrmMap )
1859 		{
1860 			mpFrmMap = new SwAccessibleContextMap_Impl;
1861 #ifdef DBG_UTIL
1862 			mpFrmMap->mbLocked = sal_False;
1863 #endif
1864 		}
1865 
1866 #ifdef DBG_UTIL
1867 		ASSERT( !mpFrmMap->mbLocked, "Map is locked" );
1868 		mpFrmMap->mbLocked = sal_True;
1869 #endif
1870 
1871 		const SwRootFrm *pRootFrm = GetShell()->GetLayout();
1872 		SwAccessibleContextMap_Impl::iterator aIter = mpFrmMap->find( pRootFrm );
1873 		if( aIter != mpFrmMap->end() )
1874 			xAcc = (*aIter).second;
1875 		if( xAcc.is() )
1876 		{
1877 			bSetVisArea = sal_True; // Set VisArea when map mutex is not
1878 									// locked
1879 		}
1880 		else
1881 		{
1882             if( bPagePreview )
1883                 xAcc = new SwAccessiblePreview( this );
1884             else
1885                 xAcc = new SwAccessibleDocument( this );
1886 
1887 			if( aIter != mpFrmMap->end() )
1888 			{
1889 				(*aIter).second = xAcc;
1890 			}
1891 			else
1892 			{
1893 				SwAccessibleContextMap_Impl::value_type aEntry( pRootFrm, xAcc );
1894 				mpFrmMap->insert( aEntry );
1895 			}
1896 		}
1897 
1898 #ifdef DBG_UTIL
1899 		mpFrmMap->mbLocked = sal_False;
1900 #endif
1901 	}
1902 
1903 	if( bSetVisArea )
1904 	{
1905 		SwAccessibleDocumentBase *pAcc =
1906 			static_cast< SwAccessibleDocumentBase * >( xAcc.get() );
1907 		pAcc->SetVisArea();
1908 	}
1909 
1910 	return xAcc;
1911 }
1912 
1913 uno::Reference< XAccessible > SwAccessibleMap::GetDocumentView( )
1914 {
1915     return _GetDocumentView( sal_False );
1916 }
1917 
1918 // OD 14.01.2003 #103492# - complete re-factoring of method due to new page/print
1919 // preview functionality.
1920 uno::Reference<XAccessible> SwAccessibleMap::GetDocumentPreview(
1921                                     const std::vector<PrevwPage*>& _rPrevwPages,
1922                                     const Fraction&  _rScale,
1923                                     const SwPageFrm* _pSelectedPageFrm,
1924                                     const Size&      _rPrevwWinSize )
1925 {
1926     // create & update preview data object
1927     if( mpPreview == NULL )
1928         mpPreview = new SwAccPreviewData();
1929     mpPreview->Update( *this, _rPrevwPages, _rScale, _pSelectedPageFrm, _rPrevwWinSize );
1930 
1931     uno::Reference<XAccessible> xAcc = _GetDocumentView( sal_True );
1932     return xAcc;
1933 }
1934 
1935 uno::Reference< XAccessible> SwAccessibleMap::GetContext( const SwFrm *pFrm,
1936 												     sal_Bool bCreate )
1937 {
1938 	uno::Reference < XAccessible > xAcc;
1939 	uno::Reference < XAccessible > xOldCursorAcc;
1940 	sal_Bool bOldShapeSelected = sal_False;
1941 
1942 	{
1943 		vos::OGuard aGuard( maMutex );
1944 
1945 		if( !mpFrmMap && bCreate )
1946 			mpFrmMap = new SwAccessibleContextMap_Impl;
1947 		if( mpFrmMap )
1948 		{
1949 			SwAccessibleContextMap_Impl::iterator aIter = mpFrmMap->find( pFrm );
1950 			if( aIter != mpFrmMap->end() )
1951 				xAcc = (*aIter).second;
1952 
1953 			if( !xAcc.is() && bCreate )
1954 			{
1955 				SwAccessibleContext *pAcc = 0;
1956 				switch( pFrm->GetType() )
1957 				{
1958 				case FRM_TXT:
1959                     mnPara++;
1960                     pAcc = new SwAccessibleParagraph( *this,
1961                                     static_cast< const SwTxtFrm& >( *pFrm ) );
1962 					break;
1963 				case FRM_HEADER:
1964 					pAcc = new SwAccessibleHeaderFooter( this,
1965 									static_cast< const SwHeaderFrm *>( pFrm ) );
1966 					break;
1967 				case FRM_FOOTER:
1968 					pAcc = new SwAccessibleHeaderFooter( this,
1969 									static_cast< const SwFooterFrm *>( pFrm ) );
1970 					break;
1971 				case FRM_FTN:
1972 					{
1973 						const SwFtnFrm *pFtnFrm =
1974 							static_cast < const SwFtnFrm * >( pFrm );
1975 						sal_Bool bIsEndnote =
1976 							SwAccessibleFootnote::IsEndnote( pFtnFrm );
1977 						pAcc = new SwAccessibleFootnote( this, bIsEndnote,
1978 									/*(bIsEndnote ? mnEndnote++ : mnFootnote++),*/
1979 									pFtnFrm );
1980 					}
1981 					break;
1982 				case FRM_FLY:
1983 					{
1984 						const SwFlyFrm *pFlyFrm =
1985 							static_cast < const SwFlyFrm * >( pFrm );
1986 						switch( SwAccessibleFrameBase::GetNodeType( pFlyFrm ) )
1987 						{
1988 						case ND_GRFNODE:
1989 							pAcc = new SwAccessibleGraphic( this, pFlyFrm );
1990 							break;
1991 						case ND_OLENODE:
1992 							pAcc = new SwAccessibleEmbeddedObject( this, pFlyFrm );
1993 							break;
1994 						default:
1995 							pAcc = new SwAccessibleTextFrame( this, pFlyFrm );
1996 							break;
1997 						}
1998 					}
1999 					break;
2000 				case FRM_CELL:
2001 					pAcc = new SwAccessibleCell( this,
2002 									static_cast< const SwCellFrm *>( pFrm ) );
2003 					break;
2004 				case FRM_TAB:
2005                     pAcc = new SwAccessibleTable( this,
2006 									static_cast< const SwTabFrm *>( pFrm ) );
2007 					break;
2008                 case FRM_PAGE:
2009                     DBG_ASSERT( GetShell()->IsPreView(),
2010                                 "accessible page frames only in PagePreview" );
2011                     pAcc = new SwAccessiblePage( this, pFrm );
2012                     break;
2013 				}
2014 				xAcc = pAcc;
2015 
2016 				ASSERT( xAcc.is(), "unknown frame type" );
2017 				if( xAcc.is() )
2018 				{
2019 					if( aIter != mpFrmMap->end() )
2020 					{
2021 						(*aIter).second = xAcc;
2022 					}
2023 					else
2024 					{
2025 						SwAccessibleContextMap_Impl::value_type aEntry( pFrm, xAcc );
2026 						mpFrmMap->insert( aEntry );
2027 					}
2028 
2029 					if( pAcc->HasCursor() &&
2030 						!AreInSameTable( mxCursorContext, pFrm ) )
2031 					{
2032 						// If the new context has the focus, and if we know
2033 						// another context that had the focus, then the focus
2034 						// just moves from the old context to the new one. We
2035 						// have to send a focus event and a caret event for
2036 						// the old context then. We have to to that know,
2037 						// because after we have left this method, anyone might
2038 						// call getStates for the new context and will get a
2039 						// focused state then. Sending the focus changes event
2040 						// after that seems to be strange. However, we cannot
2041 						// send a focus event fo the new context now, because
2042 					    // noone except us knows it. In any case, we remeber
2043 						// the new context as the one that has the focus
2044 						// currently.
2045 
2046 						xOldCursorAcc = mxCursorContext;
2047 						mxCursorContext = xAcc;
2048 
2049 						bOldShapeSelected = mbShapeSelected;
2050 						mbShapeSelected = sal_False;
2051 					}
2052 				}
2053 			}
2054 		}
2055 	}
2056 
2057 	// Invalidate focus for old object when map is not locked
2058 	if( xOldCursorAcc.is() )
2059 		InvalidateCursorPosition( xOldCursorAcc );
2060 	if( bOldShapeSelected )
2061 		InvalidateShapeSelection();
2062 
2063 	return xAcc;
2064 }
2065 
2066 ::vos::ORef < SwAccessibleContext > SwAccessibleMap::GetContextImpl(
2067 			const SwFrm *pFrm,
2068 			sal_Bool bCreate )
2069 {
2070 	uno::Reference < XAccessible > xAcc( GetContext( pFrm, bCreate ) );
2071 
2072 	::vos::ORef < SwAccessibleContext > xAccImpl(
2073 		 static_cast< SwAccessibleContext * >( xAcc.get() ) );
2074 
2075 	return xAccImpl;
2076 }
2077 
2078 uno::Reference< XAccessible> SwAccessibleMap::GetContext(
2079 		const SdrObject *pObj,
2080 		SwAccessibleContext *pParentImpl,
2081 		sal_Bool bCreate )
2082 {
2083 	uno::Reference < XAccessible > xAcc;
2084 	uno::Reference < XAccessible > xOldCursorAcc;
2085 
2086 	{
2087 		vos::OGuard aGuard( maMutex );
2088 
2089 		if( !mpShapeMap && bCreate )
2090 			mpShapeMap = new SwAccessibleShapeMap_Impl( this );
2091 		if( mpShapeMap )
2092 		{
2093 			SwAccessibleShapeMap_Impl::iterator aIter =
2094 			   	mpShapeMap->find( pObj );
2095 			if( aIter != mpShapeMap->end() )
2096 				xAcc = (*aIter).second;
2097 
2098 			if( !xAcc.is() && bCreate )
2099 			{
2100 				::accessibility::AccessibleShape *pAcc = 0;
2101 				uno::Reference < drawing::XShape > xShape(
2102 					const_cast< SdrObject * >( pObj )->getUnoShape(),
2103 					uno::UNO_QUERY );
2104 				if( xShape.is() )
2105 				{
2106 					::accessibility::ShapeTypeHandler& rShapeTypeHandler =
2107 								::accessibility::ShapeTypeHandler::Instance();
2108 					uno::Reference < XAccessible > xParent( pParentImpl );
2109 					::accessibility::AccessibleShapeInfo aShapeInfo(
2110 							xShape, xParent, this );
2111 
2112 					pAcc = rShapeTypeHandler.CreateAccessibleObject(
2113 								aShapeInfo, mpShapeMap->GetInfo() );
2114 				}
2115 				xAcc = pAcc;
2116 
2117 				ASSERT( xAcc.is(), "unknown shape type" );
2118 				if( xAcc.is() )
2119 				{
2120 					pAcc->Init();
2121 					if( aIter != mpShapeMap->end() )
2122 					{
2123 						(*aIter).second = xAcc;
2124 					}
2125 					else
2126 					{
2127 						SwAccessibleShapeMap_Impl::value_type aEntry( pObj,
2128 																	  xAcc );
2129 						mpShapeMap->insert( aEntry );
2130 					}
2131 					// TODO: focus!!!
2132 				}
2133 				//IAccessibility2 Implementation 2009-----
2134 				if (xAcc.is())
2135 					AddGroupContext(pObj, xAcc);
2136 				//-----IAccessibility2 Implementation 2009
2137 			}
2138 		}
2139 	}
2140 
2141 	// Invalidate focus for old object when map is not locked
2142 	if( xOldCursorAcc.is() )
2143 		InvalidateCursorPosition( xOldCursorAcc );
2144 
2145 	return xAcc;
2146 }
2147 //IAccessibility2 Implementation 2009-----
2148 sal_Bool SwAccessibleMap::IsInSameLevel(const SdrObject* pObj, const SwFEShell* pFESh)
2149 {
2150 	if (pFESh)
2151 		return pFESh->IsObjSameLevelWithMarked(pObj);
2152 	return sal_False;
2153 }
2154 void SwAccessibleMap::AddShapeContext(const SdrObject *pObj, uno::Reference < XAccessible > xAccShape)
2155 {
2156 	vos::OGuard aGuard( maMutex );
2157 
2158 	if( mpShapeMap )
2159 	{
2160 		SwAccessibleShapeMap_Impl::value_type aEntry( pObj, xAccShape );
2161 		mpShapeMap->insert( aEntry );
2162 	}
2163 
2164 }
2165 
2166 //Added by yanjun for sym2_6407
2167 void SwAccessibleMap::RemoveGroupContext(const SdrObject *pParentObj, ::com::sun::star::uno::Reference < ::com::sun::star::accessibility::XAccessible > xAccParent)
2168 {
2169 	vos::OGuard aGuard( maMutex );
2170 	if (mpShapeMap && pParentObj && pParentObj->IsGroupObject() && xAccParent.is())
2171 	{
2172 		uno::Reference < XAccessibleContext > xContext = xAccParent->getAccessibleContext();
2173 		if (xContext.is())
2174 		{
2175 			for (sal_Int32 i = 0; i < xContext->getAccessibleChildCount(); ++i)
2176 			{
2177 				uno::Reference < XAccessible > xChild = xContext->getAccessibleChild(i);
2178 				if (xChild.is())
2179 				{
2180 					uno::Reference < XAccessibleContext > xChildContext = xChild->getAccessibleContext();
2181 					if (xChildContext.is())
2182 					{
2183 						if (xChildContext->getAccessibleRole() == AccessibleRole::SHAPE)
2184 						{
2185 							::accessibility::AccessibleShape* pAccShape = static_cast < ::accessibility::AccessibleShape* >( xChild.get());
2186 							uno::Reference < drawing::XShape > xShape = pAccShape->GetXShape();
2187 							if (xShape.is())
2188 							{
2189 								SdrObject* pObj = GetSdrObjectFromXShape(xShape);
2190 								if (pObj)
2191 									RemoveContext(pObj);
2192 							}
2193 						}
2194 					}
2195 				}
2196 			}
2197 		}
2198 	}
2199 }
2200 //End
2201 
2202 
2203 void SwAccessibleMap::AddGroupContext(const SdrObject *pParentObj, uno::Reference < XAccessible > xAccParent)
2204 {
2205 	vos::OGuard aGuard( maMutex );
2206 	if( mpShapeMap )
2207 	{
2208 		//here get all the sub list.
2209 		if (pParentObj->IsGroupObject())
2210 		{
2211 			if (xAccParent.is())
2212 			{
2213 				uno::Reference < XAccessibleContext > xContext = xAccParent->getAccessibleContext();
2214 				if (xContext.is())
2215 				{
2216 					sal_Int32 nChildren = xContext->getAccessibleChildCount();
2217 					for(sal_Int32 i = 0; i<nChildren; i++)
2218 					{
2219 						uno::Reference < XAccessible > xChild = xContext->getAccessibleChild(i);
2220 						if (xChild.is())
2221 						{
2222 							uno::Reference < XAccessibleContext > xChildContext = xChild->getAccessibleContext();
2223 							if (xChildContext.is())
2224 							{
2225 								short nRole = xChildContext->getAccessibleRole();
2226 								if (nRole == AccessibleRole::SHAPE)
2227 								{
2228 									::accessibility::AccessibleShape* pAccShape = static_cast < ::accessibility::AccessibleShape* >( xChild.get());
2229 									uno::Reference < drawing::XShape > xShape = pAccShape->GetXShape();
2230 									if (xShape.is())
2231 									{
2232 										SdrObject* pObj = GetSdrObjectFromXShape(xShape);
2233 										AddShapeContext(pObj, xChild);
2234 										AddGroupContext(pObj,xChild);
2235 									}
2236 								}
2237 							}
2238 						}
2239 					}
2240 				}
2241 			}
2242 		}
2243 	}
2244 }
2245 //-----IAccessibility2 Implementation 2009
2246 
2247 ::vos::ORef < ::accessibility::AccessibleShape > SwAccessibleMap::GetContextImpl(
2248 			const SdrObject *pObj,
2249 			SwAccessibleContext *pParentImpl,
2250 			sal_Bool bCreate )
2251 {
2252 	uno::Reference < XAccessible > xAcc( GetContext( pObj, pParentImpl, bCreate ) );
2253 
2254 	::vos::ORef < ::accessibility::AccessibleShape > xAccImpl(
2255 		 static_cast< ::accessibility::AccessibleShape* >( xAcc.get() ) );
2256 
2257 	return xAccImpl;
2258 }
2259 
2260 
2261 void SwAccessibleMap::RemoveContext( const SwFrm *pFrm )
2262 {
2263 	vos::OGuard aGuard( maMutex );
2264 
2265 	if( mpFrmMap )
2266 	{
2267 		SwAccessibleContextMap_Impl::iterator aIter =
2268 			mpFrmMap->find( pFrm );
2269 		if( aIter != mpFrmMap->end() )
2270 		{
2271 			mpFrmMap->erase( aIter );
2272 
2273 			// Remove reference to old caret object. Though mxCursorContext
2274 			// is a weak reference and cleared automatically, clearing it
2275 			// directly makes sure to not keep a defunctional object.
2276 			uno::Reference < XAccessible > xOldAcc( mxCursorContext );
2277 			if( xOldAcc.is() )
2278 			{
2279 				SwAccessibleContext *pOldAccImpl =
2280 					static_cast< SwAccessibleContext *>( xOldAcc.get() );
2281 				ASSERT( pOldAccImpl->GetFrm(), "old caret context is disposed" );
2282 				if( pOldAccImpl->GetFrm() == pFrm )
2283 				{
2284 					xOldAcc.clear();	// get an empty ref
2285 					mxCursorContext = xOldAcc;
2286 				}
2287 			}
2288 
2289 			if( mpFrmMap->empty() )
2290 			{
2291 				delete mpFrmMap;
2292 				mpFrmMap = 0;
2293 			}
2294 		}
2295 	}
2296 }
2297 
2298 void SwAccessibleMap::RemoveContext( const SdrObject *pObj )
2299 {
2300 	vos::OGuard aGuard( maMutex );
2301 
2302 	if( mpShapeMap )
2303 	{
2304 		SwAccessibleShapeMap_Impl::iterator aIter =
2305 			mpShapeMap->find( pObj );
2306 		if( aIter != mpShapeMap->end() )
2307 		{
2308 			//IAccessible2 Implementation 2009 ----
2309 			uno::Reference < XAccessible > xAcc( (*aIter).second );
2310 			mpShapeMap->erase( aIter );
2311 			RemoveGroupContext(pObj, xAcc);
2312 			// The shape selection flag is not cleared, but one might do
2313 			// so but has to make sure that the removed context is the one
2314 			// that is selected.
2315 
2316 			if( mpShapeMap && mpShapeMap->empty() )
2317 			//---- IAccessible2 Implementation 2009
2318 			{
2319 				delete mpShapeMap;
2320 				mpShapeMap = 0;
2321 			}
2322 		}
2323 	}
2324 }
2325 
2326 
2327 void SwAccessibleMap::Dispose( const SwFrm *pFrm,
2328                                const SdrObject *pObj,
2329                                Window* pWindow,
2330 							   sal_Bool bRecursive )
2331 {
2332     SwAccessibleChild aFrmOrObj( pFrm, pObj, pWindow );
2333 
2334 	// Indeed, the following assert checks the frame's accessible flag,
2335 	// because that's the one that is evaluated in the layout. The frame
2336 	// might not be accessible anyway. That's the case for cell frames that
2337 	// contain further cells.
2338 	ASSERT( !aFrmOrObj.GetSwFrm() || aFrmOrObj.GetSwFrm()->IsAccessibleFrm(),
2339 			"non accessible frame should be disposed" );
2340 
2341 	if( aFrmOrObj.IsAccessible( GetShell()->IsPreView() ) )
2342 	{
2343         ::vos::ORef< SwAccessibleContext > xAccImpl;
2344         ::vos::ORef< SwAccessibleContext > xParentAccImpl;
2345         ::vos::ORef< ::accessibility::AccessibleShape > xShapeAccImpl;
2346 		// get accessible context for frame
2347 		{
2348 			vos::OGuard aGuard( maMutex );
2349 
2350 			// First of all look for an accessible context for a frame
2351 			if( aFrmOrObj.GetSwFrm() && mpFrmMap )
2352 			{
2353 				SwAccessibleContextMap_Impl::iterator aIter =
2354 					mpFrmMap->find( aFrmOrObj.GetSwFrm() );
2355 				if( aIter != mpFrmMap->end() )
2356 				{
2357 					uno::Reference < XAccessible > xAcc( (*aIter).second );
2358 					xAccImpl =
2359 						static_cast< SwAccessibleContext *>( xAcc.get() );
2360 				}
2361 			}
2362 			if( !xAccImpl.isValid() && mpFrmMap )
2363 			{
2364 				// If there is none, look if the parent is accessible.
2365 				const SwFrm *pParent =
2366 						SwAccessibleFrame::GetParent( aFrmOrObj,
2367                                                       GetShell()->IsPreView());
2368 
2369 				if( pParent )
2370 				{
2371 					SwAccessibleContextMap_Impl::iterator aIter =
2372 						mpFrmMap->find( pParent );
2373 					if( aIter != mpFrmMap->end() )
2374 					{
2375 						uno::Reference < XAccessible > xAcc( (*aIter).second );
2376 						xParentAccImpl =
2377 							static_cast< SwAccessibleContext *>( xAcc.get() );
2378 					}
2379 				}
2380 			}
2381 			if( !xParentAccImpl.isValid() && !aFrmOrObj.GetSwFrm() &&
2382 				mpShapeMap )
2383 			{
2384 				SwAccessibleShapeMap_Impl::iterator aIter =
2385                     mpShapeMap->find( aFrmOrObj.GetDrawObject() );
2386 				if( aIter != mpShapeMap->end() )
2387 				{
2388 					uno::Reference < XAccessible > xAcc( (*aIter).second );
2389 					xShapeAccImpl =
2390 						static_cast< ::accessibility::AccessibleShape *>( xAcc.get() );
2391 				}
2392 			}
2393 			if( pObj && GetShell()->ActionPend() &&
2394 				(xParentAccImpl.isValid() || xShapeAccImpl.isValid()) )
2395 			{
2396 				// Keep a reference to the XShape to avoid that it
2397 				// is deleted with a SwFrmFmt::Modify.
2398 				uno::Reference < drawing::XShape > xShape(
2399 					const_cast< SdrObject * >( pObj )->getUnoShape(),
2400 					uno::UNO_QUERY );
2401 				if( xShape.is() )
2402 				{
2403 					if( !mpShapes )
2404 						mpShapes = new SwShapeList_Impl;
2405 					mpShapes->push_back( xShape );
2406 				}
2407 			}
2408 		}
2409 
2410 		// remove events stored for the frame
2411 		{
2412 			vos::OGuard aGuard( maEventMutex );
2413 			if( mpEvents )
2414 			{
2415 				SwAccessibleEventMap_Impl::iterator aIter =
2416 					mpEventMap->find( aFrmOrObj );
2417 				if( aIter != mpEventMap->end() )
2418 				{
2419 					SwAccessibleEvent_Impl aEvent(
2420 							SwAccessibleEvent_Impl::DISPOSE, aFrmOrObj );
2421 					AppendEvent( aEvent );
2422 				}
2423 			}
2424 		}
2425 
2426 		// If the frame is accessible and there is a context for it, dispose
2427 		// the frame. If the frame is no context for it but disposing should
2428 		// take place recursive, the frame's children have to be disposed
2429 		// anyway, so we have to create the context then.
2430 		if( xAccImpl.isValid() )
2431 		{
2432 			xAccImpl->Dispose( bRecursive );
2433 		}
2434 		else if( xParentAccImpl.isValid() )
2435 		{
2436 			// If the frame is a cell frame, the table must be notified.
2437 			// If we are in an action, a table model change event will
2438 			// be broadcasted at the end of the action to give the table
2439 			// a chance to generate a single table change event.
2440 
2441 			xParentAccImpl->DisposeChild( aFrmOrObj, bRecursive );
2442 		}
2443 		else if( xShapeAccImpl.isValid() )
2444 		{
2445             RemoveContext( aFrmOrObj.GetDrawObject() );
2446 			xShapeAccImpl->dispose();
2447 		}
2448 
2449 		if( mpPreview && pFrm && pFrm->IsPageFrm() )
2450 			mpPreview->DisposePage( static_cast< const SwPageFrm *>( pFrm ) );
2451 	}
2452 }
2453 
2454 void SwAccessibleMap::InvalidatePosOrSize( const SwFrm *pFrm,
2455 										   const SdrObject *pObj,
2456                                            Window* pWindow,
2457 										   const SwRect& rOldBox )
2458 {
2459     SwAccessibleChild aFrmOrObj( pFrm, pObj, pWindow );
2460 	if( aFrmOrObj.IsAccessible( GetShell()->IsPreView() ) )
2461 	{
2462 		::vos::ORef< SwAccessibleContext > xAccImpl;
2463 		::vos::ORef< SwAccessibleContext > xParentAccImpl;
2464 		const SwFrm *pParent =NULL; //IAccessibility2 Implementation 2009
2465 		{
2466 			vos::OGuard aGuard( maMutex );
2467 
2468 			if( mpFrmMap )
2469 			{
2470 				if( aFrmOrObj.GetSwFrm() )
2471 				{
2472 					SwAccessibleContextMap_Impl::iterator aIter =
2473 						mpFrmMap->find( aFrmOrObj.GetSwFrm() );
2474 					if( aIter != mpFrmMap->end() )
2475 					{
2476 						// If there is an accesible object already it is
2477 						// notified directly.
2478 						uno::Reference < XAccessible > xAcc( (*aIter).second );
2479 						xAccImpl =
2480 							static_cast< SwAccessibleContext *>( xAcc.get() );
2481 					}
2482 				}
2483 				if( !xAccImpl.isValid() )
2484 				{
2485 					// Otherwise we look if the parent is accessible.
2486 					// If not, there is nothing to do.
2487 					pParent = //IAccessibility2 Implementation 2009
2488 						SwAccessibleFrame::GetParent( aFrmOrObj,
2489                                                       GetShell()->IsPreView());
2490 
2491 					if( pParent )
2492 					{
2493 						SwAccessibleContextMap_Impl::iterator aIter =
2494 							mpFrmMap->find( pParent );
2495 						if( aIter != mpFrmMap->end() )
2496 						{
2497 							uno::Reference < XAccessible > xAcc( (*aIter).second );
2498 							xParentAccImpl =
2499 								static_cast< SwAccessibleContext *>( xAcc.get() );
2500 						}
2501 					}
2502 				}
2503 			}
2504 		}
2505 
2506 		if( xAccImpl.isValid() )
2507 		{
2508 			if( GetShell()->ActionPend() )
2509 			{
2510 				SwAccessibleEvent_Impl aEvent(
2511 					SwAccessibleEvent_Impl::POS_CHANGED, xAccImpl.getBodyPtr(),
2512 					aFrmOrObj, rOldBox );
2513 				AppendEvent( aEvent );
2514 			}
2515 			else
2516 			{
2517 				FireEvents();
2518 				xAccImpl->InvalidatePosOrSize( rOldBox );
2519 			}
2520 		}
2521 		else if( xParentAccImpl.isValid() )
2522 		{
2523 			if( GetShell()->ActionPend() )
2524 			{
2525 				SwAccessibleEvent_Impl aEvent(
2526 					SwAccessibleEvent_Impl::CHILD_POS_CHANGED,
2527 					xParentAccImpl.getBodyPtr(), aFrmOrObj, rOldBox );
2528 				AppendEvent( aEvent );
2529 			}
2530 			else
2531 			{
2532 				FireEvents();
2533 				xParentAccImpl->InvalidateChildPosOrSize( aFrmOrObj,
2534 														  rOldBox );
2535 			}
2536 		}
2537 		//IAccessibility2 Implementation 2009-----
2538 		else if(pParent)
2539 		{
2540 /*
2541 For child graphic and it's parent paragraph,if split 2 graphic to 2 paragraph,
2542 will delete one graphic swfrm and new create 1 graphic swfrm ,
2543 then the new paragraph and the new graphic SwFrm will add .
2544 but when add graphic SwFrm ,the accessible of the new Paragraph is not created yet.
2545 so the new graphic accessible 'parent is NULL,
2546 so run here: save the parent's SwFrm not the accessible object parent,
2547 */
2548 			sal_Bool bIsValidFrm = sal_False;
2549 			sal_Bool bIsTxtParent = sal_False;
2550 			if (aFrmOrObj.GetSwFrm())
2551 			{
2552 				int nType = pFrm->GetType();
2553 				if ( FRM_FLY == nType )
2554 				{
2555 					bIsValidFrm =sal_True;
2556 				}
2557 			}
2558 			else if(pObj)
2559 			{
2560 				int nType = pParent->GetType();
2561 				if (FRM_TXT == nType)
2562 				{
2563 					bIsTxtParent =sal_True;
2564 				}
2565 			}
2566 //			sal_Bool bIsVisibleChildrenOnly =aFrmOrObj.IsVisibleChildrenOnly() ;
2567 //			sal_Bool bIsBoundAsChar =aFrmOrObj.IsBoundAsChar() ;//bIsVisibleChildrenOnly && bIsBoundAsChar &&
2568 			if((bIsValidFrm || bIsTxtParent) )
2569 			{
2570 				if( GetShell()->ActionPend() )
2571 				{
2572 					SwAccessibleEvent_Impl aEvent(
2573 						SwAccessibleEvent_Impl::CHILD_POS_CHANGED,
2574 						pParent, aFrmOrObj, rOldBox );
2575 					AppendEvent( aEvent );
2576 				}
2577 				else
2578 				{
2579 					OSL_ENSURE(false,"");
2580 				}
2581 			}
2582 		}
2583 	}
2584 	//-----IAccessibility2 Implementation 2009
2585 }
2586 
2587 void SwAccessibleMap::InvalidateContent( const SwFrm *pFrm )
2588 {
2589     SwAccessibleChild aFrmOrObj( pFrm );
2590 	if( aFrmOrObj.IsAccessible( GetShell()->IsPreView() ) )
2591 	{
2592 		uno::Reference < XAccessible > xAcc;
2593 		{
2594 			vos::OGuard aGuard( maMutex );
2595 
2596 			if( mpFrmMap )
2597 			{
2598 				SwAccessibleContextMap_Impl::iterator aIter =
2599 					mpFrmMap->find( aFrmOrObj.GetSwFrm() );
2600 				if( aIter != mpFrmMap->end() )
2601 					xAcc = (*aIter).second;
2602 			}
2603 		}
2604 
2605 		if( xAcc.is() )
2606 		{
2607 			SwAccessibleContext *pAccImpl =
2608 				static_cast< SwAccessibleContext *>( xAcc.get() );
2609 			if( GetShell()->ActionPend() )
2610 			{
2611 				SwAccessibleEvent_Impl aEvent(
2612 					SwAccessibleEvent_Impl::INVALID_CONTENT, pAccImpl,
2613 					aFrmOrObj );
2614 				AppendEvent( aEvent );
2615 			}
2616 			else
2617 			{
2618 				FireEvents();
2619 				pAccImpl->InvalidateContent();
2620 			}
2621 		}
2622 	}
2623 }
2624 
2625 // --> OD 2009-01-06 #i88069#
2626 void SwAccessibleMap::InvalidateAttr( const SwTxtFrm& rTxtFrm )
2627 {
2628     SwAccessibleChild aFrmOrObj( &rTxtFrm );
2629     if( aFrmOrObj.IsAccessible( GetShell()->IsPreView() ) )
2630     {
2631         uno::Reference < XAccessible > xAcc;
2632         {
2633             vos::OGuard aGuard( maMutex );
2634 
2635             if( mpFrmMap )
2636             {
2637                 SwAccessibleContextMap_Impl::iterator aIter =
2638                     mpFrmMap->find( aFrmOrObj.GetSwFrm() );
2639                 if( aIter != mpFrmMap->end() )
2640                     xAcc = (*aIter).second;
2641             }
2642         }
2643 
2644         if( xAcc.is() )
2645         {
2646             SwAccessibleContext *pAccImpl =
2647                 static_cast< SwAccessibleContext *>( xAcc.get() );
2648             if( GetShell()->ActionPend() )
2649             {
2650                 SwAccessibleEvent_Impl aEvent( SwAccessibleEvent_Impl::INVALID_ATTR,
2651                                                pAccImpl, aFrmOrObj );
2652                 aEvent.SetStates( ACC_STATE_TEXT_ATTRIBUTE_CHANGED );
2653                 AppendEvent( aEvent );
2654             }
2655             else
2656             {
2657                 FireEvents();
2658                 pAccImpl->InvalidateAttr();
2659             }
2660         }
2661     }
2662 }
2663 // <--
2664 
2665 void SwAccessibleMap::InvalidateCursorPosition( const SwFrm *pFrm )
2666 {
2667     SwAccessibleChild aFrmOrObj( pFrm );
2668 	sal_Bool bShapeSelected = sal_False;
2669 	const ViewShell *pVSh = GetShell();
2670 	if( pVSh->ISA( SwCrsrShell ) )
2671 	{
2672 		const SwCrsrShell *pCSh = static_cast< const SwCrsrShell * >( pVSh );
2673 		if( pCSh->IsTableMode() )
2674 		{
2675 			while( aFrmOrObj.GetSwFrm() && !aFrmOrObj.GetSwFrm()->IsCellFrm() )
2676 				aFrmOrObj = aFrmOrObj.GetSwFrm()->GetUpper();
2677 		}
2678 		else if( pVSh->ISA( SwFEShell ) )
2679 		{
2680 			sal_uInt16 nObjCount;
2681 			const SwFEShell *pFESh = static_cast< const SwFEShell * >( pVSh );
2682 			const SwFrm *pFlyFrm = pFESh->GetCurrFlyFrm();
2683 			if( pFlyFrm )
2684 			{
2685 				ASSERT( !pFrm || pFrm->FindFlyFrm() == pFlyFrm,
2686 						"cursor is not contained in fly frame" );
2687 				aFrmOrObj = pFlyFrm;
2688 			}
2689 			else if( (nObjCount = pFESh->IsObjSelected()) > 0 )
2690 			{
2691 				bShapeSelected = sal_True;
2692 				aFrmOrObj = static_cast<const SwFrm *>( 0 );
2693 			}
2694 		}
2695 	}
2696 
2697 	ASSERT( bShapeSelected || aFrmOrObj.IsAccessible(GetShell()->IsPreView()),
2698 			"frame is not accessible" );
2699 
2700 	uno::Reference < XAccessible > xOldAcc;
2701 	uno::Reference < XAccessible > xAcc;
2702 	sal_Bool bOldShapeSelected = sal_False;
2703 
2704 	{
2705 		vos::OGuard aGuard( maMutex );
2706 
2707 		xOldAcc = mxCursorContext;
2708 		mxCursorContext = xAcc;	// clear reference
2709 
2710 		bOldShapeSelected = mbShapeSelected;
2711 		mbShapeSelected = bShapeSelected;
2712 
2713 		if( aFrmOrObj.GetSwFrm() && mpFrmMap )
2714 		{
2715 			SwAccessibleContextMap_Impl::iterator aIter =
2716 				mpFrmMap->find( aFrmOrObj.GetSwFrm() );
2717 			if( aIter != mpFrmMap->end() )
2718 				xAcc = (*aIter).second;
2719 			//IAccessibility2 Implementation 2009-----
2720 			else
2721 			{
2722 				SwRect rcEmpty;
2723 				const SwTabFrm* pTabFrm = aFrmOrObj.GetSwFrm()->FindTabFrm();
2724 				if (pTabFrm)
2725 				{
2726 					InvalidatePosOrSize(pTabFrm,0,0,rcEmpty);
2727 				}
2728 				else
2729 				{
2730 					InvalidatePosOrSize(aFrmOrObj.GetSwFrm(),0,0,rcEmpty);
2731 				}
2732 
2733 
2734 				aIter =
2735 					mpFrmMap->find( aFrmOrObj.GetSwFrm() );
2736 				if( aIter != mpFrmMap->end() )
2737 				{
2738 					xAcc = (*aIter).second;
2739 				}
2740 			}
2741 			//-----IAccessibility2 Implementation 2009
2742 
2743 			// For cells, some extra thoughts are necessary,
2744 			// because invalidating the cursor for one cell
2745 			// invalidates the cursor for all cells of the same
2746 			// table. For this reason, we don't want to
2747 			// invalidate the cursor for the old cursor object
2748 			// and the new one if they are within the same table,
2749 			// because this would result in doing the work twice.
2750 			// Moreover, we have to make sure to invalidate the
2751 			// cursor even if the current cell has no accessible object.
2752 			// If the old cursor objects exists and is in the same
2753 			// table, its the best choice, because using it avoids
2754 			// an unnessarary cursor invalidation cycle when creating
2755 			// a new object for the current cell.
2756 			if( aFrmOrObj.GetSwFrm()->IsCellFrm() )
2757 			{
2758 				if( xOldAcc.is() &&
2759 					AreInSameTable( xOldAcc, aFrmOrObj.GetSwFrm() ) )
2760 				{
2761 					if( xAcc.is() )
2762 						xOldAcc = xAcc;	// avoid extra invalidation
2763 					else
2764 						xAcc = xOldAcc;	// make sure ate least one
2765 				}
2766 				if( !xAcc.is() )
2767 					xAcc = GetContext( aFrmOrObj.GetSwFrm(), sal_True );
2768 			}
2769 		}
2770         //IAccessibility2 Implementation 2009-----
2771         else if (bShapeSelected)
2772         {
2773             const SwFEShell *pFESh = pVSh ? static_cast< const SwFEShell * >( pVSh ) : NULL ;
2774             if(pFESh)
2775             {
2776                 const SdrMarkList *pMarkList = pFESh->GetMarkList();
2777                 if (pMarkList != NULL && pMarkList->GetMarkCount() == 1)
2778                 {
2779                     SdrObject *pObj = pMarkList->GetMark( 0 )->GetMarkedSdrObj();
2780 					::vos::ORef < ::accessibility::AccessibleShape > pAccShapeImpl = GetContextImpl(pObj,NULL,sal_False);
2781                     if (!pAccShapeImpl.isValid())
2782                     {
2783                         while (pObj && pObj->GetUpGroup())
2784                         {
2785                             pObj = pObj->GetUpGroup();
2786                         }
2787                         if (pObj != NULL)
2788                         {
2789                             const SwFrm *pParent = SwAccessibleFrame::GetParent( SwAccessibleChild(pObj), GetShell()->IsPreView() );
2790                             if( pParent )
2791                             {
2792                                 ::vos::ORef< SwAccessibleContext > xParentAccImpl = GetContextImpl(pParent,sal_False);
2793                                 if (!xParentAccImpl.isValid())
2794                                 {
2795                                     const SwTabFrm* pTabFrm = pParent->FindTabFrm();
2796                                     if (pTabFrm)
2797                                     {
2798                                         //The Table should not add in acc.because the "pParent" is not add to acc .
2799                                         uno::Reference< XAccessible>  xAccParentTab = GetContext(pTabFrm,sal_True);//Should Create.
2800 
2801                                         const SwFrm *pParentRoot = SwAccessibleFrame::GetParent( SwAccessibleChild(pTabFrm), GetShell()->IsPreView() );
2802                                         if (pParentRoot)
2803                                         {
2804                                             ::vos::ORef< SwAccessibleContext > xParentAccImplRoot = GetContextImpl(pParentRoot,sal_False);
2805                                             if(xParentAccImplRoot.isValid())
2806                                             {
2807                                                 AccessibleEventObject aEvent;
2808                                                 aEvent.EventId = AccessibleEventId::CHILD;
2809                                                 aEvent.NewValue <<= xAccParentTab;
2810                                                 xParentAccImplRoot->FireAccessibleEvent( aEvent );
2811                                             }
2812                                         }
2813 
2814                                         //Get "pParent" acc again.
2815                                         xParentAccImpl = GetContextImpl(pParent,sal_False);
2816                                     }
2817                                     else
2818                                     {
2819                                         //directly create this acc para .
2820                                         xParentAccImpl = GetContextImpl(pParent,sal_True);//Should Create.
2821 
2822                                         const SwFrm *pParentRoot = SwAccessibleFrame::GetParent( SwAccessibleChild(pParent), GetShell()->IsPreView() );
2823 
2824                                         ::vos::ORef< SwAccessibleContext > xParentAccImplRoot = GetContextImpl(pParentRoot,sal_False);
2825                                         if(xParentAccImplRoot.isValid())
2826                                         {
2827                                             AccessibleEventObject aEvent;
2828                                             aEvent.EventId = AccessibleEventId::CHILD;
2829                                             aEvent.NewValue <<= uno::Reference< XAccessible>(xParentAccImpl.getBodyPtr());
2830                                             xParentAccImplRoot->FireAccessibleEvent( aEvent );
2831                                         }
2832                                     }
2833                                 }
2834                                 if (xParentAccImpl.isValid())
2835                                 {
2836                                     uno::Reference< XAccessible>  xAccShape =
2837                                         GetContext(pObj,xParentAccImpl.getBodyPtr(),sal_True);
2838 
2839                                     AccessibleEventObject aEvent;
2840                                     aEvent.EventId = AccessibleEventId::CHILD;
2841                                     aEvent.NewValue <<= xAccShape;
2842                                     xParentAccImpl->FireAccessibleEvent( aEvent );
2843                                 }
2844                             }
2845                         }
2846                     }
2847                 }
2848             }
2849         }
2850 	}
2851 
2852 	m_setParaAdd.clear();
2853 	m_setParaRemove.clear();
2854 	if( xOldAcc.is() && xOldAcc != xAcc )
2855 		InvalidateCursorPosition( xOldAcc );
2856 	if( bOldShapeSelected || bShapeSelected )
2857 		InvalidateShapeSelection();
2858 	if( xAcc.is() )
2859 		InvalidateCursorPosition( xAcc );
2860 
2861 	InvalidateShapeInParaSelection();
2862 
2863 	SET_PARA::iterator si = m_setParaRemove.begin();
2864 	for (; si != m_setParaRemove.end() ; ++si)
2865 	{
2866 		SwAccessibleParagraph* pAccPara = *si;
2867 		if(pAccPara && pAccPara->getSelectedAccessibleChildCount() == 0 && pAccPara->getSelectedText().getLength() == 0)
2868 		{
2869 			if(pAccPara->SetSelectedState(sal_False))
2870 			{
2871 				AccessibleEventObject aEvent;
2872 				aEvent.EventId = AccessibleEventId::SELECTION_CHANGED_REMOVE;
2873 				pAccPara->FireAccessibleEvent( aEvent );
2874 			}
2875 		}
2876 	}
2877 	si = m_setParaAdd.begin();
2878 	for (; si != m_setParaAdd.end() ; ++si)
2879 	{
2880 		SwAccessibleParagraph* pAccPara = *si;
2881 		if(pAccPara && pAccPara->SetSelectedState(sal_True))
2882 		{
2883 			AccessibleEventObject aEvent;
2884 			aEvent.EventId = AccessibleEventId::SELECTION_CHANGED;
2885 			pAccPara->FireAccessibleEvent( aEvent );
2886 		}
2887 	}
2888     //-----IAccessibility2 Implementation 2009
2889 }
2890 
2891 //IAccessibility2 Implementation 2009-----
2892 //Notify the page change event to bridge.
2893 void SwAccessibleMap::FirePageChangeEvent(sal_uInt16 nOldPage, sal_uInt16 nNewPage)
2894 {
2895 	uno::Reference<XAccessible> xAcc = GetDocumentView( );
2896     	if ( xAcc.is() )
2897     	{
2898     		SwAccessibleDocumentBase *pAcc =
2899 			static_cast< SwAccessibleDocumentBase * >( xAcc.get() );
2900 			if (pAcc)
2901 			{
2902 				AccessibleEventObject aEvent;
2903 				aEvent.EventId = AccessibleEventId::PAGE_CHANGED;
2904 				aEvent.OldValue <<= nOldPage;
2905 				aEvent.NewValue <<= nNewPage;
2906 				pAcc->FireAccessibleEvent( aEvent );
2907 			}
2908     	}
2909 }
2910 
2911 void SwAccessibleMap::FireSectionChangeEvent(sal_uInt16 nOldSection, sal_uInt16 nNewSection)
2912 {
2913 	uno::Reference<XAccessible> xAcc = GetDocumentView( );
2914     	if ( xAcc.is() )
2915     	{
2916     		SwAccessibleDocumentBase *pAcc =
2917 			static_cast< SwAccessibleDocumentBase * >( xAcc.get() );
2918 			if (pAcc)
2919 			{
2920 				AccessibleEventObject aEvent;
2921 				aEvent.EventId = AccessibleEventId::SECTION_CHANGED;
2922 				aEvent.OldValue <<= nOldSection;
2923 				aEvent.NewValue <<= nNewSection;
2924 				pAcc->FireAccessibleEvent( aEvent );
2925 
2926 			}
2927     	}
2928 }
2929 void SwAccessibleMap::FireColumnChangeEvent(sal_uInt16 nOldColumn, sal_uInt16 nNewColumn)
2930 {
2931 	uno::Reference<XAccessible> xAcc = GetDocumentView( );
2932     	if ( xAcc.is() )
2933     	{
2934     		SwAccessibleDocumentBase *pAcc =
2935 			static_cast< SwAccessibleDocumentBase * >( xAcc.get() );
2936 		if (pAcc)
2937 		{
2938 				AccessibleEventObject aEvent;
2939 				aEvent.EventId = AccessibleEventId::COLUMN_CHANGED;
2940 				aEvent.OldValue <<= nOldColumn;
2941 				aEvent.NewValue <<= nNewColumn;
2942 				pAcc->FireAccessibleEvent( aEvent );
2943 
2944 		}
2945     	}
2946 }
2947 //-----IAccessibility2 Implementation 2009
2948 
2949 void SwAccessibleMap::InvalidateFocus()
2950 {
2951 	//IAccessibility2 Implementation 2009-----
2952 	if(GetShell()->IsPreView())
2953 	{
2954 		uno::Reference<XAccessible> xAcc = _GetDocumentView( sal_True );
2955 		if (xAcc.get())
2956 		{
2957 			SwAccessiblePreview *pAccPreview = static_cast<SwAccessiblePreview *>(xAcc.get());
2958 			if (pAccPreview)
2959 			{
2960 				pAccPreview->InvalidateFocus();
2961 				return ;
2962 			}
2963 		}
2964 	}
2965 	//-----IAccessibility2 Implementation 2009
2966 	uno::Reference < XAccessible > xAcc;
2967 	sal_Bool bShapeSelected;
2968 	{
2969 		vos::OGuard aGuard( maMutex );
2970 
2971 		xAcc = mxCursorContext;
2972 		bShapeSelected = mbShapeSelected;
2973 	}
2974 
2975 	if( xAcc.is() )
2976 	{
2977 		SwAccessibleContext *pAccImpl =
2978 			static_cast< SwAccessibleContext *>( xAcc.get() );
2979 		pAccImpl->InvalidateFocus();
2980 	}
2981 	//IAccessibility2 Implementation 2009-----
2982 	else
2983 	{
2984 		DoInvalidateShapeSelection(sal_True);
2985 	}
2986 	//-----IAccessibility2 Implementation 2009
2987 }
2988 
2989 void SwAccessibleMap::SetCursorContext(
2990 		const ::vos::ORef < SwAccessibleContext >& rCursorContext )
2991 {
2992 	vos::OGuard aGuard( maMutex );
2993 	uno::Reference < XAccessible > xAcc( rCursorContext.getBodyPtr() );
2994 	mxCursorContext = xAcc;
2995 }
2996 
2997 // --> OD 2005-12-12 #i27301# - use new type definition for <_nStates>
2998 void SwAccessibleMap::InvalidateStates( tAccessibleStates _nStates,
2999                                         const SwFrm* _pFrm )
3000 {
3001 	// Start with the frame or the first upper that is accessible
3002     SwAccessibleChild aFrmOrObj( _pFrm );
3003 	while( aFrmOrObj.GetSwFrm() &&
3004 			!aFrmOrObj.IsAccessible( GetShell()->IsPreView() ) )
3005 		aFrmOrObj = aFrmOrObj.GetSwFrm()->GetUpper();
3006 	if( !aFrmOrObj.GetSwFrm() )
3007 		aFrmOrObj = GetShell()->GetLayout();
3008 
3009 	uno::Reference< XAccessible > xAcc( GetContext( aFrmOrObj.GetSwFrm(), sal_True ) );
3010 	SwAccessibleContext *pAccImpl =
3011 		static_cast< SwAccessibleContext *>( xAcc.get() );
3012 	if( GetShell()->ActionPend() )
3013 	{
3014         SwAccessibleEvent_Impl aEvent( SwAccessibleEvent_Impl::CARET_OR_STATES,
3015                                        pAccImpl,
3016                                        SwAccessibleChild(pAccImpl->GetFrm()),
3017                                        _nStates );
3018 		AppendEvent( aEvent );
3019 	}
3020 	else
3021 	{
3022 		FireEvents();
3023         pAccImpl->InvalidateStates( _nStates );
3024 	}
3025 }
3026 // <--
3027 
3028 void SwAccessibleMap::_InvalidateRelationSet( const SwFrm* pFrm,
3029                                               sal_Bool bFrom )
3030 {
3031     // first, see if this frame is accessible, and if so, get the respective
3032     SwAccessibleChild aFrmOrObj( pFrm );
3033 	if( aFrmOrObj.IsAccessible( GetShell()->IsPreView() ) )
3034 	{
3035 		uno::Reference < XAccessible > xAcc;
3036 		{
3037 			vos::OGuard aGuard( maMutex );
3038 
3039 			if( mpFrmMap )
3040 			{
3041 				SwAccessibleContextMap_Impl::iterator aIter =
3042                                         mpFrmMap->find( aFrmOrObj.GetSwFrm() );
3043 				if( aIter != mpFrmMap->end() )
3044 				{
3045 					xAcc = (*aIter).second;
3046 				}
3047 			}
3048 		}
3049 
3050         // deliver event directly, or queue event
3051 		if( xAcc.is() )
3052 		{
3053 			SwAccessibleContext *pAccImpl =
3054                             static_cast< SwAccessibleContext *>( xAcc.get() );
3055             if( GetShell()->ActionPend() )
3056             {
3057                 SwAccessibleEvent_Impl aEvent( SwAccessibleEvent_Impl::CARET_OR_STATES,
3058                                                pAccImpl, SwAccessibleChild(pFrm),
3059                                                ( bFrom
3060                                                  ? ACC_STATE_RELATION_FROM
3061                                                  : ACC_STATE_RELATION_TO ) );
3062                 AppendEvent( aEvent );
3063             }
3064             else
3065             {
3066 				FireEvents();
3067                 pAccImpl->InvalidateRelation( bFrom
3068                         ? AccessibleEventId::CONTENT_FLOWS_FROM_RELATION_CHANGED
3069                         : AccessibleEventId::CONTENT_FLOWS_TO_RELATION_CHANGED );
3070             }
3071         }
3072     }
3073 }
3074 
3075 void SwAccessibleMap::InvalidateRelationSet( const SwFrm* pMaster,
3076                                              const SwFrm* pFollow )
3077 {
3078     _InvalidateRelationSet( pMaster, sal_False );
3079     _InvalidateRelationSet( pFollow, sal_True );
3080 }
3081 
3082 /** invalidation CONTENT_FLOW_FROM/_TO relation of a paragraph
3083 
3084     OD 2005-12-01 #i27138#
3085 
3086     @author OD
3087 */
3088 void SwAccessibleMap::InvalidateParaFlowRelation( const SwTxtFrm& _rTxtFrm,
3089                                                   const bool _bFrom )
3090 {
3091     _InvalidateRelationSet( &_rTxtFrm, _bFrom );
3092 }
3093 
3094 /** invalidation of text selection of a paragraph
3095 
3096     OD 2005-12-12 #i27301#
3097 
3098     @author OD
3099 */
3100 void SwAccessibleMap::InvalidateParaTextSelection( const SwTxtFrm& _rTxtFrm )
3101 {
3102     // first, see if this frame is accessible, and if so, get the respective
3103     SwAccessibleChild aFrmOrObj( &_rTxtFrm );
3104     if( aFrmOrObj.IsAccessible( GetShell()->IsPreView() ) )
3105     {
3106         uno::Reference < XAccessible > xAcc;
3107         {
3108             vos::OGuard aGuard( maMutex );
3109 
3110             if( mpFrmMap )
3111             {
3112                 SwAccessibleContextMap_Impl::iterator aIter =
3113                                         mpFrmMap->find( aFrmOrObj.GetSwFrm() );
3114                 if( aIter != mpFrmMap->end() )
3115                 {
3116                     xAcc = (*aIter).second;
3117                 }
3118             }
3119         }
3120 
3121         // deliver event directly, or queue event
3122         if( xAcc.is() )
3123         {
3124             SwAccessibleContext *pAccImpl =
3125                             static_cast< SwAccessibleContext *>( xAcc.get() );
3126             if( GetShell()->ActionPend() )
3127             {
3128                 SwAccessibleEvent_Impl aEvent(
3129                     SwAccessibleEvent_Impl::CARET_OR_STATES,
3130                     pAccImpl,
3131                     SwAccessibleChild( &_rTxtFrm ),
3132                     ACC_STATE_TEXT_SELECTION_CHANGED );
3133                 AppendEvent( aEvent );
3134             }
3135             else
3136             {
3137                 FireEvents();
3138                 pAccImpl->InvalidateTextSelection();
3139             }
3140         }
3141     }
3142 }
3143 
3144 sal_Int32 SwAccessibleMap::GetChildIndex( const SwFrm& rParentFrm,
3145                                           Window& rChild ) const
3146 {
3147     sal_Int32 nIndex( -1 );
3148 
3149     SwAccessibleChild aFrmOrObj( &rParentFrm );
3150     if( aFrmOrObj.IsAccessible( GetShell()->IsPreView() ) )
3151     {
3152         uno::Reference < XAccessible > xAcc;
3153         {
3154             vos::OGuard aGuard( maMutex );
3155 
3156             if( mpFrmMap )
3157             {
3158                 SwAccessibleContextMap_Impl::iterator aIter =
3159                                         mpFrmMap->find( aFrmOrObj.GetSwFrm() );
3160                 if( aIter != mpFrmMap->end() )
3161                 {
3162                     xAcc = (*aIter).second;
3163                 }
3164             }
3165         }
3166 
3167         if( xAcc.is() )
3168         {
3169             SwAccessibleContext *pAccImpl =
3170                             static_cast< SwAccessibleContext *>( xAcc.get() );
3171 
3172             nIndex = pAccImpl->GetChildIndex( const_cast<SwAccessibleMap&>(*this),
3173                                               SwAccessibleChild( &rChild ) );
3174         }
3175     }
3176 
3177     return nIndex;
3178 }
3179 
3180 
3181 // OD 15.01.2003 #103492# - complete re-factoring of method due to new page/print
3182 // preview functionality.
3183 void SwAccessibleMap::UpdatePreview( const std::vector<PrevwPage*>& _rPrevwPages,
3184                                      const Fraction&  _rScale,
3185                                      const SwPageFrm* _pSelectedPageFrm,
3186                                      const Size&      _rPrevwWinSize )
3187 {
3188     DBG_ASSERT( GetShell()->IsPreView(), "no preview?" );
3189     DBG_ASSERT( mpPreview != NULL, "no preview data?" );
3190 
3191     // OD 15.01.2003 #103492# - adjustments for changed method signature
3192     mpPreview->Update( *this, _rPrevwPages, _rScale, _pSelectedPageFrm, _rPrevwWinSize );
3193 
3194     // propagate change of VisArea through the document's
3195     // accessibility tree; this will also send appropriate scroll
3196     // events
3197     SwAccessibleContext* pDoc =
3198         GetContextImpl( GetShell()->GetLayout() ).getBodyPtr();
3199     static_cast<SwAccessibleDocumentBase*>( pDoc )->SetVisArea();
3200 
3201 	uno::Reference < XAccessible > xOldAcc;
3202 	uno::Reference < XAccessible > xAcc;
3203 	{
3204 		vos::OGuard aGuard( maMutex );
3205 
3206 		xOldAcc = mxCursorContext;
3207 
3208 		const SwPageFrm *pSelPage = mpPreview->GetSelPage();
3209 		if( pSelPage && mpFrmMap )
3210 		{
3211 			SwAccessibleContextMap_Impl::iterator aIter =
3212 				mpFrmMap->find( pSelPage );
3213 			if( aIter != mpFrmMap->end() )
3214 				xAcc = (*aIter).second;
3215 		}
3216 	}
3217 
3218 	if( xOldAcc.is() && xOldAcc != xAcc )
3219 		InvalidateCursorPosition( xOldAcc );
3220 	if( xAcc.is() )
3221 		InvalidateCursorPosition( xAcc );
3222 }
3223 
3224 void SwAccessibleMap::InvalidatePreViewSelection( sal_uInt16 nSelPage )
3225 {
3226     DBG_ASSERT( GetShell()->IsPreView(), "no preview?" );
3227     DBG_ASSERT( mpPreview != NULL, "no preview data?" );
3228 
3229     // OD 16.01.2003 #103492# - changed metthod call due to method signature change.
3230     mpPreview->InvalidateSelection( GetShell()->GetLayout()->GetPageByPageNum( nSelPage ) );
3231 
3232 	uno::Reference < XAccessible > xOldAcc;
3233 	uno::Reference < XAccessible > xAcc;
3234 	{
3235 		vos::OGuard aGuard( maMutex );
3236 
3237 		xOldAcc = mxCursorContext;
3238 
3239 		const SwPageFrm *pSelPage = mpPreview->GetSelPage();
3240 		if( pSelPage && mpFrmMap )
3241 		{
3242 			SwAccessibleContextMap_Impl::iterator aIter =
3243 				mpFrmMap->find( pSelPage );
3244 			if( aIter != mpFrmMap->end() )
3245 				xAcc = (*aIter).second;
3246 		}
3247 	}
3248 
3249 	if( xOldAcc.is() && xOldAcc != xAcc )
3250 		InvalidateCursorPosition( xOldAcc );
3251 	if( xAcc.is() )
3252 		InvalidateCursorPosition( xAcc );
3253 }
3254 
3255 
3256 sal_Bool SwAccessibleMap::IsPageSelected( const SwPageFrm *pPageFrm ) const
3257 {
3258 	return mpPreview && mpPreview->GetSelPage() == pPageFrm;
3259 }
3260 
3261 
3262 void SwAccessibleMap::FireEvents()
3263 {
3264 	{
3265 		vos::OGuard aGuard( maEventMutex );
3266 		if( mpEvents )
3267 		{
3268 			mpEvents->SetFiring();
3269 			//IAccessibility2 Implementation 2009-----
3270 			mpEvents->MoveInvalidXAccToEnd();
3271 			//-----IAccessibility2 Implementation 2009
3272 			SwAccessibleEventList_Impl::iterator aIter = mpEvents->begin();
3273 			while( aIter != mpEvents->end() )
3274 			{
3275 				FireEvent( *aIter );
3276 				++aIter;
3277 			}
3278 
3279 			delete mpEventMap;
3280 			mpEventMap = 0;
3281 
3282 			delete mpEvents;
3283 			mpEvents = 0;
3284 		}
3285 	}
3286 	{
3287 		vos::OGuard aGuard( maMutex );
3288 		if( mpShapes )
3289 		{
3290 			delete mpShapes;
3291 			mpShapes = 0;
3292 		}
3293 	}
3294 
3295 }
3296 
3297 sal_Bool SwAccessibleMap::IsValid() const
3298 {
3299 	return sal_True;
3300 }
3301 
3302 Rectangle SwAccessibleMap::GetVisibleArea() const
3303 {
3304     MapMode aSrc( MAP_TWIP );
3305 	MapMode aDest( MAP_100TH_MM );
3306 	return OutputDevice::LogicToLogic( GetVisArea().SVRect(), aSrc, aDest );
3307 }
3308 
3309 // Convert a MM100 value realtive to the document root into a pixel value
3310 // realtive to the screen!
3311 Point SwAccessibleMap::LogicToPixel( const Point& rPoint ) const
3312 {
3313 	MapMode aSrc( MAP_100TH_MM );
3314 	MapMode aDest( MAP_TWIP );
3315 
3316     Point aPoint = rPoint;
3317 
3318 	aPoint = OutputDevice::LogicToLogic( aPoint, aSrc, aDest );
3319 	Window *pWin = GetShell()->GetWin();
3320 	if( pWin )
3321     {
3322         // OD 16.01.2003 #103492# - get mapping mode for LogicToPixel conversion
3323         MapMode aMapMode;
3324         GetMapMode( aPoint, aMapMode );
3325         aPoint = pWin->LogicToPixel( aPoint, aMapMode );
3326 		aPoint = pWin->OutputToAbsoluteScreenPixel( aPoint );
3327     }
3328 
3329 	return aPoint;
3330 }
3331 
3332 Size SwAccessibleMap::LogicToPixel( const Size& rSize ) const
3333 {
3334 	MapMode aSrc( MAP_100TH_MM );
3335 	MapMode aDest( MAP_TWIP );
3336 	Size aSize( OutputDevice::LogicToLogic( rSize, aSrc, aDest ) );
3337 	if( GetShell()->GetWin() )
3338     {
3339         // OD 16.01.2003 #103492# - get mapping mode for LogicToPixel conversion
3340         MapMode aMapMode;
3341         GetMapMode( Point(0,0), aMapMode );
3342         aSize = GetShell()->GetWin()->LogicToPixel( aSize, aMapMode );
3343     }
3344 
3345 	return aSize;
3346 }
3347 
3348 Point SwAccessibleMap::PixelToLogic( const Point& rPoint ) const
3349 {
3350 	Point aPoint;
3351 	Window *pWin = GetShell()->GetWin();
3352 	if( pWin )
3353 	{
3354 		aPoint = pWin->ScreenToOutputPixel( rPoint );
3355         // OD 16.01.2003 #103492# - get mapping mode for PixelToLogic conversion
3356         MapMode aMapMode;
3357         GetMapMode( aPoint, aMapMode );
3358         aPoint = pWin->PixelToLogic( aPoint, aMapMode );
3359 		MapMode aSrc( MAP_TWIP );
3360 		MapMode aDest( MAP_100TH_MM );
3361 		aPoint = OutputDevice::LogicToLogic( aPoint, aSrc, aDest );
3362 	}
3363 
3364 	return aPoint;
3365 }
3366 
3367 Size SwAccessibleMap::PixelToLogic( const Size& rSize ) const
3368 {
3369 	Size aSize;
3370 	if( GetShell()->GetWin() )
3371 	{
3372         // OD 16.01.2003 #103492# - get mapping mode for PixelToLogic conversion
3373         MapMode aMapMode;
3374         GetMapMode( Point(0,0), aMapMode );
3375         aSize = GetShell()->GetWin()->PixelToLogic( rSize, aMapMode );
3376 		MapMode aSrc( MAP_TWIP );
3377 		MapMode aDest( MAP_100TH_MM );
3378 		aSize = OutputDevice::LogicToLogic( aSize, aSrc, aDest );
3379 	}
3380 
3381 	return aSize;
3382 }
3383 
3384 sal_Bool SwAccessibleMap::ReplaceChild (
3385         ::accessibility::AccessibleShape* pCurrentChild,
3386 		const uno::Reference< drawing::XShape >& _rxShape,
3387         const long /*_nIndex*/,
3388         const ::accessibility::AccessibleShapeTreeInfo& /*_rShapeTreeInfo*/
3389 	)	throw (uno::RuntimeException)
3390 {
3391 	const SdrObject *pObj = 0;
3392 	{
3393 		vos::OGuard aGuard( maMutex );
3394 		if( mpShapeMap )
3395 		{
3396 			SwAccessibleShapeMap_Impl::const_iterator aIter = mpShapeMap->begin();
3397 			SwAccessibleShapeMap_Impl::const_iterator aEndIter = mpShapeMap->end();
3398 			while( aIter != aEndIter && !pObj )
3399 			{
3400 				uno::Reference < XAccessible > xAcc( (*aIter).second );
3401 				::accessibility::AccessibleShape *pAccShape =
3402 					static_cast < ::accessibility::AccessibleShape* >( xAcc.get() );
3403 				if( pAccShape == pCurrentChild )
3404 				{
3405 					pObj = (*aIter).first;
3406 				}
3407 				++aIter;
3408 			}
3409 		}
3410 	}
3411 	if( !pObj )
3412 		return sal_False;
3413 
3414 	uno::Reference < drawing::XShape > xShape( _rxShape ); //keep reference to shape, because
3415 											 // we might be the only one that
3416 											 // hold it.
3417 	// Also get keep parent.
3418 	uno::Reference < XAccessible > xParent( pCurrentChild->getAccessibleParent() );
3419 	pCurrentChild = 0;	// well be realease by dispose
3420     Dispose( 0, pObj, 0 );
3421 
3422 	{
3423 		vos::OGuard aGuard( maMutex );
3424 
3425 		if( !mpShapeMap )
3426 			mpShapeMap = new SwAccessibleShapeMap_Impl( this );
3427 
3428 		// create the new child
3429 		::accessibility::ShapeTypeHandler& rShapeTypeHandler =
3430 						::accessibility::ShapeTypeHandler::Instance();
3431 		::accessibility::AccessibleShapeInfo aShapeInfo(
3432 											xShape, xParent, this );
3433 		::accessibility::AccessibleShape* pReplacement =
3434 			rShapeTypeHandler.CreateAccessibleObject (
3435 				aShapeInfo, mpShapeMap->GetInfo() );
3436 
3437 		uno::Reference < XAccessible > xAcc( pReplacement );
3438 		if( xAcc.is() )
3439 		{
3440 			pReplacement->Init();
3441 
3442 			SwAccessibleShapeMap_Impl::iterator aIter =
3443 				mpShapeMap->find( pObj );
3444 			if( aIter != mpShapeMap->end() )
3445 			{
3446 				(*aIter).second = xAcc;
3447 			}
3448 			else
3449 			{
3450 				SwAccessibleShapeMap_Impl::value_type aEntry( pObj, xAcc );
3451 				mpShapeMap->insert( aEntry );
3452 			}
3453 		}
3454 	}
3455 
3456 	SwRect aEmptyRect;
3457     InvalidatePosOrSize( 0, pObj, 0, aEmptyRect );
3458 
3459 	return sal_True;
3460 }
3461 
3462 //IAccessibility2 Implementation 2009-----
3463 //Get the accessible control shape from the model object, here model object is with XPropertySet type
3464 ::accessibility::AccessibleControlShape * SwAccessibleMap::GetAccControlShapeFromModel(::com::sun::star::beans::XPropertySet* pSet) throw (::com::sun::star::uno::RuntimeException)
3465 {
3466 	if( mpShapeMap )
3467 	{
3468 		SwAccessibleShapeMap_Impl::const_iterator aIter = mpShapeMap->begin();
3469 		SwAccessibleShapeMap_Impl::const_iterator aEndIter = mpShapeMap->end();
3470 		while( aIter != aEndIter)
3471 		{
3472 			uno::Reference < XAccessible > xAcc( (*aIter).second );
3473 			::accessibility::AccessibleShape *pAccShape =
3474 				static_cast < ::accessibility::AccessibleShape* >( xAcc.get() );
3475 			if(pAccShape && ::accessibility::ShapeTypeHandler::Instance().GetTypeId (pAccShape->GetXShape()) == ::accessibility::DRAWING_CONTROL)
3476 			{
3477 				::accessibility::AccessibleControlShape *pCtlAccShape = static_cast < ::accessibility::AccessibleControlShape* >(pAccShape);
3478 				if (pCtlAccShape && pCtlAccShape->GetControlModel() == pSet)
3479 					return pCtlAccShape;
3480 			}
3481 			++aIter;
3482 		}
3483 	}
3484 	return NULL;
3485 }
3486 
3487 ::com::sun::star::uno::Reference< XAccessible >
3488     SwAccessibleMap::GetAccessibleCaption (const ::com::sun::star::uno::Reference< ::com::sun::star::drawing::XShape >& xShape)
3489     throw (::com::sun::star::uno::RuntimeException)
3490 {
3491 		SdrObject* captionedObject = GetSdrObjectFromXShape(xShape);
3492 
3493 		SwDrawContact *pContact = (SwDrawContact*)GetUserCall( captionedObject );
3494 		ASSERT( RES_DRAWFRMFMT == pContact->GetFmt()->Which(),
3495 				"fail" );
3496 		if( !pContact )
3497 			return 0;
3498 
3499 		SwDrawFrmFmt *pCaptionedFmt = (SwDrawFrmFmt *)pContact->GetFmt();
3500 		if( !pCaptionedFmt )
3501 			return 0;
3502 
3503 		SwFlyFrm* pFrm = NULL;
3504 		if (pCaptionedFmt->HasCaption())
3505 		{
3506 			const SwFrmFmt *pCaptionFrmFmt = pCaptionedFmt->GetCaptionFmt();
3507 			SwClientIter aIter (*(SwModify*)pCaptionFrmFmt);
3508 			pFrm = (SwFlyFrm*)aIter.First( TYPE ( SwFlyFrm ));
3509 		}
3510 		if (!pFrm)
3511 			return 0;
3512 		//SwFrmFmt* pFrm = pCaptionedFmt->GetCaptionFmt();
3513 		uno::Reference < XAccessible > xAcc( GetContext((SwFrm*)pFrm,sal_True) );
3514 		//Reference < XAccessibleShape > xAccShape( xAcc, UNO_QUERY );
3515 
3516 		uno::Reference< XAccessibleContext > xAccContext = xAcc->getAccessibleContext();
3517 		if( xAccContext.is() )
3518 		{	//get the parent of caption frame, which is paragaph
3519 			uno::Reference< XAccessible > xAccParent = xAccContext->getAccessibleParent();
3520 			if(xAccParent.is())
3521 			{
3522 				//get the great parent of caption frame which is text frame.
3523 				uno::Reference< XAccessibleContext > xAccParentContext = xAccParent->getAccessibleContext();
3524 				uno::Reference< XAccessible > xAccGreatParent = xAccParentContext->getAccessibleParent();
3525 				if(xAccGreatParent.is())
3526 				{
3527 					AccessibleEventObject aEvent;
3528 					aEvent.EventId = AccessibleEventId::CHILD;
3529 					aEvent.NewValue <<= xAccParent;
3530 					( static_cast< SwAccessibleContext * >(xAccGreatParent.get()) )->FireAccessibleEvent( aEvent );
3531 
3532 				}
3533 
3534 				AccessibleEventObject aEvent;
3535 				aEvent.EventId = AccessibleEventId::CHILD;
3536 				aEvent.NewValue <<= xAcc;
3537 				( static_cast< SwAccessibleContext * >(xAccParent.get()) )->FireAccessibleEvent( aEvent );
3538 			}
3539 		}
3540 
3541 		if(xAcc.get())
3542 			return xAcc;
3543 		else
3544 			return NULL;
3545 
3546 }
3547 //-----IAccessibility2 Implementation 2009
3548 Point SwAccessibleMap::PixelToCore( const Point& rPoint ) const
3549 {
3550 	Point aPoint;
3551 	if( GetShell()->GetWin() )
3552 	{
3553         // OD 15.01.2003 #103492# - replace <PreviewAdjust(..)> by <GetMapMode(..)>
3554         MapMode aMapMode;
3555         GetMapMode( rPoint, aMapMode );
3556         aPoint = GetShell()->GetWin()->PixelToLogic( rPoint, aMapMode );
3557 	}
3558 	return aPoint;
3559 }
3560 
3561 static inline long lcl_CorrectCoarseValue(long aCoarseValue, long aFineValue,
3562                                           long aRefValue, bool bToLower)
3563 {
3564     long aResult = aCoarseValue;
3565 
3566     if (bToLower)
3567     {
3568         if (aFineValue < aRefValue)
3569             aResult -= 1;
3570     }
3571     else
3572     {
3573         if (aFineValue > aRefValue)
3574             aResult += 1;
3575     }
3576 
3577     return aResult;
3578 }
3579 
3580 static inline void lcl_CorrectRectangle(Rectangle & rRect,
3581                                         const Rectangle & rSource,
3582                                         const Rectangle & rInGrid)
3583 {
3584     rRect.nLeft = lcl_CorrectCoarseValue(rRect.nLeft, rSource.nLeft,
3585                                          rInGrid.nLeft, false);
3586     rRect.nTop = lcl_CorrectCoarseValue(rRect.nTop, rSource.nTop,
3587                                         rInGrid.nTop, false);
3588     rRect.nRight = lcl_CorrectCoarseValue(rRect.nRight, rSource.nRight,
3589                                           rInGrid.nRight, true);
3590     rRect.nBottom = lcl_CorrectCoarseValue(rRect.nBottom, rSource.nBottom,
3591                                            rInGrid.nBottom, true);
3592 }
3593 
3594 Rectangle SwAccessibleMap::CoreToPixel( const Rectangle& rRect ) const
3595 {
3596     Rectangle aRect;
3597 	if( GetShell()->GetWin() )
3598     {
3599         // OD 15.01.2003 #103492# - replace <PreviewAdjust(..)> by <GetMapMode(..)>
3600         MapMode aMapMode;
3601         GetMapMode( rRect.TopLeft(), aMapMode );
3602         aRect = GetShell()->GetWin()->LogicToPixel( rRect, aMapMode );
3603 
3604         Rectangle aTmpRect = GetShell()->GetWin()->PixelToLogic( aRect, aMapMode );
3605         lcl_CorrectRectangle(aRect, rRect, aTmpRect);
3606     }
3607 
3608 	return aRect;
3609 }
3610 
3611 /** get mapping mode for LogicToPixel and PixelToLogic conversions
3612 
3613     OD 15.01.2003 #103492#
3614     Replacement method <PreviewAdjust(..)> by new method <GetMapMode>.
3615     Method returns mapping mode of current output device and adjusts it,
3616     if the shell is in page/print preview.
3617     Necessary, because <PreviewAdjust(..)> changes mapping mode at current
3618     output device for mapping logic document positions to page preview window
3619     positions and vice versa and doesn't take care to recover its changes.
3620 
3621     @author OD
3622 */
3623 void SwAccessibleMap::GetMapMode( const Point& _rPoint,
3624                                   MapMode&     _orMapMode ) const
3625 {
3626     MapMode aMapMode = GetShell()->GetWin()->GetMapMode();
3627     if( GetShell()->IsPreView() )
3628     {
3629         DBG_ASSERT( mpPreview != NULL, "need preview data" );
3630 
3631         mpPreview->AdjustMapMode( aMapMode, _rPoint );
3632     }
3633     _orMapMode = aMapMode;
3634 }
3635 
3636 /** get size of a dedicated preview page
3637 
3638     OD 15.01.2003 #103492#
3639 
3640     @author OD
3641 */
3642 Size SwAccessibleMap::GetPreViewPageSize( sal_uInt16 _nPrevwPageNum ) const
3643 {
3644     DBG_ASSERT( mpVSh->IsPreView(), "no page preview accessible." );
3645     DBG_ASSERT( mpVSh->IsPreView() && ( mpPreview != NULL ),
3646                 "missing accessible preview data at page preview" );
3647     if ( mpVSh->IsPreView() && ( mpPreview != NULL ) )
3648     {
3649         return mpVSh->PagePreviewLayout()->GetPrevwPageSizeByPageNum( _nPrevwPageNum );
3650     }
3651     else
3652     {
3653         return Size( 0, 0 );
3654     }
3655 }
3656 
3657 /** method to build up a new data structure of the accessible pararaphs,
3658     which have a selection
3659 
3660     OD 2005-12-13 #i27301#
3661     Important note: method has to used inside a mutual exclusive section
3662 
3663     @author OD
3664 */
3665 SwAccessibleSelectedParas_Impl* SwAccessibleMap::_BuildSelectedParas()
3666 {
3667     // no accessible contexts, no selection
3668     if ( !mpFrmMap )
3669     {
3670         return 0L;
3671     }
3672 
3673     // get cursor as an instance of its base class <SwPaM>
3674     SwPaM* pCrsr( 0L );
3675     {
3676         SwCrsrShell* pCrsrShell = dynamic_cast<SwCrsrShell*>(GetShell());
3677         if ( pCrsrShell )
3678         {
3679             SwFEShell* pFEShell = dynamic_cast<SwFEShell*>(pCrsrShell);
3680             if ( !pFEShell ||
3681                  ( !pFEShell->IsFrmSelected() &&
3682                    pFEShell->IsObjSelected() == 0 ) )
3683             {
3684                 // get cursor without updating an existing table cursor.
3685                 pCrsr = pCrsrShell->GetCrsr( sal_False );
3686             }
3687         }
3688     }
3689     // no cursor, no selection
3690     if ( !pCrsr )
3691     {
3692         return 0L;
3693     }
3694 
3695     SwAccessibleSelectedParas_Impl* pRetSelectedParas( 0L );
3696 
3697     // loop on all cursors
3698     SwPaM* pRingStart = pCrsr;
3699     do {
3700 
3701         // for a selection the cursor has to have a mark.
3702         // for savety reasons assure that point and mark are in text nodes
3703         if ( pCrsr->HasMark() &&
3704              pCrsr->GetPoint()->nNode.GetNode().IsTxtNode() &&
3705              pCrsr->GetMark()->nNode.GetNode().IsTxtNode() )
3706         {
3707             SwPosition* pStartPos = pCrsr->Start();
3708             SwPosition* pEndPos = pCrsr->End();
3709             // loop on all text nodes inside the selection
3710             SwNodeIndex aIdx( pStartPos->nNode );
3711             for ( ; aIdx.GetIndex() <= pEndPos->nNode.GetIndex(); ++aIdx )
3712             {
3713                 SwTxtNode* pTxtNode( aIdx.GetNode().GetTxtNode() );
3714                 if ( pTxtNode )
3715                 {
3716                     // loop on all text frames registered at the text node.
3717                     SwIterator<SwTxtFrm,SwTxtNode> aIter( *pTxtNode );
3718                     for( SwTxtFrm* pTxtFrm = aIter.First(); pTxtFrm; pTxtFrm = aIter.Next() )
3719                         {
3720                             uno::WeakReference < XAccessible > xWeakAcc;
3721                             SwAccessibleContextMap_Impl::iterator aMapIter =
3722                                                     mpFrmMap->find( pTxtFrm );
3723                             if( aMapIter != mpFrmMap->end() )
3724                             {
3725                                 xWeakAcc = (*aMapIter).second;
3726                                 SwAccessibleParaSelection aDataEntry(
3727                                     pTxtNode == &(pStartPos->nNode.GetNode())
3728                                                 ? pStartPos->nContent.GetIndex()
3729                                                 : 0,
3730                                     pTxtNode == &(pEndPos->nNode.GetNode())
3731                                                 ? pEndPos->nContent.GetIndex()
3732                                                 : STRING_LEN );
3733                                 SwAccessibleSelectedParas_Impl::value_type
3734                                                 aEntry( xWeakAcc, aDataEntry );
3735                                 if ( !pRetSelectedParas )
3736                                 {
3737                                     pRetSelectedParas =
3738                                             new SwAccessibleSelectedParas_Impl;
3739                                 }
3740                                 pRetSelectedParas->insert( aEntry );
3741                             }
3742                         }
3743                     }
3744                 }
3745             }
3746 
3747         // prepare next turn: get next cursor in ring
3748         pCrsr = static_cast<SwPaM*>( pCrsr->GetNext() );
3749     } while ( pCrsr != pRingStart );
3750 
3751     return pRetSelectedParas;
3752 }
3753 
3754 /** invalidation of text selection of all paragraphs
3755 
3756     OD 2005-12-13 #i27301#
3757 
3758     @author OD
3759 */
3760 void SwAccessibleMap::InvalidateTextSelectionOfAllParas()
3761 {
3762     vos::OGuard aGuard( maMutex );
3763 
3764     // keep previously known selected paragraphs
3765     SwAccessibleSelectedParas_Impl* pPrevSelectedParas( mpSelectedParas );
3766 
3767     // determine currently selected paragraphs
3768     mpSelectedParas = _BuildSelectedParas();
3769 
3770     // compare currently selected paragraphs with the previously selected
3771     // paragraphs and submit corresponding TEXT_SELECTION_CHANGED events.
3772     // first, search for new and changed selections.
3773     // on the run remove selections from previously known ones, if they are
3774     // also in the current ones.
3775     if ( mpSelectedParas )
3776     {
3777         SwAccessibleSelectedParas_Impl::iterator aIter = mpSelectedParas->begin();
3778         for ( ; aIter != mpSelectedParas->end(); ++aIter )
3779         {
3780             bool bSubmitEvent( false );
3781             if ( !pPrevSelectedParas )
3782             {
3783                 // new selection
3784                 bSubmitEvent = true;
3785             }
3786             else
3787             {
3788                 SwAccessibleSelectedParas_Impl::iterator aPrevSelected =
3789                                         pPrevSelectedParas->find( (*aIter).first );
3790                 if ( aPrevSelected != pPrevSelectedParas->end() )
3791                 {
3792                     // check, if selection has changed
3793                     if ( (*aIter).second.nStartOfSelection !=
3794                                     (*aPrevSelected).second.nStartOfSelection ||
3795                          (*aIter).second.nEndOfSelection !=
3796                                     (*aPrevSelected).second.nEndOfSelection )
3797                     {
3798                         // changed selection
3799                         bSubmitEvent = true;
3800                     }
3801                     pPrevSelectedParas->erase( aPrevSelected );
3802                 }
3803                 else
3804                 {
3805                     // new selection
3806                     bSubmitEvent = true;
3807                 }
3808             }
3809 
3810             if ( bSubmitEvent )
3811             {
3812                 uno::Reference < XAccessible > xAcc( (*aIter).first );
3813                 if ( xAcc.is() )
3814                 {
3815                     ::vos::ORef < SwAccessibleContext > xAccImpl(
3816                                 static_cast<SwAccessibleContext*>( xAcc.get() ) );
3817                     if ( xAccImpl.isValid() && xAccImpl->GetFrm() )
3818                     {
3819                         const SwTxtFrm* pTxtFrm(
3820                             dynamic_cast<const SwTxtFrm*>(xAccImpl->GetFrm()) );
3821                         ASSERT( pTxtFrm,
3822                                 "<SwAccessibleMap::_SubmitTextSelectionChangedEvents()> - unexcepted type of frame" );
3823                         if ( pTxtFrm )
3824                         {
3825                             InvalidateParaTextSelection( *pTxtFrm );
3826                         }
3827                     }
3828                 }
3829             }
3830         }
3831     }
3832 
3833     // second, handle previous selections - after the first step the data
3834     // structure of the previously known only contains the 'old' selections
3835     if ( pPrevSelectedParas )
3836     {
3837         SwAccessibleSelectedParas_Impl::iterator aIter = pPrevSelectedParas->begin();
3838         for ( ; aIter != pPrevSelectedParas->end(); ++aIter )
3839         {
3840             uno::Reference < XAccessible > xAcc( (*aIter).first );
3841             if ( xAcc.is() )
3842             {
3843                 ::vos::ORef < SwAccessibleContext > xAccImpl(
3844                             static_cast<SwAccessibleContext*>( xAcc.get() ) );
3845                 if ( xAccImpl.isValid() && xAccImpl->GetFrm() )
3846                 {
3847                     const SwTxtFrm* pTxtFrm(
3848                             dynamic_cast<const SwTxtFrm*>(xAccImpl->GetFrm()) );
3849                     ASSERT( pTxtFrm,
3850                             "<SwAccessibleMap::_SubmitTextSelectionChangedEvents()> - unexcepted type of frame" );
3851                     if ( pTxtFrm )
3852                     {
3853                         InvalidateParaTextSelection( *pTxtFrm );
3854                     }
3855                 }
3856             }
3857         }
3858 
3859         delete pPrevSelectedParas;
3860     }
3861 }
3862 
3863 const SwRect& SwAccessibleMap::GetVisArea() const
3864 {
3865     DBG_ASSERT( !GetShell()->IsPreView() || (mpPreview != NULL),
3866                 "preview without preview data?" );
3867 
3868     return GetShell()->IsPreView()
3869            ? mpPreview->GetVisArea()
3870            : GetShell()->VisArea();
3871 }
3872 
3873 //IAccessibility2 Implementation 2009-----
3874 sal_Bool SwAccessibleMap::IsDocumentSelAll()
3875 {
3876 	return GetShell()->GetDoc()->IsPrepareSelAll();
3877 }
3878 //-----IAccessibility2 Implementation 2009
3879 
3880