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 "PresenterViewFactory.hxx"
21 #include "PresenterPaneContainer.hxx"
22 #include "PresenterHelper.hxx"
23 #include "PresenterHelpView.hxx"
24 #include "PresenterNotesView.hxx"
25 #include "PresenterSlideShowView.hxx"
26 #include "PresenterSlidePreview.hxx"
27 #include "PresenterSlideSorter.hxx"
28 #include "PresenterToolBar.hxx"
29 #include <com/sun/star/beans/XPropertySet.hpp>
30 #include <com/sun/star/drawing/framework/ResourceId.hpp>
31 #include <com/sun/star/drawing/framework/XControllerManager.hpp>
32 #include <com/sun/star/drawing/framework/XConfigurationController.hpp>
33 #include <com/sun/star/drawing/XDrawPages.hpp>
34 #include <com/sun/star/drawing/XDrawPagesSupplier.hpp>
35 #include <com/sun/star/drawing/XSlideSorterBase.hpp>
36 #include <com/sun/star/presentation/XSlideShow.hpp>
37 #include <com/sun/star/presentation/XSlideShowView.hpp>
38 #include <cppuhelper/compbase1.hxx>
39 #include <boost/bind.hpp>
41 using namespace ::com::sun::star
;
42 using namespace ::com::sun::star::uno
;
43 using namespace ::com::sun::star::drawing::framework
;
45 namespace sdext
{ namespace presenter
{
47 const OUString
PresenterViewFactory::msCurrentSlidePreviewViewURL(
48 "private:resource/view/Presenter/CurrentSlidePreview");
49 const OUString
PresenterViewFactory::msNextSlidePreviewViewURL(
50 "private:resource/view/Presenter/NextSlidePreview");
51 const OUString
PresenterViewFactory::msNotesViewURL(
52 "private:resource/view/Presenter/Notes");
53 const OUString
PresenterViewFactory::msToolBarViewURL(
54 "private:resource/view/Presenter/ToolBar");
55 const OUString
PresenterViewFactory::msSlideSorterURL(
56 "private:resource/view/Presenter/SlideSorter");
57 const OUString
PresenterViewFactory::msHelpViewURL(
58 "private:resource/view/Presenter/Help");
62 /** By default the PresenterSlidePreview shows the preview of the current
63 slide. This adapter class makes it display the preview of the next
66 class NextSlidePreview
: public PresenterSlidePreview
70 const css::uno::Reference
<css::uno::XComponentContext
>& rxContext
,
71 const css::uno::Reference
<css::drawing::framework::XResourceId
>& rxViewId
,
72 const css::uno::Reference
<css::drawing::framework::XPane
>& rxAnchorPane
,
73 const ::rtl::Reference
<PresenterController
>& rpPresenterController
)
74 : PresenterSlidePreview(rxContext
, rxViewId
, rxAnchorPane
, rpPresenterController
)
77 virtual ~NextSlidePreview() {}
78 virtual void SAL_CALL
setCurrentPage (
79 const css::uno::Reference
<css::drawing::XDrawPage
>& rxSlide
)
80 throw (css::uno::RuntimeException
, std::exception
) SAL_OVERRIDE
82 Reference
<presentation::XSlideShowController
> xSlideShowController (
83 mpPresenterController
->GetSlideShowController());
84 Reference
<drawing::XDrawPage
> xSlide
;
85 if (xSlideShowController
.is())
87 const sal_Int32
nCount (xSlideShowController
->getSlideCount());
88 sal_Int32
nNextSlideIndex (-1);
89 if (xSlideShowController
->getCurrentSlide() == rxSlide
)
91 nNextSlideIndex
= xSlideShowController
->getNextSlideIndex();
95 for (sal_Int32 nIndex
=0; nIndex
<nCount
; ++nIndex
)
97 if (rxSlide
== Reference
<drawing::XDrawPage
>(
98 xSlideShowController
->getSlideByIndex(nIndex
), UNO_QUERY
))
100 nNextSlideIndex
= nIndex
+ 1;
104 if (nNextSlideIndex
>= 0)
106 if (nNextSlideIndex
< nCount
)
108 xSlide
= Reference
<drawing::XDrawPage
>(
109 xSlideShowController
->getSlideByIndex(nNextSlideIndex
),
114 PresenterSlidePreview::setCurrentPage(xSlide
);
118 } // end of anonymous namespace
120 //===== PresenterViewFactory ==============================================
122 PresenterViewFactory::PresenterViewFactory (
123 const Reference
<uno::XComponentContext
>& rxContext
,
124 const Reference
<frame::XController
>& rxController
,
125 const ::rtl::Reference
<PresenterController
>& rpPresenterController
)
126 : PresenterViewFactoryInterfaceBase(m_aMutex
),
127 mxComponentContext(rxContext
),
128 mxConfigurationController(),
129 mxControllerWeak(rxController
),
130 mpPresenterController(rpPresenterController
),
135 Reference
<drawing::framework::XResourceFactory
> PresenterViewFactory::Create (
136 const Reference
<uno::XComponentContext
>& rxContext
,
137 const Reference
<frame::XController
>& rxController
,
138 const ::rtl::Reference
<PresenterController
>& rpPresenterController
)
140 rtl::Reference
<PresenterViewFactory
> pFactory (
141 new PresenterViewFactory(rxContext
,rxController
,rpPresenterController
));
142 pFactory
->Register(rxController
);
143 return Reference
<drawing::framework::XResourceFactory
>(
144 static_cast<XWeak
*>(pFactory
.get()), UNO_QUERY
);
147 void PresenterViewFactory::Register (const Reference
<frame::XController
>& rxController
)
151 // Get the configuration controller.
152 Reference
<XControllerManager
> xCM (rxController
, UNO_QUERY_THROW
);
153 mxConfigurationController
= xCM
->getConfigurationController();
154 if ( ! mxConfigurationController
.is())
156 throw RuntimeException();
160 mxConfigurationController
->addResourceFactory(msCurrentSlidePreviewViewURL
, this);
161 mxConfigurationController
->addResourceFactory(msNextSlidePreviewViewURL
, this);
162 mxConfigurationController
->addResourceFactory(msNotesViewURL
, this);
163 mxConfigurationController
->addResourceFactory(msToolBarViewURL
, this);
164 mxConfigurationController
->addResourceFactory(msSlideSorterURL
, this);
165 mxConfigurationController
->addResourceFactory(msHelpViewURL
, this);
168 catch (RuntimeException
&)
171 if (mxConfigurationController
.is())
172 mxConfigurationController
->removeResourceFactoryForReference(this);
173 mxConfigurationController
= NULL
;
179 PresenterViewFactory::~PresenterViewFactory()
183 void SAL_CALL
PresenterViewFactory::disposing()
184 throw (RuntimeException
)
186 if (mxConfigurationController
.is())
187 mxConfigurationController
->removeResourceFactoryForReference(this);
188 mxConfigurationController
= NULL
;
190 if (mpResourceCache
.get() != NULL
)
192 // Dispose all views in the cache.
193 ResourceContainer::const_iterator
iView (mpResourceCache
->begin());
194 ResourceContainer::const_iterator
iEnd (mpResourceCache
->end());
195 for ( ; iView
!=iEnd
; ++iView
)
199 Reference
<lang::XComponent
> xComponent (iView
->second
.first
, UNO_QUERY
);
201 xComponent
->dispose();
203 catch (lang::DisposedException
&)
207 mpResourceCache
.reset();
211 //----- XViewFactory ----------------------------------------------------------
213 Reference
<XResource
> SAL_CALL
PresenterViewFactory::createResource (
214 const Reference
<XResourceId
>& rxViewId
)
215 throw (RuntimeException
, std::exception
)
219 Reference
<XResource
> xView
;
223 Reference
<XPane
> xAnchorPane (
224 mxConfigurationController
->getResource(rxViewId
->getAnchor()),
226 xView
= GetViewFromCache(rxViewId
, xAnchorPane
);
228 xView
= CreateView(rxViewId
, xAnchorPane
);
230 // Activate the view.
231 PresenterPaneContainer::SharedPaneDescriptor
pDescriptor (
232 mpPresenterController
->GetPaneContainer()->FindPaneId(rxViewId
->getAnchor()));
233 if (pDescriptor
.get() != NULL
)
234 pDescriptor
->SetActivationState(true);
240 void SAL_CALL
PresenterViewFactory::releaseResource (const Reference
<XResource
>& rxView
)
241 throw (RuntimeException
, std::exception
)
248 // Deactivate the view.
249 PresenterPaneContainer::SharedPaneDescriptor
pDescriptor (
250 mpPresenterController
->GetPaneContainer()->FindPaneId(
251 rxView
->getResourceId()->getAnchor()));
252 if (pDescriptor
.get() != NULL
)
253 pDescriptor
->SetActivationState(false);
255 // Dispose only views that we can not put into the cache.
256 CachablePresenterView
* pView
= dynamic_cast<CachablePresenterView
*>(rxView
.get());
257 if (pView
== NULL
|| mpResourceCache
.get()==NULL
)
262 pView
->ReleaseView();
263 Reference
<lang::XComponent
> xComponent (rxView
, UNO_QUERY
);
265 xComponent
->dispose();
267 catch (lang::DisposedException
&)
269 // Do not let disposed exceptions get out. It might be interpreted
270 // as coming from the factory, which would then be removed from the
271 // drawing framework.
276 // Put cachable views in the cache.
277 Reference
<XResourceId
> xViewId (rxView
->getResourceId());
280 Reference
<XPane
> xAnchorPane (
281 mxConfigurationController
->getResource(xViewId
->getAnchor()),
283 (*mpResourceCache
)[xViewId
->getResourceURL()]
284 = ViewResourceDescriptor(Reference
<XView
>(rxView
, UNO_QUERY
), xAnchorPane
);
285 pView
->DeactivatePresenterView();
292 Reference
<XResource
> PresenterViewFactory::GetViewFromCache(
293 const Reference
<XResourceId
>& rxViewId
,
294 const Reference
<XPane
>& rxAnchorPane
) const
296 if (mpResourceCache
.get() == NULL
)
301 const OUString
sResourceURL (rxViewId
->getResourceURL());
303 // Can we use a view from the cache?
304 ResourceContainer::const_iterator
iView (mpResourceCache
->find(sResourceURL
));
305 if (iView
!= mpResourceCache
->end())
307 // The view is in the container but it can only be used if
308 // the anchor pane is the same now as it was at creation of
310 if (iView
->second
.second
== rxAnchorPane
)
312 CachablePresenterView
* pView
313 = dynamic_cast<CachablePresenterView
*>(iView
->second
.first
.get());
315 pView
->ActivatePresenterView();
316 return Reference
<XResource
>(iView
->second
.first
, UNO_QUERY
);
319 // Right view, wrong pane. Create a new view.
322 catch (RuntimeException
&)
328 Reference
<XResource
> PresenterViewFactory::CreateView(
329 const Reference
<XResourceId
>& rxViewId
,
330 const Reference
<XPane
>& rxAnchorPane
)
332 Reference
<XView
> xView
;
336 const OUString
sResourceURL (rxViewId
->getResourceURL());
338 if (sResourceURL
.equals(msCurrentSlidePreviewViewURL
))
340 xView
= CreateSlideShowView(rxViewId
);
342 else if (sResourceURL
.equals(msNotesViewURL
))
344 xView
= CreateNotesView(rxViewId
, rxAnchorPane
);
346 else if (sResourceURL
.equals(msNextSlidePreviewViewURL
))
348 xView
= CreateSlidePreviewView(rxViewId
, rxAnchorPane
);
350 else if (sResourceURL
.equals(msToolBarViewURL
))
352 xView
= CreateToolBarView(rxViewId
);
354 else if (sResourceURL
.equals(msSlideSorterURL
))
356 xView
= CreateSlideSorterView(rxViewId
);
358 else if (sResourceURL
.equals(msHelpViewURL
))
360 xView
= CreateHelpView(rxViewId
);
364 CachablePresenterView
* pView
= dynamic_cast<CachablePresenterView
*>(xView
.get());
366 pView
->ActivatePresenterView();
368 catch (RuntimeException
&)
376 Reference
<XView
> PresenterViewFactory::CreateSlideShowView(
377 const Reference
<XResourceId
>& rxViewId
) const
379 Reference
<XView
> xView
;
381 if ( ! mxConfigurationController
.is())
383 if ( ! mxComponentContext
.is())
388 rtl::Reference
<PresenterSlideShowView
> pShowView (
389 new PresenterSlideShowView(
392 Reference
<frame::XController
>(mxControllerWeak
),
393 mpPresenterController
));
394 pShowView
->LateInit();
395 xView
= Reference
<XView
>(pShowView
.get());
397 catch (RuntimeException
&)
405 Reference
<XView
> PresenterViewFactory::CreateSlidePreviewView(
406 const Reference
<XResourceId
>& rxViewId
,
407 const Reference
<XPane
>& rxAnchorPane
) const
409 Reference
<XView
> xView
;
411 if ( ! mxConfigurationController
.is())
413 if ( ! mxComponentContext
.is())
418 xView
= Reference
<XView
>(
419 static_cast<XWeak
*>(new NextSlidePreview(
423 mpPresenterController
)),
426 catch (RuntimeException
&)
434 Reference
<XView
> PresenterViewFactory::CreateToolBarView(
435 const Reference
<XResourceId
>& rxViewId
) const
437 return new PresenterToolBarView(
440 Reference
<frame::XController
>(mxControllerWeak
),
441 mpPresenterController
);
444 Reference
<XView
> PresenterViewFactory::CreateNotesView(
445 const Reference
<XResourceId
>& rxViewId
,
446 const Reference
<XPane
>& rxAnchorPane
) const
449 Reference
<XView
> xView
;
451 if ( ! mxConfigurationController
.is())
453 if ( ! mxComponentContext
.is())
458 xView
= Reference
<XView
>(static_cast<XWeak
*>(
459 new PresenterNotesView(
462 Reference
<frame::XController
>(mxControllerWeak
),
463 mpPresenterController
)),
466 catch (RuntimeException
&)
474 Reference
<XView
> PresenterViewFactory::CreateSlideSorterView(
475 const Reference
<XResourceId
>& rxViewId
) const
477 Reference
<XView
> xView
;
479 if ( ! mxConfigurationController
.is())
481 if ( ! mxComponentContext
.is())
486 rtl::Reference
<PresenterSlideSorter
> pView (
487 new PresenterSlideSorter(
490 Reference
<frame::XController
>(mxControllerWeak
),
491 mpPresenterController
));
492 PresenterPaneContainer::SharedPaneDescriptor
pDescriptor (
493 mpPresenterController
->GetPaneContainer()->FindPaneId(rxViewId
->getAnchor()));
494 if (pDescriptor
.get() != NULL
)
495 pDescriptor
->maActivator
= ::boost::bind(
496 &PresenterSlideSorter::SetActiveState
, _1
);
499 catch (RuntimeException
&)
507 Reference
<XView
> PresenterViewFactory::CreateHelpView(
508 const Reference
<XResourceId
>& rxViewId
) const
510 return Reference
<XView
>(new PresenterHelpView(
513 Reference
<frame::XController
>(mxControllerWeak
),
514 mpPresenterController
));
517 void PresenterViewFactory::ThrowIfDisposed() const
518 throw (::com::sun::star::lang::DisposedException
)
520 if (rBHelper
.bDisposed
|| rBHelper
.bInDispose
)
522 throw lang::DisposedException (
524 "PresenterViewFactory object has already been disposed"),
525 const_cast<uno::XWeak
*>(static_cast<const uno::XWeak
*>(this)));
529 //===== CachablePresenterView =================================================
531 CachablePresenterView::CachablePresenterView()
532 : mbIsPresenterViewActive(true)
536 void CachablePresenterView::ActivatePresenterView()
538 mbIsPresenterViewActive
= true;
541 void CachablePresenterView::DeactivatePresenterView()
543 mbIsPresenterViewActive
= false;
546 void CachablePresenterView::ReleaseView()
552 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */