-/////////////////////////////////////////////////////////////////////////////
-// Name: time.cpp
-// Purpose: wxTime class, from NIHCL
-// Author: Julian Smart, after K. E. Gorlen
-// Modified by:
-// Created: 04/01/98
-// RCS-ID: $Id$
-// Copyright: (c) Julian Smart and Markus Holzem
-// Licence: wxWindows license
-/////////////////////////////////////////////////////////////////////////////
-
-#ifdef __GNUG__
-#pragma implementation "time.h"
-#endif
-
-/*
-Provides an object that represents a Time, stored as the number of
-seconds since January 1, 1901, GMT.
-*/
-
-// For compilers that support precompilation, includes "wx.h".
+///////////////////////////////////////////////////////////////////////////////
+// Name: src/common/time.cpp
+// Purpose: Implementation of time-related functions.
+// Author: Vadim Zeitlin
+// Created: 2011-11-26
+// RCS-ID: $Id: wxhead.cpp,v 1.11 2010-04-22 12:44:51 zeitlin Exp $
+// Copyright: (c) 2011 Vadim Zeitlin <vadim@wxwidgets.org>
+// Licence: wxWindows licence
+///////////////////////////////////////////////////////////////////////////////
+
+// ============================================================================
+// declarations
+// ============================================================================
+
+// ----------------------------------------------------------------------------
+// headers
+// ----------------------------------------------------------------------------
+
+// for compilers that support precompilation, includes "wx.h".
#include "wx/wxprec.h"
#ifdef __BORLANDC__
-#pragma hdrstop
+ #pragma hdrstop
#endif
-#include "wx/setup.h"
-
-#if wxUSE_TIMEDATE
-
#include "wx/time.h"
-#include "wx/date.h"
-#include "wx/utils.h"
-#include "wx/intl.h"
-#if wxUSE_STD_IOSTREAM
- #include "wx/ioswrap.h"
- #if wxUSE_IOSTREAMH
- #include <iomanip.h>
- #else
- #include <iomanip>
+#ifndef WX_GMTOFF_IN_TM
+ // Define it for some systems which don't (always) use configure but are
+ // known to have tm_gmtoff field.
+ #if defined(__WXPALMOS__) || defined(__DARWIN__)
+ #define WX_GMTOFF_IN_TM
#endif
#endif
-#include <string.h>
-
-#if !USE_SHARED_LIBRARY
-IMPLEMENT_DYNAMIC_CLASS(wxTime, wxObject)
-#endif
-
-
-extern bool wxGetLocalTime(long *timeZone, int *dstObserved);
-extern long wxGetCurrentTime(void);
-
-static long TIME_ZONE; /* seconds west of GMT */
-static int DST_OBSERVED; /* flags U.S. daylight saving time observed */
-
-static bool wxTimeInitialized = FALSE;
-
-wxTime::tFormat wxTime::Format = wxTime::wx12h;
-wxTime::tPrecision wxTime::Precision = wxTime::wxStdMinSec;
-
-static const unsigned long seconds_in_day = 24*60*60L;
-static const wxDate refDate(1,1,1901);
-// static const wxDate maxDate(49709L); /* ((2**32)-1)/seconds_in_day -1 */
-
-wxTime wxTime::GetLocalTime(const wxDate& date, hourTy h, minuteTy m, secondTy s)
-/*
- Return a local wxTime for the specified Standard Time date, hour, minute,
- and second.
-*/
-{
- if (!wxTimeInitialized)
- {
- wxGetLocalTime(&TIME_ZONE, &DST_OBSERVED);
- wxTimeInitialized = TRUE;
- }
-/*
- if (!date.IsBetween(refDate,maxDate))
- setError(NIHCL_DATERANGE,DEFAULT,
- date.dayOfMonth(),date.nameOfMonth(),date.year());
-*/
- // The following line causes an error in GCC 2.1
-// long daysBetween = date-refDate;
- // ... but this seems to get round it.
- wxDate tmp1(date);
- wxDate tmp2(refDate);
- long daysBetween = tmp1 - tmp2;
-
- return wxTime(seconds_in_day*daysBetween + 60*60L*h + 60*m + s);
-}
-
-wxTime::wxTime()
-/*
- Construct a wxTime for this instant.
-*/
-{
- if (!wxTimeInitialized)
- {
- wxGetLocalTime(&TIME_ZONE, &DST_OBSERVED);
- wxTimeInitialized = TRUE;
- }
- sec = wxGetCurrentTime();
-#ifdef __SALFORDC__
- sec += (unsigned long) 2177452800; /* seconds from 1/1/01 to 1/1/70 */
-#else
- sec += 2177452800UL; /* seconds from 1/1/01 to 1/1/70 */
-#endif
-}
-
-wxTime::wxTime(hourTy h, minuteTy m, secondTy s, bool dst)
-/*
- Construct a wxTime for today at the specified (local) hour, minute, and
- second.
-*/
-{
- if (!wxTimeInitialized)
- {
- wxGetLocalTime(&TIME_ZONE, &DST_OBSERVED);
- wxTimeInitialized = TRUE;
- }
-
- sec = wxTime(wxDate(),h,m,s,dst).sec;
-}
-
-
-wxTime::wxTime(const wxDate& date, hourTy h, minuteTy m, secondTy s, bool dst)
-/*
- Construct a wxTime for the specified (local) Date, hour, minute, and
- second.
-*/
-{
- if (!wxTimeInitialized)
- {
- wxGetLocalTime(&TIME_ZONE, &DST_OBSERVED);
- wxTimeInitialized = TRUE;
- }
- sec = GetLocalTime(date,h,m,s).sec-3600;
- if (IsDST())
- {
- sec += 3600;
- if (IsDST() || dst) sec -= 3600;
- }
- else
- {
- sec += 3600;
-/*
- if (IsDST()) setError(NIHCL_BADTIME,DEFAULT,
- date.dayOfMonth(),date.nameOfMonth(),date.year(),
- h,m,s,(dst?_("DST"):""));
-*/
- }
- sec += TIME_ZONE; // adjust to GMT
-}
-
-#ifndef __SALFORDC__
-wxTime::operator wxDate() const
-/*
- Convert a wxTime to a local wxDate
-*/
-{
-// return wxDate((int)(GetLocalTime().sec/seconds_in_day)); 4.2 cc bug
- long daycount = (long)(GetLocalTime().sec/seconds_in_day);
-
- wxDate date(1,1,1901);
- date += daycount;
- return date;
-}
-#endif
-
-bool wxTime::IsBetween(const wxTime& a, const wxTime& b) const
-{
- return *this >= a && *this <= b;
-}
-
-hourTy wxTime::GetHour() const
-/*
- Return the hour of this wxTime in local time; i.e., adjust for
- time zone and Daylight Savings Time.
-*/
-{
- return GetLocalTime().GetHourGMT();
-}
-
-hourTy wxTime::GetHourGMT() const
-/*
- Return the hour of this Time in GMT.
-*/
-{
- return (hourTy)((sec % 86400) / 3600);
-}
-
-wxTime wxTime::GetBeginDST(unsigned year)
-/*
- Return the local Standard Time at which Daylight Savings Time
- begins in the specified year.
-*/
-{
- // Previous Sunday
- wxTime DSTtime(GetLocalTime(wxDate(3,31,year).Previous(1)+7,2));
- if (year<=1986) {
- // Previous Sunday
- DSTtime = GetLocalTime(wxDate(4,30,year).Previous(1),2);
- if (year==1974) DSTtime = GetLocalTime(wxDate(1,6,1974),2);
- if (year==1975) DSTtime = GetLocalTime(wxDate(2,23,1975),2);
- }
- return DSTtime;
-}
-
-wxTime wxTime::GetEndDST(unsigned year)
-/*
- Return the local Standard Time at which Daylight Savings Time
- ends in the specified year.
-*/
-{
- wxTime STDtime(GetLocalTime(wxDate(10,31,year).Previous(1),2-1));
- return STDtime;
-}
-
-bool wxTime::IsDST() const
-/*
- Return TRUE if this local Standard Time should be adjusted
- for Daylight Savings Time.
-*/
-{
- long daycount = (long)(sec/seconds_in_day);
-
- // At this point, daycount is the number of days from 1/1/1901.
- // Need to convert to julian date (which starts at 1/1/4713 B.C.)
- wxDate date(1,1,1901);
- date += daycount;
-
- unsigned year = date.GetYear();
- if (DST_OBSERVED)
- {
- if (*this >= GetBeginDST(year))
- if (*this < GetEndDST(year)) return TRUE;
- }
- return FALSE;
-}
-
-wxTime wxTime::GetLocalTime() const
-/*
- Adjusts this GM Time for local time zone and Daylight Savings Time.
-*/
-{
- wxTime local_time(sec-TIME_ZONE);
- if (local_time.IsDST()) local_time.sec += 3600;
- return local_time;
-}
-
-minuteTy wxTime::GetMinute() const
-/*
- Return the minute of this wxTime in local time; i.e., adjust
- for time zone and Daylight Savings Time.
-*/
-{
- return GetLocalTime().GetMinuteGMT();
-}
-
-minuteTy wxTime::GetMinuteGMT() const
-/*
- Return the minute of this wxTime in GMT.
-*/
-{
- return (minuteTy)(((sec % 86400) % 3600) / 60);
-}
-
-secondTy wxTime::GetSecond() const
-/*
- Return the second of this wxTime.
-*/
-{
- return (secondTy)(((sec % 86400) % 3600) % 60);
-}
-
-secondTy wxTime::GetSecondGMT() const
-/*
- Return the minute of this wxTime in GMT.
-*/
-{
- return (secondTy)(((sec % 86400) % 3600) % 60);
-}
-
-int wxTime::GetDay() const
-{
- wxDate da((wxDate) *this);
- return da.GetDay();
-}
-
-int wxTime::GetDayOfWeek() const
-{
- wxDate da((wxDate) *this);
- return da.GetDayOfWeek();
-}
-
-int wxTime::GetMonth() const
-{
- wxDate da((wxDate) *this);
- return da.GetMonth();
-}
-
-int wxTime::GetYear() const
-{
- wxDate da((wxDate) *this);
- return da.GetYear();
-}
-
-wxTime wxTime::Max(const wxTime& t) const
-{
- if (t < *this) return *this;
+// ============================================================================
+// implementation
+// ============================================================================
+
+// returns the time zone in the C sense, i.e. the difference UTC - local
+// (in seconds)
+int wxGetTimeZone()
+{
+#ifdef WX_GMTOFF_IN_TM
+ // set to true when the timezone is set
+ static bool s_timezoneSet = false;
+ static long gmtoffset = LONG_MAX; // invalid timezone
+
+ // ensure that the timezone variable is set by calling wxLocaltime_r
+ if ( !s_timezoneSet )
+ {
+ // just call wxLocaltime_r() instead of figuring out whether this
+ // system supports tzset(), _tzset() or something else
+ time_t t = time(NULL);
+ struct tm tm;
+
+ wxLocaltime_r(&t, &tm);
+ s_timezoneSet = true;
+
+ // note that GMT offset is the opposite of time zone and so to return
+ // consistent results in both WX_GMTOFF_IN_TM and !WX_GMTOFF_IN_TM
+ // cases we have to negate it
+ gmtoffset = -tm.tm_gmtoff;
+
+ // this function is supposed to return the same value whether DST is
+ // enabled or not, so we need to use an additional offset if DST is on
+ // as tm_gmtoff already does include it
+ if ( tm.tm_isdst )
+ gmtoffset += 3600;
+ }
+ return (int)gmtoffset;
+#elif defined(__DJGPP__) || defined(__WINE__)
+ struct timeb tb;
+ ftime(&tb);
+ return tb.timezone*60;
+#elif defined(__VISUALC__)
+ // We must initialize the time zone information before using it (this will
+ // be done only once internally).
+ _tzset();
+
+ // Starting with VC++ 8 timezone variable is deprecated and is not even
+ // available in some standard library version so use the new function for
+ // accessing it instead.
+ #if wxCHECK_VISUALC_VERSION(8)
+ long t;
+ _get_timezone(&t);
return t;
+ #else // VC++ < 8
+ return timezone;
+ #endif
+#elif defined(WX_TIMEZONE) // If WX_TIMEZONE was defined by configure, use it.
+ return WX_TIMEZONE;
+#elif defined(__BORLANDC__) || defined(__MINGW32__) || defined(__VISAGECPP__)
+ return _timezone;
+#elif defined(__MWERKS__)
+ return 28800;
+#else // unknown platform -- assume it has timezone
+ return timezone;
+#endif // WX_GMTOFF_IN_TM/!WX_GMTOFF_IN_TM
}
-
-wxTime wxTime::Min(const wxTime& t) const
-{
- if (t > *this) return *this;
- return t;
-}
-
-#ifndef __SALFORDC__
-wxTime::operator wxChar *(void)
-{
- return FormatTime();
-}
-#endif
-
-void wxTime::SetFormat(const wxTime::tFormat lFormat,
- const wxTime::tPrecision lPrecision) {
-
- wxTime::Format = lFormat;
- wxTime::Precision = lPrecision;
-}
-
-wxChar *wxTime::FormatTime() const {
- static wxChar timeBuf[30];
- unsigned hh(GetHour());
-
- switch (Format) {
- case wx12h:
- hh -= 12;
- break;
- case wx24h:
- break;
- }
-
- switch (Precision) {
- case wxStdMinSec:
- wxSprintf(timeBuf,wxT("%2d:%02d:%02d"),hh,GetMinute(),GetSecond());
- break;
- case wxStdMin:
- wxSprintf(timeBuf,wxT("%2d:%02d"),hh,GetMinute());
- break;
- }
-
- if (Format == wx12h)
- if (GetHour() <= 12)
- wxStrcat(timeBuf,_("am"));
- else
- wxStrcat(timeBuf,_("pm"));
-
- return timeBuf;
-}
-
-/*
-int wxTime::compare(const Object& ob) const
-{
- assertArgSpecies(ob,classDesc,"compare");
- register clockTy t = castdown(ob).sec;
- if (sec < t) return -1;
- if (sec > t) return 1;
- return 0;
-}
-
-void wxTime::deepenShallowCopy() {}
-
-unsigned wxTime::hash() const { return sec; }
-
-bool wxTime::isEqual(const Object& ob) const
-{
- return ob.isSpecies(classDesc) && *this==castdown(ob);
-}
-
-const Class* wxTime::species() const { return &classDesc; }
-
-void wxTime::printOn(ostream& strm) const
-{
- register unsigned hh = GetHour();
- wxDate(*this).printOn(strm);
- strm << ' ' << ((hh <= 12) ? hh : hh-12) << ':'
- << setfill('0') << setw(2) << GetMinute() << ':'
- << setfill('0') << setw(2) << GetSecond() << ' ';
- if (hh < 12) strm << _("am");
- else strm << _("pm");
-}
-
-wxTime::wxTime(OIOin& strm)
- : BASE(strm)
-{
- unsigned long usec;
- strm >> sec >> usec;
-}
-
-void wxTime::storer(OIOout& strm) const
-{
- BASE::storer(strm);
- strm << sec << 0l;
-}
-
-
-wxTime::wxTime(OIOifd& fd)
- : BASE(fd)
-{
- unsigned long usec;
- fd >> sec >> usec;
-}
-
-void wxTime::storer(OIOofd& fd) const
-{
- BASE::storer(fd);
- fd << sec << 0l;
-}
-*/
-
-#endif