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