LCOV - code coverage report
Current view: top level - svx/source/unodraw - unomtabl.cxx (source / functions) Hit Total Coverage
Test: commit c8344322a7af75b84dd3ca8f78b05543a976dfd5 Lines: 137 182 75.3 %
Date: 2015-06-13 12:38:46 Functions: 18 22 81.8 %
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             : 
      21             : #include <set>
      22             : #include <com/sun/star/lang/XServiceInfo.hpp>
      23             : #include <com/sun/star/container/XNameContainer.hpp>
      24             : #include <com/sun/star/drawing/PointSequence.hpp>
      25             : #include <svl/style.hxx>
      26             : 
      27             : #include <cppuhelper/implbase2.hxx>
      28             : #include <cppuhelper/supportsservice.hxx>
      29             : #include <svl/itempool.hxx>
      30             : #include <svl/itemset.hxx>
      31             : #include <svl/lstner.hxx>
      32             : #include <svx/xlnedit.hxx>
      33             : #include <svx/xlnstit.hxx>
      34             : #include <svx/svdmodel.hxx>
      35             : #include <svx/xdef.hxx>
      36             : #include <svx/xflhtit.hxx>
      37             : 
      38             : #include <vector>
      39             : #include <osl/mutex.hxx>
      40             : #include <vcl/svapp.hxx>
      41             : 
      42             : 
      43             : #include "svx/unofill.hxx"
      44             : 
      45             : #include "svx/unoapi.hxx"
      46             : 
      47             : using namespace ::com::sun::star;
      48             : using namespace ::cppu;
      49             : 
      50             : typedef std::vector< SfxItemSet* > ItemPoolVector;
      51             : 
      52             : class SvxUnoMarkerTable : public WeakImplHelper2< container::XNameContainer, lang::XServiceInfo >,
      53             :                           public SfxListener
      54             : {
      55             : private:
      56             :     SdrModel*       mpModel;
      57             :     SfxItemPool*    mpModelPool;
      58             : 
      59             :     ItemPoolVector maItemSetVector;
      60             : 
      61             : public:
      62             :     explicit SvxUnoMarkerTable( SdrModel* pModel ) throw();
      63             :     virtual ~SvxUnoMarkerTable() throw();
      64             : 
      65             :     void dispose();
      66             : 
      67             :     // SfxListener
      68             :     virtual void Notify( SfxBroadcaster& rBC, const SfxHint& rHint ) throw () SAL_OVERRIDE;
      69             : 
      70             :     void SAL_CALL ImplInsertByName( const OUString& aName, const uno::Any& aElement );
      71             : 
      72             :     // XServiceInfo
      73             :     virtual OUString SAL_CALL getImplementationName(  ) throw( uno::RuntimeException, std::exception ) SAL_OVERRIDE;
      74             :     virtual sal_Bool SAL_CALL supportsService( const  OUString& ServiceName ) throw( uno::RuntimeException, std::exception) SAL_OVERRIDE;
      75             :     virtual uno::Sequence<  OUString > SAL_CALL getSupportedServiceNames(  ) throw( uno::RuntimeException, std::exception) SAL_OVERRIDE;
      76             : 
      77             :     // XNameContainer
      78             :     virtual void SAL_CALL insertByName( const  OUString& aName, const  uno::Any& aElement ) throw( lang::IllegalArgumentException, container::ElementExistException, lang::WrappedTargetException, uno::RuntimeException, std::exception) SAL_OVERRIDE;
      79             :     virtual void SAL_CALL removeByName( const  OUString& Name ) throw( container::NoSuchElementException, lang::WrappedTargetException, uno::RuntimeException, std::exception) SAL_OVERRIDE;
      80             : 
      81             :     // XNameReplace
      82             :     virtual void SAL_CALL replaceByName( const  OUString& aName, const  uno::Any& aElement ) throw( lang::IllegalArgumentException, container::NoSuchElementException, lang::WrappedTargetException, uno::RuntimeException, std::exception) SAL_OVERRIDE;
      83             : 
      84             :     // XNameAccess
      85             :     virtual uno::Any SAL_CALL getByName( const  OUString& aName ) throw( container::NoSuchElementException, lang::WrappedTargetException, uno::RuntimeException, std::exception) SAL_OVERRIDE;
      86             :     virtual uno::Sequence<  OUString > SAL_CALL getElementNames(  ) throw( uno::RuntimeException, std::exception) SAL_OVERRIDE;
      87             :     virtual sal_Bool SAL_CALL hasByName( const  OUString& aName ) throw( uno::RuntimeException, std::exception) SAL_OVERRIDE;
      88             : 
      89             :     // XElementAccess
      90             :     virtual uno::Type SAL_CALL getElementType(  ) throw( uno::RuntimeException, std::exception) SAL_OVERRIDE;
      91             :     virtual sal_Bool SAL_CALL hasElements(  ) throw( uno::RuntimeException, std::exception) SAL_OVERRIDE;
      92             : };
      93             : 
      94         297 : SvxUnoMarkerTable::SvxUnoMarkerTable( SdrModel* pModel ) throw()
      95             : : mpModel( pModel ),
      96         297 :   mpModelPool( pModel ? &pModel->GetItemPool() : nullptr )
      97             : {
      98         297 :     if( pModel )
      99         297 :         StartListening( *pModel );
     100         297 : }
     101             : 
     102         828 : SvxUnoMarkerTable::~SvxUnoMarkerTable() throw()
     103             : {
     104         276 :     if( mpModel )
     105         276 :         EndListening( *mpModel );
     106         276 :     dispose();
     107         552 : }
     108             : 
     109         553 : void SvxUnoMarkerTable::dispose()
     110             : {
     111         553 :     ItemPoolVector::iterator aIter = maItemSetVector.begin();
     112         553 :     const ItemPoolVector::iterator aEnd = maItemSetVector.end();
     113             : 
     114        1246 :     while( aIter != aEnd )
     115             :     {
     116         140 :         delete (*aIter++);
     117             :     }
     118             : 
     119         553 :     maItemSetVector.clear();
     120         553 : }
     121             : 
     122             : // SfxListener
     123       27363 : void SvxUnoMarkerTable::Notify( SfxBroadcaster&, const SfxHint& rHint ) throw()
     124             : {
     125       27363 :     const SdrHint* pSdrHint = dynamic_cast<const SdrHint*>(&rHint);
     126             : 
     127       27363 :     if( pSdrHint && HINT_MODELCLEARED == pSdrHint->GetKind() )
     128         233 :         dispose();
     129       27363 : }
     130             : 
     131           0 : sal_Bool SAL_CALL SvxUnoMarkerTable::supportsService( const  OUString& ServiceName ) throw(uno::RuntimeException, std::exception)
     132             : {
     133           0 :     return cppu::supportsService(this, ServiceName);
     134             : }
     135             : 
     136           0 : OUString SAL_CALL SvxUnoMarkerTable::getImplementationName() throw( uno::RuntimeException, std::exception )
     137             : {
     138           0 :     return OUString("SvxUnoMarkerTable");
     139             : }
     140             : 
     141           0 : uno::Sequence< OUString > SAL_CALL SvxUnoMarkerTable::getSupportedServiceNames(  )
     142             :     throw( uno::RuntimeException, std::exception )
     143             : {
     144           0 :     uno::Sequence< OUString > aSNS( 1 );
     145           0 :     aSNS.getArray()[0] = "com.sun.star.drawing.MarkerTable";
     146           0 :     return aSNS;
     147             : }
     148             : 
     149         152 : void SAL_CALL SvxUnoMarkerTable::ImplInsertByName( const OUString& aName, const uno::Any& aElement )
     150             : {
     151         152 :     SfxItemSet* mpInSet = new SfxItemSet( *mpModelPool, XATTR_LINESTART, XATTR_LINEEND );
     152         152 :     maItemSetVector.push_back( mpInSet );
     153             : 
     154         152 :     XLineEndItem aEndMarker;
     155         152 :     aEndMarker.SetName( aName );
     156         152 :     aEndMarker.PutValue( aElement );
     157             : 
     158         152 :     mpInSet->Put( aEndMarker, XATTR_LINEEND );
     159             : 
     160         304 :     XLineStartItem aStartMarker;
     161         152 :     aStartMarker.SetName( aName );
     162         152 :     aStartMarker.PutValue( aElement );
     163             : 
     164         304 :     mpInSet->Put( aStartMarker, XATTR_LINESTART );
     165         152 : }
     166             : 
     167             : // XNameContainer
     168         108 : void SAL_CALL SvxUnoMarkerTable::insertByName( const OUString& aApiName, const uno::Any& aElement )
     169             :     throw( lang::IllegalArgumentException, container::ElementExistException, lang::WrappedTargetException, uno::RuntimeException, std::exception )
     170             : {
     171         108 :     SolarMutexGuard aGuard;
     172             : 
     173         108 :     if( hasByName( aApiName ) )
     174           0 :         throw container::ElementExistException();
     175             : 
     176         216 :     OUString aName = SvxUnogetInternalNameForItem(XATTR_LINEEND, aApiName);
     177             : 
     178         216 :     ImplInsertByName( aName, aElement );
     179         108 : }
     180             : 
     181          44 : void SAL_CALL SvxUnoMarkerTable::removeByName( const OUString& aApiName )
     182             :     throw( container::NoSuchElementException, lang::WrappedTargetException, uno::RuntimeException, std::exception)
     183             : {
     184          44 :     SolarMutexGuard aGuard;
     185             : 
     186             :     // a little quickfix for 2.0 to let applications clear api
     187             :     // created items that are not used
     188          44 :     if ( aApiName == "~clear~" )
     189             :     {
     190          44 :         dispose();
     191          44 :         return;
     192             :     }
     193             : 
     194           0 :     OUString Name = SvxUnogetInternalNameForItem(XATTR_LINEEND, aApiName);
     195             : 
     196           0 :     ItemPoolVector::iterator aIter = maItemSetVector.begin();
     197           0 :     const ItemPoolVector::iterator aEnd = maItemSetVector.end();
     198             : 
     199           0 :     const OUString aSearchName( Name );
     200             : 
     201           0 :     while( aIter != aEnd )
     202             :     {
     203           0 :         const NameOrIndex *pItem = static_cast<const NameOrIndex *>(&((*aIter)->Get( XATTR_LINEEND ) ));
     204           0 :         if( pItem->GetName() == aSearchName )
     205             :         {
     206           0 :             delete (*aIter);
     207           0 :             maItemSetVector.erase( aIter );
     208           0 :             return;
     209             :         }
     210           0 :         ++aIter;
     211             :     }
     212             : 
     213           0 :     if( !hasByName( Name ) )
     214           0 :         throw container::NoSuchElementException();
     215             : }
     216             : 
     217             : // XNameReplace
     218          44 : void SAL_CALL SvxUnoMarkerTable::replaceByName( const OUString& aApiName, const uno::Any& aElement )
     219             :     throw( lang::IllegalArgumentException, container::NoSuchElementException, lang::WrappedTargetException, uno::RuntimeException, std::exception )
     220             : {
     221          44 :     SolarMutexGuard aGuard;
     222             : 
     223          88 :     OUString aName = SvxUnogetInternalNameForItem(XATTR_LINEEND, aApiName);
     224             : 
     225          44 :     ItemPoolVector::iterator aIter = maItemSetVector.begin();
     226          44 :     const ItemPoolVector::iterator aEnd = maItemSetVector.end();
     227             : 
     228          88 :     const OUString aSearchName( aName );
     229             : 
     230          88 :     while( aIter != aEnd )
     231             :     {
     232           0 :         const NameOrIndex *pItem = static_cast<const NameOrIndex *>(&((*aIter)->Get( XATTR_LINEEND ) ));
     233           0 :         if( pItem->GetName() == aSearchName )
     234             :         {
     235           0 :             XLineEndItem aEndMarker;
     236           0 :             aEndMarker.SetName( aSearchName );
     237           0 :             if( !aEndMarker.PutValue( aElement ) )
     238           0 :                 throw lang::IllegalArgumentException();
     239             : 
     240           0 :             (*aIter)->Put( aEndMarker, XATTR_LINEEND );
     241             : 
     242           0 :             XLineStartItem aStartMarker;
     243           0 :             aStartMarker.SetName( aSearchName );
     244           0 :             aStartMarker.PutValue( aElement );
     245             : 
     246           0 :             (*aIter)->Put( aStartMarker, XATTR_LINESTART );
     247          44 :             return;
     248             :         }
     249           0 :         ++aIter;
     250             :     }
     251             : 
     252             :     // if it is not in our own sets, modify the pool!
     253          44 :     bool bFound = false;
     254             : 
     255             :     sal_uInt32 nSurrogate;
     256          44 :     const sal_uInt32 nStartCount = mpModelPool ? mpModelPool->GetItemCount2( XATTR_LINESTART ) : 0;
     257          88 :     for( nSurrogate = 0; nSurrogate < nStartCount; nSurrogate++ )
     258             :     {
     259          88 :         NameOrIndex *pItem = const_cast<NameOrIndex*>(static_cast<const NameOrIndex*>(mpModelPool->GetItem2( XATTR_LINESTART, nSurrogate)));
     260          88 :         if( pItem && pItem->GetName() == aSearchName )
     261             :         {
     262          44 :             pItem->PutValue( aElement );
     263          44 :             bFound = true;
     264          44 :             break;
     265             :         }
     266             :     }
     267             : 
     268          44 :     const sal_uInt32 nEndCount = mpModelPool ? mpModelPool->GetItemCount2( XATTR_LINEEND ) : 0;
     269          88 :     for( nSurrogate = 0; nSurrogate < nEndCount; nSurrogate++ )
     270             :     {
     271          88 :         NameOrIndex *pItem = const_cast<NameOrIndex*>(static_cast<const NameOrIndex*>(mpModelPool->GetItem2( XATTR_LINEEND, nSurrogate)));
     272          88 :         if( pItem && pItem->GetName() == aSearchName )
     273             :         {
     274          44 :             pItem->PutValue( aElement );
     275          44 :             bFound = true;
     276          44 :             break;
     277             :         }
     278             :     }
     279             : 
     280          44 :     if( bFound )
     281          44 :         ImplInsertByName( aName, aElement );
     282             :     else
     283          44 :         throw container::NoSuchElementException();
     284             : }
     285             : 
     286          19 : static bool getByNameFromPool( const OUString& rSearchName, SfxItemPool* pPool, sal_uInt16 nWhich, uno::Any& rAny )
     287             : {
     288          19 :     const sal_uInt32 nSurrogateCount = pPool ? pPool->GetItemCount2( nWhich ) : 0;
     289          37 :     for( sal_uInt32 nSurrogate = 0; nSurrogate < nSurrogateCount; nSurrogate++ )
     290             :     {
     291          37 :         const NameOrIndex *pItem = static_cast<const NameOrIndex*>(pPool->GetItem2( nWhich, nSurrogate ));
     292             : 
     293          37 :         if( pItem && pItem->GetName() == rSearchName )
     294             :         {
     295          19 :             pItem->QueryValue( rAny, 0 );
     296          19 :             return true;
     297             :         }
     298             :     }
     299             : 
     300           0 :     return false;
     301             : }
     302             : 
     303             : // XNameAccess
     304          19 : uno::Any SAL_CALL SvxUnoMarkerTable::getByName( const OUString& aApiName )
     305             :     throw( container::NoSuchElementException,  lang::WrappedTargetException, uno::RuntimeException, std::exception)
     306             : {
     307          19 :     SolarMutexGuard aGuard;
     308             : 
     309          38 :     OUString aName = SvxUnogetInternalNameForItem(XATTR_LINEEND, aApiName);
     310             : 
     311          19 :     uno::Any aAny;
     312             : 
     313          19 :     if (mpModelPool && !aName.isEmpty())
     314             :     {
     315             :         do
     316             :         {
     317          19 :             if (getByNameFromPool(aName, mpModelPool, XATTR_LINESTART, aAny))
     318          19 :                 break;
     319             : 
     320           0 :             if (getByNameFromPool(aName, mpModelPool, XATTR_LINEEND, aAny))
     321           0 :                 break;
     322             : 
     323           0 :             throw container::NoSuchElementException();
     324             :         }
     325             :         while(false);
     326             :     }
     327             : 
     328          38 :     return aAny;
     329             : }
     330             : 
     331          34 : static void createNamesForPool( SfxItemPool* pPool, sal_uInt16 nWhich, std::set< OUString >& rNameSet )
     332             : {
     333          34 :     const sal_uInt32 nSuroCount = pPool->GetItemCount2( nWhich );
     334             : 
     335         103 :     for(sal_uInt32 nSurrogate = 0; nSurrogate < nSuroCount; ++nSurrogate)
     336             :     {
     337          69 :         const NameOrIndex* pItem = static_cast<const NameOrIndex*>(pPool->GetItem2( nWhich, nSurrogate ));
     338             : 
     339          69 :         if( pItem == NULL || pItem->GetName().isEmpty() )
     340          31 :             continue;
     341             : 
     342          38 :         OUString aName = SvxUnogetApiNameForItem(XATTR_LINEEND, pItem->GetName());
     343          38 :         rNameSet.insert( aName );
     344          38 :     }
     345          34 : }
     346             : 
     347          17 : uno::Sequence< OUString > SAL_CALL SvxUnoMarkerTable::getElementNames()
     348             :     throw( uno::RuntimeException, std::exception )
     349             : {
     350          17 :     SolarMutexGuard aGuard;
     351             : 
     352          34 :     std::set< OUString > aNameSet;
     353             : 
     354             :     // search model pool for line starts
     355          17 :     createNamesForPool( mpModelPool, XATTR_LINESTART, aNameSet );
     356             : 
     357             :     // search model pool for line ends
     358          17 :     createNamesForPool( mpModelPool, XATTR_LINEEND, aNameSet );
     359             : 
     360          17 :     uno::Sequence< OUString > aSeq( aNameSet.size() );
     361          17 :     OUString* pNames = aSeq.getArray();
     362             : 
     363          17 :     std::set< OUString >::iterator aIter( aNameSet.begin() );
     364          17 :     const std::set< OUString >::iterator aEnd( aNameSet.end() );
     365             : 
     366          53 :     while( aIter != aEnd )
     367             :     {
     368          19 :         *pNames++ = *aIter++;
     369             :     }
     370             : 
     371          34 :     return aSeq;
     372             : }
     373             : 
     374         386 : sal_Bool SAL_CALL SvxUnoMarkerTable::hasByName( const OUString& aName )
     375             :     throw( uno::RuntimeException, std::exception )
     376             : {
     377         386 :     SolarMutexGuard aGuard;
     378             : 
     379         386 :     if( aName.isEmpty() )
     380           0 :         return sal_False;
     381             : 
     382         772 :     OUString aSearchName;
     383             : 
     384             :     const NameOrIndex *pItem;
     385             : 
     386         386 :     aSearchName = SvxUnogetInternalNameForItem(XATTR_LINESTART, aName);
     387         386 :     sal_uInt32 nStartCount = mpModelPool ? mpModelPool->GetItemCount2( XATTR_LINESTART ) : 0;
     388             :     sal_uInt32 nSurrogate;
     389         801 :     for( nSurrogate = 0; nSurrogate < nStartCount; nSurrogate++ )
     390             :     {
     391         551 :         pItem = static_cast<const NameOrIndex*>(mpModelPool->GetItem2( XATTR_LINESTART, nSurrogate));
     392         551 :         if( pItem && pItem->GetName() == aSearchName )
     393         136 :             return sal_True;
     394             :     }
     395             : 
     396         250 :     aSearchName = SvxUnogetInternalNameForItem(XATTR_LINEEND, aName);
     397         250 :     sal_uInt32 nEndCount = mpModelPool ? mpModelPool->GetItemCount2( XATTR_LINEEND ) : 0;
     398         603 :     for( nSurrogate = 0; nSurrogate < nEndCount; nSurrogate++ )
     399             :     {
     400         353 :         pItem = static_cast<const NameOrIndex*>(mpModelPool->GetItem2( XATTR_LINEEND, nSurrogate));
     401         353 :         if( pItem && pItem->GetName() == aSearchName )
     402           0 :             return sal_True;
     403             :     }
     404             : 
     405         636 :     return sal_False;
     406             : }
     407             : 
     408             : // XElementAccess
     409           0 : uno::Type SAL_CALL SvxUnoMarkerTable::getElementType(  )
     410             :     throw( uno::RuntimeException, std::exception )
     411             : {
     412           0 :     return cppu::UnoType<drawing::PointSequence>::get();
     413             : }
     414             : 
     415         386 : sal_Bool SAL_CALL SvxUnoMarkerTable::hasElements(  )
     416             :     throw( uno::RuntimeException, std::exception )
     417             : {
     418         386 :     SolarMutexGuard aGuard;
     419             : 
     420             :     const NameOrIndex *pItem;
     421             : 
     422         386 :     const sal_uInt32 nStartCount = mpModelPool ? mpModelPool->GetItemCount2( XATTR_LINESTART ) : 0;
     423             :     sal_uInt32 nSurrogate;
     424         401 :     for( nSurrogate = 0; nSurrogate < nStartCount; nSurrogate++ )
     425             :     {
     426          32 :         pItem = static_cast<const NameOrIndex*>(mpModelPool->GetItem2( XATTR_LINESTART, nSurrogate));
     427          32 :         if( pItem && !pItem->GetName().isEmpty() )
     428          17 :             return sal_True;
     429             :     }
     430             : 
     431         369 :     const sal_uInt32 nEndCount = mpModelPool ? mpModelPool->GetItemCount2( XATTR_LINEEND ) : 0;
     432         369 :     for( nSurrogate = 0; nSurrogate < nEndCount; nSurrogate++ )
     433             :     {
     434           0 :         pItem = static_cast<const NameOrIndex*>(mpModelPool->GetItem2( XATTR_LINEEND, nSurrogate));
     435           0 :         if( pItem && !pItem->GetName().isEmpty() )
     436           0 :             return sal_True;
     437             :     }
     438             : 
     439         369 :     return sal_False;
     440             : }
     441             : 
     442             : /**
     443             :  * Create a hatchtable
     444             :  */
     445         297 : uno::Reference< uno::XInterface > SAL_CALL SvxUnoMarkerTable_createInstance( SdrModel* pModel )
     446             : {
     447         297 :     return *new SvxUnoMarkerTable(pModel);
     448         435 : }
     449             : 
     450             : 
     451             : 
     452             : /* vim:set shiftwidth=4 softtabstop=4 expandtab: */

Generated by: LCOV version 1.11