xref: /AOO41X/main/sw/source/core/access/accdoc.cxx (revision 4d7c9de063a797b8b4f3d45e3561e82ad1f8ef1f)
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 #include <vcl/window.hxx>
27 #include <rootfrm.hxx>
28 
29 
30 #include <com/sun/star/accessibility/AccessibleRole.hpp>
31 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
32 #include <com/sun/star/beans/XPropertyChangeListener.hpp>
33 #include <com/sun/star/accessibility/AccessibleEventId.hpp>
34 #include <unotools/accessiblestatesethelper.hxx>
35 #include <tools/link.hxx>
36 #include <sfx2/viewsh.hxx>
37 #include <vos/mutex.hxx>
38 #include <vcl/svapp.hxx>
39 #include <viewsh.hxx>
40 #include <doc.hxx>
41 #include <accmap.hxx>
42 #include <accdoc.hxx>
43 #ifndef _ACCESS_HRC
44 #include "access.hrc"
45 #endif
46 #include <pagefrm.hxx>
47 
48 #include <editeng/brshitem.hxx>
49 #include <swatrset.hxx>
50 #include <frmatr.hxx>
51 #include "unostyle.hxx"
52 #include "viewsh.hxx"
53 #include "docsh.hxx"
54 #include <crsrsh.hxx>
55 #include "fesh.hxx"
56 #include <fmtclds.hxx>
57 #include <flyfrm.hxx>
58 #include <colfrm.hxx>
59 #include <txtfrm.hxx>
60 #include <sectfrm.hxx>
61 #include <section.hxx>
62 #include <svx/unoapi.hxx>
63 #include <swmodule.hxx>
64 #include <svtools/colorcfg.hxx>
65 
66 #include <fmtanchr.hxx>
67 #include <viewimp.hxx>
68 #include <dview.hxx>
69 #include <dcontact.hxx>
70 #include <svx/svdmark.hxx>
71 const sal_Char sServiceName[] = "com.sun.star.text.AccessibleTextDocumentView";
72 const sal_Char sImplementationName[] = "com.sun.star.comp.Writer.SwAccessibleDocumentView";
73 
74 
75 using namespace ::com::sun::star;
76 using namespace ::com::sun::star::accessibility;
77 using ::rtl::OUString;
78 
79 using lang::IndexOutOfBoundsException;
80 
81 
82 
83 //
84 // SwAccessibleDocumentBase: base class for SwAccessibleDocument and
85 // SwAccessiblePreview
86 //
87 
SwAccessibleDocumentBase(SwAccessibleMap * _pMap)88 SwAccessibleDocumentBase::SwAccessibleDocumentBase ( SwAccessibleMap *_pMap ) :
89     SwAccessibleContext( _pMap, AccessibleRole::DOCUMENT,
90                          _pMap->GetShell()->GetLayout() ),//swmod 071107//swmod 071225
91     mxParent( _pMap->GetShell()->GetWin()->GetAccessibleParentWindow()->GetAccessible() ),
92     mpChildWin( 0 )
93 {
94 }
95 
~SwAccessibleDocumentBase()96 SwAccessibleDocumentBase::~SwAccessibleDocumentBase()
97 {
98 }
99 
SetVisArea()100 void SwAccessibleDocumentBase::SetVisArea()
101 {
102     vos::OGuard aGuard(Application::GetSolarMutex());
103 
104     SwRect aOldVisArea( GetVisArea() );
105     const SwRect& rNewVisArea = GetMap()->GetVisArea();
106     if( aOldVisArea != rNewVisArea )
107     {
108         SwAccessibleFrame::SetVisArea( GetMap()->GetVisArea() );
109         // --> OD 2007-12-07 #i58139#
110         // showing state of document view needs also be updated.
111         // Thus, call method <Scrolled(..)> instead of <ChildrenScrolled(..)>
112 //        ChildrenScrolled( GetFrm(), aOldVisArea );
113         Scrolled( aOldVisArea );
114         // <--
115     }
116 }
117 
AddChild(Window * pWin,sal_Bool bFireEvent)118 void SwAccessibleDocumentBase::AddChild( Window *pWin, sal_Bool bFireEvent )
119 {
120     vos::OGuard aGuard(Application::GetSolarMutex());
121 
122     ASSERT( !mpChildWin, "only one child window is supported" );
123     if( !mpChildWin )
124     {
125         mpChildWin = pWin;
126 
127         if( bFireEvent )
128         {
129             AccessibleEventObject aEvent;
130             aEvent.EventId = AccessibleEventId::CHILD;
131             aEvent.NewValue <<= mpChildWin->GetAccessible();
132             FireAccessibleEvent( aEvent );
133         }
134     }
135 }
136 
RemoveChild(Window * pWin)137 void SwAccessibleDocumentBase::RemoveChild( Window *pWin )
138 {
139     vos::OGuard aGuard(Application::GetSolarMutex());
140 
141     ASSERT( !mpChildWin || pWin == mpChildWin, "invalid child window to remove" );
142     if( mpChildWin && pWin == mpChildWin )
143     {
144         AccessibleEventObject aEvent;
145         aEvent.EventId = AccessibleEventId::CHILD;
146         aEvent.OldValue <<= mpChildWin->GetAccessible();
147         FireAccessibleEvent( aEvent );
148 
149         mpChildWin = 0;
150     }
151 }
152 
getAccessibleChildCount(void)153 sal_Int32 SAL_CALL SwAccessibleDocumentBase::getAccessibleChildCount( void )
154         throw (uno::RuntimeException)
155 {
156     vos::OGuard aGuard(Application::GetSolarMutex());
157 
158     // CHECK_FOR_DEFUNC is called by parent
159 
160     sal_Int32 nChildren = SwAccessibleContext::getAccessibleChildCount();
161     if( !IsDisposing() && mpChildWin )
162         nChildren++;
163 
164     return nChildren;
165 }
166 
167 uno::Reference< XAccessible> SAL_CALL
getAccessibleChild(sal_Int32 nIndex)168     SwAccessibleDocumentBase::getAccessibleChild( sal_Int32 nIndex )
169         throw (uno::RuntimeException,
170                 lang::IndexOutOfBoundsException)
171 {
172     vos::OGuard aGuard(Application::GetSolarMutex());
173 
174     if( mpChildWin  )
175     {
176         CHECK_FOR_DEFUNC( XAccessibleContext )
177         if ( nIndex == GetChildCount( *(GetMap()) ) )
178         {
179             return mpChildWin->GetAccessible();
180         }
181     }
182 
183     return SwAccessibleContext::getAccessibleChild( nIndex );
184 }
185 
186 
getAccessibleParent(void)187 uno::Reference< XAccessible> SAL_CALL SwAccessibleDocumentBase::getAccessibleParent (void)
188         throw (uno::RuntimeException)
189 {
190     return mxParent;
191 }
192 
getAccessibleIndexInParent(void)193 sal_Int32 SAL_CALL SwAccessibleDocumentBase::getAccessibleIndexInParent (void)
194         throw (uno::RuntimeException)
195 {
196     vos::OGuard aGuard(Application::GetSolarMutex());
197 
198     uno::Reference < XAccessibleContext > xAcc( mxParent->getAccessibleContext() );
199     uno::Reference < XAccessible > xThis( this );
200     sal_Int32 nCount = xAcc->getAccessibleChildCount();
201 
202     for( sal_Int32 i=0; i < nCount; i++ )
203     {
204         try
205         {
206             if( xAcc->getAccessibleChild( i ) == xThis )
207                 return i;
208         }
209         catch(::com::sun::star::lang::IndexOutOfBoundsException e)
210         {
211             return -1L;
212         }
213     }
214     return -1L;
215 }
216 
getAccessibleDescription(void)217 OUString SAL_CALL SwAccessibleDocumentBase::getAccessibleDescription (void)
218     throw (uno::RuntimeException)
219 {
220     return GetResource( STR_ACCESS_DOC_DESC );
221 }
222 
getAccessibleName(void)223 OUString SAL_CALL SwAccessibleDocumentBase::getAccessibleName (void)
224         throw (::com::sun::star::uno::RuntimeException)
225 {
226     OUString sAccName = GetResource( STR_ACCESS_DOC_WORDPROCESSING );
227     SwDoc *pDoc = GetShell()->GetDoc();
228     if ( pDoc )
229     {
230         OUString sFileName = pDoc->getDocAccTitle();
231         if ( !sFileName.getLength() )
232         {
233             SwDocShell* pDocSh = pDoc->GetDocShell();
234             if ( pDocSh )
235             {
236                 sFileName = pDocSh->GetTitle( SFX_TITLE_APINAME );
237             }
238         }
239         OUString sReadOnly;
240         if(pDoc->getDocReadOnly())
241         {
242             sReadOnly = GetResource( STR_ACCESS_DOC_WORDPROCESSING_READONLY );
243         }
244 
245         if ( sFileName.getLength() )
246         {
247             sAccName = sFileName + sReadOnly + OUString(RTL_CONSTASCII_USTRINGPARAM(" - ")) + sAccName;
248         }
249     }
250 
251     return sAccName;
252 }
253 
getBounds()254 awt::Rectangle SAL_CALL SwAccessibleDocumentBase::getBounds()
255         throw (uno::RuntimeException)
256 {
257     try
258     {
259         vos::OGuard aGuard(Application::GetSolarMutex());
260 
261         Window *pWin = GetWindow();
262 
263         CHECK_FOR_WINDOW( XAccessibleComponent, pWin )
264 
265             Rectangle aPixBounds( pWin->GetWindowExtentsRelative( pWin->GetAccessibleParentWindow() ) );
266         awt::Rectangle aBox( aPixBounds.Left(), aPixBounds.Top(),
267             aPixBounds.GetWidth(), aPixBounds.GetHeight() );
268 
269         return aBox;
270     }
271     catch(::com::sun::star::lang::IndexOutOfBoundsException e)
272     {
273         return awt::Rectangle();
274     }
275 }
276 
277 
getLocation()278 awt::Point SAL_CALL SwAccessibleDocumentBase::getLocation()
279         throw (uno::RuntimeException)
280 {
281     vos::OGuard aGuard(Application::GetSolarMutex());
282 
283     Window *pWin = GetWindow();
284 
285     CHECK_FOR_WINDOW( XAccessibleComponent, pWin )
286 
287     Point aPixPos( pWin->GetWindowExtentsRelative( pWin->GetAccessibleParentWindow() ).TopLeft() );
288     awt::Point aLoc( aPixPos.X(), aPixPos.Y() );
289 
290     return aLoc;
291 }
292 
293 
getLocationOnScreen()294 ::com::sun::star::awt::Point SAL_CALL SwAccessibleDocumentBase::getLocationOnScreen()
295         throw (uno::RuntimeException)
296 {
297     vos::OGuard aGuard(Application::GetSolarMutex());
298 
299     Window *pWin = GetWindow();
300 
301     CHECK_FOR_WINDOW( XAccessibleComponent, pWin )
302 
303     Point aPixPos( pWin->GetWindowExtentsRelative( 0 ).TopLeft() );
304     awt::Point aLoc( aPixPos.X(), aPixPos.Y() );
305 
306     return aLoc;
307 }
308 
309 
getSize()310 ::com::sun::star::awt::Size SAL_CALL SwAccessibleDocumentBase::getSize()
311         throw (uno::RuntimeException)
312 {
313     vos::OGuard aGuard(Application::GetSolarMutex());
314 
315     Window *pWin = GetWindow();
316 
317     CHECK_FOR_WINDOW( XAccessibleComponent, pWin )
318 
319     Size aPixSize( pWin->GetWindowExtentsRelative( 0 ).GetSize() );
320     awt::Size aSize( aPixSize.Width(), aPixSize.Height() );
321 
322     return aSize;
323 }
324 
containsPoint(const awt::Point & aPoint)325 sal_Bool SAL_CALL SwAccessibleDocumentBase::containsPoint(
326             const awt::Point& aPoint )
327         throw (uno::RuntimeException)
328 {
329     vos::OGuard aGuard(Application::GetSolarMutex());
330 
331     Window *pWin = GetWindow();
332 
333     CHECK_FOR_WINDOW( XAccessibleComponent, pWin )
334 
335     Rectangle aPixBounds( pWin->GetWindowExtentsRelative( 0 ) );
336     aPixBounds.Move(-aPixBounds.Left(), -aPixBounds.Top());
337 
338     Point aPixPoint( aPoint.X, aPoint.Y );
339     return aPixBounds.IsInside( aPixPoint );
340 }
341 
getAccessibleAtPoint(const awt::Point & aPoint)342 uno::Reference< XAccessible > SAL_CALL SwAccessibleDocumentBase::getAccessibleAtPoint(
343                 const awt::Point& aPoint )
344         throw (uno::RuntimeException)
345 {
346     vos::OGuard aGuard(Application::GetSolarMutex());
347 
348     if( mpChildWin  )
349     {
350         CHECK_FOR_DEFUNC( XAccessibleComponent )
351 
352         Window *pWin = GetWindow();
353         CHECK_FOR_WINDOW( XAccessibleComponent, pWin )
354 
355         Point aPixPoint( aPoint.X, aPoint.Y ); // px rel to window
356         if( mpChildWin->GetWindowExtentsRelative( pWin ).IsInside( aPixPoint ) )
357             return mpChildWin->GetAccessible();
358     }
359 
360     return SwAccessibleContext::getAccessibleAtPoint( aPoint );
361 }
362 
363 //
364 // SwAccessibeDocument
365 //
366 
GetStates(::utl::AccessibleStateSetHelper & rStateSet)367 void SwAccessibleDocument::GetStates(
368         ::utl::AccessibleStateSetHelper& rStateSet )
369 {
370     SwAccessibleContext::GetStates( rStateSet );
371 
372     // MULTISELECTABLE
373     rStateSet.AddState( AccessibleStateType::MULTI_SELECTABLE );
374     rStateSet.AddState( AccessibleStateType::MANAGES_DESCENDANTS );
375 }
376 
377 
SwAccessibleDocument(SwAccessibleMap * pInitMap)378 SwAccessibleDocument::SwAccessibleDocument ( SwAccessibleMap* pInitMap ) :
379     SwAccessibleDocumentBase( pInitMap ),
380     maSelectionHelper( *this )
381 {
382     SetName( GetResource( STR_ACCESS_DOC_NAME ) );
383     Window *pWin = pInitMap->GetShell()->GetWin();
384     if( pWin )
385     {
386         pWin->AddChildEventListener( LINK( this, SwAccessibleDocument, WindowChildEventListener ));
387         sal_uInt16 nCount =   pWin->GetChildCount();
388         for( sal_uInt16 i=0; i < nCount; i++ )
389         {
390             Window* pChildWin = pWin->GetChild( i );
391             if( pChildWin &&
392                 AccessibleRole::EMBEDDED_OBJECT == pChildWin->GetAccessibleRole() )
393                 AddChild( pChildWin, sal_False );
394         }
395     }
396 }
397 
~SwAccessibleDocument()398 SwAccessibleDocument::~SwAccessibleDocument()
399 {
400     Window *pWin = GetMap() ? GetMap()->GetShell()->GetWin() : 0;
401     if( pWin )
402         pWin->RemoveChildEventListener( LINK( this, SwAccessibleDocument, WindowChildEventListener ));
403 }
404 
Dispose(sal_Bool bRecursive)405 void SwAccessibleDocument::Dispose( sal_Bool bRecursive )
406 {
407     ASSERT( GetFrm() && GetMap(), "already disposed" );
408 
409     Window *pWin = GetMap() ? GetMap()->GetShell()->GetWin() : 0;
410     if( pWin )
411         pWin->RemoveChildEventListener( LINK( this, SwAccessibleDocument, WindowChildEventListener ));
412     SwAccessibleContext::Dispose( bRecursive );
413 }
414 
IMPL_LINK(SwAccessibleDocument,WindowChildEventListener,VclSimpleEvent *,pEvent)415 IMPL_LINK( SwAccessibleDocument, WindowChildEventListener, VclSimpleEvent*, pEvent )
416 {
417     DBG_ASSERT( pEvent && pEvent->ISA( VclWindowEvent ), "Unknown WindowEvent!" );
418     if ( pEvent && pEvent->ISA( VclWindowEvent ) )
419     {
420         VclWindowEvent *pVclEvent = static_cast< VclWindowEvent * >( pEvent );
421         DBG_ASSERT( pVclEvent->GetWindow(), "Window???" );
422         switch ( pVclEvent->GetId() )
423         {
424         case VCLEVENT_WINDOW_SHOW:  // send create on show for direct accessible children
425             {
426                 Window* pChildWin = static_cast< Window* >( pVclEvent->GetData() );
427                 if( pChildWin && AccessibleRole::EMBEDDED_OBJECT == pChildWin->GetAccessibleRole() )
428                 {
429                     AddChild( pChildWin );
430                 }
431             }
432             break;
433         case VCLEVENT_WINDOW_HIDE:  // send destroy on hide for direct accessible children
434             {
435                 Window* pChildWin = static_cast< Window* >( pVclEvent->GetData() );
436                 if( pChildWin && AccessibleRole::EMBEDDED_OBJECT == pChildWin->GetAccessibleRole() )
437                 {
438                     RemoveChild( pChildWin );
439                 }
440             }
441             break;
442         case VCLEVENT_OBJECT_DYING:  // send destroy on hide for direct accessible children
443             {
444                 Window* pChildWin = pVclEvent->GetWindow();
445                 if( pChildWin && AccessibleRole::EMBEDDED_OBJECT == pChildWin->GetAccessibleRole() )
446                 {
447                     RemoveChild( pChildWin );
448                 }
449             }
450             break;
451         }
452     }
453     return 0;
454 }
455 
456 
getImplementationName()457 OUString SAL_CALL SwAccessibleDocument::getImplementationName()
458         throw( uno::RuntimeException )
459 {
460     return OUString(RTL_CONSTASCII_USTRINGPARAM(sImplementationName));
461 }
462 
supportsService(const::rtl::OUString & sTestServiceName)463 sal_Bool SAL_CALL SwAccessibleDocument::supportsService(
464         const ::rtl::OUString& sTestServiceName)
465     throw (uno::RuntimeException)
466 {
467     return sTestServiceName.equalsAsciiL( sServiceName,
468                                           sizeof(sServiceName)-1 ) ||
469            sTestServiceName.equalsAsciiL( sAccessibleServiceName,
470                                           sizeof(sAccessibleServiceName)-1 );
471 }
472 
getSupportedServiceNames()473 uno::Sequence< OUString > SAL_CALL SwAccessibleDocument::getSupportedServiceNames()
474         throw( uno::RuntimeException )
475 {
476     uno::Sequence< OUString > aRet(2);
477     OUString* pArray = aRet.getArray();
478     pArray[0] = OUString( RTL_CONSTASCII_USTRINGPARAM(sServiceName) );
479     pArray[1] = OUString( RTL_CONSTASCII_USTRINGPARAM(sAccessibleServiceName) );
480     return aRet;
481 }
482 
483 //=====  XInterface  ======================================================
484 
queryInterface(const uno::Type & rType)485 uno::Any SwAccessibleDocument::queryInterface(
486     const uno::Type& rType )
487     throw ( uno::RuntimeException )
488 {
489     uno::Any aRet;
490     if ( rType == ::getCppuType( static_cast< uno::Reference< XAccessibleSelection > * >( 0 ) ) )
491     {
492         uno::Reference<XAccessibleSelection> aSelect = this;
493         aRet <<= aSelect;
494     }
495     //Solution:Add XEventListener interface support.
496     else if ( (rType == ::getCppuType((uno::Reference<com::sun::star::document::XEventListener> *)NULL)) )
497     {
498         uno::Reference<com::sun::star::document::XEventListener> aSelect = this;
499         aRet <<= aSelect;
500     }
501     else  if ( rType == ::getCppuType((uno::Reference<XAccessibleExtendedAttributes> *)NULL) )
502     {
503         uno::Reference<XAccessibleExtendedAttributes> aAttribute = this;
504         aRet <<= aAttribute;
505     }
506     else if(rType == ::getCppuType((uno::Reference<XAccessibleGetAccFlowTo> *)NULL) )
507     {
508         uno::Reference<XAccessibleGetAccFlowTo> AccFlowTo = this;
509         aRet <<= AccFlowTo;
510     }
511     else
512         aRet = SwAccessibleContext::queryInterface( rType );
513     return aRet;
514 }
515 
516 //====== XTypeProvider ====================================================
getTypes()517 uno::Sequence< uno::Type > SAL_CALL SwAccessibleDocument::getTypes()
518     throw(uno::RuntimeException)
519 {
520     uno::Sequence< uno::Type > aTypes( SwAccessibleDocumentBase::getTypes() );
521 
522     sal_Int32 nIndex = aTypes.getLength();
523     //Solution:Reset types memory alloc
524     //aTypes.realloc( nIndex + 1 );
525     aTypes.realloc( nIndex + 2 );
526 
527     uno::Type* pTypes = aTypes.getArray();
528     pTypes[nIndex] = ::getCppuType( static_cast< uno::Reference< XAccessibleSelection > * >( 0 ) );
529     //Solution:Add XEventListener interface support.
530     pTypes[nIndex + 1 ] = ::getCppuType( static_cast< uno::Reference< com::sun::star::document::XEventListener > * >( 0 ) );
531     return aTypes;
532 }
533 
getImplementationId()534 uno::Sequence< sal_Int8 > SAL_CALL SwAccessibleDocument::getImplementationId()
535         throw(uno::RuntimeException)
536 {
537     vos::OGuard aGuard(Application::GetSolarMutex());
538     static uno::Sequence< sal_Int8 > aId( 16 );
539     static sal_Bool bInit = sal_False;
540     if(!bInit)
541     {
542         rtl_createUuid( (sal_uInt8 *)(aId.getArray() ), 0, sal_True );
543         bInit = sal_True;
544     }
545     return aId;
546 }
547 
548 //=====  XAccessibleSelection  ============================================
549 
selectAccessibleChild(sal_Int32 nChildIndex)550 void SwAccessibleDocument::selectAccessibleChild(
551     sal_Int32 nChildIndex )
552     throw ( lang::IndexOutOfBoundsException,
553             uno::RuntimeException )
554 {
555     maSelectionHelper.selectAccessibleChild(nChildIndex);
556 }
557 
isAccessibleChildSelected(sal_Int32 nChildIndex)558 sal_Bool SwAccessibleDocument::isAccessibleChildSelected(
559     sal_Int32 nChildIndex )
560     throw ( lang::IndexOutOfBoundsException,
561             uno::RuntimeException )
562 {
563     return maSelectionHelper.isAccessibleChildSelected(nChildIndex);
564 }
565 
clearAccessibleSelection()566 void SwAccessibleDocument::clearAccessibleSelection(  )
567     throw ( uno::RuntimeException )
568 {
569     maSelectionHelper.clearAccessibleSelection();
570 }
571 
selectAllAccessibleChildren()572 void SwAccessibleDocument::selectAllAccessibleChildren(  )
573     throw ( uno::RuntimeException )
574 {
575     maSelectionHelper.selectAllAccessibleChildren();
576 }
577 
getSelectedAccessibleChildCount()578 sal_Int32 SwAccessibleDocument::getSelectedAccessibleChildCount(  )
579     throw ( uno::RuntimeException )
580 {
581     return maSelectionHelper.getSelectedAccessibleChildCount();
582 }
583 
getSelectedAccessibleChild(sal_Int32 nSelectedChildIndex)584 uno::Reference<XAccessible> SwAccessibleDocument::getSelectedAccessibleChild(
585     sal_Int32 nSelectedChildIndex )
586     throw ( lang::IndexOutOfBoundsException,
587             uno::RuntimeException)
588 {
589     return maSelectionHelper.getSelectedAccessibleChild(nSelectedChildIndex);
590 }
591 
592 // --> OD 2004-11-16 #111714# - index has to be treated as global child index.
deselectAccessibleChild(sal_Int32 nChildIndex)593 void SwAccessibleDocument::deselectAccessibleChild(
594     sal_Int32 nChildIndex )
595     throw ( lang::IndexOutOfBoundsException,
596             uno::RuntimeException )
597 {
598     maSelectionHelper.deselectAccessibleChild( nChildIndex );
599 }
600 //Solution:Implement XEventListener interfaces
notifyEvent(const::com::sun::star::document::EventObject & Event)601 void SAL_CALL SwAccessibleDocument::notifyEvent( const ::com::sun::star::document::EventObject& Event )
602             throw (::com::sun::star::uno::RuntimeException)
603 {
604     if ( Event.EventName.equalsAscii( "FirstPageShows" ) )
605     {
606         FireStateChangedEvent( AccessibleStateType::FOCUSED,sal_True );
607     }
608     else if ( Event.EventName.equalsAscii( "LoadFinished" ) )
609     {
610         // IA2 CWS. MT: OFFSCREEN == !SHOWING, should stay consistent
611         // FireStateChangedEvent( AccessibleStateType::OFFSCREEN,sal_True );
612         // MT: LoadFinished => Why not SHOWING == TRUE?
613         FireStateChangedEvent( AccessibleStateType::SHOWING,sal_False );
614     }
615     else if ( Event.EventName.equalsAscii( "FormatFinished" ) )
616     {
617         FireStateChangedEvent( AccessibleStateType::BUSY,sal_False );
618         // FireStateChangedEvent( AccessibleStateType::OFFSCREEN,sal_False );
619         FireStateChangedEvent( AccessibleStateType::SHOWING,sal_True );
620     }
621     else
622     {
623         isIfAsynLoad = sal_False;
624     }
625 }
626 
disposing(const::com::sun::star::lang::EventObject &)627 void SAL_CALL SwAccessibleDocument::disposing( const ::com::sun::star::lang::EventObject& )
628             throw (::com::sun::star::uno::RuntimeException)
629 {
630 }
631 
getExtendedAttributes()632 uno::Any SAL_CALL SwAccessibleDocument::getExtendedAttributes()
633         throw (::com::sun::star::lang::IndexOutOfBoundsException, ::com::sun::star::uno::RuntimeException)
634 {
635     uno::Any anyAtrribute;
636     SwDoc *pDoc = GetShell()->GetDoc();
637 
638     if (!pDoc)
639         return anyAtrribute;
640     SwCrsrShell* pCrsrShell = GetCrsrShell();
641     if( !pCrsrShell )
642         return anyAtrribute;
643 
644     SwFEShell* pFEShell = pCrsrShell->ISA( SwFEShell )
645                                 ? static_cast<SwFEShell*>( pCrsrShell )
646                             : 0;
647     rtl::OUString sAttrName;
648     rtl::OUString sValue;
649     sal_uInt16 nPage, nLogPage;
650     String sDisplay;
651 
652     if( pFEShell )
653     {
654         pFEShell->GetPageNumber(-1,sal_True,nPage,nLogPage,sDisplay);
655         sAttrName = rtl::OUString::createFromAscii("page-name:");
656 
657 
658         sValue = sAttrName + sDisplay ;
659         sAttrName = rtl::OUString::createFromAscii(";page-number:");
660         sValue += sAttrName;
661         sValue += String::CreateFromInt32( nPage ) ;
662         sAttrName = rtl::OUString::createFromAscii(";total-pages:");
663         sValue += sAttrName;
664         sValue += String::CreateFromInt32( pCrsrShell->GetPageCnt() ) ;
665         sValue +=  rtl::OUString::createFromAscii(";");
666 
667 
668         sAttrName=rtl::OUString::createFromAscii("line-number:");
669 
670 
671 
672         SwCntntFrm* pCurrFrm = pCrsrShell->GetCurrFrm();
673         SwPageFrm* pCurrPage=((SwFrm*)pCurrFrm)->FindPageFrm();
674         sal_uLong nLineNum = 0;
675         SwTxtFrm* pTxtFrm = NULL;
676         SwTxtFrm* pCurrTxtFrm = NULL;
677         pTxtFrm = static_cast< SwTxtFrm* >(static_cast< SwPageFrm* > (pCurrPage)->ContainsCntnt());
678         if (pCurrFrm->IsInFly())//such as, graphic,chart
679         {
680             SwFlyFrm *pFlyFrm = pCurrFrm->FindFlyFrm();
681             const SwFmtAnchor& rAnchor = pFlyFrm->GetFmt()->GetAnchor();
682             RndStdIds eAnchorId = rAnchor.GetAnchorId();
683             if(eAnchorId == FLY_AS_CHAR)
684             {
685                 const SwFrm *pSwFrm = pFlyFrm->GetAnchorFrm();
686                 if(pSwFrm->IsTxtFrm())
687                     pCurrTxtFrm = ((SwTxtFrm*)(pSwFrm));
688             }
689         }
690         else
691             pCurrTxtFrm = static_cast< SwTxtFrm* >(pCurrFrm);
692         //check whether the text frame where the Graph/OLE/Frame anchored is in the Header/Footer
693         SwFrm* pFrm = pCurrTxtFrm;
694         while ( pFrm && !pFrm->IsHeaderFrm() && !pFrm->IsFooterFrm() )
695             pFrm = pFrm->GetUpper();
696         if ( pFrm )
697             pCurrTxtFrm = NULL;
698         //check shape
699         if(pCrsrShell->Imp()->GetDrawView())
700         {
701             const SdrMarkList &rMrkList = pCrsrShell->Imp()->GetDrawView()->GetMarkedObjectList();
702             for ( sal_uInt16 i = 0; i < rMrkList.GetMarkCount(); ++i )
703             {
704                 SdrObject *pObj = rMrkList.GetMark(i)->GetMarkedSdrObj();
705                 SwFrmFmt* pFmt = ((SwDrawContact*)pObj->GetUserCall())->GetFmt();
706                 const SwFmtAnchor& rAnchor = pFmt->GetAnchor();
707                 if( FLY_AS_CHAR != rAnchor.GetAnchorId() )
708                     pCurrTxtFrm = NULL;
709             }
710         }
711         //calculate line number
712         if (pCurrTxtFrm && pTxtFrm)
713         {
714             if (!(pCurrTxtFrm->IsInTab() || pCurrTxtFrm->IsInFtn()))
715             {
716                 while( pTxtFrm != pCurrTxtFrm )
717                 {
718                     //check header/footer
719                     pFrm = pTxtFrm;
720                     while ( pFrm && !pFrm->IsHeaderFrm() && !pFrm->IsFooterFrm() )
721                         pFrm = pFrm->GetUpper();
722                     if ( pFrm )
723                     {
724                         pTxtFrm = static_cast< SwTxtFrm*>(pTxtFrm->GetNextCntntFrm());
725                         continue;
726                     }
727                     if (!(pTxtFrm->IsInTab() || pTxtFrm->IsInFtn() || pTxtFrm->IsInFly()))
728                         nLineNum += pTxtFrm->GetThisLines();
729                     pTxtFrm = static_cast< SwTxtFrm* >(pTxtFrm ->GetNextCntntFrm());
730                 }
731                 SwPaM* pCaret = pCrsrShell->GetCrsr();
732                 if (!pCurrTxtFrm->IsEmpty() && pCaret)
733                 {
734                     sal_uInt16 nActPos = 0;
735                     if (pCurrTxtFrm->IsTxtFrm())
736                     {
737                         const SwPosition* pPoint = NULL;
738                         if(pCurrTxtFrm->IsInFly())
739                         {
740                             SwFlyFrm *pFlyFrm = pCurrTxtFrm->FindFlyFrm();
741                             const SwFmtAnchor& rAnchor = pFlyFrm->GetFmt()->GetAnchor();
742                             pPoint= rAnchor.GetCntntAnchor();
743                         }
744                         else
745                             pPoint = pCaret->GetPoint();
746                         nActPos = pPoint->nContent.GetIndex();
747                         nLineNum += pCurrTxtFrm->GetLineCount( nActPos );
748                     }
749                     else//graphic, form, shape, etc.
750                     {
751                         SwPosition* pPoint =  pCaret->GetPoint();
752                         Point aPt = pCrsrShell->_GetCrsr()->GetPtPos();
753                         if( pCrsrShell->GetLayout()->GetCrsrOfst( pPoint, aPt/*,* &eTmpState*/ ) )
754                         {
755                             nActPos = pPoint->nContent.GetIndex();
756                             nLineNum += pCurrTxtFrm->GetLineCount( nActPos );
757                         }
758                     }
759                 }
760                 else
761                     ++nLineNum;
762             }
763         }
764 
765         sValue += sAttrName;
766         sValue += String::CreateFromInt32( nLineNum ) ;
767 
768         sValue +=  rtl::OUString::createFromAscii(";");
769 
770 
771         SwFrm* pCurrCol=((SwFrm*)pCurrFrm)->FindColFrm();
772 
773         sAttrName=rtl::OUString::createFromAscii("column-number:");
774         sValue += sAttrName;
775 
776         sal_uInt16 nCurrCol = 1;
777         if(pCurrCol!=NULL)
778         {
779             //SwLayoutFrm* pParent = pCurrCol->GetUpper();
780             SwFrm* pCurrPageCol=((SwFrm*)pCurrFrm)->FindColFrm();
781             while(pCurrPageCol && pCurrPageCol->GetUpper() && pCurrPageCol->GetUpper()->IsPageFrm())
782             {
783                 pCurrPageCol = pCurrPageCol->GetUpper();
784             }
785 
786             SwLayoutFrm* pParent = (SwLayoutFrm*)(pCurrPageCol->GetUpper());
787 
788             if(pParent!=NULL)
789             {
790                 SwFrm* pCol = pParent->Lower();
791                 while(pCol&&(pCol!=pCurrPageCol))
792                 {
793                     pCol = pCol->GetNext();
794                     nCurrCol +=1;
795                 }
796             }
797         }
798         sValue += String::CreateFromInt32( nCurrCol ) ;
799         sValue +=  rtl::OUString::createFromAscii(";");
800 
801         sAttrName=rtl::OUString::createFromAscii("total-columns:");
802 
803         const SwFmtCol &rFmtCol=pCurrPage->GetAttrSet()->GetCol();
804         sal_uInt16 nColCount=rFmtCol.GetNumCols();
805         nColCount = nColCount>0?nColCount:1;
806         sValue += sAttrName;
807         sValue += String::CreateFromInt32( nColCount ) ;
808 
809         sValue +=  rtl::OUString::createFromAscii(";");
810 
811         if(pCurrFrm!=NULL)
812         {
813             SwSectionFrm* pCurrSctFrm=((SwFrm*)pCurrFrm)->FindSctFrm();
814             if(pCurrSctFrm!=NULL && pCurrSctFrm->GetSection()!=NULL )
815             {
816                 sAttrName = rtl::OUString::createFromAscii("section-name:");
817 
818                 sValue += sAttrName;
819                 String sectionName = pCurrSctFrm->GetSection()->GetSectionName();
820 
821                 sectionName.SearchAndReplace( String::CreateFromAscii( "\\" ), String::CreateFromAscii("\\\\" ));
822                 sectionName.SearchAndReplace( String::CreateFromAscii( "=" ), String::CreateFromAscii("\\=" ) );
823                 sectionName.SearchAndReplace( String::CreateFromAscii( ";" ), String::CreateFromAscii("\\;" ) );
824                 sectionName.SearchAndReplace( String::CreateFromAscii( "," ), String::CreateFromAscii("\\," ) );
825                 sectionName.SearchAndReplace( String::CreateFromAscii( ":" ), String::CreateFromAscii("\\:" ) );
826 
827                 sValue += sectionName;
828                 //sValue += pCurrSctFrm->GetSection()->GetName();
829 
830                 sValue += rtl::OUString::createFromAscii(";");
831 
832                 //section-columns-number
833                 {
834                 sAttrName=rtl::OUString::createFromAscii("section-columns-number:");
835 
836                 nCurrCol = 1;
837 
838                 if(pCurrCol!=NULL)
839                 {
840                     SwLayoutFrm* pParent = pCurrCol->GetUpper();
841                     if(pParent!=NULL)
842                     {
843                         SwFrm* pCol = pParent->Lower();
844                         while(pCol&&(pCol!=pCurrCol))
845                         {
846                             pCol = pCol->GetNext();
847                             nCurrCol +=1;
848                         }
849                     }
850                 }
851                 sValue += sAttrName;
852                 sValue += String::CreateFromInt32( nCurrCol ) ;
853                 sValue +=  rtl::OUString::createFromAscii(";");
854                 }
855 
856                 //section-total-columns
857                 {
858                 sAttrName=rtl::OUString::createFromAscii("section-total-columns:");
859                 const SwFmtCol &rFmtSctCol=pCurrSctFrm->GetAttrSet()->GetCol();
860                 sal_uInt16 nSctColCount=rFmtSctCol.GetNumCols();
861                 nSctColCount = nSctColCount>0?nSctColCount:1;
862                 sValue += sAttrName;
863                 sValue += String::CreateFromInt32( nSctColCount ) ;
864 
865                 sValue +=  rtl::OUString::createFromAscii(";");
866                 }
867             }
868         }
869         anyAtrribute <<= sValue;
870     }
871     return anyAtrribute;
872 }
873 
getBackground()874 sal_Int32 SAL_CALL SwAccessibleDocument::getBackground()
875         throw (::com::sun::star::uno::RuntimeException)
876 {
877     vos::OGuard aGuard(Application::GetSolarMutex());
878     return SW_MOD()->GetColorConfig().GetColorValue( ::svtools::DOCCOLOR ).nColor;
879 }
880 
881 ::com::sun::star::uno::Sequence< ::com::sun::star::uno::Any >
get_AccFlowTo(const::com::sun::star::uno::Any & rAny,sal_Int32 nType)882         SAL_CALL SwAccessibleDocument::get_AccFlowTo(const ::com::sun::star::uno::Any& rAny, sal_Int32 nType)
883         throw ( ::com::sun::star::uno::RuntimeException )
884 {
885     const sal_Int32 FORSPELLCHECKFLOWTO = 1;
886     const sal_Int32 FORFINDREPLACEFLOWTO = 2;
887     SwAccessibleMap* pAccMap = GetMap();
888     if ( !pAccMap )
889     {
890         goto Rt;
891     }
892 
893     if ( nType == FORSPELLCHECKFLOWTO )
894     {
895         uno::Reference< ::com::sun::star::drawing::XShape > xShape;
896         rAny >>= xShape;
897         if( xShape.is() )
898         {
899             SdrObject* pObj = GetSdrObjectFromXShape(xShape);
900             if( pObj )
901             {
902                 uno::Reference<XAccessible> xAcc = pAccMap->GetContext(pObj, this, sal_False);
903                 uno::Reference < XAccessibleSelection > xAccSelection( xAcc, uno::UNO_QUERY );
904                 if ( xAccSelection.is() )
905                 {
906                     try
907                     {
908                         if ( xAccSelection->getSelectedAccessibleChildCount() )
909                         {
910                             uno::Reference < XAccessible > xSel = xAccSelection->getSelectedAccessibleChild( 0 );
911                             if ( xSel.is() )
912                             {
913                                 uno::Reference < XAccessibleContext > xSelContext( xSel->getAccessibleContext() );
914                                 if ( xSelContext.is() )
915                                 {
916                                     //if in sw we find the selected paragraph here
917                                     if ( xSelContext->getAccessibleRole() == AccessibleRole::PARAGRAPH )
918                                     {
919                                         uno::Sequence<uno::Any> aRet( 1 );
920                                         aRet[0] = uno::makeAny( xSel );
921                                         return aRet;
922                                     }
923                                 }
924                             }
925                         }
926                     }
927                     catch ( com::sun::star::lang::IndexOutOfBoundsException )
928                     {
929                         //return empty sequence
930                         goto Rt;
931                     }
932                     //end of try...catch
933                 }
934                 /*uno::Sequence< uno::Any > aRet(1);
935                 aRet[0] = uno::makeAny( xAcc );
936                 return aRet;*/
937             }
938         }
939         else
940         {
941             uno::Reference< XAccessible > xAcc = pAccMap->GetCursorContext();
942             SwAccessibleContext *pAccImpl = static_cast< SwAccessibleContext *>( xAcc.get() );
943             if ( pAccImpl && pAccImpl->getAccessibleRole() == AccessibleRole::PARAGRAPH )
944             {
945                 uno::Sequence< uno::Any > aRet(1);
946                 aRet[0] = uno::makeAny( xAcc );
947                 return aRet;
948             }
949         }
950     }
951     else if ( nType == FORFINDREPLACEFLOWTO )
952     {
953         SwCrsrShell* pCrsrShell = GetCrsrShell();
954         if ( pCrsrShell )
955         {
956             SwPaM *_pStartCrsr = pCrsrShell->GetCrsr(), *__pStartCrsr = _pStartCrsr;
957             SwCntntNode* pPrevNode = NULL;
958             std::vector<SwFrm*> vFrmList;
959             do
960             {
961                 if ( _pStartCrsr && _pStartCrsr->HasMark() )
962                 {
963                     SwCntntNode* pCntntNode = _pStartCrsr->GetCntntNode();
964                     if ( pCntntNode == pPrevNode )
965                     {
966                         continue;
967                     }
968                     SwFrm* pFrm = pCntntNode ? pCntntNode->getLayoutFrm( pCrsrShell->GetLayout() ) : NULL;
969                     if ( pFrm )
970                     {
971                         vFrmList.push_back( pFrm );
972                     }
973 
974                     pPrevNode = pCntntNode;
975                 }
976             }
977 
978             while( _pStartCrsr && ( (_pStartCrsr=(SwPaM *)_pStartCrsr->GetNext()) != __pStartCrsr) );
979 
980             if ( vFrmList.size() )
981             {
982                 uno::Sequence< uno::Any > aRet(vFrmList.size());
983                 std::vector<SwFrm*>::iterator aIter = vFrmList.begin();
984                 for ( sal_Int32 nIndex = 0; aIter != vFrmList.end(); aIter++, nIndex++ )
985                 {
986                     uno::Reference< XAccessible > xAcc = pAccMap->GetContext(*aIter, sal_False);
987                     if ( xAcc.is() )
988                     {
989                         SwAccessibleContext *pAccImpl = static_cast< SwAccessibleContext *>( xAcc.get() );
990                         if ( pAccImpl && pAccImpl->getAccessibleRole() == AccessibleRole::PARAGRAPH )
991                         {
992                             aRet[nIndex] = uno::makeAny( xAcc );
993                         }
994                     }
995                 }
996 
997                 return aRet;
998             }
999         }
1000     }
1001 
1002 Rt:
1003     uno::Sequence< uno::Any > aEmpty;
1004     return aEmpty;
1005 }
1006