LCOV - code coverage report
Current view: top level - framework/source/uiconfiguration - imagemanagerimpl.cxx (source / functions) Hit Total Coverage
Test: commit c8344322a7af75b84dd3ca8f78b05543a976dfd5 Lines: 212 705 30.1 %
Date: 2015-06-13 12:38:46 Functions: 27 49 55.1 %
Legend: Lines: hit not hit

          Line data    Source code
       1             : /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
       2             : /*
       3             :  * This file is part of the LibreOffice project.
       4             :  *
       5             :  * This Source Code Form is subject to the terms of the Mozilla Public
       6             :  * License, v. 2.0. If a copy of the MPL was not distributed with this
       7             :  * file, You can obtain one at http://mozilla.org/MPL/2.0/.
       8             :  *
       9             :  * This file incorporates work covered by the following license notice:
      10             :  *
      11             :  *   Licensed to the Apache Software Foundation (ASF) under one or more
      12             :  *   contributor license agreements. See the NOTICE file distributed
      13             :  *   with this work for additional information regarding copyright
      14             :  *   ownership. The ASF licenses this file to you under the Apache
      15             :  *   License, Version 2.0 (the "License"); you may not use this file
      16             :  *   except in compliance with the License. You may obtain a copy of
      17             :  *   the License at http://www.apache.org/licenses/LICENSE-2.0 .
      18             :  */
      19             : 
      20             : #include "imagemanagerimpl.hxx"
      21             : #include <xml/imagesconfiguration.hxx>
      22             : #include <uiconfiguration/graphicnameaccess.hxx>
      23             : #include <services.h>
      24             : 
      25             : #include "properties.h"
      26             : 
      27             : #include <com/sun/star/frame/theUICommandDescription.hpp>
      28             : #include <com/sun/star/ui/UIElementType.hpp>
      29             : #include <com/sun/star/ui/ConfigurationEvent.hpp>
      30             : #include <com/sun/star/lang/DisposedException.hpp>
      31             : #include <com/sun/star/beans/XPropertySet.hpp>
      32             : #include <com/sun/star/beans/PropertyValue.hpp>
      33             : #include <com/sun/star/embed/ElementModes.hpp>
      34             : #include <com/sun/star/io/XStream.hpp>
      35             : #include <com/sun/star/ui/ImageType.hpp>
      36             : 
      37             : #include <vcl/svapp.hxx>
      38             : #include <rtl/ustrbuf.hxx>
      39             : #include <osl/mutex.hxx>
      40             : #include <comphelper/sequence.hxx>
      41             : #include <tools/urlobj.hxx>
      42             : #include <unotools/ucbstreamhelper.hxx>
      43             : #include <vcl/pngread.hxx>
      44             : #include <vcl/pngwrite.hxx>
      45             : #include <rtl/instance.hxx>
      46             : #include <svtools/miscopt.hxx>
      47             : #include <boost/scoped_ptr.hpp>
      48             : 
      49             : using ::com::sun::star::uno::Sequence;
      50             : using ::com::sun::star::uno::XInterface;
      51             : using ::com::sun::star::uno::Exception;
      52             : using ::com::sun::star::uno::RuntimeException;
      53             : using ::com::sun::star::uno::UNO_QUERY;
      54             : using ::com::sun::star::uno::Any;
      55             : using ::com::sun::star::uno::makeAny;
      56             : using ::com::sun::star::graphic::XGraphic;
      57             : using namespace ::com::sun::star;
      58             : using namespace ::com::sun::star::io;
      59             : using namespace ::com::sun::star::embed;
      60             : using namespace ::com::sun::star::lang;
      61             : using namespace ::com::sun::star::container;
      62             : using namespace ::com::sun::star::beans;
      63             : using namespace ::com::sun::star::ui;
      64             : using namespace ::cppu;
      65             : 
      66             : // Image sizes for our toolbars/menus
      67             : const sal_Int32 IMAGE_SIZE_NORMAL         = 16;
      68             : const sal_Int32 IMAGE_SIZE_LARGE          = 26;
      69             : const sal_Int16 MAX_IMAGETYPE_VALUE       = ::com::sun::star::ui::ImageType::SIZE_LARGE;
      70             : 
      71             : static const char   IMAGE_FOLDER[]        = "images";
      72             : static const char   BITMAPS_FOLDER[]      = "Bitmaps";
      73             : 
      74             : static const char   ModuleImageList[]     = "private:resource/images/moduleimages";
      75             : 
      76             : static const char*  IMAGELIST_XML_FILE[]  =
      77             : {
      78             :     "sc_imagelist.xml",
      79             :     "lc_imagelist.xml"
      80             : };
      81             : 
      82             : static const char*  BITMAP_FILE_NAMES[]   =
      83             : {
      84             :     "sc_userimages.png",
      85             :     "lc_userimages.png"
      86             : };
      87             : 
      88             : namespace framework
      89             : {
      90             :     static GlobalImageList*     pGlobalImageList = 0;
      91             :     static const char* ImageType_Prefixes[ImageType_COUNT] =
      92             :     {
      93             :         "cmd/sc_",
      94             :         "cmd/lc_"
      95             :     };
      96             : 
      97             : typedef GraphicNameAccess CmdToXGraphicNameAccess;
      98             : 
      99             : namespace
     100             : {
     101             :     class theGlobalImageListMutex
     102             :         : public rtl::Static<osl::Mutex, theGlobalImageListMutex> {};
     103             : }
     104             : 
     105       71341 : static osl::Mutex& getGlobalImageListMutex()
     106             : {
     107       71341 :     return theGlobalImageListMutex::get();
     108             : }
     109             : 
     110          63 : static GlobalImageList* getGlobalImageList( const uno::Reference< uno::XComponentContext >& rxContext )
     111             : {
     112          63 :     osl::MutexGuard guard( getGlobalImageListMutex() );
     113             : 
     114          63 :     if ( pGlobalImageList == 0 )
     115          47 :         pGlobalImageList = new GlobalImageList( rxContext );
     116             : 
     117          63 :     return pGlobalImageList;
     118             : }
     119             : 
     120         270 : static OUString getCanonicalName( const OUString& rFileName )
     121             : {
     122         270 :     bool               bRemoveSlash( true );
     123         270 :     sal_Int32          nLength = rFileName.getLength();
     124         270 :     const sal_Unicode* pString = rFileName.getStr();
     125             : 
     126         270 :     OUStringBuffer aBuf( nLength );
     127       18360 :     for ( sal_Int32 i = 0; i < nLength; i++ )
     128             :     {
     129       18090 :         const sal_Unicode c = pString[i];
     130       18090 :         switch ( c )
     131             :         {
     132             :             // map forbidden characters to escape
     133           0 :             case '/' : if ( !bRemoveSlash )
     134           0 :                          aBuf.appendAscii( "%2f" );
     135           0 :                        break;
     136           0 :             case '\\': aBuf.appendAscii( "%5c" ); bRemoveSlash = false; break;
     137         540 :             case ':' : aBuf.appendAscii( "%3a" ); bRemoveSlash = false; break;
     138           0 :             case '*' : aBuf.appendAscii( "%2a" ); bRemoveSlash = false; break;
     139         270 :             case '?' : aBuf.appendAscii( "%3f" ); bRemoveSlash = false; break;
     140           0 :             case '<' : aBuf.appendAscii( "%3c" ); bRemoveSlash = false; break;
     141           0 :             case '>' : aBuf.appendAscii( "%3e" ); bRemoveSlash = false; break;
     142           0 :             case '|' : aBuf.appendAscii( "%7c" ); bRemoveSlash = false; break;
     143       17280 :             default: aBuf.append( c ); bRemoveSlash = false;
     144             :         }
     145             :     }
     146         270 :     return aBuf.makeStringAndClear();
     147             : }
     148             : 
     149         110 : CmdImageList::CmdImageList( const uno::Reference< uno::XComponentContext >& rxContext, const OUString& aModuleIdentifier ) :
     150             :     m_bVectorInit( false ),
     151             :     m_aModuleIdentifier( aModuleIdentifier ),
     152             :     m_xContext( rxContext ),
     153         110 :     m_sIconTheme( SvtMiscOptions().GetIconTheme() )
     154             : {
     155         330 :     for ( sal_Int32 n=0; n < ImageType_COUNT; n++ )
     156         220 :         m_pImageList[n] = 0;
     157         110 : }
     158             : 
     159         278 : CmdImageList::~CmdImageList()
     160             : {
     161         324 :     for ( sal_Int32 n=0; n < ImageType_COUNT; n++ )
     162         216 :         delete m_pImageList[n];
     163         170 : }
     164             : 
     165      162182 : void CmdImageList::impl_fillCommandToImageNameMap()
     166             : {
     167             :     SAL_INFO( "fwk", "framework: CmdImageList::impl_fillCommandToImageNameMap" );
     168             : 
     169      162182 :     if ( !m_bVectorInit )
     170             :     {
     171         107 :         const OUString aCommandImageList( UICOMMANDDESCRIPTION_NAMEACCESS_COMMANDIMAGELIST );
     172         214 :         Sequence< OUString > aCmdImageSeq;
     173         214 :         uno::Reference< XNameAccess > xCmdDesc = frame::theUICommandDescription::get( m_xContext );
     174             : 
     175         107 :         if ( !m_aModuleIdentifier.isEmpty() )
     176             :         {
     177             :             // If we have a module identifier - use to retrieve the command image name list from it.
     178             :             // Otherwise we will use the global command image list
     179             :             try
     180             :             {
     181          63 :                 xCmdDesc->getByName( m_aModuleIdentifier ) >>= xCmdDesc;
     182          63 :                 if ( xCmdDesc.is() )
     183          63 :                     xCmdDesc->getByName( aCommandImageList ) >>= aCmdImageSeq;
     184             :             }
     185           0 :             catch ( const NoSuchElementException& )
     186             :             {
     187             :                 // Module unknown we will work with an empty command image list!
     188      162182 :                 return;
     189             :             }
     190             :         }
     191             : 
     192         107 :         if ( xCmdDesc.is() )
     193             :         {
     194             :             try
     195             :             {
     196         107 :                 xCmdDesc->getByName( aCommandImageList ) >>= aCmdImageSeq;
     197             :             }
     198           0 :             catch ( const NoSuchElementException& )
     199             :             {
     200             :             }
     201           0 :             catch ( const WrappedTargetException& )
     202             :             {
     203             :             }
     204             :         }
     205             : 
     206             :         // We have to map commands which uses special characters like '/',':','?','\','<'.'>','|'
     207         214 :         OUString aExt = ".png";
     208         107 :         m_aImageCommandNameVector.resize(aCmdImageSeq.getLength() );
     209         107 :         m_aImageNameVector.resize( aCmdImageSeq.getLength() );
     210             : 
     211             :         ::std::copy( aCmdImageSeq.begin(), aCmdImageSeq.end(),
     212         107 :                      m_aImageCommandNameVector.begin() );
     213             : 
     214             :         // Create a image name vector that must be provided to the vcl imagelist. We also need
     215             :         // a command to image name map to speed up access time for image retrieval.
     216         214 :         OUString aUNOString( ".uno:" );
     217         214 :         OUString aEmptyString;
     218         107 :         const sal_uInt32 nCount = m_aImageCommandNameVector.size();
     219       32770 :         for ( sal_uInt32 i = 0; i < nCount; i++ )
     220             :         {
     221       32663 :             OUString aCommandName( m_aImageCommandNameVector[i] );
     222       65326 :             OUString aImageName;
     223             : 
     224       32663 :             if ( aCommandName.indexOf( aUNOString ) != 0 )
     225             :             {
     226           0 :                 INetURLObject aUrlObject( aCommandName, INetURLObject::ENCODE_ALL );
     227           0 :                 aImageName = aUrlObject.GetURLPath();
     228           0 :                 aImageName = getCanonicalName( aImageName ); // convert to valid filename
     229             :             }
     230             :             else
     231             :             {
     232             :                 // just remove the schema
     233       32663 :                 if ( aCommandName.getLength() > 5 )
     234       32663 :                     aImageName = aCommandName.copy( 5 );
     235             :                 else
     236           0 :                     aImageName = aEmptyString;
     237             : 
     238             :                 // Search for query part.
     239       32663 :                 if ( aImageName.indexOf('?') != -1 )
     240         270 :                     aImageName = getCanonicalName( aImageName ); // convert to valid filename
     241             :             }
     242             :             // Image names are not case-dependent. Always use lower case characters to
     243             :             // reflect this.
     244       32663 :             aImageName += aExt;
     245       32663 :             aImageName = aImageName.toAsciiLowerCase();
     246             : 
     247       32663 :             m_aImageNameVector[i] = aImageName;
     248       32663 :             m_aCommandToImageNameMap.insert( CommandToImageNameMap::value_type( aCommandName, aImageName ));
     249       32663 :         }
     250             : 
     251         214 :         m_bVectorInit = true;
     252             :     }
     253             : }
     254             : 
     255       74451 : ImageList* CmdImageList::impl_getImageList( sal_Int16 nImageType )
     256             : {
     257       74451 :     SvtMiscOptions aMiscOptions;
     258             : 
     259      148902 :     const OUString& rIconTheme = aMiscOptions.GetIconTheme();
     260       74451 :     if ( rIconTheme != m_sIconTheme )
     261             :     {
     262           0 :         m_sIconTheme = rIconTheme;
     263           0 :         for ( sal_Int32 n=0; n < ImageType_COUNT; n++ )
     264           0 :             delete m_pImageList[n], m_pImageList[n] = NULL;
     265             :     }
     266             : 
     267       74451 :     if ( !m_pImageList[nImageType] )
     268             :     {
     269         108 :         m_pImageList[nImageType] = new ImageList( m_aImageNameVector,
     270         216 :                                                   OUString::createFromAscii( ImageType_Prefixes[nImageType] ) );
     271             :     }
     272             : 
     273      148902 :     return m_pImageList[nImageType];
     274             : }
     275             : 
     276             : 
     277             : 
     278      162182 : Image CmdImageList::getImageFromCommandURL( sal_Int16 nImageType, const OUString& rCommandURL )
     279             : {
     280      162182 :     impl_fillCommandToImageNameMap();
     281      162182 :     CommandToImageNameMap::const_iterator pIter = m_aCommandToImageNameMap.find( rCommandURL );
     282      162182 :     if ( pIter != m_aCommandToImageNameMap.end() )
     283             :     {
     284       74451 :         ImageList* pImageList = impl_getImageList( nImageType );
     285       74451 :         return pImageList->GetImage( pIter->second );
     286             :     }
     287             : 
     288       87731 :     return Image();
     289             : }
     290             : 
     291           0 : bool CmdImageList::hasImage( sal_Int16 /*nImageType*/, const OUString& rCommandURL )
     292             : {
     293           0 :     impl_fillCommandToImageNameMap();
     294           0 :     CommandToImageNameMap::const_iterator pIter = m_aCommandToImageNameMap.find( rCommandURL );
     295           0 :     if ( pIter != m_aCommandToImageNameMap.end() )
     296           0 :         return true;
     297             :     else
     298           0 :         return false;
     299             : }
     300             : 
     301           0 : ::std::vector< OUString >& CmdImageList::getImageNames()
     302             : {
     303           0 :     return impl_getImageNameVector();
     304             : }
     305             : 
     306           0 : ::std::vector< OUString >& CmdImageList::getImageCommandNames()
     307             : {
     308           0 :     return impl_getImageCommandNameVector();
     309             : }
     310             : 
     311          47 : GlobalImageList::GlobalImageList( const uno::Reference< uno::XComponentContext >& rxContext ) :
     312          47 :     CmdImageList( rxContext, OUString() )
     313             : {
     314          47 : }
     315             : 
     316         138 : GlobalImageList::~GlobalImageList()
     317             : {
     318          46 :     osl::MutexGuard guard( getGlobalImageListMutex() );
     319             :     // remove global pointer as we destroy the object now
     320          46 :     pGlobalImageList = 0;
     321          92 : }
     322             : 
     323       71232 : Image GlobalImageList::getImageFromCommandURL( sal_Int16 nImageType, const OUString& rCommandURL )
     324             : {
     325       71232 :     osl::MutexGuard guard( getGlobalImageListMutex() );
     326       71232 :     return CmdImageList::getImageFromCommandURL( nImageType, rCommandURL );
     327             : }
     328             : 
     329           0 : bool GlobalImageList::hasImage( sal_Int16 nImageType, const OUString& rCommandURL )
     330             : {
     331           0 :     osl::MutexGuard guard( getGlobalImageListMutex() );
     332           0 :     return CmdImageList::hasImage( nImageType, rCommandURL );
     333             : }
     334             : 
     335           0 : ::std::vector< OUString >& GlobalImageList::getImageNames()
     336             : {
     337           0 :     osl::MutexGuard guard( getGlobalImageListMutex() );
     338           0 :     return impl_getImageNameVector();
     339             : }
     340             : 
     341           0 : ::std::vector< OUString >& GlobalImageList::getImageCommandNames()
     342             : {
     343           0 :     osl::MutexGuard guard( getGlobalImageListMutex() );
     344           0 :     return impl_getImageCommandNameVector();
     345             : }
     346             : 
     347           0 : static bool implts_checkAndScaleGraphic( uno::Reference< XGraphic >& rOutGraphic, const uno::Reference< XGraphic >& rInGraphic, sal_Int16 nImageType )
     348             : {
     349           0 :     static Size   aNormSize( IMAGE_SIZE_NORMAL, IMAGE_SIZE_NORMAL );
     350           0 :     static Size   aLargeSize( IMAGE_SIZE_LARGE, IMAGE_SIZE_LARGE );
     351             : 
     352           0 :     if ( !rInGraphic.is() )
     353             :     {
     354           0 :         rOutGraphic = Image().GetXGraphic();
     355           0 :         return false;
     356             :     }
     357             : 
     358             :     // Check size and scale it
     359           0 :     Image  aImage( rInGraphic );
     360           0 :     Size   aSize = aImage.GetSizePixel();
     361           0 :     bool   bMustScale( false );
     362             : 
     363           0 :     if ( nImageType == ImageType_Color_Large )
     364           0 :         bMustScale = ( aSize != aLargeSize );
     365             :     else
     366           0 :         bMustScale = ( aSize != aNormSize );
     367             : 
     368           0 :     if ( bMustScale )
     369             :     {
     370           0 :         BitmapEx aBitmap = aImage.GetBitmapEx();
     371           0 :         aBitmap.Scale( aNormSize );
     372           0 :         aImage = Image( aBitmap );
     373           0 :         rOutGraphic = aImage.GetXGraphic();
     374             :     }
     375             :     else
     376           0 :         rOutGraphic = rInGraphic;
     377           0 :     return true;
     378             : }
     379             : 
     380       75586 : static sal_Int16 implts_convertImageTypeToIndex( sal_Int16 nImageType )
     381             : {
     382       75586 :     sal_Int16 nIndex( 0 );
     383       75586 :     if ( nImageType & ::com::sun::star::ui::ImageType::SIZE_LARGE )
     384          20 :         nIndex += 1;
     385       75586 :     return nIndex;
     386             : }
     387             : 
     388       75586 : ImageList* ImageManagerImpl::implts_getUserImageList( ImageType nImageType )
     389             : {
     390       75586 :     SolarMutexGuard g;
     391       75586 :     if ( !m_pUserImageList[nImageType] )
     392         650 :         implts_loadUserImages( nImageType, m_xUserImageStorage, m_xUserBitmapsStorage );
     393             : 
     394       75586 :     return m_pUserImageList[nImageType];
     395             : }
     396             : 
     397        3326 : void ImageManagerImpl::implts_initialize()
     398             : {
     399             :     // Initialize the top-level structures with the storage data
     400        3326 :     if ( m_xUserConfigStorage.is() )
     401             :     {
     402        3295 :         long nModes = m_bReadOnly ? ElementModes::READ : ElementModes::READWRITE;
     403             : 
     404             :         try
     405             :         {
     406        9885 :             m_xUserImageStorage = m_xUserConfigStorage->openStorageElement( OUString(IMAGE_FOLDER ),
     407        6590 :                                                                             nModes );
     408        3295 :             if ( m_xUserImageStorage.is() )
     409             :             {
     410        9885 :                 m_xUserBitmapsStorage = m_xUserImageStorage->openStorageElement( OUString(BITMAPS_FOLDER ),
     411        6590 :                                                                                  nModes );
     412             :             }
     413             :         }
     414           0 :         catch ( const ::com::sun::star::container::NoSuchElementException& )
     415             :         {
     416             :         }
     417           0 :         catch ( const ::com::sun::star::embed::InvalidStorageException& )
     418             :         {
     419             :         }
     420           0 :         catch ( const ::com::sun::star::lang::IllegalArgumentException& )
     421             :         {
     422             :         }
     423           0 :         catch ( const ::com::sun::star::io::IOException& )
     424             :         {
     425             :         }
     426           0 :         catch ( const ::com::sun::star::embed::StorageWrappedTargetException& )
     427             :         {
     428             :         }
     429             :     }
     430        3326 : }
     431             : 
     432         650 : bool ImageManagerImpl::implts_loadUserImages(
     433             :     ImageType nImageType,
     434             :     const uno::Reference< XStorage >& xUserImageStorage,
     435             :     const uno::Reference< XStorage >& xUserBitmapsStorage )
     436             : {
     437         650 :     SolarMutexGuard g;
     438             : 
     439         650 :     if ( xUserImageStorage.is() && xUserBitmapsStorage.is() )
     440             :     {
     441             :         try
     442             :         {
     443         648 :             uno::Reference< XStream > xStream = xUserImageStorage->openStreamElement( OUString::createFromAscii( IMAGELIST_XML_FILE[nImageType] ),
     444        1296 :                                                                                       ElementModes::READ );
     445           0 :             uno::Reference< XInputStream > xInputStream = xStream->getInputStream();
     446             : 
     447           0 :             ImageListsDescriptor aUserImageListInfo;
     448             :             ImagesConfiguration::LoadImages( m_xContext,
     449             :                                              xInputStream,
     450           0 :                                              aUserImageListInfo );
     451           0 :             if (( aUserImageListInfo.pImageList != 0 ) &&
     452           0 :                 ( !aUserImageListInfo.pImageList->empty() ))
     453             :             {
     454           0 :                 ImageListItemDescriptor* pList = &aUserImageListInfo.pImageList->front();
     455           0 :                 sal_Int32 nCount = pList->pImageItemList->size();
     456           0 :                 std::vector< OUString > aUserImagesVector;
     457           0 :                 aUserImagesVector.reserve(nCount);
     458           0 :                 for ( sal_Int32 i=0; i < nCount; i++ )
     459             :                 {
     460           0 :                     const ImageItemDescriptor* pItem = &(*pList->pImageItemList)[i];
     461           0 :                     aUserImagesVector.push_back( pItem->aCommandURL );
     462             :                 }
     463             : 
     464           0 :                 uno::Reference< XStream > xBitmapStream = xUserBitmapsStorage->openStreamElement(
     465             :                                                         OUString::createFromAscii( BITMAP_FILE_NAMES[nImageType] ),
     466           0 :                                                         ElementModes::READ );
     467             : 
     468           0 :                 if ( xBitmapStream.is() )
     469             :                 {
     470           0 :                     BitmapEx aUserBitmap;
     471             :                     {
     472           0 :                         boost::scoped_ptr<SvStream> pSvStream(utl::UcbStreamHelper::CreateStream( xBitmapStream ));
     473           0 :                         vcl::PNGReader aPngReader( *pSvStream );
     474           0 :                         aUserBitmap = aPngReader.Read();
     475             :                     }
     476             : 
     477             :                     // Delete old image list and create a new one from the read bitmap
     478           0 :                     delete m_pUserImageList[nImageType];
     479           0 :                     m_pUserImageList[nImageType] = new ImageList();
     480           0 :                     m_pUserImageList[nImageType]->InsertFromHorizontalStrip
     481           0 :                         ( aUserBitmap, aUserImagesVector );
     482           0 :                     return true;
     483           0 :                 }
     484           0 :             }
     485             :         }
     486           0 :         catch ( const ::com::sun::star::container::NoSuchElementException& )
     487             :         {
     488             :         }
     489           0 :         catch ( const ::com::sun::star::embed::InvalidStorageException& )
     490             :         {
     491             :         }
     492           0 :         catch ( const ::com::sun::star::lang::IllegalArgumentException& )
     493             :         {
     494             :         }
     495         648 :         catch ( const ::com::sun::star::io::IOException& )
     496             :         {
     497             :         }
     498           0 :         catch ( const ::com::sun::star::embed::StorageWrappedTargetException& )
     499             :         {
     500             :         }
     501             :     }
     502             : 
     503             :     // Destroy old image list - create a new empty one
     504         650 :     delete m_pUserImageList[nImageType];
     505         650 :     m_pUserImageList[nImageType] = new ImageList;
     506             : 
     507         650 :     return true;
     508             : }
     509             : 
     510           0 : bool ImageManagerImpl::implts_storeUserImages(
     511             :     ImageType nImageType,
     512             :     const uno::Reference< XStorage >& xUserImageStorage,
     513             :     const uno::Reference< XStorage >& xUserBitmapsStorage )
     514             : {
     515           0 :     SolarMutexGuard g;
     516             : 
     517           0 :     if ( m_bModified )
     518             :     {
     519           0 :         ImageList* pImageList = implts_getUserImageList( nImageType );
     520           0 :         if ( pImageList->GetImageCount() > 0 )
     521             :         {
     522           0 :             ImageListsDescriptor aUserImageListInfo;
     523           0 :             aUserImageListInfo.pImageList = new ImageListDescriptor;
     524             : 
     525           0 :             ImageListItemDescriptor* pList = new ImageListItemDescriptor;
     526           0 :             aUserImageListInfo.pImageList->push_back( pList );
     527             : 
     528           0 :             pList->pImageItemList = new ImageItemListDescriptor;
     529           0 :             for ( sal_uInt16 i=0; i < pImageList->GetImageCount(); i++ )
     530             :             {
     531           0 :                 ImageItemDescriptor* pItem = new ::framework::ImageItemDescriptor;
     532             : 
     533           0 :                 pItem->nIndex = i;
     534           0 :                 pItem->aCommandURL = pImageList->GetImageName( i );
     535           0 :                 pList->pImageItemList->push_back( pItem );
     536             :             }
     537             : 
     538           0 :             pList->aURL = "Bitmaps/" + OUString::createFromAscii(BITMAP_FILE_NAMES[nImageType]);
     539             : 
     540           0 :             uno::Reference< XTransactedObject > xTransaction;
     541           0 :             uno::Reference< XOutputStream >     xOutputStream;
     542           0 :             uno::Reference< XStream > xStream = xUserImageStorage->openStreamElement( OUString::createFromAscii( IMAGELIST_XML_FILE[nImageType] ),
     543           0 :                                                                                       ElementModes::WRITE|ElementModes::TRUNCATE );
     544           0 :             if ( xStream.is() )
     545             :             {
     546             :                 uno::Reference< XStream > xBitmapStream =
     547           0 :                     xUserBitmapsStorage->openStreamElement( OUString::createFromAscii( BITMAP_FILE_NAMES[nImageType] ),
     548           0 :                                                             ElementModes::WRITE|ElementModes::TRUNCATE );
     549           0 :                 if ( xBitmapStream.is() )
     550             :                 {
     551             :                     {
     552           0 :                         boost::scoped_ptr<SvStream> pSvStream(utl::UcbStreamHelper::CreateStream( xBitmapStream ));
     553           0 :                         vcl::PNGWriter aPngWriter( pImageList->GetAsHorizontalStrip() );
     554           0 :                         aPngWriter.Write( *pSvStream );
     555             :                     }
     556             : 
     557             :                     // Commit user bitmaps storage
     558           0 :                     xTransaction = uno::Reference< XTransactedObject >( xUserBitmapsStorage, UNO_QUERY );
     559           0 :                     if ( xTransaction.is() )
     560           0 :                         xTransaction->commit();
     561             :                 }
     562             : 
     563           0 :                 xOutputStream = xStream->getOutputStream();
     564           0 :                 if ( xOutputStream.is() )
     565           0 :                     ImagesConfiguration::StoreImages( m_xContext, xOutputStream, aUserImageListInfo );
     566             : 
     567             :                 // Commit user image storage
     568           0 :                 xTransaction = uno::Reference< XTransactedObject >( xUserImageStorage, UNO_QUERY );
     569           0 :                 if ( xTransaction.is() )
     570           0 :                     xTransaction->commit();
     571             :             }
     572             : 
     573           0 :             return true;
     574             :         }
     575             :         else
     576             :         {
     577             :             // Remove the streams from the storage, if we have no data. We have to catch
     578             :             // the NoSuchElementException as it can be possible that there is no stream at all!
     579             :             try
     580             :             {
     581           0 :                 xUserImageStorage->removeElement( OUString::createFromAscii( IMAGELIST_XML_FILE[nImageType] ));
     582             :             }
     583           0 :             catch ( const ::com::sun::star::container::NoSuchElementException& )
     584             :             {
     585             :             }
     586             : 
     587             :             try
     588             :             {
     589           0 :                 xUserBitmapsStorage->removeElement( OUString::createFromAscii( BITMAP_FILE_NAMES[nImageType] ));
     590             :             }
     591           0 :             catch ( const ::com::sun::star::container::NoSuchElementException& )
     592             :             {
     593             :             }
     594             : 
     595           0 :             uno::Reference< XTransactedObject > xTransaction;
     596             : 
     597             :             // Commit user image storage
     598           0 :             xTransaction = uno::Reference< XTransactedObject >( xUserImageStorage, UNO_QUERY );
     599           0 :             if ( xTransaction.is() )
     600           0 :                 xTransaction->commit();
     601             : 
     602             :             // Commit user bitmaps storage
     603           0 :             xTransaction = uno::Reference< XTransactedObject >( xUserBitmapsStorage, UNO_QUERY );
     604           0 :             if ( xTransaction.is() )
     605           0 :                 xTransaction->commit();
     606             : 
     607           0 :             return true;
     608             :         }
     609             :     }
     610             : 
     611           0 :     return false;
     612             : }
     613             : 
     614       38033 : const rtl::Reference< GlobalImageList >& ImageManagerImpl::implts_getGlobalImageList()
     615             : {
     616       38033 :     SolarMutexGuard g;
     617             : 
     618       38033 :     if ( !m_pGlobalImageList.is() )
     619          63 :         m_pGlobalImageList = getGlobalImageList( m_xContext );
     620       38033 :     return m_pGlobalImageList;
     621             : }
     622             : 
     623       38033 : CmdImageList* ImageManagerImpl::implts_getDefaultImageList()
     624             : {
     625       38033 :     SolarMutexGuard g;
     626             : 
     627       38033 :     if ( !m_pDefaultImageList )
     628          63 :         m_pDefaultImageList = new CmdImageList( m_xContext, m_aModuleIdentifier );
     629             : 
     630       38033 :     return m_pDefaultImageList;
     631             : }
     632             : 
     633        3306 : ImageManagerImpl::ImageManagerImpl( const uno::Reference< uno::XComponentContext >& rxContext,::cppu::OWeakObject* pOwner,bool _bUseGlobal ) :
     634             :     m_xContext( rxContext )
     635             :     , m_pOwner(pOwner)
     636             :     , m_pDefaultImageList( 0 )
     637             :     , m_aXMLPostfix( ".xml" )
     638             :     , m_aResourceString( ModuleImageList )
     639             :     , m_aListenerContainer( m_mutex )
     640             :     , m_bUseGlobal(_bUseGlobal)
     641             :     , m_bReadOnly( true )
     642             :     , m_bInitialized( false )
     643             :     , m_bModified( false )
     644             :     , m_bConfigRead( false )
     645        3306 :     , m_bDisposed( false )
     646             : {
     647        9918 :     for ( sal_Int32 n=0; n < ImageType_COUNT; n++ )
     648             :     {
     649        6612 :         m_pUserImageList[n] = 0;
     650        6612 :         m_bUserImageListModified[n] = false;
     651             :     }
     652        3306 : }
     653             : 
     654        6596 : ImageManagerImpl::~ImageManagerImpl()
     655             : {
     656        3298 :     clear();
     657        3298 : }
     658             : 
     659         125 : void ImageManagerImpl::dispose()
     660             : {
     661         125 :     uno::Reference< uno::XInterface > xOwner(static_cast< OWeakObject* >(m_pOwner));
     662         250 :     css::lang::EventObject aEvent( xOwner );
     663         125 :     m_aListenerContainer.disposeAndClear( aEvent );
     664             : 
     665             :     {
     666         125 :         SolarMutexGuard g;
     667         125 :         m_xUserConfigStorage.clear();
     668         125 :         m_xUserImageStorage.clear();
     669         125 :         m_xUserRootCommit.clear();
     670         125 :         m_bConfigRead = false;
     671         125 :         m_bModified = false;
     672         125 :         m_bDisposed = true;
     673             : 
     674             :         // delete user and default image list on dispose
     675         375 :         for ( sal_Int32 n=0; n < ImageType_COUNT; n++ )
     676             :         {
     677         250 :             delete m_pUserImageList[n];
     678         250 :             m_pUserImageList[n] = 0;
     679             :         }
     680         125 :         delete m_pDefaultImageList;
     681         125 :         m_pDefaultImageList = 0;
     682         125 :     }
     683             : 
     684         125 : }
     685           0 : void ImageManagerImpl::addEventListener( const uno::Reference< XEventListener >& xListener ) throw (::com::sun::star::uno::RuntimeException)
     686             : {
     687             :     {
     688           0 :         SolarMutexGuard g;
     689             : 
     690             :         /* SAFE AREA ----------------------------------------------------------------------------------------------- */
     691           0 :         if ( m_bDisposed )
     692           0 :             throw DisposedException();
     693             :     }
     694             : 
     695           0 :     m_aListenerContainer.addInterface( cppu::UnoType<XEventListener>::get(), xListener );
     696           0 : }
     697             : 
     698           0 : void ImageManagerImpl::removeEventListener( const uno::Reference< XEventListener >& xListener ) throw (::com::sun::star::uno::RuntimeException)
     699             : {
     700             :     /* SAFE AREA ----------------------------------------------------------------------------------------------- */
     701           0 :     m_aListenerContainer.removeInterface( cppu::UnoType<XEventListener>::get(), xListener );
     702           0 : }
     703             : 
     704             : // XInitialization
     705        3305 : void ImageManagerImpl::initialize( const Sequence< Any >& aArguments )
     706             : {
     707        3305 :     SolarMutexGuard g;
     708             : 
     709        3305 :     if ( !m_bInitialized )
     710             :     {
     711       10040 :         for ( sal_Int32 n = 0; n < aArguments.getLength(); n++ )
     712             :         {
     713        6735 :             PropertyValue aPropValue;
     714        6735 :             if ( aArguments[n] >>= aPropValue )
     715             :             {
     716        6735 :                 if ( aPropValue.Name == "UserConfigStorage" )
     717             :                 {
     718        3305 :                     aPropValue.Value >>= m_xUserConfigStorage;
     719             :                 }
     720        3430 :                 else if ( aPropValue.Name == "ModuleIdentifier" )
     721             :                 {
     722        3305 :                     aPropValue.Value >>= m_aModuleIdentifier;
     723             :                 }
     724         125 :                 else if ( aPropValue.Name == "UserRootCommit" )
     725             :                 {
     726         125 :                     aPropValue.Value >>= m_xUserRootCommit;
     727             :                 }
     728             :             }
     729        6735 :         }
     730             : 
     731        3305 :         if ( m_xUserConfigStorage.is() )
     732             :         {
     733        3274 :             uno::Reference< XPropertySet > xPropSet( m_xUserConfigStorage, UNO_QUERY );
     734        3274 :             if ( xPropSet.is() )
     735             :             {
     736        3274 :                 long nOpenMode = 0;
     737        3274 :                 if ( xPropSet->getPropertyValue("OpenMode") >>= nOpenMode )
     738        3274 :                     m_bReadOnly = !( nOpenMode & ElementModes::WRITE );
     739        3274 :             }
     740             :         }
     741             : 
     742        3305 :         implts_initialize();
     743             : 
     744        3305 :         m_bInitialized = true;
     745        3305 :     }
     746        3305 : }
     747             : 
     748             : // XImageManagerImpl
     749           0 : void ImageManagerImpl::reset()
     750             : throw (::com::sun::star::uno::RuntimeException, lang::IllegalAccessException)
     751             : {
     752           0 :     SolarMutexGuard g;
     753             : 
     754             :     /* SAFE AREA ----------------------------------------------------------------------------------------------- */
     755           0 :     if ( m_bDisposed )
     756           0 :         throw DisposedException();
     757             : 
     758           0 :     std::vector< OUString > aUserImageNames;
     759             : 
     760           0 :     for ( sal_Int32 i = 0; i < ImageType_COUNT; i++ )
     761             :     {
     762           0 :         aUserImageNames.clear();
     763           0 :         ImageList* pImageList = implts_getUserImageList( ImageType(i));
     764           0 :         pImageList->GetImageNames( aUserImageNames );
     765             : 
     766           0 :         Sequence< OUString > aRemoveList( aUserImageNames.size() );
     767           0 :         const sal_uInt32 nCount = aUserImageNames.size();
     768           0 :         for ( sal_uInt32 j = 0; j < nCount; j++ )
     769           0 :             aRemoveList[j] = aUserImageNames[j];
     770             : 
     771             :         // Remove images
     772           0 :         removeImages( sal_Int16( i ), aRemoveList );
     773           0 :         m_bUserImageListModified[i] = true;
     774           0 :     }
     775             : 
     776           0 :     m_bModified = true;
     777           0 : }
     778             : 
     779           0 : Sequence< OUString > ImageManagerImpl::getAllImageNames( ::sal_Int16 nImageType )
     780             : throw (::com::sun::star::uno::RuntimeException)
     781             : {
     782           0 :     SolarMutexGuard g;
     783             : 
     784             :     /* SAFE AREA ----------------------------------------------------------------------------------------------- */
     785           0 :     if ( m_bDisposed )
     786           0 :         throw DisposedException();
     787             : 
     788           0 :     ImageNameMap aImageCmdNameMap;
     789             : 
     790           0 :     sal_Int16 nIndex = implts_convertImageTypeToIndex( nImageType );
     791             : 
     792           0 :     sal_uInt32 i( 0 );
     793           0 :     if ( m_bUseGlobal )
     794             :     {
     795           0 :         rtl::Reference< GlobalImageList > rGlobalImageList = implts_getGlobalImageList();
     796             : 
     797           0 :         const std::vector< OUString >& rGlobalImageNameVector = rGlobalImageList->getImageCommandNames();
     798           0 :         const sal_uInt32 nGlobalCount = rGlobalImageNameVector.size();
     799           0 :         for ( i = 0; i < nGlobalCount; i++ )
     800           0 :             aImageCmdNameMap.insert( ImageNameMap::value_type( rGlobalImageNameVector[i], sal_True ));
     801             : 
     802           0 :         const std::vector< OUString >& rModuleImageNameVector = implts_getDefaultImageList()->getImageCommandNames();
     803           0 :         const sal_uInt32 nModuleCount = rModuleImageNameVector.size();
     804           0 :         for ( i = 0; i < nModuleCount; i++ )
     805           0 :             aImageCmdNameMap.insert( ImageNameMap::value_type( rModuleImageNameVector[i], sal_True ));
     806             :     }
     807             : 
     808           0 :     ImageList* pImageList = implts_getUserImageList( ImageType( nIndex ));
     809           0 :     std::vector< OUString > rUserImageNames;
     810           0 :     pImageList->GetImageNames( rUserImageNames );
     811           0 :     const sal_uInt32 nUserCount = rUserImageNames.size();
     812           0 :     for ( i = 0; i < nUserCount; i++ )
     813           0 :         aImageCmdNameMap.insert( ImageNameMap::value_type( rUserImageNames[i], sal_True ));
     814             : 
     815           0 :     Sequence< OUString > aImageNameSeq( aImageCmdNameMap.size() );
     816           0 :     ImageNameMap::const_iterator pIter;
     817           0 :     i = 0;
     818           0 :     for ( pIter = aImageCmdNameMap.begin(); pIter != aImageCmdNameMap.end(); ++pIter )
     819           0 :         aImageNameSeq[i++] = pIter->first;
     820             : 
     821           0 :     return aImageNameSeq;
     822             : }
     823             : 
     824           0 : bool ImageManagerImpl::hasImage( ::sal_Int16 nImageType, const OUString& aCommandURL )
     825             : throw (::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException)
     826             : {
     827           0 :     SolarMutexGuard g;
     828             : 
     829             :     /* SAFE AREA ----------------------------------------------------------------------------------------------- */
     830           0 :     if ( m_bDisposed )
     831           0 :         throw DisposedException();
     832             : 
     833           0 :     if (( nImageType < 0 ) || ( nImageType > MAX_IMAGETYPE_VALUE ))
     834           0 :         throw IllegalArgumentException();
     835             : 
     836           0 :     sal_Int16 nIndex = implts_convertImageTypeToIndex( nImageType );
     837           0 :     if ( m_bUseGlobal && implts_getGlobalImageList()->hasImage( nIndex, aCommandURL ))
     838           0 :         return true;
     839             :     else
     840             :     {
     841           0 :         if ( m_bUseGlobal && implts_getDefaultImageList()->hasImage( nIndex, aCommandURL ))
     842           0 :             return true;
     843             :         else
     844             :         {
     845             :             // User layer
     846           0 :             ImageList* pImageList = implts_getUserImageList( ImageType( nIndex ));
     847           0 :             if ( pImageList )
     848           0 :                 return ( pImageList->GetImagePos( aCommandURL ) != IMAGELIST_IMAGE_NOTFOUND );
     849             :         }
     850             :     }
     851             : 
     852           0 :     return false;
     853             : }
     854             : 
     855       75586 : Sequence< uno::Reference< XGraphic > > ImageManagerImpl::getImages(
     856             :     ::sal_Int16 nImageType,
     857             :     const Sequence< OUString >& aCommandURLSequence )
     858             : throw ( ::com::sun::star::lang::IllegalArgumentException, ::com::sun::star::uno::RuntimeException )
     859             : {
     860       75586 :     SolarMutexGuard g;
     861             : 
     862             :     /* SAFE AREA ----------------------------------------------------------------------------------------------- */
     863       75586 :     if ( m_bDisposed )
     864           0 :         throw DisposedException();
     865             : 
     866       75586 :     if (( nImageType < 0 ) || ( nImageType > MAX_IMAGETYPE_VALUE ))
     867           0 :         throw IllegalArgumentException();
     868             : 
     869       75586 :     Sequence< uno::Reference< XGraphic > > aGraphSeq( aCommandURLSequence.getLength() );
     870             : 
     871       75586 :     const OUString* aStrArray = aCommandURLSequence.getConstArray();
     872             : 
     873       75586 :     sal_Int16                         nIndex            = implts_convertImageTypeToIndex( nImageType );
     874      151172 :     rtl::Reference< GlobalImageList > rGlobalImageList;
     875       75586 :     CmdImageList*                     pDefaultImageList = NULL;
     876       75586 :     if ( m_bUseGlobal )
     877             :     {
     878       38033 :         rGlobalImageList  = implts_getGlobalImageList();
     879       38033 :         pDefaultImageList = implts_getDefaultImageList();
     880             :     }
     881       75586 :     ImageList*                        pUserImageList    = implts_getUserImageList( ImageType( nIndex ));
     882             : 
     883             :     // We have to search our image list in the following order:
     884             :     // 1. user image list (read/write)
     885             :     // 2. module image list (read)
     886             :     // 3. global image list (read)
     887      256253 :     for ( sal_Int32 n = 0; n < aCommandURLSequence.getLength(); n++ )
     888             :     {
     889      180670 :         Image aImage = pUserImageList->GetImage( aStrArray[n] );
     890      180670 :         if ( !aImage && m_bUseGlobal )
     891             :         {
     892       90950 :             aImage = pDefaultImageList->getImageFromCommandURL( nIndex, aStrArray[n] );
     893       90950 :             if ( !aImage )
     894       71232 :                 aImage = rGlobalImageList->getImageFromCommandURL( nIndex, aStrArray[n] );
     895             :         }
     896             : 
     897      180670 :         aGraphSeq[n] = aImage.GetXGraphic();
     898      180670 :     }
     899             : 
     900      151169 :     return aGraphSeq;
     901             : }
     902             : 
     903           0 : void ImageManagerImpl::replaceImages(
     904             :     ::sal_Int16 nImageType,
     905             :     const Sequence< OUString >& aCommandURLSequence,
     906             :     const Sequence< uno::Reference< XGraphic > >& aGraphicsSequence )
     907             : throw (css::lang::IllegalArgumentException,
     908             :        css::lang::IllegalAccessException,
     909             :        css::uno::RuntimeException,
     910             :        std::exception)
     911             : {
     912           0 :     CmdToXGraphicNameAccess* pInsertedImages( 0 );
     913           0 :     CmdToXGraphicNameAccess* pReplacedImages( 0 );
     914             : 
     915             :     {
     916           0 :         SolarMutexGuard g;
     917             : 
     918             :         /* SAFE AREA ----------------------------------------------------------------------------------------------- */
     919           0 :         if ( m_bDisposed )
     920           0 :             throw DisposedException();
     921             : 
     922           0 :         if (( aCommandURLSequence.getLength() != aGraphicsSequence.getLength() ) ||
     923           0 :             (( nImageType < 0 ) || ( nImageType > MAX_IMAGETYPE_VALUE )))
     924           0 :             throw IllegalArgumentException();
     925             : 
     926           0 :         if ( m_bReadOnly )
     927           0 :             throw IllegalAccessException();
     928             : 
     929           0 :         sal_Int16 nIndex = implts_convertImageTypeToIndex( nImageType );
     930           0 :         ImageList* pImageList = implts_getUserImageList( ImageType( nIndex ));
     931             : 
     932           0 :         uno::Reference< XGraphic > xGraphic;
     933           0 :         for ( sal_Int32 i = 0; i < aCommandURLSequence.getLength(); i++ )
     934             :         {
     935             :             // Check size and scale. If we don't have any graphics ignore it
     936           0 :             if ( !implts_checkAndScaleGraphic( xGraphic, aGraphicsSequence[i], nIndex ))
     937           0 :                 continue;
     938             : 
     939           0 :             sal_uInt16 nPos = pImageList->GetImagePos( aCommandURLSequence[i] );
     940           0 :             if ( nPos == IMAGELIST_IMAGE_NOTFOUND )
     941             :             {
     942           0 :                 pImageList->AddImage(aCommandURLSequence[i], Image(xGraphic));
     943           0 :                 if ( !pInsertedImages )
     944           0 :                     pInsertedImages = new CmdToXGraphicNameAccess();
     945           0 :                 pInsertedImages->addElement( aCommandURLSequence[i], xGraphic );
     946             :             }
     947             :             else
     948             :             {
     949           0 :                 pImageList->ReplaceImage(aCommandURLSequence[i], Image(xGraphic));
     950           0 :                 if ( !pReplacedImages )
     951           0 :                     pReplacedImages = new CmdToXGraphicNameAccess();
     952           0 :                 pReplacedImages->addElement( aCommandURLSequence[i], xGraphic );
     953             :             }
     954             :         }
     955             : 
     956           0 :         if (( pInsertedImages != 0 ) || (  pReplacedImages != 0 ))
     957             :         {
     958           0 :             m_bModified = true;
     959           0 :             m_bUserImageListModified[nIndex] = true;
     960           0 :         }
     961             :     }
     962             : 
     963           0 :     uno::Reference< uno::XInterface > xOwner(static_cast< OWeakObject* >(m_pOwner));
     964             :     // Notify listeners
     965           0 :     if ( pInsertedImages != 0 )
     966             :     {
     967           0 :         ConfigurationEvent aInsertEvent;
     968           0 :         aInsertEvent.aInfo           <<= nImageType;
     969           0 :         aInsertEvent.Accessor        <<= xOwner;
     970           0 :         aInsertEvent.Source          = xOwner;
     971           0 :         aInsertEvent.ResourceURL     = m_aResourceString;
     972           0 :         aInsertEvent.Element         = uno::makeAny( uno::Reference< XNameAccess >(
     973           0 :                                         static_cast< OWeakObject *>( pInsertedImages ), UNO_QUERY ));
     974           0 :         implts_notifyContainerListener( aInsertEvent, NotifyOp_Insert );
     975             :     }
     976           0 :     if ( pReplacedImages != 0 )
     977             :     {
     978           0 :         ConfigurationEvent aReplaceEvent;
     979           0 :         aReplaceEvent.aInfo           <<= nImageType;
     980           0 :         aReplaceEvent.Accessor        <<= xOwner;
     981           0 :         aReplaceEvent.Source          = xOwner;
     982           0 :         aReplaceEvent.ResourceURL     = m_aResourceString;
     983           0 :         aReplaceEvent.ReplacedElement = Any();
     984           0 :         aReplaceEvent.Element         = uno::makeAny( uno::Reference< XNameAccess >(
     985           0 :                                             static_cast< OWeakObject *>( pReplacedImages ), UNO_QUERY ));
     986           0 :         implts_notifyContainerListener( aReplaceEvent, NotifyOp_Replace );
     987           0 :     }
     988           0 : }
     989             : 
     990           0 : void ImageManagerImpl::removeImages( ::sal_Int16 nImageType, const Sequence< OUString >& aCommandURLSequence )
     991             : throw ( ::com::sun::star::lang::IllegalArgumentException,
     992             :         ::com::sun::star::lang::IllegalAccessException,
     993             :         ::com::sun::star::uno::RuntimeException)
     994             : {
     995           0 :     CmdToXGraphicNameAccess* pRemovedImages( 0 );
     996           0 :     CmdToXGraphicNameAccess* pReplacedImages( 0 );
     997             : 
     998             :     {
     999           0 :         SolarMutexGuard g;
    1000             : 
    1001             :         /* SAFE AREA ----------------------------------------------------------------------------------------------- */
    1002           0 :         if ( m_bDisposed )
    1003           0 :             throw DisposedException();
    1004             : 
    1005           0 :         if (( nImageType < 0 ) || ( nImageType > MAX_IMAGETYPE_VALUE ))
    1006           0 :             throw IllegalArgumentException();
    1007             : 
    1008           0 :         if ( m_bReadOnly )
    1009           0 :             throw IllegalAccessException();
    1010             : 
    1011           0 :         sal_Int16 nIndex = implts_convertImageTypeToIndex( nImageType );
    1012           0 :         rtl::Reference< GlobalImageList > rGlobalImageList;
    1013           0 :         CmdImageList*                     pDefaultImageList = NULL;
    1014           0 :         if ( m_bUseGlobal )
    1015             :         {
    1016           0 :             rGlobalImageList  = implts_getGlobalImageList();
    1017           0 :             pDefaultImageList = implts_getDefaultImageList();
    1018             :         }
    1019           0 :         ImageList*                        pImageList        = implts_getUserImageList( ImageType( nIndex ));
    1020           0 :         uno::Reference< XGraphic >        xEmptyGraphic( Image().GetXGraphic() );
    1021             : 
    1022           0 :         for ( sal_Int32 i = 0; i < aCommandURLSequence.getLength(); i++ )
    1023             :         {
    1024           0 :             sal_uInt16 nPos = pImageList->GetImagePos( aCommandURLSequence[i] );
    1025           0 :             if ( nPos != IMAGELIST_IMAGE_NOTFOUND )
    1026             :             {
    1027           0 :                 Image aImage = pImageList->GetImage( nPos );
    1028           0 :                 sal_uInt16 nId   = pImageList->GetImageId( nPos );
    1029           0 :                 pImageList->RemoveImage( nId );
    1030             : 
    1031           0 :                 if ( m_bUseGlobal )
    1032             :                 {
    1033             :                     // Check, if we have a image in our module/global image list. If we find one =>
    1034             :                     // this is a replace instead of a remove operation!
    1035           0 :                     Image aNewImage = pDefaultImageList->getImageFromCommandURL( nIndex, aCommandURLSequence[i] );
    1036           0 :                     if ( !aNewImage )
    1037           0 :                         aNewImage = rGlobalImageList->getImageFromCommandURL( nIndex, aCommandURLSequence[i] );
    1038           0 :                     if ( !aNewImage )
    1039             :                     {
    1040           0 :                         if ( !pRemovedImages )
    1041           0 :                             pRemovedImages = new CmdToXGraphicNameAccess();
    1042           0 :                         pRemovedImages->addElement( aCommandURLSequence[i], xEmptyGraphic );
    1043             :                     }
    1044             :                     else
    1045             :                     {
    1046           0 :                         if ( !pReplacedImages )
    1047           0 :                             pReplacedImages = new CmdToXGraphicNameAccess();
    1048           0 :                         pReplacedImages->addElement( aCommandURLSequence[i], aNewImage.GetXGraphic() );
    1049           0 :                     }
    1050             :                 } // if ( m_bUseGlobal )
    1051             :                 else
    1052             :                 {
    1053           0 :                     if ( !pRemovedImages )
    1054           0 :                         pRemovedImages = new CmdToXGraphicNameAccess();
    1055           0 :                     pRemovedImages->addElement( aCommandURLSequence[i], xEmptyGraphic );
    1056           0 :                 }
    1057             :             }
    1058             :         }
    1059             : 
    1060           0 :         if (( pReplacedImages != 0 ) || ( pRemovedImages != 0 ))
    1061             :         {
    1062           0 :             m_bModified = true;
    1063           0 :             m_bUserImageListModified[nIndex] = true;
    1064           0 :         }
    1065             :     }
    1066             : 
    1067             :     // Notify listeners
    1068           0 :     uno::Reference< uno::XInterface > xOwner(static_cast< OWeakObject* >(m_pOwner));
    1069           0 :     if ( pRemovedImages != 0 )
    1070             :     {
    1071           0 :         ConfigurationEvent aRemoveEvent;
    1072           0 :         aRemoveEvent.aInfo           = uno::makeAny( nImageType );
    1073           0 :         aRemoveEvent.Accessor        = uno::makeAny( xOwner );
    1074           0 :         aRemoveEvent.Source          = xOwner;
    1075           0 :         aRemoveEvent.ResourceURL     = m_aResourceString;
    1076           0 :         aRemoveEvent.Element         = uno::makeAny( uno::Reference< XNameAccess >(
    1077           0 :                                             static_cast< OWeakObject *>( pRemovedImages ), UNO_QUERY ));
    1078           0 :         implts_notifyContainerListener( aRemoveEvent, NotifyOp_Remove );
    1079             :     }
    1080           0 :     if ( pReplacedImages != 0 )
    1081             :     {
    1082           0 :         ConfigurationEvent aReplaceEvent;
    1083           0 :         aReplaceEvent.aInfo           = uno::makeAny( nImageType );
    1084           0 :         aReplaceEvent.Accessor        = uno::makeAny( xOwner );
    1085           0 :         aReplaceEvent.Source          = xOwner;
    1086           0 :         aReplaceEvent.ResourceURL     = m_aResourceString;
    1087           0 :         aReplaceEvent.ReplacedElement = Any();
    1088           0 :         aReplaceEvent.Element         = uno::makeAny( uno::Reference< XNameAccess >(
    1089           0 :                                             static_cast< OWeakObject *>( pReplacedImages ), UNO_QUERY ));
    1090           0 :         implts_notifyContainerListener( aReplaceEvent, NotifyOp_Replace );
    1091           0 :     }
    1092           0 : }
    1093             : 
    1094           0 : void ImageManagerImpl::insertImages( ::sal_Int16 nImageType, const Sequence< OUString >& aCommandURLSequence, const Sequence< uno::Reference< XGraphic > >& aGraphicSequence )
    1095             : throw ( ::com::sun::star::container::ElementExistException,
    1096             :         ::com::sun::star::lang::IllegalArgumentException,
    1097             :         ::com::sun::star::lang::IllegalAccessException,
    1098             :         ::com::sun::star::uno::RuntimeException)
    1099             : {
    1100           0 :     replaceImages(nImageType,aCommandURLSequence,aGraphicSequence);
    1101           0 : }
    1102             : 
    1103             : // XUIConfigurationPersistence
    1104           0 : void ImageManagerImpl::reload()
    1105             :     throw (css::uno::Exception,
    1106             :            css::uno::RuntimeException,
    1107             :            std::exception)
    1108             : {
    1109           0 :     SolarMutexClearableGuard aGuard;
    1110             : 
    1111           0 :     if ( m_bDisposed )
    1112           0 :         throw DisposedException();
    1113             : 
    1114           0 :     CommandMap                   aOldUserCmdImageSet;
    1115           0 :     std::vector< OUString > aNewUserCmdImageSet;
    1116             : 
    1117           0 :     if ( m_bModified )
    1118             :     {
    1119           0 :         for ( sal_Int16 i = 0; i < sal_Int16( ImageType_COUNT ); i++ )
    1120             :         {
    1121           0 :             if ( !m_bDisposed && m_bUserImageListModified[i] )
    1122             :             {
    1123           0 :                 std::vector< OUString > aOldUserCmdImageVector;
    1124           0 :                 ImageList* pImageList = implts_getUserImageList( (ImageType)i );
    1125           0 :                 pImageList->GetImageNames( aOldUserCmdImageVector );
    1126             : 
    1127             :                 // Fill hash map to speed up search afterwards
    1128           0 :                 sal_uInt32 j( 0 );
    1129           0 :                 const sal_uInt32 nOldCount = aOldUserCmdImageVector.size();
    1130           0 :                 for ( j = 0; j < nOldCount; j++ )
    1131           0 :                     aOldUserCmdImageSet.insert( CommandMap::value_type( aOldUserCmdImageVector[j], false ));
    1132             : 
    1133             :                 // Attention: This can make the old image list pointer invalid!
    1134           0 :                 implts_loadUserImages( (ImageType)i, m_xUserImageStorage, m_xUserBitmapsStorage );
    1135           0 :                 pImageList = implts_getUserImageList( (ImageType)i );
    1136           0 :                 pImageList->GetImageNames( aNewUserCmdImageSet );
    1137             : 
    1138           0 :                 CmdToXGraphicNameAccess* pInsertedImages( 0 );
    1139           0 :                 CmdToXGraphicNameAccess* pReplacedImages( 0 );
    1140           0 :                 CmdToXGraphicNameAccess* pRemovedImages( 0 );
    1141             : 
    1142           0 :                 const sal_uInt32 nNewCount = aNewUserCmdImageSet.size();
    1143           0 :                 for ( j = 0; j < nNewCount; j++ )
    1144             :                 {
    1145           0 :                     CommandMap::iterator pIter = aOldUserCmdImageSet.find( aNewUserCmdImageSet[j] );
    1146           0 :                     if ( pIter != aOldUserCmdImageSet.end() )
    1147             :                     {
    1148           0 :                         pIter->second = true; // mark entry as replaced
    1149           0 :                         if ( !pReplacedImages )
    1150           0 :                             pReplacedImages = new CmdToXGraphicNameAccess();
    1151           0 :                         pReplacedImages->addElement( aNewUserCmdImageSet[j],
    1152           0 :                                                      pImageList->GetImage( aNewUserCmdImageSet[j] ).GetXGraphic() );
    1153             :                     }
    1154             :                     else
    1155             :                     {
    1156           0 :                         if ( !pInsertedImages )
    1157           0 :                             pInsertedImages = new CmdToXGraphicNameAccess();
    1158           0 :                         pInsertedImages->addElement( aNewUserCmdImageSet[j],
    1159           0 :                                                      pImageList->GetImage( aNewUserCmdImageSet[j] ).GetXGraphic() );
    1160             :                     }
    1161             :                 }
    1162             : 
    1163             :                 // Search map for unmarked entries => they have been removed from the user list
    1164             :                 // through this reload operation.
    1165             :                 // We have to search the module and global image list!
    1166           0 :                 rtl::Reference< GlobalImageList > rGlobalImageList;
    1167           0 :                 CmdImageList*                     pDefaultImageList = NULL;
    1168           0 :                 if ( m_bUseGlobal )
    1169             :                 {
    1170           0 :                     rGlobalImageList  = implts_getGlobalImageList();
    1171           0 :                     pDefaultImageList = implts_getDefaultImageList();
    1172             :                 }
    1173           0 :                 uno::Reference< XGraphic >        xEmptyGraphic( Image().GetXGraphic() );
    1174           0 :                 CommandMap::const_iterator        pIter = aOldUserCmdImageSet.begin();
    1175           0 :                 while ( pIter != aOldUserCmdImageSet.end() )
    1176             :                 {
    1177           0 :                     if ( !pIter->second )
    1178             :                     {
    1179           0 :                         if ( m_bUseGlobal )
    1180             :                         {
    1181           0 :                             Image aImage = pDefaultImageList->getImageFromCommandURL( i, pIter->first );
    1182           0 :                             if ( !aImage )
    1183           0 :                                 aImage = rGlobalImageList->getImageFromCommandURL( i, pIter->first );
    1184             : 
    1185           0 :                             if ( !aImage )
    1186             :                             {
    1187             :                                 // No image in the module/global image list => remove user image
    1188           0 :                                 if ( !pRemovedImages )
    1189           0 :                                     pRemovedImages = new CmdToXGraphicNameAccess();
    1190           0 :                                 pRemovedImages->addElement( pIter->first, xEmptyGraphic );
    1191             :                             }
    1192             :                             else
    1193             :                             {
    1194             :                                 // Image has been found in the module/global image list => replace user image
    1195           0 :                                 if ( !pReplacedImages )
    1196           0 :                                     pReplacedImages = new CmdToXGraphicNameAccess();
    1197           0 :                                 pReplacedImages->addElement( pIter->first, aImage.GetXGraphic() );
    1198           0 :                             }
    1199             :                         } // if ( m_bUseGlobal )
    1200             :                         else
    1201             :                         {
    1202             :                             // No image in the user image list => remove user image
    1203           0 :                             if ( !pRemovedImages )
    1204           0 :                                 pRemovedImages = new CmdToXGraphicNameAccess();
    1205           0 :                             pRemovedImages->addElement( pIter->first, xEmptyGraphic );
    1206             :                         }
    1207             :                     }
    1208           0 :                     ++pIter;
    1209             :                 }
    1210             : 
    1211           0 :                 aGuard.clear();
    1212             : 
    1213             :                 // Now notify our listeners. Unlock mutex to prevent deadlocks
    1214           0 :                 uno::Reference< uno::XInterface > xOwner(static_cast< OWeakObject* >(m_pOwner));
    1215           0 :                 if ( pInsertedImages != 0 )
    1216             :                 {
    1217           0 :                     ConfigurationEvent aInsertEvent;
    1218           0 :                     aInsertEvent.aInfo           = uno::makeAny( i );
    1219           0 :                     aInsertEvent.Accessor        = uno::makeAny( xOwner );
    1220           0 :                     aInsertEvent.Source          = xOwner;
    1221           0 :                     aInsertEvent.ResourceURL     = m_aResourceString;
    1222           0 :                     aInsertEvent.Element         = uno::makeAny( uno::Reference< XNameAccess >(
    1223           0 :                                                     static_cast< OWeakObject *>( pInsertedImages ), UNO_QUERY ));
    1224           0 :                     implts_notifyContainerListener( aInsertEvent, NotifyOp_Insert );
    1225             :                 }
    1226           0 :                 if ( pReplacedImages != 0 )
    1227             :                 {
    1228           0 :                     ConfigurationEvent aReplaceEvent;
    1229           0 :                     aReplaceEvent.aInfo           = uno::makeAny( i );
    1230           0 :                     aReplaceEvent.Accessor        = uno::makeAny( xOwner );
    1231           0 :                     aReplaceEvent.Source          = xOwner;
    1232           0 :                     aReplaceEvent.ResourceURL     = m_aResourceString;
    1233           0 :                     aReplaceEvent.ReplacedElement = Any();
    1234           0 :                     aReplaceEvent.Element         = uno::makeAny( uno::Reference< XNameAccess >(
    1235           0 :                                                     static_cast< OWeakObject *>( pReplacedImages ), UNO_QUERY ));
    1236           0 :                     implts_notifyContainerListener( aReplaceEvent, NotifyOp_Replace );
    1237             :                 }
    1238           0 :                 if ( pRemovedImages != 0 )
    1239             :                 {
    1240           0 :                     ConfigurationEvent aRemoveEvent;
    1241           0 :                     aRemoveEvent.aInfo           = uno::makeAny( i );
    1242           0 :                     aRemoveEvent.Accessor        = uno::makeAny( xOwner );
    1243           0 :                     aRemoveEvent.Source          = xOwner;
    1244           0 :                     aRemoveEvent.ResourceURL     = m_aResourceString;
    1245           0 :                     aRemoveEvent.Element         = uno::makeAny( uno::Reference< XNameAccess >(
    1246           0 :                                                         static_cast< OWeakObject *>( pRemovedImages ), UNO_QUERY ));
    1247           0 :                     implts_notifyContainerListener( aRemoveEvent, NotifyOp_Remove );
    1248             :                 }
    1249             : 
    1250           0 :                 aGuard.clear();
    1251             :             }
    1252             :         }
    1253           0 :     }
    1254           0 : }
    1255             : 
    1256           0 : void ImageManagerImpl::store()
    1257             :     throw (::com::sun::star::uno::Exception,
    1258             :            ::com::sun::star::uno::RuntimeException,
    1259             :            std::exception)
    1260             : {
    1261           0 :     SolarMutexGuard g;
    1262             : 
    1263           0 :     if ( m_bDisposed )
    1264           0 :         throw DisposedException();
    1265             : 
    1266           0 :     if ( m_bModified )
    1267             :     {
    1268           0 :         bool bWritten( false );
    1269           0 :         for ( sal_Int32 i = 0; i < ImageType_COUNT; i++ )
    1270             :         {
    1271           0 :             bool bSuccess = implts_storeUserImages( ImageType(i), m_xUserImageStorage, m_xUserBitmapsStorage );
    1272           0 :             if ( bSuccess )
    1273           0 :                 bWritten = true;
    1274           0 :             m_bUserImageListModified[i] = false;
    1275             :         }
    1276             : 
    1277           0 :         if ( bWritten &&
    1278           0 :              m_xUserConfigStorage.is() )
    1279             :         {
    1280           0 :             uno::Reference< XTransactedObject > xUserConfigStorageCommit( m_xUserConfigStorage, UNO_QUERY );
    1281           0 :             if ( xUserConfigStorageCommit.is() )
    1282           0 :                 xUserConfigStorageCommit->commit();
    1283           0 :             if ( m_xUserRootCommit.is() )
    1284           0 :                 m_xUserRootCommit->commit();
    1285             :         }
    1286             : 
    1287           0 :         m_bModified = false;
    1288           0 :     }
    1289           0 : }
    1290             : 
    1291           0 : void ImageManagerImpl::storeToStorage( const uno::Reference< XStorage >& Storage )
    1292             :     throw (::com::sun::star::uno::Exception,
    1293             :            ::com::sun::star::uno::RuntimeException,
    1294             :            std::exception)
    1295             : {
    1296           0 :     SolarMutexGuard g;
    1297             : 
    1298           0 :     if ( m_bDisposed )
    1299           0 :         throw DisposedException();
    1300             : 
    1301           0 :     if ( m_bModified && Storage.is() )
    1302             :     {
    1303           0 :         long nModes = ElementModes::READWRITE;
    1304             : 
    1305           0 :         uno::Reference< XStorage > xUserImageStorage = Storage->openStorageElement( OUString(IMAGE_FOLDER ),
    1306           0 :                                                                                     nModes );
    1307           0 :         if ( xUserImageStorage.is() )
    1308             :         {
    1309           0 :             uno::Reference< XStorage > xUserBitmapsStorage = xUserImageStorage->openStorageElement( OUString(BITMAPS_FOLDER ),
    1310           0 :                                                                                                     nModes );
    1311           0 :             for ( sal_Int32 i = 0; i < ImageType_COUNT; i++ )
    1312             :             {
    1313           0 :                 implts_getUserImageList( (ImageType)i );
    1314           0 :                 implts_storeUserImages( (ImageType)i, xUserImageStorage, xUserBitmapsStorage );
    1315             :             }
    1316             : 
    1317           0 :             uno::Reference< XTransactedObject > xTransaction( Storage, UNO_QUERY );
    1318           0 :             if ( xTransaction.is() )
    1319           0 :                 xTransaction->commit();
    1320           0 :         }
    1321           0 :     }
    1322           0 : }
    1323             : 
    1324           0 : bool ImageManagerImpl::isModified()
    1325             : throw (::com::sun::star::uno::RuntimeException)
    1326             : {
    1327           0 :     SolarMutexGuard g;
    1328           0 :     return m_bModified;
    1329             : }
    1330             : 
    1331           0 : bool ImageManagerImpl::isReadOnly() throw (::com::sun::star::uno::RuntimeException)
    1332             : {
    1333           0 :     SolarMutexGuard g;
    1334           0 :     return m_bReadOnly;
    1335             : }
    1336             : // XUIConfiguration
    1337       65893 : void ImageManagerImpl::addConfigurationListener( const uno::Reference< ::com::sun::star::ui::XUIConfigurationListener >& xListener )
    1338             : throw (::com::sun::star::uno::RuntimeException)
    1339             : {
    1340             :     {
    1341       65893 :         SolarMutexGuard g;
    1342             : 
    1343             :         /* SAFE AREA ----------------------------------------------------------------------------------------------- */
    1344       65893 :         if ( m_bDisposed )
    1345           0 :             throw DisposedException();
    1346             :     }
    1347             : 
    1348       65893 :     m_aListenerContainer.addInterface( cppu::UnoType<XUIConfigurationListener>::get(), xListener );
    1349       65893 : }
    1350             : 
    1351       65881 : void ImageManagerImpl::removeConfigurationListener( const uno::Reference< ::com::sun::star::ui::XUIConfigurationListener >& xListener )
    1352             : throw (::com::sun::star::uno::RuntimeException)
    1353             : {
    1354             :     /* SAFE AREA ----------------------------------------------------------------------------------------------- */
    1355       65881 :     m_aListenerContainer.removeInterface( cppu::UnoType<XUIConfigurationListener>::get(), xListener );
    1356       65881 : }
    1357             : 
    1358           0 : void ImageManagerImpl::implts_notifyContainerListener( const ConfigurationEvent& aEvent, NotifyOp eOp )
    1359             : {
    1360             :     ::cppu::OInterfaceContainerHelper* pContainer = m_aListenerContainer.getContainer(
    1361           0 :                                         cppu::UnoType<com::sun::star::ui::XUIConfigurationListener>::get());
    1362           0 :     if ( pContainer != NULL )
    1363             :     {
    1364           0 :         ::cppu::OInterfaceIteratorHelper pIterator( *pContainer );
    1365           0 :         while ( pIterator.hasMoreElements() )
    1366             :         {
    1367             :             try
    1368             :             {
    1369           0 :                 switch ( eOp )
    1370             :                 {
    1371             :                     case NotifyOp_Replace:
    1372           0 :                         static_cast< ::com::sun::star::ui::XUIConfigurationListener*>(pIterator.next())->elementReplaced( aEvent );
    1373           0 :                         break;
    1374             :                     case NotifyOp_Insert:
    1375           0 :                         static_cast< ::com::sun::star::ui::XUIConfigurationListener*>(pIterator.next())->elementInserted( aEvent );
    1376           0 :                         break;
    1377             :                     case NotifyOp_Remove:
    1378           0 :                         static_cast< ::com::sun::star::ui::XUIConfigurationListener*>(pIterator.next())->elementRemoved( aEvent );
    1379           0 :                         break;
    1380             :                 }
    1381             :             }
    1382           0 :             catch( const css::uno::RuntimeException& )
    1383             :             {
    1384           0 :                 pIterator.remove();
    1385             :             }
    1386           0 :         }
    1387             :     }
    1388           0 : }
    1389        6472 : void ImageManagerImpl::clear()
    1390             : {
    1391        6472 :     SolarMutexGuard g;
    1392             : 
    1393       19416 :     for ( sal_Int32 n = 0; n < ImageType_COUNT; n++ )
    1394             :     {
    1395       12944 :         delete m_pUserImageList[n];
    1396       12944 :         m_pUserImageList[n] = 0;
    1397        6472 :     }
    1398        6472 : }
    1399             : } // namespace framework
    1400             : 
    1401             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.11