|
|
From the Web:
Dave Eisenberg's Calendar
Dave Eisenberg's calendar (http://www.best.com/~nessus/js-today.html)
is a good example of the use of expressions and variables, as
well as functions and objects. The program generates a dynamic
Web page that includes a greeting suited to the time of day (such
as "Good Evening!"), the time of day, and the current
month's calendar with the current date highlighted.
In addition, the page includes an image suited to the current
time of day.
In doing this, Eisenberg makes use of several techniques that
we haven't seen yet. His script uses the Date
object, as well as several new methods including Math.floor()
from the Math object and
others from the Date object.
The source code for the page is in Listing W1.1.
Listing W1.1. Dave Eisenberg's calendar.
<HTML>
<HEAD>
<TITLE>Greetings from Dave Eisenberg</TITLE>
</HEAD>
<BODY>
<SCRIPT LANGUAGE="JavaScript">
<!-- to hide script contents from old browsers
function greeting()
{
var today = new Date();
var hrs = today.getHours();
document.writeln("<CENTER>");
if ((hrs >=6) && (hrs <=18))
{
document.writeln("<IMG
SRC=\"daypix/day");
document.write(Math.floor(hrs
/ 10));
document.write(Math.floor(hrs
% 10));
document.write("00.gif\">");
}
else
document.write("<IMG
SRC=\"daypix/night1.gif\">");
document.writeln("<BR>");
document.write("<H1>Good ");
if (hrs < 6)
document.write("(Early)
Morning");
else if (hrs < 12)
document.write("Morning");
else if (hrs <= 18)
document.write("Afternoon");
else
document.write("Evening");
document.writeln("!</H1>");
document.write("You entered this page at
");
dayStr = today.toLocaleString();
i = dayStr.indexOf(' ');
n = dayStr.length;
document.write(dayStr.substring(i+1, n));
document.writeln("</CENTER>");
}
function montharr(m0, m1, m2, m3, m4, m5, m6, m7, m8, m9, m10,
m11)
{
this[0] = m0;
this[1] = m1;
this[2] = m2;
this[3] = m3;
this[4] = m4;
this[5] = m5;
this[6] = m6;
this[7] = m7;
this[8] = m8;
this[9] = m9;
this[10] = m10;
this[11] = m11;
}
function calendar()
{
var monthNames = "JanFebMarAprMayJunJulAugSepOctNovDec";
var today = new Date();
var thisDay;
var monthDays = new montharr(31, 28, 31, 30,
31, 30, 31, 31, 30,
31, 30, 31);
year = today.getYear() + 1900;
thisDay = today.getDate();
// do the classic leap year calculation
if (((year % 4 == 0) && (year % 100
!= 0)) || (year % 400 == 0))
monthDays[1] = 29;
// figure out how many days this month will
have...
nDays = monthDays[today.getMonth()];
// and go back to the first day of the month...
firstDay = today;
firstDay.setDate(1);
// and figure out which day of the week it hits...
startDay = firstDay.getDay();
document.writeln("<CENTER>");
document.write("<TABLE BORDER>");
document.write("<TR><TH COLSPAN=7>");
document.write(monthNames.substring(today.getMonth()
* 3,
(today.getMonth() + 1) * 3));
document.write(". ");
document.write(year);
document.write("<TR><TH>Sun<TH>Mon<TH>Tue<TH>Wed<TH>Thu<TH>Fri<TH>Sat");
// now write the blanks at the beginning of
the calendar
document.write("<TR>");
column = 0;
for (i=0; i<startDay; i++)
{
document.write("<TD>");
column++;
}
for (i=1; i<=nDays; i++)
{
document.write("<TD>");
if (i == thisDay)
document.write("<FONT
COLOR=\"#FF0000\">")
document.write(i);
if (i == thisDay)
document.write("</FONT>")
column++;
if (column == 7)
{
document.write("<TR>");
// start a new row
column =
0;
}
}
document.write("</TABLE>");
document.writeln("</CENTER>");
}
document.write(greeting());
document.write("<HR>");
document.write(calendar());
document.write("<HR>");
document.write("<A HREF=\"http://www.best.com/~nessus\">");
document.write("Back to Dave Eisenberg's resume<\A>");
<!-- end hiding contents from old browsers -->
</SCRIPT>
</BODY>
</HTML>
The code produces results like those in Figures W1.1 and W1.2.
Figure W1.1 : During the daytime, the user gets one of several images depicting the time of day.
Figure W1.2 :Using the Date object, the program builds a calendar for the current month.
|
The first thing you notice about this script is that it is not placed inside the header of the HTML file. The author does this because there is no chance of events triggering calls to functions which have not yet been defined.
|
In addition, all HTML code is dynamically generated by the script.
The calendar program uses three functions. The calls are made
in sequence by the main body of the script:
document.write(greeting());
document.write("<HR>");
document.write(calendar());
document.write("<HR>");
document.write("<A HREF=\"http://www.best.com/~nessus\">");
document.write("Back to Dave Eisenberg's resume<\A>");
At the top of the script, two global declarations (today
and hrs) occur. The command
var today = new Date(); creates
an instance of the system's Date
object in much the same way you could create an instance of any
object you defined yourself.
The Date object enables programmers
to create an object that contains information about a particular
date and provides a set of methods to work with that information.
In order to create an instance of the Date
object, you use the form: variable =
new Date(parameters) where the parameters can be any
of the following:
- Empty to create today's date and the current time
- A string of the form "Month
day, year hours:minutes:seconds" (for example
"May 11, 1979 8:00:00")
- Integer values for the current year, month, and day as in
Date(79,5,11)
- Integer values for the current year, month, day, and time
as in Date(79,5,11,8,0,0)
Note |
In JavaScript, it is not possible to create dates before 1 January 1970. The date 1 January 1970 at 00:00:00 is known as the epoch.
|
The Date object provides
the methods outlined in Table W1.1.
Table W1.1. Methods of the Date
object.
Name | Description
|
getDate
| Returns the day of the month as an integer from 1 to 31
|
getDay
| Returns the day of the week as an integer where zero is Sunday and one is Monday
|
getHours
| Returns the hour as an integer between 0 and 23
|
getMinutes
| Returns the minutes as an integer from 0 to 59
|
getMonth
| Returns the month as an integer from 0 to 11 where zero is January and 11 is December
|
getSeconds
| Returns the seconds as an integer between 0 and 59
|
getTime
| Returns the number of milliseconds since 1 January 1970 at 00:00:00
|
getTimezoneOffset
| Returns the difference between the local time and Greenwich Mean Time in minutes
|
getYear
| Returns the year as a two-digit integer |
parse |
Returns the number of milliseconds since 1 January 1970 at 00:00:00 for the date string passed to it
|
setDate
| Sets the day of the month based on an integer argument from 1 to 31
|
setHours
| Sets the hour based on an argument from 0 to 23
|
setMinutes
| Sets the minutes based on an argument from 0 to 59
|
setMonth
| Sets the month based on an argument from 0 to 11
|
setSeconds
| Sets the seconds based on an argument between 0 and 59
|
setTime
| Sets the time based on an argument representing the number of milliseconds since 1 January 1970 at 00:00:00
|
setYear
| Sets the year based on a four-digit integer greater than 1900
|
toString
| Returns the current date as a string |
toGMTString
| Returns the current date and time using the Internet GMT conventions (i.e. in the form "Mon, 18 Dec 1995 17:28:35 GMT")
|
toLocaleString
| Returns the date as a string in the form "MM/DD/YY HH:MM:SS"
|
UTC |
Takes a comma delimited date and returns the number of milliseconds since 1 January 1970 at 00:00:00 GMT time
|
Based on this information, the variable declaration var
hrs = today=getHours() will contain the current hour
when the user loads the page.
The first function the script calls is greeting(),
which displays the appropriate image and welcome message along
with the current time:
function greeting()
{
var today = new Date();
var hrs = today.getHours();
document.writeln("<CENTER>");
if ((hrs >=6) && (hrs <=18))
{
document.writeln("<IMG
SRC=\"daypix/day");
document.write(Math.floor(hrs
/ 10));
document.write(Math.floor(hrs
% 10));
document.write("00.gif\">");
}
else
document.write("<IMG
SRC=\"daypix/night1.gif\">");
document.writeln("<BR>");
document.write("<H1>Good ");
if (hrs < 6)
document.write("(Early)
Morning");
else if (hrs < 12)
document.write("Morning");
else if (hrs <= 18)
document.write("Afternoon");
else
document.write("Evening");
document.writeln("!</H1>");
document.write("You entered this page at
");
dayStr = today.toLocaleString();
i = dayStr.indexOf(' ');
n = dayStr.length;
document.write(dayStr.substring(i+1, n));
document.writeln("</CENTER>");
}
The function determines that it is daytime if hrs
is between 6 and 18
and then builds an image tag. The filename includes a number built
out of the hrs variable using
Math.floor(). This method
returns the closest integer less than the argument. In that way,
if hrs is 12,
the image's filename would be day1200.gif.
Tip |
Math.ceil() is similar to Math.floor() except it returns the nearest integer greater than the value of the argument.
|
The current time, which is output at the end of the function,
is obtained from the string returned by the Date.toLocaleString()
method. This string contains the date and time separated by a
single space. The function uses the indexOf()
method of the string object
to locate the index of the space in the string. The length
property of the string object
is used to determine the index of the last character in the string.
The substring() method then
returns the portion of the string after the index up to the end
of the string. The string
object, and in particular the substring()
method, are discussed in more detail in later chapters. The string
object is covered in depth in Chapter 10,
"Strings, Math, and the History List."
The next function to be called is the calendar()
function, which does the more complex job of building the calendar.
The calendar is designed using HTML tables, which are discussed
further in Chapter 7, "Loops."
function calendar()
{
var monthNames = "JanFebMarAprMayJunJulAugSepOctNovDec";
var today = new Date();
var thisDay;
var monthDays = new montharr(31, 28, 31, 30,
31, 30, 31, 31, 30,
31, 30, 31);
year = today.getYear() + 1900;
thisDay = today.getDate();
// do the classic leap year calculation
if (((year % 4 == 0) && (year % 100
!= 0)) || (year % 400 == 0))
monthDays[1] = 29;
// figure out how many days this month will
have...
nDays = monthDays[today.getMonth()];
// and go back to the first day of the month...
firstDay = today;
firstDay.setDate(1);
// and figure out which day of the week it hits...
startDay = firstDay.getDay();
document.writeln("<CENTER>");
document.write("<TABLE BORDER>");
document.write("<TR><TH COLSPAN=7>");
document.write(monthNames.substring(today.getMonth()
* 3,
(today.getMonth() + 1) * 3));
document.write(". ");
document.write(year);
document.write("<TR><TH>Sun<TH>Mon<TH>Tue<TH>Wed<TH>Thu<TH>Fri<TH>Sat");
// now write the blanks at the beginning of
the calendar
document.write("<TR>");
column = 0;
for (i=0; i<startDay; i++)
{
document.write("<TD>");
column++;
}
for (i=1; i<=nDays; i++)
{
document.write("<TD>");
if (i == thisDay)
document.write("<FONT
COLOR=\"#FF0000\">")
document.write(i);
if (i == thisDay)
document.write("</FONT>")
column++;
if (column == 7)
{
document.write("<TR>");
// start a new row
column =
0;
}
}
document.write("</TABLE>");
document.writeln("</CENTER>");
}
The function starts by defining variables that will be used later
in the function, as well as defining an instance of the Date
object called today and an
instance of the montharr
object (defined by the montharr()
function), which contains 12 properties with the number of days
in each month of the year.
The first step is to determine whether it is a leap year so that
the value of monthDays[1]
(for February) can be adjusted. This is done by using today.getYear()
to get the current year and then using the following if
statement to check whether the year is a leap year:
if (((year % 4 == 0) && (year
% 100 != 0)) || (year % 400 == 0))
monthDays[1] = 29;
Next, the variable nDays
is assigned the number of days in the current month. The index
used in monthDays is the
value returned by today.getMonth()
because it returns an integer that corresponds to the indexes
of the monthDays object.
A copy of today, called firstDay,
is created, and the date is set to the first of the month using
firstDay.setDate(1), in order
to figure out the day of the week using startDay
= firstDay.getDay(). You could have used today.setDate(1)
and today.getDay(), but that
would have made the script harder to read and understand.
The function then outputs the opening tags of the table and writes
out the current month by using the substring()
method on the variable monthNames.
This is followed by writing the number of blank calendar spaces
needed in the first row, using a for
loop, which is covered in Chapter 7.
Next, another for loop is
used to write out the dates of the month in sequence. The if
statements with the condition (i== thisDay)
are used to determine whether the text color should be changed
for the current table cell.
The variable column is incremented
throughout both for loops
to keep track of which column of the seven-column table the current
date is written into. If the date has been written into the seventh
column, then the last if
statement in the second loop starts a table row with the TR
tag and resets column to
zero.
Finally, the function writes out all the closing HTML for the
table.
|