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 #ifndef INCLUDED_XMLOFF_XMLUCONV_HXX
21 #define INCLUDED_XMLOFF_XMLUCONV_HXX
22 
23 #include <sal/config.h>
24 #include <xmloff/dllapi.h>
25 #include <sal/types.h>
26 
27 #include <memory>
28 
29 #include <rtl/ustring.hxx>
30 #include <rtl/ustrbuf.hxx>
31 #include <xmloff/xmltoken.hxx>
32 
33 #include <unotools/saveopt.hxx>
34 
35 #include <tools/fldunit.hxx>
36 
37 namespace com::sun::star {
38     namespace text { class XNumberingTypeInfo; }
39 }
40 
41 namespace basegfx
42 {
43     class B3DVector;
44 }
45 
46 namespace com::sun::star::beans { class XPropertySet; }
47 namespace com::sun::star::beans { struct PropertyValue; }
48 namespace com::sun::star::drawing { struct Position3D; }
49 namespace com::sun::star::frame { class XModel; }
50 namespace com::sun::star::uno { class XComponentContext; }
51 namespace com::sun::star::uno { template <class E> class Sequence; }
52 namespace com::sun::star::util { struct Date; }
53 template <typename EnumT> struct SvXMLEnumMapEntry;
54 template <typename EnumT> struct SvXMLEnumStringMapEntry;
55 
56 class XMLOFF_DLLPUBLIC SvXMLTokenEnumerator
57 {
58 private:
59     std::u16string_view     maTokenString;
60     size_t                  mnNextTokenPos;
61     sal_Unicode             mcSeparator;
62 
63 public:
64     SvXMLTokenEnumerator( std::u16string_view rString, sal_Unicode cSeparator = u' ' );
65     /** just so no-one accidentally passes a temporary to this, and ends up with this class
66      * accessing the temporary after the temporary has been deleted. */
67     SvXMLTokenEnumerator( OUString&& , sal_Unicode cSeparator = u' ' ) = delete;
68 
69     bool getNextToken( std::u16string_view& rToken );
70 };
71 
72 /** the SvXMLTypeConverter converts values of various types from
73     their internal representation to the textual form used in xml
74     and back.
75     Most of the methods are static but the SvXMLTypeConverter can
76     also store default units for both numerical and textual measures.
77 
78     @attention:
79         a lot of the methods here have been moved to <sax/tools/converter.hxx>!
80 */
81 
82 class XMLOFF_DLLPUBLIC SvXMLUnitConverter final
83 {
84 private:
85     SvXMLUnitConverter(const SvXMLUnitConverter&) = delete;
86     SvXMLUnitConverter& operator=(const SvXMLUnitConverter&) = delete;
87 
88     struct SAL_DLLPRIVATE Impl;
89     ::std::unique_ptr<Impl> m_pImpl;
90 
91 public:
92     /** constructs a SvXMLUnitConverter. The core measure unit is the
93         default unit for numerical measures, the XML measure unit is
94         the default unit for textual measures */
95     SvXMLUnitConverter(
96         const css::uno::Reference< css::uno::XComponentContext >& xContext,
97         sal_Int16 eCoreMeasureUnit /*css::util::MeasureUnit*/,
98         sal_Int16 eXMLMeasureUnit /*css::util::MeasureUnit*/,
99         SvtSaveOptions::ODFSaneDefaultVersion const nODFVersion);
100 
101     ~SvXMLUnitConverter();
102 
103     static sal_Int16 GetMeasureUnit(FieldUnit const nFieldUnit);
104 
105     /** sets the default unit for numerical measures */
106     void SetCoreMeasureUnit( sal_Int16 const eCoreMeasureUnit /*css::util::MeasureUnit*/);
107 
108     /** sets the default unit for textual measures */
109     void SetXMLMeasureUnit( sal_Int16 const eXMLMeasureUnit /*css::util::MeasureUnit*/);
110 
111     /** gets the default unit for textual measures */
112     sal_Int16 GetXMLMeasureUnit() const;
113 
114     /// ODF version, only when exporting
115     SvtSaveOptions::ODFSaneDefaultVersion getSaneDefaultVersion() const;
116     void overrideSaneDefaultVersion(SvtSaveOptions::ODFSaneDefaultVersion const);
117 
118     /** gets XNumberingTypeInfo */
119     const css::uno::Reference< css::text::XNumberingTypeInfo >& getNumTypeInfo() const;
120 
121     /** convert string to measure with meCoreMeasureUnit,
122         using optional min and max values*/
123     bool convertMeasureToCore( sal_Int32& rValue,
124                          std::u16string_view rString,
125                          sal_Int32 nMin = SAL_MIN_INT32,
126                          sal_Int32 nMax = SAL_MAX_INT32) const;
127 
128     /** convert string to measure with meCoreMeasureUnit,
129         using optional min and max values*/
130     bool convertMeasureToCore( sal_Int32& rValue,
131                          std::string_view rString,
132                          sal_Int32 nMin = SAL_MIN_INT32,
133                          sal_Int32 nMax = SAL_MAX_INT32) const;
134 
135     /** convert measure to string: from meCoreMeasureUnit to meXMLMeasureUnit */
136     void convertMeasureToXML( OUStringBuffer& rBuffer,
137                          sal_Int32 nMeasure ) const;
138 
139     /** convert measure to string: from meCoreMeasureUnit to meXMLMeasureUnit */
140     OUString convertMeasureToXML( sal_Int32 nMeasure ) const;
141 
142     /** convert string to enum using given enum map, if the enum is
143         not found in the map, this method will return false */
144     template<typename EnumT>
convertEnum(EnumT & rEnum,std::u16string_view rValue,const SvXMLEnumMapEntry<EnumT> * pMap)145     static bool convertEnum( EnumT& rEnum,
146                              std::u16string_view rValue,
147                              const SvXMLEnumMapEntry<EnumT> *pMap )
148     {
149         sal_uInt16 nTmp;
150         bool bRet = convertEnumImpl(nTmp, rValue,
151                         reinterpret_cast<const SvXMLEnumMapEntry<sal_uInt16>*>(pMap));
152         if (bRet)
153             rEnum = static_cast<EnumT>(nTmp);
154         return bRet;
155     }
156 
157     /** convert string to enum using given enum map, if the enum is
158         not found in the map, this method will return false */
159     template<typename EnumT>
convertEnum(EnumT & rEnum,std::string_view rValue,const SvXMLEnumMapEntry<EnumT> * pMap)160     static bool convertEnum( EnumT& rEnum,
161                              std::string_view rValue,
162                              const SvXMLEnumMapEntry<EnumT> *pMap )
163     {
164         sal_uInt16 nTmp;
165         bool bRet = convertEnumImpl(nTmp, rValue,
166                         reinterpret_cast<const SvXMLEnumMapEntry<sal_uInt16>*>(pMap));
167         if (bRet)
168             rEnum = static_cast<EnumT>(nTmp);
169         return bRet;
170     }
171 
172     /** convert string to enum using given token map, if the enum is
173         not found in the map, this method will return false */
174     template<typename EnumT>
convertEnum(EnumT & rEnum,std::u16string_view rValue,const SvXMLEnumStringMapEntry<EnumT> * pMap)175     static bool convertEnum( EnumT& rEnum,
176                              std::u16string_view rValue,
177                              const SvXMLEnumStringMapEntry<EnumT> *pMap )
178     {
179         sal_uInt16 nTmp;
180         bool bRet = convertEnumImpl(nTmp, rValue,
181                         reinterpret_cast<const SvXMLEnumStringMapEntry<sal_uInt16>*>(pMap));
182         if (bRet)
183             rEnum = static_cast<EnumT>(nTmp);
184         return bRet;
185     }
186 
187     /** convert string to enum using given token map, if the enum is
188         not found in the map, this method will return false */
189     template<typename EnumT>
convertEnum(EnumT & rEnum,std::string_view rValue,const SvXMLEnumStringMapEntry<EnumT> * pMap)190     static bool convertEnum( EnumT& rEnum,
191                              std::string_view rValue,
192                              const SvXMLEnumStringMapEntry<EnumT> *pMap )
193     {
194         sal_uInt16 nTmp;
195         bool bRet = convertEnumImpl(nTmp, rValue,
196                         reinterpret_cast<const SvXMLEnumStringMapEntry<sal_uInt16>*>(pMap));
197         if (bRet)
198             rEnum = static_cast<EnumT>(nTmp);
199         return bRet;
200     }
201 
202     /** convert enum to string using given enum map with an optional
203         default token. If the enum is not found in the map,
204         this method will either use the given default or return
205         false if not default is set */
206     template<typename EnumT>
convertEnum(OUStringBuffer & rBuffer,EnumT nValue,const SvXMLEnumMapEntry<EnumT> * pMap,enum::xmloff::token::XMLTokenEnum eDefault=::xmloff::token::XML_TOKEN_INVALID)207     static bool convertEnum( OUStringBuffer& rBuffer,
208                              EnumT nValue,
209                              const SvXMLEnumMapEntry<EnumT> *pMap,
210                              enum ::xmloff::token::XMLTokenEnum eDefault =
211                                          ::xmloff::token::XML_TOKEN_INVALID )
212     {
213         return convertEnumImpl(rBuffer, static_cast<sal_uInt16>(nValue),
214                    reinterpret_cast<const SvXMLEnumMapEntry<sal_uInt16>*>(pMap), eDefault);
215     }
216 
217     /** convert double number to string (using ::rtl::math) and DO
218         convert to export MapUnit using meCoreMeasureUnit/meXMLMeasureUnit */
219     void convertDouble(OUStringBuffer& rBuffer,
220         double fNumber) const;
221 
222     /** convert string to double number (using ::rtl::math) and DO convert. */
223     bool convertDouble(double& rValue, std::u16string_view rString) const;
224 
225     /** get the Null Date of the XModel and set it to the UnitConverter */
226     bool setNullDate (
227         const css::uno::Reference <css::frame::XModel>& xModel);
228 
229     /** convert double to ISO Date Time String */
230     void convertDateTime( OUStringBuffer& rBuffer,
231                                 const double& fDateTime,
232                                 bool const bAddTimeIf0AM = false);
233 
234     /** convert ISO Date Time String to double */
235     bool convertDateTime(double& fDateTime,
236                          std::u16string_view rString);
237 
238     /** convert ISO Date Time String to double */
239     bool convertDateTime(double& fDateTime,
240                          std::string_view rString);
241 
242     /// these 2 functions use tools Date, so they're not yet moved to sax
243 
244     /** convert double to ISO Date Time String */
245     static void convertDateTime( OUStringBuffer& rBuffer,
246                                 const double& fDateTime,
247                                 const css::util::Date& aNullDate,
248                                 bool bAddTimeIf0AM = false);
249     /** convert ISO Date Time String to double */
250     static bool convertDateTime( double& fDateTime,
251                                 std::u16string_view rString,
252                                 const css::util::Date& aNullDate);
253     /** convert ISO Date Time String to double */
254     static bool convertDateTime( double& fDateTime,
255                                 std::string_view rString,
256                                 const css::util::Date& aNullDate);
257 
258 
259     /** convert string to ::basegfx::B3DVector */
260     static bool convertB3DVector( ::basegfx::B3DVector& rVector,
261                               std::u16string_view rValue );
262 
263     /** convert string to ::basegfx::B3DVector */
264     static bool convertB3DVector( ::basegfx::B3DVector& rVector,
265                               std::string_view rValue );
266 
267     /** convert B3DVector to string */
268     static void convertB3DVector( OUStringBuffer &rBuffer,
269         const ::basegfx::B3DVector& rVector );
270 
271     /** convert string to Position3D */
272     bool convertPosition3D( css::drawing::Position3D& rPosition,
273                               std::string_view rValue );
274 
275     /** convert Position3D to string */
276     void convertPosition3D( OUStringBuffer &rBuffer,
277                               const css::drawing::Position3D& rVector );
278 
279 
280     /** convert num-format and num-letter-sync values to NumberingType */
281     bool convertNumFormat( sal_Int16& rType,
282                            const OUString& rNumFormat,
283                            std::u16string_view rNumLetterSync,
284                            bool bNumberNone = false ) const;
285 
286     /** convert NumberingType to num-format and num-letter-sync values */
287     void convertNumFormat( OUStringBuffer& rBuffer,
288                            sal_Int16 nType ) const;
289     static void convertNumLetterSync( OUStringBuffer& rBuffer,
290                                   sal_Int16 nType );
291 
292     static void convertPropertySet(css::uno::Sequence<css::beans::PropertyValue>& rProps,
293                         const css::uno::Reference<css::beans::XPropertySet>& aProperties);
294     static void convertPropertySet(css::uno::Reference<css::beans::XPropertySet> const & rProperties,
295                         const css::uno::Sequence<css::beans::PropertyValue>& aProps);
296 
297     OUString encodeStyleName( const OUString& rName,
298                                      bool *pEncoded=nullptr ) const;
299     /** convert string (hex) to number (sal_uInt32) */
300     static bool convertHex( sal_uInt32& nVal,
301                               std::u16string_view rValue );
302 
303     /** convert number (sal_uInt32) to string (hex) */
304     static void convertHex( OUStringBuffer& rBuffer,
305                                sal_uInt32 nVal );
306 
307 private:
308     static bool convertEnumImpl( sal_uInt16& rEnum,
309                              std::u16string_view rValue,
310                              const SvXMLEnumMapEntry<sal_uInt16> *pMap );
311 
312     static bool convertEnumImpl( sal_uInt16& rEnum,
313                              std::u16string_view rValue,
314                              const SvXMLEnumStringMapEntry<sal_uInt16> *pMap );
315 
316     static bool convertEnumImpl( sal_uInt16& rEnum,
317                              std::string_view rValue,
318                              const SvXMLEnumMapEntry<sal_uInt16> *pMap );
319 
320     static bool convertEnumImpl( sal_uInt16& rEnum,
321                              std::string_view rValue,
322                              const SvXMLEnumStringMapEntry<sal_uInt16> *pMap );
323 
324     static bool convertEnumImpl( OUStringBuffer& rBuffer,
325                              sal_uInt16 nValue,
326                              const SvXMLEnumMapEntry<sal_uInt16> *pMap,
327                              enum ::xmloff::token::XMLTokenEnum eDefault );
328 };
329 
330 #endif // INCLUDED_XMLOFF_XMLUCONV_HXX
331 
332 /* vim:set shiftwidth=4 softtabstop=4 expandtab: */
333