Following on from this thread, I thought I’d have a more decent stab at creating a function to calculate floating days. Useful for calculating some holidays that occur on particular days or for calculating when the next pay day is due :hugegrin:
nthDay FUNCTION
Calculates the nth day of the month,
e.g. the first Wednesday, the third Friday, the last Sunday, and the third Friday from the end of the month, etc.
ARGUMENTS:
[COLOR=“Red”]nth[/COLOR] - an integer that represents which nth day occurrence to search for, e.g. 1, 2, 3, 4, 5
n.b. A zero value will return the date of the last weekday.
n.b. A negative value will return the nth day counting back from the end of the month.
[COLOR=“red”]weekday[/COLOR] - day of the week to search for (Sunday = 0, Monday = 1, etc.)
[COLOR=“red”]*month *[/COLOR]- month to search in (January = 0, February = 1, etc.)
[COLOR=“red”]year[/COLOR] - year to search in (1995, 2008, etc.)
RETURNS:
[COLOR=“red”]nthDate[/COLOR] - new date object for the nth day
[COLOR=“red”]error[/COLOR] - an error message if the nth day argument is outside the month
function nthDay(nth, weekday, month, year) {
var nthDate:Date = new Date(year, month + ((nth <= 0) ? 1 : 0), 1);
var dayofweek:Number = nthDate.getDay();
var offset:Number = weekday - dayofweek;
nthDate = new Date(year, month + ((nth <= 0) ? 1 : 0), nthDate.getDate() + (offset + (nth - (offset >= 0 ? 1 : 0)) * 7));
if (nthDate.getMonth() <> month) {
return "**ERROR ** nthDay (" + nth + ") Out of range";
} else {
return nthDate;
}
}
Sample Use:
trace("Memorial Day = " + nthDay(0, 1, 4, 2008));
// outputs Mon May 26 00:00:00 GMT+0100 2008
trace("Thanksgiving Day = " + nthDay(4, 4, 10, 2008));
// outputs Thu Nov 27 00:00:00 GMT+0000 2008
The function can also be combined with existing date objects, e.g.
today = new Date();
trace("Last Saturday in this month = " + nthDay(0, 6, today.getMonth(), today.getFullYear()));
// outputs Sat Jul 26 00:00:00 GMT+0100 2008
trace("Second occurrence of this weekday in two months time = " + nthDay(2, today.getDay(), today.getMonth() + 2, today.getFullYear()));
// outputs Wed Sep 10 00:00:00 GMT+0100 2008
trace("Last but one Thursday in this month = " + nthDay(-1, 4, today.getMonth(), today.getFullYear()));
// outputs Thu Jul 24 00:00:00 GMT+0100 2008
The function will also throw up an error message if the nth day doesn’t exist within that month, e.g.
trace("Fifth Saturday in this month = " + nthDay(5, 6, today.getMonth(), today.getFullYear()));
// outputs **ERROR ** nthDay (5) Out of range
Optional Code:
It’s also possible to use optional code to allow for the use of friendlier arguments. Simply add the following code before the function to give you an idea of how it would work:
// Optional code to allow for the friendlier input of arguments
var first = 1, second = 2, third = 3, fourth = 4, fifth = 5, last = -1;
var firstlast = -1, secondlast = -2, thirdlast = -3, fourthlast = -4, fifthlast = -5; penultimate = -1, antepenultimate = -2, preantepenultimate = -3;
var sun = 0, mon = 1, tue = 2, wed = 3, thu = 4, fri = 5, sat = 6;
var jan = 0, feb = 1, mar = 2, apr = 3, may = 4, jun = 5, jul = 6, aug = 7, sep = 8, oct = 9, nov = 10, dec = 11;
// End of optional code
The optional code allows for the use of friendlier arguments, e.g.
[LIST]
[]The nth arguments (1, 2, 3, 4, 5 and 0) can be substituted with first, second, third, fourth, fifth, and last.
[]Additional nth arguments (-1, -2, -3, -4, and -5) can be substituted with firstlast, secondlast, thirdlast, fourthlast, fifthlast, or by the technical terms penultimate, antepenultimate, and preantepenultimate.
[]The weekday argument can be susbstituted with sun, mon, tue, etc.
[]The month argument can be substituted with jan, feb, mar, etc.
[/LIST]
trace("Memorial Day = " + nthDay(last, mon, may, 2008));
// outputs Mon May 26 00:00:00 GMT+0100 2008
trace("The third from last Tuesday in May was " + nthDay(preantepenultimate, tue, may, today.getFullYear()));
// outputs Tue May 6 00:00:00 GMT+0100 2008
The [COLOR=“red”]nthDate[/COLOR] date object that is returned can be manipulated just the same as any other date object in Actionscript, for example to make it more friendly to read, or to enter into a textfield. Hopefully it will be of use to someone.