nss: upgrade to release 3.73
[LibreOffice.git] / writerfilter / source / ooxml / OOXMLPropertySet.cxx
blob1d1724c9c4513546f0e40de8ff2e69e7fff76f3f
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 "OOXMLPropertySet.hxx"
21 #include <stdio.h>
22 #include <iostream>
23 #include <ooxml/QNameToString.hxx>
24 #include <com/sun/star/drawing/XShape.hpp>
25 #include <sax/tools/converter.hxx>
26 #include <tools/color.hxx>
28 namespace writerfilter::ooxml
30 using namespace ::std;
31 using namespace com::sun::star;
33 OOXMLProperty::OOXMLProperty(Id id, const OOXMLValue::Pointer_t& pValue,
34 OOXMLProperty::Type_t eType)
35 : mId(id), mpValue(pValue), meType(eType)
39 OOXMLProperty::~OOXMLProperty()
43 sal_uInt32 OOXMLProperty::getId() const
45 return mId;
48 Value::Pointer_t OOXMLProperty::getValue()
50 Value::Pointer_t pResult;
52 if (mpValue)
53 pResult = Value::Pointer_t(mpValue->clone());
54 else
55 pResult = Value::Pointer_t(new OOXMLValue());
57 return pResult;
60 writerfilter::Reference<Properties>::Pointer_t OOXMLProperty::getProps()
62 writerfilter::Reference<Properties>::Pointer_t pResult;
64 if (mpValue)
65 pResult = mpValue->getProperties();
67 return pResult;
70 #ifdef DBG_UTIL
71 string OOXMLProperty::getName() const
73 string sResult(QNameToString(mId));
75 if (sResult.length() == 0)
76 sResult = fastTokenToId(mId);
78 if (sResult.length() == 0)
80 static char sBuffer[256];
82 snprintf(sBuffer, sizeof(sBuffer), "%" SAL_PRIxUINT32, mId);
83 sResult = sBuffer;
86 return sResult;
88 #endif
90 #ifdef DBG_UTIL
91 string OOXMLProperty::toString() const
93 string sResult = "(";
95 sResult += getName();
96 sResult += ", ";
97 if (mpValue)
98 sResult += mpValue->toString();
99 else
100 sResult +="(null)";
101 sResult +=")";
103 return sResult;
105 #endif
107 void OOXMLProperty::resolve(writerfilter::Properties & rProperties)
109 switch (meType)
111 case SPRM:
112 if (mId != 0x0)
113 rProperties.sprm(*this);
114 break;
115 case ATTRIBUTE:
116 rProperties.attribute(mId, *getValue());
117 break;
122 class OOXMLValue
125 OOXMLValue::OOXMLValue()
129 OOXMLValue::~OOXMLValue()
133 int OOXMLValue::getInt() const
135 return 0;
138 OUString OOXMLValue::getString() const
140 return OUString();
143 uno::Any OOXMLValue::getAny() const
145 return uno::Any();
148 writerfilter::Reference<Properties>::Pointer_t OOXMLValue::getProperties()
150 return writerfilter::Reference<Properties>::Pointer_t();
153 writerfilter::Reference<BinaryObj>::Pointer_t OOXMLValue::getBinary()
155 return writerfilter::Reference<BinaryObj>::Pointer_t();
158 #ifdef DBG_UTIL
159 string OOXMLValue::toString() const
161 return "OOXMLValue";
163 #endif
165 OOXMLValue * OOXMLValue::clone() const
167 return new OOXMLValue(*this);
171 class OOXMLBinaryValue
174 OOXMLBinaryValue::OOXMLBinaryValue(OOXMLBinaryObjectReference::Pointer_t const &
175 pBinaryObj)
176 : mpBinaryObj(pBinaryObj)
180 OOXMLBinaryValue::~OOXMLBinaryValue()
184 writerfilter::Reference<BinaryObj>::Pointer_t OOXMLBinaryValue::getBinary()
186 return mpBinaryObj;
189 #ifdef DBG_UTIL
190 string OOXMLBinaryValue::toString() const
192 return "BinaryObj";
194 #endif
196 OOXMLValue * OOXMLBinaryValue::clone() const
198 return new OOXMLBinaryValue(mpBinaryObj);
202 class OOXMLBooleanValue
205 static bool GetBooleanValue(const char *pValue)
207 return !strcmp(pValue, "true")
208 || !strcmp(pValue, "True")
209 || !strcmp(pValue, "1")
210 || !strcmp(pValue, "on")
211 || !strcmp(pValue, "On");
214 OOXMLValue::Pointer_t const & OOXMLBooleanValue::Create(bool bValue)
216 static OOXMLValue::Pointer_t False(new OOXMLBooleanValue (false));
217 static OOXMLValue::Pointer_t True(new OOXMLBooleanValue (true));
219 return bValue ? True : False;
222 OOXMLValue::Pointer_t const & OOXMLBooleanValue::Create(const char *pValue)
224 return Create (GetBooleanValue(pValue));
227 OOXMLBooleanValue::OOXMLBooleanValue(bool bValue)
228 : mbValue(bValue)
232 OOXMLBooleanValue::~OOXMLBooleanValue()
236 int OOXMLBooleanValue::getInt() const
238 return mbValue ? 1 : 0;
241 uno::Any OOXMLBooleanValue::getAny() const
243 return uno::Any(mbValue);
246 #ifdef DBG_UTIL
247 string OOXMLBooleanValue::toString() const
249 return mbValue ? "true" : "false";
251 #endif
253 OOXMLValue * OOXMLBooleanValue::clone() const
255 return new OOXMLBooleanValue(*this);
259 class OOXMLStringValue
262 OOXMLStringValue::OOXMLStringValue(const OUString & rStr)
263 : mStr(rStr)
267 OOXMLStringValue::~OOXMLStringValue()
271 uno::Any OOXMLStringValue::getAny() const
273 return uno::Any(mStr);
276 OUString OOXMLStringValue::getString() const
278 return mStr;
281 #ifdef DBG_UTIL
282 string OOXMLStringValue::toString() const
284 return OUStringToOString(mStr, RTL_TEXTENCODING_ASCII_US).getStr();
286 #endif
288 OOXMLValue * OOXMLStringValue::clone() const
290 return new OOXMLStringValue(*this);
294 class OOXMLInputStreamValue
296 OOXMLInputStreamValue::OOXMLInputStreamValue(uno::Reference<io::XInputStream> const & xInputStream)
297 : mxInputStream(xInputStream)
301 OOXMLInputStreamValue::~OOXMLInputStreamValue()
305 uno::Any OOXMLInputStreamValue::getAny() const
307 return uno::Any(mxInputStream);
310 #ifdef DBG_UTIL
311 string OOXMLInputStreamValue::toString() const
313 return "InputStream";
315 #endif
317 OOXMLValue * OOXMLInputStreamValue::clone() const
319 return new OOXMLInputStreamValue(mxInputStream);
323 class OOXMLPropertySet
326 OOXMLPropertySet::OOXMLPropertySet()
330 OOXMLPropertySet::~OOXMLPropertySet()
334 void OOXMLPropertySet::resolve(Properties & rHandler)
336 // The pProp->resolve(rHandler) call below can cause elements to
337 // be appended to mProperties. I don't think it can cause elements
338 // to be deleted. But let's check with < here just to be safe that
339 // the indexing below works.
340 for (size_t nIt = 0; nIt < mProperties.size(); ++nIt)
342 OOXMLProperty::Pointer_t pProp = mProperties[nIt];
344 if (pProp)
345 pProp->resolve(rHandler);
349 OOXMLPropertySet::OOXMLProperties_t::iterator OOXMLPropertySet::begin()
351 return mProperties.begin();
354 OOXMLPropertySet::OOXMLProperties_t::iterator OOXMLPropertySet::end()
356 return mProperties.end();
359 OOXMLPropertySet::OOXMLProperties_t::const_iterator
360 OOXMLPropertySet::begin() const
362 return mProperties.begin();
365 OOXMLPropertySet::OOXMLProperties_t::const_iterator
366 OOXMLPropertySet::end() const
368 return mProperties.end();
371 void OOXMLPropertySet::add(const OOXMLProperty::Pointer_t& pProperty)
373 if (pProperty && pProperty->getId() != 0x0)
375 mProperties.push_back(pProperty);
379 void OOXMLPropertySet::add(Id id, const OOXMLValue::Pointer_t& pValue, OOXMLProperty::Type_t eType)
381 OOXMLProperty::Pointer_t pProperty(new OOXMLProperty(id, pValue, eType));
382 add(pProperty);
385 void OOXMLPropertySet::add(const OOXMLPropertySet::Pointer_t& pPropertySet)
387 const OOXMLPropertySet * pSet = pPropertySet.get();
389 if (pSet != nullptr)
391 mProperties.insert( mProperties.end(), pSet->mProperties.begin(), pSet->mProperties.end() );
395 OOXMLPropertySet * OOXMLPropertySet::clone() const
397 return new OOXMLPropertySet(*this);
400 #ifdef DBG_UTIL
401 string OOXMLPropertySet::toString()
403 string sResult = "[";
404 char sBuffer[256];
405 snprintf(sBuffer, sizeof(sBuffer), "%p", this);
406 sResult += sBuffer;
407 sResult += ":";
409 OOXMLProperties_t::iterator aItBegin = begin();
410 OOXMLProperties_t::iterator aItEnd = end();
412 for (OOXMLProperties_t::iterator aIt = aItBegin; aIt != aItEnd; ++aIt)
414 if (aIt != aItBegin)
415 sResult += ", ";
417 if (*aIt)
418 sResult += (*aIt)->toString();
419 else
420 sResult += "0x0";
423 sResult += "]";
425 return sResult;
427 #endif
430 class OOXMLPropertySetValue
433 OOXMLPropertySetValue::OOXMLPropertySetValue(const OOXMLPropertySet::Pointer_t& pPropertySet)
434 : mpPropertySet(pPropertySet)
438 OOXMLPropertySetValue::~OOXMLPropertySetValue()
442 writerfilter::Reference<Properties>::Pointer_t OOXMLPropertySetValue::getProperties()
444 return writerfilter::Reference<Properties>::Pointer_t
445 (mpPropertySet->clone());
448 #ifdef DBG_UTIL
449 string OOXMLPropertySetValue::toString() const
451 char sBuffer[256];
453 snprintf(sBuffer, sizeof(sBuffer), "t:%p, m:%p", this, mpPropertySet.get());
455 return "OOXMLPropertySetValue(" + string(sBuffer) + ")";
457 #endif
459 OOXMLValue * OOXMLPropertySetValue::clone() const
461 return new OOXMLPropertySetValue(*this);
465 class OOXMLIntegerValue
468 OOXMLValue::Pointer_t OOXMLIntegerValue::Create(sal_Int32 nValue)
470 static OOXMLValue::Pointer_t Zero(new OOXMLIntegerValue (0));
471 static OOXMLValue::Pointer_t One(new OOXMLIntegerValue (1));
472 static OOXMLValue::Pointer_t Two(new OOXMLIntegerValue (2));
473 static OOXMLValue::Pointer_t Three(new OOXMLIntegerValue (3));
474 static OOXMLValue::Pointer_t Four(new OOXMLIntegerValue (4));
475 static OOXMLValue::Pointer_t Five(new OOXMLIntegerValue (5));
476 static OOXMLValue::Pointer_t Six(new OOXMLIntegerValue (6));
477 static OOXMLValue::Pointer_t Seven(new OOXMLIntegerValue (7));
478 static OOXMLValue::Pointer_t Eight(new OOXMLIntegerValue (8));
479 static OOXMLValue::Pointer_t Nine(new OOXMLIntegerValue (9));
481 switch (nValue) {
482 case 0: return Zero;
483 case 1: return One;
484 case 2: return Two;
485 case 3: return Three;
486 case 4: return Four;
487 case 5: return Five;
488 case 6: return Six;
489 case 7: return Seven;
490 case 8: return Eight;
491 case 9: return Nine;
492 default: break;
495 OOXMLValue::Pointer_t value(new OOXMLIntegerValue(nValue));
497 return value;
500 OOXMLIntegerValue::OOXMLIntegerValue(sal_Int32 nValue)
501 : mnValue(nValue)
505 OOXMLIntegerValue::~OOXMLIntegerValue()
509 int OOXMLIntegerValue::getInt() const
511 return mnValue;
514 uno::Any OOXMLIntegerValue::getAny() const
516 return uno::Any(mnValue);
519 OOXMLValue * OOXMLIntegerValue::clone() const
521 return new OOXMLIntegerValue(*this);
524 #ifdef DBG_UTIL
525 string OOXMLIntegerValue::toString() const
527 char buffer[256];
528 snprintf(buffer, sizeof(buffer), "%" SAL_PRIdINT32, mnValue);
530 return buffer;
532 #endif
535 class OOXMLHexValue
538 OOXMLHexValue::OOXMLHexValue(sal_uInt32 nValue)
539 : mnValue(nValue)
543 OOXMLHexValue::OOXMLHexValue(const char * pValue)
544 : mnValue(rtl_str_toUInt32(pValue, 16))
548 OOXMLHexValue::~OOXMLHexValue()
552 int OOXMLHexValue::getInt() const
554 return mnValue;
557 OOXMLValue * OOXMLHexValue::clone() const
559 return new OOXMLHexValue(*this);
562 #ifdef DBG_UTIL
563 string OOXMLHexValue::toString() const
565 char buffer[256];
566 snprintf(buffer, sizeof(buffer), "0x%" SAL_PRIxUINT32, mnValue);
568 return buffer;
570 #endif
573 class OOXMLHexColorValue
575 OOXMLHexColorValue::OOXMLHexColorValue(const char * pValue)
576 : OOXMLHexValue(sal_uInt32(COL_AUTO))
578 if (!strcmp(pValue, "auto"))
579 return;
581 mnValue = rtl_str_toUInt32(pValue, 16);
583 // Convert hash-encoded values (like #FF0080)
584 const sal_Int32 nLen = strlen(pValue);
585 if ( !mnValue && nLen > 1 && pValue[0] == '#' )
587 sal_Int32 nColor(COL_AUTO);
588 // Word appears to require strict 6 digit length, else it ignores it
589 if ( nLen == 7 )
591 const OUString sHashColor(pValue, nLen, RTL_TEXTENCODING_ASCII_US);
592 sax::Converter::convertColor( nColor, sHashColor );
594 mnValue = nColor;
598 // OOXMLUniversalMeasureValue
599 // ECMA-376 5th ed. Part 1 , 22.9.2.15
600 OOXMLUniversalMeasureValue::OOXMLUniversalMeasureValue(const char * pValue, sal_uInt32 npPt)
602 double val = rtl_str_toDouble(pValue); // will ignore the trailing unit
604 int nLen = strlen(pValue);
605 if (nLen > 2 &&
606 pValue[nLen-2] == 'p' &&
607 pValue[nLen-1] == 't')
609 mnValue = static_cast<int>(val * npPt);
611 else if (nLen > 2 &&
612 pValue[nLen - 2] == 'c' &&
613 pValue[nLen - 1] == 'm')
615 mnValue = static_cast<int>(val * npPt * 72 / 2.54);
617 else if (nLen > 2 &&
618 pValue[nLen - 2] == 'm' &&
619 pValue[nLen - 1] == 'm')
621 mnValue = static_cast<int>(val * npPt * 72 / 25.4);
623 else if (nLen > 2 &&
624 pValue[nLen - 2] == 'i' &&
625 pValue[nLen - 1] == 'n')
627 mnValue = static_cast<int>(val * npPt * 72);
629 else if (nLen > 2 &&
630 pValue[nLen - 2] == 'p' &&
631 ( pValue[nLen - 1] == 'c' || pValue[nLen - 1] == 'i' ))
633 mnValue = static_cast<int>(val * npPt * 12);
635 else
637 mnValue = static_cast<int>(val);
641 OOXMLUniversalMeasureValue::~OOXMLUniversalMeasureValue()
645 int OOXMLUniversalMeasureValue::getInt() const
647 return mnValue;
650 #ifdef DBG_UTIL
651 string OOXMLUniversalMeasureValue::toString() const
653 return OString::number(mnValue).getStr();
655 #endif
657 // OOXMLMeasurementOrPercentValue
658 // ECMA-376 5th ed. Part 1 , 17.18.107; 17.18.11
659 OOXMLMeasurementOrPercentValue::OOXMLMeasurementOrPercentValue(const char * pValue)
661 double val = rtl_str_toDouble(pValue); // will ignore the trailing unit
663 int nLen = strlen(pValue);
664 if (nLen > 1 &&
665 pValue[nLen - 1] == '%')
667 mnValue = static_cast<int>(val * 50);
669 else
671 mnValue = OOXMLTwipsMeasureValue(pValue).getInt();
675 int OOXMLMeasurementOrPercentValue::getInt() const
677 return mnValue;
680 #ifdef DBG_UTIL
681 string OOXMLMeasurementOrPercentValue::toString() const
683 return OString::number(mnValue).getStr();
685 #endif
688 class OOXMLShapeValue
692 OOXMLShapeValue::OOXMLShapeValue(uno::Reference<drawing::XShape> const & rShape)
693 : mrShape(rShape)
697 OOXMLShapeValue::~OOXMLShapeValue()
701 uno::Any OOXMLShapeValue::getAny() const
703 return uno::Any(mrShape);
706 #ifdef DBG_UTIL
707 string OOXMLShapeValue::toString() const
709 return "Shape";
711 #endif
713 OOXMLValue * OOXMLShapeValue::clone() const
715 return new OOXMLShapeValue(mrShape);
719 class OOXMLStarMathValue
723 OOXMLStarMathValue::OOXMLStarMathValue( uno::Reference< embed::XEmbeddedObject > const & c )
724 : component(c)
728 OOXMLStarMathValue::~OOXMLStarMathValue()
732 uno::Any OOXMLStarMathValue::getAny() const
734 return uno::Any(component);
737 #ifdef DBG_UTIL
738 string OOXMLStarMathValue::toString() const
740 return "StarMath";
742 #endif
744 OOXMLValue * OOXMLStarMathValue::clone() const
746 return new OOXMLStarMathValue( component );
750 class OOXMLTableImpl
753 OOXMLTable::OOXMLTable()
757 OOXMLTable::~OOXMLTable()
762 void OOXMLTable::resolve(Table & rTable)
764 Table * pTable = &rTable;
766 int nPos = 0;
768 for (const auto& rPropSet : mPropertySets)
770 writerfilter::Reference<Properties>::Pointer_t pProperties
771 (rPropSet->getProperties());
773 if (pProperties)
774 pTable->entry(nPos, pProperties);
776 ++nPos;
780 void OOXMLTable::add(const ValuePointer_t& pPropertySet)
782 if (pPropertySet)
783 mPropertySets.push_back(pPropertySet);
786 OOXMLTable * OOXMLTable::clone() const
788 return new OOXMLTable(*this);
792 class: OOXMLPropertySetEntryToString
795 OOXMLPropertySetEntryToString::OOXMLPropertySetEntryToString(Id nId)
796 : mnId(nId)
800 OOXMLPropertySetEntryToString::~OOXMLPropertySetEntryToString()
804 void OOXMLPropertySetEntryToString::sprm(Sprm & /*rSprm*/)
808 void OOXMLPropertySetEntryToString::attribute(Id nId, Value & rValue)
810 if (nId == mnId)
811 mStr = rValue.getString();
815 class: OOXMLPropertySetEntryToInteger
818 OOXMLPropertySetEntryToInteger::OOXMLPropertySetEntryToInteger(Id nId)
819 : mnId(nId), mnValue(0)
823 OOXMLPropertySetEntryToInteger::~OOXMLPropertySetEntryToInteger()
827 void OOXMLPropertySetEntryToInteger::sprm(Sprm & /*rSprm*/)
831 void OOXMLPropertySetEntryToInteger::attribute(Id nId, Value & rValue)
833 if (nId == mnId)
834 mnValue = rValue.getInt();
838 class: OOXMLPropertySetEntryToBool
841 OOXMLPropertySetEntryToBool::OOXMLPropertySetEntryToBool(Id nId)
842 : mnId(nId), mValue(false)
845 OOXMLPropertySetEntryToBool::~OOXMLPropertySetEntryToBool() {}
847 void OOXMLPropertySetEntryToBool::sprm(Sprm & /*rSprm*/) {}
849 void OOXMLPropertySetEntryToBool::attribute(Id nId, Value & rValue)
851 if (nId == mnId)
852 mValue = (rValue.getInt() != 0);
857 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */