1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
3 * This file is part of the LibreOffice project.
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/.
9 * This file incorporates work covered by the following license notice:
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 .
20 #include <com/sun/star/beans/XPropertySet.hpp>
21 #include <svl/eitem.hxx>
23 #include <svl/itemprop.hxx>
25 #include <editeng/unoipset.hxx>
26 #include <editeng/editids.hrc>
27 #include <editeng/editeng.hxx>
28 #include <svl/itempool.hxx>
29 #include <osl/diagnose.h>
32 using namespace ::com::sun::star
;
36 struct SvxIDPropertyCombine
43 SvxItemPropertySet::SvxItemPropertySet( const SfxItemPropertyMapEntry
* pMap
, SfxItemPool
& rItemPool
, bool bConvertTwips
)
44 : m_aPropertyMap( pMap
),
45 _pMap(pMap
), mbConvertTwips(bConvertTwips
), mrItemPool( rItemPool
)
50 SvxItemPropertySet::~SvxItemPropertySet()
56 uno::Any
* SvxItemPropertySet::GetUsrAnyForID(sal_uInt16 nWID
) const
58 for ( size_t i
= 0, n
= aCombineList
.size(); i
< n
; ++i
)
60 SvxIDPropertyCombine
* pActual
= aCombineList
[ i
];
61 if( pActual
->nWID
== nWID
)
62 return &pActual
->aAny
;
68 void SvxItemPropertySet::AddUsrAnyForID(const uno::Any
& rAny
, sal_uInt16 nWID
)
70 SvxIDPropertyCombine
* pNew
= new SvxIDPropertyCombine
;
73 aCombineList
.push_back( pNew
);
78 void SvxItemPropertySet::ClearAllUsrAny()
80 for ( size_t i
= 0, n
= aCombineList
.size(); i
< n
; ++i
)
81 delete aCombineList
[ i
];
87 bool SvxUnoCheckForPositiveValue( const uno::Any
& rVal
)
89 bool bConvert
= true; // the default is that all metric items must be converted
92 bConvert
= (nValue
> 0);
98 uno::Any
SvxItemPropertySet::getPropertyValue( const SfxItemPropertySimpleEntry
* pMap
, const SfxItemSet
& rSet
, bool bSearchInParent
, bool bDontConvertNegativeValues
)
101 if(!pMap
|| !pMap
->nWID
)
104 const SfxPoolItem
* pItem
= 0;
105 SfxItemPool
* pPool
= rSet
.GetPool();
106 rSet
.GetItemState( pMap
->nWID
, bSearchInParent
, &pItem
);
107 if( NULL
== pItem
&& pPool
)
108 pItem
= &(pPool
->GetDefaultItem( pMap
->nWID
));
110 const SfxMapUnit eMapUnit
= pPool
? pPool
->GetMetric((sal_uInt16
)pMap
->nWID
) : SFX_MAPUNIT_100TH_MM
;
111 sal_uInt8 nMemberId
= pMap
->nMemberId
& (~SFX_METRIC_ITEM
);
112 if( eMapUnit
== SFX_MAPUNIT_100TH_MM
)
113 nMemberId
&= (~CONVERT_TWIPS
);
117 pItem
->QueryValue( aVal
, nMemberId
);
118 if( pMap
->nMemberId
& SFX_METRIC_ITEM
)
120 if( eMapUnit
!= SFX_MAPUNIT_100TH_MM
)
122 if ( !bDontConvertNegativeValues
|| SvxUnoCheckForPositiveValue( aVal
) )
123 SvxUnoConvertToMM( eMapUnit
, aVal
);
126 else if ( pMap
->aType
.getTypeClass() == uno::TypeClass_ENUM
&&
127 aVal
.getValueType() == ::cppu::UnoType
<sal_Int32
>::get() )
129 // convert typeless SfxEnumItem to enum type
132 aVal
.setValue( &nEnum
, pMap
->aType
);
137 OSL_FAIL( "No SfxPoolItem found for property!" );
144 void SvxItemPropertySet::setPropertyValue( const SfxItemPropertySimpleEntry
* pMap
, const uno::Any
& rVal
, SfxItemSet
& rSet
, bool bDontConvertNegativeValues
)
146 if(!pMap
|| !pMap
->nWID
)
150 const SfxPoolItem
* pItem
= 0;
151 SfxItemState eState
= rSet
.GetItemState( pMap
->nWID
, true, &pItem
);
152 SfxItemPool
* pPool
= rSet
.GetPool();
154 // Put UnoAny in the item value
155 if(eState
< SfxItemState::DEFAULT
|| pItem
== NULL
)
159 OSL_FAIL( "No default item and no pool?" );
163 pItem
= &pPool
->GetDefaultItem( pMap
->nWID
);
166 DBG_ASSERT( pItem
, "Got no default for item!" );
169 uno::Any
aValue( rVal
);
171 const SfxMapUnit eMapUnit
= pPool
? pPool
->GetMetric((sal_uInt16
)pMap
->nWID
) : SFX_MAPUNIT_100TH_MM
;
173 // check for needed metric translation
174 if( (pMap
->nMemberId
& SFX_METRIC_ITEM
) && eMapUnit
!= SFX_MAPUNIT_100TH_MM
)
176 if ( !bDontConvertNegativeValues
|| SvxUnoCheckForPositiveValue( aValue
) )
177 SvxUnoConvertFromMM( eMapUnit
, aValue
);
180 SfxPoolItem
*pNewItem
= pItem
->Clone();
182 sal_uInt8 nMemberId
= pMap
->nMemberId
& (~SFX_METRIC_ITEM
);
183 if( eMapUnit
== SFX_MAPUNIT_100TH_MM
)
184 nMemberId
&= (~CONVERT_TWIPS
);
186 if( pNewItem
->PutValue( aValue
, nMemberId
) )
188 // Set new item in item set
189 rSet
.Put( *pNewItem
, pMap
->nWID
);
196 uno::Any
SvxItemPropertySet::getPropertyValue( const SfxItemPropertySimpleEntry
* pMap
) const
198 // Already entered a value? Then finish quickly
199 uno::Any
* pUsrAny
= GetUsrAnyForID(pMap
->nWID
);
203 // No UsrAny detected yet, generate Default entry and return this
204 const SfxMapUnit eMapUnit
= mrItemPool
.GetMetric((sal_uInt16
)pMap
->nWID
);
205 sal_uInt8 nMemberId
= pMap
->nMemberId
& (~SFX_METRIC_ITEM
);
206 if( eMapUnit
== SFX_MAPUNIT_100TH_MM
)
207 nMemberId
&= (~CONVERT_TWIPS
);
209 SfxItemSet
aSet( mrItemPool
, pMap
->nWID
, pMap
->nWID
);
211 if( (pMap
->nWID
< OWN_ATTR_VALUE_START
) && (pMap
->nWID
> OWN_ATTR_VALUE_END
) )
213 // Get Default from ItemPool
214 if(SfxItemPool::IsWhich(pMap
->nWID
))
215 aSet
.Put(mrItemPool
.GetDefaultItem(pMap
->nWID
));
220 const SfxPoolItem
* pItem
= NULL
;
221 SfxItemState eState
= aSet
.GetItemState( pMap
->nWID
, true, &pItem
);
222 if(eState
>= SfxItemState::DEFAULT
&& pItem
)
224 pItem
->QueryValue( aVal
, nMemberId
);
225 const_cast<SvxItemPropertySet
*>(this)->AddUsrAnyForID(aVal
, pMap
->nWID
);
229 if( pMap
->nMemberId
& SFX_METRIC_ITEM
)
231 // check for needed metric translation
232 if(pMap
->nMemberId
& SFX_METRIC_ITEM
&& eMapUnit
!= SFX_MAPUNIT_100TH_MM
)
234 SvxUnoConvertToMM( eMapUnit
, aVal
);
238 if ( pMap
->aType
.getTypeClass() == uno::TypeClass_ENUM
&&
239 aVal
.getValueType() == ::cppu::UnoType
<sal_Int32
>::get() )
244 aVal
.setValue( &nEnum
, pMap
->aType
);
252 void SvxItemPropertySet::setPropertyValue( const SfxItemPropertySimpleEntry
* pMap
, const uno::Any
& rVal
) const
254 uno::Any
* pUsrAny
= GetUsrAnyForID(pMap
->nWID
);
256 const_cast<SvxItemPropertySet
*>(this)->AddUsrAnyForID(rVal
, pMap
->nWID
);
263 const SfxItemPropertySimpleEntry
* SvxItemPropertySet::getPropertyMapEntry(const OUString
&rName
) const
265 return m_aPropertyMap
.getByName( rName
);
270 uno::Reference
< beans::XPropertySetInfo
> SvxItemPropertySet::getPropertySetInfo() const
273 m_xInfo
= new SfxItemPropertySetInfo( m_aPropertyMap
);
280 #define TWIPS_TO_MM(val) ((val * 127 + 36) / 72)
283 #define MM_TO_TWIPS(val) ((val * 72 + 63) / 127)
286 /** converts the given any with a metric to 100th/mm if needed */
287 void SvxUnoConvertToMM( const SfxMapUnit eSourceMapUnit
, uno::Any
& rMetric
) throw()
289 // map the metric of the itempool to 100th mm
290 switch(eSourceMapUnit
)
292 case SFX_MAPUNIT_TWIP
:
294 switch( rMetric
.getValueTypeClass() )
296 case uno::TypeClass_BYTE
:
297 rMetric
<<= (sal_Int8
)(TWIPS_TO_MM(*static_cast<sal_Int8
const *>(rMetric
.getValue())));
299 case uno::TypeClass_SHORT
:
300 rMetric
<<= (sal_Int16
)(TWIPS_TO_MM(*static_cast<sal_Int16
const *>(rMetric
.getValue())));
302 case uno::TypeClass_UNSIGNED_SHORT
:
303 rMetric
<<= (sal_uInt16
)(TWIPS_TO_MM(*static_cast<sal_uInt16
const *>(rMetric
.getValue())));
305 case uno::TypeClass_LONG
:
306 rMetric
<<= (sal_Int32
)(TWIPS_TO_MM(*static_cast<sal_Int32
const *>(rMetric
.getValue())));
308 case uno::TypeClass_UNSIGNED_LONG
:
309 rMetric
<<= (sal_uInt32
)(TWIPS_TO_MM(*static_cast<sal_uInt32
const *>(rMetric
.getValue())));
312 OSL_FAIL("AW: Missing unit translation to 100th mm!");
318 OSL_FAIL("AW: Missing unit translation to 100th mm!");
325 /** converts the given any with a metric from 100th/mm to the given metric if needed */
326 void SvxUnoConvertFromMM( const SfxMapUnit eDestinationMapUnit
, uno::Any
& rMetric
) throw()
328 switch(eDestinationMapUnit
)
330 case SFX_MAPUNIT_TWIP
:
332 switch( rMetric
.getValueTypeClass() )
334 case uno::TypeClass_BYTE
:
335 rMetric
<<= (sal_Int8
)(MM_TO_TWIPS(*static_cast<sal_Int8
const *>(rMetric
.getValue())));
337 case uno::TypeClass_SHORT
:
338 rMetric
<<= (sal_Int16
)(MM_TO_TWIPS(*static_cast<sal_Int16
const *>(rMetric
.getValue())));
340 case uno::TypeClass_UNSIGNED_SHORT
:
341 rMetric
<<= (sal_uInt16
)(MM_TO_TWIPS(*static_cast<sal_uInt16
const *>(rMetric
.getValue())));
343 case uno::TypeClass_LONG
:
344 rMetric
<<= (sal_Int32
)(MM_TO_TWIPS(*static_cast<sal_Int32
const *>(rMetric
.getValue())));
346 case uno::TypeClass_UNSIGNED_LONG
:
347 rMetric
<<= (sal_uInt32
)(MM_TO_TWIPS(*static_cast<sal_uInt32
const *>(rMetric
.getValue())));
350 OSL_FAIL("AW: Missing unit translation to 100th mm!");
356 OSL_FAIL("AW: Missing unit translation to PoolMetrics!");
361 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */