1*5900e8ecSAndrew Rist /**************************************************************
2*5900e8ecSAndrew Rist  *
3*5900e8ecSAndrew Rist  * Licensed to the Apache Software Foundation (ASF) under one
4*5900e8ecSAndrew Rist  * or more contributor license agreements.  See the NOTICE file
5*5900e8ecSAndrew Rist  * distributed with this work for additional information
6*5900e8ecSAndrew Rist  * regarding copyright ownership.  The ASF licenses this file
7*5900e8ecSAndrew Rist  * to you under the Apache License, Version 2.0 (the
8*5900e8ecSAndrew Rist  * "License"); you may not use this file except in compliance
9*5900e8ecSAndrew Rist  * with the License.  You may obtain a copy of the License at
10*5900e8ecSAndrew Rist  *
11*5900e8ecSAndrew Rist  *   http://www.apache.org/licenses/LICENSE-2.0
12*5900e8ecSAndrew Rist  *
13*5900e8ecSAndrew Rist  * Unless required by applicable law or agreed to in writing,
14*5900e8ecSAndrew Rist  * software distributed under the License is distributed on an
15*5900e8ecSAndrew Rist  * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
16*5900e8ecSAndrew Rist  * KIND, either express or implied.  See the License for the
17*5900e8ecSAndrew Rist  * specific language governing permissions and limitations
18*5900e8ecSAndrew Rist  * under the License.
19*5900e8ecSAndrew Rist  *
20*5900e8ecSAndrew Rist  *************************************************************/
21*5900e8ecSAndrew Rist 
22*5900e8ecSAndrew Rist 
23cdf0e10cSrcweir 
24cdf0e10cSrcweir #include "precompiled_svtools.hxx"
25cdf0e10cSrcweir 
26cdf0e10cSrcweir #include "cellvalueconversion.hxx"
27cdf0e10cSrcweir 
28cdf0e10cSrcweir /** === begin UNO includes === **/
29cdf0e10cSrcweir #include <com/sun/star/util/XNumberFormatter.hpp>
30cdf0e10cSrcweir #include <com/sun/star/util/XNumberFormatsSupplier.hpp>
31cdf0e10cSrcweir #include <com/sun/star/beans/XPropertySet.hpp>
32cdf0e10cSrcweir #include <com/sun/star/util/Date.hpp>
33cdf0e10cSrcweir #include <com/sun/star/util/DateTime.hpp>
34cdf0e10cSrcweir #include <com/sun/star/util/Time.hpp>
35cdf0e10cSrcweir #include <com/sun/star/util/XNumberFormatTypes.hpp>
36cdf0e10cSrcweir #include <com/sun/star/util/NumberFormat.hpp>
37cdf0e10cSrcweir /** === end UNO includes === **/
38cdf0e10cSrcweir 
39cdf0e10cSrcweir #include <comphelper/componentcontext.hxx>
40cdf0e10cSrcweir #include <rtl/math.hxx>
41cdf0e10cSrcweir #include <rtl/strbuf.hxx>
42cdf0e10cSrcweir #include <tools/date.hxx>
43cdf0e10cSrcweir #include <tools/time.hxx>
44cdf0e10cSrcweir #include <tools/diagnose_ex.h>
45cdf0e10cSrcweir #include <unotools/syslocale.hxx>
46cdf0e10cSrcweir 
47cdf0e10cSrcweir #include <boost/shared_ptr.hpp>
48cdf0e10cSrcweir #include <hash_map>
49cdf0e10cSrcweir 
50cdf0e10cSrcweir //......................................................................................................................
51cdf0e10cSrcweir namespace svt
52cdf0e10cSrcweir {
53cdf0e10cSrcweir //......................................................................................................................
54cdf0e10cSrcweir 
55cdf0e10cSrcweir     /** === begin UNO using === **/
56cdf0e10cSrcweir     using ::com::sun::star::uno::Any;
57cdf0e10cSrcweir     using ::com::sun::star::util::XNumberFormatter;
58cdf0e10cSrcweir     using ::com::sun::star::uno::UNO_QUERY_THROW;
59cdf0e10cSrcweir     using ::com::sun::star::util::XNumberFormatsSupplier;
60cdf0e10cSrcweir     using ::com::sun::star::beans::XPropertySet;
61cdf0e10cSrcweir     using ::com::sun::star::uno::UNO_SET_THROW;
62cdf0e10cSrcweir     using ::com::sun::star::uno::Exception;
63cdf0e10cSrcweir     using ::com::sun::star::util::DateTime;
64cdf0e10cSrcweir     using ::com::sun::star::uno::TypeClass;
65cdf0e10cSrcweir     using ::com::sun::star::util::XNumberFormatTypes;
66cdf0e10cSrcweir     using ::com::sun::star::uno::Reference;
67cdf0e10cSrcweir     using ::com::sun::star::uno::Sequence;
68cdf0e10cSrcweir     using ::com::sun::star::uno::makeAny;
69cdf0e10cSrcweir     using ::com::sun::star::uno::Type;
70cdf0e10cSrcweir     using ::com::sun::star::uno::TypeClass_BYTE;
71cdf0e10cSrcweir     using ::com::sun::star::uno::TypeClass_SHORT;
72cdf0e10cSrcweir     using ::com::sun::star::uno::TypeClass_UNSIGNED_SHORT;
73cdf0e10cSrcweir     using ::com::sun::star::uno::TypeClass_LONG;
74cdf0e10cSrcweir     using ::com::sun::star::uno::TypeClass_UNSIGNED_LONG;
75cdf0e10cSrcweir     using ::com::sun::star::uno::TypeClass_HYPER;
76cdf0e10cSrcweir     /** === end UNO using === **/
77cdf0e10cSrcweir     namespace NumberFormat = ::com::sun::star::util::NumberFormat;
78cdf0e10cSrcweir 
79cdf0e10cSrcweir     typedef ::com::sun::star::util::Time UnoTime;
80cdf0e10cSrcweir     typedef ::com::sun::star::util::Date UnoDate;
81cdf0e10cSrcweir 
82cdf0e10cSrcweir     //==================================================================================================================
83cdf0e10cSrcweir     //= helper
84cdf0e10cSrcweir     //==================================================================================================================
85cdf0e10cSrcweir     namespace
86cdf0e10cSrcweir     {
87cdf0e10cSrcweir         //--------------------------------------------------------------------------------------------------------------
88cdf0e10cSrcweir         double lcl_convertDateToDays( long const i_day, long const i_month, long const i_year )
89cdf0e10cSrcweir         {
90cdf0e10cSrcweir             long const nNullDateDays = ::Date::DateToDays( 1, 1, 1900 );
91cdf0e10cSrcweir             long const nValueDateDays = ::Date::DateToDays( i_day, i_month, i_year );
92cdf0e10cSrcweir 
93cdf0e10cSrcweir             return nValueDateDays - nNullDateDays;
94cdf0e10cSrcweir         }
95cdf0e10cSrcweir 
96cdf0e10cSrcweir         //--------------------------------------------------------------------------------------------------------------
97cdf0e10cSrcweir         double lcl_convertTimeToDays( long const i_hours, long const i_minutes, long const i_seconds, long const i_100thSeconds )
98cdf0e10cSrcweir         {
99cdf0e10cSrcweir             return Time( i_hours, i_minutes, i_seconds, i_100thSeconds ).GetTimeInDays();
100cdf0e10cSrcweir         }
101cdf0e10cSrcweir     }
102cdf0e10cSrcweir 
103cdf0e10cSrcweir     //==================================================================================================================
104cdf0e10cSrcweir     //= IValueNormalization
105cdf0e10cSrcweir     //==================================================================================================================
106cdf0e10cSrcweir     class SAL_NO_VTABLE IValueNormalization
107cdf0e10cSrcweir     {
108cdf0e10cSrcweir     public:
109cdf0e10cSrcweir         virtual ~IValueNormalization() { }
110cdf0e10cSrcweir 
111cdf0e10cSrcweir         /** converts the given <code>Any</code> into a <code>double</code> value to be fed into a number formatter
112cdf0e10cSrcweir         */
113cdf0e10cSrcweir         virtual double convertToDouble( Any const & i_value ) const = 0;
114cdf0e10cSrcweir 
115cdf0e10cSrcweir         /** returns the format key to be used for formatting values
116cdf0e10cSrcweir         */
117cdf0e10cSrcweir         virtual ::sal_Int32 getFormatKey() const = 0;
118cdf0e10cSrcweir     };
119cdf0e10cSrcweir 
120cdf0e10cSrcweir     typedef ::boost::shared_ptr< IValueNormalization >                                      PValueNormalization;
121cdf0e10cSrcweir     typedef ::std::hash_map< ::rtl::OUString, PValueNormalization, ::rtl::OUStringHash >    NormalizerCache;
122cdf0e10cSrcweir 
123cdf0e10cSrcweir     //==================================================================================================================
124cdf0e10cSrcweir     //= CellValueConversion_Data
125cdf0e10cSrcweir     //==================================================================================================================
126cdf0e10cSrcweir     struct CellValueConversion_Data
127cdf0e10cSrcweir     {
128cdf0e10cSrcweir         ::comphelper::ComponentContext const    aContext;
129cdf0e10cSrcweir         Reference< XNumberFormatter >           xNumberFormatter;
130cdf0e10cSrcweir         bool                                    bAttemptedFormatterCreation;
131cdf0e10cSrcweir         NormalizerCache                         aNormalizers;
132cdf0e10cSrcweir 
133cdf0e10cSrcweir         CellValueConversion_Data( ::comphelper::ComponentContext const & i_context )
134cdf0e10cSrcweir             :aContext( i_context )
135cdf0e10cSrcweir             ,xNumberFormatter()
136cdf0e10cSrcweir             ,bAttemptedFormatterCreation( false )
137cdf0e10cSrcweir             ,aNormalizers()
138cdf0e10cSrcweir         {
139cdf0e10cSrcweir         }
140cdf0e10cSrcweir     };
141cdf0e10cSrcweir 
142cdf0e10cSrcweir     //==================================================================================================================
143cdf0e10cSrcweir     //= StandardFormatNormalizer
144cdf0e10cSrcweir     //==================================================================================================================
145cdf0e10cSrcweir     class StandardFormatNormalizer : public IValueNormalization
146cdf0e10cSrcweir     {
147cdf0e10cSrcweir     protected:
148cdf0e10cSrcweir         StandardFormatNormalizer( Reference< XNumberFormatter > const & i_formatter, ::sal_Int32 const i_numberFormatType )
149cdf0e10cSrcweir             :m_nFormatKey( 0 )
150cdf0e10cSrcweir         {
151cdf0e10cSrcweir             try
152cdf0e10cSrcweir             {
153cdf0e10cSrcweir                 ENSURE_OR_THROW( i_formatter.is(), "StandardFormatNormalizer: no formatter!" );
154cdf0e10cSrcweir                 Reference< XNumberFormatsSupplier > const xSupplier( i_formatter->getNumberFormatsSupplier(), UNO_SET_THROW );
155cdf0e10cSrcweir                 Reference< XNumberFormatTypes > const xTypes( xSupplier->getNumberFormats(), UNO_QUERY_THROW );
156cdf0e10cSrcweir                 m_nFormatKey = xTypes->getStandardFormat( i_numberFormatType, SvtSysLocale().GetLocale() );
157cdf0e10cSrcweir             }
158cdf0e10cSrcweir             catch( const Exception& )
159cdf0e10cSrcweir             {
160cdf0e10cSrcweir             	DBG_UNHANDLED_EXCEPTION();
161cdf0e10cSrcweir             }
162cdf0e10cSrcweir         }
163cdf0e10cSrcweir 
164cdf0e10cSrcweir         virtual ::sal_Int32 getFormatKey() const
165cdf0e10cSrcweir         {
166cdf0e10cSrcweir             return m_nFormatKey;
167cdf0e10cSrcweir         }
168cdf0e10cSrcweir 
169cdf0e10cSrcweir     private:
170cdf0e10cSrcweir         ::sal_Int32 m_nFormatKey;
171cdf0e10cSrcweir     };
172cdf0e10cSrcweir 
173cdf0e10cSrcweir     //==================================================================================================================
174cdf0e10cSrcweir     //= DoubleNormalization
175cdf0e10cSrcweir     //==================================================================================================================
176cdf0e10cSrcweir     class DoubleNormalization : public StandardFormatNormalizer
177cdf0e10cSrcweir     {
178cdf0e10cSrcweir     public:
179cdf0e10cSrcweir         DoubleNormalization( Reference< XNumberFormatter > const & i_formatter )
180cdf0e10cSrcweir             :StandardFormatNormalizer( i_formatter, NumberFormat::NUMBER )
181cdf0e10cSrcweir         {
182cdf0e10cSrcweir         }
183cdf0e10cSrcweir 
184cdf0e10cSrcweir         virtual double convertToDouble( Any const & i_value ) const
185cdf0e10cSrcweir         {
186cdf0e10cSrcweir             double returnValue(0);
187cdf0e10cSrcweir             ::rtl::math::setNan( &returnValue );
188cdf0e10cSrcweir             OSL_VERIFY( i_value >>= returnValue );
189cdf0e10cSrcweir             return returnValue;
190cdf0e10cSrcweir         }
191cdf0e10cSrcweir 
192cdf0e10cSrcweir         virtual ~DoubleNormalization() { }
193cdf0e10cSrcweir     };
194cdf0e10cSrcweir 
195cdf0e10cSrcweir     //==================================================================================================================
196cdf0e10cSrcweir     //= IntegerNormalization
197cdf0e10cSrcweir     //==================================================================================================================
198cdf0e10cSrcweir     class IntegerNormalization : public StandardFormatNormalizer
199cdf0e10cSrcweir     {
200cdf0e10cSrcweir     public:
201cdf0e10cSrcweir         IntegerNormalization( Reference< XNumberFormatter > const & i_formatter )
202cdf0e10cSrcweir             :StandardFormatNormalizer( i_formatter, NumberFormat::NUMBER )
203cdf0e10cSrcweir         {
204cdf0e10cSrcweir         }
205cdf0e10cSrcweir 
206cdf0e10cSrcweir         virtual ~IntegerNormalization() {}
207cdf0e10cSrcweir 
208cdf0e10cSrcweir         virtual double convertToDouble( Any const & i_value ) const
209cdf0e10cSrcweir         {
210cdf0e10cSrcweir             sal_Int64 value( 0 );
211cdf0e10cSrcweir             OSL_VERIFY( i_value >>= value );
212cdf0e10cSrcweir             return value;
213cdf0e10cSrcweir         }
214cdf0e10cSrcweir     };
215cdf0e10cSrcweir 
216cdf0e10cSrcweir     //==================================================================================================================
217cdf0e10cSrcweir     //= BooleanNormalization
218cdf0e10cSrcweir     //==================================================================================================================
219cdf0e10cSrcweir     class BooleanNormalization : public StandardFormatNormalizer
220cdf0e10cSrcweir     {
221cdf0e10cSrcweir     public:
222cdf0e10cSrcweir         BooleanNormalization( Reference< XNumberFormatter > const & i_formatter )
223cdf0e10cSrcweir             :StandardFormatNormalizer( i_formatter, NumberFormat::LOGICAL )
224cdf0e10cSrcweir         {
225cdf0e10cSrcweir         }
226cdf0e10cSrcweir 
227cdf0e10cSrcweir         virtual ~BooleanNormalization() {}
228cdf0e10cSrcweir 
229cdf0e10cSrcweir         virtual double convertToDouble( Any const & i_value ) const
230cdf0e10cSrcweir         {
231cdf0e10cSrcweir             bool value( false );
232cdf0e10cSrcweir             OSL_VERIFY( i_value >>= value );
233cdf0e10cSrcweir             return value ? 1 : 0;
234cdf0e10cSrcweir         }
235cdf0e10cSrcweir     };
236cdf0e10cSrcweir 
237cdf0e10cSrcweir     //==================================================================================================================
238cdf0e10cSrcweir     //= DateTimeNormalization
239cdf0e10cSrcweir     //==================================================================================================================
240cdf0e10cSrcweir     class DateTimeNormalization : public StandardFormatNormalizer
241cdf0e10cSrcweir     {
242cdf0e10cSrcweir     public:
243cdf0e10cSrcweir         DateTimeNormalization( Reference< XNumberFormatter > const & i_formatter )
244cdf0e10cSrcweir             :StandardFormatNormalizer( i_formatter, NumberFormat::DATETIME )
245cdf0e10cSrcweir         {
246cdf0e10cSrcweir         }
247cdf0e10cSrcweir 
248cdf0e10cSrcweir         virtual ~DateTimeNormalization() {}
249cdf0e10cSrcweir 
250cdf0e10cSrcweir         virtual double convertToDouble( Any const & i_value ) const
251cdf0e10cSrcweir         {
252cdf0e10cSrcweir             double returnValue(0);
253cdf0e10cSrcweir             ::rtl::math::setNan( &returnValue );
254cdf0e10cSrcweir 
255cdf0e10cSrcweir             // extract actual UNO value
256cdf0e10cSrcweir             DateTime aDateTimeValue;
257cdf0e10cSrcweir             ENSURE_OR_RETURN( i_value >>= aDateTimeValue, "allowed for DateTime values only", returnValue );
258cdf0e10cSrcweir 
259cdf0e10cSrcweir             // date part
260cdf0e10cSrcweir             returnValue = lcl_convertDateToDays( aDateTimeValue.Day, aDateTimeValue.Month, aDateTimeValue.Year );
261cdf0e10cSrcweir 
262cdf0e10cSrcweir             // time part
263cdf0e10cSrcweir             returnValue += lcl_convertTimeToDays(
264cdf0e10cSrcweir                 aDateTimeValue.Hours, aDateTimeValue.Minutes, aDateTimeValue.Seconds, aDateTimeValue.HundredthSeconds );
265cdf0e10cSrcweir 
266cdf0e10cSrcweir             // done
267cdf0e10cSrcweir             return returnValue;
268cdf0e10cSrcweir         }
269cdf0e10cSrcweir     };
270cdf0e10cSrcweir 
271cdf0e10cSrcweir     //==================================================================================================================
272cdf0e10cSrcweir     //= DateNormalization
273cdf0e10cSrcweir     //==================================================================================================================
274cdf0e10cSrcweir     class DateNormalization : public StandardFormatNormalizer
275cdf0e10cSrcweir     {
276cdf0e10cSrcweir     public:
277cdf0e10cSrcweir         DateNormalization( Reference< XNumberFormatter > const & i_formatter )
278cdf0e10cSrcweir             :StandardFormatNormalizer( i_formatter, NumberFormat::DATE )
279cdf0e10cSrcweir         {
280cdf0e10cSrcweir         }
281cdf0e10cSrcweir 
282cdf0e10cSrcweir         virtual ~DateNormalization() {}
283cdf0e10cSrcweir 
284cdf0e10cSrcweir         virtual double convertToDouble( Any const & i_value ) const
285cdf0e10cSrcweir         {
286cdf0e10cSrcweir             double returnValue(0);
287cdf0e10cSrcweir             ::rtl::math::setNan( &returnValue );
288cdf0e10cSrcweir 
289cdf0e10cSrcweir             // extract
290cdf0e10cSrcweir             UnoDate aDateValue;
291cdf0e10cSrcweir             ENSURE_OR_RETURN( i_value >>= aDateValue, "allowed for Date values only", returnValue );
292cdf0e10cSrcweir 
293cdf0e10cSrcweir             // convert
294cdf0e10cSrcweir             returnValue = lcl_convertDateToDays( aDateValue.Day, aDateValue.Month, aDateValue.Year );
295cdf0e10cSrcweir 
296cdf0e10cSrcweir             // done
297cdf0e10cSrcweir             return returnValue;
298cdf0e10cSrcweir         }
299cdf0e10cSrcweir     };
300cdf0e10cSrcweir 
301cdf0e10cSrcweir     //==================================================================================================================
302cdf0e10cSrcweir     //= TimeNormalization
303cdf0e10cSrcweir     //==================================================================================================================
304cdf0e10cSrcweir     class TimeNormalization : public StandardFormatNormalizer
305cdf0e10cSrcweir     {
306cdf0e10cSrcweir     public:
307cdf0e10cSrcweir         TimeNormalization( Reference< XNumberFormatter > const & i_formatter )
308cdf0e10cSrcweir             :StandardFormatNormalizer( i_formatter, NumberFormat::TIME )
309cdf0e10cSrcweir         {
310cdf0e10cSrcweir         }
311cdf0e10cSrcweir 
312cdf0e10cSrcweir         virtual ~TimeNormalization() {}
313cdf0e10cSrcweir 
314cdf0e10cSrcweir         virtual double convertToDouble( Any const & i_value ) const
315cdf0e10cSrcweir         {
316cdf0e10cSrcweir             double returnValue(0);
317cdf0e10cSrcweir             ::rtl::math::setNan( &returnValue );
318cdf0e10cSrcweir 
319cdf0e10cSrcweir             // extract
320cdf0e10cSrcweir             UnoTime aTimeValue;
321cdf0e10cSrcweir             ENSURE_OR_RETURN( i_value >>= aTimeValue, "allowed for Time values only", returnValue );
322cdf0e10cSrcweir 
323cdf0e10cSrcweir             // convert
324cdf0e10cSrcweir             returnValue += lcl_convertTimeToDays(
325cdf0e10cSrcweir                 aTimeValue.Hours, aTimeValue.Minutes, aTimeValue.Seconds, aTimeValue.HundredthSeconds );
326cdf0e10cSrcweir 
327cdf0e10cSrcweir             // done
328cdf0e10cSrcweir             return returnValue;
329cdf0e10cSrcweir         }
330cdf0e10cSrcweir     };
331cdf0e10cSrcweir 
332cdf0e10cSrcweir     //==================================================================================================================
333cdf0e10cSrcweir     //= operations
334cdf0e10cSrcweir     //==================================================================================================================
335cdf0e10cSrcweir     namespace
336cdf0e10cSrcweir     {
337cdf0e10cSrcweir         //--------------------------------------------------------------------------------------------------------------
338cdf0e10cSrcweir         bool lcl_ensureNumberFormatter( CellValueConversion_Data & io_data )
339cdf0e10cSrcweir         {
340cdf0e10cSrcweir             if ( io_data.bAttemptedFormatterCreation )
341cdf0e10cSrcweir                 return io_data.xNumberFormatter.is();
342cdf0e10cSrcweir             io_data.bAttemptedFormatterCreation = true;
343cdf0e10cSrcweir 
344cdf0e10cSrcweir             try
345cdf0e10cSrcweir             {
346cdf0e10cSrcweir                 // a number formatter
347cdf0e10cSrcweir                 Reference< XNumberFormatter > const xFormatter(
348cdf0e10cSrcweir                     io_data.aContext.createComponent( "com.sun.star.util.NumberFormatter" ), UNO_QUERY_THROW );
349cdf0e10cSrcweir 
350cdf0e10cSrcweir                 // a supplier of number formats
351cdf0e10cSrcweir                 Sequence< Any > aInitArgs(1);
352cdf0e10cSrcweir                 aInitArgs[0] <<= SvtSysLocale().GetLocale();
353cdf0e10cSrcweir 
354cdf0e10cSrcweir                 Reference< XNumberFormatsSupplier > const xSupplier(
355cdf0e10cSrcweir                     io_data.aContext.createComponentWithArguments( "com.sun.star.util.NumberFormatsSupplier", aInitArgs ),
356cdf0e10cSrcweir                     UNO_QUERY_THROW
357cdf0e10cSrcweir                 );
358cdf0e10cSrcweir 
359cdf0e10cSrcweir                 // ensure a NullDate we will assume later on
360cdf0e10cSrcweir                 UnoDate const aNullDate( 1, 1, 1900 );
361cdf0e10cSrcweir                 Reference< XPropertySet > const xFormatSettings( xSupplier->getNumberFormatSettings(), UNO_SET_THROW );
362cdf0e10cSrcweir                 xFormatSettings->setPropertyValue( ::rtl::OUString::createFromAscii( "NullDate" ), makeAny( aNullDate ) );
363cdf0e10cSrcweir 
364cdf0e10cSrcweir                 // knit
365cdf0e10cSrcweir                 xFormatter->attachNumberFormatsSupplier( xSupplier );
366cdf0e10cSrcweir 
367cdf0e10cSrcweir                 // done
368cdf0e10cSrcweir                 io_data.xNumberFormatter = xFormatter;
369cdf0e10cSrcweir             }
370cdf0e10cSrcweir             catch( const Exception& )
371cdf0e10cSrcweir             {
372cdf0e10cSrcweir             	DBG_UNHANDLED_EXCEPTION();
373cdf0e10cSrcweir             }
374cdf0e10cSrcweir 
375cdf0e10cSrcweir             return io_data.xNumberFormatter.is();
376cdf0e10cSrcweir         }
377cdf0e10cSrcweir 
378cdf0e10cSrcweir         //--------------------------------------------------------------------------------------------------------------
379cdf0e10cSrcweir         bool lcl_getValueNormalizer( CellValueConversion_Data & io_data, Type const & i_valueType,
380cdf0e10cSrcweir             PValueNormalization & o_formatter )
381cdf0e10cSrcweir         {
382cdf0e10cSrcweir             NormalizerCache::const_iterator pos = io_data.aNormalizers.find( i_valueType.getTypeName() );
383cdf0e10cSrcweir             if ( pos == io_data.aNormalizers.end() )
384cdf0e10cSrcweir             {
385cdf0e10cSrcweir                 // never encountered this type before
386cdf0e10cSrcweir                 o_formatter.reset();
387cdf0e10cSrcweir 
388cdf0e10cSrcweir                 ::rtl::OUString const sTypeName( i_valueType.getTypeName() );
389cdf0e10cSrcweir                 TypeClass const eTypeClass = i_valueType.getTypeClass();
390cdf0e10cSrcweir 
391cdf0e10cSrcweir                 if ( sTypeName.equals( ::cppu::UnoType< DateTime >::get().getTypeName() ) )
392cdf0e10cSrcweir                 {
393cdf0e10cSrcweir                     o_formatter.reset( new DateTimeNormalization( io_data.xNumberFormatter ) );
394cdf0e10cSrcweir                 }
395cdf0e10cSrcweir                 else if ( sTypeName.equals( ::cppu::UnoType< UnoDate >::get().getTypeName() ) )
396cdf0e10cSrcweir                 {
397cdf0e10cSrcweir                     o_formatter.reset( new DateNormalization( io_data.xNumberFormatter ) );
398cdf0e10cSrcweir                 }
399cdf0e10cSrcweir                 else if ( sTypeName.equals( ::cppu::UnoType< UnoTime >::get().getTypeName() ) )
400cdf0e10cSrcweir                 {
401cdf0e10cSrcweir                     o_formatter.reset( new TimeNormalization( io_data.xNumberFormatter ) );
402cdf0e10cSrcweir                 }
403cdf0e10cSrcweir                 else if ( sTypeName.equals( ::cppu::UnoType< ::sal_Bool >::get().getTypeName() ) )
404cdf0e10cSrcweir                 {
405cdf0e10cSrcweir                     o_formatter.reset( new BooleanNormalization( io_data.xNumberFormatter ) );
406cdf0e10cSrcweir                 }
407cdf0e10cSrcweir                 else if (   sTypeName.equals( ::cppu::UnoType< double >::get().getTypeName() )
408cdf0e10cSrcweir                         ||  sTypeName.equals( ::cppu::UnoType< float >::get().getTypeName() )
409cdf0e10cSrcweir                         )
410cdf0e10cSrcweir                 {
411cdf0e10cSrcweir                     o_formatter.reset( new DoubleNormalization( io_data.xNumberFormatter ) );
412cdf0e10cSrcweir                 }
413cdf0e10cSrcweir                 else if (   ( eTypeClass == TypeClass_BYTE )
414cdf0e10cSrcweir                         ||  ( eTypeClass == TypeClass_SHORT )
415cdf0e10cSrcweir                         ||  ( eTypeClass == TypeClass_UNSIGNED_SHORT )
416cdf0e10cSrcweir                         ||  ( eTypeClass == TypeClass_LONG )
417cdf0e10cSrcweir                         ||  ( eTypeClass == TypeClass_UNSIGNED_LONG )
418cdf0e10cSrcweir                         ||  ( eTypeClass == TypeClass_HYPER )
419cdf0e10cSrcweir                         )
420cdf0e10cSrcweir                 {
421cdf0e10cSrcweir                     o_formatter.reset( new IntegerNormalization( io_data.xNumberFormatter ) );
422cdf0e10cSrcweir                 }
423cdf0e10cSrcweir                 else
424cdf0e10cSrcweir                 {
425cdf0e10cSrcweir #if OSL_DEBUG_LEVEL > 0
426cdf0e10cSrcweir                     ::rtl::OStringBuffer message( "lcl_getValueNormalizer: unsupported type '" );
427cdf0e10cSrcweir                     message.append( ::rtl::OUStringToOString( sTypeName, RTL_TEXTENCODING_ASCII_US ) );
428cdf0e10cSrcweir                     message.append( "'!" );
429cdf0e10cSrcweir                     OSL_ENSURE( false, message.makeStringAndClear() );
430cdf0e10cSrcweir #endif
431cdf0e10cSrcweir                 }
432cdf0e10cSrcweir                 io_data.aNormalizers[ sTypeName ] = o_formatter;
433cdf0e10cSrcweir             }
434cdf0e10cSrcweir             else
435cdf0e10cSrcweir                 o_formatter = pos->second;
436cdf0e10cSrcweir 
437cdf0e10cSrcweir             return !!o_formatter;
438cdf0e10cSrcweir         }
439cdf0e10cSrcweir     }
440cdf0e10cSrcweir 
441cdf0e10cSrcweir     //==================================================================================================================
442cdf0e10cSrcweir     //= CellValueConversion
443cdf0e10cSrcweir     //==================================================================================================================
444cdf0e10cSrcweir     //------------------------------------------------------------------------------------------------------------------
445cdf0e10cSrcweir     CellValueConversion::CellValueConversion( ::comphelper::ComponentContext const & i_context )
446cdf0e10cSrcweir         :m_pData( new CellValueConversion_Data( i_context ) )
447cdf0e10cSrcweir     {
448cdf0e10cSrcweir     }
449cdf0e10cSrcweir 
450cdf0e10cSrcweir     //------------------------------------------------------------------------------------------------------------------
451cdf0e10cSrcweir     CellValueConversion::~CellValueConversion()
452cdf0e10cSrcweir     {
453cdf0e10cSrcweir     }
454cdf0e10cSrcweir 
455cdf0e10cSrcweir     //------------------------------------------------------------------------------------------------------------------
456cdf0e10cSrcweir     ::rtl::OUString CellValueConversion::convertToString( const Any& i_value )
457cdf0e10cSrcweir     {
458cdf0e10cSrcweir         ::rtl::OUString sStringValue;
459cdf0e10cSrcweir         if ( !i_value.hasValue() )
460cdf0e10cSrcweir             return sStringValue;
461cdf0e10cSrcweir 
462cdf0e10cSrcweir         if ( ! ( i_value >>= sStringValue ) )
463cdf0e10cSrcweir         {
464cdf0e10cSrcweir             if ( lcl_ensureNumberFormatter( *m_pData ) )
465cdf0e10cSrcweir             {
466cdf0e10cSrcweir                 PValueNormalization pNormalizer;
467cdf0e10cSrcweir                 if ( lcl_getValueNormalizer( *m_pData, i_value.getValueType(), pNormalizer ) )
468cdf0e10cSrcweir                 {
469cdf0e10cSrcweir                     try
470cdf0e10cSrcweir                     {
471cdf0e10cSrcweir                         double const formatterCompliantValue = pNormalizer->convertToDouble( i_value );
472cdf0e10cSrcweir                         sal_Int32 const formatKey = pNormalizer->getFormatKey();
473cdf0e10cSrcweir                         sStringValue = m_pData->xNumberFormatter->convertNumberToString(
474cdf0e10cSrcweir                             formatKey, formatterCompliantValue );
475cdf0e10cSrcweir                     }
476cdf0e10cSrcweir                     catch( const Exception& )
477cdf0e10cSrcweir                     {
478cdf0e10cSrcweir                     	DBG_UNHANDLED_EXCEPTION();
479cdf0e10cSrcweir                     }
480cdf0e10cSrcweir                 }
481cdf0e10cSrcweir             }
482cdf0e10cSrcweir         }
483cdf0e10cSrcweir 
484cdf0e10cSrcweir         return sStringValue;
485cdf0e10cSrcweir     }
486cdf0e10cSrcweir 
487cdf0e10cSrcweir //......................................................................................................................
488cdf0e10cSrcweir } // namespace svt
489cdf0e10cSrcweir //......................................................................................................................
490