1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
9 * This file incorporates work covered by the following license notice:
11 * Licensed to the Apache Software Foundation (ASF) under one or more
12 * contributor license agreements. See the NOTICE file distributed
13 * with this work for additional information regarding copyright
14 * ownership. The ASF licenses this file to you under the Apache
15 * License, Version 2.0 (the "License"); you may not use this file
16 * except in compliance with the License. You may obtain a copy of
17 * the License at http://www.apache.org/licenses/LICENSE-2.0 .
20 #include "AccessibleSlideSorterView.hxx"
21 #include "AccessibleSlideSorterObject.hxx"
23 #include "SlideSorter.hxx"
24 #include "controller/SlideSorterController.hxx"
25 #include "controller/SlsPageSelector.hxx"
26 #include "controller/SlsFocusManager.hxx"
27 #include "controller/SlsSelectionManager.hxx"
28 #include "view/SlideSorterView.hxx"
29 #include "model/SlideSorterModel.hxx"
30 #include "model/SlsPageDescriptor.hxx"
31 #include "SlideSorterViewShell.hxx"
33 #include "ViewShellHint.hxx"
35 #include "drawdoc.hxx"
37 #include "sdresid.hxx"
38 #include "accessibility.hrc"
39 #include <com/sun/star/accessibility/AccessibleRole.hpp>
40 #include <com/sun/star/accessibility/AccessibleEventId.hpp>
41 #include <com/sun/star/accessibility/AccessibleStateType.hpp>
42 #include <comphelper/accessibleeventnotifier.hxx>
43 #include <cppuhelper/supportsservice.hxx>
44 #include <unotools/accessiblestatesethelper.hxx>
45 #include <rtl/ref.hxx>
47 #include <vcl/settings.hxx>
48 #include <vcl/svapp.hxx>
50 using namespace ::com::sun::star
;
51 using namespace ::com::sun::star::uno
;
52 using namespace ::com::sun::star::accessibility
;
54 namespace accessibility
{
56 /** Inner implementation class of the AccessibleSlideSorterView.
58 Note that some event broadcasting is done asynchronously because
59 otherwise it could lead to deadlocks on (at least) some Solaris
60 machines. Probably (but unverified) this can happen on all GTK based
61 systems. The asynchronous broadcasting is just a workaround for a
62 poorly understood problem.
64 class AccessibleSlideSorterView::Implementation
69 AccessibleSlideSorterView
& rAccessibleSlideSorter
,
70 ::sd::slidesorter::SlideSorter
& rSlideSorter
,
71 vcl::Window
* pWindow
);
72 virtual ~Implementation();
74 void RequestUpdateChildren();
76 sal_Int32
GetVisibleChildCount() const;
77 AccessibleSlideSorterObject
* GetAccessibleChild (sal_Int32 nIndex
);
78 AccessibleSlideSorterObject
* GetVisibleChild (sal_Int32 nIndex
);
80 void ConnectListeners();
81 void ReleaseListeners();
82 void Notify (SfxBroadcaster
& rBroadcaster
, const SfxHint
& rHint
) SAL_OVERRIDE
;
83 DECL_LINK(WindowEventListener
, VclWindowEvent
*);
84 DECL_LINK(SelectionChangeListener
, void*);
85 DECL_LINK(BroadcastSelectionChange
, void*);
86 DECL_LINK(FocusChangeListener
, void*);
87 DECL_LINK(VisibilityChangeListener
, void*);
88 DECL_LINK(UpdateChildrenCallback
, void*);
92 AccessibleSlideSorterView
& mrAccessibleSlideSorter
;
93 ::sd::slidesorter::SlideSorter
& mrSlideSorter
;
94 typedef ::std::vector
<rtl::Reference
<AccessibleSlideSorterObject
> > PageObjectList
;
95 PageObjectList maPageObjects
;
96 sal_Int32 mnFirstVisibleChild
;
97 sal_Int32 mnLastVisibleChild
;
98 bool mbListeningToDocument
;
99 VclPtr
<vcl::Window
> mpWindow
;
100 sal_Int32 mnFocusedIndex
;
101 bool mbModelChangeLocked
;
102 ImplSVEvent
* mnUpdateChildrenUserEventId
;
103 ImplSVEvent
* mnSelectionChangeUserEventId
;
105 void UpdateChildren();
108 //===== AccessibleSlideSorterView =============================================
110 AccessibleSlideSorterView::AccessibleSlideSorterView(
111 ::sd::slidesorter::SlideSorter
& rSlideSorter
,
112 const Reference
<XAccessible
>& rxParent
,
113 vcl::Window
* pContentWindow
)
114 : AccessibleSlideSorterViewBase(MutexOwner::maMutex
),
115 mrSlideSorter(rSlideSorter
),
118 mpContentWindow(pContentWindow
)
122 void AccessibleSlideSorterView::Init()
124 mpImpl
.reset(new Implementation(*this,mrSlideSorter
,mpContentWindow
));
127 AccessibleSlideSorterView::~AccessibleSlideSorterView()
132 void AccessibleSlideSorterView::FireAccessibleEvent (
134 const uno::Any
& rOldValue
,
135 const uno::Any
& rNewValue
)
139 AccessibleEventObject aEventObject
;
141 aEventObject
.Source
= Reference
<XWeak
>(this);
142 aEventObject
.EventId
= nEventId
;
143 aEventObject
.NewValue
= rNewValue
;
144 aEventObject
.OldValue
= rOldValue
;
146 comphelper::AccessibleEventNotifier::addEvent (mnClientId
, aEventObject
);
150 void SAL_CALL
AccessibleSlideSorterView::disposing()
154 comphelper::AccessibleEventNotifier::revokeClientNotifyDisposing( mnClientId
, *this );
160 AccessibleSlideSorterObject
* AccessibleSlideSorterView::GetAccessibleChildImplementation (
163 AccessibleSlideSorterObject
* pResult
= NULL
;
164 ::osl::MutexGuard
aGuard (maMutex
);
166 if (nIndex
>=0 && nIndex
<mpImpl
->GetVisibleChildCount())
167 pResult
= mpImpl
->GetVisibleChild(nIndex
);
172 void AccessibleSlideSorterView::Destroyed()
174 ::osl::MutexGuard
aGuard (maMutex
);
176 // Send a disposing to all listeners.
179 comphelper::AccessibleEventNotifier::revokeClientNotifyDisposing( mnClientId
, *this );
184 //===== XAccessible =========================================================
186 Reference
<XAccessibleContext
> SAL_CALL
187 AccessibleSlideSorterView::getAccessibleContext()
188 throw (uno::RuntimeException
, std::exception
)
194 //===== XAccessibleContext ==================================================
196 sal_Int32 SAL_CALL
AccessibleSlideSorterView::getAccessibleChildCount()
197 throw (RuntimeException
, std::exception
)
200 ::osl::MutexGuard
aGuard (maMutex
);
201 return mpImpl
->GetVisibleChildCount();
204 Reference
<XAccessible
> SAL_CALL
205 AccessibleSlideSorterView::getAccessibleChild (sal_Int32 nIndex
)
206 throw (lang::IndexOutOfBoundsException
, RuntimeException
, std::exception
)
209 ::osl::MutexGuard
aGuard (maMutex
);
211 if (nIndex
<0 || nIndex
>=mpImpl
->GetVisibleChildCount())
212 throw lang::IndexOutOfBoundsException();
214 return mpImpl
->GetVisibleChild(nIndex
);
217 Reference
<XAccessible
> SAL_CALL
AccessibleSlideSorterView::getAccessibleParent()
218 throw (uno::RuntimeException
, std::exception
)
221 const SolarMutexGuard aSolarGuard
;
222 Reference
<XAccessible
> xParent
;
224 if (mpContentWindow
!= nullptr)
226 vcl::Window
* pParent
= mpContentWindow
->GetAccessibleParentWindow();
228 xParent
= pParent
->GetAccessible();
234 sal_Int32 SAL_CALL
AccessibleSlideSorterView::getAccessibleIndexInParent()
235 throw (uno::RuntimeException
, std::exception
)
237 OSL_ASSERT(getAccessibleParent().is());
239 const SolarMutexGuard aSolarGuard
;
240 sal_Int32
nIndexInParent(-1);
242 Reference
<XAccessibleContext
> xParentContext (getAccessibleParent()->getAccessibleContext());
243 if (xParentContext
.is())
245 sal_Int32
nChildCount (xParentContext
->getAccessibleChildCount());
246 for (sal_Int32 i
=0; i
<nChildCount
; ++i
)
247 if (xParentContext
->getAccessibleChild(i
).get()
248 == static_cast<XAccessible
*>(this))
255 return nIndexInParent
;
258 sal_Int16 SAL_CALL
AccessibleSlideSorterView::getAccessibleRole()
259 throw (uno::RuntimeException
, std::exception
)
262 static sal_Int16 nRole
= AccessibleRole::DOCUMENT
;
266 OUString SAL_CALL
AccessibleSlideSorterView::getAccessibleDescription()
267 throw (uno::RuntimeException
, std::exception
)
270 SolarMutexGuard aGuard
;
272 return SD_RESSTR(SID_SD_A11Y_I_SLIDEVIEW_D
);
275 OUString SAL_CALL
AccessibleSlideSorterView::getAccessibleName()
276 throw (uno::RuntimeException
, std::exception
)
279 SolarMutexGuard aGuard
;
281 return SD_RESSTR(SID_SD_A11Y_I_SLIDEVIEW_N
);
284 Reference
<XAccessibleRelationSet
> SAL_CALL
285 AccessibleSlideSorterView::getAccessibleRelationSet()
286 throw (uno::RuntimeException
, std::exception
)
288 return Reference
<XAccessibleRelationSet
>();
291 Reference
<XAccessibleStateSet
> SAL_CALL
292 AccessibleSlideSorterView::getAccessibleStateSet()
293 throw (uno::RuntimeException
, std::exception
)
296 const SolarMutexGuard aSolarGuard
;
297 ::utl::AccessibleStateSetHelper
* pStateSet
= new ::utl::AccessibleStateSetHelper();
299 pStateSet
->AddState(AccessibleStateType::FOCUSABLE
);
300 pStateSet
->AddState(AccessibleStateType::SELECTABLE
);
301 pStateSet
->AddState(AccessibleStateType::ENABLED
);
302 pStateSet
->AddState(AccessibleStateType::ACTIVE
);
303 pStateSet
->AddState(AccessibleStateType::MULTI_SELECTABLE
);
304 pStateSet
->AddState(AccessibleStateType::OPAQUE
);
305 if (mpContentWindow
!=nullptr)
307 if (mpContentWindow
->IsVisible())
308 pStateSet
->AddState(AccessibleStateType::VISIBLE
);
309 if (mpContentWindow
->IsReallyVisible())
310 pStateSet
->AddState(AccessibleStateType::SHOWING
);
316 lang::Locale SAL_CALL
AccessibleSlideSorterView::getLocale()
317 throw (IllegalAccessibleComponentStateException
,
318 RuntimeException
, std::exception
)
321 Reference
<XAccessibleContext
> xParentContext
;
322 Reference
<XAccessible
> xParent (getAccessibleParent());
324 xParentContext
= xParent
->getAccessibleContext();
326 if (xParentContext
.is())
327 return xParentContext
->getLocale();
329 // Strange, no parent! Anyway, return the default locale.
330 return Application::GetSettings().GetLanguageTag().getLocale();
333 void SAL_CALL
AccessibleSlideSorterView::addAccessibleEventListener(
334 const Reference
<XAccessibleEventListener
>& rxListener
)
335 throw (RuntimeException
, std::exception
)
339 const osl::MutexGuard
aGuard(maMutex
);
343 uno::Reference
<uno::XInterface
> x ((lang::XComponent
*)this, uno::UNO_QUERY
);
344 rxListener
->disposing (lang::EventObject (x
));
349 mnClientId
= comphelper::AccessibleEventNotifier::registerClient();
350 comphelper::AccessibleEventNotifier::addEventListener(mnClientId
, rxListener
);
355 void SAL_CALL
AccessibleSlideSorterView::removeAccessibleEventListener(
356 const Reference
<XAccessibleEventListener
>& rxListener
)
357 throw (RuntimeException
, std::exception
)
362 const osl::MutexGuard
aGuard(maMutex
);
366 sal_Int32 nListenerCount
= comphelper::AccessibleEventNotifier::removeEventListener(
367 mnClientId
, rxListener
);
368 if ( !nListenerCount
)
370 // no listeners anymore -> revoke ourself. This may lead to
371 // the notifier thread dying (if we were the last client),
372 // and at least to us not firing any events anymore, in case
373 // somebody calls NotifyAccessibleEvent, again
374 comphelper::AccessibleEventNotifier::revokeClient( mnClientId
);
381 //===== XAccessibleComponent ==================================================
383 sal_Bool SAL_CALL
AccessibleSlideSorterView::containsPoint (const awt::Point
& aPoint
)
384 throw (RuntimeException
, std::exception
)
387 const awt::Rectangle
aBBox (getBounds());
388 return (aPoint
.X
>= 0)
389 && (aPoint
.X
< aBBox
.Width
)
391 && (aPoint
.Y
< aBBox
.Height
);
394 Reference
<XAccessible
> SAL_CALL
395 AccessibleSlideSorterView::getAccessibleAtPoint (const awt::Point
& aPoint
)
396 throw (RuntimeException
, std::exception
)
399 Reference
<XAccessible
> xAccessible
;
400 const SolarMutexGuard aSolarGuard
;
402 const Point
aTestPoint (aPoint
.X
, aPoint
.Y
);
403 ::sd::slidesorter::model::SharedPageDescriptor
pHitDescriptor (
404 mrSlideSorter
.GetController().GetPageAt(aTestPoint
));
405 if (pHitDescriptor
.get() != NULL
)
406 xAccessible
= mpImpl
->GetAccessibleChild(
407 (pHitDescriptor
->GetPage()->GetPageNum()-1)/2);
412 awt::Rectangle SAL_CALL
AccessibleSlideSorterView::getBounds()
413 throw (uno::RuntimeException
, std::exception
)
416 const SolarMutexGuard aSolarGuard
;
417 awt::Rectangle aBBox
;
419 if (mpContentWindow
!= nullptr)
421 const Point
aPosition (mpContentWindow
->GetPosPixel());
422 const Size
aSize (mpContentWindow
->GetOutputSizePixel());
424 aBBox
.X
= aPosition
.X();
425 aBBox
.Y
= aPosition
.Y();
426 aBBox
.Width
= aSize
.Width();
427 aBBox
.Height
= aSize
.Height();
433 awt::Point SAL_CALL
AccessibleSlideSorterView::getLocation()
434 throw (uno::RuntimeException
, std::exception
)
437 awt::Point aLocation
;
439 if (mpContentWindow
!= nullptr)
441 const Point
aPosition (mpContentWindow
->GetPosPixel());
442 aLocation
.X
= aPosition
.X();
443 aLocation
.Y
= aPosition
.Y();
449 /** Calculate the location on screen from the parent's location on screen
450 and our own relative location.
452 awt::Point SAL_CALL
AccessibleSlideSorterView::getLocationOnScreen()
453 throw (uno::RuntimeException
, std::exception
)
456 const SolarMutexGuard aSolarGuard
;
457 awt::Point aParentLocationOnScreen
;
459 Reference
<XAccessible
> xParent (getAccessibleParent());
462 Reference
<XAccessibleComponent
> xParentComponent (
463 xParent
->getAccessibleContext(), uno::UNO_QUERY
);
464 if (xParentComponent
.is())
465 aParentLocationOnScreen
= xParentComponent
->getLocationOnScreen();
468 awt::Point
aLocationOnScreen (getLocation());
469 aLocationOnScreen
.X
+= aParentLocationOnScreen
.X
;
470 aLocationOnScreen
.Y
+= aParentLocationOnScreen
.Y
;
472 return aLocationOnScreen
;
475 awt::Size SAL_CALL
AccessibleSlideSorterView::getSize()
476 throw (uno::RuntimeException
, std::exception
)
481 if (mpContentWindow
!= nullptr)
483 const Size
aOutputSize (mpContentWindow
->GetOutputSizePixel());
484 aSize
.Width
= aOutputSize
.Width();
485 aSize
.Height
= aOutputSize
.Height();
491 void SAL_CALL
AccessibleSlideSorterView::grabFocus()
492 throw (uno::RuntimeException
, std::exception
)
495 const SolarMutexGuard aSolarGuard
;
498 mpContentWindow
->GrabFocus();
501 sal_Int32 SAL_CALL
AccessibleSlideSorterView::getForeground()
502 throw (RuntimeException
, std::exception
)
505 svtools::ColorConfig aColorConfig
;
506 sal_uInt32 nColor
= aColorConfig
.GetColorValue( svtools::FONTCOLOR
).nColor
;
507 return static_cast<sal_Int32
>(nColor
);
510 sal_Int32 SAL_CALL
AccessibleSlideSorterView::getBackground()
511 throw (RuntimeException
, std::exception
)
514 sal_uInt32 nColor
= Application::GetSettings().GetStyleSettings().GetWindowColor().GetColor();
515 return static_cast<sal_Int32
>(nColor
);
518 //===== XAccessibleSelection ==================================================
520 void SAL_CALL
AccessibleSlideSorterView::selectAccessibleChild (sal_Int32 nChildIndex
)
521 throw (lang::IndexOutOfBoundsException
,
522 RuntimeException
, std::exception
)
525 const SolarMutexGuard aSolarGuard
;
527 AccessibleSlideSorterObject
* pChild
= mpImpl
->GetAccessibleChild(nChildIndex
);
529 mrSlideSorter
.GetController().GetPageSelector().SelectPage(pChild
->GetPageNumber());
531 throw lang::IndexOutOfBoundsException();
534 sal_Bool SAL_CALL
AccessibleSlideSorterView::isAccessibleChildSelected (sal_Int32 nChildIndex
)
535 throw (lang::IndexOutOfBoundsException
,
536 RuntimeException
, std::exception
)
539 bool bIsSelected
= false;
540 const SolarMutexGuard aSolarGuard
;
542 AccessibleSlideSorterObject
* pChild
= mpImpl
->GetAccessibleChild(nChildIndex
);
544 bIsSelected
= mrSlideSorter
.GetController().GetPageSelector().IsPageSelected(
545 pChild
->GetPageNumber());
547 throw lang::IndexOutOfBoundsException();
552 void SAL_CALL
AccessibleSlideSorterView::clearAccessibleSelection()
553 throw (uno::RuntimeException
, std::exception
)
556 const SolarMutexGuard aSolarGuard
;
558 mrSlideSorter
.GetController().GetPageSelector().DeselectAllPages();
561 void SAL_CALL
AccessibleSlideSorterView::selectAllAccessibleChildren()
562 throw (uno::RuntimeException
, std::exception
)
565 const SolarMutexGuard aSolarGuard
;
567 mrSlideSorter
.GetController().GetPageSelector().SelectAllPages();
570 sal_Int32 SAL_CALL
AccessibleSlideSorterView::getSelectedAccessibleChildCount()
571 throw (uno::RuntimeException
, std::exception
)
574 const SolarMutexGuard aSolarGuard
;
575 return mrSlideSorter
.GetController().GetPageSelector().GetSelectedPageCount();
578 Reference
<XAccessible
> SAL_CALL
579 AccessibleSlideSorterView::getSelectedAccessibleChild (sal_Int32 nSelectedChildIndex
)
580 throw (lang::IndexOutOfBoundsException
, uno::RuntimeException
, std::exception
)
583 const SolarMutexGuard aSolarGuard
;
584 Reference
<XAccessible
> xChild
;
586 ::sd::slidesorter::controller::PageSelector
& rSelector (
587 mrSlideSorter
.GetController().GetPageSelector());
588 sal_Int32
nPageCount(rSelector
.GetPageCount());
589 sal_Int32 nSelectedCount
= 0;
590 for (sal_Int32 i
=0; i
<nPageCount
; i
++)
591 if (rSelector
.IsPageSelected(i
))
593 if (nSelectedCount
== nSelectedChildIndex
)
595 xChild
= mpImpl
->GetAccessibleChild(i
);
602 throw lang::IndexOutOfBoundsException();
607 void SAL_CALL
AccessibleSlideSorterView::deselectAccessibleChild (sal_Int32 nChildIndex
)
608 throw (lang::IndexOutOfBoundsException
,
609 RuntimeException
, std::exception
)
612 const SolarMutexGuard aSolarGuard
;
614 AccessibleSlideSorterObject
* pChild
= mpImpl
->GetAccessibleChild(nChildIndex
);
616 mrSlideSorter
.GetController().GetPageSelector().DeselectPage(pChild
->GetPageNumber());
618 throw lang::IndexOutOfBoundsException();
623 AccessibleSlideSorterView::getImplementationName()
624 throw (::com::sun::star::uno::RuntimeException
, std::exception
)
626 return OUString("AccessibleSlideSorterView");
629 sal_Bool SAL_CALL
AccessibleSlideSorterView::supportsService (const OUString
& sServiceName
)
630 throw (::com::sun::star::uno::RuntimeException
, std::exception
)
632 return cppu::supportsService(this, sServiceName
);
635 uno::Sequence
< OUString
> SAL_CALL
636 AccessibleSlideSorterView::getSupportedServiceNames()
637 throw (::com::sun::star::uno::RuntimeException
, std::exception
)
641 static const OUString sServiceNames
[3] = {
642 OUString("com.sun.star.accessibility.Accessible"),
643 OUString("com.sun.star.accessibility.AccessibleContext"),
644 OUString("com.sun.star.drawing.AccessibleSlideSorterView")
646 return uno::Sequence
<OUString
> (sServiceNames
, 3);
649 void AccessibleSlideSorterView::ThrowIfDisposed()
650 throw (lang::DisposedException
)
652 if (rBHelper
.bDisposed
|| rBHelper
.bInDispose
)
654 OSL_TRACE ("Calling disposed object. Throwing exception:");
655 throw lang::DisposedException ("object has been already disposed",
656 static_cast<uno::XWeak
*>(this));
660 bool AccessibleSlideSorterView::IsDisposed()
662 return (rBHelper
.bDisposed
|| rBHelper
.bInDispose
);
665 //===== AccessibleSlideSorterView::Implementation =============================
667 AccessibleSlideSorterView::Implementation::Implementation (
668 AccessibleSlideSorterView
& rAccessibleSlideSorter
,
669 ::sd::slidesorter::SlideSorter
& rSlideSorter
,
670 vcl::Window
* pWindow
)
671 : mrAccessibleSlideSorter(rAccessibleSlideSorter
),
672 mrSlideSorter(rSlideSorter
),
674 mnFirstVisibleChild(0),
675 mnLastVisibleChild(-1),
676 mbListeningToDocument(false),
679 mbModelChangeLocked(false),
680 mnUpdateChildrenUserEventId(0),
681 mnSelectionChangeUserEventId(0)
687 AccessibleSlideSorterView::Implementation::~Implementation()
689 if (mnUpdateChildrenUserEventId
!= 0)
690 Application::RemoveUserEvent(mnUpdateChildrenUserEventId
);
691 if (mnSelectionChangeUserEventId
!= 0)
692 Application::RemoveUserEvent(mnSelectionChangeUserEventId
);
697 void AccessibleSlideSorterView::Implementation::RequestUpdateChildren()
699 if (mnUpdateChildrenUserEventId
== 0)
700 mnUpdateChildrenUserEventId
= Application::PostUserEvent(
701 LINK(this, AccessibleSlideSorterView::Implementation
,
702 UpdateChildrenCallback
));
705 void AccessibleSlideSorterView::Implementation::UpdateChildren()
707 //By default, all children should be accessible. So here workaround is to make all children visible.
708 // MT: THis was in UpdateVisibility, which has some similarity, and hg merge automatically has put it here. Correct?!
709 // In the IA2 CWS, also setting mnFirst/LastVisibleChild was commented out!
710 mnLastVisibleChild
= maPageObjects
.size();
712 if (mbModelChangeLocked
)
714 // Do nothing right now. When the flag is reset, this method is
719 const Pair
aRange (mrSlideSorter
.GetView().GetVisiblePageRange());
720 mnFirstVisibleChild
= aRange
.A();
721 mnLastVisibleChild
= aRange
.B();
723 // Release all children.
726 // Create new children for the modified visible range.
727 maPageObjects
.resize(mrSlideSorter
.GetModel().GetPageCount());
729 // No Visible children
730 if (mnFirstVisibleChild
== -1 && mnLastVisibleChild
== -1)
733 for (sal_Int32
nIndex(mnFirstVisibleChild
); nIndex
<=mnLastVisibleChild
; ++nIndex
)
734 GetAccessibleChild(nIndex
);
737 void AccessibleSlideSorterView::Implementation::Clear()
739 PageObjectList::iterator iPageObject
;
740 PageObjectList::iterator iEnd
= maPageObjects
.end();
741 for (iPageObject
=maPageObjects
.begin(); iPageObject
!=iEnd
; ++iPageObject
)
742 if (*iPageObject
!= NULL
)
744 mrAccessibleSlideSorter
.FireAccessibleEvent(
745 AccessibleEventId::CHILD
,
746 Any(Reference
<XAccessible
>(iPageObject
->get())),
749 Reference
<XComponent
> xComponent (Reference
<XWeak
>(iPageObject
->get()), UNO_QUERY
);
751 xComponent
->dispose();
754 maPageObjects
.clear();
757 sal_Int32
AccessibleSlideSorterView::Implementation::GetVisibleChildCount() const
759 if (mnFirstVisibleChild
<=mnLastVisibleChild
&& mnFirstVisibleChild
>=0)
760 return mnLastVisibleChild
- mnFirstVisibleChild
+ 1;
765 AccessibleSlideSorterObject
* AccessibleSlideSorterView::Implementation::GetVisibleChild (
768 assert(nIndex
>=0 && nIndex
<GetVisibleChildCount());
770 return GetAccessibleChild(nIndex
+mnFirstVisibleChild
);
773 AccessibleSlideSorterObject
* AccessibleSlideSorterView::Implementation::GetAccessibleChild (
776 AccessibleSlideSorterObject
* pChild
= NULL
;
778 if (nIndex
>=0 && (sal_uInt32
)nIndex
<maPageObjects
.size())
780 if (maPageObjects
[nIndex
] == NULL
)
782 ::sd::slidesorter::model::SharedPageDescriptor
pDescriptor(
783 mrSlideSorter
.GetModel().GetPageDescriptor(nIndex
));
784 if (pDescriptor
.get() != NULL
)
786 maPageObjects
[nIndex
] = new AccessibleSlideSorterObject(
787 &mrAccessibleSlideSorter
,
789 (pDescriptor
->GetPage()->GetPageNum()-1)/2);
791 mrAccessibleSlideSorter
.FireAccessibleEvent(
792 AccessibleEventId::CHILD
,
794 Any(Reference
<XAccessible
>(maPageObjects
[nIndex
].get())));
799 pChild
= maPageObjects
[nIndex
].get();
803 OSL_ASSERT(nIndex
>=0 && (sal_uInt32
)nIndex
<maPageObjects
.size());
809 void AccessibleSlideSorterView::Implementation::ConnectListeners()
811 StartListening (*mrSlideSorter
.GetModel().GetDocument());
812 if (mrSlideSorter
.GetViewShell() != NULL
)
813 StartListening (*mrSlideSorter
.GetViewShell());
814 mbListeningToDocument
= true;
816 if (mpWindow
!= nullptr)
817 mpWindow
->AddEventListener(
818 LINK(this,AccessibleSlideSorterView::Implementation
,WindowEventListener
));
820 mrSlideSorter
.GetController().GetSelectionManager()->AddSelectionChangeListener(
821 LINK(this,AccessibleSlideSorterView::Implementation
,SelectionChangeListener
));
822 mrSlideSorter
.GetController().GetFocusManager().AddFocusChangeListener(
823 LINK(this,AccessibleSlideSorterView::Implementation
,FocusChangeListener
));
824 mrSlideSorter
.GetView().AddVisibilityChangeListener(
825 LINK(this,AccessibleSlideSorterView::Implementation
,VisibilityChangeListener
));
828 void AccessibleSlideSorterView::Implementation::ReleaseListeners()
830 mrSlideSorter
.GetController().GetFocusManager().RemoveFocusChangeListener(
831 LINK(this,AccessibleSlideSorterView::Implementation
,FocusChangeListener
));
832 mrSlideSorter
.GetController().GetSelectionManager()->RemoveSelectionChangeListener(
833 LINK(this,AccessibleSlideSorterView::Implementation
,SelectionChangeListener
));
834 mrSlideSorter
.GetView().RemoveVisibilityChangeListener(
835 LINK(this,AccessibleSlideSorterView::Implementation
,VisibilityChangeListener
));
837 if (mpWindow
!= nullptr)
838 mpWindow
->RemoveEventListener(
839 LINK(this,AccessibleSlideSorterView::Implementation
,WindowEventListener
));
841 if (mbListeningToDocument
)
843 if (mrSlideSorter
.GetViewShell() != NULL
)
844 StartListening(*mrSlideSorter
.GetViewShell());
845 EndListening (*mrSlideSorter
.GetModel().GetDocument());
846 mbListeningToDocument
= false;
850 void AccessibleSlideSorterView::Implementation::Notify (
852 const SfxHint
& rHint
)
854 const SdrHint
* pSdrHint
= dynamic_cast<const SdrHint
*>(&rHint
);
857 switch (pSdrHint
->GetKind())
859 case HINT_PAGEORDERCHG
:
860 RequestUpdateChildren();
866 else if (dynamic_cast<const sd::ViewShellHint
*>(&rHint
))
868 const sd::ViewShellHint
& rViewShellHint
= static_cast<const sd::ViewShellHint
&>(rHint
);
869 switch (rViewShellHint
.GetHintId())
871 case sd::ViewShellHint::HINT_COMPLEX_MODEL_CHANGE_START
:
872 mbModelChangeLocked
= true;
875 case sd::ViewShellHint::HINT_COMPLEX_MODEL_CHANGE_END
:
876 mbModelChangeLocked
= false;
877 RequestUpdateChildren();
885 void AccessibleSlideSorterView::SwitchViewActivated()
887 // Firstly, set focus to view
888 this->FireAccessibleEvent(AccessibleEventId::STATE_CHANGED
,
890 Any(AccessibleStateType::FOCUSED
));
895 void AccessibleSlideSorterView::Implementation::Activated()
897 mrSlideSorter
.GetController().GetFocusManager().ShowFocus();
901 IMPL_LINK(AccessibleSlideSorterView::Implementation
, WindowEventListener
, VclWindowEvent
*, pEvent
)
903 switch (pEvent
->GetId())
905 case VCLEVENT_WINDOW_MOVE
:
906 case VCLEVENT_WINDOW_RESIZE
:
907 RequestUpdateChildren();
910 case VCLEVENT_WINDOW_GETFOCUS
:
911 case VCLEVENT_WINDOW_LOSEFOCUS
:
912 mrAccessibleSlideSorter
.FireAccessibleEvent(
913 AccessibleEventId::SELECTION_CHANGED
,
923 IMPL_LINK_NOARG(AccessibleSlideSorterView::Implementation
, SelectionChangeListener
)
925 if (mnSelectionChangeUserEventId
== 0)
926 mnSelectionChangeUserEventId
= Application::PostUserEvent(
927 LINK(this, AccessibleSlideSorterView::Implementation
, BroadcastSelectionChange
));
931 IMPL_LINK_NOARG(AccessibleSlideSorterView::Implementation
, BroadcastSelectionChange
)
933 mnSelectionChangeUserEventId
= 0;
934 mrAccessibleSlideSorter
.FireAccessibleEvent(
935 AccessibleEventId::SELECTION_CHANGED
,
941 IMPL_LINK_NOARG(AccessibleSlideSorterView::Implementation
, FocusChangeListener
)
943 sal_Int32
nNewFocusedIndex (
944 mrSlideSorter
.GetController().GetFocusManager().GetFocusedPageIndex());
946 bool bHasFocus
= mrSlideSorter
.GetController().GetFocusManager().IsFocusShowing();
948 nNewFocusedIndex
= -1;
950 // add a checker whether the focus event is sent out. Only after sent, the mnFocusedIndex should be updated.
951 bool bSentFocus
= false;
952 if (nNewFocusedIndex
!= mnFocusedIndex
)
954 if (mnFocusedIndex
>= 0)
956 AccessibleSlideSorterObject
* pObject
= GetAccessibleChild(mnFocusedIndex
);
959 pObject
->FireAccessibleEvent(
960 AccessibleEventId::STATE_CHANGED
,
961 Any(AccessibleStateType::FOCUSED
),
966 if (nNewFocusedIndex
>= 0)
968 AccessibleSlideSorterObject
* pObject
= GetAccessibleChild(nNewFocusedIndex
);
971 pObject
->FireAccessibleEvent(
972 AccessibleEventId::STATE_CHANGED
,
974 Any(AccessibleStateType::FOCUSED
));
979 mnFocusedIndex
= nNewFocusedIndex
;
984 IMPL_LINK_NOARG(AccessibleSlideSorterView::Implementation
, UpdateChildrenCallback
)
986 mnUpdateChildrenUserEventId
= 0;
992 IMPL_LINK_NOARG(AccessibleSlideSorterView::Implementation
, VisibilityChangeListener
)
998 } // end of namespace ::accessibility
1000 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */