home *** CD-ROM | disk | FTP | other *** search
- /* Object to hold a date -- created 8/26/88 acr
-
- 11/30/88 mzu -added a test in asString to use international
- date format.
- -asLongString, dayOfWeek are hard coded in english
- */!!
-
- inherit(Magnitude, #Date, #(month /* Month 1-12 */
- day /* Day 1-31 */
- year /* Year */), 2, nil)!!
-
- now(DateClass)!!
-
- /* Create a new Date object and initialize. */
- Def new(self)
- { ^init(new(self:Behavior))
- }!!
-
- /* Return current date. */
- Def current(self | ds)
- { ds := new(Struct, 16);
- putMSB(ds, 0x2a, 4);
- call(ds);
-
- ^date(atMSB(ds, 10), atLSB(ds, 10), wordAt(ds, 8))
- }!!
-
- now(Date)!!
-
- /* Return date in string in international date format */
- Def asString(self | iDate)
- {
- iDate := getProfileString("intl", "iDate");
- select
- case iDate = "2"
- ^asYYMMDDString(self);
- endCase
- case iDate = "1"
- ^asDDMMYYString(self);
- endCase
- default /* "0" or not found */
- ^asMMDDYYString(self);
- endSelect;
- }!!
-
- /* Return date in abbreviated YY/MM/DD string format. */
- Def asYYMMDDString(self)
- { ^asPaddedString(year mod 100, 2) + "/" +
- asString(month) + "/" +
- asString(day);
- }!!
-
- /* Return date in abbreviated MM/DD/YY string format. */
- Def asMMDDYYString(self)
- { ^asString(month) + "/" +
- asString(day) + "/" +
- asPaddedString(year mod 100, 2)
- }!!
-
- /* Return date in abbreviated DD/MM/YY string format. */
- Def asDDMMYYString(self)
- { ^asString(day) + "/" +
- asString(month) + "/" +
- asPaddedString(year mod 100, 2)
- }!!
-
- /* Return date in long string format. */
- Def asLongString(self)
- { ^#("January" "February" "March" "April" "May" "June" "July"
- "August" "September" "October" "November" "December")[month-1] +
- " " + asString(day) + ", " + asString(year)
- }!!
-
- /* Return date in 'day of the week' format. */
- Def asDayString(self)
- { ^dayOfWeek(self) + ", " + asLongString(self)
- }!!
-
- /* Return number of days since 1/1/1901. */
- Def asLong(self)
- { ^asLong(
- (year - 1901) * 365 +
- daysBeforeMonth(self) +
- day - 1 +
- leapDays(self)
- )
- }!!
-
- /* Included so that addition and subtraction
- will work with Longs or Ints. */
- Def asInt(self)
- { ^asLong(self)
- }!!
-
- /* Infix operation. Return 0 if x = self, otherwise returns nil. */
- Def =(self, x)
- { if class(self) == class(x)
- ^(x.day == day) cand (x.month == month) cand (x.year == year)
- else
- ^nil
- endif
- }!!
-
- /* Infix operation. Return 0 if x < self, otherwise return nil. */
- Def <(self, x)
- { select
- case (x.year < year)
- ^0
- endCase
- case (x.year == year) cand (x.month < month)
- ^0
- endCase
- case (x.year == year) cand (x.month == month) cand (x.day < day)
- ^0
- endCase
- default
- ^nil
- endSelect;
- }!!
-
- /* Infix operation. Return 0 if x <= self, otherwise return nil. */
- Def <=(self, x)
- { ^(x < self) cor (x = self)
- }!!
-
- /* Infix operation. Return 0 if x > self, otherwise return nil. */
- Def >(self, x)
- { select
- case (x.year > year)
- ^0
- endCase
- case (x.year == year) cand (x.month > month)
- ^0
- endCase
- case (x.year == year) cand (x.month == month) cand (x.day > day)
- ^0
- endCase
- default
- ^nil
- endSelect;
- }!!
-
- /* Infix operation. Return 0 if x >= self, otherwise return nil. */
- Def >=(self, x)
- { ^(x > self) cor (x = self)
- }!!
-
- /* Infix operation. Add a Date to another Date, an Int, or a Long.
- Return a Long. You must use asDate() to convert back to a Date. */
- Def +(self, x)
- { ^asLong(x) + asLong(self):Long
- }!!
-
- /* Infix operation. Find difference between two dates, or
- subtract a number of days (an Int or Long) from a Date. */
- Def -(self, x)
- { ^asLong(x) - asLong(self):Long
- }!!
-
- /* Return number of days between two dates. This
- is a more efficient than date1 - date2. */
- Def diff(self, y)
- { ^(year - y.year) * 365 +
- daysBeforeMonth(self) - daysBeforeMonth(y) +
- day - y.day +
- leapDays(self) - leapDays(y)
- }!!
-
- /* Increment a Date by one, modifying it directly. */
- Def inc(self)
- { day := day + 1;
-
- if day > #(31 28 31 30 31 30 31 31 30 31 30 31)[month - 1]
- if month ~= 2 cor not(year mod 4 == 0) cor day > 29
- month := month + 1;
- day := 1;
- if month > 12
- year := year + 1;
- month := 1;
- endif;
- endif;
- endif
- }!!
-
- /* Decrement a Date by one, modifying it directly. */
- Def dec(self)
- { day := day - 1;
-
- if day == 0
- month := (month - 1);
-
- if month == 0
- year := year - 1;
- month := 12;
- endif;
-
- day := #(0 31 28 31 30 31 30 31 31 30 31 30 31)[month];
-
- if (month == 2) cand (year mod 4 == 0)
- day := 29
- endif;
- endif
- }!!
-
- /* Given a date, return the next date. Preserve original date. */
- Def next(self | aDate)
- { aDate := new(Date);
- aDate.day := day;
- aDate.month := month;
- aDate.year := year;
- ^inc(aDate)
- }!!
-
- /* Given a date, return the previous date. Preserve original date. */
- Def previous(self | aDate)
- { aDate := new(Date);
- aDate.day := day;
- aDate.month := month;
- aDate.year := year;
- ^dec(aDate)
- }!!
-
- /* Return number of February 29s since 1/1/1901. */
- Def leapDays(self)
- { if (month < 3) cand (year mod 4 == 0)
- ^(year - 1900)/4 - 1
- else
- ^(year - 1900)/4
- endif
- }!!
-
- /* Private method. Return number of days in a year before this month. */
- Def daysBeforeMonth(self)
- { ^#(0 31 59 90 120 151 181 212 243 273 304 334 365)[abs((month - 1) mod 13)]
- }!!
-
- /* Initialize a date to 1/1/80. */
- Def init(self)
- { month := 1;
- day := 1;
- year := 1980;
- }!!
-
- /* Determine if a Date is valid. Used by conversion
- methods to guarantee that dates are always valid. */
- Def isValid(self)
- { if self <> asDate(asLong(self))
- ^nil
- endif
- }!!
-
- /* Return day of the week. */
- Def dayOfWeek(self)
- { ^#("Tuesday" "Wednesday" "Thursday"
- "Friday" "Saturday" "Sunday" "Monday")[asInt(asLong(self) mod 7)]
- }!!
-
- /* Print a date. */
- Def print(self)
- { print(asString(self))
- }!!
-
- /* Put a date onto the specified Stream. */
- Def printOn(self, aStrm)
- { printOn(asString(self), aStrm)
- }!!
-