//------------------------------------------------------------------------------
// Compilation Unit Header
//------------------------------------------------------------------------------
//
// Copyright (c) 2006 Waysys LLC. All Rights Reserved.
//
// Permission to use, copy, modify, and distribute this software
// and its documentation for NON-COMMERCIAL purposes and without
// fee is hereby granted provided that this copyright notice
// appears in all copies.
//
// Waysys MAKES NO REPRESENTATIONS OR WARRANTIES ABOUT THE SUITABILITY OF
// THE SOFTWARE, EITHER EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED
// TO THE IMPLIED WARRANTIES OF MERCHANTABILITY, FITNESS FOR A
// PARTICULAR PURPOSE, OR NON-INFRINGEMENT. Waysys SHALL NOT BE LIABLE FOR
// ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF USING, MODIFYING OR
// DISTRIBUTING THIS SOFTWARE OR ITS DERIVATIVES.
//
// For further information, contact Waysys LLC at waysys@waysyweb.com
// or 800-622-5315 (USA).
//
//------------------------------------------------------------------------------
// Maintenance History
//------------------------------------------------------------------------------
//
// Person Date Change
// ------ ----------- ----------------------------------------------------
//
// Shaffer 09-Jul-2006 File created
// Shaffer 07-Jan-2007 Removed reference to WayDateException
//
//------------------------------------------------------------------------------
// Imports
//------------------------------------------------------------------------------
package com.waysysweb.util;
//------------------------------------------------------------------------------
// Public Class Declaration
//------------------------------------------------------------------------------
/**
* This class computes a set of dates corresponding to various holidays. The
* class generates instances of the WayDate class.
*
* @see com.waysysweb.util.WayDate
* @see Wikipedia
* @see Federal Holidays
* @see Easter
*
* @author William A. Shaffer
* @version 1.00
*/
public class Holiday
{
//------------------------------------------------------------------------------
// Fields
//------------------------------------------------------------------------------
/** First day of the week in the month */
public static final int FIRST = 1;
/** Second day of the week in the month */
public static final int SECOND = 2;
/** Third day of the week in the month */
public static final int THIRD = 3;
/** Forth day of the week in the month */
public static final int FOURTH = 4;
/** Last day of the week in the month */
public static final int LAST = 0;;
//------------------------------------------------------------------------------
// Constructors
//------------------------------------------------------------------------------
/**
* Create an instance of this class.
*
*/
public Holiday()
{
super();
return;
}
//------------------------------------------------------------------------------
// Holiday Methods
//------------------------------------------------------------------------------
/**
* Return the date for New Year's Day
*
* @param year the desired year (year inset range(MINYEAR, MAXYEAR))
* @return the date for New Year's Day
*/
public static WayDate getNewYearsDay(int year)
{
assert WayDate.isValidYear(year) : "Illegal year: " + year;
return new WayDate(1, 1, year);
}
/**
* Return the date for Birthday of Martin Luther King, Jr.
*
* @param year the desired year (year inset range(MINYEAR, MAXYEAR))
* @return the date for Birthday of Martin Luther King, Jr.
* @exception WayDateException thrown if date is out of range
*/
public static WayDate getMartinLutherKingsBirthday(int year)
throws WayDateException
{
assert WayDate.isValidYear(year) : "Illegal year: " + year;
WayDate date = getDateFromPosition(1, year, WayDate.MONDAY, THIRD);
return date;
}
/**
* Return the date for Birthday of George Washington
*
* @param year the desired year (year inset range(MINYEAR, MAXYEAR))
* @return the date for Birthday of George Washington
* @exception WayDateException thrown if date is out of range
*/
public static WayDate getWashingtonsBirthday(int year)
throws WayDateException
{
assert WayDate.isValidYear(year) : "Illegal year: " + year;
WayDate date = getDateFromPosition(2, year, WayDate.MONDAY, THIRD);
return date;
}
/**
* Return the date for Memorial Day
*
* @param year the desired year (year inset range(MINYEAR, MAXYEAR))
* @return the date for Memorial day
* @exception WayDateException thrown if date is out of range
*/
public static WayDate getMemorialDay(int year)
throws WayDateException
{
assert WayDate.isValidYear(year) : "Illegal year: " + year;
WayDate date = getDateFromPosition(5, year, WayDate.MONDAY, LAST);
return date;
}
/**
* Return the date for Independence Day
*
* @param year the desired year (year inset range(MINYEAR, MAXYEAR))
* @return the date for Independence Day
*/
public static WayDate getIndependenceDay(int year)
{
assert WayDate.isValidYear(year) : "Illegal year: " + year;
WayDate date = new WayDate(7, 4, year);
return date;
}
/**
* Return the date for Labor Day
*
* @param year the desired year (year inset range(MINYEAR, MAXYEAR))
* @return the date for Labor Day
* @exception WayDateException thrown if date is out of bounds
*/
public static WayDate getLaborDay(int year)
throws WayDateException
{
assert WayDate.isValidYear(year) : "Illegal year: " + year;
WayDate date = getDateFromPosition(9, year, WayDate.MONDAY, FIRST);
return date;
}
/**
* Return the date for Columbus Day
*
* @param year the desired year (year inset range(MINYEAR, MAXYEAR))
* @return the date for Columbus Day
* @exception WayDateException thrown if date is out of bounds
*/
public static WayDate getColumbusDay(int year)
throws WayDateException
{
assert WayDate.isValidYear(year) : "Illegal year: " + year;
WayDate date = getDateFromPosition(10, year, WayDate.MONDAY, SECOND);
return date;
}
/**
* Return the date for Veterans' Day
*
* @param year the desired year (year inset range(MINYEAR, MAXYEAR))
* @return the date for Veterans' Day
*/
public static WayDate getVeteransDay(int year)
{
assert WayDate.isValidYear(year) : "Illegal year: " + year;
WayDate date = new WayDate(11, 11, year);
return date;
}
/**
* Return the date for Thanksgiving
*
* @param year the desired year (year inset range(MINYEAR, MAXYEAR))
* @return the date for Thanksgiving
* @exception WayDateException thrown if date is out of bounds
*/
public static WayDate getThanksgiving(int year)
throws WayDateException
{
assert WayDate.isValidYear(year) : "Illegal year: " + year;
WayDate date = getDateFromPosition(11, year, WayDate.THURSDAY, FOURTH);
return date;
}
/**
* Return the date for Christmas.
*
* @param year the desired year (year inset range(MINYEAR, MAXYEAR))
* @return the date for Christmas
*/
public static WayDate getChristmas(int year)
{
assert WayDate.isValidYear(year) : "Illegal year: " + year;
WayDate date = new WayDate(12, 25, year);
return date;
}
//------------------------------------------------------------------------------
// Date Support Methods
//------------------------------------------------------------------------------
/**
* Return a date on a specified day of the week on or before a specified
* date.
*
* @param inputDate the date being considered
* @param dayOfWeek the day of the week (dayOfWeek inset range(0, 6))
* @return the date such that dayOfWeek(date) = dayOfWeek andalso
* compare(inputDate, date) <> LESS
* @exception WayDateException thrown if the result of adds are out of bounds
*/
public static WayDate getDateOnDayOfWeekOnOrBefore(WayDate inputDate, int dayOfWeek)
throws WayDateException
{
assert WayDate.isValidDayOfWeek(dayOfWeek) :
"Invalid day of week " + dayOfWeek;
WayDate date1 = (WayDate)inputDate.clone();
date1.add(-dayOfWeek);
int priorDayOfWeek = date1.getDayOfWeek();
date1 = (WayDate)inputDate.clone();
date1.add(-priorDayOfWeek);
return date1;
}
/**
* Return the date on a specified day of the week after a specified date
*
* @param inputDate the date being considered
* @param dayOfWeek the day of the week (dayOfWeek inset range(0, 6))
* @return the date such that dayOfWeek(date) = dayOfWeek andalso
* compare(inputDate, date) = GREATER
* @exception WayDateException thrown if the result of adds are out of bounds
*/
public static WayDate getDateOnDayOfWeekAfter(WayDate inputDate, int dayOfWeek)
throws WayDateException
{
assert WayDate.isValidDayOfWeek(dayOfWeek) :
"Invalid day of week " + dayOfWeek;
WayDate date = (WayDate)inputDate.clone();
date.add(7);
date = getDateOnDayOfWeekOnOrBefore(date, dayOfWeek);
return date;
}
/**
* Return the date on a specified day of the week after a specified date
*
* @param inputDate the date being considered
* @param dayOfWeek the day of the week (dayOfWeek inset range(0, 6))
* @return the date such that dayOfWeek(date) = dayOfWeek andalso
* compare(inputDate, date) = GREATER
* @exception WayDateException thrown if the result of adds are out of bounds
*/
public static WayDate getDateOnDayOfWeekBefore(WayDate inputDate, int dayOfWeek)
throws WayDateException
{
assert WayDate.isValidDayOfWeek(dayOfWeek) :
"Invalid day of week " + dayOfWeek;
WayDate date = (WayDate)inputDate.clone();
date.add(-1);
date = getDateOnDayOfWeekOnOrBefore(date, dayOfWeek);
return date;
}
/**
* Return the nth day that is on a specified day of the week from
* a specified date.
*
* @param inputDate the date being considered
* @param dayOfWeek the day of the week (dayOfWeek inset range(0, 6))
* @param monthPosition the position in the month
* (monthPosition inset range(0, 4)
* @return a date in the Nth position
* @exception WayDateException thrown if adding offset puts the date out
* of bound
*/
public static WayDate getNthDayFromDate(WayDate inputDate, int dayOfWeek,
int monthPosition)
throws WayDateException
{
assert WayDate.isValidDayOfWeek(dayOfWeek) :
"Invalid day of week " + dayOfWeek;
assert isValidMonthPosition(monthPosition);
//
// Determine offset
//
int offset = 0;
switch (monthPosition)
{
case FIRST: offset = 7; break;
case SECOND: offset = 14; break;
case THIRD: offset = 21; break;
case FOURTH: offset = 28; break;
case LAST: offset = -7; break;
default: assert false: "Illegal month position";
}
//
// Get working date
//
WayDate date;
if (monthPosition == LAST)
date = getDateOnDayOfWeekAfter(inputDate, dayOfWeek);
else date = getDateOnDayOfWeekBefore(inputDate, dayOfWeek);
//
// Add the offset
//
date.add(offset);
return date;
}
/**
* Return a date with the specified month and year and day of week.
* The month position of the date is as specified.
*
* @param month the month of the date (month inset range(1, 12))
* @param year the year of the date (year inset range(MINYEAR, MAXYEAR))
* @param dayOfWk the day of the week
* (dayOfWeek inset range(SUNDAY, SATURDAY))
* @param monthPosition the month position
* (monthPosition inset range(LAST, FOURTH))
* @return an instance of WayDate with the specified month, year, day of week
* and month position
* @exception WayDateException thrown if calculation puts date out of range
*/
public static WayDate getDateFromPosition(int month, int year, int dayOfWk,
int monthPosition)
throws WayDateException
{
assert WayDate.isValidMonth(month) :
"Illegal month: " + month;
assert WayDate.isValidYear(year) :
"Illegal year: " + year;
assert WayDate.isValidDayOfWeek(dayOfWk) :
"Illegal day of week: " + dayOfWk;
assert isValidMonthPosition(monthPosition) :
"Illegal month position: " + monthPosition;
//
// Create initial date
//
WayDate date;
if (monthPosition == LAST)
date = new WayDate(month, WayDate.daysInMonth(month, year), year);
else date = new WayDate(month, 1, year);
//
// Move the date to the proper position
//
date = getNthDayFromDate(date, dayOfWk, monthPosition);
return date;
}
/**
* Return the date a holiday would be observed if it were a federal
* holiday.
*
* @param date the holiday being checked
* @return the date a holiday will be observed
*/
public static WayDate getObservedHoliday(WayDate date)
{
int dayOfWeek = date.getDayOfWeek();
WayDate result = (WayDate)date.clone();
switch (dayOfWeek)
{
case WayDate.SUNDAY : result.increment(); break;
case WayDate.SATURDAY: result.decrement(); break;
// default: return original date
}
return result;
}
//------------------------------------------------------------------------------
// Validation Return
//------------------------------------------------------------------------------
/**
* Return true if the month posiiton is valid.
*
* @param monthPosition the month position
* @return monthPosition inset range(LAST, FORTH)
*/
public static boolean isValidMonthPosition(int monthPosition)
{
boolean result;
if ((monthPosition >= 0) && (monthPosition <= FOURTH))
result = true;
else result = false;
return result;
}
//------------------------------------------------------------------------------
// Easter Calculations
//------------------------------------------------------------------------------
}