Line data Source code
1 : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 : /*
3 : * This file is part of the LibreOffice project.
4 : *
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/.
8 : *
9 : * This file incorporates work covered by the following license notice:
10 : *
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 .
18 : */
19 :
20 :
21 : #include "taskpane/ToolPanelViewShell.hxx"
22 :
23 : #include "TaskPaneShellManager.hxx"
24 : #include "TaskPaneFocusManager.hxx"
25 : #include "taskpane/TaskPaneControlFactory.hxx"
26 : #include "controls/MasterPagesPanel.hxx"
27 : #include "LayoutMenu.hxx"
28 : #include "DrawDocShell.hxx"
29 : #include "controls/TableDesignPanel.hxx"
30 : #include "controls/CustomAnimationPanel.hxx"
31 : #include "controls/SlideTransitionPanel.hxx"
32 : #include "controls/MasterPagesSelector.hxx"
33 : #include "ToolPanel.hxx"
34 : #include "ToolPanelUIElement.hxx"
35 : #include "PaneDockingWindow.hxx"
36 : #include "FrameView.hxx"
37 : #include "Window.hxx"
38 : #include "sdmod.hxx"
39 : #include "app.hrc"
40 : #include "glob.hrc"
41 : #include "res_bmp.hrc"
42 : #include "helpids.h"
43 : #include "strings.hrc"
44 : #include "sdresid.hxx"
45 : #include "framework/FrameworkHelper.hxx"
46 :
47 : #include <com/sun/star/drawing/framework/XResourceId.hpp>
48 : #include <com/sun/star/drawing/framework/ResourceActivationMode.hpp>
49 : #include <com/sun/star/drawing/framework/AnchorBindingMode.hpp>
50 : #include <com/sun/star/drawing/XDrawSubController.hpp>
51 :
52 : #include <svtools/toolpanel/toolpanel.hxx>
53 : #include <svtools/toolpanel/toolpaneldeck.hxx>
54 : #include <svx/dlgctrl.hxx>
55 : #include <sfx2/taskpane.hxx>
56 : #include <sfx2/imagemgr.hxx>
57 : #include <sfx2/bindings.hxx>
58 : #include <sfx2/dispatch.hxx>
59 : #include <sfx2/viewfrm.hxx>
60 : #include <sfx2/msg.hxx>
61 : #include <sfx2/objface.hxx>
62 : #include <svx/colrctrl.hxx>
63 : #include <svx/xtable.hxx>
64 : #include <vcl/dockwin.hxx>
65 : #include "sdtreelb.hxx"
66 : #include "DrawViewShell.hxx"
67 : #include "drawdoc.hxx"
68 : #include "ViewShellBase.hxx"
69 : #include <svx/ruler.hxx>
70 : #include <vcl/svapp.hxx>
71 : #include <vcl/toolbox.hxx>
72 : #include <tools/diagnose_ex.h>
73 : #include <unotools/confignode.hxx>
74 : #include <comphelper/processfactory.hxx>
75 : #include <comphelper/componentcontext.hxx>
76 : #include <cppuhelper/implbase1.hxx>
77 : #include <cppuhelper/basemutex.hxx>
78 :
79 : #include <vector>
80 :
81 : using namespace ::sd::toolpanel;
82 :
83 : #define ToolPanelViewShell
84 : #include "sdslots.hxx"
85 :
86 : /** === begin UNO using === **/
87 : using ::com::sun::star::uno::Reference;
88 : using ::com::sun::star::uno::XInterface;
89 : using ::com::sun::star::uno::UNO_QUERY;
90 : using ::com::sun::star::uno::UNO_QUERY_THROW;
91 : using ::com::sun::star::uno::UNO_SET_THROW;
92 : using ::com::sun::star::uno::Exception;
93 : using ::com::sun::star::uno::RuntimeException;
94 : using ::com::sun::star::uno::Any;
95 : using ::com::sun::star::uno::makeAny;
96 : using ::com::sun::star::uno::Sequence;
97 : using ::com::sun::star::uno::Type;
98 : using ::com::sun::star::accessibility::XAccessible;
99 : using ::com::sun::star::drawing::XDrawSubController;
100 : using ::com::sun::star::frame::XFrame;
101 : using ::com::sun::star::drawing::framework::XResourceId;
102 : using ::com::sun::star::drawing::framework::XConfigurationChangeListener;
103 : using ::com::sun::star::drawing::framework::ConfigurationChangeEvent;
104 : using ::com::sun::star::lang::EventObject;
105 : using ::com::sun::star::lang::DisposedException;
106 : using ::com::sun::star::drawing::framework::XConfigurationControllerBroadcaster;
107 : using ::com::sun::star::drawing::framework::XConfigurationController;
108 : using ::com::sun::star::drawing::framework::XConfiguration;
109 : using ::com::sun::star::drawing::framework::AnchorBindingMode_DIRECT;
110 : using ::com::sun::star::ui::XUIElement;
111 : using ::com::sun::star::ui::XToolPanel;
112 : using ::com::sun::star::drawing::framework::ResourceActivationMode_REPLACE;
113 : /** === end UNO using === **/
114 :
115 : using ::sd::framework::FrameworkHelper;
116 :
117 : namespace sd { namespace toolpanel {
118 :
119 : // =====================================================================================================================
120 : // = misc helper
121 : // =====================================================================================================================
122 : // ---------------------------------------------------------------------------------------------------------------------
123 0 : PanelId GetStandardPanelId( const ::rtl::OUString& i_rTaskPanelResourceURL, const bool i_bIgnoreUnknown )
124 : {
125 0 : PanelId ePanelId( PID_UNKNOWN );
126 :
127 0 : if ( i_rTaskPanelResourceURL.equals( FrameworkHelper::msMasterPagesTaskPanelURL ) )
128 : {
129 0 : ePanelId = PID_MASTER_PAGES;
130 : }
131 0 : else if ( i_rTaskPanelResourceURL.equals( FrameworkHelper::msLayoutTaskPanelURL ) )
132 : {
133 0 : ePanelId = PID_LAYOUT;
134 : }
135 0 : else if ( i_rTaskPanelResourceURL.equals( FrameworkHelper::msTableDesignPanelURL ) )
136 : {
137 0 : ePanelId = PID_TABLE_DESIGN;
138 : }
139 0 : else if ( i_rTaskPanelResourceURL.equals( FrameworkHelper::msCustomAnimationTaskPanelURL ) )
140 : {
141 0 : ePanelId = PID_CUSTOM_ANIMATION;
142 : }
143 0 : else if ( i_rTaskPanelResourceURL.equals( FrameworkHelper::msSlideTransitionTaskPanelURL ) )
144 : {
145 0 : ePanelId = PID_SLIDE_TRANSITION;
146 : }
147 : else
148 : {
149 : OSL_ENSURE( i_bIgnoreUnknown, "GetStandardPanelId: cannot translate the given resource URL!" );
150 : (void)i_bIgnoreUnknown;
151 : }
152 :
153 0 : return ePanelId;
154 : }
155 :
156 : // ---------------------------------------------------------------------------------------------------------------------
157 0 : PanelId GetStandardPanelId( const ::rtl::OUString& i_rTaskPanelResourceURL )
158 : {
159 0 : return GetStandardPanelId( i_rTaskPanelResourceURL, false );
160 : }
161 :
162 : // =====================================================================================================================
163 : // = ConfigurationListener - declaration
164 : // =====================================================================================================================
165 : typedef ::cppu::WeakImplHelper1 < XConfigurationChangeListener
166 : > ConfigurationListener_Base;
167 :
168 : class ConfigurationListener :public ::cppu::BaseMutex
169 : ,public ConfigurationListener_Base
170 : {
171 : public:
172 : ConfigurationListener( ToolPanelViewShell_Impl& i_rShellImpl );
173 :
174 : // XConfigurationChangeListener
175 : virtual void SAL_CALL notifyConfigurationChange( const ConfigurationChangeEvent& aEvent ) throw (RuntimeException);
176 :
177 : // XEventListener
178 : virtual void SAL_CALL disposing( const EventObject& Source ) throw (RuntimeException);
179 :
180 : // XComponent equivalents (not available per UNO interface)
181 : void dispose();
182 :
183 : protected:
184 : ~ConfigurationListener();
185 :
186 0 : void impl_checkDisposed_throw()
187 : {
188 0 : if ( !m_pShellImpl )
189 0 : throw DisposedException( ::rtl::OUString(), *this );
190 0 : }
191 :
192 : private:
193 : ToolPanelViewShell_Impl* m_pShellImpl;
194 : };
195 :
196 : // =====================================================================================================================
197 : // = ToolPanelViewShell_Impl - declaration
198 : // =====================================================================================================================
199 : /** Inner implementation class of ToolPanelViewShell.
200 : */
201 : class ToolPanelViewShell_Impl :public ::boost::noncopyable
202 : ,public ::svt::IToolPanelDeckListener
203 : ,public ::sfx2::IToolPanelCompare
204 : {
205 : public:
206 : static const size_t mnInvalidId = static_cast< size_t >( -1 );
207 :
208 : ToolPanelViewShell_Impl( ToolPanelViewShell& i_rPanelViewShell, ::Window& i_rPanelDeckParent );
209 : virtual ~ToolPanelViewShell_Impl();
210 :
211 0 : ToolPanelViewShell& GetAntiImpl() { return m_rPanelViewShell; }
212 :
213 : /** Here the panels are created that are shown in the task pane.
214 : */
215 : void Setup();
216 :
217 : /** clean up the instance
218 : */
219 : void Cleanup();
220 :
221 : /** activates the panel which has the given resource URL
222 : */
223 : void ActivatePanelByResource( const ::rtl::OUString& i_rPanelResourceURL );
224 :
225 : /** de-activates the panel given by its resource URL, bypassing the configuration controller
226 :
227 : If the panel is not active currently, nothing happens.
228 : */
229 : void DeactivatePanelByResource( const ::rtl::OUString& i_rPanelResourceURL );
230 :
231 : /** provides access to the the VCL window of the panel deck
232 : */
233 0 : ::sfx2::ModuleTaskPane& GetTaskPane() { return *m_pTaskPane; }
234 : const ::sfx2::ModuleTaskPane& GetTaskPane() const { return *m_pTaskPane; }
235 :
236 0 : ::svt::ToolPanelDeck& GetToolPanelDeck() { return GetTaskPane().GetPanelDeck(); }
237 : const ::svt::ToolPanelDeck& GetToolPanelDeck() const { return GetTaskPane().GetPanelDeck(); }
238 :
239 : Reference< XAccessible >
240 : CreateAccessible( ::sd::Window& i_rWindow );
241 :
242 : void ConnectToDockingWindow();
243 :
244 : private:
245 : // IToolPanelDeckListener overridables
246 : virtual void PanelInserted( const ::svt::PToolPanel& i_pPanel, const size_t i_nPosition );
247 : virtual void PanelRemoved( const size_t i_nPosition );
248 : virtual void ActivePanelChanged( const ::boost::optional< size_t >& i_rOldActive, const ::boost::optional< size_t >& i_rNewActive );
249 : virtual void LayouterChanged( const ::svt::PDeckLayouter& i_rNewLayouter );
250 : virtual void Dying();
251 :
252 : // IToolPanelCompare overridables
253 : virtual short compareToolPanelsURLs( const ::rtl::OUString& i_rLHS, const ::rtl::OUString& i_rRHS ) const;
254 :
255 : private:
256 0 : struct InitialPanel
257 : {
258 : ::rtl::OUString sPanelResourceURL;
259 : bool bActivateDirectly;
260 0 : InitialPanel()
261 : :sPanelResourceURL()
262 0 : ,bActivateDirectly( true )
263 : {
264 0 : }
265 : };
266 : InitialPanel impl_determineInitialPanel();
267 : ::rtl::OUString impl_getPanelURL( const ::boost::optional< size_t >& i_rPanel );
268 :
269 : private:
270 : ToolPanelViewShell& m_rPanelViewShell;
271 : ::boost::scoped_ptr< ::sfx2::ModuleTaskPane > m_pTaskPane;
272 : SAL_WNODEPRECATED_DECLARATIONS_PUSH
273 : ::std::auto_ptr< ::sfx2::TaskPaneController > m_pTaskPaneController;
274 : SAL_WNODEPRECATED_DECLARATIONS_POP
275 : ::rtl::Reference< ConfigurationListener > m_pConfigListener;
276 : bool m_bInitialized;
277 : };
278 :
279 : // =====================================================================================================================
280 : // = ConfigurationListener - implementation
281 : // =====================================================================================================================
282 : // ---------------------------------------------------------------------------------------------------------------------
283 0 : ConfigurationListener::ConfigurationListener( ToolPanelViewShell_Impl& i_rShellImpl )
284 0 : :m_pShellImpl( &i_rShellImpl )
285 : {
286 0 : ::boost::shared_ptr< FrameworkHelper > pFrameworkHelper( FrameworkHelper::Instance( i_rShellImpl.GetAntiImpl().GetViewShellBase() ) );
287 0 : Reference< XConfigurationControllerBroadcaster > xBroadcaster;
288 0 : if ( pFrameworkHelper.get() )
289 0 : xBroadcaster.set( pFrameworkHelper->GetConfigurationController().get() );
290 0 : ENSURE_OR_THROW( pFrameworkHelper.get(), "no access to the config controller" );
291 :
292 0 : osl_atomic_increment( &m_refCount );
293 : {
294 0 : xBroadcaster->addConfigurationChangeListener( this, ::rtl::OUString(), Any() );
295 : }
296 0 : osl_atomic_decrement( &m_refCount );
297 0 : }
298 :
299 : // ---------------------------------------------------------------------------------------------------------------------
300 0 : ConfigurationListener::~ConfigurationListener()
301 : {
302 0 : }
303 :
304 : // ---------------------------------------------------------------------------------------------------------------------
305 0 : void SAL_CALL ConfigurationListener::notifyConfigurationChange( const ConfigurationChangeEvent& i_rEvent ) throw (RuntimeException)
306 : {
307 0 : ::osl::MutexGuard aGuard( m_aMutex );
308 0 : impl_checkDisposed_throw();
309 :
310 : // is this an event we're interested in?
311 0 : if ( i_rEvent.Type != FrameworkHelper::msResourceActivationEvent )
312 : return;
313 :
314 : // is this a resource we're interested in? Must be anchored in the task pane ...
315 0 : Reference< XResourceId > xAnchorId;
316 0 : if ( i_rEvent.ResourceId.is() )
317 0 : xAnchorId = i_rEvent.ResourceId->getAnchor();
318 0 : if ( !xAnchorId.is() )
319 : return;
320 0 : const ::rtl::OUString sAnchorURL( xAnchorId->getResourceURL() );
321 0 : if ( sAnchorURL != FrameworkHelper::msTaskPaneURL )
322 : return;
323 :
324 0 : m_pShellImpl->ActivatePanelByResource( i_rEvent.ResourceId->getResourceURL() );
325 : }
326 :
327 : // ---------------------------------------------------------------------------------------------------------------------
328 0 : void SAL_CALL ConfigurationListener::disposing( const EventObject& i_rEvent ) throw (RuntimeException)
329 : {
330 : (void)i_rEvent;
331 : {
332 0 : ::osl::MutexGuard aGuard( m_aMutex );
333 0 : impl_checkDisposed_throw();
334 : }
335 :
336 0 : dispose();
337 0 : }
338 :
339 : // ---------------------------------------------------------------------------------------------------------------------
340 0 : void ConfigurationListener::dispose()
341 : {
342 0 : ::osl::MutexGuard aGuard( m_aMutex );
343 0 : m_pShellImpl = NULL;
344 0 : }
345 :
346 : // =====================================================================================================================
347 : // = ToolPanelViewShell
348 : // =====================================================================================================================
349 : // ---------------------------------------------------------------------------------------------------------------------
350 9 : SFX_IMPL_INTERFACE(ToolPanelViewShell, SfxShell, SdResId(STR_TASKPANEVIEWSHELL))
351 : {
352 3 : }
353 :
354 : // ---------------------------------------------------------------------------------------------------------------------
355 0 : TYPEINIT1(ToolPanelViewShell, ViewShell);
356 :
357 : // ---------------------------------------------------------------------------------------------------------------------
358 0 : ToolPanelViewShell_Impl::InitialPanel ToolPanelViewShell_Impl::impl_determineInitialPanel()
359 : {
360 0 : InitialPanel aPanelToActivate;
361 0 : if ( GetAntiImpl().GetViewShellBase().GetDocShell()->GetDocumentType() == DOCUMENT_TYPE_DRAW )
362 : // for Draw, rely on SFX's default handling, which is to activate the previously active panel
363 0 : return aPanelToActivate;
364 :
365 : // Default to Layout panel, but check whether the requested configuration already contains a tool panel, in this case,
366 : // use that one.
367 0 : aPanelToActivate.sPanelResourceURL = FrameworkHelper::msLayoutTaskPanelURL;
368 0 : aPanelToActivate.bActivateDirectly = false;
369 : try
370 : {
371 0 : ::boost::shared_ptr< FrameworkHelper > pFrameworkHelper( FrameworkHelper::Instance( m_rPanelViewShell.GetViewShellBase() ) );
372 0 : const Reference< XResourceId > xToolPanelId( pFrameworkHelper->CreateResourceId( FrameworkHelper::msTaskPaneURL, FrameworkHelper::msRightPaneURL ) );
373 0 : Reference< XConfigurationController > xCC( pFrameworkHelper->GetConfigurationController(), UNO_QUERY_THROW );
374 0 : Reference< XConfiguration > xConfiguration( xCC->getRequestedConfiguration(), UNO_QUERY_THROW );
375 0 : Sequence< Reference< XResourceId > > aViewIds( xConfiguration->getResources(
376 : FrameworkHelper::CreateResourceId( FrameworkHelper::msTaskPaneURL, FrameworkHelper::msRightPaneURL ),
377 0 : FrameworkHelper::msTaskPanelURLPrefix, AnchorBindingMode_DIRECT ) );
378 :
379 0 : if ( aViewIds.getLength() > 0 )
380 : {
381 0 : const ::rtl::OUString sResourceURL( aViewIds[0]->getResourceURL() );
382 0 : PanelId nRequestedPanel = GetStandardPanelId( sResourceURL );
383 0 : if ( nRequestedPanel != PID_UNKNOWN )
384 : {
385 0 : aPanelToActivate.sPanelResourceURL = sResourceURL;
386 0 : aPanelToActivate.bActivateDirectly = true;
387 0 : }
388 0 : }
389 : }
390 0 : catch( const Exception& )
391 : {
392 : DBG_UNHANDLED_EXCEPTION();
393 : }
394 0 : return aPanelToActivate;
395 : }
396 :
397 : // ---------------------------------------------------------------------------------------------------------------------
398 0 : void ToolPanelViewShell_Impl::Setup()
399 : {
400 0 : if ( m_bInitialized )
401 0 : return;
402 0 : m_bInitialized = true;
403 :
404 : // initially activate a panel
405 0 : const InitialPanel aInitialPanel = impl_determineInitialPanel();
406 0 : if ( !aInitialPanel.sPanelResourceURL.isEmpty() )
407 : {
408 0 : if ( aInitialPanel.bActivateDirectly )
409 : {
410 0 : ActivatePanelByResource( aInitialPanel.sPanelResourceURL );
411 : }
412 : else
413 : {
414 0 : ::boost::shared_ptr< FrameworkHelper > pFrameworkHelper( FrameworkHelper::Instance( GetAntiImpl().GetViewShellBase() ) );
415 0 : pFrameworkHelper->RequestTaskPanel( aInitialPanel.sPanelResourceURL );
416 : }
417 : }
418 :
419 : // listen at the configuration
420 0 : m_pConfigListener.set( new ConfigurationListener( *this ) );
421 :
422 0 : m_pTaskPane->Show();
423 : }
424 :
425 : // ---------------------------------------------------------------------------------------------------------------------
426 0 : void ToolPanelViewShell_Impl::Cleanup()
427 : {
428 0 : if ( m_bInitialized )
429 : {
430 0 : if ( m_pConfigListener.is() )
431 0 : m_pConfigListener->dispose();
432 : }
433 0 : GetToolPanelDeck().RemoveListener( *this );
434 0 : m_pTaskPaneController.reset();
435 0 : m_pTaskPane.reset();
436 0 : }
437 :
438 : // ---------------------------------------------------------------------------------------------------------------------
439 0 : void ToolPanelViewShell_Impl::ActivatePanelByResource( const ::rtl::OUString& i_rResourceURL )
440 : {
441 : // determine position of the requested panel
442 0 : ::boost::optional< size_t > aPanelPos = GetTaskPane().GetPanelPos( i_rResourceURL );
443 : OSL_ENSURE( !!aPanelPos, "ToolPanelViewShell_Impl::ActivatePanelByResource: illegal panel resource, or illegal panel deck setup!" );
444 0 : if ( !!aPanelPos )
445 0 : GetToolPanelDeck().ActivatePanel( *aPanelPos );
446 0 : }
447 :
448 : // ---------------------------------------------------------------------------------------------------------------------
449 0 : void ToolPanelViewShell_Impl::DeactivatePanelByResource( const ::rtl::OUString& i_rPanelResourceURL )
450 : {
451 : // determine position of the requested panel
452 0 : ::boost::optional< size_t > aPanelPos = GetTaskPane().GetPanelPos( i_rPanelResourceURL );
453 : OSL_ENSURE( !!aPanelPos, "ToolPanelViewShell_Impl::DeactivatePanelByResource: illegal panel resource, or illegal panel deck setup!" );
454 0 : if ( !!aPanelPos )
455 : {
456 0 : if ( GetToolPanelDeck().GetActivePanel() == *aPanelPos )
457 0 : GetToolPanelDeck().ActivatePanel( ::boost::optional< size_t >() );
458 0 : }
459 0 : }
460 :
461 : // ---------------------------------------------------------------------------------------------------------------------
462 0 : void ToolPanelViewShell::Initialize()
463 : {
464 0 : mpImpl->Setup();
465 0 : }
466 :
467 : // ---------------------------------------------------------------------------------------------------------------------
468 0 : ToolPanelViewShell::ToolPanelViewShell( SfxViewFrame* pFrame, ViewShellBase& rViewShellBase, ::Window* pParentWindow,
469 : FrameView* pFrameViewArgument )
470 : :ViewShell(pFrame, pParentWindow, rViewShellBase)
471 0 : ,mpImpl( new ToolPanelViewShell_Impl( *this, *mpContentWindow.get() ) )
472 : ,mpSubShellManager()
473 0 : ,mnMenuId(0)
474 : {
475 0 : doShow();
476 :
477 0 : meShellType = ST_TASK_PANE;
478 :
479 0 : mpContentWindow->SetCenterAllowed( false );
480 0 : pParentWindow->SetStyle( pParentWindow->GetStyle() | WB_DIALOGCONTROL );
481 :
482 0 : GetParentWindow()->SetBackground( Wallpaper() );
483 0 : mpContentWindow->SetBackground( Wallpaper() );
484 :
485 0 : GetParentWindow()->SetHelpId(HID_SD_TASK_PANE);
486 :
487 0 : mpImpl->ConnectToDockingWindow();
488 :
489 0 : SetPool( &GetDoc()->GetPool() );
490 :
491 0 : if ( pFrameViewArgument )
492 0 : mpFrameView = pFrameViewArgument;
493 : else
494 0 : mpFrameView = new FrameView( GetDoc() );
495 0 : GetFrameView()->Connect();
496 :
497 : // Hide or delete unused controls that we have inherited from the
498 : // ViewShell base class.
499 0 : mpHorizontalScrollBar.reset();
500 0 : mpVerticalScrollBar.reset();
501 0 : mpScrollBarBox.reset();
502 0 : mpHorizontalRuler.reset();
503 0 : mpVerticalRuler.reset();
504 :
505 0 : SetName( rtl::OUString( "ToolPanelViewShell" ) );
506 :
507 : // enforce the creation of the Accessible object here.
508 : // In some not-always-to-reproduce situations, creating the accessible on demand only leads to some
509 : // cycliy parenthood references between the involved objects, which make some AT tools (accerciser, in particular)
510 : // loop (which is /not/ a bug in the tool, of course).
511 : // However, since those situations were not reproducible anymore, we deliberately leave the Accessible creation
512 : // (which originally was intended as a workaround) herein. Better to be safe ...
513 : // Note that this is not a performance problem: The implementation of the ToolPanelDeck's Accessible
514 : // is separated from the implementation of its AccessibleContext (which even is in a separate library) - we only
515 : // create the former here, the latter is still created on demand, when somebody requests it.
516 : // #i113671# / 2010-09-17 / frank.schoenheit@oracle.com
517 0 : if (mpContentWindow.get())
518 0 : mpContentWindow->GetAccessible( sal_True );
519 :
520 : // For accessibility we have to shortly hide the content window. This
521 : // triggers the construction of a new accessibility object for the new
522 : // view shell. (One is created earlier while the construtor of the base
523 : // class is executed. At that time the correct accessibility object can
524 : // not be constructed.)
525 0 : if (mpContentWindow.get())
526 : {
527 0 : mpContentWindow->Hide();
528 0 : mpContentWindow->Show();
529 : }
530 :
531 : // Register the shell manager as factory at the ViewShellManager.
532 : mpSubShellManager.reset( new TaskPaneShellManager(
533 0 : GetViewShellBase().GetViewShellManager(),
534 : *this
535 0 : ) );
536 0 : GetViewShellBase().GetViewShellManager()->AddSubShellFactory( this, mpSubShellManager );
537 0 : }
538 :
539 : // ---------------------------------------------------------------------------------------------------------------------
540 0 : ToolPanelViewShell::~ToolPanelViewShell()
541 : {
542 0 : mpImpl->Cleanup();
543 :
544 : // reset our impl before destroying the panel deck, to ensure the hidden panels are properly
545 : // disposed/destroyed, too
546 0 : mpImpl.reset();
547 0 : GetViewShellBase().GetViewShellManager()->RemoveSubShellFactory(this, mpSubShellManager);
548 0 : GetFrameView()->Disconnect();
549 0 : }
550 :
551 : // ---------------------------------------------------------------------------------------------------------------------
552 : // static
553 3 : void ToolPanelViewShell::RegisterControls()
554 : {
555 3 : SfxModule* pModule = SD_MOD();
556 3 : controls::MasterPagesSelector::RegisterInterface( pModule );
557 3 : LayoutMenu::RegisterInterface( pModule );
558 3 : }
559 :
560 : // ---------------------------------------------------------------------------------------------------------------------
561 0 : void ToolPanelViewShell::ArrangeGUIElements()
562 : {
563 0 : ViewShell::ArrangeGUIElements();
564 :
565 0 : Initialize();
566 :
567 0 : mpImpl->GetTaskPane().SetPosSizePixel( Point(), maViewSize );
568 0 : }
569 :
570 : // ---------------------------------------------------------------------------------------------------------------------
571 0 : void ToolPanelViewShell::GetFocus()
572 : {
573 0 : Invalidate();
574 0 : }
575 :
576 : // ---------------------------------------------------------------------------------------------------------------------
577 0 : void ToolPanelViewShell::LoseFocus()
578 : {
579 0 : Invalidate();
580 0 : }
581 :
582 : // ---------------------------------------------------------------------------------------------------------------------
583 0 : void ToolPanelViewShell::KeyInput( const KeyEvent& i_rKeyEvent )
584 : {
585 0 : const KeyCode nCode = i_rKeyEvent.GetKeyCode();
586 0 : if ( nCode == KEY_RETURN )
587 : {
588 0 : if ( !mpImpl->GetTaskPane().HasChildPathFocus() )
589 0 : mpImpl->GetTaskPane().GrabFocus();
590 : }
591 : else
592 0 : ViewShell::KeyInput( i_rKeyEvent, NULL );
593 0 : }
594 :
595 : // ---------------------------------------------------------------------------------------------------------------------
596 0 : SdPage* ToolPanelViewShell::GetActualPage()
597 : {
598 0 : return NULL;
599 : }
600 :
601 : // ---------------------------------------------------------------------------------------------------------------------
602 0 : SdPage* ToolPanelViewShell::getCurrentPage() const
603 : {
604 0 : return NULL;
605 : }
606 :
607 : // ---------------------------------------------------------------------------------------------------------------------
608 0 : TaskPaneShellManager& ToolPanelViewShell::GetSubShellManager() const
609 : {
610 0 : return *mpSubShellManager.get();
611 : }
612 :
613 : // ---------------------------------------------------------------------------------------------------------------------
614 0 : DockingWindow* ToolPanelViewShell::GetDockingWindow()
615 : {
616 0 : ::Window* pParentWindow = GetParentWindow();
617 0 : DockingWindow* pDockingWindow = NULL;
618 0 : while (pParentWindow!=NULL && pDockingWindow==NULL)
619 : {
620 0 : pDockingWindow = dynamic_cast<DockingWindow*>(pParentWindow);
621 0 : pParentWindow = pParentWindow->GetParent();
622 : }
623 0 : return pDockingWindow;
624 : }
625 :
626 : // ---------------------------------------------------------------------------------------------------------------------
627 0 : Reference< XAccessible > ToolPanelViewShell::CreateAccessibleDocumentView( ::sd::Window* i_pWindow )
628 : {
629 0 : ENSURE_OR_RETURN( i_pWindow, "ToolPanelViewShell::CreateAccessibleDocumentView: illegal window!", NULL );
630 0 : return mpImpl->CreateAccessible( *i_pWindow );
631 : }
632 :
633 : // ---------------------------------------------------------------------------------------------------------------------
634 0 : Reference< XDrawSubController > ToolPanelViewShell::CreateSubController()
635 : {
636 : // This view shell is not designed to be the main view shell and thus
637 : // does not support a UNO sub controller.
638 0 : return Reference< XDrawSubController >();
639 : }
640 :
641 : // ---------------------------------------------------------------------------------------------------------------------
642 0 : bool ToolPanelViewShell::RelocateToParentWindow( ::Window* pParentWindow )
643 : {
644 0 : ::Window* pOldParentWindow = GetParentWindow();
645 0 : FocusManager::Instance().RemoveLinks( pOldParentWindow, &mpImpl->GetTaskPane() );
646 0 : FocusManager::Instance().RemoveLinks( &mpImpl->GetTaskPane(), pOldParentWindow );
647 :
648 0 : PaneDockingWindow* pDockingWindow = dynamic_cast< PaneDockingWindow* >( GetDockingWindow() );
649 0 : if ( pDockingWindow != NULL )
650 : {
651 0 : pDockingWindow->SetEndDockingHdl( Link() );
652 : }
653 :
654 0 : ViewShell::RelocateToParentWindow(pParentWindow);
655 :
656 0 : mpImpl->ConnectToDockingWindow();
657 :
658 0 : Resize();
659 :
660 0 : return true;
661 : }
662 :
663 : //---------------------------------------------------------------------------------------------------------------------
664 0 : bool ToolPanelViewShell::IsPanelAnchorWindow( const ::Window& i_rWindow ) const
665 : {
666 0 : return &mpImpl->GetToolPanelDeck().GetPanelWindowAnchor() == &i_rWindow;
667 : }
668 :
669 : //---------------------------------------------------------------------------------------------------------------------
670 : namespace
671 : {
672 : typedef std::auto_ptr< ControlFactory > (*ControlFactoryFactory)( ToolPanelViewShell& i_rToolPanelShell );
673 :
674 0 : struct PanelFactory
675 : {
676 : ControlFactoryFactory pFactory;
677 : rtl::OString sHelpID;
678 0 : PanelFactory( const ControlFactoryFactory i_pFactory, const rtl::OString& i_nHelpID )
679 : :pFactory( i_pFactory )
680 0 : ,sHelpID( i_nHelpID )
681 : {
682 0 : }
683 : };
684 :
685 0 : const PanelFactory lcl_describePanel( const PanelId i_ePanelId )
686 : {
687 0 : switch ( i_ePanelId )
688 : {
689 : case PID_MASTER_PAGES:
690 0 : return PanelFactory( &controls::MasterPagesPanel::CreateControlFactory, HID_SD_SLIDE_DESIGNS );
691 : case PID_LAYOUT:
692 0 : return PanelFactory( &LayoutMenu::CreateControlFactory, HID_SD_SLIDE_LAYOUTS );
693 : case PID_TABLE_DESIGN:
694 0 : return PanelFactory( &controls::TableDesignPanel::CreateControlFactory, HID_SD_TABLE_DESIGN );
695 : case PID_CUSTOM_ANIMATION:
696 0 : return PanelFactory( &controls::CustomAnimationPanel::CreateControlFactory, HID_SD_CUSTOM_ANIMATIONS );
697 : case PID_SLIDE_TRANSITION:
698 0 : return PanelFactory( &controls::SlideTransitionPanel::CreateControlFactory, HID_SD_SLIDE_TRANSITIONS );
699 : default:
700 0 : break;
701 : }
702 0 : throw RuntimeException( "illegal panel ID" , NULL );
703 : }
704 : }
705 :
706 : //---------------------------------------------------------------------------------------------------------------------
707 0 : Reference< XUIElement > ToolPanelViewShell::CreatePanelUIElement( const Reference< XFrame >& i_rDocFrame, const ::rtl::OUString& i_rPanelResourceURL )
708 : {
709 0 : const PanelId ePanelId( GetStandardPanelId( i_rPanelResourceURL ) );
710 0 : ENSURE_OR_RETURN( ePanelId != PID_UNKNOWN, "ToolPanelViewShell::CreatePanelUIElement: illegal panel URL!", NULL );
711 :
712 : // a TreeNode which will resemble the panel
713 0 : const PanelFactory aPanelFactory( lcl_describePanel( ePanelId ) );
714 : SAL_WNODEPRECATED_DECLARATIONS_PUSH
715 0 : ::std::auto_ptr< ControlFactory > pControlFactory( (*aPanelFactory.pFactory)( *this ) );
716 0 : ::std::auto_ptr< TreeNode > pNode( pControlFactory->CreateControl( mpImpl->GetToolPanelDeck().GetPanelWindowAnchor() ) );
717 : SAL_WNODEPRECATED_DECLARATIONS_POP
718 0 : ENSURE_OR_THROW( ( pNode.get() != NULL ) && ( pNode->GetWindow() != NULL ),
719 : "illegal node returned by the control factory" );
720 0 : pNode->GetWindow()->SetHelpId( aPanelFactory.sHelpID );
721 :
722 : // create an XToolPanel
723 0 : Reference< XToolPanel > xPanel( new ToolPanel( pNode ) );
724 :
725 : // create an XUIElement providing this panel
726 0 : const Reference< XUIElement > xUIElement( new ToolPanelUIElement( i_rDocFrame, i_rPanelResourceURL, xPanel ) );
727 :
728 0 : return xUIElement;
729 : }
730 :
731 : // ---------------------------------------------------------------------------------------------------------------------
732 0 : void ToolPanelViewShell::ActivatePanel( const ::rtl::OUString& i_rPanelResourceURL )
733 : {
734 : OSL_ENSURE( i_rPanelResourceURL.indexOf( FrameworkHelper::msTaskPanelURLPrefix ) < 0,
735 : "ToolPanelViewShell::ActivatePanel: for drawing-framework-controller panels, please use FrameworkHelper::RequestTaskPanel!" );
736 0 : mpImpl->ActivatePanelByResource( i_rPanelResourceURL );
737 0 : }
738 :
739 : // ---------------------------------------------------------------------------------------------------------------------
740 0 : void ToolPanelViewShell::DeactivatePanel( const ::rtl::OUString& i_rPanelResourceURL )
741 : {
742 0 : mpImpl->DeactivatePanelByResource( i_rPanelResourceURL );
743 0 : }
744 :
745 : // =====================================================================================================================
746 : // = ToolPanelViewShell_Impl - implementation
747 : // =====================================================================================================================
748 : // ---------------------------------------------------------------------------------------------------------------------
749 0 : ToolPanelViewShell_Impl::ToolPanelViewShell_Impl( ToolPanelViewShell& i_rPanelViewShell, ::Window& i_rPanelDeckParent )
750 : :m_rPanelViewShell( i_rPanelViewShell )
751 0 : ,m_pTaskPane( new ::sfx2::ModuleTaskPane( i_rPanelDeckParent, i_rPanelViewShell.GetViewShellBase().GetViewFrame()->GetFrame().GetFrameInterface(), *this ) )
752 0 : ,m_bInitialized( false )
753 : {
754 0 : const String sPaneTitle( SdResId( STR_RIGHT_PANE_TITLE ) );
755 0 : GetToolPanelDeck().SetAccessibleName( sPaneTitle );
756 0 : GetToolPanelDeck().SetAccessibleDescription( sPaneTitle );
757 :
758 0 : GetToolPanelDeck().AddListener( *this );
759 0 : }
760 :
761 : // ---------------------------------------------------------------------------------------------------------------------
762 0 : ToolPanelViewShell_Impl::~ToolPanelViewShell_Impl()
763 : {
764 0 : }
765 :
766 : // ---------------------------------------------------------------------------------------------------------------------
767 0 : void ToolPanelViewShell_Impl::PanelInserted( const ::svt::PToolPanel& i_pPanel, const size_t i_nPosition )
768 : {
769 : // not interested in
770 : (void)i_pPanel;
771 : (void)i_nPosition;
772 0 : }
773 :
774 : // ---------------------------------------------------------------------------------------------------------------------
775 0 : void ToolPanelViewShell_Impl::PanelRemoved( const size_t i_nPosition )
776 : {
777 : // not interested in
778 : (void)i_nPosition;
779 0 : }
780 :
781 : // ---------------------------------------------------------------------------------------------------------------------
782 0 : ::rtl::OUString ToolPanelViewShell_Impl::impl_getPanelURL( const ::boost::optional< size_t >& i_rPanel )
783 : {
784 0 : ::rtl::OUString sPanelURL;
785 0 : if ( !!i_rPanel )
786 : {
787 0 : sPanelURL = GetTaskPane().GetPanelResourceURL( *i_rPanel );
788 0 : const PanelId ePanelId( GetStandardPanelId( sPanelURL, true ) );
789 0 : if ( ePanelId == PID_UNKNOWN )
790 0 : sPanelURL = ::rtl::OUString();
791 : }
792 0 : return sPanelURL;
793 : }
794 :
795 : // ---------------------------------------------------------------------------------------------------------------------
796 0 : void ToolPanelViewShell_Impl::ActivePanelChanged( const ::boost::optional< size_t >& i_rOldActive, const ::boost::optional< size_t >& i_rNewActive )
797 : {
798 : // update the configuration controller, since this change in the active panel might have been triggered by means other
799 : // than the drawing framework, so it does not yet know about it.
800 :
801 0 : const ::rtl::OUString sOldPanelURL( impl_getPanelURL( i_rOldActive ) );
802 0 : const ::rtl::OUString sNewPanelURL( impl_getPanelURL( i_rNewActive ) );
803 :
804 0 : const ::boost::shared_ptr< FrameworkHelper > pFrameworkHelper( FrameworkHelper::Instance( GetAntiImpl().GetViewShellBase() ) );
805 0 : if ( !sNewPanelURL.isEmpty() )
806 : {
807 : // activate the resource belonging to the new panel. This will automatically de-activate the previously active
808 : // panel resource (since ResourceActivationMode_REPLACE is used)
809 0 : pFrameworkHelper->RequestTaskPanel( sNewPanelURL );
810 : }
811 0 : else if ( !sOldPanelURL.isEmpty() )
812 : {
813 : // there is no new active panel, or it is not one of our standard panels, i.e. it is not covered by the
814 : // resource framework. => Deactivate the old resource.
815 : try
816 : {
817 0 : Reference< XConfigurationController > xConfigController( pFrameworkHelper->GetConfigurationController(), UNO_QUERY_THROW );
818 0 : xConfigController->requestResourceDeactivation(
819 0 : pFrameworkHelper->CreateResourceId(
820 : sOldPanelURL,
821 : FrameworkHelper::msTaskPaneURL,
822 : FrameworkHelper::msRightPaneURL
823 : )
824 0 : );
825 : }
826 0 : catch( const Exception& )
827 : {
828 : DBG_UNHANDLED_EXCEPTION();
829 : }
830 0 : }
831 0 : }
832 :
833 : // ---------------------------------------------------------------------------------------------------------------------
834 0 : void ToolPanelViewShell_Impl::LayouterChanged( const ::svt::PDeckLayouter& i_rNewLayouter )
835 : {
836 : // not interested in
837 : (void)i_rNewLayouter;
838 0 : }
839 :
840 : // ---------------------------------------------------------------------------------------------------------------------
841 0 : void ToolPanelViewShell_Impl::Dying()
842 : {
843 : // not interested in
844 0 : }
845 :
846 : // ---------------------------------------------------------------------------------------------------------------------
847 0 : short ToolPanelViewShell_Impl::compareToolPanelsURLs( const ::rtl::OUString& i_rLHS, const ::rtl::OUString& i_rRHS ) const
848 : {
849 0 : const PanelId eLHS( GetStandardPanelId( i_rLHS, true ) );
850 0 : const PanelId eRHS( GetStandardPanelId( i_rRHS, true ) );
851 0 : if ( eLHS < eRHS )
852 0 : return -1;
853 0 : if ( eLHS == eRHS )
854 0 : return 0;
855 0 : return 1;
856 : }
857 :
858 : // ---------------------------------------------------------------------------------------------------------------------
859 0 : void ToolPanelViewShell_Impl::ConnectToDockingWindow()
860 : {
861 0 : m_pTaskPaneController.reset();
862 0 : DockingWindow* pDockingWindow( GetAntiImpl().GetDockingWindow() );
863 0 : if ( pDockingWindow )
864 : {
865 0 : PaneDockingWindow* pPaneDockingWindow = dynamic_cast< PaneDockingWindow* >( pDockingWindow );
866 : OSL_ENSURE( pPaneDockingWindow, "ToolPanelViewShell_Impl::ConnectToDockingWindow: unsupported docking window type!" );
867 0 : if ( pPaneDockingWindow != NULL )
868 0 : m_pTaskPaneController.reset( new ::sfx2::TaskPaneController( GetTaskPane(), *pPaneDockingWindow ) );
869 : }
870 :
871 : // Tell the focus manager that we want to pass the focus to our
872 : // child.
873 0 : FocusManager::Instance().RegisterDownLink( GetAntiImpl().GetParentWindow(), &GetTaskPane() );
874 0 : }
875 :
876 : // ---------------------------------------------------------------------------------------------------------------------
877 0 : Reference< XAccessible > ToolPanelViewShell_Impl::CreateAccessible( ::sd::Window& i_rWindow )
878 : {
879 0 : Reference< XAccessible > xAccessible( GetToolPanelDeck().GetAccessible( sal_False ) );
880 0 : if ( !xAccessible.is() )
881 : {
882 : // determine the XAccessible which is the parent of the to-be-created object
883 0 : ::Window* pAccessibleParent = i_rWindow.GetAccessibleParentWindow();
884 : OSL_ENSURE( pAccessibleParent, "ToolPanelViewShell_Impl::CreateAccessible: illegal accessible parent provided by the sd::Window!" );
885 0 : GetToolPanelDeck().SetAccessibleParentWindow( pAccessibleParent );
886 :
887 0 : xAccessible = GetToolPanelDeck().GetAccessible( sal_True );
888 0 : ENSURE_OR_RETURN( xAccessible.is(), "ToolPanelViewShell_Impl::CreateAccessible: illegal ToolPanelDeck accessible!", NULL );
889 : OSL_ENSURE( xAccessible->getAccessibleContext().is()
890 : && xAccessible->getAccessibleContext()->getAccessibleParent() == pAccessibleParent->GetAccessible(),
891 : "ToolPanelViewShell_Impl::CreateAccessible: illegal parenthood!" );
892 : }
893 0 : return xAccessible;
894 : }
895 :
896 9 : } } // end of namespace ::sd::toolpanel
897 :
898 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|