]>
Commit | Line | Data |
---|---|---|
7c673cae FG |
1 | #ifndef DATE_TIME_DATE_NAMES_PUT_HPP___ |
2 | #define DATE_TIME_DATE_NAMES_PUT_HPP___ | |
3 | ||
4 | /* Copyright (c) 2002-2005 CrystalClear Software, Inc. | |
5 | * Use, modification and distribution is subject to the | |
6 | * Boost Software License, Version 1.0. (See accompanying | |
7 | * file LICENSE_1_0.txt or http://www.boost.org/LICENSE_1_0.txt) | |
8 | * Author: Jeff Garland, Bart Garst | |
9 | * $Date$ | |
10 | */ | |
11 | ||
12 | ||
13 | #include "boost/date_time/locale_config.hpp" // set BOOST_DATE_TIME_NO_LOCALE | |
14 | ||
15 | #ifndef BOOST_DATE_TIME_NO_LOCALE | |
16 | ||
17 | #include "boost/date_time/special_defs.hpp" | |
18 | #include "boost/date_time/date_defs.hpp" | |
19 | #include "boost/date_time/parse_format_base.hpp" | |
20 | #include "boost/lexical_cast.hpp" | |
21 | #include <locale> | |
22 | ||
23 | ||
24 | namespace boost { | |
25 | namespace date_time { | |
26 | ||
27 | //! Output facet base class for gregorian dates. | |
28 | /*! This class is a base class for date facets used to localize the | |
29 | * names of months and the names of days in the week. | |
30 | * | |
31 | * Requirements of Config | |
32 | * - define an enumeration month_enum that enumerates the months. | |
33 | * The enumeration should be '1' based eg: Jan==1 | |
34 | * - define as_short_string and as_long_string | |
35 | * | |
36 | * (see langer & kreft p334). | |
37 | * | |
38 | */ | |
39 | template<class Config, | |
40 | class charT = char, | |
41 | class OutputIterator = std::ostreambuf_iterator<charT> > | |
42 | class date_names_put : public std::locale::facet | |
43 | { | |
44 | public: | |
45 | date_names_put() {} | |
46 | typedef OutputIterator iter_type; | |
47 | typedef typename Config::month_type month_type; | |
48 | typedef typename Config::month_enum month_enum; | |
49 | typedef typename Config::weekday_enum weekday_enum; | |
50 | typedef typename Config::special_value_enum special_value_enum; | |
51 | //typedef typename Config::format_type format_type; | |
52 | typedef std::basic_string<charT> string_type; | |
53 | typedef charT char_type; | |
54 | static const char_type default_special_value_names[3][17]; | |
55 | static const char_type separator[2]; | |
56 | ||
57 | static std::locale::id id; | |
58 | ||
59 | #if defined (__SUNPRO_CC) && defined (_RWSTD_VER) | |
60 | std::locale::id& __get_id (void) const { return id; } | |
61 | #endif | |
62 | ||
63 | void put_special_value(iter_type& oitr, special_value_enum sv) const | |
64 | { | |
65 | do_put_special_value(oitr, sv); | |
66 | } | |
67 | void put_month_short(iter_type& oitr, month_enum moy) const | |
68 | { | |
69 | do_put_month_short(oitr, moy); | |
70 | } | |
71 | void put_month_long(iter_type& oitr, month_enum moy) const | |
72 | { | |
73 | do_put_month_long(oitr, moy); | |
74 | } | |
75 | void put_weekday_short(iter_type& oitr, weekday_enum wd) const | |
76 | { | |
77 | do_put_weekday_short(oitr, wd); | |
78 | } | |
79 | void put_weekday_long(iter_type& oitr, weekday_enum wd) const | |
80 | { | |
81 | do_put_weekday_long(oitr, wd); | |
82 | } | |
83 | bool has_date_sep_chars() const | |
84 | { | |
85 | return do_has_date_sep_chars(); | |
86 | } | |
87 | void year_sep_char(iter_type& oitr) const | |
88 | { | |
89 | do_year_sep_char(oitr); | |
90 | } | |
91 | //! char between year-month | |
92 | void month_sep_char(iter_type& oitr) const | |
93 | { | |
94 | do_month_sep_char(oitr); | |
95 | } | |
96 | //! Char to separate month-day | |
97 | void day_sep_char(iter_type& oitr) const | |
98 | { | |
99 | do_day_sep_char(oitr); | |
100 | } | |
101 | //! Determines the order to put the date elements | |
102 | ymd_order_spec date_order() const | |
103 | { | |
104 | return do_date_order(); | |
105 | } | |
106 | //! Determines if month is displayed as integer, short or long string | |
107 | month_format_spec month_format() const | |
108 | { | |
109 | return do_month_format(); | |
110 | } | |
111 | ||
112 | protected: | |
113 | //! Default facet implementation uses month_type defaults | |
114 | virtual void do_put_month_short(iter_type& oitr, month_enum moy) const | |
115 | { | |
116 | month_type gm(moy); | |
117 | charT c = '\0'; | |
118 | put_string(oitr, gm.as_short_string(c)); | |
119 | } | |
120 | //! Default facet implementation uses month_type defaults | |
121 | virtual void do_put_month_long(iter_type& oitr, | |
122 | month_enum moy) const | |
123 | { | |
124 | month_type gm(moy); | |
125 | charT c = '\0'; | |
126 | put_string(oitr, gm.as_long_string(c)); | |
127 | } | |
128 | //! Default facet implementation for special value types | |
129 | virtual void do_put_special_value(iter_type& oitr, special_value_enum sv) const | |
130 | { | |
131 | if(sv <= 2) { // only output not_a_date_time, neg_infin, or pos_infin | |
132 | string_type s(default_special_value_names[sv]); | |
133 | put_string(oitr, s); | |
134 | } | |
135 | } | |
136 | virtual void do_put_weekday_short(iter_type&, weekday_enum) const | |
137 | { | |
138 | } | |
139 | virtual void do_put_weekday_long(iter_type&, weekday_enum) const | |
140 | { | |
141 | } | |
142 | virtual bool do_has_date_sep_chars() const | |
143 | { | |
144 | return true; | |
145 | } | |
146 | virtual void do_year_sep_char(iter_type& oitr) const | |
147 | { | |
148 | string_type s(separator); | |
149 | put_string(oitr, s); | |
150 | } | |
151 | //! char between year-month | |
152 | virtual void do_month_sep_char(iter_type& oitr) const | |
153 | { | |
154 | string_type s(separator); | |
155 | put_string(oitr, s); | |
156 | } | |
157 | //! Char to separate month-day | |
158 | virtual void do_day_sep_char(iter_type& oitr) const | |
159 | { | |
160 | string_type s(separator); //put in '-' | |
161 | put_string(oitr, s); | |
162 | } | |
163 | //! Default for date order | |
164 | virtual ymd_order_spec do_date_order() const | |
165 | { | |
166 | return ymd_order_iso; | |
167 | } | |
168 | //! Default month format | |
169 | virtual month_format_spec do_month_format() const | |
170 | { | |
171 | return month_as_short_string; | |
172 | } | |
173 | void put_string(iter_type& oi, const charT* const s) const | |
174 | { | |
175 | string_type s1(boost::lexical_cast<string_type>(s)); | |
176 | typename string_type::iterator si,end; | |
177 | for (si=s1.begin(), end=s1.end(); si!=end; si++, oi++) { | |
178 | *oi = *si; | |
179 | } | |
180 | } | |
181 | void put_string(iter_type& oi, const string_type& s1) const | |
182 | { | |
183 | typename string_type::const_iterator si,end; | |
184 | for (si=s1.begin(), end=s1.end(); si!=end; si++, oi++) { | |
185 | *oi = *si; | |
186 | } | |
187 | } | |
188 | }; | |
189 | ||
190 | template<class Config, class charT, class OutputIterator> | |
191 | const typename date_names_put<Config, charT, OutputIterator>::char_type | |
192 | date_names_put<Config, charT, OutputIterator>::default_special_value_names[3][17] = { | |
193 | {'n','o','t','-','a','-','d','a','t','e','-','t','i','m','e'}, | |
194 | {'-','i','n','f','i','n','i','t','y'}, | |
195 | {'+','i','n','f','i','n','i','t','y'} }; | |
196 | ||
197 | template<class Config, class charT, class OutputIterator> | |
198 | const typename date_names_put<Config, charT, OutputIterator>::char_type | |
199 | date_names_put<Config, charT, OutputIterator>::separator[2] = | |
200 | {'-', '\0'} ; | |
201 | ||
202 | ||
203 | //! Generate storage location for a std::locale::id | |
204 | template<class Config, class charT, class OutputIterator> | |
205 | std::locale::id date_names_put<Config, charT, OutputIterator>::id; | |
206 | ||
207 | //! A date name output facet that takes an array of char* to define strings | |
208 | template<class Config, | |
209 | class charT = char, | |
210 | class OutputIterator = std::ostreambuf_iterator<charT> > | |
211 | class all_date_names_put : public date_names_put<Config, charT, OutputIterator> | |
212 | { | |
213 | public: | |
214 | all_date_names_put(const charT* const month_short_names[], | |
215 | const charT* const month_long_names[], | |
216 | const charT* const special_value_names[], | |
217 | const charT* const weekday_short_names[], | |
218 | const charT* const weekday_long_names[], | |
219 | charT separator_char = '-', | |
220 | ymd_order_spec order_spec = ymd_order_iso, | |
221 | month_format_spec month_format = month_as_short_string) : | |
222 | month_short_names_(month_short_names), | |
223 | month_long_names_(month_long_names), | |
224 | special_value_names_(special_value_names), | |
225 | weekday_short_names_(weekday_short_names), | |
226 | weekday_long_names_(weekday_long_names), | |
227 | order_spec_(order_spec), | |
228 | month_format_spec_(month_format) | |
229 | { | |
230 | separator_char_[0] = separator_char; | |
231 | separator_char_[1] = '\0'; | |
232 | ||
233 | } | |
234 | typedef OutputIterator iter_type; | |
235 | typedef typename Config::month_enum month_enum; | |
236 | typedef typename Config::weekday_enum weekday_enum; | |
237 | typedef typename Config::special_value_enum special_value_enum; | |
238 | ||
239 | const charT* const* get_short_month_names() const | |
240 | { | |
241 | return month_short_names_; | |
242 | } | |
243 | const charT* const* get_long_month_names() const | |
244 | { | |
245 | return month_long_names_; | |
246 | } | |
247 | const charT* const* get_special_value_names() const | |
248 | { | |
249 | return special_value_names_; | |
250 | } | |
251 | const charT* const* get_short_weekday_names()const | |
252 | { | |
253 | return weekday_short_names_; | |
254 | } | |
255 | const charT* const* get_long_weekday_names()const | |
256 | { | |
257 | return weekday_long_names_; | |
258 | } | |
259 | ||
260 | protected: | |
261 | //! Generic facet that takes array of chars | |
262 | virtual void do_put_month_short(iter_type& oitr, month_enum moy) const | |
263 | { | |
264 | this->put_string(oitr, month_short_names_[moy-1]); | |
265 | } | |
266 | //! Long month names | |
267 | virtual void do_put_month_long(iter_type& oitr, month_enum moy) const | |
268 | { | |
269 | this->put_string(oitr, month_long_names_[moy-1]); | |
270 | } | |
271 | //! Special values names | |
272 | virtual void do_put_special_value(iter_type& oitr, special_value_enum sv) const | |
273 | { | |
274 | this->put_string(oitr, special_value_names_[sv]); | |
275 | } | |
276 | virtual void do_put_weekday_short(iter_type& oitr, weekday_enum wd) const | |
277 | { | |
278 | this->put_string(oitr, weekday_short_names_[wd]); | |
279 | } | |
280 | virtual void do_put_weekday_long(iter_type& oitr, weekday_enum wd) const | |
281 | { | |
282 | this->put_string(oitr, weekday_long_names_[wd]); | |
283 | } | |
284 | //! char between year-month | |
285 | virtual void do_month_sep_char(iter_type& oitr) const | |
286 | { | |
287 | this->put_string(oitr, separator_char_); | |
288 | } | |
289 | //! Char to separate month-day | |
290 | virtual void do_day_sep_char(iter_type& oitr) const | |
291 | { | |
292 | this->put_string(oitr, separator_char_); | |
293 | } | |
294 | //! Set the date ordering | |
295 | virtual ymd_order_spec do_date_order() const | |
296 | { | |
297 | return order_spec_; | |
298 | } | |
299 | //! Set the date ordering | |
300 | virtual month_format_spec do_month_format() const | |
301 | { | |
302 | return month_format_spec_; | |
303 | } | |
304 | ||
305 | private: | |
306 | const charT* const* month_short_names_; | |
307 | const charT* const* month_long_names_; | |
308 | const charT* const* special_value_names_; | |
309 | const charT* const* weekday_short_names_; | |
310 | const charT* const* weekday_long_names_; | |
311 | charT separator_char_[2]; | |
312 | ymd_order_spec order_spec_; | |
313 | month_format_spec month_format_spec_; | |
314 | }; | |
315 | ||
316 | } } //namespace boost::date_time | |
317 | ||
318 | #endif //BOOST_NO_STD_LOCALE | |
319 | ||
320 | #endif |