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 : #include <uielement/menubarmanager.hxx>
21 : #include <framework/menuconfiguration.hxx>
22 : #include <framework/bmkmenu.hxx>
23 : #include <framework/addonmenu.hxx>
24 : #include <framework/imageproducer.hxx>
25 : #include <threadhelp/resetableguard.hxx>
26 : #include "framework/addonsoptions.hxx"
27 : #include <classes/fwkresid.hxx>
28 : #include <classes/menumanager.hxx>
29 : #include <helper/mischelper.hxx>
30 : #include <framework/menuextensionsupplier.hxx>
31 : #include <classes/resource.hrc>
32 : #include <services.h>
33 :
34 : #include <com/sun/star/frame/XDispatch.hpp>
35 : #include <com/sun/star/lang/XMultiServiceFactory.hpp>
36 : #include <com/sun/star/lang/DisposedException.hpp>
37 : #include <com/sun/star/frame/XFramesSupplier.hpp>
38 : #include <com/sun/star/frame/XDesktop.hpp>
39 : #include <com/sun/star/container/XEnumeration.hpp>
40 : #include <com/sun/star/util/XStringWidth.hpp>
41 : #include <com/sun/star/uno/XComponentContext.hpp>
42 : #include <com/sun/star/uno/XCurrentContext.hpp>
43 : #include <com/sun/star/lang/XMultiComponentFactory.hpp>
44 : #include <com/sun/star/frame/XPopupMenuController.hpp>
45 : #include <com/sun/star/frame/XUIControllerRegistration.hpp>
46 : #include <com/sun/star/lang/SystemDependent.hpp>
47 : #include <com/sun/star/ui/GlobalAcceleratorConfiguration.hpp>
48 : #include <com/sun/star/ui/ItemType.hpp>
49 : #include <com/sun/star/ui/ImageType.hpp>
50 : #include <com/sun/star/container/XNameAccess.hpp>
51 : #include <com/sun/star/frame/ModuleManager.hpp>
52 : #include <com/sun/star/ui/ModuleUIConfigurationManagerSupplier.hpp>
53 : #include <com/sun/star/ui/XUIConfigurationManagerSupplier.hpp>
54 : #include <com/sun/star/ui/ItemStyle.hpp>
55 : #include <com/sun/star/frame/status/Visibility.hpp>
56 : #include <com/sun/star/util/URLTransformer.hpp>
57 :
58 : #include <comphelper/processfactory.hxx>
59 : #include <comphelper/extract.hxx>
60 : #include <svtools/menuoptions.hxx>
61 : #include <svtools/javainteractionhandler.hxx>
62 : #include <uno/current_context.hxx>
63 : #include <unotools/historyoptions.hxx>
64 : #include <unotools/pathoptions.hxx>
65 : #include <unotools/cmdoptions.hxx>
66 : #include <unotools/localfilehelper.hxx>
67 : #include <toolkit/unohlp.hxx>
68 : #include <vcl/svapp.hxx>
69 : #include <vcl/window.hxx>
70 : #include <osl/mutex.hxx>
71 : #include <vcl/svapp.hxx>
72 : #include <osl/file.hxx>
73 : #include <cppuhelper/implbase1.hxx>
74 : #include <svtools/acceleratorexecute.hxx>
75 : #include <rtl/logfile.hxx>
76 : #include "svtools/miscopt.hxx"
77 : #include <framework/addonmenu.hxx>
78 : #include <uielement/menubarmerger.hxx>
79 :
80 : // Be careful removing this "bad" construct. There are serious problems
81 : // with #define STRICT and including windows.h. Changing this needs some
82 : // redesign on other projects, too. Especially sal/main.h which defines
83 : // HINSTANCE depending on STRCIT!!!!!!!!!!!!!!!
84 : struct SystemMenuData
85 : {
86 : unsigned long nSize;
87 : long hMenu;
88 : };
89 :
90 : using namespace ::cppu;
91 : using namespace ::com::sun::star;
92 : using namespace ::com::sun::star::uno;
93 : using namespace ::com::sun::star::util;
94 : using namespace ::com::sun::star::beans;
95 : using namespace ::com::sun::star::frame;
96 : using namespace ::com::sun::star::container;
97 : using namespace ::com::sun::star::lang;
98 : using namespace ::com::sun::star::frame;
99 : using namespace ::com::sun::star::ui;
100 :
101 : static const char ITEM_DESCRIPTOR_COMMANDURL[] = "CommandURL";
102 : static const char ITEM_DESCRIPTOR_HELPURL[] = "HelpURL";
103 : static const char ITEM_DESCRIPTOR_CONTAINER[] = "ItemDescriptorContainer";
104 : static const char ITEM_DESCRIPTOR_LABEL[] = "Label";
105 : static const char ITEM_DESCRIPTOR_TYPE[] = "Type";
106 : static const char ITEM_DESCRIPTOR_MODULEIDENTIFIER[] = "ModuleIdentifier";
107 : static const char ITEM_DESCRIPTOR_DISPATCHPROVIDER[] = "DispatchProvider";
108 : static const char ITEM_DESCRIPTOR_STYLE[] = "Style";
109 : static const char ITEM_DESCRIPTOR_ISVISIBLE[] = "IsVisible";
110 : static const char ITEM_DESCRIPTOR_ENABLED[] = "Enabled";
111 :
112 : static const sal_Int32 LEN_DESCRIPTOR_COMMANDURL = 10;
113 : static const sal_Int32 LEN_DESCRIPTOR_HELPURL = 7;
114 : static const sal_Int32 LEN_DESCRIPTOR_CONTAINER = 23;
115 : static const sal_Int32 LEN_DESCRIPTOR_LABEL = 5;
116 : static const sal_Int32 LEN_DESCRIPTOR_TYPE = 4;
117 : static const sal_Int32 LEN_DESCRIPTOR_MODULEIDENTIFIER = 16;
118 : static const sal_Int32 LEN_DESCRIPTOR_DISPATCHPROVIDER = 16;
119 : static const sal_Int32 LEN_DESCRIPTOR_STYLE = 5;
120 : static const sal_Int32 LEN_DESCRIPTOR_ISVISIBLE = 9;
121 : static const sal_Int32 LEN_DESCRIPTOR_ENABLED = 7;
122 :
123 : const sal_uInt16 ADDONMENU_MERGE_ITEMID_START = 1500;
124 :
125 : class StringLength : public ::cppu::WeakImplHelper1< ::com::sun::star::util::XStringWidth >
126 : {
127 : public:
128 : StringLength() {}
129 0 : virtual ~StringLength() {}
130 :
131 : // XStringWidth
132 0 : sal_Int32 SAL_CALL queryStringWidth( const ::rtl::OUString& aString )
133 : throw (RuntimeException)
134 : {
135 0 : return aString.getLength();
136 : }
137 : };
138 :
139 : namespace framework
140 : {
141 :
142 : // special menu ids/command ids for dynamic popup menus
143 : #define SID_SFX_START 5000
144 : #define SID_NEWDOCDIRECT (SID_SFX_START + 537)
145 : #define SID_AUTOPILOTMENU (SID_SFX_START + 1381)
146 : #define SID_PICKLIST (SID_SFX_START + 510)
147 : #define SID_MDIWINDOWLIST (SID_SFX_START + 610)
148 : #define SID_ADDONLIST (SID_SFX_START + 1677)
149 : #define SID_HELPMENU (SID_SFX_START + 410)
150 :
151 : #define SFX_REFERER_USER "private:user"
152 :
153 : #define aCmdHelpIndex ".uno:HelpIndex"
154 : #define aCmdToolsMenu ".uno:ToolsMenu"
155 : #define aCmdHelpMenu ".uno:HelpMenu"
156 : #define aSlotHelpMenu "slot:5410"
157 :
158 : #define aSpecialWindowMenu "window"
159 : #define aSlotSpecialWindowMenu "slot:5610"
160 : #define aSlotSpecialToolsMenu "slot:6677"
161 :
162 : // special uno commands for window list
163 : #define aSpecialWindowCommand ".uno:WindowList"
164 :
165 0 : static sal_Int16 getImageTypeFromBools( sal_Bool bBig )
166 : {
167 0 : sal_Int16 n( 0 );
168 0 : if ( bBig )
169 0 : n |= ::com::sun::star::ui::ImageType::SIZE_LARGE;
170 0 : return n;
171 : }
172 :
173 582 : MenuBarManager::MenuBarManager(
174 : const Reference< XMultiServiceFactory >& xServiceFactory,
175 : const Reference< XFrame >& rFrame,
176 : const Reference< XURLTransformer >& _xURLTransformer,
177 : const Reference< XDispatchProvider >& rDispatchProvider,
178 : const rtl::OUString& rModuleIdentifier,
179 : Menu* pMenu, sal_Bool bDelete, sal_Bool bDeleteChildren )
180 582 : : ThreadHelpBase( &Application::GetSolarMutex() ), OWeakObject()
181 : , m_bDisposed( sal_False )
182 : , m_bRetrieveImages( sal_False )
183 : , m_bAcceleratorCfg( sal_False )
184 : , m_bModuleIdentified( sal_False )
185 582 : , m_aListenerContainer( m_aLock.getShareableOslMutex() )
186 : , mxServiceFactory(xServiceFactory)
187 : , m_xURLTransformer(_xURLTransformer)
188 1746 : , m_nSymbolsStyle( SvtMiscOptions().GetCurrentSymbolsStyle() )
189 : {
190 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::MenuBarManager" );
191 : m_xPopupMenuControllerRegistration = Reference< ::com::sun::star::frame::XUIControllerRegistration >(
192 582 : getServiceFactory()->createInstance( rtl::OUString( "com.sun.star.frame.PopupMenuControllerFactory" )),
193 582 : UNO_QUERY );
194 582 : FillMenuManager( pMenu, rFrame, rDispatchProvider, rModuleIdentifier, bDelete, bDeleteChildren );
195 582 : }
196 :
197 0 : MenuBarManager::MenuBarManager(
198 : const Reference< XMultiServiceFactory >& xServiceFactory,
199 : const Reference< XFrame >& rFrame,
200 : const Reference< XURLTransformer >& _xURLTransformer,
201 : AddonMenu* pAddonMenu,
202 : sal_Bool bDelete,
203 : sal_Bool bDeleteChildren )
204 0 : : ThreadHelpBase( &Application::GetSolarMutex() )
205 : , OWeakObject()
206 : , m_bDisposed( sal_False )
207 : , m_bRetrieveImages( sal_True )
208 : , m_bAcceleratorCfg( sal_False )
209 : , m_bModuleIdentified( sal_False )
210 0 : , m_aListenerContainer( m_aLock.getShareableOslMutex() )
211 : , mxServiceFactory(xServiceFactory)
212 : , m_xURLTransformer(_xURLTransformer)
213 0 : , m_nSymbolsStyle( SvtMiscOptions().GetCurrentSymbolsStyle() )
214 : {
215 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::MenuBarManager" );
216 0 : Init(rFrame,pAddonMenu,bDelete,bDeleteChildren);
217 0 : }
218 :
219 0 : MenuBarManager::MenuBarManager(
220 : const Reference< XMultiServiceFactory >& xServiceFactory,
221 : const Reference< XFrame >& rFrame,
222 : const Reference< XURLTransformer >& _xURLTransformer,
223 : AddonPopupMenu* pAddonPopupMenu,
224 : sal_Bool bDelete,
225 : sal_Bool bDeleteChildren )
226 0 : : ThreadHelpBase( &Application::GetSolarMutex() )
227 : , OWeakObject()
228 : , m_bDisposed( sal_False )
229 : , m_bRetrieveImages( sal_True )
230 : , m_bAcceleratorCfg( sal_False )
231 : , m_bModuleIdentified( sal_False )
232 0 : , m_aListenerContainer( m_aLock.getShareableOslMutex() )
233 : , mxServiceFactory(xServiceFactory)
234 : , m_xURLTransformer(_xURLTransformer)
235 0 : , m_nSymbolsStyle( SvtMiscOptions().GetCurrentSymbolsStyle() )
236 : {
237 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::MenuBarManager" );
238 0 : Init(rFrame,pAddonPopupMenu,bDelete,bDeleteChildren,true);
239 0 : }
240 :
241 3580 : Any SAL_CALL MenuBarManager::queryInterface( const Type & rType ) throw ( RuntimeException )
242 : {
243 : Any a = ::cppu::queryInterface(
244 : rType ,
245 : (static_cast< ::com::sun::star::frame::XStatusListener* >(this)),
246 : (static_cast< ::com::sun::star::frame::XFrameActionListener* >(this)),
247 : (static_cast< ::com::sun::star::ui::XUIConfigurationListener* >(this)),
248 : (static_cast< XEventListener* >((XStatusListener *)this)),
249 : (static_cast< XComponent* >(this)),
250 3580 : (static_cast< ::com::sun::star::awt::XSystemDependentMenuPeer* >(this)));
251 :
252 3580 : if ( a.hasValue() )
253 2992 : return a;
254 :
255 588 : return OWeakObject::queryInterface( rType );
256 : }
257 :
258 :
259 14444 : void SAL_CALL MenuBarManager::acquire() throw()
260 : {
261 14444 : OWeakObject::acquire();
262 14444 : }
263 :
264 :
265 13624 : void SAL_CALL MenuBarManager::release() throw()
266 : {
267 13624 : OWeakObject::release();
268 13624 : }
269 :
270 :
271 0 : Any SAL_CALL MenuBarManager::getMenuHandle( const Sequence< sal_Int8 >& /*ProcessId*/, sal_Int16 SystemType ) throw (RuntimeException)
272 : {
273 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::getMenuHandle" );
274 0 : ResetableGuard aGuard( m_aLock );
275 :
276 0 : if ( m_bDisposed )
277 0 : throw com::sun::star::lang::DisposedException();
278 :
279 0 : Any a;
280 :
281 0 : if ( m_pVCLMenu )
282 : {
283 0 : SolarMutexGuard aSolarGuard;
284 :
285 : SystemMenuData aSystemMenuData;
286 0 : aSystemMenuData.nSize = sizeof( SystemMenuData );
287 :
288 0 : m_pVCLMenu->GetSystemMenuData( &aSystemMenuData );
289 : #ifdef QUARTZ
290 : if( SystemType == SystemDependent::SYSTEM_MAC )
291 : {
292 : }
293 : #elif (defined WNT)
294 : if( SystemType == SystemDependent::SYSTEM_WIN32 )
295 : {
296 : a <<= (long) aSystemMenuData.hMenu;
297 : }
298 : #elif (defined UNX)
299 : if( SystemType == SystemDependent::SYSTEM_XWINDOW )
300 : {
301 0 : }
302 : #endif
303 : }
304 :
305 0 : return a;
306 : }
307 :
308 516 : MenuBarManager::~MenuBarManager()
309 : {
310 : // stop asynchronous settings timer
311 172 : m_xDeferedItemContainer.clear();
312 172 : m_aAsyncSettingsTimer.Stop();
313 :
314 : DBG_ASSERT( OWeakObject::m_refCount == 0, "Who wants to delete an object with refcount > 0!" );
315 344 : }
316 :
317 172 : void MenuBarManager::Destroy()
318 : {
319 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::Destroy" );
320 172 : SolarMutexGuard aGuard;
321 :
322 172 : if ( !m_bDisposed )
323 : {
324 : // stop asynchronous settings timer and
325 : // release defered item container reference
326 172 : m_aAsyncSettingsTimer.Stop();
327 172 : m_xDeferedItemContainer.clear();
328 172 : RemoveListener();
329 :
330 172 : std::vector< MenuItemHandler* >::iterator p;
331 798 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
332 : {
333 626 : MenuItemHandler* pItemHandler = *p;
334 626 : pItemHandler->xMenuItemDispatch.clear();
335 626 : pItemHandler->xSubMenuManager.clear();
336 626 : pItemHandler->xPopupMenu.clear();
337 626 : delete pItemHandler;
338 : }
339 172 : m_aMenuItemHandlerVector.clear();
340 :
341 172 : if ( m_bDeleteMenu )
342 : {
343 74 : delete m_pVCLMenu;
344 74 : m_pVCLMenu = 0;
345 : }
346 172 : }
347 172 : }
348 :
349 : // XComponent
350 172 : void SAL_CALL MenuBarManager::dispose() throw( RuntimeException )
351 : {
352 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::dispose" );
353 172 : Reference< XComponent > xThis( static_cast< OWeakObject* >(this), UNO_QUERY );
354 :
355 172 : EventObject aEvent( xThis );
356 172 : m_aListenerContainer.disposeAndClear( aEvent );
357 :
358 : {
359 172 : ResetableGuard aGuard( m_aLock );
360 172 : Destroy();
361 172 : m_bDisposed = sal_True;
362 :
363 172 : if ( m_xDocImageManager.is() )
364 : {
365 : try
366 : {
367 172 : m_xDocImageManager->removeConfigurationListener(
368 : Reference< XUIConfigurationListener >(
369 172 : static_cast< OWeakObject* >( this ), UNO_QUERY ));
370 : }
371 0 : catch ( const Exception& )
372 : {
373 : }
374 : }
375 172 : if ( m_xModuleImageManager.is() )
376 : {
377 : try
378 : {
379 172 : m_xModuleImageManager->removeConfigurationListener(
380 : Reference< XUIConfigurationListener >(
381 172 : static_cast< OWeakObject* >( this ), UNO_QUERY ));
382 : }
383 0 : catch ( const Exception& )
384 : {
385 : }
386 : }
387 172 : m_xDocImageManager.clear();
388 172 : m_xModuleImageManager.clear();
389 172 : m_xGlobalAcceleratorManager.clear();
390 172 : m_xModuleAcceleratorManager.clear();
391 172 : m_xDocAcceleratorManager.clear();
392 172 : m_xUICommandLabels.clear();
393 172 : m_xPopupMenuControllerRegistration.clear();
394 172 : mxServiceFactory.clear();
395 172 : }
396 172 : }
397 :
398 0 : void SAL_CALL MenuBarManager::addEventListener( const Reference< XEventListener >& xListener ) throw( RuntimeException )
399 : {
400 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::addEventListener" );
401 0 : ResetableGuard aGuard( m_aLock );
402 :
403 : /* SAFE AREA ----------------------------------------------------------------------------------------------- */
404 0 : if ( m_bDisposed )
405 0 : throw DisposedException();
406 :
407 0 : m_aListenerContainer.addInterface( ::getCppuType( ( const Reference< XEventListener >* ) NULL ), xListener );
408 0 : }
409 :
410 0 : void SAL_CALL MenuBarManager::removeEventListener( const Reference< XEventListener >& xListener ) throw( RuntimeException )
411 : {
412 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::removeEventListener" );
413 0 : ResetableGuard aGuard( m_aLock );
414 : /* SAFE AREA ----------------------------------------------------------------------------------------------- */
415 0 : m_aListenerContainer.removeInterface( ::getCppuType( ( const Reference< XEventListener >* ) NULL ), xListener );
416 0 : }
417 :
418 0 : void SAL_CALL MenuBarManager::elementInserted( const ::com::sun::star::ui::ConfigurationEvent& Event )
419 : throw (RuntimeException)
420 : {
421 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::elementInserted" );
422 0 : ResetableGuard aGuard( m_aLock );
423 :
424 : /* SAFE AREA ----------------------------------------------------------------------------------------------- */
425 0 : if ( m_bDisposed )
426 0 : return;
427 :
428 0 : sal_Int16 nImageType = sal_Int16();
429 0 : sal_Int16 nCurrentImageType = getImageTypeFromBools( sal_False );
430 0 : if (( Event.aInfo >>= nImageType ) &&
431 : ( nImageType == nCurrentImageType ))
432 0 : RequestImages();
433 : }
434 :
435 0 : void SAL_CALL MenuBarManager::elementRemoved( const ::com::sun::star::ui::ConfigurationEvent& Event )
436 : throw (RuntimeException)
437 : {
438 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::elementRemoved" );
439 0 : elementInserted(Event);
440 0 : }
441 :
442 0 : void SAL_CALL MenuBarManager::elementReplaced( const ::com::sun::star::ui::ConfigurationEvent& Event )
443 : throw (RuntimeException)
444 : {
445 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::elementReplaced" );
446 0 : elementInserted(Event);
447 0 : }
448 :
449 : // XFrameActionListener
450 148 : void SAL_CALL MenuBarManager::frameAction( const FrameActionEvent& Action )
451 : throw ( RuntimeException )
452 : {
453 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::frameAction" );
454 148 : ResetableGuard aGuard( m_aLock );
455 :
456 148 : if ( m_bDisposed )
457 0 : throw com::sun::star::lang::DisposedException();
458 :
459 148 : if ( Action.Action == FrameAction_CONTEXT_CHANGED )
460 : {
461 0 : std::vector< MenuItemHandler* >::iterator p;
462 0 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
463 : {
464 : // Clear dispatch reference as we will requery it later o
465 0 : MenuItemHandler* pItemHandler = *p;
466 0 : pItemHandler->xMenuItemDispatch.clear();
467 : }
468 148 : }
469 148 : }
470 :
471 : // XStatusListener
472 0 : void SAL_CALL MenuBarManager::statusChanged( const FeatureStateEvent& Event )
473 : throw ( RuntimeException )
474 : {
475 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::statusChanged" );
476 0 : ::rtl::OUString aFeatureURL = Event.FeatureURL.Complete;
477 :
478 0 : SolarMutexGuard aSolarGuard;
479 : {
480 0 : ResetableGuard aGuard( m_aLock );
481 :
482 0 : if ( m_bDisposed )
483 0 : return;
484 :
485 : // We have to check all menu entries as there can be identical entries in a popup menu.
486 0 : std::vector< MenuItemHandler* >::iterator p;
487 0 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
488 : {
489 0 : MenuItemHandler* pMenuItemHandler = *p;
490 0 : if ( pMenuItemHandler->aMenuItemURL == aFeatureURL )
491 : {
492 0 : sal_Bool bCheckmark( sal_False );
493 0 : sal_Bool bMenuItemEnabled( m_pVCLMenu->IsItemEnabled( pMenuItemHandler->nItemId ));
494 0 : sal_Bool bEnabledItem( Event.IsEnabled );
495 0 : rtl::OUString aItemText;
496 0 : status::Visibility aVisibilityStatus;
497 :
498 : #ifdef UNIX
499 : //enable some slots hardly, because UNIX clipboard does not notify all changes
500 : // Can be removed if follow up task will be fixed directly within applications.
501 : // Note: PasteSpecial is handled specifically by calc
502 0 : if ( pMenuItemHandler->aMenuItemURL == ".uno:Paste"
503 0 : || pMenuItemHandler->aMenuItemURL == ".uno:PasteClipboard" ) // special for draw/impress
504 0 : bEnabledItem = sal_True;
505 : #endif
506 :
507 : // Enable/disable item
508 0 : if ( bEnabledItem != bMenuItemEnabled )
509 0 : m_pVCLMenu->EnableItem( pMenuItemHandler->nItemId, bEnabledItem );
510 :
511 0 : if ( Event.State >>= bCheckmark )
512 : {
513 : // Checkmark or RadioButton
514 0 : m_pVCLMenu->ShowItem( pMenuItemHandler->nItemId, sal_True );
515 0 : m_pVCLMenu->CheckItem( pMenuItemHandler->nItemId, bCheckmark );
516 :
517 0 : MenuItemBits nBits = m_pVCLMenu->GetItemBits( pMenuItemHandler->nItemId );
518 : //If not already designated RadioButton set as CheckMark
519 0 : if (!(nBits & MIB_RADIOCHECK))
520 0 : m_pVCLMenu->SetItemBits( pMenuItemHandler->nItemId, nBits | MIB_CHECKABLE );
521 : }
522 0 : else if ( Event.State >>= aItemText )
523 : {
524 : // Replacement for place holders
525 0 : if ( aItemText.matchAsciiL( "($1)", 4 ))
526 : {
527 0 : String aResStr = String( FwkResId( STR_UPDATEDOC ));
528 0 : rtl::OUString aTmp( aResStr );
529 0 : aTmp += rtl::OUString( " " );
530 0 : aTmp += aItemText.copy( 4 );
531 0 : aItemText = aTmp;
532 : }
533 0 : else if ( aItemText.matchAsciiL( "($2)", 4 ))
534 : {
535 0 : String aResStr = String( FwkResId( STR_CLOSEDOC_ANDRETURN ));
536 0 : rtl::OUString aTmp( aResStr );
537 0 : aTmp += aItemText.copy( 4 );
538 0 : aItemText = aTmp;
539 : }
540 0 : else if ( aItemText.matchAsciiL( "($3)", 4 ))
541 : {
542 0 : String aResStr = String( FwkResId( STR_SAVECOPYDOC ));
543 0 : rtl::OUString aTmp( aResStr );
544 0 : aTmp += aItemText.copy( 4 );
545 0 : aItemText = aTmp;
546 : }
547 :
548 0 : m_pVCLMenu->ShowItem( pMenuItemHandler->nItemId, sal_True );
549 0 : m_pVCLMenu->SetItemText( pMenuItemHandler->nItemId, aItemText );
550 : }
551 0 : else if ( Event.State >>= aVisibilityStatus )
552 : {
553 : // Visibility
554 0 : m_pVCLMenu->ShowItem( pMenuItemHandler->nItemId, aVisibilityStatus.bVisible );
555 : }
556 : else
557 0 : m_pVCLMenu->ShowItem( pMenuItemHandler->nItemId, sal_True );
558 : }
559 :
560 0 : if ( Event.Requery )
561 : {
562 : // Release dispatch object - will be requeried on the next activate!
563 0 : pMenuItemHandler->xMenuItemDispatch.clear();
564 : }
565 0 : }
566 0 : }
567 : }
568 :
569 : // Helper to retrieve own structure from item ID
570 0 : MenuBarManager::MenuItemHandler* MenuBarManager::GetMenuItemHandler( sal_uInt16 nItemId )
571 : {
572 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::GetMenuItemHandler" );
573 0 : ResetableGuard aGuard( m_aLock );
574 :
575 0 : std::vector< MenuItemHandler* >::iterator p;
576 0 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
577 : {
578 0 : MenuItemHandler* pItemHandler = *p;
579 0 : if ( pItemHandler->nItemId == nItemId )
580 0 : return pItemHandler;
581 : }
582 :
583 0 : return 0;
584 : }
585 :
586 : // Helper to set request images flag
587 0 : void MenuBarManager::RequestImages()
588 : {
589 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::RequestImages" );
590 :
591 0 : m_bRetrieveImages = sal_True;
592 0 : const sal_uInt32 nCount = m_aMenuItemHandlerVector.size();
593 0 : for ( sal_uInt32 i = 0; i < nCount; ++i )
594 : {
595 0 : MenuItemHandler* pItemHandler = m_aMenuItemHandlerVector[i];
596 0 : if ( pItemHandler->xSubMenuManager.is() )
597 : {
598 0 : MenuBarManager* pMenuBarManager = (MenuBarManager*)(pItemHandler->xSubMenuManager.get());
599 0 : pMenuBarManager->RequestImages();
600 : }
601 : }
602 0 : }
603 :
604 : // Helper to reset objects to prepare shutdown
605 172 : void MenuBarManager::RemoveListener()
606 : {
607 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::RemoveListener" );
608 172 : ResetableGuard aGuard( m_aLock );
609 :
610 : // Check service manager reference. Remove listener can be called due
611 : // to a disposing call from the frame and therefore we already removed
612 : // our listeners and release the service manager reference!
613 172 : Reference< XMultiServiceFactory > xServiceManager = getServiceFactory();
614 172 : if ( xServiceManager.is() )
615 : {
616 172 : std::vector< MenuItemHandler* >::iterator p;
617 798 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
618 : {
619 626 : MenuItemHandler* pItemHandler = *p;
620 626 : if ( pItemHandler->xMenuItemDispatch.is() )
621 : {
622 0 : URL aTargetURL;
623 0 : aTargetURL.Complete = pItemHandler->aMenuItemURL;
624 0 : m_xURLTransformer->parseStrict( aTargetURL );
625 :
626 0 : pItemHandler->xMenuItemDispatch->removeStatusListener(
627 0 : static_cast< XStatusListener* >( this ), aTargetURL );
628 : }
629 :
630 626 : pItemHandler->xMenuItemDispatch.clear();
631 626 : if ( pItemHandler->xPopupMenu.is() )
632 : {
633 : {
634 : // Remove popup menu from menu structure
635 22 : SolarMutexGuard aGuard2;
636 22 : m_pVCLMenu->SetPopupMenu( pItemHandler->nItemId, 0 );
637 : }
638 :
639 22 : Reference< com::sun::star::lang::XEventListener > xEventListener( pItemHandler->xPopupMenuController, UNO_QUERY );
640 22 : if ( xEventListener.is() )
641 : {
642 0 : EventObject aEventObject;
643 0 : aEventObject.Source = (OWeakObject *)this;
644 0 : xEventListener->disposing( aEventObject );
645 : }
646 :
647 : // We now provide a popup menu controller to external code.
648 : // Therefore the life-time must be explicitly handled via
649 : // dispose!!
650 : try
651 : {
652 22 : Reference< XComponent > xComponent( pItemHandler->xPopupMenuController, UNO_QUERY );
653 22 : if ( xComponent.is() )
654 0 : xComponent->dispose();
655 : }
656 0 : catch ( const RuntimeException& )
657 : {
658 0 : throw;
659 : }
660 0 : catch ( const Exception& )
661 : {
662 : }
663 :
664 : // Release references to controller and popup menu
665 22 : pItemHandler->xPopupMenuController.clear();
666 22 : pItemHandler->xPopupMenu.clear();
667 : }
668 :
669 626 : Reference< XComponent > xComponent( pItemHandler->xSubMenuManager, UNO_QUERY );
670 626 : if ( xComponent.is() )
671 74 : xComponent->dispose();
672 626 : }
673 : }
674 :
675 : try
676 : {
677 172 : if ( m_xFrame.is() )
678 172 : m_xFrame->removeFrameActionListener( Reference< XFrameActionListener >(
679 172 : static_cast< OWeakObject* >( this ), UNO_QUERY ));
680 : }
681 0 : catch ( const Exception& )
682 : {
683 : }
684 :
685 172 : m_xFrame = 0;
686 172 : }
687 :
688 410 : void SAL_CALL MenuBarManager::disposing( const EventObject& Source ) throw ( RuntimeException )
689 : {
690 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::disposing(evt)" );
691 410 : MenuItemHandler* pMenuItemDisposing = NULL;
692 :
693 410 : ResetableGuard aGuard( m_aLock );
694 :
695 410 : std::vector< MenuItemHandler* >::iterator p;
696 410 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
697 : {
698 0 : MenuItemHandler* pMenuItemHandler = *p;
699 0 : if ( pMenuItemHandler->xMenuItemDispatch.is() &&
700 0 : pMenuItemHandler->xMenuItemDispatch == Source.Source )
701 : {
702 : // disposing called from menu item dispatcher, remove listener
703 0 : pMenuItemDisposing = pMenuItemHandler;
704 0 : break;
705 : }
706 : }
707 :
708 410 : if ( pMenuItemDisposing )
709 : {
710 : // Release references to the dispatch object
711 0 : URL aTargetURL;
712 0 : aTargetURL.Complete = pMenuItemDisposing->aMenuItemURL;
713 :
714 : // Check reference of service manager before we use it. Reference could
715 : // be cleared due to RemoveListener call!
716 0 : Reference< XMultiServiceFactory > xServiceManager( getServiceFactory() );
717 0 : if ( xServiceManager.is() )
718 : {
719 0 : m_xURLTransformer->parseStrict( aTargetURL );
720 :
721 0 : pMenuItemDisposing->xMenuItemDispatch->removeStatusListener(
722 0 : static_cast< XStatusListener* >( this ), aTargetURL );
723 0 : pMenuItemDisposing->xMenuItemDispatch = Reference< XDispatch >();
724 0 : if ( pMenuItemDisposing->xPopupMenu.is() )
725 : {
726 0 : Reference< com::sun::star::lang::XEventListener > xEventListener( pMenuItemDisposing->xPopupMenuController, UNO_QUERY );
727 0 : if ( xEventListener.is() )
728 0 : xEventListener->disposing( Source );
729 :
730 : {
731 : // Remove popup menu from menu structure as we release our reference to
732 : // the controller.
733 0 : SolarMutexGuard aGuard2;
734 0 : m_pVCLMenu->SetPopupMenu( pMenuItemDisposing->nItemId, 0 );
735 : }
736 :
737 0 : pMenuItemDisposing->xPopupMenuController.clear();
738 0 : pMenuItemDisposing->xPopupMenu.clear();
739 : }
740 : }
741 410 : return;
742 : }
743 410 : else if ( Source.Source == m_xFrame )
744 : {
745 : // Our frame gets disposed. We have to remove all our listeners
746 0 : RemoveListener();
747 : }
748 410 : else if ( Source.Source == Reference< XInterface >( m_xDocImageManager, UNO_QUERY ))
749 0 : m_xDocImageManager.clear();
750 410 : else if ( Source.Source == Reference< XInterface >( m_xModuleImageManager, UNO_QUERY ))
751 410 : m_xModuleImageManager.clear();
752 : }
753 :
754 :
755 2 : void MenuBarManager::CheckAndAddMenuExtension( Menu* pMenu )
756 : {
757 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::CheckAndAddMenuExtension" );
758 :
759 : // retrieve menu extension item
760 2 : MenuExtensionItem aMenuItem( GetMenuExtension() );
761 2 : if (( !aMenuItem.aURL.isEmpty() ) &&
762 0 : ( !aMenuItem.aLabel.isEmpty() ))
763 : {
764 : // remove all old window list entries from menu
765 0 : sal_uInt16 nNewItemId( 0 );
766 0 : sal_uInt16 nInsertPos( MENU_APPEND );
767 0 : sal_uInt16 nBeforePos( MENU_APPEND );
768 0 : String aCommandBefore( rtl::OUString(".uno:About"));
769 0 : for ( sal_uInt16 n = 0; n < pMenu->GetItemCount(); n++ )
770 : {
771 0 : sal_uInt16 nItemId = pMenu->GetItemId( n );
772 0 : nNewItemId = std::max( nItemId, nNewItemId );
773 0 : if ( pMenu->GetItemCommand( nItemId ) == aCommandBefore )
774 0 : nBeforePos = n;
775 : }
776 0 : ++nNewItemId;
777 :
778 0 : if ( nBeforePos != MENU_APPEND )
779 0 : nInsertPos = nBeforePos;
780 :
781 0 : pMenu->InsertItem( nNewItemId, aMenuItem.aLabel, 0, nInsertPos );
782 0 : pMenu->SetItemCommand( nNewItemId, aMenuItem.aURL );
783 2 : }
784 2 : }
785 :
786 22 : static void lcl_CheckForChildren(Menu* pMenu, sal_uInt16 nItemId)
787 : {
788 22 : if (PopupMenu* pThisPopup = pMenu->GetPopupMenu( nItemId ))
789 22 : pMenu->EnableItem( nItemId, pThisPopup->GetItemCount() ? true : false );
790 22 : }
791 :
792 : //_________________________________________________________________________________________________________________
793 : // vcl handler
794 : //_________________________________________________________________________________________________________________
795 :
796 : namespace {
797 :
798 : class QuietInteractionContext:
799 : public cppu::WeakImplHelper1< com::sun::star::uno::XCurrentContext >,
800 : private boost::noncopyable
801 : {
802 : public:
803 0 : QuietInteractionContext(
804 : com::sun::star::uno::Reference< com::sun::star::uno::XCurrentContext >
805 : const & context):
806 0 : context_(context) {}
807 :
808 : private:
809 0 : virtual ~QuietInteractionContext() {}
810 :
811 0 : virtual com::sun::star::uno::Any SAL_CALL getValueByName(
812 : rtl::OUString const & Name)
813 : throw (com::sun::star::uno::RuntimeException)
814 : {
815 0 : return Name != JAVA_INTERACTION_HANDLER_NAME && context_.is()
816 0 : ? context_->getValueByName(Name)
817 0 : : com::sun::star::uno::Any();
818 : }
819 :
820 : com::sun::star::uno::Reference< com::sun::star::uno::XCurrentContext >
821 : context_;
822 : };
823 :
824 : }
825 :
826 0 : IMPL_LINK( MenuBarManager, Activate, Menu *, pMenu )
827 : {
828 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::Activate" );
829 0 : if ( pMenu == m_pVCLMenu )
830 : {
831 : com::sun::star::uno::ContextLayer layer(
832 : new QuietInteractionContext(
833 0 : com::sun::star::uno::getCurrentContext()));
834 :
835 : // set/unset hiding disabled menu entries
836 0 : sal_Bool bDontHide = SvtMenuOptions().IsEntryHidingEnabled();
837 0 : const StyleSettings& rSettings = Application::GetSettings().GetStyleSettings();
838 0 : sal_Bool bShowMenuImages = rSettings.GetUseImagesInMenus();
839 0 : sal_Bool bHasDisabledEntries = SvtCommandOptions().HasEntries( SvtCommandOptions::CMDOPTION_DISABLED );
840 :
841 0 : ResetableGuard aGuard( m_aLock );
842 :
843 0 : sal_uInt16 nFlag = pMenu->GetMenuFlags();
844 0 : if ( bDontHide )
845 0 : nFlag &= ~MENU_FLAG_HIDEDISABLEDENTRIES;
846 : else
847 0 : nFlag |= MENU_FLAG_HIDEDISABLEDENTRIES;
848 0 : pMenu->SetMenuFlags( nFlag );
849 :
850 0 : if ( m_bActive )
851 0 : return 0;
852 :
853 0 : m_bActive = sal_True;
854 :
855 0 : ::rtl::OUString aMenuCommand( m_aMenuItemCommand );
856 0 : if ( m_aMenuItemCommand == aSpecialWindowMenu || m_aMenuItemCommand == aSlotSpecialWindowMenu || aMenuCommand == aSpecialWindowCommand )
857 0 : MenuManager::UpdateSpecialWindowMenu( pMenu,getServiceFactory(),m_aLock );
858 :
859 : // Check if some modes have changed so we have to update our menu images
860 0 : sal_Int16 nSymbolsStyle = SvtMiscOptions().GetCurrentSymbolsStyle();
861 :
862 0 : if ( m_bRetrieveImages ||
863 : bShowMenuImages != m_bShowMenuImages ||
864 : nSymbolsStyle != m_nSymbolsStyle )
865 : {
866 0 : m_bShowMenuImages = bShowMenuImages;
867 0 : m_bRetrieveImages = sal_False;
868 0 : m_nSymbolsStyle = nSymbolsStyle;
869 0 : MenuManager::FillMenuImages( m_xFrame, pMenu, bShowMenuImages );
870 : }
871 :
872 : // Try to map commands to labels
873 0 : for ( sal_uInt16 nPos = 0; nPos < pMenu->GetItemCount(); nPos++ )
874 : {
875 0 : sal_uInt16 nItemId = pMenu->GetItemId( nPos );
876 0 : if (( pMenu->GetItemType( nPos ) != MENUITEM_SEPARATOR ) &&
877 0 : ( pMenu->GetItemText( nItemId ).Len() == 0 ))
878 : {
879 0 : String aCommand = pMenu->GetItemCommand( nItemId );
880 0 : if ( aCommand.Len() > 0 ) {
881 0 : pMenu->SetItemText( nItemId, RetrieveLabelFromCommand( aCommand ));
882 0 : }
883 : }
884 : }
885 :
886 : // Try to set accelerator keys
887 : {
888 0 : RetrieveShortcuts( m_aMenuItemHandlerVector );
889 0 : std::vector< MenuItemHandler* >::iterator p;
890 0 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
891 : {
892 0 : MenuItemHandler* pMenuItemHandler = *p;
893 :
894 : // Set key code, workaround for hard-coded shortcut F1 mapped to .uno:HelpIndex
895 : // Only non-popup menu items can have a short-cut
896 0 : if ( pMenuItemHandler->aMenuItemURL == aCmdHelpIndex )
897 : {
898 0 : KeyCode aKeyCode( KEY_F1 );
899 0 : pMenu->SetAccelKey( pMenuItemHandler->nItemId, aKeyCode );
900 : }
901 0 : else if ( pMenu->GetPopupMenu( pMenuItemHandler->nItemId ) == 0 )
902 0 : pMenu->SetAccelKey( pMenuItemHandler->nItemId, pMenuItemHandler->aKeyCode );
903 : }
904 : }
905 :
906 0 : URL aTargetURL;
907 :
908 : // Use provided dispatch provider => fallback to frame as dispatch provider
909 0 : Reference< XDispatchProvider > xDispatchProvider;
910 0 : if ( m_xDispatchProvider.is() )
911 0 : xDispatchProvider = m_xDispatchProvider;
912 : else
913 0 : xDispatchProvider = Reference< XDispatchProvider >( m_xFrame, UNO_QUERY );
914 :
915 0 : if ( xDispatchProvider.is() )
916 : {
917 0 : KeyCode aEmptyKeyCode;
918 0 : SvtCommandOptions aCmdOptions;
919 0 : std::vector< MenuItemHandler* >::iterator p;
920 0 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
921 : {
922 0 : MenuItemHandler* pMenuItemHandler = *p;
923 0 : if ( pMenuItemHandler )
924 : {
925 0 : if ( !pMenuItemHandler->xMenuItemDispatch.is() &&
926 0 : !pMenuItemHandler->xSubMenuManager.is() )
927 : {
928 : // There is no dispatch mechanism for the special window list menu items,
929 : // because they are handled directly through XFrame->activate!!!
930 : // Don't update dispatches for special file menu items.
931 0 : if ( !(( pMenuItemHandler->nItemId >= START_ITEMID_WINDOWLIST &&
932 0 : pMenuItemHandler->nItemId < END_ITEMID_WINDOWLIST )))
933 : {
934 0 : Reference< XDispatch > xMenuItemDispatch;
935 :
936 0 : ::rtl::OUString aItemCommand = pMenu->GetItemCommand( pMenuItemHandler->nItemId );
937 0 : if ( aItemCommand.isEmpty() )
938 : {
939 0 : aItemCommand = ::rtl::OUString( "slot:" );
940 0 : aItemCommand += ::rtl::OUString::valueOf( (sal_Int32)pMenuItemHandler->nItemId );
941 0 : pMenu->SetItemCommand( pMenuItemHandler->nItemId, aItemCommand );
942 : }
943 :
944 0 : aTargetURL.Complete = aItemCommand;
945 :
946 0 : m_xURLTransformer->parseStrict( aTargetURL );
947 :
948 0 : if ( bHasDisabledEntries )
949 : {
950 0 : if ( aCmdOptions.Lookup( SvtCommandOptions::CMDOPTION_DISABLED, aTargetURL.Path ))
951 0 : pMenu->HideItem( pMenuItemHandler->nItemId );
952 : }
953 :
954 0 : if ( m_bIsBookmarkMenu )
955 0 : xMenuItemDispatch = xDispatchProvider->queryDispatch( aTargetURL, pMenuItemHandler->aTargetFrame, 0 );
956 : else
957 0 : xMenuItemDispatch = xDispatchProvider->queryDispatch( aTargetURL, ::rtl::OUString(), 0 );
958 :
959 0 : sal_Bool bPopupMenu( sal_False );
960 0 : if ( !pMenuItemHandler->xPopupMenuController.is() &&
961 0 : m_xPopupMenuControllerRegistration->hasController( aItemCommand, rtl::OUString() ))
962 : {
963 0 : bPopupMenu = CreatePopupMenuController( pMenuItemHandler );
964 : }
965 0 : else if ( pMenuItemHandler->xPopupMenuController.is() )
966 : {
967 : // Force update of popup menu
968 0 : pMenuItemHandler->xPopupMenuController->updatePopupMenu();
969 0 : bPopupMenu = sal_True;
970 0 : if (PopupMenu* pThisPopup = pMenu->GetPopupMenu( pMenuItemHandler->nItemId ))
971 0 : pMenu->EnableItem( pMenuItemHandler->nItemId, pThisPopup->GetItemCount() ? true : false );
972 : }
973 :
974 0 : lcl_CheckForChildren(pMenu, pMenuItemHandler->nItemId);
975 :
976 0 : if ( xMenuItemDispatch.is() )
977 : {
978 0 : pMenuItemHandler->xMenuItemDispatch = xMenuItemDispatch;
979 0 : pMenuItemHandler->aMenuItemURL = aTargetURL.Complete;
980 :
981 0 : if ( !bPopupMenu )
982 : {
983 : // We need only an update to reflect the current state
984 0 : xMenuItemDispatch->addStatusListener( static_cast< XStatusListener* >( this ), aTargetURL );
985 0 : xMenuItemDispatch->removeStatusListener( static_cast< XStatusListener* >( this ), aTargetURL );
986 : }
987 : }
988 0 : else if ( !bPopupMenu )
989 0 : pMenu->EnableItem( pMenuItemHandler->nItemId, sal_False );
990 : }
991 : }
992 0 : else if ( pMenuItemHandler->xPopupMenuController.is() )
993 : {
994 : // Force update of popup menu
995 0 : pMenuItemHandler->xPopupMenuController->updatePopupMenu();
996 0 : lcl_CheckForChildren(pMenu, pMenuItemHandler->nItemId);
997 : }
998 0 : else if ( pMenuItemHandler->xMenuItemDispatch.is() )
999 : {
1000 : // We need an update to reflect the current state
1001 : try
1002 : {
1003 0 : aTargetURL.Complete = pMenuItemHandler->aMenuItemURL;
1004 0 : m_xURLTransformer->parseStrict( aTargetURL );
1005 :
1006 0 : pMenuItemHandler->xMenuItemDispatch->addStatusListener(
1007 0 : static_cast< XStatusListener* >( this ), aTargetURL );
1008 0 : pMenuItemHandler->xMenuItemDispatch->removeStatusListener(
1009 0 : static_cast< XStatusListener* >( this ), aTargetURL );
1010 : }
1011 0 : catch ( const Exception& )
1012 : {
1013 : }
1014 : }
1015 0 : else if ( pMenuItemHandler->xSubMenuManager.is() )
1016 0 : lcl_CheckForChildren(pMenu, pMenuItemHandler->nItemId);
1017 : }
1018 0 : }
1019 0 : }
1020 : }
1021 :
1022 0 : return 1;
1023 : }
1024 :
1025 :
1026 0 : IMPL_LINK( MenuBarManager, Deactivate, Menu *, pMenu )
1027 : {
1028 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::Deactivate" );
1029 0 : if ( pMenu == m_pVCLMenu )
1030 : {
1031 0 : m_bActive = sal_False;
1032 0 : if ( pMenu->IsMenuBar() && m_xDeferedItemContainer.is() )
1033 : {
1034 : // Start timer to handle settings asynchronous
1035 : // Changing the menu inside this handler leads to
1036 : // a crash under X!
1037 0 : m_aAsyncSettingsTimer.SetTimeoutHdl(LINK(this, MenuBarManager, AsyncSettingsHdl));
1038 0 : m_aAsyncSettingsTimer.SetTimeout(10);
1039 0 : m_aAsyncSettingsTimer.Start();
1040 : }
1041 : }
1042 :
1043 0 : return 1;
1044 : }
1045 :
1046 0 : IMPL_LINK( MenuBarManager, AsyncSettingsHdl, Timer*,)
1047 : {
1048 0 : SolarMutexGuard aGuard;
1049 : Reference< XInterface > xSelfHold(
1050 0 : static_cast< ::cppu::OWeakObject* >( this ), UNO_QUERY_THROW );
1051 :
1052 0 : m_aAsyncSettingsTimer.Stop();
1053 0 : if ( !m_bActive && m_xDeferedItemContainer.is() )
1054 : {
1055 0 : SetItemContainer( m_xDeferedItemContainer );
1056 0 : m_xDeferedItemContainer.clear();
1057 : }
1058 :
1059 0 : return 0;
1060 : }
1061 :
1062 0 : IMPL_LINK( MenuBarManager, Select, Menu *, pMenu )
1063 : {
1064 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::Select" );
1065 0 : URL aTargetURL;
1066 0 : Sequence<PropertyValue> aArgs;
1067 0 : Reference< XDispatch > xDispatch;
1068 :
1069 : {
1070 0 : ResetableGuard aGuard( m_aLock );
1071 :
1072 0 : sal_uInt16 nCurItemId = pMenu->GetCurItemId();
1073 0 : sal_uInt16 nCurPos = pMenu->GetItemPos( nCurItemId );
1074 0 : if ( pMenu == m_pVCLMenu &&
1075 0 : pMenu->GetItemType( nCurPos ) != MENUITEM_SEPARATOR )
1076 : {
1077 0 : if ( nCurItemId >= START_ITEMID_WINDOWLIST &&
1078 : nCurItemId <= END_ITEMID_WINDOWLIST )
1079 : {
1080 : // window list menu item selected
1081 :
1082 0 : Reference< XFramesSupplier > xDesktop( getServiceFactory()->createInstance( SERVICENAME_DESKTOP ), UNO_QUERY );
1083 :
1084 0 : if ( xDesktop.is() )
1085 : {
1086 0 : sal_uInt16 nTaskId = START_ITEMID_WINDOWLIST;
1087 0 : Reference< XIndexAccess > xList( xDesktop->getFrames(), UNO_QUERY );
1088 0 : sal_Int32 nCount = xList->getCount();
1089 0 : for ( sal_Int32 i=0; i<nCount; ++i )
1090 : {
1091 0 : Reference< XFrame > xFrame;
1092 0 : xList->getByIndex(i) >>= xFrame;
1093 0 : if ( xFrame.is() && nTaskId == nCurItemId )
1094 : {
1095 0 : Window* pWin = VCLUnoHelper::GetWindow( xFrame->getContainerWindow() );
1096 0 : pWin->GrabFocus();
1097 0 : pWin->ToTop( TOTOP_RESTOREWHENMIN );
1098 : break;
1099 : }
1100 :
1101 0 : nTaskId++;
1102 0 : }
1103 0 : }
1104 : }
1105 : else
1106 : {
1107 0 : MenuItemHandler* pMenuItemHandler = GetMenuItemHandler( nCurItemId );
1108 0 : if ( pMenuItemHandler && pMenuItemHandler->xMenuItemDispatch.is() )
1109 : {
1110 0 : aTargetURL.Complete = pMenuItemHandler->aMenuItemURL;
1111 0 : m_xURLTransformer->parseStrict( aTargetURL );
1112 :
1113 0 : if ( m_bIsBookmarkMenu )
1114 : {
1115 : // bookmark menu item selected
1116 0 : aArgs.realloc( 1 );
1117 0 : aArgs[0].Name = ::rtl::OUString( "Referer" );
1118 0 : aArgs[0].Value <<= ::rtl::OUString( SFX_REFERER_USER );
1119 : }
1120 :
1121 0 : xDispatch = pMenuItemHandler->xMenuItemDispatch;
1122 : }
1123 : }
1124 0 : }
1125 : }
1126 :
1127 0 : if ( xDispatch.is() )
1128 : {
1129 0 : const sal_uInt32 nRef = Application::ReleaseSolarMutex();
1130 0 : xDispatch->dispatch( aTargetURL, aArgs );
1131 0 : Application::AcquireSolarMutex( nRef );
1132 : }
1133 :
1134 0 : return 1;
1135 : }
1136 :
1137 :
1138 0 : IMPL_LINK_NOARG(MenuBarManager, Highlight)
1139 : {
1140 0 : return 0;
1141 : }
1142 :
1143 0 : sal_Bool MenuBarManager::MustBeHidden( PopupMenu* pPopupMenu, const Reference< XURLTransformer >& rTransformer )
1144 : {
1145 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::MustBeHidden" );
1146 0 : if ( pPopupMenu )
1147 : {
1148 0 : URL aTargetURL;
1149 0 : SvtCommandOptions aCmdOptions;
1150 :
1151 0 : sal_uInt16 nCount = pPopupMenu->GetItemCount();
1152 0 : sal_uInt16 nHideCount( 0 );
1153 :
1154 0 : for ( sal_uInt16 i = 0; i < nCount; i++ )
1155 : {
1156 0 : sal_uInt16 nId = pPopupMenu->GetItemId( i );
1157 0 : if ( nId > 0 )
1158 : {
1159 0 : PopupMenu* pSubPopupMenu = pPopupMenu->GetPopupMenu( nId );
1160 0 : if ( pSubPopupMenu )
1161 : {
1162 0 : if ( MustBeHidden( pSubPopupMenu, rTransformer ))
1163 : {
1164 0 : pPopupMenu->HideItem( nId );
1165 0 : ++nHideCount;
1166 : }
1167 : }
1168 : else
1169 : {
1170 0 : aTargetURL.Complete = pPopupMenu->GetItemCommand( nId );
1171 0 : rTransformer->parseStrict( aTargetURL );
1172 :
1173 0 : if ( aCmdOptions.Lookup( SvtCommandOptions::CMDOPTION_DISABLED, aTargetURL.Path ))
1174 0 : ++nHideCount;
1175 : }
1176 : }
1177 : else
1178 0 : ++nHideCount;
1179 : }
1180 :
1181 0 : return ( nCount == nHideCount );
1182 : }
1183 :
1184 0 : return sal_True;
1185 : }
1186 18 : String MenuBarManager::RetrieveLabelFromCommand( const String& aCmdURL )
1187 : {
1188 18 : return framework::RetrieveLabelFromCommand(aCmdURL,mxServiceFactory,m_xUICommandLabels,m_xFrame,m_aModuleIdentifier,m_bModuleIdentified,"Label");
1189 : }
1190 :
1191 :
1192 :
1193 0 : sal_Bool MenuBarManager::CreatePopupMenuController( MenuItemHandler* pMenuItemHandler )
1194 : {
1195 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::CreatePopupMenuController" );
1196 0 : rtl::OUString aItemCommand( pMenuItemHandler->aMenuItemURL );
1197 :
1198 : // Try instanciate a popup menu controller. It is stored in the menu item handler.
1199 0 : Reference< XMultiComponentFactory > xPopupMenuControllerFactory( m_xPopupMenuControllerRegistration, UNO_QUERY );
1200 0 : if ( xPopupMenuControllerFactory.is() )
1201 : {
1202 0 : Sequence< Any > aSeq( 2 );
1203 0 : PropertyValue aPropValue;
1204 :
1205 0 : aPropValue.Name = rtl::OUString( "ModuleName" );
1206 0 : aPropValue.Value <<= m_aModuleIdentifier;
1207 0 : aSeq[0] <<= aPropValue;
1208 0 : aPropValue.Name = rtl::OUString( "Frame" );
1209 0 : aPropValue.Value <<= m_xFrame;
1210 0 : aSeq[1] <<= aPropValue;
1211 :
1212 : Reference< XComponentContext > xComponentContext(
1213 0 : comphelper::getComponentContext( getServiceFactory() ) );
1214 :
1215 : Reference< XPopupMenuController > xPopupMenuController(
1216 0 : xPopupMenuControllerFactory->createInstanceWithArgumentsAndContext(
1217 : aItemCommand,
1218 : aSeq,
1219 0 : xComponentContext ),
1220 0 : UNO_QUERY );
1221 :
1222 0 : if ( xPopupMenuController.is() )
1223 : {
1224 : // Provide our awt popup menu to the popup menu controller
1225 0 : pMenuItemHandler->xPopupMenuController = xPopupMenuController;
1226 0 : xPopupMenuController->setPopupMenu( pMenuItemHandler->xPopupMenu );
1227 0 : return sal_True;
1228 0 : }
1229 : }
1230 :
1231 0 : return sal_False;
1232 : }
1233 :
1234 582 : void MenuBarManager::FillMenuManager( Menu* pMenu, const Reference< XFrame >& rFrame, const Reference< XDispatchProvider >& rDispatchProvider, const rtl::OUString& rModuleIdentifier, sal_Bool bDelete, sal_Bool bDeleteChildren )
1235 : {
1236 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::FillMenuManager" );
1237 582 : m_xFrame = rFrame;
1238 582 : m_bActive = sal_False;
1239 582 : m_bDeleteMenu = bDelete;
1240 582 : m_bDeleteChildren = bDeleteChildren;
1241 582 : m_pVCLMenu = pMenu;
1242 582 : m_bInitialized = sal_False;
1243 582 : m_bIsBookmarkMenu = sal_False;
1244 582 : m_xDispatchProvider = rDispatchProvider;
1245 :
1246 582 : const StyleSettings& rSettings = Application::GetSettings().GetStyleSettings();
1247 582 : m_bShowMenuImages = rSettings.GetUseImagesInMenus();
1248 582 : m_bRetrieveImages = sal_False;
1249 :
1250 582 : sal_Int32 nAddonsURLPrefixLength = ADDONSPOPUPMENU_URL_PREFIX.getLength();
1251 :
1252 : // Add root as ui configuration listener
1253 582 : RetrieveImageManagers();
1254 :
1255 582 : if ( pMenu->IsMenuBar() && rFrame.is() )
1256 : {
1257 : // First merge all addon popup menus into our structure
1258 508 : sal_uInt16 nPos = 0;
1259 522 : for ( nPos = 0; nPos < pMenu->GetItemCount(); nPos++ )
1260 : {
1261 16 : sal_uInt16 nItemId = pMenu->GetItemId( nPos );
1262 16 : ::rtl::OUString aCommand = pMenu->GetItemCommand( nItemId );
1263 16 : if ( nItemId == SID_MDIWINDOWLIST || aCommand == aSpecialWindowCommand)
1264 : {
1265 : // Retrieve addon popup menus and add them to our menu bar
1266 2 : Reference< com::sun::star::frame::XModel > xModel;
1267 2 : Reference< com::sun::star::frame::XController > xController( rFrame->getController(), UNO_QUERY );
1268 2 : if ( xController.is() )
1269 2 : xModel = Reference< com::sun::star::frame::XModel >( xController->getModel(), UNO_QUERY );
1270 2 : framework::AddonMenuManager::MergeAddonPopupMenus( rFrame, xModel, nPos, (MenuBar *)pMenu );
1271 2 : break;
1272 : }
1273 16 : }
1274 :
1275 : // Merge the Add-Ons help menu items into the Office help menu
1276 508 : framework::AddonMenuManager::MergeAddonHelpMenu( rFrame, (MenuBar *)pMenu );
1277 : }
1278 :
1279 582 : String aEmpty;
1280 582 : sal_Bool bAccessibilityEnabled( Application::GetSettings().GetMiscSettings().GetEnableATToolSupport() );
1281 582 : sal_uInt16 nItemCount = pMenu->GetItemCount();
1282 582 : ::rtl::OUString aItemCommand;
1283 582 : m_aMenuItemHandlerVector.reserve(nItemCount);
1284 1316 : for ( sal_uInt16 i = 0; i < nItemCount; i++ )
1285 : {
1286 734 : sal_uInt16 nItemId = FillItemCommand(aItemCommand,pMenu, i );
1287 :
1288 : // Set module identifier when provided from outside
1289 734 : if ( !rModuleIdentifier.isEmpty() )
1290 : {
1291 734 : m_aModuleIdentifier = rModuleIdentifier;
1292 734 : m_bModuleIdentified = sal_True;
1293 : }
1294 :
1295 1504 : if (( pMenu->IsMenuBar() || bAccessibilityEnabled ) &&
1296 770 : ( pMenu->GetItemText( nItemId ).Len() == 0 ))
1297 : {
1298 18 : if ( !aItemCommand.isEmpty() )
1299 18 : pMenu->SetItemText( nItemId, RetrieveLabelFromCommand( aItemCommand ));
1300 : }
1301 :
1302 734 : Reference< XDispatch > xDispatch;
1303 734 : Reference< XStatusListener > xStatusListener;
1304 734 : PopupMenu* pPopup = pMenu->GetPopupMenu( nItemId );
1305 734 : bool bItemShowMenuImages = m_bShowMenuImages;
1306 : // overwrite the show icons on menu option?
1307 734 : if (!bItemShowMenuImages)
1308 : {
1309 0 : MenuItemBits nBits = pMenu->GetItemBits( nItemId );
1310 0 : bItemShowMenuImages = ( ( nBits & MIB_ICON ) == MIB_ICON );
1311 : }
1312 734 : if ( pPopup )
1313 : {
1314 : // Retrieve module identifier from Help Command entry
1315 76 : rtl::OUString aModuleIdentifier( rModuleIdentifier );
1316 76 : if ( pMenu->GetHelpCommand( nItemId ).Len() > 0 )
1317 : {
1318 76 : aModuleIdentifier = pMenu->GetHelpCommand( nItemId );
1319 76 : pMenu->SetHelpCommand( nItemId, aEmpty );
1320 : }
1321 :
1322 232 : if ( m_xPopupMenuControllerRegistration.is() &&
1323 76 : pPopup->GetItemCount() == 0 &&
1324 80 : m_xPopupMenuControllerRegistration->hasController( aItemCommand, rtl::OUString() )
1325 : )
1326 : {
1327 : // Check if we have to create a popup menu for a uno based popup menu controller.
1328 : // We have to set an empty popup menu into our menu structure so the controller also
1329 : // works with inplace OLE. Remove old dummy popup menu!
1330 2 : MenuItemHandler* pItemHandler = new MenuItemHandler( nItemId, xStatusListener, xDispatch );
1331 2 : VCLXPopupMenu* pVCLXPopupMenu = new VCLXPopupMenu;
1332 2 : PopupMenu* pNewPopupMenu = (PopupMenu *)pVCLXPopupMenu->GetMenu();
1333 2 : pMenu->SetPopupMenu( nItemId, pNewPopupMenu );
1334 2 : pItemHandler->xPopupMenu = Reference< com::sun::star::awt::XPopupMenu >( (OWeakObject *)pVCLXPopupMenu, UNO_QUERY );
1335 2 : pItemHandler->aMenuItemURL = aItemCommand;
1336 2 : m_aMenuItemHandlerVector.push_back( pItemHandler );
1337 2 : delete pPopup;
1338 :
1339 2 : if ( bAccessibilityEnabled )
1340 : {
1341 0 : if ( CreatePopupMenuController( pItemHandler ))
1342 0 : pItemHandler->xPopupMenuController->updatePopupMenu();
1343 : }
1344 2 : lcl_CheckForChildren(pMenu, nItemId);
1345 : }
1346 184 : else if (( aItemCommand.getLength() > nAddonsURLPrefixLength ) &&
1347 110 : ( aItemCommand.indexOf( ADDONSPOPUPMENU_URL_PREFIX ) == 0 ))
1348 : {
1349 : // A special addon popup menu, must be created with a different ctor
1350 0 : MenuBarManager* pSubMenuManager = new MenuBarManager( getServiceFactory(), m_xFrame, m_xURLTransformer,(AddonPopupMenu *)pPopup, bDeleteChildren, bDeleteChildren );
1351 0 : AddMenu(pSubMenuManager,aItemCommand,nItemId);
1352 : }
1353 : else
1354 : {
1355 74 : Reference< XDispatchProvider > xPopupMenuDispatchProvider( rDispatchProvider );
1356 :
1357 : // Retrieve possible attributes struct
1358 74 : MenuConfiguration::Attributes* pAttributes = (MenuConfiguration::Attributes *)(pMenu->GetUserValue( nItemId ));
1359 74 : if ( pAttributes )
1360 0 : xPopupMenuDispatchProvider = pAttributes->xDispatchProvider;
1361 :
1362 : // Check if this is the help menu. Add menu item if needed
1363 74 : if ( nItemId == SID_HELPMENU || aItemCommand == aSlotHelpMenu || aItemCommand == aCmdHelpMenu )
1364 : {
1365 : // Check if this is the help menu. Add menu item if needed
1366 2 : CheckAndAddMenuExtension( pPopup );
1367 : }
1368 74 : else if (( nItemId == SID_ADDONLIST || aItemCommand == aSlotSpecialToolsMenu || aItemCommand == aCmdToolsMenu ) &&
1369 2 : AddonMenuManager::HasAddonMenuElements() )
1370 : {
1371 : // Create addon popup menu if there exist elements and this is the tools popup menu
1372 0 : AddonMenu* pSubMenu = AddonMenuManager::CreateAddonMenu( rFrame );
1373 0 : if ( pSubMenu && ( pSubMenu->GetItemCount() > 0 ))
1374 : {
1375 0 : sal_uInt16 nCount = 0;
1376 0 : if ( pPopup->GetItemType( nCount-1 ) != MENUITEM_SEPARATOR )
1377 0 : pPopup->InsertSeparator();
1378 :
1379 : // Use resource to load popup menu title
1380 0 : String aAddonsStrRes = String( FwkResId( STR_MENU_ADDONS ));
1381 0 : pPopup->InsertItem( ITEMID_ADDONLIST, aAddonsStrRes );
1382 0 : pPopup->SetPopupMenu( ITEMID_ADDONLIST, pSubMenu );
1383 :
1384 : // Set item command for popup menu to enable it for GetImageFromURL
1385 0 : const ::rtl::OUString aSlotString( "slot:" );
1386 0 : ::rtl::OUString aNewItemCommand( aSlotString );
1387 0 : aNewItemCommand += ::rtl::OUString::valueOf( (sal_Int32)ITEMID_ADDONLIST );
1388 0 : pPopup->SetItemCommand( ITEMID_ADDONLIST, aNewItemCommand );
1389 : }
1390 : else
1391 0 : delete pSubMenu;
1392 : }
1393 :
1394 74 : if ( nItemId == ITEMID_ADDONLIST )
1395 : {
1396 0 : AddonMenu* pSubMenu = dynamic_cast< AddonMenu* >( pPopup );
1397 0 : if ( pSubMenu )
1398 : {
1399 0 : MenuBarManager* pSubMenuManager = new MenuBarManager( getServiceFactory(), m_xFrame, m_xURLTransformer,pSubMenu, sal_True, sal_False );
1400 0 : AddMenu(pSubMenuManager,aItemCommand,nItemId);
1401 0 : pSubMenuManager->m_aMenuItemCommand = ::rtl::OUString();
1402 :
1403 : // Set image for the addon popup menu item
1404 0 : if ( bItemShowMenuImages && !pPopup->GetItemImage( ITEMID_ADDONLIST ))
1405 : {
1406 0 : Reference< XFrame > xTemp( rFrame );
1407 0 : Image aImage = GetImageFromURL( xTemp, aItemCommand, false );
1408 0 : if ( !!aImage )
1409 0 : pPopup->SetItemImage( ITEMID_ADDONLIST, aImage );
1410 : }
1411 : }
1412 : }
1413 : else
1414 : {
1415 74 : MenuBarManager* pSubMenuMgr = new MenuBarManager( getServiceFactory(), rFrame, m_xURLTransformer,rDispatchProvider, aModuleIdentifier, pPopup, bDeleteChildren, bDeleteChildren );
1416 74 : AddMenu(pSubMenuMgr,aItemCommand,nItemId);
1417 74 : }
1418 76 : }
1419 : }
1420 658 : else if ( pMenu->GetItemType( i ) != MENUITEM_SEPARATOR )
1421 : {
1422 550 : if ( bItemShowMenuImages )
1423 : {
1424 550 : if ( AddonMenuManager::IsAddonMenuId( nItemId ))
1425 : {
1426 : // Add-Ons uses images from different places
1427 0 : Image aImage;
1428 0 : rtl::OUString aImageId;
1429 :
1430 : MenuConfiguration::Attributes* pMenuAttributes =
1431 0 : (MenuConfiguration::Attributes*)pMenu->GetUserValue( nItemId );
1432 :
1433 0 : if ( pMenuAttributes && !pMenuAttributes->aImageId.isEmpty() )
1434 : {
1435 : // Retrieve image id from menu attributes
1436 0 : aImage = GetImageFromURL( m_xFrame, aImageId, false );
1437 : }
1438 :
1439 0 : if ( !aImage )
1440 : {
1441 0 : aImage = GetImageFromURL( m_xFrame, aItemCommand, false );
1442 0 : if ( !aImage )
1443 0 : aImage = AddonsOptions().GetImageFromURL( aItemCommand, false );
1444 : }
1445 :
1446 0 : if ( !!aImage )
1447 0 : pMenu->SetItemImage( nItemId, aImage );
1448 : else
1449 0 : m_bRetrieveImages = sal_True;
1450 : }
1451 550 : m_bRetrieveImages = sal_True;
1452 : }
1453 :
1454 550 : MenuItemHandler* pItemHandler = new MenuItemHandler( nItemId, xStatusListener, xDispatch );
1455 550 : pItemHandler->aMenuItemURL = aItemCommand;
1456 :
1457 2200 : if ( m_xPopupMenuControllerRegistration.is() &&
1458 1650 : m_xPopupMenuControllerRegistration->hasController( aItemCommand, rtl::OUString() ))
1459 : {
1460 : // Check if we have to create a popup menu for a uno based popup menu controller.
1461 : // We have to set an empty popup menu into our menu structure so the controller also
1462 : // works with inplace OLE.
1463 20 : VCLXPopupMenu* pVCLXPopupMenu = new VCLXPopupMenu;
1464 20 : PopupMenu* pPopupMenu = (PopupMenu *)pVCLXPopupMenu->GetMenu();
1465 20 : pMenu->SetPopupMenu( pItemHandler->nItemId, pPopupMenu );
1466 20 : pItemHandler->xPopupMenu = Reference< com::sun::star::awt::XPopupMenu >( (OWeakObject *)pVCLXPopupMenu, UNO_QUERY );
1467 :
1468 20 : if ( bAccessibilityEnabled && CreatePopupMenuController( pItemHandler ) )
1469 : {
1470 0 : pItemHandler->xPopupMenuController->updatePopupMenu();
1471 : }
1472 :
1473 20 : lcl_CheckForChildren(pMenu, pItemHandler->nItemId);
1474 : }
1475 :
1476 550 : m_aMenuItemHandlerVector.push_back( pItemHandler );
1477 : }
1478 734 : }
1479 :
1480 582 : if ( bAccessibilityEnabled )
1481 : {
1482 0 : RetrieveShortcuts( m_aMenuItemHandlerVector );
1483 0 : std::vector< MenuItemHandler* >::iterator p;
1484 0 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
1485 : {
1486 0 : MenuItemHandler* pMenuItemHandler = *p;
1487 :
1488 : // Set key code, workaround for hard-coded shortcut F1 mapped to .uno:HelpIndex
1489 : // Only non-popup menu items can have a short-cut
1490 0 : if ( pMenuItemHandler->aMenuItemURL == aCmdHelpIndex )
1491 : {
1492 0 : KeyCode aKeyCode( KEY_F1 );
1493 0 : pMenu->SetAccelKey( pMenuItemHandler->nItemId, aKeyCode );
1494 : }
1495 0 : else if ( pMenu->GetPopupMenu( pMenuItemHandler->nItemId ) == 0 )
1496 0 : pMenu->SetAccelKey( pMenuItemHandler->nItemId, pMenuItemHandler->aKeyCode );
1497 : }
1498 : }
1499 :
1500 582 : SetHdl();
1501 582 : }
1502 :
1503 0 : void MenuBarManager::impl_RetrieveShortcutsFromConfiguration(
1504 : const Reference< XAcceleratorConfiguration >& rAccelCfg,
1505 : const Sequence< rtl::OUString >& rCommands,
1506 : std::vector< MenuItemHandler* >& aMenuShortCuts )
1507 : {
1508 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::impl_RetrieveShortcutsFromConfiguration" );
1509 0 : if ( rAccelCfg.is() )
1510 : {
1511 : try
1512 : {
1513 0 : com::sun::star::awt::KeyEvent aKeyEvent;
1514 0 : Sequence< Any > aSeqKeyCode = rAccelCfg->getPreferredKeyEventsForCommandList( rCommands );
1515 0 : for ( sal_Int32 i = 0; i < aSeqKeyCode.getLength(); i++ )
1516 : {
1517 0 : if ( aSeqKeyCode[i] >>= aKeyEvent )
1518 0 : aMenuShortCuts[i]->aKeyCode = svt::AcceleratorExecute::st_AWTKey2VCLKey( aKeyEvent );
1519 0 : }
1520 : }
1521 0 : catch ( const IllegalArgumentException& )
1522 : {
1523 : }
1524 : }
1525 0 : }
1526 :
1527 0 : void MenuBarManager::RetrieveShortcuts( std::vector< MenuItemHandler* >& aMenuShortCuts )
1528 : {
1529 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::RetrieveShortcuts" );
1530 0 : if ( !m_bModuleIdentified )
1531 : {
1532 0 : m_bModuleIdentified = sal_True;
1533 0 : Reference< XModuleManager2 > xModuleManager = ModuleManager::create( comphelper::getComponentContext( getServiceFactory() ) );
1534 :
1535 : try
1536 : {
1537 0 : m_aModuleIdentifier = xModuleManager->identify( m_xFrame );
1538 : }
1539 0 : catch( const Exception& )
1540 : {
1541 0 : }
1542 : }
1543 :
1544 0 : if ( m_bModuleIdentified )
1545 : {
1546 0 : Reference< XAcceleratorConfiguration > xDocAccelCfg( m_xDocAcceleratorManager );
1547 0 : Reference< XAcceleratorConfiguration > xModuleAccelCfg( m_xModuleAcceleratorManager );
1548 0 : Reference< XAcceleratorConfiguration > xGlobalAccelCfg( m_xGlobalAcceleratorManager );
1549 :
1550 0 : if ( !m_bAcceleratorCfg )
1551 : {
1552 : // Retrieve references on demand
1553 0 : m_bAcceleratorCfg = sal_True;
1554 0 : if ( !xDocAccelCfg.is() )
1555 : {
1556 0 : Reference< XController > xController = m_xFrame->getController();
1557 0 : Reference< XModel > xModel;
1558 0 : if ( xController.is() )
1559 : {
1560 0 : xModel = xController->getModel();
1561 0 : if ( xModel.is() )
1562 : {
1563 0 : Reference< XUIConfigurationManagerSupplier > xSupplier( xModel, UNO_QUERY );
1564 0 : if ( xSupplier.is() )
1565 : {
1566 0 : Reference< XUIConfigurationManager > xDocUICfgMgr( xSupplier->getUIConfigurationManager(), UNO_QUERY );
1567 0 : if ( xDocUICfgMgr.is() )
1568 : {
1569 0 : xDocAccelCfg = Reference< XAcceleratorConfiguration >( xDocUICfgMgr->getShortCutManager(), UNO_QUERY );
1570 0 : m_xDocAcceleratorManager = xDocAccelCfg;
1571 0 : }
1572 0 : }
1573 : }
1574 0 : }
1575 : }
1576 :
1577 0 : if ( !xModuleAccelCfg.is() )
1578 : {
1579 : Reference< XModuleUIConfigurationManagerSupplier > xModuleCfgMgrSupplier =
1580 0 : ModuleUIConfigurationManagerSupplier::create( comphelper::getComponentContext(getServiceFactory()) );
1581 : try
1582 : {
1583 0 : Reference< XUIConfigurationManager > xUICfgMgr = xModuleCfgMgrSupplier->getUIConfigurationManager( m_aModuleIdentifier );
1584 0 : if ( xUICfgMgr.is() )
1585 : {
1586 0 : xModuleAccelCfg = Reference< XAcceleratorConfiguration >( xUICfgMgr->getShortCutManager(), UNO_QUERY );
1587 0 : m_xModuleAcceleratorManager = xModuleAccelCfg;
1588 0 : }
1589 : }
1590 0 : catch ( const RuntimeException& )
1591 : {
1592 0 : throw;
1593 : }
1594 0 : catch ( const Exception& )
1595 : {
1596 0 : }
1597 : }
1598 :
1599 0 : if ( !xGlobalAccelCfg.is() )
1600 : {
1601 0 : xGlobalAccelCfg = GlobalAcceleratorConfiguration::create( comphelper::getComponentContext(getServiceFactory()) );
1602 0 : m_xGlobalAcceleratorManager = xGlobalAccelCfg;
1603 : }
1604 : }
1605 :
1606 0 : KeyCode aEmptyKeyCode;
1607 0 : Sequence< rtl::OUString > aSeq( aMenuShortCuts.size() );
1608 0 : const sal_uInt32 nCount = aMenuShortCuts.size();
1609 0 : for ( sal_uInt32 i = 0; i < nCount; ++i )
1610 : {
1611 0 : aSeq[i] = aMenuShortCuts[i]->aMenuItemURL;
1612 0 : aMenuShortCuts[i]->aKeyCode = aEmptyKeyCode;
1613 : }
1614 :
1615 0 : if ( m_xGlobalAcceleratorManager.is() )
1616 0 : impl_RetrieveShortcutsFromConfiguration( xGlobalAccelCfg, aSeq, aMenuShortCuts );
1617 0 : if ( m_xModuleAcceleratorManager.is() )
1618 0 : impl_RetrieveShortcutsFromConfiguration( xModuleAccelCfg, aSeq, aMenuShortCuts );
1619 0 : if ( m_xDocAcceleratorManager.is() )
1620 0 : impl_RetrieveShortcutsFromConfiguration( xDocAccelCfg, aSeq, aMenuShortCuts );
1621 : }
1622 0 : }
1623 :
1624 582 : void MenuBarManager::RetrieveImageManagers()
1625 : {
1626 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::RetrieveImageManagers" );
1627 582 : if ( !m_xDocImageManager.is() )
1628 : {
1629 582 : Reference< XController > xController = m_xFrame->getController();
1630 582 : Reference< XModel > xModel;
1631 582 : if ( xController.is() )
1632 : {
1633 582 : xModel = xController->getModel();
1634 582 : if ( xModel.is() )
1635 : {
1636 582 : Reference< XUIConfigurationManagerSupplier > xSupplier( xModel, UNO_QUERY );
1637 582 : if ( xSupplier.is() )
1638 : {
1639 582 : Reference< XUIConfigurationManager > xDocUICfgMgr( xSupplier->getUIConfigurationManager(), UNO_QUERY );
1640 582 : m_xDocImageManager = Reference< XImageManager >( xDocUICfgMgr->getImageManager(), UNO_QUERY );
1641 582 : m_xDocImageManager->addConfigurationListener(
1642 : Reference< XUIConfigurationListener >(
1643 582 : static_cast< OWeakObject* >( this ), UNO_QUERY ));
1644 582 : }
1645 : }
1646 582 : }
1647 : }
1648 :
1649 582 : Reference< XModuleManager2 > xModuleManager;
1650 582 : if ( m_aModuleIdentifier.isEmpty() )
1651 582 : xModuleManager.set( ModuleManager::create( comphelper::getComponentContext( getServiceFactory() ) ) );
1652 :
1653 : try
1654 : {
1655 582 : if ( xModuleManager.is() )
1656 582 : m_aModuleIdentifier = xModuleManager->identify( Reference< XInterface >( m_xFrame, UNO_QUERY ) );
1657 : }
1658 0 : catch( const Exception& )
1659 : {
1660 : }
1661 :
1662 582 : if ( !m_xModuleImageManager.is() )
1663 : {
1664 : Reference< XModuleUIConfigurationManagerSupplier > xModuleCfgMgrSupplier =
1665 582 : ModuleUIConfigurationManagerSupplier::create( comphelper::getComponentContext(getServiceFactory()) );
1666 582 : Reference< XUIConfigurationManager > xUICfgMgr = xModuleCfgMgrSupplier->getUIConfigurationManager( m_aModuleIdentifier );
1667 582 : m_xModuleImageManager.set( xUICfgMgr->getImageManager(), UNO_QUERY );
1668 582 : m_xModuleImageManager->addConfigurationListener( Reference< XUIConfigurationListener >(
1669 582 : static_cast< OWeakObject* >( this ), UNO_QUERY ));
1670 582 : }
1671 582 : }
1672 :
1673 2 : void MenuBarManager::FillMenuWithConfiguration(
1674 : sal_uInt16& nId,
1675 : Menu* pMenu,
1676 : const ::rtl::OUString& rModuleIdentifier,
1677 : const Reference< XIndexAccess >& rItemContainer,
1678 : const Reference< XURLTransformer >& rTransformer )
1679 : {
1680 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::FillMenuWithConfiguration" );
1681 2 : Reference< XDispatchProvider > xEmptyDispatchProvider;
1682 2 : MenuBarManager::FillMenu( nId, pMenu, rModuleIdentifier, rItemContainer, xEmptyDispatchProvider );
1683 :
1684 : // Merge add-on menu entries into the menu bar
1685 : MenuBarManager::MergeAddonMenus( static_cast< Menu* >( pMenu ),
1686 4 : AddonsOptions().GetMergeMenuInstructions(),
1687 2 : rModuleIdentifier );
1688 :
1689 2 : sal_Bool bHasDisabledEntries = SvtCommandOptions().HasEntries( SvtCommandOptions::CMDOPTION_DISABLED );
1690 2 : if ( bHasDisabledEntries )
1691 : {
1692 0 : sal_uInt16 nCount = pMenu->GetItemCount();
1693 0 : for ( sal_uInt16 i = 0; i < nCount; i++ )
1694 : {
1695 0 : sal_uInt16 nID = pMenu->GetItemId( i );
1696 0 : if ( nID > 0 )
1697 : {
1698 0 : PopupMenu* pPopupMenu = pMenu->GetPopupMenu( nID );
1699 0 : if ( pPopupMenu )
1700 : {
1701 0 : if ( MustBeHidden( pPopupMenu, rTransformer ))
1702 0 : pMenu->HideItem( nId );
1703 : }
1704 : }
1705 : }
1706 2 : }
1707 2 : }
1708 :
1709 78 : void MenuBarManager::FillMenu(
1710 : sal_uInt16& nId,
1711 : Menu* pMenu,
1712 : const rtl::OUString& rModuleIdentifier,
1713 : const Reference< XIndexAccess >& rItemContainer,
1714 : const Reference< XDispatchProvider >& rDispatchProvider )
1715 : {
1716 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::FillMenu" );
1717 : // Fill menu bar with container contents
1718 812 : for ( sal_Int32 n = 0; n < rItemContainer->getCount(); n++ )
1719 : {
1720 734 : Sequence< PropertyValue > aProp;
1721 734 : rtl::OUString aCommandURL;
1722 734 : rtl::OUString aLabel;
1723 734 : rtl::OUString aHelpURL;
1724 734 : rtl::OUString aModuleIdentifier( rModuleIdentifier );
1725 734 : sal_Bool bShow(sal_True);
1726 734 : sal_Bool bEnabled(sal_True);
1727 734 : sal_uInt16 nType = 0;
1728 734 : Reference< XIndexAccess > xIndexContainer;
1729 734 : Reference< XDispatchProvider > xDispatchProvider( rDispatchProvider );
1730 734 : sal_Int16 nStyle = 0;
1731 : try
1732 : {
1733 734 : if ( rItemContainer->getByIndex( n ) >>= aProp )
1734 : {
1735 4598 : for ( int i = 0; i < aProp.getLength(); i++ )
1736 : {
1737 3864 : rtl::OUString aPropName = aProp[i].Name;
1738 3864 : if ( aPropName.equalsAsciiL( ITEM_DESCRIPTOR_COMMANDURL, LEN_DESCRIPTOR_COMMANDURL ))
1739 626 : aProp[i].Value >>= aCommandURL;
1740 3238 : else if ( aPropName.equalsAsciiL( ITEM_DESCRIPTOR_HELPURL, LEN_DESCRIPTOR_HELPURL ))
1741 626 : aProp[i].Value >>= aHelpURL;
1742 2612 : else if ( aPropName.equalsAsciiL( ITEM_DESCRIPTOR_CONTAINER, LEN_DESCRIPTOR_CONTAINER ))
1743 626 : aProp[i].Value >>= xIndexContainer;
1744 1986 : else if ( aPropName.equalsAsciiL( ITEM_DESCRIPTOR_LABEL, LEN_DESCRIPTOR_LABEL ))
1745 626 : aProp[i].Value >>= aLabel;
1746 1360 : else if ( aPropName.equalsAsciiL( ITEM_DESCRIPTOR_TYPE, LEN_DESCRIPTOR_TYPE ))
1747 734 : aProp[i].Value >>= nType;
1748 626 : else if ( aPropName.equalsAsciiL( ITEM_DESCRIPTOR_MODULEIDENTIFIER, LEN_DESCRIPTOR_MODULEIDENTIFIER ))
1749 0 : aProp[i].Value >>= aModuleIdentifier;
1750 626 : else if ( aPropName.equalsAsciiL( ITEM_DESCRIPTOR_DISPATCHPROVIDER, LEN_DESCRIPTOR_DISPATCHPROVIDER ))
1751 0 : aProp[i].Value >>= xDispatchProvider;
1752 626 : else if ( aProp[i].Name.equalsAsciiL( ITEM_DESCRIPTOR_STYLE, LEN_DESCRIPTOR_STYLE ))
1753 626 : aProp[i].Value >>= nStyle;
1754 0 : else if ( aProp[i].Name.equalsAsciiL( ITEM_DESCRIPTOR_ISVISIBLE, LEN_DESCRIPTOR_ISVISIBLE ))
1755 0 : aProp[i].Value >>= bShow;
1756 0 : else if ( aProp[i].Name.equalsAsciiL( ITEM_DESCRIPTOR_ENABLED, LEN_DESCRIPTOR_ENABLED ))
1757 0 : aProp[i].Value >>= bEnabled;
1758 3864 : }
1759 :
1760 734 : if ( nType == ::com::sun::star::ui::ItemType::DEFAULT )
1761 : {
1762 626 : pMenu->InsertItem( nId, aLabel );
1763 626 : pMenu->SetItemCommand( nId, aCommandURL );
1764 :
1765 626 : if ( nStyle )
1766 : {
1767 26 : MenuItemBits nBits = pMenu->GetItemBits( nId );
1768 26 : if ( nStyle & ::com::sun::star::ui::ItemStyle::ICON )
1769 0 : nBits |= MIB_ICON;
1770 26 : if ( nStyle & ::com::sun::star::ui::ItemStyle::TEXT )
1771 0 : nBits |= MIB_TEXT;
1772 26 : if ( nStyle & ::com::sun::star::ui::ItemStyle::RADIO_CHECK )
1773 26 : nBits |= MIB_RADIOCHECK;
1774 26 : pMenu->SetItemBits( nId, nBits );
1775 : }
1776 :
1777 626 : if ( !bShow )
1778 0 : pMenu->HideItem( nId );
1779 :
1780 626 : if ( !bEnabled)
1781 0 : pMenu->EnableItem( nId, sal_False );
1782 :
1783 626 : if ( xIndexContainer.is() )
1784 : {
1785 76 : PopupMenu* pNewPopupMenu = new PopupMenu;
1786 76 : pMenu->SetPopupMenu( nId, pNewPopupMenu );
1787 :
1788 76 : if ( xDispatchProvider.is() )
1789 : {
1790 : // Use attributes struct to transport special dispatch provider
1791 0 : MenuConfiguration::Attributes* pAttributes = new MenuConfiguration::Attributes;
1792 0 : pAttributes->xDispatchProvider = xDispatchProvider;
1793 0 : pMenu->SetUserValue( nId, (sal_uIntPtr)( pAttributes ));
1794 : }
1795 :
1796 : // Use help command to transport module identifier
1797 76 : if ( !aModuleIdentifier.isEmpty() )
1798 76 : pMenu->SetHelpCommand( nId, aModuleIdentifier );
1799 :
1800 76 : ++nId;
1801 76 : FillMenu( nId, pNewPopupMenu, aModuleIdentifier, xIndexContainer, xDispatchProvider );
1802 : }
1803 : else
1804 550 : ++nId;
1805 : }
1806 : else
1807 : {
1808 108 : pMenu->InsertSeparator();
1809 108 : ++nId;
1810 : }
1811 : }
1812 : }
1813 0 : catch ( const IndexOutOfBoundsException& )
1814 : {
1815 : break;
1816 : }
1817 734 : }
1818 78 : }
1819 :
1820 2 : void MenuBarManager::MergeAddonMenus(
1821 : Menu* pMenuBar,
1822 : const MergeMenuInstructionContainer& aMergeInstructionContainer,
1823 : const ::rtl::OUString& rModuleIdentifier )
1824 : {
1825 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::MergeAddonMenus" );
1826 : // set start value for the item ID for the new addon menu items
1827 2 : sal_uInt16 nItemId = ADDONMENU_MERGE_ITEMID_START;
1828 :
1829 2 : const sal_uInt32 nCount = aMergeInstructionContainer.size();
1830 4 : for ( sal_uInt32 i = 0; i < nCount; i++ )
1831 : {
1832 2 : const MergeMenuInstruction& rMergeInstruction = aMergeInstructionContainer[i];
1833 :
1834 2 : if ( MenuBarMerger::IsCorrectContext( rMergeInstruction.aMergeContext, rModuleIdentifier ))
1835 : {
1836 0 : ::std::vector< ::rtl::OUString > aMergePath;
1837 :
1838 : // retrieve the merge path from the merge point string
1839 0 : MenuBarMerger::RetrieveReferencePath( rMergeInstruction.aMergePoint, aMergePath );
1840 :
1841 : // convert the sequence/sequence property value to a more convenient vector<>
1842 0 : AddonMenuContainer aMergeMenuItems;
1843 0 : MenuBarMerger::GetSubMenu( rMergeInstruction.aMergeMenu, aMergeMenuItems );
1844 :
1845 : // try to find the reference point for our merge operation
1846 0 : Menu* pMenu = pMenuBar;
1847 0 : ReferencePathInfo aResult = MenuBarMerger::FindReferencePath( aMergePath, pMenu );
1848 :
1849 0 : if ( aResult.eResult == RP_OK )
1850 : {
1851 : // normal merge operation
1852 : MenuBarMerger::ProcessMergeOperation( aResult.pPopupMenu,
1853 : aResult.nPos,
1854 : nItemId,
1855 : rMergeInstruction.aMergeCommand,
1856 : rMergeInstruction.aMergeCommandParameter,
1857 : rModuleIdentifier,
1858 0 : aMergeMenuItems );
1859 : }
1860 : else
1861 : {
1862 : // fallback
1863 : MenuBarMerger::ProcessFallbackOperation( aResult,
1864 : nItemId,
1865 : rMergeInstruction.aMergeCommand,
1866 : rMergeInstruction.aMergeFallback,
1867 : aMergePath,
1868 : rModuleIdentifier,
1869 0 : aMergeMenuItems );
1870 0 : }
1871 : }
1872 : }
1873 2 : }
1874 :
1875 0 : void MenuBarManager::SetItemContainer( const Reference< XIndexAccess >& rItemContainer )
1876 : {
1877 : RTL_LOGFILE_CONTEXT( aLog, "framework (cd100003) ::MenuBarManager::SetItemContainer" );
1878 :
1879 0 : ResetableGuard aGuard( m_aLock );
1880 :
1881 0 : Reference< XFrame > xFrame = m_xFrame;
1882 :
1883 0 : if ( !m_bModuleIdentified )
1884 : {
1885 0 : m_bModuleIdentified = sal_True;
1886 0 : Reference< XModuleManager2 > xModuleManager = ModuleManager::create( comphelper::getComponentContext(getServiceFactory()) );
1887 :
1888 : try
1889 : {
1890 0 : m_aModuleIdentifier = xModuleManager->identify( xFrame );
1891 : }
1892 0 : catch( const Exception& )
1893 : {
1894 0 : }
1895 : }
1896 :
1897 : // Clear MenuBarManager structures
1898 : {
1899 0 : SolarMutexGuard aSolarMutexGuard;
1900 :
1901 : // Check active state as we cannot change our VCL menu during activation by the user
1902 0 : if ( m_bActive )
1903 : {
1904 0 : m_xDeferedItemContainer = rItemContainer;
1905 0 : return;
1906 : }
1907 :
1908 0 : RemoveListener();
1909 0 : std::vector< MenuItemHandler* >::iterator p;
1910 0 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
1911 : {
1912 0 : MenuItemHandler* pItemHandler = *p;
1913 0 : pItemHandler->xMenuItemDispatch.clear();
1914 0 : pItemHandler->xSubMenuManager.clear();
1915 0 : delete pItemHandler;
1916 : }
1917 0 : m_aMenuItemHandlerVector.clear();
1918 :
1919 : // Remove top-level parts
1920 0 : m_pVCLMenu->Clear();
1921 :
1922 0 : sal_uInt16 nId = 1;
1923 :
1924 : // Fill menu bar with container contents
1925 0 : FillMenuWithConfiguration( nId, (Menu *)m_pVCLMenu, m_aModuleIdentifier, rItemContainer, m_xURLTransformer );
1926 :
1927 : // Refill menu manager again
1928 0 : Reference< XDispatchProvider > xDispatchProvider;
1929 0 : FillMenuManager( m_pVCLMenu, xFrame, xDispatchProvider, m_aModuleIdentifier, sal_False, sal_True );
1930 :
1931 : // add itself as frame action listener
1932 0 : m_xFrame->addFrameActionListener( Reference< XFrameActionListener >( static_cast< OWeakObject* >( this ), UNO_QUERY ));
1933 0 : }
1934 : }
1935 :
1936 0 : void MenuBarManager::GetPopupController( PopupControllerCache& rPopupController )
1937 : {
1938 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::GetPopupController" );
1939 :
1940 0 : SolarMutexGuard aSolarMutexGuard;
1941 :
1942 0 : std::vector< MenuItemHandler* >::iterator p;
1943 0 : for ( p = m_aMenuItemHandlerVector.begin(); p != m_aMenuItemHandlerVector.end(); ++p )
1944 : {
1945 0 : MenuItemHandler* pItemHandler = *p;
1946 0 : if ( pItemHandler->xPopupMenuController.is() )
1947 : {
1948 0 : Reference< XDispatchProvider > xDispatchProvider( pItemHandler->xPopupMenuController, UNO_QUERY );
1949 :
1950 0 : PopupControllerEntry aPopupControllerEntry;
1951 0 : aPopupControllerEntry.m_xDispatchProvider = xDispatchProvider;
1952 :
1953 : // Just use the main part of the URL for popup menu controllers
1954 0 : sal_Int32 nQueryPart( 0 );
1955 0 : sal_Int32 nSchemePart( 0 );
1956 0 : rtl::OUString aMainURL( "vnd.sun.star.popup:" );
1957 0 : rtl::OUString aMenuURL( pItemHandler->aMenuItemURL );
1958 :
1959 0 : nSchemePart = aMenuURL.indexOf( ':' );
1960 0 : if (( nSchemePart > 0 ) &&
1961 0 : ( aMenuURL.getLength() > ( nSchemePart+1 )))
1962 : {
1963 0 : nQueryPart = aMenuURL.indexOf( '?', nSchemePart );
1964 0 : if ( nQueryPart > 0 )
1965 0 : aMainURL += aMenuURL.copy( nSchemePart, nQueryPart-nSchemePart );
1966 0 : else if ( nQueryPart == -1 )
1967 0 : aMainURL += aMenuURL.copy( nSchemePart+1 );
1968 :
1969 : rPopupController.insert( PopupControllerCache::value_type(
1970 0 : aMainURL, aPopupControllerEntry ));
1971 0 : }
1972 : }
1973 0 : if ( pItemHandler->xSubMenuManager.is() )
1974 : {
1975 0 : MenuBarManager* pMenuBarManager = (MenuBarManager*)(pItemHandler->xSubMenuManager.get());
1976 0 : if ( pMenuBarManager )
1977 0 : pMenuBarManager->GetPopupController( rPopupController );
1978 : }
1979 0 : }
1980 0 : }
1981 :
1982 1992 : const Reference< XMultiServiceFactory >& MenuBarManager::getServiceFactory()
1983 : {
1984 1992 : return mxServiceFactory;
1985 : }
1986 :
1987 74 : void MenuBarManager::AddMenu(MenuBarManager* pSubMenuManager,const ::rtl::OUString& _sItemCommand,sal_uInt16 _nItemId)
1988 : {
1989 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::AddMenu" );
1990 74 : Reference< XStatusListener > xSubMenuManager( static_cast< OWeakObject *>( pSubMenuManager ), UNO_QUERY );
1991 74 : m_xFrame->addFrameActionListener( Reference< XFrameActionListener >( xSubMenuManager, UNO_QUERY ));
1992 :
1993 : // store menu item command as we later have to know which menu is active (see Activate handler)
1994 74 : pSubMenuManager->m_aMenuItemCommand = _sItemCommand;
1995 74 : Reference< XDispatch > xDispatch;
1996 : MenuItemHandler* pMenuItemHandler = new MenuItemHandler(
1997 : _nItemId,
1998 : xSubMenuManager,
1999 74 : xDispatch );
2000 74 : pMenuItemHandler->aMenuItemURL = _sItemCommand;
2001 74 : m_aMenuItemHandlerVector.push_back( pMenuItemHandler );
2002 74 : }
2003 :
2004 734 : sal_uInt16 MenuBarManager::FillItemCommand(::rtl::OUString& _rItemCommand, Menu* _pMenu,sal_uInt16 _nIndex) const
2005 : {
2006 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::FillItemCommand" );
2007 734 : sal_uInt16 nItemId = _pMenu->GetItemId( _nIndex );
2008 :
2009 734 : _rItemCommand = _pMenu->GetItemCommand( nItemId );
2010 734 : if ( _rItemCommand.isEmpty() )
2011 : {
2012 42 : const static ::rtl::OUString aSlotString( "slot:" );
2013 42 : _rItemCommand = aSlotString;
2014 42 : _rItemCommand += ::rtl::OUString::valueOf( (sal_Int32)nItemId );
2015 42 : _pMenu->SetItemCommand( nItemId, _rItemCommand );
2016 : }
2017 734 : return nItemId;
2018 : }
2019 0 : void MenuBarManager::Init(const Reference< XFrame >& rFrame,AddonMenu* pAddonMenu,sal_Bool bDelete,sal_Bool bDeleteChildren,bool _bHandlePopUp)
2020 : {
2021 : RTL_LOGFILE_CONTEXT_AUTHOR( aLogger, "framework", "Ocke.Janssen@sun.com", "MenuBarManager::Init" );
2022 0 : m_bActive = sal_False;
2023 0 : m_bDeleteMenu = bDelete;
2024 0 : m_bDeleteChildren = bDeleteChildren;
2025 0 : m_pVCLMenu = pAddonMenu;
2026 0 : m_xFrame = rFrame;
2027 0 : m_bInitialized = sal_False;
2028 0 : m_bIsBookmarkMenu = sal_True;
2029 :
2030 0 : rtl::OUString aModuleIdentifier;
2031 : m_xPopupMenuControllerRegistration = Reference< ::com::sun::star::frame::XUIControllerRegistration >(
2032 0 : getServiceFactory()->createInstance( rtl::OUString( "com.sun.star.frame.PopupMenuControllerFactory" )),
2033 0 : UNO_QUERY );
2034 :
2035 0 : Reference< XStatusListener > xStatusListener;
2036 0 : Reference< XDispatch > xDispatch;
2037 0 : sal_uInt16 nItemCount = pAddonMenu->GetItemCount();
2038 0 : ::rtl::OUString aItemCommand;
2039 0 : m_aMenuItemHandlerVector.reserve(nItemCount);
2040 0 : for ( sal_uInt16 i = 0; i < nItemCount; i++ )
2041 : {
2042 0 : sal_uInt16 nItemId = FillItemCommand(aItemCommand,pAddonMenu, i );
2043 :
2044 0 : PopupMenu* pPopupMenu = pAddonMenu->GetPopupMenu( nItemId );
2045 0 : if ( pPopupMenu )
2046 : {
2047 0 : Reference< XDispatchProvider > xDispatchProvider;
2048 0 : MenuBarManager* pSubMenuManager = new MenuBarManager( getServiceFactory(), rFrame, m_xURLTransformer,xDispatchProvider, aModuleIdentifier, pPopupMenu, _bHandlePopUp ? sal_False : bDeleteChildren, _bHandlePopUp ? sal_False : bDeleteChildren );
2049 :
2050 0 : Reference< XStatusListener > xSubMenuManager( static_cast< OWeakObject *>( pSubMenuManager ), UNO_QUERY );
2051 :
2052 : // store menu item command as we later have to know which menu is active (see Acivate handler)
2053 0 : pSubMenuManager->m_aMenuItemCommand = aItemCommand;
2054 :
2055 : MenuItemHandler* pMenuItemHandler = new MenuItemHandler(
2056 : nItemId,
2057 : xSubMenuManager,
2058 0 : xDispatch );
2059 0 : m_aMenuItemHandlerVector.push_back( pMenuItemHandler );
2060 : }
2061 : else
2062 : {
2063 0 : if ( pAddonMenu->GetItemType( i ) != MENUITEM_SEPARATOR )
2064 : {
2065 0 : MenuConfiguration::Attributes* pAddonAttributes = (MenuConfiguration::Attributes *)(pAddonMenu->GetUserValue( nItemId ));
2066 0 : MenuItemHandler* pMenuItemHandler = new MenuItemHandler( nItemId, xStatusListener, xDispatch );
2067 :
2068 0 : if ( pAddonAttributes )
2069 : {
2070 : // read additional attributes from attributes struct and AddonMenu implementation will delete all attributes itself!!
2071 0 : pMenuItemHandler->aTargetFrame = pAddonAttributes->aTargetFrame;
2072 : }
2073 :
2074 0 : pMenuItemHandler->aMenuItemURL = aItemCommand;
2075 0 : if ( _bHandlePopUp )
2076 : {
2077 : // Check if we have to create a popup menu for a uno based popup menu controller.
2078 : // We have to set an empty popup menu into our menu structure so the controller also
2079 : // works with inplace OLE.
2080 0 : if ( m_xPopupMenuControllerRegistration.is() &&
2081 0 : m_xPopupMenuControllerRegistration->hasController( aItemCommand, rtl::OUString() ))
2082 : {
2083 0 : VCLXPopupMenu* pVCLXPopupMenu = new VCLXPopupMenu;
2084 0 : PopupMenu* pCtlPopupMenu = (PopupMenu *)pVCLXPopupMenu->GetMenu();
2085 0 : pAddonMenu->SetPopupMenu( pMenuItemHandler->nItemId, pCtlPopupMenu );
2086 0 : pMenuItemHandler->xPopupMenu = Reference< com::sun::star::awt::XPopupMenu >( (OWeakObject *)pVCLXPopupMenu, UNO_QUERY );
2087 :
2088 : }
2089 : }
2090 0 : m_aMenuItemHandlerVector.push_back( pMenuItemHandler );
2091 : }
2092 : }
2093 : }
2094 :
2095 0 : SetHdl();
2096 0 : }
2097 :
2098 582 : void MenuBarManager::SetHdl()
2099 : {
2100 582 : m_pVCLMenu->SetHighlightHdl( LINK( this, MenuBarManager, Highlight ));
2101 582 : m_pVCLMenu->SetActivateHdl( LINK( this, MenuBarManager, Activate ));
2102 582 : m_pVCLMenu->SetDeactivateHdl( LINK( this, MenuBarManager, Deactivate ));
2103 582 : m_pVCLMenu->SetSelectHdl( LINK( this, MenuBarManager, Select ));
2104 :
2105 582 : if ( !m_xURLTransformer.is() && mxServiceFactory.is() )
2106 : m_xURLTransformer.set(
2107 : URLTransformer::create(
2108 0 : ::comphelper::getComponentContext(mxServiceFactory)) );
2109 582 : }
2110 :
2111 : }
2112 :
2113 : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
|