Source Code for:
"Prototyping an Advanced Calendar Class Using JavaScript," Vol. 9, Issue 12, p. 56

Listing 1.
class DayEvent extends Day {
     String today() {
         return new Date().getDay();
     }
 }
class Meeting extends DayEvent {
     String today() {
         String i = "<FONT SIZE=1>"  +
                        super.today() + "</FONT>"
         return i;
     }
 }

Listing 2: Open a window and spawn a thread to poll for events
//
// This is the Day Object
//
// open window for viewing meetings
//
this.CalendarChild.cwindow = open(
    "jvcal3.htm",
    "VIEWMEETINGS",
    "toolbar=0,location=0,directories=0, "+
    "status=0,menubar=0,scrollbars=0, " +
    "resizable=0,width=600,height=300"
);

// the Day.render_subject() method reference is
// stored in the action property, and the method
// parameter stored in the parameter property

this.CalendarChild.actions = this.render_subject;
this.CalendarChild.parameters = "browse";

// check_frame checks that the frame in the
// child window != null, which means that is has
//  loaded
this.CalendarChild.event = this.check_frame;

// Finally, a call to the event handler is
// scheduled in background, to be actioned in one half second

// Note that you cannot pass 'this'
// e.g., this.pollEvent()
// because the string is executed outside the
// context of the current object

this.tid = setTimeout("Day.pollEvent();",500);

Listing 3.
function f_poll_signal()
{
    if ( GetCookie("SIGNAL") == "READY" ) {
        SetCookie("SIGNAL", "NONE");
        // the 'action' method will be invoked
        // when this function returns to the
        // event handler
        return !null
    }
    else {
        return null;
    }
}

Listing 4: Polling events in background and implementing the ‘on Event then Action’ rule.
// Day.pollEvent()
function pollEvent()
{
    // wait until frame loaded
    clearTimeout( this.tid );

    if ( this.CalendarChild.event() == null ) {
        this.tid = setTimeout(
                          "Day.pollEvent()", 500
                          );
    }
    else {
        this.CalendarChild.action(
                    this.CalendarChild.parameters
                     );
    }
}

Listing 5: Generating the mail header.
var pstr=document.MEETING.PARTICIPANTS.value;
var y= pstr.length - 1;

var startpos=0;
var outstr="";
var z;

while (startpos <= y) {
    z=pstr.indexOf("\r",startpos)
    if ( z != -1 )
    {
        outstr+= pstr.substring(startpos, z) + ','
        startpos = z+2;
    }
    else {
        outstr+= pstr.substring(startpos,y-2)
        break;
    }
}
// set the Adressee and Subject fields
with ( document.MEETING ) {
    var mx = document.MEETING.MONTH.selectedIndex
    var yx = document.MEETING.YEAR.selectedIndex
    document.links[0].href=
         'mailto:'  +
        outstr.substring(0,outstr.length-1) +
         '?subject='+ SUBJECT.value+', ' +
        DAY.value + ' '  +
        MONTH[ mx ].text + ' '   +
        YEAR[ yx ].value + ' '     +
        TIME_HRS.value + ':'     +
        TIME_MINS.value + ', '  +
        VENUE.value
}