1 /************************************************************************* 2 * 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. 4 * 5 * Copyright 2000, 2010 Oracle and/or its affiliates. 6 * 7 * OpenOffice.org - a multi-platform office productivity suite 8 * 9 * This file is part of OpenOffice.org. 10 * 11 * OpenOffice.org is free software: you can redistribute it and/or modify 12 * it under the terms of the GNU Lesser General Public License version 3 13 * only, as published by the Free Software Foundation. 14 * 15 * OpenOffice.org is distributed in the hope that it will be useful, 16 * but WITHOUT ANY WARRANTY; without even the implied warranty of 17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 18 * GNU Lesser General Public License version 3 for more details 19 * (a copy is included in the LICENSE file that accompanied this code). 20 * 21 * You should have received a copy of the GNU Lesser General Public License 22 * version 3 along with OpenOffice.org. If not, see 23 * <http://www.openoffice.org/license.html> 24 * for a copy of the LGPLv3 License. 25 * 26 ************************************************************************/ 27 28 // MARKER(update_precomp.py): autogen include statement, do not remove 29 #include "precompiled_framework.hxx" 30 #include <uiconfiguration/uiconfigurationmanager.hxx> 31 #include <threadhelp/resetableguard.hxx> 32 #include <services.h> 33 #include <uielement/rootitemcontainer.hxx> 34 #include <uielement/constitemcontainer.hxx> 35 #include <uielement/uielementtypenames.hxx> 36 #include <framework/menuconfiguration.hxx> 37 #include <framework/toolboxconfiguration.hxx> 38 39 #ifndef __FRAMEWORK_XML_STATUSBARCONFIGURATION_HXX_ 40 #include <framework/statusbarconfiguration.hxx> 41 #endif 42 43 //_________________________________________________________________________________________________________________ 44 // interface includes 45 //_________________________________________________________________________________________________________________ 46 #include <com/sun/star/ui/UIElementType.hpp> 47 #include <com/sun/star/ui/ConfigurationEvent.hpp> 48 #include <com/sun/star/lang/XInitialization.hpp> 49 #include <com/sun/star/lang/DisposedException.hpp> 50 #include <com/sun/star/beans/XPropertySet.hpp> 51 #include <com/sun/star/embed/ElementModes.hpp> 52 #include <com/sun/star/container/XNameAccess.hpp> 53 #include <com/sun/star/io/XStream.hpp> 54 #include <com/sun/star/embed/XTransactedObject.hpp> 55 56 //_________________________________________________________________________________________________________________ 57 // other includes 58 //_________________________________________________________________________________________________________________ 59 60 #include <vcl/svapp.hxx> 61 #include <rtl/ustrbuf.hxx> 62 63 //_________________________________________________________________________________________________________________ 64 // namespaces 65 //_________________________________________________________________________________________________________________ 66 67 using namespace com::sun::star::uno; 68 using namespace com::sun::star::io; 69 using namespace com::sun::star::embed; 70 using namespace com::sun::star::lang; 71 using namespace com::sun::star::container; 72 using namespace com::sun::star::beans; 73 using namespace ::com::sun::star::ui; 74 75 namespace framework 76 { 77 78 //***************************************************************************************************************** 79 // XInterface, XTypeProvider, XServiceInfo 80 //***************************************************************************************************************** 81 DEFINE_XINTERFACE_7 ( UIConfigurationManager , 82 OWeakObject , 83 DIRECT_INTERFACE( css::lang::XTypeProvider ), 84 DIRECT_INTERFACE( css::lang::XServiceInfo ), 85 DIRECT_INTERFACE( css::lang::XComponent ), 86 DIRECT_INTERFACE( ::com::sun::star::ui::XUIConfiguration ), 87 DIRECT_INTERFACE( ::com::sun::star::ui::XUIConfigurationManager ), 88 DIRECT_INTERFACE( ::com::sun::star::ui::XUIConfigurationPersistence ), 89 DIRECT_INTERFACE( ::com::sun::star::ui::XUIConfigurationStorage ) 90 ) 91 92 DEFINE_XTYPEPROVIDER_7 ( UIConfigurationManager , 93 css::lang::XTypeProvider , 94 css::lang::XServiceInfo , 95 css::lang::XComponent , 96 ::com::sun::star::ui::XUIConfiguration , 97 ::com::sun::star::ui::XUIConfigurationManager , 98 ::com::sun::star::ui::XUIConfigurationPersistence , 99 ::com::sun::star::ui::XUIConfigurationStorage 100 ) 101 102 DEFINE_XSERVICEINFO_MULTISERVICE ( UIConfigurationManager , 103 ::cppu::OWeakObject , 104 SERVICENAME_UICONFIGURATIONMANAGER , 105 IMPLEMENTATIONNAME_UICONFIGURATIONMANAGER 106 ) 107 108 DEFINE_INIT_SERVICE ( UIConfigurationManager, {} ) 109 110 111 // important: The order and position of the elements must match the constant 112 // definition of "::com::sun::star::ui::UIElementType" 113 static const char* UIELEMENTTYPENAMES[] = 114 { 115 "", // Dummy value for unknown! 116 UIELEMENTTYPE_MENUBAR_NAME, 117 UIELEMENTTYPE_POPUPMENU_NAME, 118 UIELEMENTTYPE_TOOLBAR_NAME, 119 UIELEMENTTYPE_STATUSBAR_NAME, 120 UIELEMENTTYPE_FLOATINGWINDOW_NAME, 121 UIELEMENTTYPE_PROGRESSBAR_NAME, 122 UIELEMENTTYPE_TOOLPANEL_NAME 123 }; 124 125 static const char RESOURCEURL_PREFIX[] = "private:resource/"; 126 static const sal_Int32 RESOURCEURL_PREFIX_SIZE = 17; 127 128 static sal_Int16 RetrieveTypeFromResourceURL( const rtl::OUString& aResourceURL ) 129 { 130 131 if (( aResourceURL.indexOf( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( RESOURCEURL_PREFIX ))) == 0 ) && 132 ( aResourceURL.getLength() > RESOURCEURL_PREFIX_SIZE )) 133 { 134 rtl::OUString aTmpStr = aResourceURL.copy( RESOURCEURL_PREFIX_SIZE ); 135 sal_Int32 nIndex = aTmpStr.indexOf( '/' ); 136 if (( nIndex > 0 ) && ( aTmpStr.getLength() > nIndex )) 137 { 138 rtl::OUString aTypeStr( aTmpStr.copy( 0, nIndex )); 139 for ( int i = 0; i < UIElementType::COUNT; i++ ) 140 { 141 if ( aTypeStr.equalsAscii( UIELEMENTTYPENAMES[i] )) 142 return sal_Int16( i ); 143 } 144 } 145 } 146 147 return UIElementType::UNKNOWN; 148 } 149 150 static rtl::OUString RetrieveNameFromResourceURL( const rtl::OUString& aResourceURL ) 151 { 152 if (( aResourceURL.indexOf( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( RESOURCEURL_PREFIX ))) == 0 ) && 153 ( aResourceURL.getLength() > RESOURCEURL_PREFIX_SIZE )) 154 { 155 sal_Int32 nIndex = aResourceURL.lastIndexOf( '/' ); 156 if (( nIndex > 0 ) && (( nIndex+1 ) < aResourceURL.getLength())) 157 return aResourceURL.copy( nIndex+1 ); 158 } 159 160 return rtl::OUString(); 161 } 162 163 void UIConfigurationManager::impl_fillSequenceWithElementTypeInfo( UIElementInfoHashMap& aUIElementInfoCollection, sal_Int16 nElementType ) 164 { 165 // preload list of element types on demand 166 impl_preloadUIElementTypeList( nElementType ); 167 168 UIElementDataHashMap& rUserElements = m_aUIElements[nElementType].aElementsHashMap; 169 UIElementDataHashMap::const_iterator pUserIter = rUserElements.begin(); 170 171 while ( pUserIter != rUserElements.end() ) 172 { 173 UIElementData* pDataSettings = impl_findUIElementData( pUserIter->second.aResourceURL, nElementType ); 174 if ( pDataSettings && !pDataSettings->bDefault ) 175 { 176 // Retrieve user interface name from XPropertySet interface 177 rtl::OUString aUIName; 178 Reference< XPropertySet > xPropSet( pDataSettings->xSettings, UNO_QUERY ); 179 if ( xPropSet.is() ) 180 { 181 Any a = xPropSet->getPropertyValue( m_aPropUIName ); 182 a >>= aUIName; 183 } 184 185 UIElementInfo aInfo( pUserIter->second.aResourceURL, aUIName ); 186 aUIElementInfoCollection.insert( UIElementInfoHashMap::value_type( pUserIter->second.aResourceURL, aInfo )); 187 } 188 ++pUserIter; 189 } 190 } 191 192 void UIConfigurationManager::impl_preloadUIElementTypeList( sal_Int16 nElementType ) 193 { 194 UIElementType& rElementTypeData = m_aUIElements[nElementType]; 195 196 if ( !rElementTypeData.bLoaded ) 197 { 198 Reference< XStorage > xElementTypeStorage = rElementTypeData.xStorage; 199 if ( xElementTypeStorage.is() ) 200 { 201 rtl::OUStringBuffer aBuf( RESOURCEURL_PREFIX_SIZE ); 202 aBuf.appendAscii( RESOURCEURL_PREFIX ); 203 aBuf.appendAscii( UIELEMENTTYPENAMES[ nElementType ] ); 204 aBuf.appendAscii( "/" ); 205 rtl::OUString aResURLPrefix( aBuf.makeStringAndClear() ); 206 207 UIElementDataHashMap& rHashMap = rElementTypeData.aElementsHashMap; 208 Reference< XNameAccess > xNameAccess( xElementTypeStorage, UNO_QUERY ); 209 Sequence< rtl::OUString > aUIElementNames = xNameAccess->getElementNames(); 210 for ( sal_Int32 n = 0; n < aUIElementNames.getLength(); n++ ) 211 { 212 UIElementData aUIElementData; 213 214 // Resource name must be without ".xml" 215 sal_Int32 nIndex = aUIElementNames[n].lastIndexOf( '.' ); 216 if (( nIndex > 0 ) && ( nIndex < aUIElementNames[n].getLength() )) 217 { 218 rtl::OUString aExtension( aUIElementNames[n].copy( nIndex+1 )); 219 rtl::OUString aUIElementName( aUIElementNames[n].copy( 0, nIndex )); 220 221 if (( aUIElementName.getLength() > 0 ) && 222 ( aExtension.equalsIgnoreAsciiCaseAsciiL( "xml", 3 ))) 223 { 224 aUIElementData.aResourceURL = aResURLPrefix + aUIElementName; 225 aUIElementData.aName = aUIElementNames[n]; 226 aUIElementData.bModified = false; 227 aUIElementData.bDefault = false; 228 229 // Create hash_map entries for all user interface elements inside the storage. We don't load the 230 // settings to speed up the process. 231 rHashMap.insert( UIElementDataHashMap::value_type( aUIElementData.aResourceURL, aUIElementData )); 232 } 233 } 234 } 235 } 236 } 237 238 rElementTypeData.bLoaded = true; 239 } 240 241 void UIConfigurationManager::impl_requestUIElementData( sal_Int16 nElementType, UIElementData& aUIElementData ) 242 { 243 UIElementType& rElementTypeData = m_aUIElements[nElementType]; 244 245 Reference< XStorage > xElementTypeStorage = rElementTypeData.xStorage; 246 if ( xElementTypeStorage.is() && aUIElementData.aName.getLength() ) 247 { 248 try 249 { 250 Reference< XStream > xStream = xElementTypeStorage->openStreamElement( aUIElementData.aName, ElementModes::READ ); 251 Reference< XInputStream > xInputStream = xStream->getInputStream(); 252 253 if ( xInputStream.is() ) 254 { 255 switch ( nElementType ) 256 { 257 case ::com::sun::star::ui::UIElementType::UNKNOWN: 258 break; 259 260 case ::com::sun::star::ui::UIElementType::MENUBAR: 261 { 262 try 263 { 264 MenuConfiguration aMenuCfg( m_xServiceManager ); 265 Reference< XIndexAccess > xContainer( aMenuCfg.CreateMenuBarConfigurationFromXML( xInputStream )); 266 RootItemContainer* pRootItemContainer = RootItemContainer::GetImplementation( xContainer ); 267 if ( pRootItemContainer ) 268 aUIElementData.xSettings = Reference< XIndexAccess >( static_cast< OWeakObject * >( new ConstItemContainer( pRootItemContainer, sal_True ) ), UNO_QUERY ); 269 else 270 aUIElementData.xSettings = Reference< XIndexAccess >( static_cast< OWeakObject * >( new ConstItemContainer( xContainer, sal_True ) ), UNO_QUERY ); 271 return; 272 } 273 catch ( ::com::sun::star::lang::WrappedTargetException& ) 274 { 275 } 276 } 277 break; 278 279 case ::com::sun::star::ui::UIElementType::POPUPMENU: 280 { 281 break; 282 } 283 284 case ::com::sun::star::ui::UIElementType::TOOLBAR: 285 { 286 try 287 { 288 Reference< XIndexContainer > xIndexContainer( static_cast< OWeakObject * >( new RootItemContainer() ), UNO_QUERY ); 289 ToolBoxConfiguration::LoadToolBox( m_xServiceManager, xInputStream, xIndexContainer ); 290 RootItemContainer* pRootItemContainer = RootItemContainer::GetImplementation( xIndexContainer ); 291 aUIElementData.xSettings = Reference< XIndexAccess >( static_cast< OWeakObject * >( new ConstItemContainer( pRootItemContainer, sal_True ) ), UNO_QUERY ); 292 return; 293 } 294 catch ( ::com::sun::star::lang::WrappedTargetException& ) 295 { 296 } 297 298 break; 299 } 300 301 case ::com::sun::star::ui::UIElementType::STATUSBAR: 302 { 303 try 304 { 305 Reference< XIndexContainer > xIndexContainer( static_cast< OWeakObject * >( new RootItemContainer() ), UNO_QUERY ); 306 StatusBarConfiguration::LoadStatusBar( m_xServiceManager, xInputStream, xIndexContainer ); 307 RootItemContainer* pRootItemContainer = RootItemContainer::GetImplementation( xIndexContainer ); 308 aUIElementData.xSettings = Reference< XIndexAccess >( static_cast< OWeakObject * >( new ConstItemContainer( pRootItemContainer, sal_True ) ), UNO_QUERY ); 309 return; 310 } 311 catch ( ::com::sun::star::lang::WrappedTargetException& ) 312 { 313 } 314 315 break; 316 } 317 318 case ::com::sun::star::ui::UIElementType::FLOATINGWINDOW: 319 { 320 break; 321 } 322 } 323 } 324 } 325 catch ( ::com::sun::star::embed::InvalidStorageException& ) 326 { 327 } 328 catch ( ::com::sun::star::lang::IllegalArgumentException& ) 329 { 330 } 331 catch ( ::com::sun::star::io::IOException& ) 332 { 333 } 334 catch ( ::com::sun::star::embed::StorageWrappedTargetException& ) 335 { 336 } 337 } 338 339 // At least we provide an empty settings container! 340 aUIElementData.xSettings = Reference< XIndexAccess >( static_cast< OWeakObject * >( new ConstItemContainer()), UNO_QUERY ); 341 } 342 343 UIConfigurationManager::UIElementData* UIConfigurationManager::impl_findUIElementData( const rtl::OUString& aResourceURL, sal_Int16 nElementType, bool bLoad ) 344 { 345 // preload list of element types on demand 346 impl_preloadUIElementTypeList( nElementType ); 347 348 // try to look into our document vector/hash_map combination 349 UIElementDataHashMap& rUserHashMap = m_aUIElements[nElementType].aElementsHashMap; 350 UIElementDataHashMap::iterator pIter = rUserHashMap.find( aResourceURL ); 351 if ( pIter != rUserHashMap.end() ) 352 { 353 // Default data settings data means removed! 354 if ( pIter->second.bDefault ) 355 return &(pIter->second); 356 else 357 { 358 if ( !pIter->second.xSettings.is() && bLoad ) 359 impl_requestUIElementData( nElementType, pIter->second ); 360 return &(pIter->second); 361 } 362 } 363 364 // Nothing has been found! 365 return NULL; 366 } 367 368 void UIConfigurationManager::impl_storeElementTypeData( Reference< XStorage >& xStorage, UIElementType& rElementType, bool bResetModifyState ) 369 { 370 UIElementDataHashMap& rHashMap = rElementType.aElementsHashMap; 371 UIElementDataHashMap::iterator pIter = rHashMap.begin(); 372 373 while ( pIter != rHashMap.end() ) 374 { 375 UIElementData& rElement = pIter->second; 376 if ( rElement.bModified ) 377 { 378 if ( rElement.bDefault ) 379 { 380 xStorage->removeElement( rElement.aName ); 381 rElement.bModified = sal_False; // mark as not modified 382 } 383 else 384 { 385 Reference< XStream > xStream( xStorage->openStreamElement( rElement.aName, ElementModes::WRITE|ElementModes::TRUNCATE ), UNO_QUERY ); 386 Reference< XOutputStream > xOutputStream( xStream->getOutputStream() ); 387 388 if ( xOutputStream.is() ) 389 { 390 switch( rElementType.nElementType ) 391 { 392 case ::com::sun::star::ui::UIElementType::MENUBAR: 393 { 394 try 395 { 396 MenuConfiguration aMenuCfg( m_xServiceManager ); 397 aMenuCfg.StoreMenuBarConfigurationToXML( rElement.xSettings, xOutputStream ); 398 } 399 catch ( ::com::sun::star::lang::WrappedTargetException& ) 400 { 401 } 402 } 403 break; 404 405 case ::com::sun::star::ui::UIElementType::TOOLBAR: 406 { 407 try 408 { 409 ToolBoxConfiguration::StoreToolBox( m_xServiceManager, xOutputStream, rElement.xSettings ); 410 } 411 catch ( ::com::sun::star::lang::WrappedTargetException& ) 412 { 413 } 414 } 415 break; 416 417 case ::com::sun::star::ui::UIElementType::STATUSBAR: 418 { 419 try 420 { 421 StatusBarConfiguration::StoreStatusBar( m_xServiceManager, xOutputStream, rElement.xSettings ); 422 } 423 catch ( ::com::sun::star::lang::WrappedTargetException& ) 424 { 425 } 426 } 427 break; 428 429 default: 430 break; 431 } 432 } 433 434 // mark as not modified if we store to our own storage 435 if ( bResetModifyState ) 436 rElement.bModified = sal_False; 437 } 438 } 439 440 ++pIter; 441 } 442 443 // commit element type storage 444 Reference< XTransactedObject > xTransactedObject( xStorage, UNO_QUERY ); 445 if ( xTransactedObject.is() ) 446 xTransactedObject->commit(); 447 448 // mark UIElementType as not modified if we store to our own storage 449 if ( bResetModifyState ) 450 rElementType.bModified = sal_False; 451 } 452 453 void UIConfigurationManager::impl_resetElementTypeData( 454 UIElementType& rDocElementType, 455 ConfigEventNotifyContainer& rRemoveNotifyContainer ) 456 { 457 UIElementDataHashMap& rHashMap = rDocElementType.aElementsHashMap; 458 UIElementDataHashMap::iterator pIter = rHashMap.begin(); 459 460 Reference< XUIConfigurationManager > xThis( static_cast< OWeakObject* >( this ), UNO_QUERY ); 461 Reference< XInterface > xIfac( xThis, UNO_QUERY ); 462 463 // Make copies of the event structures to be thread-safe. We have to unlock our mutex before calling 464 // our listeners! 465 while ( pIter != rHashMap.end() ) 466 { 467 UIElementData& rElement = pIter->second; 468 if ( !rElement.bDefault ) 469 { 470 // Remove user-defined settings from document 471 ConfigurationEvent aEvent; 472 aEvent.ResourceURL = rElement.aResourceURL; 473 aEvent.Accessor <<= xThis; 474 aEvent.Source = xIfac; 475 aEvent.Element <<= rElement.xSettings; 476 477 rRemoveNotifyContainer.push_back( aEvent ); 478 479 // Mark element as default. 480 rElement.bModified = false; 481 rElement.bDefault = true; 482 } 483 else 484 rElement.bModified = false; 485 486 ++pIter; 487 } 488 489 // Remove all settings from our user interface elements 490 rHashMap.clear(); 491 } 492 493 void UIConfigurationManager::impl_reloadElementTypeData( 494 UIElementType& rDocElementType, 495 ConfigEventNotifyContainer& rRemoveNotifyContainer, 496 ConfigEventNotifyContainer& rReplaceNotifyContainer ) 497 { 498 UIElementDataHashMap& rHashMap = rDocElementType.aElementsHashMap; 499 UIElementDataHashMap::iterator pIter = rHashMap.begin(); 500 Reference< XStorage > xElementStorage( rDocElementType.xStorage ); 501 Reference< XNameAccess > xElementNameAccess( xElementStorage, UNO_QUERY ); 502 503 Reference< XUIConfigurationManager > xThis( static_cast< OWeakObject* >( this ), UNO_QUERY ); 504 Reference< XInterface > xIfac( xThis, UNO_QUERY ); 505 sal_Int16 nType = rDocElementType.nElementType; 506 507 while ( pIter != rHashMap.end() ) 508 { 509 UIElementData& rElement = pIter->second; 510 if ( rElement.bModified ) 511 { 512 if ( xElementNameAccess->hasByName( rElement.aName )) 513 { 514 // Replace settings with data from user layer 515 Reference< XIndexAccess > xOldSettings( rElement.xSettings ); 516 517 impl_requestUIElementData( nType, rElement ); 518 519 ConfigurationEvent aReplaceEvent; 520 521 aReplaceEvent.ResourceURL = rElement.aResourceURL; 522 aReplaceEvent.Accessor <<= xThis; 523 aReplaceEvent.Source = xIfac; 524 aReplaceEvent.ReplacedElement <<= xOldSettings; 525 aReplaceEvent.Element <<= rElement.xSettings; 526 rReplaceNotifyContainer.push_back( aReplaceEvent ); 527 528 rElement.bModified = false; 529 } 530 else 531 { 532 // Element settings are not in any storage => remove 533 ConfigurationEvent aRemoveEvent; 534 535 aRemoveEvent.ResourceURL = rElement.aResourceURL; 536 aRemoveEvent.Accessor <<= xThis; 537 aRemoveEvent.Source = xIfac; 538 aRemoveEvent.Element <<= rElement.xSettings; 539 540 rRemoveNotifyContainer.push_back( aRemoveEvent ); 541 542 // Mark element as default and not modified. That means "not active" in the document anymore 543 rElement.bModified = false; 544 rElement.bDefault = true; 545 } 546 } 547 ++pIter; 548 } 549 550 rDocElementType.bModified = sal_False; 551 } 552 553 void UIConfigurationManager::impl_Initialize() 554 { 555 // Initialize the top-level structures with the storage data 556 if ( m_xDocConfigStorage.is() ) 557 { 558 long nModes = m_bReadOnly ? ElementModes::READ : ElementModes::READWRITE; 559 560 // Try to access our module sub folder 561 for ( sal_Int16 i = 1; i < ::com::sun::star::ui::UIElementType::COUNT; 562 i++ ) 563 { 564 Reference< XStorage > xElementTypeStorage; 565 try 566 { 567 xElementTypeStorage = m_xDocConfigStorage->openStorageElement( rtl::OUString::createFromAscii( UIELEMENTTYPENAMES[i] ), nModes ); 568 } 569 catch ( com::sun::star::container::NoSuchElementException& ) 570 { 571 } 572 catch ( ::com::sun::star::embed::InvalidStorageException& ) 573 { 574 } 575 catch ( ::com::sun::star::lang::IllegalArgumentException& ) 576 { 577 } 578 catch ( ::com::sun::star::io::IOException& ) 579 { 580 } 581 catch ( ::com::sun::star::embed::StorageWrappedTargetException& ) 582 { 583 } 584 585 m_aUIElements[i].nElementType = i; 586 m_aUIElements[i].bModified = false; 587 m_aUIElements[i].xStorage = xElementTypeStorage; 588 m_aUIElements[i].bDefaultLayer = false; 589 } 590 } 591 else 592 { 593 // We have no storage, just initialize ui element types with empty storage! 594 for ( int i = 1; i < ::com::sun::star::ui::UIElementType::COUNT; i++ ) 595 m_aUIElements[i].xStorage = m_xDocConfigStorage; 596 } 597 } 598 599 UIConfigurationManager::UIConfigurationManager( com::sun::star::uno::Reference< com::sun::star::lang::XMultiServiceFactory > xServiceManager ) : 600 ThreadHelpBase( &Application::GetSolarMutex() ) 601 , m_xDocConfigStorage( 0 ) 602 , m_bReadOnly( true ) 603 , m_bInitialized( false ) 604 , m_bModified( false ) 605 , m_bConfigRead( false ) 606 , m_bDisposed( false ) 607 , m_aXMLPostfix( RTL_CONSTASCII_USTRINGPARAM( ".xml" )) 608 , m_aPropUIName( RTL_CONSTASCII_USTRINGPARAM( "UIName" )) 609 , m_aPropResourceURL( RTL_CONSTASCII_USTRINGPARAM( "ResourceURL" )) 610 , m_xServiceManager( xServiceManager ) 611 , m_aListenerContainer( m_aLock.getShareableOslMutex() ) 612 { 613 // Make sure we have a default initialized entry for every layer and user interface element type! 614 // The following code depends on this! 615 m_aUIElements.resize( ::com::sun::star::ui::UIElementType::COUNT ); 616 } 617 618 UIConfigurationManager::~UIConfigurationManager() 619 { 620 } 621 622 // XComponent 623 void SAL_CALL UIConfigurationManager::dispose() throw (::com::sun::star::uno::RuntimeException) 624 { 625 Reference< XComponent > xThis( static_cast< OWeakObject* >(this), UNO_QUERY ); 626 627 css::lang::EventObject aEvent( xThis ); 628 m_aListenerContainer.disposeAndClear( aEvent ); 629 630 { 631 ResetableGuard aGuard( m_aLock ); 632 try 633 { 634 if ( m_xImageManager.is() ) 635 m_xImageManager->dispose(); 636 } 637 catch ( Exception& ) 638 { 639 } 640 641 m_xImageManager.clear(); 642 m_aUIElements.clear(); 643 m_xDocConfigStorage.clear(); 644 m_bConfigRead = false; 645 m_bModified = false; 646 m_bDisposed = true; 647 } 648 } 649 650 void SAL_CALL UIConfigurationManager::addEventListener( const Reference< XEventListener >& xListener ) throw (::com::sun::star::uno::RuntimeException) 651 { 652 { 653 ResetableGuard aGuard( m_aLock ); 654 655 /* SAFE AREA ----------------------------------------------------------------------------------------------- */ 656 if ( m_bDisposed ) 657 throw DisposedException(); 658 } 659 660 m_aListenerContainer.addInterface( ::getCppuType( ( const Reference< XEventListener >* ) NULL ), xListener ); 661 } 662 663 void SAL_CALL UIConfigurationManager::removeEventListener( const Reference< XEventListener >& xListener ) throw (::com::sun::star::uno::RuntimeException) 664 { 665 /* SAFE AREA ----------------------------------------------------------------------------------------------- */ 666 m_aListenerContainer.removeInterface( ::getCppuType( ( const Reference< XEventListener >* ) NULL ), xListener ); 667 } 668 669 // XUIConfigurationManager 670 void SAL_CALL UIConfigurationManager::addConfigurationListener( const Reference< ::com::sun::star::ui::XUIConfigurationListener >& xListener ) throw (::com::sun::star::uno::RuntimeException) 671 { 672 { 673 ResetableGuard aGuard( m_aLock ); 674 675 /* SAFE AREA ----------------------------------------------------------------------------------------------- */ 676 if ( m_bDisposed ) 677 throw DisposedException(); 678 } 679 680 m_aListenerContainer.addInterface( ::getCppuType( ( const Reference< XUIConfigurationListener >* ) NULL ), xListener ); 681 } 682 683 void SAL_CALL UIConfigurationManager::removeConfigurationListener( const Reference< ::com::sun::star::ui::XUIConfigurationListener >& xListener ) throw (::com::sun::star::uno::RuntimeException) 684 { 685 /* SAFE AREA ----------------------------------------------------------------------------------------------- */ 686 m_aListenerContainer.removeInterface( ::getCppuType( ( const Reference< XUIConfigurationListener >* ) NULL ), xListener ); 687 } 688 689 690 void SAL_CALL UIConfigurationManager::reset() throw (::com::sun::star::uno::RuntimeException) 691 { 692 ResetableGuard aGuard( m_aLock ); 693 694 /* SAFE AREA ----------------------------------------------------------------------------------------------- */ 695 if ( m_bDisposed ) 696 throw DisposedException(); 697 698 if ( isReadOnly() ) 699 return; 700 701 bool bResetStorage( false ); 702 if ( m_xDocConfigStorage.is() ) 703 { 704 try 705 { 706 // Remove all elements from our user-defined storage! 707 bool bCommit( false ); 708 for ( int i = 1; i < ::com::sun::star::ui::UIElementType::COUNT; i++ ) 709 { 710 UIElementType& rElementType = m_aUIElements[i]; 711 Reference< XStorage > xSubStorage( rElementType.xStorage, UNO_QUERY ); 712 713 if ( xSubStorage.is() ) 714 { 715 bool bCommitSubStorage( false ); 716 Reference< XNameAccess > xSubStorageNameAccess( xSubStorage, UNO_QUERY ); 717 Sequence< rtl::OUString > aUIElementStreamNames = xSubStorageNameAccess->getElementNames(); 718 for ( sal_Int32 j = 0; j < aUIElementStreamNames.getLength(); j++ ) 719 { 720 xSubStorage->removeElement( aUIElementStreamNames[j] ); 721 bCommitSubStorage = true; 722 bCommit = true; 723 } 724 725 if ( bCommitSubStorage ) 726 { 727 Reference< XTransactedObject > xTransactedObject( xSubStorage, UNO_QUERY ); 728 if ( xTransactedObject.is() ) 729 xTransactedObject->commit(); 730 } 731 } 732 } 733 734 // Commit changes 735 if ( bCommit ) 736 { 737 Reference< XTransactedObject > xTransactedObject( m_xDocConfigStorage, UNO_QUERY ); 738 if ( xTransactedObject.is() ) 739 xTransactedObject->commit(); 740 } 741 bResetStorage = true; 742 743 // remove settings from user defined layer and notify listener about removed settings data! 744 // Try to access our module sub folder 745 ConfigEventNotifyContainer aRemoveEventNotifyContainer; 746 for ( sal_Int16 j = 1; j < ::com::sun::star::ui::UIElementType::COUNT; j++ ) 747 { 748 UIElementType& rDocElementType = m_aUIElements[j]; 749 750 impl_resetElementTypeData( rDocElementType, aRemoveEventNotifyContainer ); 751 rDocElementType.bModified = sal_False; 752 } 753 754 m_bModified = sal_False; 755 756 // Unlock mutex before notify our listeners 757 aGuard.unlock(); 758 759 // Notify our listeners 760 for ( sal_uInt32 k = 0; k < aRemoveEventNotifyContainer.size(); k++ ) 761 implts_notifyContainerListener( aRemoveEventNotifyContainer[k], NotifyOp_Remove ); 762 } 763 catch ( ::com::sun::star::lang::IllegalArgumentException& ) 764 { 765 } 766 catch ( ::com::sun::star::container::NoSuchElementException& ) 767 { 768 } 769 catch ( ::com::sun::star::embed::InvalidStorageException& ) 770 { 771 } 772 catch ( ::com::sun::star::embed::StorageWrappedTargetException& ) 773 { 774 } 775 } 776 } 777 778 Sequence< Sequence< PropertyValue > > SAL_CALL UIConfigurationManager::getUIElementsInfo( sal_Int16 ElementType ) 779 throw ( IllegalArgumentException, RuntimeException ) 780 { 781 if (( ElementType < 0 ) || ( ElementType >= ::com::sun::star::ui::UIElementType::COUNT )) 782 throw IllegalArgumentException(); 783 784 ResetableGuard aGuard( m_aLock ); 785 if ( m_bDisposed ) 786 throw DisposedException(); 787 788 Sequence< Sequence< PropertyValue > > aElementInfoSeq; 789 UIElementInfoHashMap aUIElementInfoCollection; 790 791 if ( ElementType == ::com::sun::star::ui::UIElementType::UNKNOWN ) 792 { 793 for ( sal_Int16 i = 0; i < ::com::sun::star::ui::UIElementType::COUNT; i++ ) 794 impl_fillSequenceWithElementTypeInfo( aUIElementInfoCollection, sal_Int16( i ) ); 795 } 796 else 797 impl_fillSequenceWithElementTypeInfo( aUIElementInfoCollection, ElementType ); 798 799 Sequence< PropertyValue > aUIElementInfo( 2 ); 800 aUIElementInfo[0].Name = m_aPropResourceURL; 801 aUIElementInfo[1].Name = m_aPropUIName; 802 803 aElementInfoSeq.realloc( aUIElementInfoCollection.size() ); 804 UIElementInfoHashMap::const_iterator pIter = aUIElementInfoCollection.begin(); 805 806 sal_Int32 n = 0; 807 while ( pIter != aUIElementInfoCollection.end() ) 808 { 809 aUIElementInfo[0].Value <<= pIter->second.aResourceURL; 810 aUIElementInfo[1].Value <<= pIter->second.aUIName; 811 aElementInfoSeq[n++] = aUIElementInfo; 812 ++pIter; 813 } 814 815 return aElementInfoSeq; 816 } 817 818 Reference< XIndexContainer > SAL_CALL UIConfigurationManager::createSettings() throw (::com::sun::star::uno::RuntimeException) 819 { 820 ResetableGuard aGuard( m_aLock ); 821 822 if ( m_bDisposed ) 823 throw DisposedException(); 824 825 // Creates an empty item container which can be filled from outside 826 return Reference< XIndexContainer >( static_cast< OWeakObject * >( new RootItemContainer()), UNO_QUERY ); 827 } 828 829 sal_Bool SAL_CALL UIConfigurationManager::hasSettings( const ::rtl::OUString& ResourceURL ) 830 throw (::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException) 831 { 832 sal_Int16 nElementType = RetrieveTypeFromResourceURL( ResourceURL ); 833 834 if (( nElementType == ::com::sun::star::ui::UIElementType::UNKNOWN ) || 835 ( nElementType >= ::com::sun::star::ui::UIElementType::COUNT )) 836 throw IllegalArgumentException(); 837 else 838 { 839 UIElementData* pDataSettings = impl_findUIElementData( ResourceURL, nElementType, false ); 840 if ( pDataSettings && !pDataSettings->bDefault ) 841 return sal_True; 842 } 843 844 return sal_False; 845 } 846 847 Reference< XIndexAccess > SAL_CALL UIConfigurationManager::getSettings( const ::rtl::OUString& ResourceURL, sal_Bool bWriteable ) 848 throw (::com::sun::star::container::NoSuchElementException, ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException) 849 { 850 sal_Int16 nElementType = RetrieveTypeFromResourceURL( ResourceURL ); 851 852 if (( nElementType == ::com::sun::star::ui::UIElementType::UNKNOWN ) || 853 ( nElementType >= ::com::sun::star::ui::UIElementType::COUNT )) 854 throw IllegalArgumentException(); 855 else 856 { 857 ResetableGuard aGuard( m_aLock ); 858 859 if ( m_bDisposed ) 860 throw DisposedException(); 861 862 UIElementData* pDataSettings = impl_findUIElementData( ResourceURL, nElementType ); 863 if ( pDataSettings && !pDataSettings->bDefault ) 864 { 865 // Create a copy of our data if someone wants to change the data. 866 if ( bWriteable ) 867 return Reference< XIndexAccess >( static_cast< OWeakObject * >( new RootItemContainer( pDataSettings->xSettings ) ), UNO_QUERY ); 868 else 869 return pDataSettings->xSettings; 870 } 871 } 872 873 throw NoSuchElementException(); 874 } 875 876 void SAL_CALL UIConfigurationManager::replaceSettings( const ::rtl::OUString& ResourceURL, const Reference< ::com::sun::star::container::XIndexAccess >& aNewData ) 877 throw (::com::sun::star::container::NoSuchElementException, ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::lang::IllegalAccessException, ::com::sun::star::uno::RuntimeException) 878 { 879 sal_Int16 nElementType = RetrieveTypeFromResourceURL( ResourceURL ); 880 881 if (( nElementType == ::com::sun::star::ui::UIElementType::UNKNOWN ) || 882 ( nElementType >= ::com::sun::star::ui::UIElementType::COUNT )) 883 throw IllegalArgumentException(); 884 else if ( m_bReadOnly ) 885 throw IllegalAccessException(); 886 else 887 { 888 ResetableGuard aGuard( m_aLock ); 889 890 if ( m_bDisposed ) 891 throw DisposedException(); 892 893 UIElementData* pDataSettings = impl_findUIElementData( ResourceURL, nElementType ); 894 if ( pDataSettings && !pDataSettings->bDefault ) 895 { 896 // we have a settings entry in our user-defined layer - replace 897 Reference< XIndexAccess > xOldSettings = pDataSettings->xSettings; 898 899 // Create a copy of the data if the container is not const 900 Reference< XIndexReplace > xReplace( aNewData, UNO_QUERY ); 901 if ( xReplace.is() ) 902 pDataSettings->xSettings = Reference< XIndexAccess >( static_cast< OWeakObject * >( new ConstItemContainer( aNewData ) ), UNO_QUERY ); 903 else 904 pDataSettings->xSettings = aNewData; 905 906 pDataSettings->bDefault = false; 907 pDataSettings->bModified = true; 908 m_bModified = true; 909 910 // Modify type container 911 UIElementType& rElementType = m_aUIElements[nElementType]; 912 rElementType.bModified = true; 913 914 Reference< XUIConfigurationManager > xThis( static_cast< OWeakObject* >( this ), UNO_QUERY ); 915 916 // Create event to notify listener about replaced element settings 917 ConfigurationEvent aEvent; 918 Reference< XInterface > xIfac( xThis, UNO_QUERY ); 919 920 aEvent.ResourceURL = ResourceURL; 921 aEvent.Accessor <<= xThis; 922 aEvent.Source = xIfac; 923 aEvent.ReplacedElement <<= xOldSettings; 924 aEvent.Element <<= pDataSettings->xSettings; 925 926 aGuard.unlock(); 927 928 implts_notifyContainerListener( aEvent, NotifyOp_Replace ); 929 } 930 else 931 throw NoSuchElementException(); 932 } 933 } 934 935 void SAL_CALL UIConfigurationManager::removeSettings( const ::rtl::OUString& ResourceURL ) 936 throw ( NoSuchElementException, IllegalArgumentException, IllegalAccessException, RuntimeException) 937 { 938 sal_Int16 nElementType = RetrieveTypeFromResourceURL( ResourceURL ); 939 940 if (( nElementType == ::com::sun::star::ui::UIElementType::UNKNOWN ) || 941 ( nElementType >= ::com::sun::star::ui::UIElementType::COUNT )) 942 throw IllegalArgumentException(); 943 else if ( m_bReadOnly ) 944 throw IllegalAccessException(); 945 else 946 { 947 ResetableGuard aGuard( m_aLock ); 948 949 if ( m_bDisposed ) 950 throw DisposedException(); 951 952 UIElementData* pDataSettings = impl_findUIElementData( ResourceURL, nElementType ); 953 if ( pDataSettings ) 954 { 955 // If element settings are default, we don't need to change anything! 956 if ( pDataSettings->bDefault ) 957 return; 958 else 959 { 960 Reference< XIndexAccess > xRemovedSettings = pDataSettings->xSettings; 961 pDataSettings->bDefault = true; 962 963 // check if this is a default layer node 964 pDataSettings->bModified = true; // we have to remove this node from the user layer! 965 pDataSettings->xSettings.clear(); 966 m_bModified = true; // user layer must be written 967 968 // Modify type container 969 UIElementType& rElementType = m_aUIElements[nElementType]; 970 rElementType.bModified = true; 971 972 Reference< XUIConfigurationManager > xThis( static_cast< OWeakObject* >( this ), UNO_QUERY ); 973 Reference< XInterface > xIfac( xThis, UNO_QUERY ); 974 975 // Create event to notify listener about removed element settings 976 ConfigurationEvent aEvent; 977 978 aEvent.ResourceURL = ResourceURL; 979 aEvent.Accessor <<= xThis; 980 aEvent.Source = xIfac; 981 aEvent.Element <<= xRemovedSettings; 982 983 aGuard.unlock(); 984 985 implts_notifyContainerListener( aEvent, NotifyOp_Remove ); 986 } 987 } 988 else 989 throw NoSuchElementException(); 990 } 991 } 992 993 void SAL_CALL UIConfigurationManager::insertSettings( const ::rtl::OUString& NewResourceURL, const Reference< XIndexAccess >& aNewData ) 994 throw ( ElementExistException, IllegalArgumentException, IllegalAccessException, RuntimeException ) 995 { 996 sal_Int16 nElementType = RetrieveTypeFromResourceURL( NewResourceURL ); 997 998 if (( nElementType == ::com::sun::star::ui::UIElementType::UNKNOWN ) || 999 ( nElementType >= ::com::sun::star::ui::UIElementType::COUNT )) 1000 throw IllegalArgumentException(); 1001 else if ( m_bReadOnly ) 1002 throw IllegalAccessException(); 1003 else 1004 { 1005 ResetableGuard aGuard( m_aLock ); 1006 1007 if ( m_bDisposed ) 1008 throw DisposedException(); 1009 1010 bool bInsertData( false ); 1011 UIElementData aUIElementData; 1012 UIElementData* pDataSettings = impl_findUIElementData( NewResourceURL, nElementType ); 1013 1014 if ( pDataSettings && !pDataSettings->bDefault ) 1015 throw ElementExistException(); 1016 1017 if ( !pDataSettings ) 1018 { 1019 pDataSettings = &aUIElementData; 1020 bInsertData = true; 1021 } 1022 1023 { 1024 pDataSettings->bDefault = false; 1025 pDataSettings->bModified = true; 1026 1027 // Create a copy of the data if the container is not const 1028 Reference< XIndexReplace > xReplace( aNewData, UNO_QUERY ); 1029 if ( xReplace.is() ) 1030 pDataSettings->xSettings = Reference< XIndexAccess >( static_cast< OWeakObject * >( new ConstItemContainer( aNewData ) ), UNO_QUERY ); 1031 else 1032 pDataSettings->xSettings = aNewData; 1033 1034 m_bModified = true; 1035 1036 UIElementType& rElementType = m_aUIElements[nElementType]; 1037 rElementType.bModified = true; 1038 1039 if ( bInsertData ) 1040 { 1041 pDataSettings->aName = RetrieveNameFromResourceURL( NewResourceURL ) + m_aXMLPostfix; 1042 pDataSettings->aResourceURL = NewResourceURL; 1043 1044 UIElementDataHashMap& rElements = rElementType.aElementsHashMap; 1045 rElements.insert( UIElementDataHashMap::value_type( NewResourceURL, *pDataSettings )); 1046 } 1047 1048 Reference< XIndexAccess > xInsertSettings( aUIElementData.xSettings ); 1049 Reference< XUIConfigurationManager > xThis( static_cast< OWeakObject* >( this ), UNO_QUERY ); 1050 Reference< XInterface > xIfac( xThis, UNO_QUERY ); 1051 1052 // Create event to notify listener about removed element settings 1053 ConfigurationEvent aEvent; 1054 1055 aEvent.ResourceURL = NewResourceURL; 1056 aEvent.Accessor <<= xThis; 1057 aEvent.Source = xIfac; 1058 aEvent.Element <<= xInsertSettings; 1059 1060 aGuard.unlock(); 1061 1062 implts_notifyContainerListener( aEvent, NotifyOp_Insert ); 1063 } 1064 } 1065 } 1066 1067 Reference< XInterface > SAL_CALL UIConfigurationManager::getImageManager() throw (::com::sun::star::uno::RuntimeException) 1068 { 1069 if ( m_bDisposed ) 1070 throw DisposedException(); 1071 1072 if ( !m_xImageManager.is() ) 1073 { 1074 m_xImageManager = Reference< XComponent >( static_cast< cppu::OWeakObject *>( new ImageManager( m_xServiceManager )), 1075 UNO_QUERY ); 1076 Reference< XInitialization > xInit( m_xImageManager, UNO_QUERY ); 1077 1078 Sequence< Any > aPropSeq( 2 ); 1079 PropertyValue aPropValue; 1080 aPropValue.Name = rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "UserConfigStorage" )); 1081 aPropValue.Value = makeAny( m_xDocConfigStorage ); 1082 aPropSeq[0] = makeAny( aPropValue ); 1083 aPropValue.Name = rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "ModuleIdentifier" )); 1084 aPropValue.Value = makeAny( m_aModuleIdentifier ); 1085 aPropSeq[1] = makeAny( aPropValue ); 1086 1087 xInit->initialize( aPropSeq ); 1088 } 1089 1090 return Reference< XInterface >( m_xImageManager, UNO_QUERY ); 1091 } 1092 1093 Reference< XInterface > SAL_CALL UIConfigurationManager::getShortCutManager() throw (::com::sun::star::uno::RuntimeException) 1094 { 1095 // SAFE -> 1096 ResetableGuard aGuard( m_aLock ); 1097 1098 if (m_xAccConfig.is()) 1099 return m_xAccConfig; 1100 1101 Reference< XMultiServiceFactory > xSMGR = m_xServiceManager; 1102 Reference< XStorage > xDocumentRoot = m_xDocConfigStorage; 1103 1104 aGuard.unlock(); 1105 // <- SAFE 1106 1107 Reference< XInterface > xAccConfig = xSMGR->createInstance(SERVICENAME_DOCUMENTACCELERATORCONFIGURATION); 1108 Reference< XInitialization > xInit (xAccConfig, UNO_QUERY_THROW); 1109 1110 PropertyValue aProp; 1111 aProp.Name = ::rtl::OUString::createFromAscii("DocumentRoot"); 1112 aProp.Value <<= xDocumentRoot; 1113 1114 Sequence< Any > lArgs(1); 1115 lArgs[0] <<= aProp; 1116 1117 xInit->initialize(lArgs); 1118 1119 // SAFE -> 1120 aGuard.lock(); 1121 m_xAccConfig = xAccConfig; 1122 aGuard.unlock(); 1123 // <- SAFE 1124 1125 return xAccConfig; 1126 } 1127 1128 Reference< XInterface > SAL_CALL UIConfigurationManager::getEventsManager() throw (::com::sun::star::uno::RuntimeException) 1129 { 1130 return Reference< XInterface >(); 1131 } 1132 1133 // XUIConfigurationStorage 1134 void SAL_CALL UIConfigurationManager::setStorage( const Reference< XStorage >& Storage ) throw (::com::sun::star::uno::RuntimeException) 1135 { 1136 ResetableGuard aGuard( m_aLock ); 1137 1138 if ( m_bDisposed ) 1139 throw DisposedException(); 1140 1141 if ( m_xDocConfigStorage.is() ) 1142 { 1143 try 1144 { 1145 // Dispose old storage to be sure that it will be closed 1146 Reference< XComponent > xComponent( m_xDocConfigStorage, UNO_QUERY ); 1147 if ( xComponent.is() ) 1148 xComponent->dispose(); 1149 } 1150 catch ( Exception& ) 1151 { 1152 } 1153 } 1154 1155 // We store the new storage. Be careful it could be an empty reference! 1156 m_xDocConfigStorage = Storage; 1157 m_bReadOnly = sal_True; 1158 1159 Reference< XUIConfigurationStorage > xAccUpdate(m_xAccConfig, UNO_QUERY); 1160 if ( xAccUpdate.is() ) 1161 xAccUpdate->setStorage( m_xDocConfigStorage ); 1162 1163 if ( m_xImageManager.is() ) 1164 { 1165 ImageManager* pImageManager = (ImageManager*)m_xImageManager.get(); 1166 if ( pImageManager ) 1167 pImageManager->setStorage( m_xDocConfigStorage ); 1168 } 1169 1170 if ( m_xDocConfigStorage.is() ) 1171 { 1172 Reference< XPropertySet > xPropSet( m_xDocConfigStorage, UNO_QUERY ); 1173 if ( xPropSet.is() ) 1174 { 1175 try 1176 { 1177 long nOpenMode = 0; 1178 Any a = xPropSet->getPropertyValue( rtl::OUString( RTL_CONSTASCII_USTRINGPARAM( "OpenMode" ))); 1179 if ( a >>= nOpenMode ) 1180 m_bReadOnly = !( nOpenMode & ElementModes::WRITE ); 1181 } 1182 catch ( com::sun::star::beans::UnknownPropertyException& ) 1183 { 1184 } 1185 catch ( com::sun::star::lang::WrappedTargetException& ) 1186 { 1187 } 1188 } 1189 } 1190 1191 impl_Initialize(); 1192 } 1193 1194 sal_Bool SAL_CALL UIConfigurationManager::hasStorage() throw (::com::sun::star::uno::RuntimeException) 1195 { 1196 ResetableGuard aGuard( m_aLock ); 1197 1198 if ( m_bDisposed ) 1199 throw DisposedException(); 1200 1201 return ( m_xDocConfigStorage.is() ); 1202 } 1203 1204 // XUIConfigurationPersistence 1205 void SAL_CALL UIConfigurationManager::reload() throw (::com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException) 1206 { 1207 ResetableGuard aGuard( m_aLock ); 1208 1209 if ( m_bDisposed ) 1210 throw DisposedException(); 1211 1212 if ( m_xDocConfigStorage.is() && m_bModified && !m_bReadOnly ) 1213 { 1214 // Try to access our module sub folder 1215 ConfigEventNotifyContainer aRemoveNotifyContainer; 1216 ConfigEventNotifyContainer aReplaceNotifyContainer; 1217 for ( sal_Int16 i = 1; i < ::com::sun::star::ui::UIElementType::COUNT; i++ ) 1218 { 1219 try 1220 { 1221 UIElementType& rDocElementType = m_aUIElements[i]; 1222 if ( rDocElementType.bModified ) 1223 impl_reloadElementTypeData( rDocElementType, aRemoveNotifyContainer, aReplaceNotifyContainer ); 1224 } 1225 catch ( Exception& ) 1226 { 1227 throw IOException(); 1228 } 1229 } 1230 1231 m_bModified = sal_False; 1232 1233 // Unlock mutex before notify our listeners 1234 aGuard.unlock(); 1235 1236 // Notify our listeners 1237 for ( sal_uInt32 j = 0; j < aRemoveNotifyContainer.size(); j++ ) 1238 implts_notifyContainerListener( aRemoveNotifyContainer[j], NotifyOp_Remove ); 1239 for ( sal_uInt32 k = 0; k < aReplaceNotifyContainer.size(); k++ ) 1240 implts_notifyContainerListener( aReplaceNotifyContainer[k], NotifyOp_Replace ); 1241 } 1242 } 1243 1244 void SAL_CALL UIConfigurationManager::store() throw (::com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException) 1245 { 1246 ResetableGuard aGuard( m_aLock ); 1247 1248 if ( m_bDisposed ) 1249 throw DisposedException(); 1250 1251 if ( m_xDocConfigStorage.is() && m_bModified && !m_bReadOnly ) 1252 { 1253 // Try to access our module sub folder 1254 for ( int i = 1; i < ::com::sun::star::ui::UIElementType::COUNT; i++ ) 1255 { 1256 try 1257 { 1258 UIElementType& rElementType = m_aUIElements[i]; 1259 Reference< XStorage > xStorage( rElementType.xStorage, UNO_QUERY ); 1260 1261 if ( rElementType.bModified && xStorage.is() ) 1262 impl_storeElementTypeData( xStorage, rElementType ); 1263 } 1264 catch ( Exception& ) 1265 { 1266 throw IOException(); 1267 } 1268 } 1269 1270 m_bModified = false; 1271 Reference< XTransactedObject > xTransactedObject( m_xDocConfigStorage, UNO_QUERY ); 1272 if ( xTransactedObject.is() ) 1273 xTransactedObject->commit(); 1274 } 1275 } 1276 1277 void SAL_CALL UIConfigurationManager::storeToStorage( const Reference< XStorage >& Storage ) throw (::com::sun::star::uno::Exception, ::com::sun::star::uno::RuntimeException) 1278 { 1279 ResetableGuard aGuard( m_aLock ); 1280 1281 if ( m_bDisposed ) 1282 throw DisposedException(); 1283 1284 if ( m_xDocConfigStorage.is() && m_bModified && !m_bReadOnly ) 1285 { 1286 // Try to access our module sub folder 1287 for ( int i = 1; i < ::com::sun::star::ui::UIElementType::COUNT; i++ ) 1288 { 1289 try 1290 { 1291 Reference< XStorage > xElementTypeStorage( Storage->openStorageElement( 1292 rtl::OUString::createFromAscii( UIELEMENTTYPENAMES[i] ), ElementModes::READWRITE )); 1293 UIElementType& rElementType = m_aUIElements[i]; 1294 1295 if ( rElementType.bModified && xElementTypeStorage.is() ) 1296 impl_storeElementTypeData( xElementTypeStorage, rElementType, false ); // store data to storage, but don't reset modify flag! 1297 } 1298 catch ( Exception& ) 1299 { 1300 throw IOException(); 1301 } 1302 } 1303 1304 Reference< XTransactedObject > xTransactedObject( Storage, UNO_QUERY ); 1305 if ( xTransactedObject.is() ) 1306 xTransactedObject->commit(); 1307 } 1308 } 1309 1310 sal_Bool SAL_CALL UIConfigurationManager::isModified() throw (::com::sun::star::uno::RuntimeException) 1311 { 1312 ResetableGuard aGuard( m_aLock ); 1313 1314 return m_bModified; 1315 } 1316 1317 sal_Bool SAL_CALL UIConfigurationManager::isReadOnly() throw (::com::sun::star::uno::RuntimeException) 1318 { 1319 ResetableGuard aGuard( m_aLock ); 1320 1321 return m_bReadOnly; 1322 } 1323 1324 void UIConfigurationManager::implts_notifyContainerListener( const ConfigurationEvent& aEvent, NotifyOp eOp ) 1325 { 1326 ::cppu::OInterfaceContainerHelper* pContainer = m_aListenerContainer.getContainer( ::getCppuType( ( const css::uno::Reference< ::com::sun::star::ui::XUIConfigurationListener >*) NULL ) ); 1327 if ( pContainer != NULL ) 1328 { 1329 ::cppu::OInterfaceIteratorHelper pIterator( *pContainer ); 1330 while ( pIterator.hasMoreElements() ) 1331 { 1332 try 1333 { 1334 switch ( eOp ) 1335 { 1336 case NotifyOp_Replace: 1337 ((::com::sun::star::ui::XUIConfigurationListener*)pIterator.next())->elementReplaced( aEvent ); 1338 break; 1339 case NotifyOp_Insert: 1340 ((::com::sun::star::ui::XUIConfigurationListener*)pIterator.next())->elementInserted( aEvent ); 1341 break; 1342 case NotifyOp_Remove: 1343 ((::com::sun::star::ui::XUIConfigurationListener*)pIterator.next())->elementRemoved( aEvent ); 1344 break; 1345 } 1346 } 1347 catch( css::uno::RuntimeException& ) 1348 { 1349 pIterator.remove(); 1350 } 1351 } 1352 } 1353 } 1354 1355 } // namespace framework 1356