1 /*************************************************************************
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
5 * Copyright 2008 by Sun Microsystems, Inc.
7 * OpenOffice.org - a multi-platform office productivity suite
9 * $RCSfile: unomtabl.cxx,v $
12 * This file is part of OpenOffice.org.
14 * OpenOffice.org is free software: you can redistribute it and/or modify
15 * it under the terms of the GNU Lesser General Public License version 3
16 * only, as published by the Free Software Foundation.
18 * OpenOffice.org is distributed in the hope that it will be useful,
19 * but WITHOUT ANY WARRANTY; without even the implied warranty of
20 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
21 * GNU Lesser General Public License version 3 for more details
22 * (a copy is included in the LICENSE file that accompanied this code).
24 * You should have received a copy of the GNU Lesser General Public License
25 * version 3 along with OpenOffice.org. If not, see
26 * <http://www.openoffice.org/license.html>
27 * for a copy of the LGPLv3 License.
29 ************************************************************************/
31 // MARKER(update_precomp.py): autogen include statement, do not remove
32 #include "precompiled_svx.hxx"
35 #include <comphelper/stl_types.hxx>
36 #include <com/sun/star/lang/XServiceInfo.hpp>
37 #include <com/sun/star/container/XNameContainer.hpp>
38 #include <com/sun/star/drawing/PointSequence.hpp>
39 #include <svtools/style.hxx>
41 #include <cppuhelper/implbase2.hxx>
42 #include <svtools/itempool.hxx>
43 #include <svtools/itemset.hxx>
44 #include <svtools/lstner.hxx>
45 #include <svx/xlnedit.hxx>
46 #include <svx/xlnstit.hxx>
47 #include <svx/svdmodel.hxx>
48 #include <svx/xdef.hxx>
49 #include <svx/xflhtit.hxx>
52 #include <vos/mutex.hxx>
53 #include <vcl/svapp.hxx>
56 #include "unofill.hxx"
60 using namespace ::com::sun::star
;
61 using namespace ::rtl
;
62 using namespace ::cppu
;
63 using namespace ::vos
;
65 typedef std::vector
< SfxItemSet
* > ItemPoolVector
;
67 class SvxUnoMarkerTable
: public WeakImplHelper2
< container::XNameContainer
, lang::XServiceInfo
>,
72 SfxItemPool
* mpModelPool
;
74 ItemPoolVector maItemSetVector
;
77 SvxUnoMarkerTable( SdrModel
* pModel
) throw();
78 virtual ~SvxUnoMarkerTable() throw();
83 virtual void Notify( SfxBroadcaster
& rBC
, const SfxHint
& rHint
) throw ();
85 void SAL_CALL
ImplInsertByName( const OUString
& aName
, const uno::Any
& aElement
);
88 virtual OUString SAL_CALL
getImplementationName( ) throw( uno::RuntimeException
);
89 virtual sal_Bool SAL_CALL
supportsService( const OUString
& ServiceName
) throw( uno::RuntimeException
);
90 virtual uno::Sequence
< OUString
> SAL_CALL
getSupportedServiceNames( ) throw( uno::RuntimeException
);
93 virtual void SAL_CALL
insertByName( const OUString
& aName
, const uno::Any
& aElement
) throw( lang::IllegalArgumentException
, container::ElementExistException
, lang::WrappedTargetException
, uno::RuntimeException
);
94 virtual void SAL_CALL
removeByName( const OUString
& Name
) throw( container::NoSuchElementException
, lang::WrappedTargetException
, uno::RuntimeException
);
97 virtual void SAL_CALL
replaceByName( const OUString
& aName
, const uno::Any
& aElement
) throw( lang::IllegalArgumentException
, container::NoSuchElementException
, lang::WrappedTargetException
, uno::RuntimeException
);
100 virtual uno::Any SAL_CALL
getByName( const OUString
& aName
) throw( container::NoSuchElementException
, lang::WrappedTargetException
, uno::RuntimeException
);
101 virtual uno::Sequence
< OUString
> SAL_CALL
getElementNames( ) throw( uno::RuntimeException
);
102 virtual sal_Bool SAL_CALL
hasByName( const OUString
& aName
) throw( uno::RuntimeException
);
105 virtual uno::Type SAL_CALL
getElementType( ) throw( uno::RuntimeException
);
106 virtual sal_Bool SAL_CALL
hasElements( ) throw( uno::RuntimeException
);
109 SvxUnoMarkerTable::SvxUnoMarkerTable( SdrModel
* pModel
) throw()
111 mpModelPool( pModel
? &pModel
->GetItemPool() : (SfxItemPool
*)NULL
)
114 StartListening( *pModel
);
117 SvxUnoMarkerTable::~SvxUnoMarkerTable() throw()
120 EndListening( *mpModel
);
124 void SvxUnoMarkerTable::dispose()
126 ItemPoolVector::iterator aIter
= maItemSetVector
.begin();
127 const ItemPoolVector::iterator aEnd
= maItemSetVector
.end();
129 while( aIter
!= aEnd
)
134 maItemSetVector
.clear();
138 void SvxUnoMarkerTable::Notify( SfxBroadcaster
&, const SfxHint
& rHint
) throw()
140 const SdrHint
* pSdrHint
= PTR_CAST( SdrHint
, &rHint
);
142 if( pSdrHint
&& HINT_MODELCLEARED
== pSdrHint
->GetKind() )
146 sal_Bool SAL_CALL
SvxUnoMarkerTable::supportsService( const OUString
& ServiceName
) throw(uno::RuntimeException
)
148 uno::Sequence
< OUString
> aSNL( getSupportedServiceNames() );
149 const OUString
* pArray
= aSNL
.getConstArray();
151 for( INT32 i
= 0; i
< aSNL
.getLength(); i
++ )
152 if( pArray
[i
] == ServiceName
)
158 OUString SAL_CALL
SvxUnoMarkerTable::getImplementationName() throw( uno::RuntimeException
)
160 return OUString( RTL_CONSTASCII_USTRINGPARAM("SvxUnoMarkerTable") );
163 uno::Sequence
< OUString
> SAL_CALL
SvxUnoMarkerTable::getSupportedServiceNames( )
164 throw( uno::RuntimeException
)
166 uno::Sequence
< OUString
> aSNS( 1 );
167 aSNS
.getArray()[0] = OUString( RTL_CONSTASCII_USTRINGPARAM("com.sun.star.drawing.MarkerTable" ));
171 void SAL_CALL
SvxUnoMarkerTable::ImplInsertByName( const OUString
& aName
, const uno::Any
& aElement
)
173 SfxItemSet
* mpInSet
= new SfxItemSet( *mpModelPool
, XATTR_LINESTART
, XATTR_LINEEND
);
174 maItemSetVector
.push_back( mpInSet
);
176 XLineEndItem aEndMarker
;
177 aEndMarker
.SetName( String( aName
) );
178 aEndMarker
.PutValue( aElement
);
180 mpInSet
->Put( aEndMarker
, XATTR_LINEEND
);
182 XLineStartItem aStartMarker
;
183 aStartMarker
.SetName( String( aName
) );
184 aStartMarker
.PutValue( aElement
);
186 mpInSet
->Put( aStartMarker
, XATTR_LINESTART
);
190 void SAL_CALL
SvxUnoMarkerTable::insertByName( const OUString
& aApiName
, const uno::Any
& aElement
)
191 throw( lang::IllegalArgumentException
, container::ElementExistException
, lang::WrappedTargetException
, uno::RuntimeException
)
193 OGuard
aGuard( Application::GetSolarMutex() );
195 if( hasByName( aApiName
) )
196 throw container::ElementExistException();
199 SvxUnogetInternalNameForItem( XATTR_LINEEND
, aApiName
, aName
);
201 ImplInsertByName( aName
, aElement
);
204 void SAL_CALL
SvxUnoMarkerTable::removeByName( const OUString
& aApiName
)
205 throw( container::NoSuchElementException
, lang::WrappedTargetException
, uno::RuntimeException
)
207 OGuard
aGuard( Application::GetSolarMutex() );
209 // a little quickfix for 2.0 to let applications clear api
210 // created items that are not used
211 if( aApiName
.equalsAsciiL( RTL_CONSTASCII_STRINGPARAM("~clear~") ) )
218 SvxUnogetInternalNameForItem( XATTR_LINEEND
, aApiName
, Name
);
220 ItemPoolVector::iterator aIter
= maItemSetVector
.begin();
221 const ItemPoolVector::iterator aEnd
= maItemSetVector
.end();
224 const String
aSearchName( Name
);
226 while( aIter
!= aEnd
)
228 pItem
= (NameOrIndex
*)&((*aIter
)->Get( XATTR_LINEEND
) );
229 if( pItem
->GetName() == aSearchName
)
232 maItemSetVector
.erase( aIter
);
238 if( !hasByName( Name
) )
239 throw container::NoSuchElementException();
243 void SAL_CALL
SvxUnoMarkerTable::replaceByName( const OUString
& aApiName
, const uno::Any
& aElement
)
244 throw( lang::IllegalArgumentException
, container::NoSuchElementException
, lang::WrappedTargetException
, uno::RuntimeException
)
246 OGuard
aGuard( Application::GetSolarMutex() );
249 SvxUnogetInternalNameForItem( XATTR_LINEEND
, aApiName
, aName
);
251 ItemPoolVector::iterator aIter
= maItemSetVector
.begin();
252 const ItemPoolVector::iterator aEnd
= maItemSetVector
.end();
255 const String
aSearchName( aName
);
257 while( aIter
!= aEnd
)
259 pItem
= (NameOrIndex
*)&((*aIter
)->Get( XATTR_LINEEND
) );
260 if( pItem
->GetName() == aSearchName
)
262 XLineEndItem aEndMarker
;
263 aEndMarker
.SetName( aSearchName
);
264 if( !aEndMarker
.PutValue( aElement
) )
265 throw lang::IllegalArgumentException();
267 (*aIter
)->Put( aEndMarker
, XATTR_LINEEND
);
269 XLineStartItem aStartMarker
;
270 aStartMarker
.SetName( aSearchName
);
271 aStartMarker
.PutValue( aElement
);
273 (*aIter
)->Put( aStartMarker
, XATTR_LINESTART
);
279 // if it is not in our own sets, modify the pool!
280 sal_Bool bFound
= sal_False
;
283 const USHORT nStartCount
= mpModelPool
? mpModelPool
->GetItemCount( XATTR_LINESTART
) : 0;
284 for( nSurrogate
= 0; nSurrogate
< nStartCount
; nSurrogate
++ )
286 pItem
= (NameOrIndex
*)mpModelPool
->GetItem( XATTR_LINESTART
, nSurrogate
);
287 if( pItem
&& pItem
->GetName() == aSearchName
)
289 pItem
->PutValue( aElement
);
295 const USHORT nEndCount
= mpModelPool
? mpModelPool
->GetItemCount( XATTR_LINEEND
) : 0;
296 for( nSurrogate
= 0; nSurrogate
< nEndCount
; nSurrogate
++ )
298 pItem
= (NameOrIndex
*)mpModelPool
->GetItem( XATTR_LINEEND
, nSurrogate
);
299 if( pItem
&& pItem
->GetName() == aSearchName
)
301 pItem
->PutValue( aElement
);
308 ImplInsertByName( aName
, aElement
);
310 throw container::NoSuchElementException();
313 static sal_Bool
getByNameFromPool( const String
& rSearchName
, SfxItemPool
* pPool
, USHORT nWhich
, uno::Any
& rAny
)
316 const sal_Int32 nSurrogateCount
= pPool
? (sal_Int32
)pPool
->GetItemCount( nWhich
) : 0;
317 for( sal_Int32 nSurrogate
= 0; nSurrogate
< nSurrogateCount
; nSurrogate
++ )
319 pItem
= (NameOrIndex
*)pPool
->GetItem( nWhich
, (USHORT
)nSurrogate
);
321 if( pItem
&& pItem
->GetName() == rSearchName
)
323 pItem
->QueryValue( rAny
, 0 );
332 uno::Any SAL_CALL
SvxUnoMarkerTable::getByName( const OUString
& aApiName
)
333 throw( container::NoSuchElementException
, lang::WrappedTargetException
, uno::RuntimeException
)
335 OGuard
aGuard( Application::GetSolarMutex() );
338 SvxUnogetInternalNameForItem( XATTR_LINEEND
, aApiName
, aName
);
342 if( mpModelPool
&& aName
.Len() != 0 )
346 const String
aSearchName( aName
);
347 if( getByNameFromPool( aSearchName
, mpModelPool
, XATTR_LINESTART
, aAny
) )
350 if( getByNameFromPool( aSearchName
, mpModelPool
, XATTR_LINEEND
, aAny
) )
353 throw container::NoSuchElementException();
361 static void createNamesForPool( SfxItemPool
* pPool
, USHORT nWhich
, std::set
< OUString
, comphelper::UStringLess
>& rNameSet
)
363 const sal_Int32 nSuroCount
= pPool
->GetItemCount( nWhich
);
364 sal_Int32 nSurrogate
;
369 for( nSurrogate
= 0; nSurrogate
< nSuroCount
; nSurrogate
++ )
371 pItem
= (NameOrIndex
*)pPool
->GetItem( nWhich
, (USHORT
)nSurrogate
);
373 if( pItem
== NULL
|| pItem
->GetName().Len() == 0 )
376 SvxUnogetApiNameForItem( XATTR_LINEEND
, pItem
->GetName(), aName
);
377 rNameSet
.insert( aName
);
381 uno::Sequence
< OUString
> SAL_CALL
SvxUnoMarkerTable::getElementNames()
382 throw( uno::RuntimeException
)
384 OGuard
aGuard( Application::GetSolarMutex() );
386 std::set
< OUString
, comphelper::UStringLess
> aNameSet
;
388 // search model pool for line starts
389 createNamesForPool( mpModelPool
, XATTR_LINESTART
, aNameSet
);
391 // search model pool for line ends
392 createNamesForPool( mpModelPool
, XATTR_LINEEND
, aNameSet
);
394 uno::Sequence
< OUString
> aSeq( aNameSet
.size() );
395 OUString
* pNames
= aSeq
.getArray();
397 std::set
< OUString
, comphelper::UStringLess
>::iterator
aIter( aNameSet
.begin() );
398 const std::set
< OUString
, comphelper::UStringLess
>::iterator
aEnd( aNameSet
.end() );
400 while( aIter
!= aEnd
)
402 *pNames
++ = *aIter
++;
408 sal_Bool SAL_CALL
SvxUnoMarkerTable::hasByName( const OUString
& aName
)
409 throw( uno::RuntimeException
)
411 OGuard
aGuard( Application::GetSolarMutex() );
413 if( aName
.getLength() == 0 )
420 SvxUnogetInternalNameForItem( XATTR_LINESTART
, aName
, aSearchName
);
421 USHORT nStartCount
= mpModelPool
? mpModelPool
->GetItemCount( XATTR_LINESTART
) : 0;
423 for( nSurrogate
= 0; nSurrogate
< nStartCount
; nSurrogate
++ )
425 pItem
= (NameOrIndex
*)mpModelPool
->GetItem( XATTR_LINESTART
, nSurrogate
);
426 if( pItem
&& pItem
->GetName() == aSearchName
)
430 SvxUnogetInternalNameForItem( XATTR_LINEEND
, aName
, aSearchName
);
431 USHORT nEndCount
= mpModelPool
? mpModelPool
->GetItemCount( XATTR_LINEEND
) : 0;
432 for( nSurrogate
= 0; nSurrogate
< nEndCount
; nSurrogate
++ )
434 pItem
= (NameOrIndex
*)mpModelPool
->GetItem( XATTR_LINEEND
, nSurrogate
);
435 if( pItem
&& pItem
->GetName() == aSearchName
)
443 uno::Type SAL_CALL
SvxUnoMarkerTable::getElementType( )
444 throw( uno::RuntimeException
)
446 return ::getCppuType((const drawing::PointSequence
*)0);
449 sal_Bool SAL_CALL
SvxUnoMarkerTable::hasElements( )
450 throw( uno::RuntimeException
)
452 OGuard
aGuard( Application::GetSolarMutex() );
456 const USHORT nStartCount
= mpModelPool
? mpModelPool
->GetItemCount( XATTR_LINESTART
) : 0;
458 for( nSurrogate
= 0; nSurrogate
< nStartCount
; nSurrogate
++ )
460 pItem
= (NameOrIndex
*)mpModelPool
->GetItem( XATTR_LINESTART
, nSurrogate
);
461 if( pItem
&& pItem
->GetName().Len() != 0 )
465 const USHORT nEndCount
= mpModelPool
? mpModelPool
->GetItemCount( XATTR_LINEEND
) : 0;
466 for( nSurrogate
= 0; nSurrogate
< nEndCount
; nSurrogate
++ )
468 pItem
= (NameOrIndex
*)mpModelPool
->GetItem( XATTR_LINEEND
, nSurrogate
);
469 if( pItem
&& pItem
->GetName().Len() != 0 )
477 * Create a hatchtable
479 uno::Reference
< uno::XInterface
> SAL_CALL
SvxUnoMarkerTable_createInstance( SdrModel
* pModel
)
481 return *new SvxUnoMarkerTable(pModel
);