Back to home page

EIC code displayed by LXR

 
 

    


File indexing completed on 2025-01-18 09:39:16

0001 //
0002 // Copyright (c) 2009-2011 Artyom Beilis (Tonkikh)
0003 //
0004 // Distributed under the Boost Software License, Version 1.0.
0005 // https://www.boost.org/LICENSE_1_0.txt
0006 
0007 #ifndef BOOST_LOCALE_DATE_TIME_FACET_HPP_INCLUDED
0008 #define BOOST_LOCALE_DATE_TIME_FACET_HPP_INCLUDED
0009 
0010 #include <boost/locale/config.hpp>
0011 #include <boost/locale/detail/facet_id.hpp>
0012 #include <cstdint>
0013 #include <locale>
0014 
0015 #ifdef BOOST_MSVC
0016 #    pragma warning(push)
0017 #    pragma warning(disable : 4275 4251 4231 4660)
0018 #endif
0019 
0020 namespace boost { namespace locale {
0021 
0022     /// \brief Namespace that contains various types for manipulation with dates
0023     namespace period {
0024 
0025         /// \brief This namespace holds a enum of various period types like era, year, month, etc..
0026         namespace marks {
0027 
0028             /// \brief the type that defines a flag that holds a period identifier
0029             enum period_mark {
0030                 invalid,       ///< Special invalid value, should not be used directly
0031                 era,           ///< Era i.e. AC, BC in Gregorian and Julian calendar, range [0,1]
0032                 year,          ///< Year, it is calendar specific, for example 2011 in Gregorian calendar.
0033                 extended_year, ///< Extended year for Gregorian/Julian calendars, where 1 BC == 0, 2 BC == -1.
0034                 month,         ///< The month of year, calendar specific, in Gregorian [0..11]
0035                 day,           ///< The day of month, calendar specific, in Gregorian [1..31]
0036                 day_of_year,   ///< The number of day in year, starting from 1, in Gregorian  [1..366]
0037                 day_of_week,   ///< Day of week, Sunday=1, Monday=2,..., Saturday=7.
0038                                ///< Note that updating this value respects local day of week, so for example,
0039                                ///< If first day of week is Monday and the current day is Tuesday then setting
0040                                ///< the value to Sunday (1) would forward the date by 5 days forward and not backward
0041                                ///< by two days as it could be expected if the numbers were taken as is.
0042                 day_of_week_in_month, ///< Original number of the day of the week in month. For example 1st Sunday,
0043                                       ///< 2nd Sunday, etc. in Gregorian [1..5]
0044                 day_of_week_local, ///< Local day of week, for example in France Monday is 1, in US Sunday is 1, [1..7]
0045                 hour,              ///< 24 clock hour [0..23]
0046                 hour_12,           ///< 12 clock hour [0..11]
0047                 am_pm,             ///< am or pm marker [0..1]
0048                 minute,            ///< minute [0..59]
0049                 second,            ///< second [0..59]
0050                 week_of_year,      ///< The week number in the year
0051                 week_of_month,     ///< The week number within current month
0052                 first_day_of_week, ///< First day of week, constant, for example Sunday in US = 1, Monday in France = 2
0053             };
0054 
0055         } // namespace marks
0056 
0057         /// \brief This class holds a type that represents certain period of time like
0058         /// year, hour, second and so on.
0059         ///
0060         /// It can be created from either marks::period_mark type or by using shortcuts in period
0061         /// namespace - calling functions like period::year(), period::hour() and so on.
0062         ///
0063         /// Basically it represents the same object as enum marks::period_mark but allows to
0064         /// provide save operator overloading that would not collide with casing of enum to
0065         /// numeric values.
0066         class period_type {
0067         public:
0068             /// Create a period of specific type, default is invalid.
0069             period_type(marks::period_mark m = marks::invalid) : mark_(m) {}
0070 
0071             /// Get the value of marks::period_mark it was created with.
0072             marks::period_mark mark() const { return mark_; }
0073 
0074             /// Check if two periods are the same
0075             bool operator==(const period_type& other) const { return mark() == other.mark(); }
0076             /// Check if two periods are different
0077             bool operator!=(const period_type& other) const { return mark() != other.mark(); }
0078 
0079         private:
0080             marks::period_mark mark_;
0081         };
0082 
0083     } // namespace period
0084 
0085     /// Structure that define POSIX time, seconds and milliseconds
0086     /// since Jan 1, 1970, 00:00 not including leap seconds.
0087     struct posix_time {
0088         int64_t seconds;      ///< Seconds since epoch
0089         uint32_t nanoseconds; ///< Nanoseconds resolution
0090     };
0091 
0092     /// This class defines generic calendar class, it is used by date_time and calendar
0093     /// objects internally. It is less useful for end users, but it is build for localization
0094     /// backend implementation
0095     class BOOST_SYMBOL_VISIBLE abstract_calendar {
0096     public:
0097         /// Type that defines how to fetch the value
0098         enum value_type {
0099             absolute_minimum, ///< Absolute possible minimum for the value, for example for day is 1
0100             actual_minimum,   ///< Actual minimal value for this period.
0101             greatest_minimum, ///< Maximal minimum value that can be for this period
0102             current,          ///< Current value of this period
0103             least_maximum,    ///< The last maximal value for this period, For example for Gregorian calendar
0104                               ///< day it is 28
0105             actual_maximum,   ///< Actual maximum, for it can be 28, 29, 30, 31 for day according to current month
0106             absolute_maximum, ///< Maximal value, for Gregorian day it would be 31.
0107         };
0108 
0109         /// A way to update the value
0110         enum update_type {
0111             move, ///< Change the value up or down effecting others for example 1990-12-31 + 1 day = 1991-01-01
0112             roll, ///< Change the value up or down not effecting others for example 1990-12-31 + 1 day = 1990-12-01
0113         };
0114 
0115         /// Information about calendar
0116         enum calendar_option_type {
0117             is_gregorian, ///< Check if the calendar is Gregorian
0118             is_dst        ///< Check if the current time is in daylight time savings
0119         };
0120 
0121         /// Make a polymorphic copy of the calendar
0122         virtual abstract_calendar* clone() const = 0;
0123 
0124         /// Set specific \a value for period \a p, note not all values are settable.
0125         ///
0126         /// After calling set_value you may want to call normalize() function to make sure
0127         /// all periods are updated, if you set several fields that are part of a single
0128         /// date/time representation you should call set_value several times and then
0129         /// call normalize().
0130         ///
0131         /// If normalize() is not called after set_value, the behavior is undefined
0132         virtual void set_value(period::marks::period_mark m, int value) = 0;
0133 
0134         /// Recalculate all periods after setting them, should be called after use of set_value() function.
0135         virtual void normalize() = 0;
0136 
0137         /// Get specific value for period \a p according to a value_type \a v
0138         virtual int get_value(period::marks::period_mark m, value_type v) const = 0;
0139 
0140         /// Set current time point
0141         virtual void set_time(const posix_time& p) = 0;
0142         /// Get current time point
0143         virtual posix_time get_time() const = 0;
0144         /// Get current time since epoch in milliseconds
0145         virtual double get_time_ms() const = 0;
0146 
0147         /// Set option for calendar, for future use
0148         virtual void set_option(calendar_option_type opt, int v) = 0;
0149         /// Get option for calendar, currently only check if it is Gregorian calendar
0150         virtual int get_option(calendar_option_type opt) const = 0;
0151 
0152         /// Adjust period's \a p value by \a difference items using a update_type \a u.
0153         /// Note: not all values are adjustable
0154         virtual void adjust_value(period::marks::period_mark m, update_type u, int difference) = 0;
0155 
0156         /// Calculate the difference between this calendar  and \a other in \a p units
0157         virtual int difference(const abstract_calendar& other, period::marks::period_mark m) const = 0;
0158 
0159         /// Set time zone, empty - use system
0160         virtual void set_timezone(const std::string& tz) = 0;
0161         /// Get current time zone, empty - system one
0162         virtual std::string get_timezone() const = 0;
0163 
0164         /// Check of two calendars have same rules
0165         virtual bool same(const abstract_calendar* other) const = 0;
0166 
0167         virtual ~abstract_calendar() = default;
0168     };
0169 
0170     /// \brief the facet that generates calendar for specific locale
0171     class BOOST_SYMBOL_VISIBLE calendar_facet : public std::locale::facet, public detail::facet_id<calendar_facet> {
0172     public:
0173         /// Basic constructor
0174         calendar_facet(size_t refs = 0) : std::locale::facet(refs) {}
0175         /// Create a new calendar that points to current point of time.
0176         virtual abstract_calendar* create_calendar() const = 0;
0177     };
0178 
0179 }} // namespace boost::locale
0180 
0181 #ifdef BOOST_MSVC
0182 #    pragma warning(pop)
0183 #endif
0184 
0185 #endif