[devel_3.0_main] Cherry-pick Beautification of source-code. 80383
[platform/framework/native/appfw.git] / src / base / FBase_LocalizedNumParser.cpp
1 //
2 // Copyright (c) 2013 Samsung Electronics Co., Ltd.
3 //
4 // Licensed under the Apache License, Version 2.0 (the License);
5 // you may not use this file except in compliance with the License.
6 // You may obtain a copy of the License at
7 //
8 //     http://www.apache.org/licenses/LICENSE-2.0
9 //
10 // Unless required by applicable law or agreed to in writing, software
11 // distributed under the License is distributed on an "AS IS" BASIS,
12 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 // See the License for the specific language governing permissions and
14 // limitations under the License.
15 //
16
17 /**
18  * @file                FBase_LocalizedNumParser.cpp
19  * @brief               This is the implementation file for _LocalizedNumParser class.
20  */
21 #include <cerrno>
22 #include <clocale>
23 #include <cmath>
24 #include <cwchar>
25 #include <limits>
26 #include <FBaseSysLog.h>
27 #include "FBase_LocalizedNumParser.h"
28
29 namespace Tizen { namespace Base
30 {
31
32 class _CLocaleWrapper
33 {
34 public:
35         _CLocaleWrapper(void)
36                 : _locale(0)
37         {
38         }
39
40         ~_CLocaleWrapper(void)
41         {
42                 if (_locale != null)
43                 {
44                         freelocale(_locale);
45                         uselocale(LC_GLOBAL_LOCALE);
46                 }
47         }
48
49         result Construct(const char* pLocale)
50         {
51                 _locale = newlocale(LC_ALL, pLocale, null);
52                 SysTryReturnResult(NID_BASE, _locale != null, E_INVALID_ARG, "Creating a new locale object is failed. pLocale is invalid.");
53
54                 uselocale(_locale);
55                 return E_SUCCESS;
56         }
57
58 private:
59         locale_t _locale;
60 };
61
62 double
63 _LocalizedNumParser::ToDouble(const String& str, const char* pLocale)
64 {
65         ClearLastResult();
66
67         _CLocaleWrapper clocale;
68         result r = clocale.Construct(pLocale);
69         SysTryReturn(NID_BASE, r == E_SUCCESS, std::numeric_limits< double >::quiet_NaN(), r, "[%s] Propagating.", GetErrorMessage(r));
70
71         wchar_t* pEnd = null;
72         errno = 0;
73
74         double ret = wcstod(str.GetPointer(), &pEnd);
75         SysTryReturn(NID_BASE, !(ret == 0 && errno == EINVAL) && (pEnd[0] == 0), std::numeric_limits< double >::quiet_NaN(),
76                 E_NUM_FORMAT, "[%s] wcstod() failed. Scan stopped at (%ls)", GetErrorMessage(E_NUM_FORMAT), pEnd);
77         SysTryReturn(NID_BASE, errno == 0 || (ret != HUGE_VAL && ret != -HUGE_VAL), std::numeric_limits< double >::quiet_NaN(),
78                 E_NUM_FORMAT, "[%s] Parsed value cannot fit into a Double.", GetErrorMessage(E_NUM_FORMAT));
79
80         return ret;
81 }
82
83 float
84 _LocalizedNumParser::ToFloat(const String& str, const char* pLocale)
85 {
86         ClearLastResult();
87
88         _CLocaleWrapper clocale;
89         result r = clocale.Construct(pLocale);
90         SysTryReturn(NID_BASE, r == E_SUCCESS, std::numeric_limits< float >::quiet_NaN(), r, "[%s] Propagating.", GetErrorMessage(r));
91
92         wchar_t* pEnd = null;
93         errno = 0;
94
95         float ret = wcstof(str.GetPointer(), &pEnd);
96         SysTryReturn(NID_BASE, !(ret == 0 && errno == EINVAL) && pEnd[0] == 0, std::numeric_limits< float >::quiet_NaN(),
97                 E_NUM_FORMAT, "[%s] wcstof() failed. Scan stopped at (%ls).", GetErrorMessage(E_NUM_FORMAT), pEnd);
98         SysTryReturn(NID_BASE, errno == 0 || (ret != HUGE_VAL && ret != -HUGE_VAL), std::numeric_limits< float >::quiet_NaN(),
99                 E_NUM_FORMAT, "[%s] Parsed value cannot fit into a Float.", GetErrorMessage(E_NUM_FORMAT));
100
101         return ret;
102 }
103
104 String
105 _LocalizedNumParser::ToString(double value, const char* pLocale)
106 {
107         ClearLastResult();
108
109         if (std::isnan(value))
110         {
111                 return String(L"NaN");
112         }
113
114         if (std::isinf(value))
115         {
116                 return String(L"Infinity");
117         }
118
119         _CLocaleWrapper clocale;
120         result r = clocale.Construct(pLocale);
121         SysTryReturn(NID_BASE, r == E_SUCCESS, null, r, "[%s] Propagating.", GetErrorMessage(r));
122
123         wchar_t sValue[DBL_MAX_LENGTH + 1] = {0, };
124         swprintf(sValue, sizeof(sValue) / sizeof(sValue[0]), L"%#lg", value);
125
126         return String(sValue);
127 }
128
129 String
130 _LocalizedNumParser::ToString(float value, const char* pLocale)
131 {
132         ClearLastResult();
133
134         if (std::isnan(value))
135         {
136                 return String(L"NaN");
137         }
138
139         if (std::isinf(value))
140         {
141                 return String(L"Infinity");
142         }
143
144         _CLocaleWrapper clocale;
145         result r = clocale.Construct(pLocale);
146         SysTryReturn(NID_BASE, r == E_SUCCESS, null, r, "[%s] Propagating.", GetErrorMessage(r));
147
148         wchar_t sValue[FLOAT_LENGTH_MAX + 1] = {0, };
149         swprintf(sValue, sizeof(sValue) / sizeof(sValue[0]), L"%g", value);
150
151         return String(sValue);
152 }
153
154 }}  // Tizen::Base