Branch data 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 "sfx2/taskpane.hxx"
22 : : #include "imagemgr.hxx"
23 : : #include "sfx2/sfxsids.hrc"
24 : : #include "sfx2/bindings.hxx"
25 : : #include "sfx2/dispatch.hxx"
26 : : #include "sfxresid.hxx"
27 : : #include "sfxlocal.hrc"
28 : : #include "helpid.hrc"
29 : :
30 : : #include <com/sun/star/frame/XModuleManager.hpp>
31 : : #include <com/sun/star/container/XNameAccess.hpp>
32 : : #include <com/sun/star/ui/XToolPanel.hpp>
33 : : #include <com/sun/star/ui/XUIElementFactory.hpp>
34 : : #include <com/sun/star/awt/XWindowPeer.hpp>
35 : : #include <com/sun/star/awt/PosSize.hpp>
36 : : #include <com/sun/star/graphic/GraphicProvider.hpp>
37 : : #include <com/sun/star/graphic/XGraphicProvider.hpp>
38 : : #include <com/sun/star/accessibility/XAccessible.hpp>
39 : : #include <com/sun/star/awt/XControl.hpp>
40 : :
41 : : #include <comphelper/componentcontext.hxx>
42 : : #include <comphelper/namedvaluecollection.hxx>
43 : : #include <comphelper/types.hxx>
44 : : #include <comphelper/processfactory.hxx>
45 : : #include <tools/diagnose_ex.h>
46 : : #include <svtools/toolpanel/toolpaneldeck.hxx>
47 : : #include <svtools/toolpanel/tablayouter.hxx>
48 : : #include <svtools/toolpanel/drawerlayouter.hxx>
49 : : #include <unotools/confignode.hxx>
50 : : #include <vcl/menu.hxx>
51 : : #include <vcl/svapp.hxx>
52 : : #include <toolkit/helper/vclunohelper.hxx>
53 : : #include <tools/urlobj.hxx>
54 : : #include <boost/noncopyable.hpp>
55 : :
56 : : //......................................................................................................................
57 : : namespace sfx2
58 : : {
59 : : //......................................................................................................................
60 : :
61 : : /** === begin UNO using === **/
62 : : using ::com::sun::star::uno::Reference;
63 : : using ::com::sun::star::uno::XComponentContext;
64 : : using ::com::sun::star::uno::XInterface;
65 : : using ::com::sun::star::uno::UNO_QUERY;
66 : : using ::com::sun::star::uno::UNO_QUERY_THROW;
67 : : using ::com::sun::star::uno::UNO_SET_THROW;
68 : : using ::com::sun::star::uno::Exception;
69 : : using ::com::sun::star::uno::RuntimeException;
70 : : using ::com::sun::star::uno::Any;
71 : : using ::com::sun::star::uno::makeAny;
72 : : using ::com::sun::star::uno::Sequence;
73 : : using ::com::sun::star::uno::Type;
74 : : using ::com::sun::star::frame::XModuleManager;
75 : : using ::com::sun::star::container::XNameAccess;
76 : : using ::com::sun::star::ui::XToolPanel;
77 : : using ::com::sun::star::ui::XUIElementFactory;
78 : : using ::com::sun::star::ui::XUIElement;
79 : : using ::com::sun::star::awt::XWindow;
80 : : using ::com::sun::star::frame::XModuleManager;
81 : : using ::com::sun::star::frame::XFrame;
82 : : using ::com::sun::star::lang::XComponent;
83 : : using ::com::sun::star::graphic::XGraphicProvider;
84 : : using ::com::sun::star::graphic::XGraphic;
85 : : using ::com::sun::star::accessibility::XAccessible;
86 : : using ::com::sun::star::awt::XControl;
87 : : /** === end UNO using === **/
88 : : namespace PosSize = ::com::sun::star::awt::PosSize;
89 : :
90 : : //==================================================================================================================
91 : : //= helpers
92 : : //==================================================================================================================
93 : : namespace
94 : : {
95 : : //--------------------------------------------------------------------------------------------------------------
96 : 84 : ::utl::OConfigurationTreeRoot lcl_getModuleUIElementStatesConfig( const ::rtl::OUString& i_rModuleIdentifier,
97 : : const ::rtl::OUString& i_rResourceURL = ::rtl::OUString() )
98 : : {
99 [ + - ][ + - ]: 84 : const ::comphelper::ComponentContext aContext( ::comphelper::getProcessServiceFactory() );
100 : 84 : ::rtl::OUStringBuffer aPathComposer;
101 : : try
102 : : {
103 [ + - ][ + - ]: 84 : const Reference< XNameAccess > xModuleAccess( aContext.createComponent( "com.sun.star.frame.ModuleManager" ), UNO_QUERY_THROW );
104 [ + - ][ + - ]: 84 : const ::comphelper::NamedValueCollection aModuleProps( xModuleAccess->getByName( i_rModuleIdentifier ) );
[ + - ]
105 : :
106 [ + - ]: 84 : const ::rtl::OUString sWindowStateRef( aModuleProps.getOrDefault( "ooSetupFactoryWindowStateConfigRef", ::rtl::OUString() ) );
107 : :
108 : : aPathComposer.appendAscii(RTL_CONSTASCII_STRINGPARAM(
109 [ + - ]: 84 : "org.openoffice.Office.UI."));
110 [ + - ]: 84 : aPathComposer.append( sWindowStateRef );
111 [ + - ]: 84 : aPathComposer.appendAscii(RTL_CONSTASCII_STRINGPARAM("/UIElements/States"));
112 [ - + ]: 84 : if ( !i_rResourceURL.isEmpty() )
113 : : {
114 [ # # ][ # # ]: 0 : aPathComposer.append('/').append( i_rResourceURL );
115 [ + - ][ # # ]: 84 : }
116 : : }
117 [ # # ]: 0 : catch( const Exception& )
118 : : {
119 : : DBG_UNHANDLED_EXCEPTION();
120 : : }
121 [ + - ][ + - ]: 84 : return ::utl::OConfigurationTreeRoot( aContext, aPathComposer.makeStringAndClear(), false );
[ + - ]
122 : : }
123 : :
124 : : //--------------------------------------------------------------------------------------------------------------
125 : 84 : ::rtl::OUString lcl_identifyModule( const Reference< XFrame >& i_rDocumentFrame )
126 : : {
127 : 84 : ::rtl::OUString sModuleName;
128 : : try
129 : : {
130 [ + - ][ + - ]: 84 : const ::comphelper::ComponentContext aContext( ::comphelper::getProcessServiceFactory() );
131 [ + - ][ + - ]: 84 : const Reference< XModuleManager > xModuleManager( aContext.createComponent( "com.sun.star.frame.ModuleManager" ), UNO_QUERY_THROW );
132 [ + - ][ + - ]: 84 : sModuleName = xModuleManager->identify( i_rDocumentFrame );
[ # # ][ + - ]
133 : : }
134 [ # # ]: 0 : catch( const Exception& )
135 : : {
136 : : DBG_UNHANDLED_EXCEPTION();
137 : : }
138 : 84 : return sModuleName;
139 : : }
140 : :
141 : : //--------------------------------------------------------------------------------------------------------------
142 : 0 : Reference< XFrame > lcl_getFrame( const SfxBindings* i_pBindings )
143 : : {
144 : 0 : const SfxViewFrame* pViewFrame = i_pBindings->GetDispatcher()->GetFrame();
145 : 0 : const SfxFrame& rFrame = pViewFrame->GetFrame();
146 : 0 : const Reference< XFrame > xFrame( rFrame.GetFrameInterface() );
147 : 0 : return xFrame;
148 : : }
149 : :
150 : : //--------------------------------------------------------------------------------------------------------------
151 : 130 : ::rtl::OUString lcl_getPanelHelpURL( const ::utl::OConfigurationNode& i_rPanelConfigNode )
152 : : {
153 [ + - ]: 130 : const ::rtl::OUString sHelpURL( ::comphelper::getString( i_rPanelConfigNode.getNodeValue( "HelpURL" ) ) );
154 : 130 : return sHelpURL;
155 : : }
156 : :
157 : : //--------------------------------------------------------------------------------------------------------------
158 : 130 : Image lcl_getPanelImage( const Reference< XFrame >& i_rDocFrame, const ::utl::OConfigurationNode& i_rPanelConfigNode )
159 : : {
160 [ + - ]: 130 : const ::rtl::OUString sImageURL( ::comphelper::getString( i_rPanelConfigNode.getNodeValue( "ImageURL" ) ) );
161 [ + - ]: 130 : if ( !sImageURL.isEmpty() )
162 : : {
163 : : try
164 : : {
165 [ + - ]: 130 : ::comphelper::NamedValueCollection aMediaProperties;
166 [ + - ]: 130 : aMediaProperties.put( "URL", sImageURL );
167 : :
168 : : // special handling: if the ImageURL denotes a CommandName, then retrieve the image for that command
169 : 130 : const sal_Char* pCommandImagePrefix = "private:commandimage/";
170 : 130 : const sal_Int32 nCommandImagePrefixLen = strlen( pCommandImagePrefix );
171 [ + - ]: 130 : if ( sImageURL.compareToAscii( pCommandImagePrefix, nCommandImagePrefixLen ) == 0 )
172 : : {
173 : 130 : ::rtl::OUStringBuffer aCommandName;
174 [ + - ]: 130 : aCommandName.appendAscii(RTL_CONSTASCII_STRINGPARAM(".uno:"));
175 [ + - ]: 130 : aCommandName.append( sImageURL.copy( nCommandImagePrefixLen ) );
176 [ + - ]: 130 : const ::rtl::OUString sCommandName( aCommandName.makeStringAndClear() );
177 : :
178 [ + - ]: 130 : const Image aPanelImage( GetImage( i_rDocFrame, sCommandName, sal_False ) );
179 [ + - ][ + - ]: 130 : return aPanelImage.GetXGraphic();
[ + - ]
180 : : }
181 : :
182 : : // otherwise, delegate to the GraphicProvider
183 [ # # ]: 0 : const Reference< XComponentContext > xContext( ::comphelper::getProcessComponentContext() );
184 [ # # ]: 0 : const Reference< XGraphicProvider > xGraphicProvider( com::sun::star::graphic::GraphicProvider::create(xContext) );
185 : :
186 [ # # ][ # # ]: 0 : const Reference< XGraphic > xGraphic( xGraphicProvider->queryGraphic( aMediaProperties.getPropertyValues() ), UNO_SET_THROW );
[ # # ][ # # ]
[ # # ]
187 [ # # ][ + - ]: 130 : return Image( xGraphic );
[ # # ]
188 : : }
189 [ # # ]: 0 : catch( const Exception& )
190 : : {
191 : : DBG_UNHANDLED_EXCEPTION();
192 : : }
193 : : }
194 [ # # ]: 130 : return Image();
195 : : }
196 : : }
197 : :
198 : : //==================================================================================================================
199 : : //= TaskPaneDockingWindow
200 : : //==================================================================================================================
201 : : //------------------------------------------------------------------------------------------------------------------
202 : 0 : TaskPaneDockingWindow::TaskPaneDockingWindow( SfxBindings* i_pBindings, TaskPaneWrapper& i_rWrapper, Window* i_pParent, WinBits i_nBits )
203 : : :TitledDockingWindow( i_pBindings, &i_rWrapper, i_pParent, i_nBits )
204 : 0 : ,m_aTaskPane( GetContentWindow(), lcl_getFrame( i_pBindings ) )
205 [ # # # # ]: 0 : ,m_aPaneController( m_aTaskPane, *this )
[ # # ]
206 : : {
207 [ # # ]: 0 : m_aTaskPane.Show();
208 [ # # ][ # # ]: 0 : SetText( SfxResId( SID_TASKPANE ).toString() );
[ # # ][ # # ]
[ # # ]
209 : 0 : }
210 : :
211 : : //------------------------------------------------------------------------------------------------------------------
212 : 0 : void TaskPaneDockingWindow::ActivateToolPanel( const ::rtl::OUString& i_rPanelURL )
213 : : {
214 : 0 : m_aPaneController.ActivateToolPanel( i_rPanelURL );
215 : 0 : }
216 : :
217 : : //------------------------------------------------------------------------------------------------------------------
218 : 0 : void TaskPaneDockingWindow::GetFocus()
219 : : {
220 : 0 : TitledDockingWindow::GetFocus();
221 : 0 : m_aTaskPane.GrabFocus();
222 : 0 : }
223 : :
224 : : //------------------------------------------------------------------------------------------------------------------
225 : 0 : void TaskPaneDockingWindow::onLayoutDone()
226 : : {
227 [ # # ]: 0 : m_aTaskPane.SetPosSizePixel( Point(), GetContentWindow().GetOutputSizePixel() );
228 : 0 : }
229 : :
230 : : //==================================================================================================================
231 : : //= TaskPaneWrapper
232 : : //==================================================================================================================
233 : : //------------------------------------------------------------------------------------------------------------------
234 [ # # ][ + - ]: 134 : SFX_IMPL_DOCKINGWINDOW( TaskPaneWrapper, SID_TASKPANE );
[ # # ]
235 : :
236 : : //------------------------------------------------------------------------------------------------------------------
237 : 0 : TaskPaneWrapper::TaskPaneWrapper( Window* i_pParent, sal_uInt16 i_nId, SfxBindings* i_pBindings, SfxChildWinInfo* i_pInfo )
238 : 0 : :SfxChildWindow( i_pParent, i_nId )
239 : : {
240 : : pWindow = new TaskPaneDockingWindow( i_pBindings, *this, i_pParent,
241 [ # # ][ # # ]: 0 : WB_STDDOCKWIN | WB_CLIPCHILDREN | WB_SIZEABLE | WB_3DLOOK | WB_ROLLABLE);
242 : 0 : eChildAlignment = SFX_ALIGN_RIGHT;
243 : :
244 [ # # ]: 0 : pWindow->SetHelpId( HID_TASKPANE_WINDOW );
245 [ # # ]: 0 : pWindow->SetOutputSizePixel( Size( 300, 450 ) );
246 : :
247 [ # # ][ # # ]: 0 : dynamic_cast< SfxDockingWindow* >( pWindow )->Initialize( i_pInfo );
248 [ # # ]: 0 : SetHideNotDelete( sal_True );
249 : :
250 [ # # ]: 0 : pWindow->Show();
251 : 0 : }
252 : :
253 : : //------------------------------------------------------------------------------------------------------------------
254 : 0 : void TaskPaneWrapper::ActivateToolPanel( const ::rtl::OUString& i_rPanelURL )
255 : : {
256 [ # # ]: 0 : TaskPaneDockingWindow* pDockingWindow = dynamic_cast< TaskPaneDockingWindow* >( GetWindow() );
257 [ # # ]: 0 : ENSURE_OR_RETURN_VOID( pDockingWindow, "TaskPaneWrapper::ActivateToolPanel: invalid docking window implementation!" );
258 : 0 : pDockingWindow->ActivateToolPanel( i_rPanelURL );
259 : : }
260 : :
261 : : //==================================================================================================================
262 : : //= CustomPanelUIElement
263 : : //==================================================================================================================
264 : 194 : class CustomPanelUIElement
265 : : {
266 : : public:
267 : 130 : CustomPanelUIElement()
268 : : :m_xUIElement()
269 : : ,m_xToolPanel()
270 : 130 : ,m_xPanelWindow()
271 : : {
272 : 130 : }
273 : :
274 : 32 : CustomPanelUIElement( const Reference< XUIElement >& i_rUIElement )
275 : : :m_xUIElement( i_rUIElement, UNO_SET_THROW )
276 [ + - ]: 32 : ,m_xToolPanel( i_rUIElement->getRealInterface(), UNO_QUERY_THROW )
277 [ + - ][ + - ]: 64 : ,m_xPanelWindow( m_xToolPanel->getWindow(), UNO_SET_THROW )
[ + - ][ + - ]
[ + - ]
278 : : {
279 : 32 : }
280 : :
281 : 177 : bool is() const { return m_xPanelWindow.is(); }
282 : :
283 : 32 : const Reference< XUIElement >& getUIElement() const { return m_xUIElement; }
284 : 0 : const Reference< XToolPanel >& getToolPanel() const { return m_xToolPanel; }
285 : 145 : const Reference< XWindow >& getPanelWindow() const { return m_xPanelWindow; }
286 : :
287 : : private:
288 : : Reference< XUIElement > m_xUIElement;
289 : : Reference< XToolPanel > m_xToolPanel;
290 : : Reference< XWindow > m_xPanelWindow;
291 : : };
292 : :
293 : : //==================================================================================================================
294 : : //= CustomToolPanel
295 : : //==================================================================================================================
296 : : class CustomToolPanel : public ::svt::ToolPanelBase
297 : : {
298 : : public:
299 : : CustomToolPanel( const ::utl::OConfigurationNode& i_rPanelWindowState, const Reference< XFrame >& i_rFrame );
300 : :
301 : : virtual ::rtl::OUString GetDisplayName() const;
302 : : virtual Image GetImage() const;
303 : : virtual rtl::OString GetHelpID() const;
304 : : virtual void Activate( Window& i_rParentWindow );
305 : : virtual void Deactivate();
306 : : virtual void SetSizePixel( const Size& i_rPanelWindowSize );
307 : : virtual void GrabFocus();
308 : : virtual void Dispose();
309 : : virtual Reference< XAccessible >
310 : : CreatePanelAccessible( const Reference< XAccessible >& i_rParentAccessible );
311 : :
312 : : const ::rtl::OUString&
313 : 361 : GetResourceURL() const { return m_sResourceURL; }
314 : :
315 : : protected:
316 : : ~CustomToolPanel();
317 : :
318 : : private:
319 : : bool impl_ensureToolPanelWindow( Window& i_rPanelParentWindow );
320 : : void impl_updatePanelConfig( const bool i_bVisible ) const;
321 : :
322 : : private:
323 : : const ::rtl::OUString m_sUIName;
324 : : const Image m_aPanelImage;
325 : : const ::rtl::OUString m_aPanelHelpURL;
326 : : const ::rtl::OUString m_sResourceURL;
327 : : const ::rtl::OUString m_sPanelConfigPath;
328 : : Reference< XFrame > m_xFrame;
329 : : CustomPanelUIElement m_aCustomPanel;
330 : : bool m_bAttemptedCreation;
331 : : };
332 : :
333 : : //------------------------------------------------------------------------------------------------------------------
334 : 130 : CustomToolPanel::CustomToolPanel( const ::utl::OConfigurationNode& i_rPanelWindowState, const Reference< XFrame >& i_rFrame )
335 : : :m_sUIName( ::comphelper::getString( i_rPanelWindowState.getNodeValue( "UIName" ) ) )
336 : : ,m_aPanelImage( lcl_getPanelImage( i_rFrame, i_rPanelWindowState ) )
337 : : ,m_aPanelHelpURL( lcl_getPanelHelpURL( i_rPanelWindowState ) )
338 : : ,m_sResourceURL( i_rPanelWindowState.getLocalName() )
339 : : ,m_sPanelConfigPath( i_rPanelWindowState.getNodePath() )
340 : : ,m_xFrame( i_rFrame )
341 : : ,m_aCustomPanel()
342 [ + - ][ + - ]: 130 : ,m_bAttemptedCreation( false )
[ + - ][ + - ]
[ + - ][ + - ]
343 : : {
344 : 130 : }
345 : :
346 : : //------------------------------------------------------------------------------------------------------------------
347 [ + - ][ + - ]: 130 : CustomToolPanel::~CustomToolPanel()
348 : : {
349 [ - + ]: 260 : }
350 : :
351 : : //------------------------------------------------------------------------------------------------------------------
352 : 32 : bool CustomToolPanel::impl_ensureToolPanelWindow( Window& i_rPanelParentWindow )
353 : : {
354 [ - + ]: 32 : if ( m_bAttemptedCreation )
355 : 0 : return m_aCustomPanel.is();
356 : :
357 : 32 : m_bAttemptedCreation = true;
358 : : try
359 : : {
360 [ + - ][ + - ]: 32 : const ::comphelper::ComponentContext aContext( ::comphelper::getProcessServiceFactory() );
361 [ + - ][ + - ]: 32 : const Reference< XUIElementFactory > xFactory( aContext.createComponent( "com.sun.star.ui.UIElementFactoryManager" ), UNO_QUERY_THROW );
362 : :
363 [ + - ]: 32 : ::comphelper::NamedValueCollection aCreationArgs;
364 [ + - ][ + - ]: 32 : aCreationArgs.put( "Frame", makeAny( m_xFrame ) );
365 [ + - ][ + - ]: 32 : aCreationArgs.put( "ParentWindow", makeAny( i_rPanelParentWindow.GetComponentInterface() ) );
[ + - ]
366 : :
367 : : const Reference< XUIElement > xElement(
368 [ + - ]: 32 : xFactory->createUIElement( m_sResourceURL, aCreationArgs.getPropertyValues() ),
369 [ + - ][ + - ]: 32 : UNO_SET_THROW );
[ + - ][ + - ]
370 : :
371 [ + - ][ + - ]: 32 : m_aCustomPanel = CustomPanelUIElement( xElement );
[ + - ][ + - ]
[ + - ][ # # ]
372 : : }
373 : 0 : catch( const Exception& )
374 : : {
375 : : DBG_UNHANDLED_EXCEPTION();
376 : : }
377 : 32 : return m_aCustomPanel.is();
378 : : }
379 : :
380 : : //------------------------------------------------------------------------------------------------------------------
381 : 38 : void CustomToolPanel::impl_updatePanelConfig( const bool i_bVisible ) const
382 : : {
383 [ + - ][ + - ]: 38 : ::comphelper::ComponentContext aContext( ::comphelper::getProcessServiceFactory() );
384 [ + - ]: 38 : ::utl::OConfigurationTreeRoot aConfig( aContext, m_sPanelConfigPath, true );
385 : :
386 [ + - ]: 38 : aConfig.setNodeValue( "Visible", makeAny( i_bVisible ) );
387 [ + - ][ + - ]: 38 : aConfig.commit();
388 : 38 : }
389 : :
390 : : //------------------------------------------------------------------------------------------------------------------
391 : 130 : ::rtl::OUString CustomToolPanel::GetDisplayName() const
392 : : {
393 : 130 : return m_sUIName;
394 : : }
395 : :
396 : : //------------------------------------------------------------------------------------------------------------------
397 : 0 : Image CustomToolPanel::GetImage() const
398 : : {
399 : 0 : return m_aPanelImage;
400 : : }
401 : :
402 : 130 : static rtl::OString lcl_getHelpId( const ::rtl::OUString& _rHelpURL )
403 : : {
404 [ + - ]: 130 : INetURLObject aHID( _rHelpURL );
405 [ - + ]: 130 : if ( aHID.GetProtocol() == INET_PROT_HID )
406 [ # # ][ # # ]: 0 : return rtl::OUStringToOString( aHID.GetURLPath(), RTL_TEXTENCODING_UTF8 );
407 : : else
408 [ + - ][ + - ]: 130 : return rtl::OUStringToOString( _rHelpURL, RTL_TEXTENCODING_UTF8 );
409 : : }
410 : :
411 : : //------------------------------------------------------------------------------------------------------------------
412 : 130 : rtl::OString CustomToolPanel::GetHelpID() const
413 : : {
414 : 130 : return lcl_getHelpId( m_aPanelHelpURL );
415 : : }
416 : :
417 : : //------------------------------------------------------------------------------------------------------------------
418 : 32 : void CustomToolPanel::Activate( Window& i_rParentWindow )
419 : : {
420 [ - + ]: 64 : ENSURE_OR_RETURN_VOID( impl_ensureToolPanelWindow( i_rParentWindow ), "no panel to activate!" );
421 : :
422 : : // TODO: we might need a mechanism to decide whether the panel should be destroyed/re-created, or (as it is
423 : : // done now) hidden/shown
424 : 32 : m_aCustomPanel.getPanelWindow()->setVisible( sal_True );
425 : :
426 : : // update the panel's configuration
427 : 32 : impl_updatePanelConfig( true );
428 : : }
429 : :
430 : : //------------------------------------------------------------------------------------------------------------------
431 : 6 : void CustomToolPanel::Deactivate()
432 : : {
433 [ - + ]: 12 : ENSURE_OR_RETURN_VOID( m_aCustomPanel.is(), "no panel to deactivate!" );
434 : :
435 : 6 : m_aCustomPanel.getPanelWindow()->setVisible( sal_False );
436 : :
437 : : // update the panel's configuration
438 : 6 : impl_updatePanelConfig( false );
439 : : }
440 : :
441 : : //------------------------------------------------------------------------------------------------------------------
442 : 75 : void CustomToolPanel::SetSizePixel( const Size& i_rPanelWindowSize )
443 : : {
444 [ - + ][ # # ]: 150 : ENSURE_OR_RETURN_VOID( m_aCustomPanel.is(), "no panel/window to position!" );
445 : :
446 : : try
447 : : {
448 [ + - ]: 75 : m_aCustomPanel.getPanelWindow()->setPosSize( 0, 0, i_rPanelWindowSize.Width(), i_rPanelWindowSize.Height(),
449 [ + - ]: 75 : PosSize::POSSIZE );
450 : : }
451 : 0 : catch( const Exception& )
452 : : {
453 : : DBG_UNHANDLED_EXCEPTION();
454 : : }
455 : : }
456 : :
457 : : //------------------------------------------------------------------------------------------------------------------
458 : 32 : void CustomToolPanel::GrabFocus()
459 : : {
460 [ - + ]: 64 : ENSURE_OR_RETURN_VOID( m_aCustomPanel.is(), "no panel/window to focus!" );
461 : :
462 : 32 : m_aCustomPanel.getPanelWindow()->setFocus();
463 : : }
464 : :
465 : : //------------------------------------------------------------------------------------------------------------------
466 : 130 : void CustomToolPanel::Dispose()
467 : : {
468 [ + + ]: 130 : if ( !m_bAttemptedCreation )
469 : : // nothing to dispose
470 : 98 : return;
471 : :
472 [ - + ]: 32 : ENSURE_OR_RETURN_VOID( m_aCustomPanel.is(), "no panel to destroy!" );
473 : : try
474 : : {
475 [ + - ]: 32 : Reference< XComponent > xUIElementComponent( m_aCustomPanel.getUIElement(), UNO_QUERY_THROW );
476 [ + - ][ + - ]: 130 : xUIElementComponent->dispose();
[ # # ]
477 : : }
478 : 0 : catch( const Exception& )
479 : : {
480 : : DBG_UNHANDLED_EXCEPTION();
481 : : }
482 : : }
483 : :
484 : : //------------------------------------------------------------------------------------------------------------------
485 : 0 : Reference< XAccessible > CustomToolPanel::CreatePanelAccessible( const Reference< XAccessible >& i_rParentAccessible )
486 : : {
487 [ # # ][ # # ]: 0 : ENSURE_OR_RETURN( m_aCustomPanel.is(), "no panel to ask!", NULL );
488 : :
489 : 0 : Reference< XAccessible > xPanelAccessible;
490 : : try
491 : : {
492 [ # # ][ # # ]: 0 : xPanelAccessible.set( m_aCustomPanel.getToolPanel()->createAccessible( i_rParentAccessible ), UNO_SET_THROW );
[ # # ][ # # ]
493 : : }
494 [ # # ]: 0 : catch( const Exception& )
495 : : {
496 : : DBG_UNHANDLED_EXCEPTION();
497 : : }
498 : 0 : return xPanelAccessible;
499 : : }
500 : :
501 : : //==================================================================================================================
502 : : //= ModuleTaskPane_Impl
503 : : //==================================================================================================================
504 : : class ModuleTaskPane_Impl : public ::boost::noncopyable
505 : : {
506 : : public:
507 : 26 : ModuleTaskPane_Impl( ModuleTaskPane& i_rAntiImpl, const Reference< XFrame >& i_rDocumentFrame,
508 : : const IToolPanelCompare* i_pPanelCompare )
509 : : :m_rAntiImpl( i_rAntiImpl )
510 : : ,m_sModuleIdentifier( lcl_identifyModule( i_rDocumentFrame ) )
511 : : ,m_xFrame( i_rDocumentFrame )
512 [ + - ][ + - ]: 26 : ,m_aPanelDeck( i_rAntiImpl )
513 : : {
514 [ + - ]: 26 : m_aPanelDeck.Show();
515 [ + - ]: 26 : OnResize();
516 [ + - ]: 26 : impl_initFromConfiguration( i_pPanelCompare );
517 : 26 : }
518 : :
519 : 26 : ~ModuleTaskPane_Impl()
520 [ + - ]: 26 : {
521 : 26 : }
522 : :
523 : : void OnResize();
524 : : void OnGetFocus();
525 : :
526 : : static bool ModuleHasToolPanels( const ::rtl::OUString& i_rModuleIdentifier );
527 : :
528 : 664 : ::svt::ToolPanelDeck& GetPanelDeck() { return m_aPanelDeck; }
529 : : const ::svt::ToolPanelDeck& GetPanelDeck() const { return m_aPanelDeck; }
530 : :
531 : : ::boost::optional< size_t >
532 : : GetPanelPos( const ::rtl::OUString& i_rResourceURL );
533 : : ::rtl::OUString
534 : : GetPanelResourceURL( const size_t i_nPanelPos ) const;
535 : :
536 : : void SetDrawersLayout();
537 : : void SetTabsLayout( const ::svt::TabAlignment i_eTabAlignment, const ::svt::TabItemContent i_eTabContent );
538 : :
539 : : private:
540 : : void impl_initFromConfiguration( const IToolPanelCompare* i_pPanelCompare );
541 : :
542 : : static bool
543 : : impl_isToolPanelResource( const ::rtl::OUString& i_rResourceURL );
544 : :
545 : : DECL_LINK( OnActivatePanel, void* );
546 : :
547 : : private:
548 : : ModuleTaskPane& m_rAntiImpl;
549 : : const ::rtl::OUString m_sModuleIdentifier;
550 : : const Reference< XFrame > m_xFrame;
551 : : ::svt::ToolPanelDeck m_aPanelDeck;
552 : : };
553 : :
554 : : //------------------------------------------------------------------------------------------------------------------
555 : 82 : void ModuleTaskPane_Impl::OnResize()
556 : : {
557 [ + - ]: 82 : m_aPanelDeck.SetPosSizePixel( Point(), m_rAntiImpl.GetOutputSizePixel() );
558 : 82 : }
559 : :
560 : : //------------------------------------------------------------------------------------------------------------------
561 : 0 : void ModuleTaskPane_Impl::OnGetFocus()
562 : : {
563 : 0 : m_aPanelDeck.GrabFocus();
564 : 0 : }
565 : :
566 : : //------------------------------------------------------------------------------------------------------------------
567 : 26 : IMPL_LINK( ModuleTaskPane_Impl, OnActivatePanel, void*, i_pArg )
568 : : {
569 [ + - ][ + - ]: 26 : m_aPanelDeck.ActivatePanel( reinterpret_cast< size_t >( i_pArg ) );
[ + - ]
570 : 26 : return 1L;
571 : : }
572 : :
573 : : //------------------------------------------------------------------------------------------------------------------
574 : 4280 : bool ModuleTaskPane_Impl::impl_isToolPanelResource( const ::rtl::OUString& i_rResourceURL )
575 : : {
576 : 4280 : return i_rResourceURL.matchAsciiL( RTL_CONSTASCII_STRINGPARAM( "private:resource/toolpanel/" ) );
577 : : }
578 : :
579 : : //------------------------------------------------------------------------------------------------------------------
580 : 26 : void ModuleTaskPane_Impl::impl_initFromConfiguration( const IToolPanelCompare* i_pPanelCompare )
581 : : {
582 [ + - ]: 26 : const ::utl::OConfigurationTreeRoot aWindowStateConfig( lcl_getModuleUIElementStatesConfig( m_sModuleIdentifier ) );
583 [ - + ]: 26 : if ( !aWindowStateConfig.isValid() )
584 : 26 : return;
585 : :
586 : 26 : ::rtl::OUString sFirstVisiblePanelResource;
587 : 26 : ::rtl::OUString sFirstPanelResource;
588 : :
589 : 26 : const Sequence< ::rtl::OUString > aUIElements( aWindowStateConfig.getNodeNames() );
590 [ + + ]: 2860 : for ( const ::rtl::OUString* resource = aUIElements.getConstArray();
591 : 1430 : resource != aUIElements.getConstArray() + aUIElements.getLength();
592 : : ++resource
593 : : )
594 : : {
595 [ + - ][ + + ]: 1404 : if ( !impl_isToolPanelResource( *resource ) )
596 : 1274 : continue;
597 : :
598 : 130 : sFirstPanelResource = *resource;
599 : :
600 : 130 : ::utl::OConfigurationNode aResourceNode( aWindowStateConfig.openNode( *resource ) );
601 [ + - ][ + - ]: 130 : ::svt::PToolPanel pCustomPanel( new CustomToolPanel( aResourceNode, m_xFrame ) );
[ + - ]
602 : :
603 [ + - ]: 130 : size_t nPanelPos = m_aPanelDeck.GetPanelCount();
604 [ + - ]: 130 : if ( i_pPanelCompare )
605 : : {
606 : : // assuming that nobody will insert hundreths of panels, a simple O(n) search should suffice here ...
607 [ + + ]: 312 : while ( nPanelPos > 0 )
608 : : {
609 : : const short nCompare = i_pPanelCompare->compareToolPanelsURLs(
610 : : *resource,
611 : : GetPanelResourceURL( --nPanelPos )
612 [ + - ][ + - ]: 182 : );
613 [ + + ]: 182 : if ( nCompare >= 0 )
614 : : {
615 : 52 : ++nPanelPos;
616 : 52 : break;
617 : : }
618 : : }
619 : : }
620 [ + - ]: 130 : nPanelPos = m_aPanelDeck.InsertPanel( pCustomPanel, nPanelPos );
621 : :
622 [ + - ][ + + ]: 130 : if ( ::comphelper::getBOOL( aResourceNode.getNodeValue( "Visible" ) ) )
623 : 18 : sFirstVisiblePanelResource = *resource;
624 [ + - ][ + - ]: 130 : }
625 : :
626 [ + + ]: 26 : if ( sFirstVisiblePanelResource.isEmpty() )
627 : 8 : sFirstVisiblePanelResource = sFirstPanelResource;
628 : :
629 [ + - ]: 26 : if ( !sFirstVisiblePanelResource.isEmpty() )
630 : : {
631 [ + - ]: 26 : ::boost::optional< size_t > aPanelPos( GetPanelPos( sFirstVisiblePanelResource ) );
632 : : OSL_ENSURE( !!aPanelPos, "ModuleTaskPane_Impl::impl_isToolPanelResource: just inserted it, and it's not there?!" );
633 [ + - ][ + - ]: 26 : if ( !!aPanelPos )
634 [ + - ][ + - ]: 26 : m_rAntiImpl.PostUserEvent( LINK( this, ModuleTaskPane_Impl, OnActivatePanel ), reinterpret_cast< void* >( *aPanelPos ) );
[ + - ][ + - ]
635 [ + - ][ + - ]: 26 : }
[ + - ]
636 : : }
637 : :
638 : : //------------------------------------------------------------------------------------------------------------------
639 : 58 : bool ModuleTaskPane_Impl::ModuleHasToolPanels( const ::rtl::OUString& i_rModuleIdentifier )
640 : : {
641 [ + - ]: 58 : const ::utl::OConfigurationTreeRoot aWindowStateConfig( lcl_getModuleUIElementStatesConfig( i_rModuleIdentifier ) );
642 [ - + ]: 58 : if ( !aWindowStateConfig.isValid() )
643 : 0 : return false;
644 : :
645 : 58 : const Sequence< ::rtl::OUString > aUIElements( aWindowStateConfig.getNodeNames() );
646 [ + + ]: 5756 : for ( const ::rtl::OUString* resource = aUIElements.getConstArray();
647 : 2878 : resource != aUIElements.getConstArray() + aUIElements.getLength();
648 : : ++resource
649 : : )
650 : : {
651 [ + - ][ + + ]: 2876 : if ( impl_isToolPanelResource( *resource ) )
652 : 56 : return true;
653 : : }
654 [ + - ][ + - ]: 58 : return false;
655 : : }
656 : :
657 : : //------------------------------------------------------------------------------------------------------------------
658 : 54 : ::boost::optional< size_t > ModuleTaskPane_Impl::GetPanelPos( const ::rtl::OUString& i_rResourceURL )
659 : : {
660 : 54 : ::boost::optional< size_t > aPanelPos;
661 [ + - ][ + - ]: 141 : for ( size_t i = 0; i < m_aPanelDeck.GetPanelCount(); ++i )
662 : : {
663 [ + - ]: 141 : const ::svt::PToolPanel pPanel( m_aPanelDeck.GetPanel( i ) );
664 [ - + ]: 141 : const CustomToolPanel* pCustomPanel = dynamic_cast< const CustomToolPanel* >( pPanel.get() );
665 [ - + ]: 141 : if ( !pCustomPanel )
666 : : {
667 : : SAL_WARN( "sfx2.dialog", "ModuleTaskPane_Impl::GetPanelPos: illegal panel implementation!" );
668 : 0 : continue;
669 : : }
670 : :
671 [ + + ]: 141 : if ( pCustomPanel->GetResourceURL() == i_rResourceURL )
672 : : {
673 [ + - ]: 141 : aPanelPos = i;
674 : : break;
675 : : }
676 [ + - ]: 141 : }
[ + - + ]
677 : 54 : return aPanelPos;
678 : : }
679 : :
680 : : //------------------------------------------------------------------------------------------------------------------
681 : 220 : ::rtl::OUString ModuleTaskPane_Impl::GetPanelResourceURL( const size_t i_nPanelPos ) const
682 : : {
683 [ + - ][ - + ]: 220 : ENSURE_OR_RETURN( i_nPanelPos < m_aPanelDeck.GetPanelCount(), "ModuleTaskPane_Impl::GetPanelResourceURL: illegal panel position!", ::rtl::OUString() );
684 [ + - ]: 220 : const ::svt::PToolPanel pPanel( m_aPanelDeck.GetPanel( i_nPanelPos ) );
685 [ - + ]: 220 : const CustomToolPanel* pCustomPanel = dynamic_cast< const CustomToolPanel* >( pPanel.get() );
686 [ - + ]: 220 : ENSURE_OR_RETURN( pCustomPanel != NULL, "ModuleTaskPane_Impl::GetPanelPos: illegal panel implementation!", ::rtl::OUString() );
687 [ + - ]: 220 : return pCustomPanel->GetResourceURL();
688 : : }
689 : :
690 : : //------------------------------------------------------------------------------------------------------------------
691 : 26 : void ModuleTaskPane_Impl::SetDrawersLayout()
692 : : {
693 [ + - ]: 26 : const ::svt::PDeckLayouter pLayouter( m_aPanelDeck.GetLayouter() );
694 [ - + ]: 26 : const ::svt::DrawerDeckLayouter* pDrawerLayouter = dynamic_cast< const ::svt::DrawerDeckLayouter* >( pLayouter.get() );
695 [ + - ]: 26 : if ( pDrawerLayouter != NULL )
696 : : // already have the proper layout
697 : 26 : return;
698 [ # # ][ # # ]: 26 : m_aPanelDeck.SetLayouter( new ::svt::DrawerDeckLayouter( m_aPanelDeck, m_aPanelDeck ) );
[ # # ][ # # ]
[ # # ][ # # ]
[ + - ][ - + ]
699 : : }
700 : :
701 : : //------------------------------------------------------------------------------------------------------------------
702 : 0 : void ModuleTaskPane_Impl::SetTabsLayout( const ::svt::TabAlignment i_eTabAlignment, const ::svt::TabItemContent i_eTabContent )
703 : : {
704 [ # # ]: 0 : ::svt::PDeckLayouter pLayouter( m_aPanelDeck.GetLayouter() );
705 [ # # ]: 0 : ::svt::TabDeckLayouter* pTabLayouter = dynamic_cast< ::svt::TabDeckLayouter* >( pLayouter.get() );
706 [ # # ][ # # ]: 0 : if ( ( pTabLayouter != NULL )
[ # # ][ # # ]
707 [ # # ]: 0 : && ( pTabLayouter->GetTabAlignment() == i_eTabAlignment )
708 [ # # ]: 0 : && ( pTabLayouter->GetTabItemContent() == i_eTabContent )
709 : : )
710 : : // already have the requested layout
711 : : return;
712 : :
713 [ # # ][ # # ]: 0 : if ( pTabLayouter && ( pTabLayouter->GetTabAlignment() == i_eTabAlignment ) )
[ # # ][ # # ]
714 : : {
715 : : // changing only the item content does not require a new layouter instance
716 [ # # ]: 0 : pTabLayouter->SetTabItemContent( i_eTabContent );
717 : : return;
718 : : }
719 : :
720 [ # # ][ # # ]: 0 : m_aPanelDeck.SetLayouter( new ::svt::TabDeckLayouter( m_aPanelDeck, m_aPanelDeck, i_eTabAlignment, i_eTabContent ) );
[ # # ][ # # ]
[ # # ][ # # ]
[ # # ][ # # ]
721 : : }
722 : :
723 : : //==================================================================================================================
724 : : //= ModuleTaskPane
725 : : //==================================================================================================================
726 : : //------------------------------------------------------------------------------------------------------------------
727 : 0 : ModuleTaskPane::ModuleTaskPane( Window& i_rParentWindow, const Reference< XFrame >& i_rDocumentFrame )
728 : : :Window( &i_rParentWindow, WB_DIALOGCONTROL )
729 [ # # ][ # # ]: 0 : ,m_pImpl( new ModuleTaskPane_Impl( *this, i_rDocumentFrame, NULL ) )
730 : : {
731 : 0 : }
732 : :
733 : : //------------------------------------------------------------------------------------------------------------------
734 : 26 : ModuleTaskPane::ModuleTaskPane( Window& i_rParentWindow, const Reference< XFrame >& i_rDocumentFrame,
735 : : const IToolPanelCompare& i_rCompare )
736 : : :Window( &i_rParentWindow, WB_DIALOGCONTROL )
737 [ + - ][ + - ]: 26 : ,m_pImpl( new ModuleTaskPane_Impl( *this, i_rDocumentFrame, &i_rCompare ) )
738 : : {
739 : 26 : }
740 : :
741 : : //------------------------------------------------------------------------------------------------------------------
742 [ + - ]: 26 : ModuleTaskPane::~ModuleTaskPane()
743 : : {
744 [ - + ]: 52 : }
745 : :
746 : : //------------------------------------------------------------------------------------------------------------------
747 : 58 : bool ModuleTaskPane::ModuleHasToolPanels( const Reference< XFrame >& i_rDocumentFrame )
748 : : {
749 [ + - ]: 58 : return ModuleTaskPane_Impl::ModuleHasToolPanels( lcl_identifyModule( i_rDocumentFrame ) );
750 : : }
751 : :
752 : : //------------------------------------------------------------------------------------------------------------------
753 : 56 : void ModuleTaskPane::Resize()
754 : : {
755 : 56 : Window::Resize();
756 : 56 : m_pImpl->OnResize();
757 : 56 : }
758 : :
759 : : //------------------------------------------------------------------------------------------------------------------
760 : 0 : void ModuleTaskPane::GetFocus()
761 : : {
762 : 0 : Window::GetFocus();
763 : 0 : m_pImpl->OnGetFocus();
764 : 0 : }
765 : :
766 : : //------------------------------------------------------------------------------------------------------------------
767 : 664 : ::svt::ToolPanelDeck& ModuleTaskPane::GetPanelDeck()
768 : : {
769 : 664 : return m_pImpl->GetPanelDeck();
770 : : }
771 : :
772 : : //------------------------------------------------------------------------------------------------------------------
773 : 0 : const ::svt::ToolPanelDeck& ModuleTaskPane::GetPanelDeck() const
774 : : {
775 : 0 : return m_pImpl->GetPanelDeck();
776 : : }
777 : :
778 : : //------------------------------------------------------------------------------------------------------------------
779 : 28 : ::boost::optional< size_t > ModuleTaskPane::GetPanelPos( const ::rtl::OUString& i_rResourceURL )
780 : : {
781 : 28 : return m_pImpl->GetPanelPos( i_rResourceURL );
782 : : }
783 : :
784 : : //------------------------------------------------------------------------------------------------------------------
785 : 38 : ::rtl::OUString ModuleTaskPane::GetPanelResourceURL( const size_t i_nPanelPos ) const
786 : : {
787 : 38 : return m_pImpl->GetPanelResourceURL( i_nPanelPos );
788 : : }
789 : :
790 : : //------------------------------------------------------------------------------------------------------------------
791 : 26 : void ModuleTaskPane::SetDrawersLayout()
792 : : {
793 : 26 : m_pImpl->SetDrawersLayout();
794 : 26 : }
795 : :
796 : : //------------------------------------------------------------------------------------------------------------------
797 : 0 : void ModuleTaskPane::SetTabsLayout( const ::svt::TabAlignment i_eTabAlignment, const ::svt::TabItemContent i_eTabContent )
798 : : {
799 : 0 : m_pImpl->SetTabsLayout( i_eTabAlignment, i_eTabContent );
800 : 0 : }
801 : :
802 : : // =====================================================================================================================
803 : : // = PanelSelectorLayout
804 : : // =====================================================================================================================
805 : : enum PanelSelectorLayout
806 : : {
807 : : LAYOUT_DRAWERS,
808 : : LAYOUT_TABS_RIGHT,
809 : : LAYOUT_TABS_LEFT,
810 : : LAYOUT_TABS_TOP,
811 : : LAYOUT_TABS_BOTTOM
812 : : };
813 : :
814 : : //==================================================================================================================
815 : : //= helper
816 : : //==================================================================================================================
817 : : namespace
818 : : {
819 : 0 : PanelSelectorLayout lcl_getTabLayoutFromAlignment( const SfxChildAlignment i_eAlignment )
820 : : {
821 [ # # # # ]: 0 : switch ( i_eAlignment )
822 : : {
823 : : case SFX_ALIGN_LEFT:
824 : 0 : return LAYOUT_TABS_LEFT;
825 : : case SFX_ALIGN_TOP:
826 : 0 : return LAYOUT_TABS_TOP;
827 : : case SFX_ALIGN_BOTTOM:
828 : 0 : return LAYOUT_TABS_BOTTOM;
829 : : default:
830 : 0 : return LAYOUT_TABS_RIGHT;
831 : : }
832 : : }
833 : : }
834 : :
835 : : // =====================================================================================================================
836 : : // = PanelDescriptor
837 : : // =====================================================================================================================
838 : : /** is a helper class for TaskPaneController_Impl, holding the details about a single panel which is not
839 : : contained in the IToolPanel implementation itself.
840 : : */
841 : 754 : struct PanelDescriptor
842 : : {
843 : : ::svt::PToolPanel pPanel;
844 : : bool bHidden;
845 : :
846 : : PanelDescriptor()
847 : : :pPanel()
848 : : ,bHidden( false )
849 : : {
850 : : }
851 : :
852 : 130 : PanelDescriptor( const ::svt::PToolPanel& i_rPanel )
853 : : :pPanel( i_rPanel )
854 : 130 : ,bHidden( false )
855 : : {
856 : 130 : }
857 : : };
858 : :
859 : : //==================================================================================================================
860 : : //= TaskPaneController_Impl
861 : : //==================================================================================================================
862 : : class TaskPaneController_Impl :public ::boost::noncopyable
863 : : ,public ::svt::IToolPanelDeckListener
864 : : {
865 : : public:
866 : : TaskPaneController_Impl(
867 : : ModuleTaskPane& i_rTaskPane,
868 : : TitledDockingWindow& i_rDockingWindow
869 : : );
870 : : virtual ~TaskPaneController_Impl();
871 : :
872 : : void SetDefaultTitle( const String& i_rTitle );
873 : : void ActivateToolPanel( const ::rtl::OUString& i_rPanelURL );
874 : :
875 : : protected:
876 : : // IToolPanelDeckListener overridables
877 : : virtual void PanelInserted( const ::svt::PToolPanel& i_pPanel, const size_t i_nPosition );
878 : : virtual void PanelRemoved( const size_t i_nPosition );
879 : : virtual void ActivePanelChanged( const ::boost::optional< size_t >& i_rOldActive, const ::boost::optional< size_t >& i_rNewActive );
880 : : virtual void LayouterChanged( const ::svt::PDeckLayouter& i_rNewLayouter );
881 : : virtual void Dying();
882 : :
883 : : private:
884 : : DECL_LINK( OnToolboxClicked, ToolBox* );
885 : : DECL_LINK( OnMenuItemSelected, Menu* );
886 : : DECL_LINK( DockingChanged, TitledDockingWindow* );
887 : : SAL_WNODEPRECATED_DECLARATIONS_PUSH
888 : : ::std::auto_ptr< PopupMenu > impl_createPopupMenu() const;
889 : : SAL_WNODEPRECATED_DECLARATIONS_POP
890 : :
891 : : /// sets the given layout for the panel selector
892 : : void impl_setLayout( const PanelSelectorLayout i_eLayout, const bool i_bForce = false );
893 : :
894 : : /// returns the current layout of the panel selector
895 : : PanelSelectorLayout
896 : 32 : impl_getLayout() const { return m_eCurrentLayout; }
897 : :
898 : : void impl_updateDockingWindowTitle();
899 : : void impl_togglePanelVisibility( const size_t i_nLogicalPanelIndex );
900 : : size_t impl_getLogicalPanelIndex( const size_t i_nVisibleIndex );
901 : :
902 : : private:
903 : : enum MenuId
904 : : {
905 : : MID_UNLOCK_TASK_PANEL = 1,
906 : : MID_LOCK_TASK_PANEL = 2,
907 : : MID_LAYOUT_TABS = 3,
908 : : MID_LAYOUT_DRAWERS = 4,
909 : : MID_FIRST_PANEL = 5
910 : : };
911 : :
912 : : private:
913 : : typedef ::std::vector< PanelDescriptor > PanelDescriptors;
914 : :
915 : : ModuleTaskPane& m_rTaskPane;
916 : : TitledDockingWindow& m_rDockingWindow;
917 : : sal_uInt16 m_nViewMenuID;
918 : : PanelSelectorLayout m_eCurrentLayout;
919 : : PanelDescriptors m_aPanelRepository;
920 : : bool m_bTogglingPanelVisibility;
921 : : ::rtl::OUString m_sDefaultTitle;
922 : : };
923 : :
924 : : //------------------------------------------------------------------------------------------------------------------
925 : 26 : TaskPaneController_Impl::TaskPaneController_Impl( ModuleTaskPane& i_rTaskPane, TitledDockingWindow& i_rDockingWindow )
926 : : :m_rTaskPane( i_rTaskPane )
927 : : ,m_rDockingWindow( i_rDockingWindow )
928 : : ,m_nViewMenuID( 0 )
929 : : ,m_eCurrentLayout( LAYOUT_DRAWERS )
930 : : ,m_aPanelRepository()
931 : : ,m_bTogglingPanelVisibility( false )
932 [ + - ]: 26 : ,m_sDefaultTitle()
933 : : {
934 [ + - ]: 26 : m_rDockingWindow.ResetToolBox();
935 : : m_nViewMenuID = m_rDockingWindow.AddDropDownToolBoxItem(
936 : : SfxResId( STR_SFX_TASK_PANE_VIEW ).toString(),
937 : : HID_TASKPANE_VIEW_MENU,
938 : : LINK( this, TaskPaneController_Impl, OnToolboxClicked )
939 [ + - ][ + - ]: 26 : );
[ + - ][ + - ]
[ + - ][ + - ]
940 [ + - ]: 26 : m_rDockingWindow.SetEndDockingHdl( LINK( this, TaskPaneController_Impl, DockingChanged ) );
941 [ + - ]: 26 : impl_setLayout( LAYOUT_DRAWERS, true );
942 : :
943 [ + - ][ + - ]: 26 : m_rTaskPane.GetPanelDeck().AddListener( *this );
944 : :
945 : : // initialize the panel repository
946 [ + - ][ + - ]: 156 : for ( size_t i = 0; i < m_rTaskPane.GetPanelDeck().GetPanelCount(); ++i )
[ + + ]
947 : : {
948 [ + - ][ + - ]: 130 : ::svt::PToolPanel pPanel( m_rTaskPane.GetPanelDeck().GetPanel( i ) );
949 [ + - ][ + - ]: 130 : m_aPanelRepository.push_back( PanelDescriptor( pPanel ) );
[ + - ]
950 [ + - ]: 130 : }
951 : :
952 [ + - ][ + - ]: 26 : SetDefaultTitle( SfxResId( STR_SFX_TASKS ).toString() );
[ + - ][ + - ]
[ + - ]
953 : 26 : }
954 : :
955 : : //------------------------------------------------------------------------------------------------------------------
956 : 26 : TaskPaneController_Impl::~TaskPaneController_Impl()
957 : : {
958 [ + - ][ + - ]: 26 : m_rTaskPane.GetPanelDeck().RemoveListener( *this );
959 : :
960 : : // remove the panels which are not under the control of the panel deck currently
961 [ + - ][ + + ]: 312 : for ( PanelDescriptors::iterator panelPos = m_aPanelRepository.begin();
962 : 156 : panelPos != m_aPanelRepository.end();
963 : : ++panelPos
964 : : )
965 : : {
966 [ - + ]: 130 : if ( panelPos->bHidden )
967 [ # # ]: 0 : panelPos->pPanel->Dispose();
968 : : }
969 : 26 : m_aPanelRepository.clear();
970 [ - + ]: 52 : }
971 : :
972 : : // -----------------------------------------------------------------------------------------------------------------
973 : 26 : void TaskPaneController_Impl::SetDefaultTitle( const String& i_rTitle )
974 : : {
975 : 26 : m_sDefaultTitle = i_rTitle;
976 : 26 : impl_updateDockingWindowTitle();
977 : 26 : }
978 : :
979 : : //------------------------------------------------------------------------------------------------------------------
980 : 0 : void TaskPaneController_Impl::ActivateToolPanel( const ::rtl::OUString& i_rPanelURL )
981 : : {
982 [ # # ]: 0 : ::boost::optional< size_t > aPanelPos( m_rTaskPane.GetPanelPos( i_rPanelURL ) );
983 [ # # ][ # # ]: 0 : ENSURE_OR_RETURN_VOID( !!aPanelPos, "TaskPaneController_Impl::ActivateToolPanel: no such panel!" );
984 : :
985 [ # # ][ # # ]: 0 : if ( aPanelPos == m_rTaskPane.GetPanelDeck().GetActivePanel() )
[ # # ][ # # ]
[ # # ]
986 : : {
987 [ # # ][ # # ]: 0 : ::svt::PToolPanel pPanel( m_rTaskPane.GetPanelDeck().GetPanel( *aPanelPos ) );
[ # # ]
988 [ # # ][ # # ]: 0 : pPanel->GrabFocus();
989 : : }
990 : : else
991 : : {
992 [ # # ][ # # ]: 0 : m_rTaskPane.GetPanelDeck().ActivatePanel( aPanelPos );
993 [ # # ][ # # ]: 0 : }
994 : : }
995 : :
996 : : // -----------------------------------------------------------------------------------------------------------------
997 : 0 : IMPL_LINK( TaskPaneController_Impl, DockingChanged, TitledDockingWindow*, i_pDockingWindow )
998 : : {
999 [ # # ][ # # ]: 0 : ENSURE_OR_RETURN( i_pDockingWindow && &m_rDockingWindow, "TaskPaneController_Impl::DockingChanged: where does this come from?", 0L );
1000 : :
1001 [ # # ]: 0 : if ( impl_getLayout() == LAYOUT_DRAWERS )
1002 : 0 : return 0L;
1003 : :
1004 : 0 : impl_setLayout( lcl_getTabLayoutFromAlignment( i_pDockingWindow->GetAlignment() ) );
1005 : 0 : return 1L;
1006 : : }
1007 : :
1008 : : // -----------------------------------------------------------------------------------------------------------------
1009 : 0 : IMPL_LINK( TaskPaneController_Impl, OnToolboxClicked, ToolBox*, i_pToolBox )
1010 : : {
1011 [ # # ]: 0 : if ( i_pToolBox->GetCurItemId() == m_nViewMenuID )
1012 : : {
1013 [ # # ]: 0 : i_pToolBox->EndSelection();
1014 : :
1015 : : SAL_WNODEPRECATED_DECLARATIONS_PUSH
1016 [ # # ][ # # ]: 0 : ::std::auto_ptr< PopupMenu > pMenu = impl_createPopupMenu();
1017 : : SAL_WNODEPRECATED_DECLARATIONS_POP
1018 [ # # ]: 0 : pMenu->SetSelectHdl( LINK( this, TaskPaneController_Impl, OnMenuItemSelected ) );
1019 : :
1020 : : // pass toolbox button rect so the menu can stay open on button up
1021 [ # # ]: 0 : Rectangle aMenuRect( i_pToolBox->GetItemRect( m_nViewMenuID ) );
1022 [ # # ]: 0 : aMenuRect.SetPos( i_pToolBox->GetPosPixel() );
1023 [ # # ][ # # ]: 0 : pMenu->Execute( &m_rDockingWindow, aMenuRect, POPUPMENU_EXECUTE_DOWN );
1024 : : }
1025 : :
1026 : 0 : return 0;
1027 : : }
1028 : :
1029 : : // ---------------------------------------------------------------------------------------------------------------------
1030 : 0 : IMPL_LINK( TaskPaneController_Impl, OnMenuItemSelected, Menu*, i_pMenu )
1031 : : {
1032 [ # # ]: 0 : ENSURE_OR_RETURN( i_pMenu, "TaskPaneController_Impl::OnMenuItemSelected: illegal menu!", 0L );
1033 : :
1034 : 0 : i_pMenu->Deactivate();
1035 [ # # # # : 0 : switch ( i_pMenu->GetCurItemId() )
# ]
1036 : : {
1037 : : case MID_UNLOCK_TASK_PANEL:
1038 : 0 : m_rDockingWindow.SetFloatingMode( sal_True );
1039 : 0 : break;
1040 : :
1041 : : case MID_LOCK_TASK_PANEL:
1042 : 0 : m_rDockingWindow.SetFloatingMode( sal_False );
1043 : 0 : break;
1044 : :
1045 : : case MID_LAYOUT_DRAWERS:
1046 : 0 : impl_setLayout( LAYOUT_DRAWERS );
1047 : 0 : break;
1048 : :
1049 : : case MID_LAYOUT_TABS:
1050 : 0 : impl_setLayout( lcl_getTabLayoutFromAlignment( m_rDockingWindow.GetAlignment() ) );
1051 : 0 : break;
1052 : :
1053 : : default:
1054 : : {
1055 : 0 : size_t nPanelIndex = size_t( i_pMenu->GetCurItemId() - MID_FIRST_PANEL );
1056 : 0 : impl_togglePanelVisibility( nPanelIndex );
1057 : : }
1058 : 0 : break;
1059 : : }
1060 : :
1061 : 0 : return 1L;
1062 : : }
1063 : :
1064 : : // ---------------------------------------------------------------------------------------------------------------------
1065 : 0 : size_t TaskPaneController_Impl::impl_getLogicalPanelIndex( const size_t i_nVisibleIndex )
1066 : : {
1067 : 0 : size_t nLogicalIndex = 0;
1068 : 0 : size_t nVisibleIndex( i_nVisibleIndex );
1069 [ # # ]: 0 : for ( size_t i=0; i < m_aPanelRepository.size(); ++i )
1070 : : {
1071 [ # # ]: 0 : if ( !m_aPanelRepository[i].bHidden )
1072 : : {
1073 [ # # ]: 0 : if ( !nVisibleIndex )
1074 : 0 : break;
1075 : 0 : --nVisibleIndex;
1076 : : }
1077 : 0 : ++nLogicalIndex;
1078 : : }
1079 : 0 : return nLogicalIndex;
1080 : : }
1081 : :
1082 : : // ---------------------------------------------------------------------------------------------------------------------
1083 : 0 : void TaskPaneController_Impl::PanelInserted( const ::svt::PToolPanel& i_pPanel, const size_t i_nPosition )
1084 : : {
1085 [ # # ]: 0 : if ( m_bTogglingPanelVisibility )
1086 : 0 : return;
1087 : :
1088 : 0 : const size_t nLogicalIndex( impl_getLogicalPanelIndex( i_nPosition ) );
1089 [ # # ][ # # ]: 0 : m_aPanelRepository.insert( m_aPanelRepository.begin() + nLogicalIndex, PanelDescriptor( i_pPanel ) );
1090 : : }
1091 : :
1092 : : // ---------------------------------------------------------------------------------------------------------------------
1093 : 0 : void TaskPaneController_Impl::PanelRemoved( const size_t i_nPosition )
1094 : : {
1095 [ # # ]: 0 : if ( m_bTogglingPanelVisibility )
1096 : 0 : return;
1097 : :
1098 : 0 : const size_t nLogicalIndex( impl_getLogicalPanelIndex( i_nPosition ) );
1099 [ # # ][ # # ]: 0 : m_aPanelRepository.erase( m_aPanelRepository.begin() + nLogicalIndex );
1100 : : }
1101 : :
1102 : : // ---------------------------------------------------------------------------------------------------------------------
1103 : 32 : void TaskPaneController_Impl::ActivePanelChanged( const ::boost::optional< size_t >& i_rOldActive, const ::boost::optional< size_t >& i_rNewActive )
1104 : : {
1105 [ + - ]: 32 : if ( impl_getLayout() == LAYOUT_DRAWERS )
1106 : : // no adjustment of the title when we use the classical "drawers" layout
1107 : 32 : return;
1108 : :
1109 : 0 : impl_updateDockingWindowTitle( );
1110 : : (void)i_rOldActive;
1111 : : (void)i_rNewActive;
1112 : : }
1113 : :
1114 : : // ---------------------------------------------------------------------------------------------------------------------
1115 : 0 : void TaskPaneController_Impl::LayouterChanged( const ::svt::PDeckLayouter& i_rNewLayouter )
1116 : : {
1117 : : // not interested in
1118 : : (void)i_rNewLayouter;
1119 : 0 : }
1120 : :
1121 : : // ---------------------------------------------------------------------------------------------------------------------
1122 : 0 : void TaskPaneController_Impl::Dying()
1123 : : {
1124 : : OSL_FAIL( "TaskPaneController_Impl::Dying: unexpected call!" );
1125 : : // We are expected to live longer than the ToolPanelDeck we work with. Since we remove ourself, in our dtor,
1126 : : // as listener from the panel deck, this method here should never be called.
1127 : 0 : }
1128 : :
1129 : : // ---------------------------------------------------------------------------------------------------------------------
1130 : 0 : void TaskPaneController_Impl::impl_togglePanelVisibility( const size_t i_nLogicalPanelIndex )
1131 : : {
1132 [ # # ]: 0 : ENSURE_OR_RETURN_VOID( i_nLogicalPanelIndex < m_aPanelRepository.size(), "illegal index" );
1133 : :
1134 : : // get the actual panel index, within the deck
1135 : 0 : size_t nActualPanelIndex(0);
1136 [ # # ]: 0 : for ( size_t i=0; i < i_nLogicalPanelIndex; ++i )
1137 : : {
1138 [ # # ]: 0 : if ( !m_aPanelRepository[i].bHidden )
1139 : 0 : ++nActualPanelIndex;
1140 : : }
1141 : :
1142 [ # # ]: 0 : ::boost::optional< size_t > aActivatePanel;
1143 : :
1144 : 0 : m_bTogglingPanelVisibility = true;
1145 [ # # ]: 0 : if ( m_aPanelRepository[ i_nLogicalPanelIndex ].bHidden )
1146 : : {
1147 [ # # ][ # # ]: 0 : OSL_VERIFY( m_rTaskPane.GetPanelDeck().InsertPanel( m_aPanelRepository[ i_nLogicalPanelIndex ].pPanel, nActualPanelIndex ) == nActualPanelIndex );
1148 : : // if there has not been an active panel before, activate the newly inserted one
1149 [ # # ][ # # ]: 0 : ::boost::optional< size_t > aActivePanel( m_rTaskPane.GetPanelDeck().GetActivePanel() );
1150 [ # # ][ # # ]: 0 : if ( !aActivePanel )
1151 [ # # ][ # # ]: 0 : aActivatePanel = nActualPanelIndex;
1152 : : }
1153 : : else
1154 : : {
1155 [ # # ][ # # ]: 0 : OSL_VERIFY( m_rTaskPane.GetPanelDeck().RemovePanel( nActualPanelIndex ).get() == m_aPanelRepository[ i_nLogicalPanelIndex ].pPanel.get() );
[ # # ]
1156 : : }
1157 : 0 : m_bTogglingPanelVisibility = false;
1158 : 0 : m_aPanelRepository[ i_nLogicalPanelIndex ].bHidden = !m_aPanelRepository[ i_nLogicalPanelIndex ].bHidden;
1159 : :
1160 [ # # ][ # # ]: 0 : if ( !!aActivatePanel )
1161 [ # # ][ # # ]: 0 : m_rTaskPane.GetPanelDeck().ActivatePanel( *aActivatePanel );
[ # # ][ # # ]
[ # # ][ # # ]
1162 : : }
1163 : :
1164 : : // ---------------------------------------------------------------------------------------------------------------------
1165 : 26 : void TaskPaneController_Impl::impl_setLayout( const PanelSelectorLayout i_eLayout, const bool i_bForce )
1166 : : {
1167 [ - + ][ # # ]: 26 : if ( !i_bForce && ( m_eCurrentLayout == i_eLayout ) )
1168 : 26 : return;
1169 : :
1170 [ + - - - : 26 : switch ( i_eLayout )
- - ]
1171 : : {
1172 : : case LAYOUT_DRAWERS:
1173 : 26 : m_rTaskPane.SetDrawersLayout();
1174 : 26 : break;
1175 : : case LAYOUT_TABS_TOP:
1176 : 0 : m_rTaskPane.SetTabsLayout( ::svt::TABS_TOP, ::svt::TABITEM_IMAGE_ONLY );
1177 : 0 : break;
1178 : : case LAYOUT_TABS_BOTTOM:
1179 : 0 : m_rTaskPane.SetTabsLayout( ::svt::TABS_BOTTOM, ::svt::TABITEM_IMAGE_ONLY );
1180 : 0 : break;
1181 : : case LAYOUT_TABS_LEFT:
1182 : 0 : m_rTaskPane.SetTabsLayout( ::svt::TABS_LEFT, ::svt::TABITEM_IMAGE_ONLY );
1183 : 0 : break;
1184 : : case LAYOUT_TABS_RIGHT:
1185 : 0 : m_rTaskPane.SetTabsLayout( ::svt::TABS_RIGHT, ::svt::TABITEM_IMAGE_ONLY );
1186 : 0 : break;
1187 : : }
1188 : 26 : m_eCurrentLayout = i_eLayout;
1189 : :
1190 : 26 : impl_updateDockingWindowTitle();
1191 : : }
1192 : :
1193 : : // ---------------------------------------------------------------------------------------------------------------------
1194 : 52 : void TaskPaneController_Impl::impl_updateDockingWindowTitle()
1195 : : {
1196 [ + - ][ + - ]: 52 : ::boost::optional< size_t > aActivePanel( m_rTaskPane.GetPanelDeck().GetActivePanel() );
1197 [ + - ][ - + ]: 52 : if ( !aActivePanel || ( impl_getLayout() == LAYOUT_DRAWERS ) )
[ # # ][ + - ]
1198 [ + - ][ + - ]: 52 : m_rDockingWindow.SetTitle( m_sDefaultTitle );
[ + - ]
1199 : : else
1200 : : {
1201 [ # # ]: 0 : size_t nNewActive( *aActivePanel );
1202 [ # # ]: 0 : for ( size_t i=0; i < m_aPanelRepository.size(); ++i )
1203 : : {
1204 [ # # ]: 0 : if ( m_aPanelRepository[i].bHidden )
1205 : 0 : continue;
1206 : :
1207 [ # # ]: 0 : if ( !nNewActive )
1208 : : {
1209 [ # # ][ # # ]: 0 : m_rDockingWindow.SetTitle( m_aPanelRepository[i].pPanel->GetDisplayName() );
[ # # ][ # # ]
1210 : 0 : break;
1211 : : }
1212 : 0 : --nNewActive;
1213 : : }
1214 [ + - ]: 52 : }
1215 : 52 : }
1216 : :
1217 : : // ---------------------------------------------------------------------------------------------------------------------
1218 : : SAL_WNODEPRECATED_DECLARATIONS_PUSH
1219 : 0 : ::std::auto_ptr< PopupMenu > TaskPaneController_Impl::impl_createPopupMenu() const
1220 : : {
1221 [ # # ]: 0 : ::std::auto_ptr<PopupMenu> pMenu( new PopupMenu );
1222 : 0 : FloatingWindow* pMenuWindow = static_cast< FloatingWindow* >( pMenu->GetWindow() );
1223 [ # # ]: 0 : if ( pMenuWindow != NULL )
1224 : : {
1225 : 0 : pMenuWindow->SetPopupModeFlags ( pMenuWindow->GetPopupModeFlags() | FLOATWIN_POPUPMODE_NOMOUSEUPCLOSE );
1226 : : }
1227 : :
1228 : : // Add one entry for every tool panel element to individually make
1229 : : // them visible or hide them.
1230 : 0 : sal_uInt16 nIndex = MID_FIRST_PANEL;
1231 [ # # ]: 0 : for ( size_t i=0; i<m_aPanelRepository.size(); ++i, ++nIndex )
1232 : : {
1233 : 0 : const PanelDescriptor& rPanelDesc( m_aPanelRepository[i] );
1234 [ # # ][ # # ]: 0 : pMenu->InsertItem( nIndex, rPanelDesc.pPanel->GetDisplayName(), MIB_CHECKABLE );
[ # # ][ # # ]
1235 [ # # ]: 0 : pMenu->CheckItem( nIndex, !rPanelDesc.bHidden );
1236 : : }
1237 [ # # ]: 0 : pMenu->InsertSeparator();
1238 : :
1239 : : #if OSL_DEBUG_LEVEL > 0
1240 : : pMenu->InsertItem( MID_LAYOUT_TABS, rtl::OUString("Tab-Layout (exp.)"), MIB_CHECKABLE );
1241 : : pMenu->CheckItem( MID_LAYOUT_TABS, impl_getLayout() != LAYOUT_DRAWERS );
1242 : : pMenu->InsertItem( MID_LAYOUT_DRAWERS, rtl::OUString("Drawer-Layout"), MIB_CHECKABLE );
1243 : : pMenu->CheckItem( MID_LAYOUT_DRAWERS, impl_getLayout() == LAYOUT_DRAWERS );
1244 : :
1245 : : pMenu->InsertSeparator();
1246 : : #endif
1247 : :
1248 : : // Add entry for docking or un-docking the tool panel.
1249 [ # # ][ # # ]: 0 : if ( m_rDockingWindow.IsFloatingMode() )
1250 : 0 : pMenu->InsertItem(
1251 : : MID_LOCK_TASK_PANEL,
1252 : : SfxResId( STR_SFX_DOCK ).toString()
1253 [ # # ][ # # ]: 0 : );
[ # # # # ]
[ # # ]
1254 : : else
1255 : 0 : pMenu->InsertItem(
1256 : : MID_UNLOCK_TASK_PANEL,
1257 : : SfxResId( STR_SFX_UNDOCK ).toString()
1258 [ # # ][ # # ]: 0 : );
[ # # # # ]
[ # # ]
1259 : :
1260 [ # # ]: 0 : pMenu->RemoveDisabledEntries( sal_False, sal_False );
1261 : :
1262 : 0 : return pMenu;
1263 : : }
1264 : : SAL_WNODEPRECATED_DECLARATIONS_POP
1265 : :
1266 : : //==================================================================================================================
1267 : : //= TaskPaneController
1268 : : //==================================================================================================================
1269 : : //------------------------------------------------------------------------------------------------------------------
1270 : 26 : TaskPaneController::TaskPaneController( ModuleTaskPane& i_rTaskPane, TitledDockingWindow& i_rDockingWindow )
1271 [ + - ]: 26 : :m_pImpl( new TaskPaneController_Impl( i_rTaskPane, i_rDockingWindow ) )
1272 : : {
1273 : 26 : }
1274 : :
1275 : : //------------------------------------------------------------------------------------------------------------------
1276 : 26 : TaskPaneController::~TaskPaneController()
1277 : : {
1278 : 26 : }
1279 : :
1280 : : //------------------------------------------------------------------------------------------------------------------
1281 : 0 : void TaskPaneController::ActivateToolPanel( const ::rtl::OUString& i_rPanelURL )
1282 : : {
1283 : 0 : m_pImpl->ActivateToolPanel( i_rPanelURL );
1284 : 0 : }
1285 : :
1286 : : //......................................................................................................................
1287 : : } // namespace sfx2
1288 : : //......................................................................................................................
1289 : :
1290 : : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|