diff options
-rw-r--r-- | include/datetime/date-time.h | 10 | ||||
-rw-r--r-- | src/date-time.cpp | 77 |
2 files changed, 71 insertions, 16 deletions
diff --git a/include/datetime/date-time.h b/include/datetime/date-time.h index 4be35f7..6e73ff3 100644 --- a/include/datetime/date-time.h +++ b/include/datetime/date-time.h @@ -38,13 +38,15 @@ public: static DateTime NowLocal(); static DateTime Local(int years, int months, int days, int hours, int minutes, int seconds); + DateTime(); explicit DateTime(time_t t); - explicit DateTime(GDateTime* in=nullptr); - DateTime& operator=(GDateTime* in); + DateTime(GTimeZone* tz, GDateTime* dt); DateTime& operator=(const DateTime& in); DateTime to_timezone(const std::string& zone) const; + DateTime start_of_day() const; + DateTime start_of_minute() const; + DateTime add_days(int days) const; DateTime add_full(int years, int months, int days, int hours, int minutes, double seconds) const; - void reset(GDateTime* in=nullptr); GDateTime* get() const; GDateTime* operator()() const {return get();} @@ -69,6 +71,8 @@ public: bool is_set() const { return m_dt != nullptr; } private: + void reset(GTimeZone*, GDateTime*); + std::shared_ptr<GTimeZone> m_tz; std::shared_ptr<GDateTime> m_dt; }; diff --git a/src/date-time.cpp b/src/date-time.cpp index a139ea9..33b1590 100644 --- a/src/date-time.cpp +++ b/src/date-time.cpp @@ -27,42 +27,49 @@ namespace datetime { **** ***/ -DateTime::DateTime(GDateTime* gdt) +DateTime::DateTime() { - reset(gdt); } -DateTime& DateTime::operator=(GDateTime* gdt) +DateTime::DateTime(GTimeZone* gtz, GDateTime* gdt) { - reset(gdt); - return *this; + g_return_if_fail((gtz==nullptr) == (gdt==nullptr)); + + reset(gtz, gdt); } DateTime& DateTime::operator=(const DateTime& that) { + m_tz = that.m_tz; m_dt = that.m_dt; return *this; } DateTime::DateTime(time_t t) { + auto gtz = g_time_zone_new_local(); auto gdt = g_date_time_new_from_unix_local(t); - reset(gdt); + reset(gtz, gdt); + g_time_zone_unref(gtz); g_date_time_unref(gdt); } DateTime DateTime::NowLocal() { + auto gtz = g_time_zone_new_local(); auto gdt = g_date_time_new_now_local(); - DateTime dt(gdt); + DateTime dt(gtz, gdt); + g_time_zone_unref(gtz); g_date_time_unref(gdt); return dt; } DateTime DateTime::Local(int year, int month, int day, int hour, int minute, int seconds) { + auto gtz = g_time_zone_new_local(); auto gdt = g_date_time_new_local (year, month, day, hour, minute, seconds); - DateTime dt(gdt); + DateTime dt(gtz, gdt); + g_time_zone_unref(gtz); g_date_time_unref(gdt); return dt; } @@ -71,20 +78,51 @@ DateTime DateTime::to_timezone(const std::string& zone) const { auto gtz = g_time_zone_new(zone.c_str()); auto gdt = g_date_time_to_timezone(get(), gtz); - DateTime dt(gdt); + DateTime dt(gtz, gdt); g_time_zone_unref(gtz); g_date_time_unref(gdt); return dt; } +DateTime DateTime::start_of_day() const +{ + g_assert(is_set()); + g_assert(m_tz.get() != nullptr); + + int y=0, m=0, d=0; + ymd(y, m, d); + auto gdt = g_date_time_new(m_tz.get(), y, m, d, 0, 0, 0); + DateTime dt(m_tz.get(), gdt); + g_date_time_unref(gdt); + return dt; +} + +DateTime DateTime::start_of_minute() const +{ + g_assert(is_set()); + g_assert(m_tz.get() != nullptr); + + int y=0, m=0, d=0; + ymd(y, m, d); + auto gdt = g_date_time_new(m_tz.get(), y, m, d, hour(), minute(), 0); + DateTime dt(m_tz.get(), gdt); + g_date_time_unref(gdt); + return dt; +} + DateTime DateTime::add_full(int years, int months, int days, int hours, int minutes, double seconds) const { auto gdt = g_date_time_add_full(get(), years, months, days, hours, minutes, seconds); - DateTime dt(gdt); + DateTime dt(m_tz.get(), gdt); g_date_time_unref(gdt); return dt; } +DateTime DateTime::add_days(int days) const +{ + return add_full(0, 0, days, 0, 0, 0); +} + GDateTime* DateTime::get() const { g_assert(m_dt); @@ -135,12 +173,25 @@ int64_t DateTime::to_unix() const return g_date_time_to_unix(get()); } -void DateTime::reset(GDateTime* in) +void DateTime::reset(GTimeZone* gtz, GDateTime* gdt) { - if (in) + g_return_if_fail ((gdt==nullptr) == (gtz==nullptr)); // all or nothin' + + if (gtz) + { + auto deleter = [](GTimeZone* tz){g_time_zone_unref(tz);}; + m_tz = std::shared_ptr<GTimeZone>(g_time_zone_ref(gtz), deleter); + g_assert(m_tz); + } + else + { + m_tz.reset(); + } + + if (gdt) { auto deleter = [](GDateTime* dt){g_date_time_unref(dt);}; - m_dt = std::shared_ptr<GDateTime>(g_date_time_ref(in), deleter); + m_dt = std::shared_ptr<GDateTime>(g_date_time_ref(gdt), deleter); g_assert(m_dt); } else |