vcl: Drop local var pointing to self in WindowData ctor
[LibreOffice.git] / editeng / source / uno / unonrule.cxx
blob75f2599c59a7c79ac91ac8a976178ccd11407488
1 /* -*- Mode: C++; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
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 <sal/config.h>
22 #include <com/sun/star/awt/FontDescriptor.hpp>
23 #include <com/sun/star/beans/PropertyValue.hpp>
24 #include <com/sun/star/lang/IllegalArgumentException.hpp>
25 #include <com/sun/star/lang/IndexOutOfBoundsException.hpp>
26 #include <com/sun/star/text/HoriOrientation.hpp>
27 #include <com/sun/star/awt/XBitmap.hpp>
28 #include <com/sun/star/graphic/XGraphic.hpp>
29 #include <cppuhelper/supportsservice.hxx>
30 #include <cppuhelper/implbase1.hxx>
31 #include <utility>
32 #include <vcl/font.hxx>
33 #include <vcl/svapp.hxx>
34 #include <vcl/graph.hxx>
35 #include <vcl/GraphicObject.hxx>
36 #include <vcl/GraphicLoader.hxx>
37 #include <tools/debug.hxx>
39 #include <editeng/brushitem.hxx>
40 #include <editeng/unoprnms.hxx>
41 #include <editeng/numitem.hxx>
42 #include <editeng/unofdesc.hxx>
43 #include <editeng/unonrule.hxx>
44 #include <editeng/editids.hrc>
45 #include <o3tl/enumarray.hxx>
46 #include <o3tl/temporary.hxx>
47 #include <memory>
49 using ::com::sun::star::util::XCloneable;
50 using ::com::sun::star::ucb::XAnyCompare;
53 using namespace ::com::sun::star;
54 using namespace ::com::sun::star::uno;
55 using namespace ::com::sun::star::lang;
56 using namespace ::com::sun::star::container;
58 const SvxAdjust aUnoToSvxAdjust[] =
60 SvxAdjust::Left,
61 SvxAdjust::Right,
62 SvxAdjust::Center,
63 SvxAdjust::Left,
64 SvxAdjust::Left,
65 SvxAdjust::Left,
66 SvxAdjust::Block
69 const o3tl::enumarray<SvxAdjust, sal_Int16> aSvxToUnoAdjust
71 text::HoriOrientation::LEFT,
72 text::HoriOrientation::RIGHT,
73 text::HoriOrientation::FULL,
74 text::HoriOrientation::CENTER,
75 text::HoriOrientation::FULL,
76 text::HoriOrientation::LEFT
79 static SvxAdjust ConvertUnoAdjust( unsigned short nAdjust )
81 DBG_ASSERT( nAdjust <= 7, "Enum has changed! [CL]" );
82 return aUnoToSvxAdjust[nAdjust];
85 static unsigned short ConvertUnoAdjust( SvxAdjust eAdjust )
87 DBG_ASSERT( static_cast<int>(eAdjust) <= 6, "Enum has changed! [CL]" );
88 return aSvxToUnoAdjust[eAdjust];
91 SvxUnoNumberingRules::SvxUnoNumberingRules(SvxNumRule aRule)
92 : maRule(std::move( aRule ))
96 SvxUnoNumberingRules::~SvxUnoNumberingRules() noexcept
100 //XIndexReplace
101 void SAL_CALL SvxUnoNumberingRules::replaceByIndex( sal_Int32 Index, const uno::Any& Element )
103 SolarMutexGuard aGuard;
105 if( Index < 0 || Index >= maRule.GetLevelCount() )
106 throw IndexOutOfBoundsException();
108 Sequence< beans::PropertyValue > aSeq;
110 if( !( Element >>= aSeq) )
111 throw IllegalArgumentException();
112 setNumberingRuleByIndex( aSeq, Index );
115 // XIndexAccess
116 sal_Int32 SAL_CALL SvxUnoNumberingRules::getCount()
118 SolarMutexGuard aGuard;
120 return maRule.GetLevelCount();
123 Any SAL_CALL SvxUnoNumberingRules::getByIndex( sal_Int32 Index )
125 SolarMutexGuard aGuard;
127 if( Index < 0 || Index >= maRule.GetLevelCount() )
128 throw IndexOutOfBoundsException();
130 return Any( getNumberingRuleByIndex(Index) );
133 //XElementAccess
134 Type SAL_CALL SvxUnoNumberingRules::getElementType()
136 return cppu::UnoType<Sequence< beans::PropertyValue >>::get();
139 sal_Bool SAL_CALL SvxUnoNumberingRules::hasElements()
141 return true;
144 // XAnyCompare
145 sal_Int16 SAL_CALL SvxUnoNumberingRules::compare( const Any& rAny1, const Any& rAny2 )
147 return SvxUnoNumberingRules::Compare( rAny1, rAny2 );
150 // XCloneable
151 Reference< XCloneable > SAL_CALL SvxUnoNumberingRules::createClone( )
153 return new SvxUnoNumberingRules(maRule);
156 OUString SAL_CALL SvxUnoNumberingRules::getImplementationName( )
158 return u"SvxUnoNumberingRules"_ustr;
161 sal_Bool SAL_CALL SvxUnoNumberingRules::supportsService( const OUString& ServiceName )
163 return cppu::supportsService(this, ServiceName);
166 Sequence< OUString > SAL_CALL SvxUnoNumberingRules::getSupportedServiceNames( )
168 return { u"com.sun.star.text.NumberingRules"_ustr };
171 Sequence<beans::PropertyValue> SvxUnoNumberingRules::getNumberingRuleByIndex(sal_Int32 nIndex) const
173 // NumberingRule aRule;
174 const SvxNumberFormat& rFmt = maRule.GetLevel(static_cast<sal_uInt16>(nIndex));
175 sal_uInt16 nIdx = 0;
177 const int nProps = 15;
178 std::unique_ptr<beans::PropertyValue[]> pArray(new beans::PropertyValue[nProps]);
180 Any aVal;
182 aVal <<= static_cast<sal_uInt16>(rFmt.GetNumberingType());
183 pArray[nIdx++] = beans::PropertyValue(UNO_NAME_NRULE_NUMBERINGTYPE, -1, aVal, beans::PropertyState_DIRECT_VALUE);
187 SvxAdjust eAdj = rFmt.GetNumAdjust();
188 aVal <<= ConvertUnoAdjust(eAdj);
189 pArray[nIdx++] = beans::PropertyValue(UNO_NAME_NRULE_ADJUST, -1, aVal, beans::PropertyState_DIRECT_VALUE);
193 aVal <<= rFmt.GetPrefix();
194 pArray[nIdx++] = beans::PropertyValue(UNO_NAME_NRULE_PREFIX, -1, aVal, beans::PropertyState_DIRECT_VALUE);
198 aVal <<= rFmt.GetSuffix();
199 pArray[nIdx++] = beans::PropertyValue(UNO_NAME_NRULE_SUFFIX, -1, aVal, beans::PropertyState_DIRECT_VALUE);
202 if(SVX_NUM_CHAR_SPECIAL == rFmt.GetNumberingType())
204 sal_UCS4 nCode = rFmt.GetBulletChar();
205 OUString aStr( &nCode, 1 );
206 aVal <<= aStr;
207 pArray[nIdx++] = beans::PropertyValue(u"BulletChar"_ustr, -1, aVal, beans::PropertyState_DIRECT_VALUE);
210 if( rFmt.GetBulletFont() )
212 awt::FontDescriptor aDesc;
213 SvxUnoFontDescriptor::ConvertFromFont( *rFmt.GetBulletFont(), aDesc );
214 aVal <<= aDesc;
215 pArray[nIdx++] = beans::PropertyValue(UNO_NAME_NRULE_BULLET_FONT, -1, aVal, beans::PropertyState_DIRECT_VALUE);
219 const SvxBrushItem* pBrush = rFmt.GetBrush();
220 const Graphic* pGraphic = nullptr;
221 if (pBrush)
222 pGraphic = pBrush->GetGraphic();
223 if (pGraphic)
225 uno::Reference<awt::XBitmap> xBitmap(pGraphic->GetXGraphic(), uno::UNO_QUERY);
226 aVal <<= xBitmap;
228 pArray[nIdx++] = beans::PropertyValue(u"GraphicBitmap"_ustr, -1, aVal, beans::PropertyState_DIRECT_VALUE);
233 const Size aSize( rFmt.GetGraphicSize() );
234 const awt::Size aUnoSize( aSize.Width(), aSize.Height() );
235 aVal <<= aUnoSize;
236 pArray[nIdx++] = beans::PropertyValue(u"GraphicSize"_ustr, -1, aVal, beans::PropertyState_DIRECT_VALUE);
239 aVal <<= static_cast<sal_Int16>(rFmt.GetStart());
240 pArray[nIdx++] = beans::PropertyValue(UNO_NAME_NRULE_START_WITH, -1, aVal, beans::PropertyState_DIRECT_VALUE);
242 aVal <<= rFmt.GetAbsLSpace();
243 pArray[nIdx++] = beans::PropertyValue(UNO_NAME_NRULE_LEFT_MARGIN, -1, aVal, beans::PropertyState_DIRECT_VALUE);
245 aVal <<= rFmt.GetFirstLineOffset();
246 pArray[nIdx++] = beans::PropertyValue(UNO_NAME_NRULE_FIRST_LINE_OFFSET, -1, aVal, beans::PropertyState_DIRECT_VALUE);
248 pArray[nIdx++] = beans::PropertyValue(u"SymbolTextDistance"_ustr, -1, aVal, beans::PropertyState_DIRECT_VALUE);
250 aVal <<= rFmt.GetBulletColor();
251 pArray[nIdx++] = beans::PropertyValue(UNO_NAME_NRULE_BULLET_COLOR, -1, aVal, beans::PropertyState_DIRECT_VALUE);
253 aVal <<= static_cast<sal_Int16>(rFmt.GetBulletRelSize());
254 pArray[nIdx++] = beans::PropertyValue(UNO_NAME_NRULE_BULLET_RELSIZE, -1, aVal, beans::PropertyState_DIRECT_VALUE);
256 DBG_ASSERT( nIdx <= nProps, "FixMe: overflow in Array!!! [CL]" );
257 Sequence< beans::PropertyValue> aSeq(pArray.get(), nIdx);
259 return aSeq;
262 void SvxUnoNumberingRules::setNumberingRuleByIndex(const Sequence<beans::PropertyValue >& rProperties, sal_Int32 nIndex)
264 SvxNumberFormat aFmt(maRule.GetLevel( static_cast<sal_uInt16>(nIndex) ));
265 for(const beans::PropertyValue& rProp : rProperties)
267 const OUString& rPropName = rProp.Name;
268 const Any& aVal = rProp.Value;
270 if ( rPropName == UNO_NAME_NRULE_NUMBERINGTYPE )
272 sal_Int16 nSet = sal_Int16();
273 aVal >>= nSet;
275 // There is no reason to limit numbering types.
276 if ( nSet>=0 )
278 aFmt.SetNumberingType(static_cast<SvxNumType>(nSet));
279 continue;
282 else if ( rPropName == UNO_NAME_NRULE_PREFIX )
284 OUString aPrefix;
285 if( aVal >>= aPrefix )
287 aFmt.SetPrefix(aPrefix);
288 continue;
291 else if ( rPropName == UNO_NAME_NRULE_SUFFIX )
293 OUString aSuffix;
294 if( aVal >>= aSuffix )
296 aFmt.SetSuffix(aSuffix);
297 continue;
300 else if ( rPropName == UNO_NAME_NRULE_BULLETID )
302 sal_Int16 nSet = sal_Int16();
303 if( aVal >>= nSet )
305 if(nSet < 0x100)
307 aFmt.SetBulletChar(nSet);
308 continue;
312 else if ( rPropName == "BulletChar" )
314 OUString aStr;
315 if( aVal >>= aStr )
317 if(!aStr.isEmpty())
319 aFmt.SetBulletChar(aStr.iterateCodePoints(&o3tl::temporary(sal_Int32(0))));
321 else
323 aFmt.SetBulletChar(0);
325 continue;
328 else if ( rPropName == UNO_NAME_NRULE_ADJUST )
330 sal_Int16 nAdjust = sal_Int16();
331 if( aVal >>= nAdjust )
333 aFmt.SetNumAdjust(ConvertUnoAdjust( static_cast<unsigned short>(nAdjust) ));
334 continue;
337 else if ( rPropName == UNO_NAME_NRULE_BULLET_FONT )
339 awt::FontDescriptor aDesc;
340 if( aVal >>= aDesc )
342 vcl::Font aFont;
343 SvxUnoFontDescriptor::ConvertToFont( aDesc, aFont );
344 aFmt.SetBulletFont(&aFont);
345 continue;
348 else if ( rPropName == "GraphicURL" )
350 OUString aURL;
351 if (aVal >>= aURL)
353 Graphic aGraphic = vcl::graphic::loadFromURL(aURL);
354 if (!aGraphic.IsNone())
356 SvxBrushItem aBrushItem(aGraphic, GPOS_AREA, SID_ATTR_BRUSH);
357 aFmt.SetGraphicBrush(&aBrushItem);
359 continue;
362 else if ( rPropName == "GraphicBitmap" )
364 uno::Reference<awt::XBitmap> xBitmap;
365 if (aVal >>= xBitmap)
367 uno::Reference<graphic::XGraphic> xGraphic(xBitmap, uno::UNO_QUERY);
368 Graphic aGraphic(xGraphic);
369 SvxBrushItem aBrushItem(aGraphic, GPOS_AREA, SID_ATTR_BRUSH);
370 aFmt.SetGraphicBrush( &aBrushItem );
371 continue;
374 else if ( rPropName == "GraphicSize" )
376 awt::Size aUnoSize;
377 if( aVal >>= aUnoSize )
379 aFmt.SetGraphicSize( Size( aUnoSize.Width, aUnoSize.Height ) );
380 continue;
383 else if ( rPropName == UNO_NAME_NRULE_START_WITH )
385 sal_Int16 nStart = sal_Int16();
386 if( aVal >>= nStart )
388 aFmt.SetStart( nStart );
389 continue;
392 else if ( rPropName == UNO_NAME_NRULE_LEFT_MARGIN )
394 sal_Int32 nMargin = 0;
395 if( aVal >>= nMargin )
397 aFmt.SetAbsLSpace(nMargin);
398 continue;
401 else if ( rPropName == UNO_NAME_NRULE_FIRST_LINE_OFFSET )
403 sal_Int32 nMargin = 0;
404 if( aVal >>= nMargin )
406 aFmt.SetFirstLineOffset(nMargin);
407 continue;
410 else if ( rPropName == "SymbolTextDistance" )
412 sal_Int32 nTextDistance = 0;
413 if( aVal >>= nTextDistance )
415 aFmt.SetCharTextDistance(static_cast<sal_uInt16>(nTextDistance));
416 continue;
419 else if ( rPropName == UNO_NAME_NRULE_BULLET_COLOR )
421 Color aColor;
422 if( aVal >>= aColor )
424 aFmt.SetBulletColor( aColor );
425 continue;
428 else if ( rPropName == UNO_NAME_NRULE_BULLET_RELSIZE )
430 sal_Int16 nSize = sal_Int16();
431 if( aVal >>= nSize )
433 // [AOO Bug 120650] the slide content corrupt when open in Aoo
434 // [TDF# 126234] when MS Office document being imported, the value of the relative size
435 // of the bullet could be as high as 400%
436 if ((nSize>400)||(nSize<=0))
438 nSize = 100;
441 aFmt.SetBulletRelSize( static_cast<short>(nSize) );
442 continue;
445 else
447 continue;
450 throw IllegalArgumentException();
453 // check that we always have a brush item for bitmap numbering
454 if( aFmt.GetNumberingType() == SVX_NUM_BITMAP )
456 if( nullptr == aFmt.GetBrush() )
458 GraphicObject aGrafObj;
459 SvxBrushItem aBrushItem( aGrafObj, GPOS_AREA, SID_ATTR_BRUSH );
460 aFmt.SetGraphicBrush( &aBrushItem );
463 maRule.SetLevel( static_cast<sal_uInt16>(nIndex), aFmt );
466 const SvxNumRule& SvxGetNumRule( Reference< XIndexReplace > const & xRule )
468 SvxUnoNumberingRules* pRule = dynamic_cast<SvxUnoNumberingRules*>( xRule.get() );
469 if( pRule == nullptr )
470 throw IllegalArgumentException();
472 return pRule->getNumRule();
475 css::uno::Reference< css::container::XIndexReplace > SvxCreateNumRule(const SvxNumRule& rRule)
477 return new SvxUnoNumberingRules( rRule );
480 namespace {
482 class SvxUnoNumberingRulesCompare : public ::cppu::WeakImplHelper< XAnyCompare >
484 public:
485 virtual sal_Int16 SAL_CALL compare( const Any& Any1, const Any& Any2 ) override;
490 sal_Int16 SAL_CALL SvxUnoNumberingRulesCompare::compare( const Any& Any1, const Any& Any2 )
492 return SvxUnoNumberingRules::Compare( Any1, Any2 );
495 sal_Int16 SvxUnoNumberingRules::Compare( const Any& Any1, const Any& Any2 )
497 Reference< XIndexReplace > x1( Any1, UNO_QUERY ), x2( Any2, UNO_QUERY );
498 if( !x1 || !x2 )
499 return -1;
501 if( x1.get() == x2.get() )
502 return 0;
504 SvxUnoNumberingRules* pRule1 = dynamic_cast<SvxUnoNumberingRules*>( x1.get() );
505 if( !pRule1 )
506 return -1;
507 SvxUnoNumberingRules* pRule2 = dynamic_cast<SvxUnoNumberingRules*>( x2.get() );
508 if( !pRule2 )
509 return -1;
511 const SvxNumRule& rRule1 = pRule1->getNumRule();
512 const SvxNumRule& rRule2 = pRule2->getNumRule();
514 const sal_uInt16 nLevelCount1 = rRule1.GetLevelCount();
515 const sal_uInt16 nLevelCount2 = rRule2.GetLevelCount();
517 if( nLevelCount1 == 0 || nLevelCount2 == 0 )
518 return -1;
520 for( sal_uInt16 i = 0; (i < nLevelCount1) && (i < nLevelCount2); i++ )
522 if( rRule1.GetLevel(i) != rRule2.GetLevel(i) )
523 return -1;
525 return 0;
528 Reference< XAnyCompare > SvxCreateNumRuleCompare() noexcept
530 return new SvxUnoNumberingRulesCompare;
533 css::uno::Reference< css::container::XIndexReplace > SvxCreateNumRule()
535 SvxNumRule aTempRule( SvxNumRuleFlags::NONE, 10, false );
536 return SvxCreateNumRule( aTempRule );
539 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */