|
|
<!-- --------------------------------------------------------------------- // // Copyright 1999 Microsoft Corporation. All Rights Reserved. // // File: calendar.htc // // Description: The calendar behavior provides an easy, declarative way // to add a standard calendar control to web pages and html // based applications. It provides a variety of properties // to customize the look and feel along with a strong set // events and functionality. // // // Changes for SR UI // // 1. Range for bold dates (min,max) // 2. Create an array of bold/valid dates // 3. New style for bold dates and navigation to only bold dates // 4. Selection of only bold dates // 5. Prev/Next month navigation for valid bold months // //-------------------------------------------------------------------- -->
<SCRIPT ID="CalResource" LANGUAGE=JavaScript SRC="calendar.js"></SCRIPT> <SCRIPT LANGUAGE="javascript">
//------------------------------------------------------------------------ // Attach to element events //------------------------------------------------------------------------
element.attachEvent("onselectstart", fnOnSelectStart) element.attachEvent("onclick", fnOnClick) element.attachEvent("onkeydown", fnOnKeyDown) element.attachEvent("onpropertychange", fnOnPropertyChange) element.attachEvent("onreadystatechange", fnOnReadyStateChange)
var Jan_Text = 'January'; var Feb_Text = 'February'; var Mar_Text = 'March'; var Apr_Text = 'April'; var May_Text = 'May'; var Jun_Text = 'June'; var Jul_Text = 'July'; var Aug_Text = 'August'; var Sep_Text = 'September'; var Oct_Text = 'October'; var Nov_Text = 'November'; var Dec_Text = 'December';
var Sun_Text = ' '; var Mon_Text = ' '; var Tue_Text = ' '; var Wed_Text = ' '; var Thu_Text = ' '; var Fri_Text = ' '; var Sat_Text = ' ';
var gaMonthNames = new Array( new Array(Jan_Text, Feb_Text, Mar_Text, Apr_Text, May_Text, Jun_Text, Jul_Text, Aug_Text, Sep_Text, Oct_Text, Nov_Text, Dec_Text), new Array(Jan_Text, Feb_Text, Mar_Text, Apr_Text, May_Text, Jun_Text, Jul_Text, Aug_Text, Sep_Text, Oct_Text, Nov_Text, Dec_Text) );
var gaDayNames = new Array( new Array(Sun_Text, Mon_Text, Tue_Text, Wed_Text, Thu_Text, Fri_Text, Sat_Text), new Array(Sun_Text, Mon_Text, Tue_Text, Wed_Text, Thu_Text, Fri_Text, Sat_Text), new Array(Sun_Text, Mon_Text, Tue_Text, Wed_Text, Thu_Text, Fri_Text, Sat_Text) );
var gaMonthDays = new Array( /* Jan */ 31, /* Feb */ 29, /* Mar */ 31, /* Apr */ 30, /* May */ 31, /* Jun */ 30, /* Jul */ 31, /* Aug */ 31, /* Sep */ 30, /* Oct */ 31, /* Nov */ 30, /* Dec */ 31 )
var StyleInfo = null // Style sheet with rules for this calendar var goStyle = new Object() // A hash of style sheet rules that apply to this calendar var gaDayCell = new Array() // an array of the table cells for days var goDayTitleRow = null // The table row containing days of the week var goYearSelect = null // The year select control var goMonthSelect = null // The month select control var goCurrentDayCell = null // The cell for the currently selected day var giStartDayIndex = 0 // The index in gaDayCell for the first day of the month var gbLoading = true // Flag for if the behavior is loading
var giDay // day of the month (1 to 31) var giMonth // month of the year (1 to 12) var giYear // year (1900 to 2099)
var giMonthLength = 0 // month length (0,1) var giDayLength = 0 // day length (0 to 2) var giFirstDay = 0 // first day of the week (0 to 6) var gsGridCellEffect = 'raised' // Grid cell effect var gsGridLinesColor = 'black' // Grid line color var gbShowDateSelectors = false // Show date selectors (0,1) var gbShowDays = true // Show the days of the week titles (0,1) var gbShowTitle = true // Show the title (0,1) var gbShowHorizontalGrid = true // Show the horizontal grid (0,1) var gbShowVerticalGrid = true // Show the vertical grid (0,1) var gbValueIsNull = false // There is no value selected (0,1) var gbReadOnly = false // The user can not interact with the control
var giMinYear = 1900 // Minimum year (1 is the lowest possible value) var giMaxYear = 2099 // Maximum year
var gaValidDate = new Array() var gbMinDateSet = false var gbMaxDateSet = false var gdMinDate = null var gdMaxDate = null var giValidDateCount = 0 var goButtonLeft = null; var goButtonRight = null; var gbValidDateChanged = false ; var gbDayNameChanged = false ; var gbMonthNameChanged = false ;
// Load the property values defined on the element to replace defaults fnGetPropertyDefaults()
// Create the style sheets needed for the calendar display fnCreateStyleSheets()
// Insert the HTML elements needed for the calendar display fnCreateCalendarHTML()
// Update the title with the month and year fnUpdateTitle()
// Get locale day month names fnSetLocaleDayMonthNames()
// Fill in the days of the week fnUpdateDayTitles()
// Build the month select control fnBuildMonthSelect()
// Build the year select control fnBuildYearSelect()
// Fill in the cells with the days of the month and set style values fnFillInCells()
//------------------------------------------------------------------------ // // Function: fnSetMinDate/fnSetMaxDate // // Synopsis: Sets the min date // // Arguments: Requires a date Value // // Returns: // // Notes: none // //------------------------------------------------------------------------
function fnSetMinDate(sValue) {
var aValue = sValue.split('/')
// ensure valid valuse for month, day, and year aValue[0]++ ; aValue[0]-- ; aValue[1]++ ; aValue[1]-- ; aValue[2]++ ; aValue[2]-- ; if ( isNaN(aValue[0]) || isNaN(aValue[1]) || isNaN(aValue[2]) ) throw 450
gdMinDate = new Object(); gdMinDate.day = aValue[0]; gdMinDate.month = aValue[1]; gdMinDate.year = aValue[2];
gbMinDateSet = true ;
}
function fnSetMaxDate(sValue) {
var aValue = sValue.split('/')
// ensure valid values for month, day, and year aValue[0]++ ; aValue[0]-- ; aValue[1]++ ; aValue[1]-- ; aValue[2]++ ; aValue[2]-- ; if ( isNaN(aValue[0]) || isNaN(aValue[1]) || isNaN(aValue[2]) ) throw 450
gdMaxDate = new Object(); gdMaxDate.day = aValue[0]; gdMaxDate.month = aValue[1]; gdMaxDate.year = aValue[2];
gbMaxDateSet = true ;
}
//------------------------------------------------------------------------ // // Function: fnAddValidDate // // Synopsis: Adds a valid day to the gaValidDay array which is used // to select valid dates // // Arguments: Requires a date Value // // Returns: // // Notes: none // //------------------------------------------------------------------------
function fnAddValidDate(sValue) {
var aValue = sValue.split('/')
// ensure valid values for month, day, and year aValue[0]++ ; aValue[0]-- ; aValue[1]++ ; aValue[1]-- ; aValue[2]++ ; aValue[2]-- ; if ( isNaN(aValue[0]) || isNaN(aValue[1]) || isNaN(aValue[2]) ) throw 450
gaValidDate[giValidDateCount] = new Object(); gaValidDate[giValidDateCount].day = aValue[0]; gaValidDate[giValidDateCount].month = aValue[1]; gaValidDate[giValidDateCount].year = aValue[2];
giValidDateCount++;
gbValidDateChanged = true ;
}
// ********************************************************************** // PROPERTY GET/SET FUNCTIONS // **********************************************************************
//------------------------------------------------------------------------ // // Function: fnGetDay / fnPutDay // // Synopsis: The day property is used to set the day of the month. The // valid range is from 1 to the maximum day of the selected // month & year. If a number is given outside that range, it // is set to the closest valid value. Invalid input will cause // an exception. // // Arguments: The put method requires an integer value for the day // // Returns: The get method will return the selected day of the month // If the valueIsNull property is set, null is returned // // Notes: none // //------------------------------------------------------------------------
function fnGetDay() { return (gbValueIsNull) ? null : giDay }
function fnPutDay(iDay) { if (gbLoading) return // return if the behavior is loading
iDay = parseInt(iDay) if (isNaN(iDay)) throw 450
fnSetDate(iDay, giMonth, giYear) }
//------------------------------------------------------------------------ // // Function: fnGetMonth / fnPutMonth // // Synopsis: The month property is used to set the month of the year. // The valid range is from 1 to 12. If a value is given // outside that range, it is set to the closest valid value. // Invalid input will cause an exception. // // Arguments: The put method requires an integer value for the month // // Returns: The get method will return the selected month value // If the valueIsNull property is set, null is returned // // Notes: Setting the year can cause the selected "day" value to be // reduced to the highest day in the selected month if needed. // //------------------------------------------------------------------------
function fnGetMonth() { return (gbValueIsNull) ? null : giMonth }
function fnPutMonth(iMonth) { if (gbLoading) return // return if the behavior is loading
iMonth = parseInt(iMonth) if (isNaN(iMonth)) throw 450
fnSetDate(giDay, iMonth, giYear) }
//------------------------------------------------------------------------ // // Function: fnGetYear / fnPutYear // // Synopsis: The year property is used to set the current year. // The valid range is from minYear to maxYear. If a value is given // outside that range, it is set to the closest valid value. // Invalid input will cause an exception. // // Arguments: The put method requires an integer value for the year // // Returns: The get method will return the selected year value // If the valueIsNull property is set, null is returned. // // Notes: Setting the year can cause the selected "day" value to be // reduced to the highest day in the selected month if needed. // //------------------------------------------------------------------------
function fnGetYear() { return (gbValueIsNull) ? null : giYear }
function fnPutYear(iYear) { if (gbLoading) return // return if the behavior is loading
iYear = parseInt(iYear) if (isNaN(iYear)) throw 450
fnSetDate(giDay, giMonth, iYear) }
//------------------------------------------------------------------------ // // Function: fnGetMonthLength / fnPutMonthLength // // Synopsis: The monthLength property is used to adjust the length of // the month name used in the title and month selection control. // // Arguments: The put method requires a value of 'short' or 'long' // // Returns: The get method will return a value of 'short' or 'long' // // Notes: none // //------------------------------------------------------------------------
function fnGetMonthLength() { if (giMonthLength == 0) return "short" if (giMonthLength == 1) return "long" }
function fnPutMonthLength(sLength) { if (gbLoading) return // return if the behavior is loading
switch (sLength.toLowerCase()) { case "short" : if (giMonthLength == 0) return giMonthLength = 0 break; case "long" : if (giMonthLength == 1) return giMonthLength = 1 break; default : throw 450 return }
fnUpdateTitle() fnBuildMonthSelect() }
//------------------------------------------------------------------------ // // Function: fnGetDayName / fnPutDayName // // Synopsis: Sets day names according to the locale // // Arguments: number from 0-6 sets Sunday -> Saturday // // Returns: Name of day // // Notes: none // //------------------------------------------------------------------------
function fnGetDayName(num) {
return gaDayNames[0][num];
}
function fnPutDayName(num,str) {
gaDayNames[0][num] = str ; gbDayNameChanged = true ;
}
//------------------------------------------------------------------------ // // Function: fnGetMonthName / fnPutMonthName // // Synopsis: Sets Month names according to the locale // // Arguments: number from 0-11 sets Jan -> Dec // // Returns: Name of Month // // Notes: none // //------------------------------------------------------------------------
function fnGetMonthName(num) {
return gaMonthNames[0][num];
}
function fnPutMonthName(num,str) {
gaMonthNames[0][num] = str ; gbMonthNameChanged = true ;
}
//------------------------------------------------------------------------ // // Function: fnGetDayLength / fnPutDayLength // // Synopsis: The dayLength property is used to adjust the length of // the day names in the calendar grid. // // Arguments: The put method requires a value of 'short', 'medium', // or 'long' // // Returns: The get method will return a value of 'short', 'medium', // or 'long' // // Notes: none // //------------------------------------------------------------------------
function fnGetDayLength() { if (giDayLength == 0) return "short" if (giDayLength == 1) return "medium" if (giDayLength == 2) return "long" }
function fnPutDayLength(sLength) { if (gbLoading) return // return if the behavior is loading
switch (sLength.toLowerCase()) { case "short" : if (giDayLength == 0) return giDayLength = 0 break; case "medium" : if (giDayLength == 1) return giDayLength = 1 break; case "long" : if (giDayLength == 2) return giDayLength = 2 break; default : throw 450 return }
fnUpdateDayTitles()
// Used to force a table resize if needed goStyle['DaySelected'].borderStyle = 'solid' }
//------------------------------------------------------------------------ // // Function: fnGetFirstDay / fnPutFirstDay // // Synopsis: The firstDay property is used to adjust the first day of // the week on the calendar grid. Valid values are 1 to 7 // where 1 is Sunday and 7 is Saturday. Setting to an invalid // value will cause an exception. // // Arguments: The put method requires a value from 1 to 7 // // Returns: The get method will return a value from 1 to 7 // // Notes: none // //------------------------------------------------------------------------
function fnGetFirstDay() { return giFirstDay }
function fnPutFirstDay(iFirstDay) { if (gbLoading) return // return if the behavior is loading if ((iFirstDay < 0) || (iFirstDay > 6)) throw 450 if (giFirstDay == iFirstDay) return giFirstDay = iFirstDay
fnUpdateDayTitles() fnFillInCells() }
//------------------------------------------------------------------------ // // Function: fnGetGridCellEffect / fnPutGridCellEffect // // Synopsis: The gridCellEffect property is used to modify the 3D effect // in the calendar grid (excluding day titles). It can take // values of 'raised', 'flat', or 'sunken'. Other values will // cause an exception. // // Arguments: The put method requires a value of 'raised', 'flat', or // 'sunken'. // // Returns: The get method will return a value of 'raised', 'flat', or // 'sunken'. // // Notes: none // //------------------------------------------------------------------------
function fnGetGridCellEffect() { return gsGridCellEffect }
function fnPutGridCellEffect(sEffect) { if (gbLoading) return // return if the behavior is loading
switch (sEffect.toLowerCase()) { case "raised" : if (gsGridCellEffect == 'raised') return gsGridCellEffect = 'raised' fnUpdateGridColors() break case "flat" : if (gsGridCellEffect == 'flat') return gsGridCellEffect = 'flat' fnUpdateGridColors() break case "sunken" : if (gsGridCellEffect == 'sunken') return gsGridCellEffect = 'sunken' fnUpdateGridColors() break default : throw 450 } }
//------------------------------------------------------------------------ // // Function: fnGetGridLinesColor / fnPutGridLinesColor // // Synopsis: The gridLinesColor property is used to change the color of // the calendar grid when the gridCellEffect property is set // to 'flat'. It can be any valid HTML color value. // // Arguments: The put method requires a HTML color value // // Returns: The get method will return a HTML color value // // Notes: No error checking is performed. Invalid values may result // in unexpected rendering. // //------------------------------------------------------------------------
function fnGetGridLinesColor() { return gsGridLinesColor }
function fnPutGridLinesColor(sGridLinesColor) { if (gbLoading) return // return if the behavior is loading
gsGridLinesColor = sGridLinesColor fnUpdateGridColors() }
//------------------------------------------------------------------------ // // Function: fnGetShowVerticalGrid / fnPutShowVerticalGrid // // Synopsis: The showVerticalGrid property is used to toggle the // visibility of vertical lines in the calendar grid. // // Arguments: The put method requires true or false value for visibility // // Returns: The get method will return a true or false value // // Notes: none // //------------------------------------------------------------------------
function fnGetShowVerticalGrid() { return gbShowVerticalGrid }
function fnPutShowVerticalGrid(bShowVerticalGrid) { if (gbLoading) return // return if the behavior is loading
if ((bShowVerticalGrid) != gbShowVerticalGrid) { gbShowVerticalGrid = (bShowVerticalGrid) ? true : false fnFireOnPropertyChange("propertyName", "showVerticalGrid") fnUpdateGridColors() } }
//------------------------------------------------------------------------ // // Function: fnGetShowHorizontalGrid / fnPutShowHorizontalGrid // // Synopsis: The showHorizontalGrid property is used to toggle the // visibility of horizontal lines in the calendar grid. // // Arguments: The put method requires true or false value for visibility // // Returns: The get method will return a true or false value // // Notes: none // //------------------------------------------------------------------------
function fnGetShowHorizontalGrid() { return gbShowHorizontalGrid }
function fnPutShowHorizontalGrid(bShowHorizontalGrid) { if (gbLoading) return // return if the behavior is loading
if ((bShowHorizontalGrid) != gbShowHorizontalGrid) { gbShowHorizontalGrid = (bShowHorizontalGrid) ? true : false fnFireOnPropertyChange("propertyName", "showHorizontalGrid") fnUpdateGridColors() } }
//------------------------------------------------------------------------ // // Function: fnGetShowDateSelectors / fnPutShowDateSelectors // // Synopsis: The showDateSelectors property toggles the visibility of // the month and year select controls. // // Arguments: The put method requires true or false value for visibility // // Returns: The get method will return a true or false value // // Notes: none // //------------------------------------------------------------------------
function fnGetShowDateSelectors() { return gbShowDateSelectors }
function fnPutShowDateSelectors(bShowDateSelectors) { if (gbLoading) return // return if the behavior is loading
gbShowDateSelectors = (bShowDateSelectors) ? true : false element.children[0].rows[0].cells[1].style.display = (gbShowDateSelectors) ? '' : 'none' element.children[0].rows[0].style.display = (gbShowDateSelectors || gbShowTitle) ? '' : 'none'
}
//------------------------------------------------------------------------ // // Function: fnGetShowDays / fnPutShowDays // // Synopsis: The showDays property toggles the visibility of // the day of the week titles row in the calendar grid. // // Arguments: The put method requires true or false value for visibility // // Returns: The get method will return a true or false value // // Notes: none // //------------------------------------------------------------------------
function fnGetShowDays() { return gbShowDays }
function fnPutShowDays(bShowDays) { if (gbLoading) return // return if the behavior is loading
gbShowDays = (bShowDays) ? true : false goDayTitleRow.style.display = (gbShowDays) ? '' : 'none' }
//------------------------------------------------------------------------ // // Function: fnGetShowTitle / fnPutShowTitle // // Synopsis: the showTitle property toggles the visibility of the month // and year title at the top of the calendar. // // Arguments: The put method requires true or false value for visibility // // Returns: The get method will return a true or false value // // Notes: none // //------------------------------------------------------------------------
function fnGetShowTitle() { return gbShowTitle }
function fnPutShowTitle(bShowTitle) { if (gbLoading) return // return if the behavior is loading
gbShowTitle = (bShowTitle) ? true : false element.children[0].rows[0].style.display = (gbShowDateSelectors || gbShowTitle) ? '' : 'none' fnUpdateTitle() }
//------------------------------------------------------------------------ // // Function: fnGetValue / fnPutValue // // Synopsis: The value property returns the day, month, and year in the // format: {day}/{month}/{year} // example: 25/02/1998 // An invalid value will cause an exception. // // Arguments: The put method requires a string in the format described // above // // Returns: The get method will return the current date value // // Notes: The day and month are returned in the two digit format. // The year is returned in a four digit format. // //------------------------------------------------------------------------
function fnGetValue() { var sValue
if (gbValueIsNull) return null sValue = ((giDay < 10) ? '0' + giDay : giDay) + '/' + ((giMonth < 10) ? '0' + giMonth : giMonth) + '/' if (giYear < 10) return sValue + '000' + giYear if (giYear < 100) return sValue + '00' + giYear if (giYear < 1000) return sValue + '0' + giYear return sValue + giYear }
function fnPutValue(sValue) { if (gbLoading) return // return if the behavior is loading
var aValue = sValue.split('/')
// ensure valid values for month, day, and year aValue[0]++ ; aValue[0]-- ; aValue[1]++ ; aValue[1]-- ; aValue[2]++ ; aValue[2]-- ; if ( isNaN(aValue[0]) || isNaN(aValue[1]) || isNaN(aValue[2]) ) throw 450
fnSetDate(aValue[0], aValue[1], aValue[2]) }
//------------------------------------------------------------------------ // // Function: fnGetValueIsNull / fnPutValueIsNull // // Synopsis: The valueIsNull property set the calendar so that no day // is selected. Changing any date property, setting one of // the date select controls, or clicking on a day will result // in the valueIsNull property getting set to false. // // Arguments: The put method requires a string in the format described // above // // Returns: The get method will return the current date value // // Notes: The day and month are returned in the two digit format. // The year is returned in a four digit format. // //------------------------------------------------------------------------
function fnGetValueIsNull() { return gbValueIsNull }
function fnPutValueIsNull(bValueIsNull) { if (gbLoading) return // return if the behavior is loading
if ((bValueIsNull) != gbValueIsNull) { gbValueIsNull = (bValueIsNull) ? true : false fnFireOnPropertyChange("propertyName", "readOnly") }
goCurrentDayCell.className = (bValueIsNull) ? 'Day_' + uniqueID : 'DaySelected_' + uniqueID }
//------------------------------------------------------------------------ // // Function: fnGetReadOnly / fnPutReadOnly // // Synopsis: The readOnly property can be set to true or false to // disable user date selection by clicking on days or through // the select controls // // Arguments: The put method requires a true/false value // // Returns: The get method will return true or false // // Notes: none // //------------------------------------------------------------------------
function fnGetReadOnly() { return (gbReadOnly) ? true : false }
function fnPutReadOnly(bReadOnly) { if (gbLoading) return // return if the behavior is loading
if ((bReadOnly) != gbReadOnly) { gbReadOnly = (bReadOnly) ? true : false fnFireOnPropertyChange("propertyName", "readOnly") }
element.children[0].rows[0].cells[1].children[0].children[0].disabled = gbReadOnly element.children[0].rows[0].cells[1].children[0].children[1].disabled = gbReadOnly }
// ********************************************************************** // CALENDAR INITIALIZATION FUNCTIONS // **********************************************************************
//------------------------------------------------------------------------ // // Function: fnCreateCalendarHTML // // Synopsis: This function adds the HTML code to the main document that // is required to display the calendar. It contains nested // tables and all style information is inherited from the // style sheet properties. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnCreateCalendarHTML() { var row, cell
// // Only calendar days direction fixed as LTR as Arabic/Hebrew will have days in same order //
element.innerHTML = '<table border=0 width=100% border=0 cellspacing=0 cellpadding=0 class=WholeCalendar_' + uniqueID + '> ' + ' <tr bgcolor=\"808080\"> ' + ' <td><button id=mlb style=\"cursor: hand;\" title=\"' + L_PreviousMonth_ToolTip + '\" class=NavButton_' + uniqueID + '><</button></td> ' + ' <td class=Title_' + uniqueID + '></td> ' + ' <td class=DateControls_' + uniqueID + '> ' + ' <nobr> <select></select> ' + ' <select></select> </nobr> </td> ' + ' <td><button id=mrb style=\"cursor: hand;\" title=\"' + L_NextMonth_ToolTip + '\" class=NavButton_' + uniqueID + '>></button></td> ' + ' </tr> ' + ' <tr> <td colspan=5><div tabindex=0> ' + ' <table id=calgrid class=CalTable_' + uniqueID + ' cellspacing=0 border=0> ' + ' <tr><td nowrap class=DayTitle_' + uniqueID + '></td>' + ' <td nowrap class=DayTitle_' + uniqueID + '></td>' + ' <td nowrap class=DayTitle_' + uniqueID + '></td>' + ' <td nowrap class=DayTitle_' + uniqueID + '></td>' + ' <td nowrap class=DayTitle_' + uniqueID + '></td>' + ' <td nowrap class=DayTitle_' + uniqueID + '></td>' + ' <td nowrap class=DayTitle_' + uniqueID + '></td></tr>' + ' <tr><td></td><td></td><td></td><td></td><td></td><td></td><td></td></tr>' + ' <tr><td></td><td></td><td></td><td></td><td></td><td></td><td></td></tr>' + ' <tr><td></td><td></td><td></td><td></td><td></td><td></td><td></td></tr>' + ' <tr><td></td><td></td><td></td><td></td><td></td><td></td><td></td></tr>' + ' <tr><td></td><td></td><td></td><td></td><td></td><td></td><td></td></tr>' + ' <tr><td></td><td></td><td></td><td></td><td></td><td></td><td></td></tr>' + ' </table> ' + ' </div></tr> ' + '</table> ';
goDayTitleRow = element.children[0].rows[1].cells[0].children[0].children[0].rows[0] goMonthSelect = element.children[0].rows[0].cells[2].children[0].children[0] goYearSelect = element.children[0].rows[0].cells[2].children[0].children[1] goButtonLeft = element.children[0].rows[0].cells[0].children[0] goButtonRight = element.children[0].rows[0].cells[3].children[0]
goButtonLeft.attachEvent("onclick", fnButtonLeftClick) goButtonRight.attachEvent("onclick", fnButtonRightClick)
for (row=1; row < 7; row++) for (cell=0; cell < 7; cell++) gaDayCell[((row-1)*7) + cell] = element.children[0].rows[1].cells[0].children[0].children[0].rows[row].cells[cell]
}
//------------------------------------------------------------------------ // // Function: fnCreateStyleSheets // // Synopsis: The calendar uses a style sheet to control the rendering // of the different calendar elements. This function creates // the style sheet in the main document using a unique name. // // Arguments: none // // Returns: // // Notes: // //------------------------------------------------------------------------
function fnCreateStyleSheets() { var StyleInfo
if (! element.document.body.BehaviorStyleSheet) { element.document.body.BehaviorStyleSheet = element.document.createStyleSheet() } StyleInfo = element.document.body.BehaviorStyleSheet
StyleInfo.addRule( '.WholeCalendar_' + uniqueID, 'background-color : white ;'+ 'border : 1px solid black ;'+ 'cursor : default ;'+ 'width : 100% ;'+ 'height : 100% ;' ) goStyle['WholeCalendar'] = StyleInfo.rules[StyleInfo.rules.length - 1].style
StyleInfo.addRule( '.Title_' + uniqueID, 'color : white ;'+ // cal--title-color 'font-family : Arial ;'+ // cal--title-font-family 'font-size : 10pt ;'+ // cal--title-font-size 'font-weight : bold ;'+ // cal--title-font-weight 'text-align : center ;'+ // cal--title-text-align 'height : 1 ;'+ 'width : 100% ;' ) goStyle['Title'] = StyleInfo.rules[StyleInfo.rules.length - 1].style
fnLoadCSSDefault('cal--title-background-color', 'calTitleBackgroundColor', goStyle['Title'], 'backgroundColor') fnLoadCSSDefault('cal--title-color', 'calTitleColor', goStyle['Title'], 'color') fnLoadCSSDefault('cal--title-font-family', 'calTitleFontFamily', goStyle['Title'], 'fontFamily') fnLoadCSSDefault('cal--title-font-size', 'calTitleFontSize', goStyle['Title'], 'fontSize') fnLoadCSSDefault('cal--title-font-weight', 'calTitleFontWeight', goStyle['Title'], 'fontWeight') fnLoadCSSDefault('cal--title-text-align', 'calTitleTextAlign', goStyle['Title'], 'textAlign')
StyleInfo.addRule( '.NavButton_' + uniqueID, 'color : white ;'+ // cal--navButton-color 'font-family : Arial ;'+ // cal--navButton-font-family 'font-size : 10pt ;'+ // cal--navButton-font-size 'font-weight : bold ;'+ // cal--navButton-font-weight 'text-align : center ;'+ // cal--navButton-text-align 'padding : 2px ;' // cal--navButton-padding ) goStyle['NavButton'] = StyleInfo.rules[StyleInfo.rules.length - 1].style
fnLoadCSSDefault('cal--navButton-background-color', 'calNavButtonBackgroundColor', goStyle['NavButton'], 'backgroundColor') fnLoadCSSDefault('cal--navButton-color', 'calNavButtonColor', goStyle['NavButton'], 'color') fnLoadCSSDefault('cal--navButton-font-family', 'calNavButtonFontFamily', goStyle['NavButton'], 'fontFamily') fnLoadCSSDefault('cal--navButton-font-size', 'calNavButtonFontSize', goStyle['NavButton'], 'fontSize') fnLoadCSSDefault('cal--navButton-font-weight', 'calNavButtonFontWeight', goStyle['NavButton'], 'fontWeight') fnLoadCSSDefault('cal--navButton-text-align', 'calNavButtonTextAlign', goStyle['NavButton'], 'textAlign') fnLoadCSSDefault('cal--navButton-padding', 'calNavButtonPadding', goStyle['NavButton'], 'padding')
StyleInfo.addRule( '.DateControls_' + uniqueID, 'text-align : right ;' ) goStyle['DateControls'] = StyleInfo.rules[StyleInfo.rules.length - 1].style
StyleInfo.addRule( '.CalTable_' + uniqueID, 'border : 0 solid black ;'+ 'width : 100% ;'+ 'height : 100% ;' ) goStyle['CalTable'] = StyleInfo.rules[StyleInfo.rules.length - 1].style
StyleInfo.addRule( '.DayTitle_' + uniqueID, 'background-color : lightgrey ;'+ // dayTitle-background-color 'color : black ;'+ // dayTitle-color 'font-family : Arial ;'+ // dayTitle-font-family 'font-size : 8pt ;'+ // dayTitle-font-size 'font-weight : bold ;'+ // dayTitle-font-weight 'text-align : center ;'+ // dayTitle-text-align 'border-width : 1px ;'+ 'border-style : solid ;'+ 'border-left-color : white ;'+ 'border-top-color : white ;'+ 'border-right-color : black ;'+ 'border-bottom-color : black ;'+ 'width : 14% ;'+ 'height : 1 ;' ) goStyle['DayTitle'] = StyleInfo.rules[StyleInfo.rules.length - 1].style
fnLoadCSSDefault('cal--dayTitle-background-color', 'calDayTitleBackgroundColor', goStyle['DayTitle'], 'backgroundColor') fnLoadCSSDefault('cal--dayTitle-color', 'calDayTitleColor', goStyle['DayTitle'], 'color') fnLoadCSSDefault('cal--dayTitle-font-family', 'calDayTitleFontFamily', goStyle['DayTitle'], 'fontFamily') fnLoadCSSDefault('cal--dayTitle-font-size', 'calDayTitleFontSize', goStyle['DayTitle'], 'fontSize') fnLoadCSSDefault('cal--dayTitle-font-weight', 'calDayTitleFontWeight', goStyle['DayTitle'], 'fontWeight') fnLoadCSSDefault('cal--dayTitle-text-align', 'calDayTitleTextAlign', goStyle['DayTitle'], 'textAlign')
StyleInfo.addRule( '.OffDay_' + uniqueID, 'background-color : lightgrey ;'+ // cal--offMonth-background-color 'color : #7F7F7F ;'+ // cal--offMonth-color 'font-family : Arial ;'+ // cal--offMonth-font-family 'font-size : 8pt ;'+ // cal--offMonth-font-size 'font-weight : normal ;'+ // cal--offMonth-font-weight 'text-align : right ;'+ // cal--offMonth-text-align 'vertical-align : text-top ;'+ // cal--offMonth-vertical-align 'border-width : 1px ;'+ 'border-style : solid ;'+ 'border-left-color : white ;'+ 'border-top-color : white ;'+ 'border-right-color : black ;'+ 'border-bottom-color : black ;'+ 'width : 14% ;'+ 'cursor : default ;' ) goStyle['OffDay'] = StyleInfo.rules[StyleInfo.rules.length - 1].style
fnLoadCSSDefault('cal--offMonth-background-color', 'calOffMonthBackgroundColor', goStyle['OffDay'], 'backgroundColor') fnLoadCSSDefault('cal--offMonth-color', 'calOffMonthColor', goStyle['OffDay'], 'color') fnLoadCSSDefault('cal--offMonth-font-family', 'calOffMonthFontFamily', goStyle['OffDay'], 'fontFamily') fnLoadCSSDefault('cal--offMonth-font-size', 'calOffMonthFontSize', goStyle['OffDay'], 'fontSize') fnLoadCSSDefault('cal--offMonth-font-weight', 'calOffMonthFontWeight', goStyle['OffDay'], 'fontWeight') fnLoadCSSDefault('cal--offMonth-text-align', 'calOffMonthTextAlign', goStyle['OffDay'], 'textAlign') fnLoadCSSDefault('cal--offMonth-vertical-align', 'calOffMonthVerticalAlign', goStyle['OffDay'], 'verticalAlign')
StyleInfo.addRule( '.Day_' + uniqueID, 'background-color : lightgrey ;'+ // cal--currentMonth-background-color 'color : #00009F ;'+ // cal--currentMonth-color 'font-family : Arial ;'+ // cal--currentMonth-font-family 'font-size : 8pt ;'+ // cal--currentMonth-font-size 'font-weight : normal ;'+ // cal--currentMonth-font-weight 'text-align : right ;'+ // cal--currentMonth-text-align 'vertical-align : text-top ;'+ // cal--currentMonth-vertical-align 'border-width : 1px ;'+ 'border-style : solid ;'+ 'border-left-color : white ;'+ 'border-top-color : white ;'+ 'border-right-color : black ;'+ 'border-bottom-color : black ;'+ 'width : 14% ;'+ 'cursor : default ;' ) goStyle['Day'] = StyleInfo.rules[StyleInfo.rules.length - 1].style
fnLoadCSSDefault('cal--currentMonth-background-color', 'calCurrentMonthBackgroundColor', goStyle['Day'], 'backgroundColor') fnLoadCSSDefault('cal--currentMonth-color', 'calCurrentMonthColor', goStyle['Day'], 'color') fnLoadCSSDefault('cal--currentMonth-font-family', 'calCurrentMonthFontFamily', goStyle['Day'], 'fontFamily') fnLoadCSSDefault('cal--currentMonth-font-size', 'calCurrentMonthFontSize', goStyle['Day'], 'fontSize') fnLoadCSSDefault('cal--currentMonth-font-weight', 'calCurrentMonthFontWeight', goStyle['Day'], 'fontWeight') fnLoadCSSDefault('cal--currentMonth-text-align', 'calCurrentMonthTextAlign', goStyle['Day'], 'textAlign') fnLoadCSSDefault('cal--currentMonth-vertical-align', 'calCurrentMonthVerticalAlign', goStyle['Day'], 'verticalAlign')
StyleInfo.addRule( '.DaySelected_' + uniqueID, 'background-color : #7F7F7F ;'+ // cal--selectedDay-background-color 'color : yellow ;'+ // cal--selectedDay-color 'font-family : Arial ;'+ // cal--selectedDay-font-family 'font-size : 8pt ;'+ // cal--selectedDay-font-size 'font-weight : bold ;'+ // cal--selectedDay-font-weight 'text-align : right ;'+ // cal--selectedMonth-text-align 'vertical-align : text-top ;'+ // cal--selectedMonth-vertical-align 'border-width : 3px ;'+ 'border-style : solid ;'+ 'border-left-color : black ;'+ 'border-top-color : black ;'+ 'border-right-color : #BFBFBF ;'+ 'border-bottom-color : #BFBFBF ;'+ 'width : 14% ;'+ 'cursor : hand ;' ) goStyle['DaySelected'] = StyleInfo.rules[StyleInfo.rules.length - 1].style
fnLoadCSSDefault('cal--selectedDay-background-color', 'calSelectedDayBackgroundColor', goStyle['DaySelected'], 'backgroundColor') fnLoadCSSDefault('cal--selectedDay-color', 'calSelectedDayColor', goStyle['DaySelected'], 'color') fnLoadCSSDefault('cal--selectedDay-font-family', 'calSelectedDayFontFamily', goStyle['DaySelected'], 'fontFamily') fnLoadCSSDefault('cal--selectedDay-font-size', 'calSelectedDayFontSize', goStyle['DaySelected'], 'fontSize') fnLoadCSSDefault('cal--selectedDay-font-weight', 'calSelectedDayFontWeight', goStyle['DaySelected'], 'fontWeight') fnLoadCSSDefault('cal--selectedDay-text-align', 'calSelectedDayTextAlign', goStyle['DaySelected'], 'textAlign') fnLoadCSSDefault('cal--selectedDay-vertical-align', 'calSelectedDayVerticalAlign', goStyle['DaySelected'], 'verticalAlign')
StyleInfo.addRule( '.DayValid_' + uniqueID, 'background-color : lightgrey ;'+ // cal--currentMonth-background-color 'color : yellow ;'+ // cal--currentMonth-color 'font-family : Arial ;'+ // cal--currentMonth-font-family 'font-size : 8pt ;'+ // cal--currentMonth-font-size 'font-weight : bold ;'+ // cal--currentMonth-font-weight 'text-align : right ;'+ // cal--currentMonth-text-align 'vertical-align : text-top ;'+ // cal--currentMonth-vertical-align 'border-width : 1px ;'+ 'border-style : solid ;'+ 'border-left-color : white ;'+ 'border-top-color : white ;'+ 'border-right-color : black ;'+ 'border-bottom-color : black ;'+ 'width : 14% ;'+ 'cursor : hand ;' ) goStyle['DayValid'] = StyleInfo.rules[StyleInfo.rules.length - 1].style
fnLoadCSSDefault('cal--validDay-background-color', 'calvalidDayBackgroundColor', goStyle['DayValid'], 'backgroundColor') fnLoadCSSDefault('cal--validDay-color', 'calvalidDayColor', goStyle['DayValid'], 'color') fnLoadCSSDefault('cal--validDay-font-family', 'calvalidDayFontFamily', goStyle['DayValid'], 'fontFamily') fnLoadCSSDefault('cal--validDay-font-size', 'calvalidDayFontSize', goStyle['DayValid'], 'fontSize') fnLoadCSSDefault('cal--validDay-font-weight', 'calvalidDayFontWeight', goStyle['DayValid'], 'fontWeight') fnLoadCSSDefault('cal--validDay-text-align', 'calvalidDayTextAlign', goStyle['DayValid'], 'textAlign') fnLoadCSSDefault('cal--validDay-vertical-align', 'calvalidDayVerticalAlign', goStyle['DayValid'], 'verticalAlign')
}
//------------------------------------------------------------------------ // // Function: fnLoadCSSDefault // // Synopsis: This helper function checks to see if a CSS property // extension was used to specify a custom style for the // calendar. If so, the style style object. // // Arguments: sCSSProp The CSS property extension used by the // page author // sScriptProp The scriptable property name to add to the // style Name of the style rule // sStyleRuleProp Name of the CSS property on the style rule // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnLoadCSSDefault(sCSSProp, sScriptProp, oStyleRule, sStyleRuleProp) { if (element.currentStyle[sCSSProp]) { oStyleRule[sStyleRuleProp] = element.currentStyle[sCSSProp] } element.style[sScriptProp] = oStyleRule[sStyleRuleProp] }
//------------------------------------------------------------------------ // // Function: fnGetPropertyDefaults // // Synopsis: When the for the properties. // If so, error checking is performed and the state of the // calendar is updated. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnGetPropertyDefaults() { var x var oDate = new Date()
giDay = oDate.getDate() giMonth = oDate.getMonth() + 1 giYear = oDate.getYear()
// The JavaScript Date.getYear function returns a 2 digit date representation // for dates in the 1900's and a 4 digit date for 2000 and beyond. if (giYear < 100) giYear += 1900
// BUGBUG : Need to fill in day/month/year loading and error checking if (element.year) { if (! isNaN(parseInt(element.year))) giYear = parseInt(element.year) if (giYear < giMinYear) giYear = giMinYear if (giYear > giMaxYear) giYear = giMaxYear }
fnCheckLeapYear(giYear)
if (element.month) { if (! isNaN(parseInt(element.month))) giMonth = parseInt(element.month) if (giMonth < 1) giMonth = 1 if (giMonth > 12) giMonth = 12 }
if (element.day) { if (! isNaN(parseInt(element.day))) giDay = parseInt(element.day) if (giDay < 1) giDay = 1 if (giDay > gaMonthDays[giMonth - 1]) giDay = gaMonthDays[giMonth - 1] }
if (element.monthLength) { switch (element.monthLength.toLowerCase()) { case 'short' : giMonthLength = 0 break case 'long' : giMonthLength = 1 break } }
if (element.dayLength) { switch (element.dayLength.toLowerCase()) { case 'short' : giDayLength = 0 break case 'medium' : giDayLength = 1 break case 'long' : giDayLength = 1 break } }
if (element.firstDay) { if ((element.firstDay >= 0) && (element.firstDay <= 6)) giFirstDay = element.firstDay }
if (element.gridCellEffect) { switch (element.gridCellEffect.toLowerCase()) { case 'raised' : giGridCellEffect = 'raised' break case 'flat' : giGridCellEffect = 'flat' break case 'sunken' : giGridCellEffect = 'sunken' break } }
if (element.gridLinesColor) gsGridLinesColor = element.gridLinesColor
if (element.showDateSelectors) gbShowDateSelectors = (element.showDateSelectors) ? true : false
if (element.showDays) gbShowDays = (element.showDays) ? true : false
if (element.showTitle) gbShowTitle = (element.showTitle) ? true : false
if (element.showHorizontalGrid) gbShowHorizontalGrid = (element.showHorizontalGrid) ? true : false
if (element.showVerticalGrid) gbShowVerticalGrid = (element.showVerticalGrid) ? true : false
if (element.valueIsNull) gbValueIsNull = (element.valueIsNull) ? true : false
if (element.name) gsName = element.name
if (element.readOnly) gbReadOnly = (element.readOnly) ? true : false }
// ********************************************************************** // CALENDAR CONTROL FUNCTIONS // **********************************************************************
//------------------------------------------------------------------------ // // Function: fnSetDate // // Synopsis: The fnSetDate function is used internally to set the day, // month, and year values. // // Arguments: iDay The new day // iMonth The new month // iYear The new year // // Returns: none // // Notes: It does some error checking and some minor performance // optimizations if the month & year are not being changed. // //------------------------------------------------------------------------
function fnSetDate(iDay, iMonth, iYear) {
var bValueChange = false var nValidDays = 0 var aValidDate = new Array()
if (gbValueIsNull) { gbValueIsNull = false fnFireOnPropertyChange("propertyName", "valueIsNull") }
// // Update day names if they have changed // if ( gbDayNameChanged ) { gbDayNameChanged = false ; fnUpdateDayTitles(); };
// // Update month names if they have changed // if ( gbMonthNameChanged ) { gbMonthNameChanged = false ; fnUpdateTitle(); };
if (iYear < giMinYear) iYear = giMinYear if (iYear > giMaxYear) iYear = giMaxYear if (giYear != iYear) { fnCheckLeapYear(iYear) }
if (iMonth < 1) iMonth = 1 if (iMonth > 12) iMonth = 12
// // Use current month iMonth // if (iDay < 1) iDay = 1 if (iDay > gaMonthDays[iMonth - 1]) iDay = gaMonthDays[iMonth - 1]
if ((giDay == iDay) && (giMonth == iMonth) && (giYear == iYear)) { if ( gbValidDateChanged ) fnFillInCells(); gbValidDateChanged = false ; return } else bValueChange = true
if (giDay != iDay) { giDay = iDay fnFireOnPropertyChange("propertyName", "day") }
// // Make a list of the valid days in the current month for use in searching // and set the flag that valid days exist in the current month // if ( fnValidDaysExistInCurMonth(iYear,iMonth) ) {
nValidDays = 0 ; for ( i = 0 ; i < giValidDateCount ; i++ ) { if ( gaValidDate[i].year != iYear ) continue ;
if ( gaValidDate[i].month != iMonth ) continue ;
aValidDate[nValidDays] = new Object(); aValidDate[nValidDays].year = gaValidDate[i].year; aValidDate[nValidDays].month = gaValidDate[i].month; aValidDate[nValidDays].day = gaValidDate[i].day;
nValidDays++; }
if ( nValidDays > 0 ) bCheckValid = true ;
}
if ((giYear == iYear) && (giMonth == iMonth)) { if ( fnValidDaysExistInCurDay(giDay,aValidDate,nValidDays)) { goCurrentDayCell.className = 'DayValid_' + uniqueID } else { goCurrentDayCell.className = 'Day_' + uniqueID } goCurrentDayCell = gaDayCell[giStartDayIndex + iDay - 1] goCurrentDayCell.className = 'DaySelected_' + uniqueID
if ( gbValidDateChanged ) fnFillInCells(); } else {
if (giYear != iYear) { giYear = iYear fnFireOnPropertyChange("propertyName", "year") fnUpdateYearSelect() }
if (giMonth != iMonth) { giMonth = iMonth fnFireOnPropertyChange("propertyName", "month") fnUpdateMonthSelect() }
fnFillInCells() }
gbValidDateChanged = false ;
fnUpdateTitle()
if (bValueChange) fnFireOnPropertyChange("propertyName", "value") }
//------------------------------------------------------------------------ // // Function: fnUpdateTitle // // Synopsis: This function updates the title with the currently selected // month and year. The month is displayed in the format // specified by the monthLength option // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnUpdateTitle() { var oTitleCell = element.children[0].rows[0].cells[1] if (gbShowTitle) { // Ignoring giMonthLength -- title is always the string returned from GetDateFormat oTitleCell.innerText = ObjSystemRestore.GetYearMonthStr( giYear, giMonth ); } else oTitleCell.innerText = ' ' }
//------------------------------------------------------------------------ // // Function: fnUpdateDayTitles // // Synopsis: This function updates the titles for the days of the week. // They are displayed in the format specified by the dayLength // option beginning with the day of the week specified by the // firstDay option. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnUpdateDayTitles() { var dayTitleRow = element.children[0].rows[1].cells[0].children[0].children[0].rows[0] var iCell = 0
for (i=giFirstDay ; i < 7 ; i++) { goDayTitleRow.cells[iCell++].innerText = gaDayNames[giDayLength][i] }
for (i=0; i < giFirstDay; i++) { goDayTitleRow.cells[iCell++].innerText = gaDayNames[giDayLength][i] } }
//------------------------------------------------------------------------ // // Function: fnUpdateMonthSelect // // Synopsis: When the month changes, this function is called to select // the correct month in the month select control. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnUpdateMonthSelect() { goMonthSelect.options[ giMonth - 1 ].selected = true }
//------------------------------------------------------------------------ // // Function: fnBuildMonthSelect // // Synopsis: When the calendar is created, this function inserts the // month values into the select control and selects the // current month. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnBuildMonthSelect() { var newMonthSelect
newMonthSelect = element.document.createElement("SELECT") goMonthSelect.parentElement.replaceChild(newMonthSelect, goMonthSelect) goMonthSelect = newMonthSelect
for (i=0 ; i < 12; i++) { e = element.document.createElement("OPTION") e.text = gaMonthNames[giMonthLength][i] goMonthSelect.options.add(e) }
goMonthSelect.options[ giMonth - 1 ].selected = true goMonthSelect.attachEvent("onchange", fnMonthSelectOnChange)
goMonthSelect.style.display = 'none';
}
//------------------------------------------------------------------------ // // Function: fnMonthSelectOnChange // // Synopsis: When the user changes the month using the month select // control, this function handles the onSelectChange event // to update the date. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnMonthSelectOnChange() { iMonth = goMonthSelect.selectedIndex + 1 fnSetDate(giDay, iMonth, giYear) }
//------------------------------------------------------------------------ // // Function: fnButtonLeftClick // // Synopsis: Left click is to decrement month using the ValidDays list // to find the next valid month, if none exists just return // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnButtonLeftClick() {
var bFoundMonth = false ; var bMonthSearch = true ; var oNewDate = new Object(); var iDay = 1 ; var iMonth = giMonth ; var iYear = giYear ;
// // Check if there is a valid date in the next month or months after till MaxDate //
while (bMonthSearch) {
iMonth = iMonth - 1 if ( iMonth == 0 ) { iMonth = 12 ; iYear = iYear - 1 ; };
if ( fnValidDaysExistInCurMonth(iYear,iMonth) ) { bFoundMonth = true ; bMonthSearch = false ; }
oNewDate.day = 1 ; oNewDate.month = iMonth; oNewDate.year = iYear ;
if ( fnCompareDate(oNewDate,gdMinDate) <= 0 ) bMonthSearch = false ;
};
if ( bFoundMonth ) {
// // Select the last valid day in the selected month // nValidDays = 0 ; for ( i = 0 ; i < giValidDateCount ; i++ ) { if ( gaValidDate[i].year != iYear ) continue ;
if ( gaValidDate[i].month != iMonth ) continue ;
if ( gaValidDate[i].day > iDay ) iDay = gaValidDate[i].day ; };
fnSetDate(iDay, iMonth, iYear);
}
}
//------------------------------------------------------------------------ // // Function: fnButtonRightClick // // Synopsis: Right click is to increment month using the ValidDays list // to find the next valid month, if none exists just return // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnButtonRightClick() {
var bFoundMonth = false ; var bMonthSearch = true ; var oNewDate = new Object(); var iDay = 40 ; var iMonth = giMonth ; var iYear = giYear ;
// // Check if there is a valid date in the next month or months after till MaxDate // while (bMonthSearch) {
iMonth = iMonth + 1
if ( iMonth == 13 ) { iMonth = 1 ; iYear = iYear + 1 ; };
if ( fnValidDaysExistInCurMonth(iYear,iMonth) ) { bFoundMonth = true ; bMonthSearch = false ; }
oNewDate.day = 1 ; oNewDate.month = iMonth; oNewDate.year = iYear ;
if ( fnCompareDate(oNewDate,gdMaxDate) >= 0 ) bMonthSearch = false ;
};
if ( bFoundMonth ) {
// // Select the first valid day in the selected month // nValidDays = 0 ; for ( i = 0 ; i < giValidDateCount ; i++ ) { if ( gaValidDate[i].year != iYear ) continue ;
if ( gaValidDate[i].month != iMonth ) continue ;
if ( gaValidDate[i].day < iDay ) iDay = gaValidDate[i].day ; };
fnSetDate(iDay, iMonth, iYear);
}
}
//------------------------------------------------------------------------ // // Function: fnUpdateYearSelect // // Synopsis: When the year changes, this function is called to select // the correct year in the year select control. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnUpdateYearSelect() { goYearSelect.options[ giYear - giMinYear ].selected = true }
//------------------------------------------------------------------------ // // Function: fnBuildYearSelect // // Synopsis: When the calendar is created, this function inserts the // year values into the select control and selects the // current year. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnBuildYearSelect() { var newYearSelect newYearSelect = element.document.createElement("SELECT") goYearSelect.parentElement.replaceChild(newYearSelect, goYearSelect) goYearSelect = newYearSelect
for (i=giMinYear; i <= giMaxYear; i++) { e = element.document.createElement("OPTION") e.text = i goYearSelect.options.add(e) }
goYearSelect.options[ giYear - giMinYear ].selected = true goYearSelect.attachEvent("onchange", fnYearSelectOnChange)
goYearSelect.style.display = 'none'
}
//------------------------------------------------------------------------ // // Function: fnYearSelectOnChange // // Synopsis: When the user changes the year using the year select // control, this function handles the onSelectChange event // to update the date. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnYearSelectOnChange() { iYear = goYearSelect.selectedIndex + giMinYear fnSetDate(giDay, giMonth, iYear) }
//------------------------------------------------------------------------ // // Function: fnCheckLeapYear // // Synopsis: When the year changes, this function must be called to // ensure that February has the correct count for the number // of days. // // Arguments: year // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnCheckLeapYear(iYear) { gaMonthDays[1] = (((!(iYear % 4)) && (iYear % 100) ) || !(iYear % 400)) ? 29 : 28 }
//------------------------------------------------------------------------ // // Function: fnFillInCells // // Synopsis: This method works through the table and sets the day and // style needed. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnFillInCells() { var iDayCell = 0 var iLastMonthIndex, iNextMonthIndex var iLastMonthTotalDays var iStartDay var bCheckValid = false var nValidDays = 0 var aValidDate = new Array()
fnCheckLeapYear(giYear)
iLastMonthDays = gaMonthDays[ ((giMonth - 1 == 0) ? 12 : giMonth - 1) - 1] iNextMonthDays = gaMonthDays[ ((giMonth + 1 == 13) ? 1 : giMonth + 1) - 1]
iLastMonthYear = (giMonth == 1) ? giYear - 1 : giYear iLastMonth = (giMonth == 1) ? 12 : giMonth - 1 iNextMonthYear = (giMonth == 12) ? giYear + 1 : giYear iNextMonth = (giMonth == 12) ? 1 : giMonth + 1
var oDate = new Date(giYear, (giMonth - 1), 1)
iStartDay = oDate.getDay() - giFirstDay if (iStartDay < 1) iStartDay += 7 iStartDay = iLastMonthDays - iStartDay + 1
// // Days before beginning of the month // for (i = iStartDay ; i <= iLastMonthDays ; i++ , iDayCell++) { gaDayCell[iDayCell].innerText = i ;
if (gaDayCell[iDayCell].className != 'OffDay_' + uniqueID) gaDayCell[iDayCell].className = 'OffDay_' + uniqueID
gaDayCell[iDayCell].day = i gaDayCell[iDayCell].month = iLastMonth gaDayCell[iDayCell].year = iLastMonthYear }
giStartDayIndex = iDayCell
// // Make a list of the valid days in the current month for use in searching // and set the flag that valid days exist in the current month // if ( fnValidDaysExistInCurMonth(giYear,giMonth) ) {
nValidDays = 0 ; for ( i = 0 ; i < giValidDateCount ; i++ ) { if ( gaValidDate[i].year != giYear ) continue ;
if ( gaValidDate[i].month != giMonth ) continue ;
aValidDate[nValidDays] = new Object(); aValidDate[nValidDays].year = gaValidDate[i].year; aValidDate[nValidDays].month = gaValidDate[i].month; aValidDate[nValidDays].day = gaValidDate[i].day;
nValidDays++; }
if ( nValidDays > 0 ) bCheckValid = true ;
}
// // Current month days // for (i = 1 ; i <= gaMonthDays[giMonth - 1] ; i++, iDayCell++) { gaDayCell[iDayCell].innerText = i ;
if (giDay == i) { goCurrentDayCell = gaDayCell[iDayCell] gaDayCell[iDayCell].className = 'DaySelected_' + uniqueID gaDayCell[iDayCell].innerHTML = '<DIV TABINDEX=-1>' + i + '</DIV>'; } else if ( fnValidDaysExistInCurDay(i,aValidDate,nValidDays)) { gaDayCell[iDayCell].className = 'DayValid_' + uniqueID gaDayCell[iDayCell].innerHTML = '<DIV TABINDEX=-1>' + i + '</DIV>'; } else { if (gaDayCell[iDayCell].className != 'Day_' + uniqueID) gaDayCell[iDayCell].className = 'Day_' + uniqueID }
gaDayCell[iDayCell].day = i gaDayCell[iDayCell].month = giMonth gaDayCell[iDayCell].year = giYear }
// // Days after end of the month // for (i = 1 ; iDayCell < 42 ; i++, iDayCell++) { gaDayCell[iDayCell].innerText = i
if (gaDayCell[iDayCell].className != 'OffDay_' + uniqueID) gaDayCell[iDayCell].className = 'OffDay_' + uniqueID
gaDayCell[iDayCell].day = i gaDayCell[iDayCell].month = iNextMonth gaDayCell[iDayCell].year = iNextMonthYear }
}
function fnValidDaysExistInCurYear(nCurYear) {
var bExists = false ;
if ( nCurYear < gdMinDate.year ) return false ; if ( nCurYear > gdMaxDate.year ) return false ;
for ( i = 0 ; i < giValidDateCount ; i++ ) { if ( gaValidDate[i].year == nCurYear ) { bExists = true ; break ; } }
return bExists ; }
function fnValidDaysExistInCurMonth(nCurYear,nCurMonth) {
var bExists = false ;
for ( i = 0 ; i < giValidDateCount ; i++ ) { if ( gaValidDate[i].year != nCurYear ) continue ;
if ( gaValidDate[i].month == nCurMonth ) { bExists = true ; break ; } }
return bExists ; }
function fnValidDaysExistInCurDay(nCurDay,aList,nCount) {
var i ; var bExists = false ;
if ( nCount < 1 ) return bExists ;
for ( i = 0 ; i < nCount ; i++ ) { if ( aList[i].day == nCurDay ) { bExists = true ; break ; } }
return bExists ; }
function fnAlertDate(d1) {
alert('Date = ' + d1.year + '-' + d1.month + '-' + d1.day);
}
//------------------------------------------------------------------------ // // Function: fnCompareDate // // Synopsis: Compares two dates // // Arguments: none // // Returns: -1,0,1 // // Notes: none // //------------------------------------------------------------------------ function fnCompareDate(d1,d2) {
// // d1 < d2 then -1 // d1 = d2 then 0 // d1 > d2 then 1 // var a1 = fnConvertDateToNumber(d1); var a2 = fnConvertDateToNumber(d2); if ( a1 < a2 ) return -1 if ( a1 == a2 ) return 0 return 1
}
//------------------------------------------------------------------------ // // Function: fnConvertDateToNumber // // Synopsis: Converts date to number // // Arguments: none // // Returns: number // // Notes: none // //------------------------------------------------------------------------ function fnConvertDateToNumber(d1) { var value = d1.year * 500 + d1.month * 40 + d1.day return (value) ; }
//------------------------------------------------------------------------ // // Function: fnSetLocaleDayMonthNames // // Synopsis: Sets month day names based on locale // // Arguments: none // // Returns: // // Notes: none // //------------------------------------------------------------------------
function fnSetLocaleDayMonthNames() {
// // Start with Sunday Jan 2nd, 2000 for getting day names for the current user locale // and set them in the calendar // var i = 0 ; var nLowResScreenHeight = 540 ;
// // Get day names // if ( screen.height <= nLowResScreenHeight ) { fnPutDayName(0,L_ShortSunday_Text); fnPutDayName(1,L_ShortMonday_Text); fnPutDayName(2,L_ShortTuesday_Text); fnPutDayName(3,L_ShortWednesday_Text); fnPutDayName(4,L_ShortThursday_Text); fnPutDayName(5,L_ShortFriday_Text); fnPutDayName(6,L_ShortSaturday_Text); } else { for ( i = 0 ; i < 7 ; i++ ) { var oStartDate = new Date(2000,0,2+i) var str = ObjSystemRestore.GetLocaleDateFormat(oStartDate.getVarDate(),"ddd"); fnPutDayName(i,str); }; }; // // Start with Sunday Jan 1st, 2000 for getting month names for the current user locale // and set them in the calendar // for ( i = 0 ; i < 12 ; i++ ) { var oStartDate = new Date(2000,i,1) var str = ObjSystemRestore.GetLocaleDateFormat(oStartDate.getVarDate(),"MMMM"); fnPutMonthName(i,str); };
// // Set first day of the week // giFirstDay = ObjSystemRestore.FirstDayOfWeek ;
}
// ********************************************************************** // EVENT HANDLERS // **********************************************************************
//------------------------------------------------------------------------ // // Function: fnOnClick // // Synopsis: When the user clicks on the calendar, change the date if // needed // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnOnClick() { var e = window.event.srcElement
if (e.tagName == "DIV" && e.parentElement.tagName == "TD" ) {
e = e.parentElement ; }
if (e.tagName == "TD") {
if (gbReadOnly || (!e.day)) return // The calendar is read only if ((e.year < giMinYear) || (e.year > giMaxYear)) return // // Do not allow selection of OffDay's // if (e.className == 'OffDay_' + uniqueID) return // // Do not allow selection of Days // if (e.className == 'Day_' + uniqueID) return
// // Set selected date // fnSetDate(e.day, e.month, e.year) } }
//------------------------------------------------------------------------ // // Function: fnOnKeyDown // // Synopsis: Trap key press events for navigation // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnOnKeyDown() {
var e = window.event.srcElement; var ArrowPressed = false; var found = false;
if (window.event.keyCode >= 37 && window.event.keyCode <= 40) { for (row=1; row < 7; row++) { for (cell=0; cell < 7; cell++) { if (gaDayCell[((row-1)*7) + cell].className == "DaySelected_" + uniqueID) { found = true; break; } } if (found == true) break; }
if (found == false) { window.event.returnValue = false; return; }
// navigate up/down/right/left
found = false; while (found == false) { if (window.event.keyCode == 38) row--; if (window.event.keyCode == 37) if (cell==0) // left wrap { row--; cell=6; } else cell--;
if (window.event.keyCode == 40) row++; if (window.event.keyCode == 39) if (cell==6) // right wrap { row++; cell=0; } else cell++;
if (row < 1 || row > 6 || cell < 0 || cell > 6) break;
if (gaDayCell[((row-1)*7) + cell].className == "DayValid_" + uniqueID) found = true; }
if (found == false) { window.event.returnValue = false; return; } e = gaDayCell[(row-1)*7+cell]; ArrowPressed = true; window.event.returnValue = true; }
if (ArrowPressed == true) { if (gbReadOnly || (!e.day)) return // The calendar is read only if ((e.year < giMinYear) || (e.year > giMaxYear)) return // // Do not allow selection of OffDay's // if (e.className == 'OffDay_' + uniqueID) return // // Do not allow selection of Days // if (e.className == 'Day_' + uniqueID) return
// // Set selected date // fnSetDate(e.day, e.month, e.year) e.focus() }
window.event.cancelBubble = true ;
}
//------------------------------------------------------------------------ // // Function: fnOnSelectStart // // Synopsis: This cancels selection when the user clicks and drags the // mouse on the calendar. It can still be selected if the // the SelectStart begins outside this element. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnOnSelectStart() { window.event.returnValue = false window.event.cancelBubble = true }
//------------------------------------------------------------------------ // // Function: fnOnReadyStateChange // // Synopsis: When the behavior is completely loaded, set the global // loading flag to false. // // Arguments: none // // Returns: none // // Notes: To improve load time, we do not want the put methods on // properties to be called. We also need to keep events from // getting fired while the behavior is loading. // //------------------------------------------------------------------------
function fnOnReadyStateChange() { gbLoading = (readyState != "complete") }
//------------------------------------------------------------------------ // // Function: fnOnPropertyChange // // Synopsis: When a property changes on the element, this function will // check it to see if part of the calendar needs to be changed // as a result. // // Arguments: none // // Returns: none // // Notes: This is currently only checking extended style // properties to alter the calendar style sheet rules. // //------------------------------------------------------------------------
function fnOnPropertyChange() { if (window.event.propertyName.substring(0, 5) == 'style') { switch (window.event.propertyName) { case 'style.calTitleBackgroundColor' : goStyle['WholeCalendar'].backgroundColor = style.calTitleBackgroundColor goStyle['Title'].backgroundColor = style.calTitleBackgroundColor break case 'style.calTitleColor' : goStyle['Title'].color = style.calTitleColor break case 'style.calTitleFontFamily' : goStyle['Title'].fontFamily = style.calTitleFontFamily break case 'style.calTitleFontSize' : goStyle['Title'].fontSize = style.calTitleFontSize break case 'style.calTitleFontWeight' : goStyle['Title'].fontWeight = style.calTitleFontWeight break case 'style.calTitleTextAlign' : goStyle['Title'].textAlign = style.calTitleTextAlign break
case 'style.calDayTitleBackgroundColor' : goStyle['DayTitle'].backgroundColor = style.calDayTitleBackgroundColor break case 'style.calDayTitleColor' : goStyle['DayTitle'].color = style.calDayTitleColor break case 'style.calDayTitleFontFamily' : goStyle['DayTitle'].fontFamily = style.calDayTitleFontFamily break case 'style.calDayTitleFontSize' : goStyle['DayTitle'].fontSize = style.calDayTitleFontSize break case 'style.calDayTitleFontWeight' : goStyle['DayTitle'].fontWeight = style.calDayTitleFontWeight break case 'style.calDayTitleTextAlign' : goStyle['DayTitle'].textAlign = style.calDayTitleTextAlign break
case 'style.calOffMonthBackgroundColor' : goStyle['OffDay'].backgroundColor = style.calOffMonthBackgroundColor break case 'style.calOffMonthColor' : goStyle['OffDay'].color = style.calOffMonthColor break case 'style.calOffMonthFontFamily' : goStyle['OffDay'].fontFamily = style.calOffMonthFontFamily break case 'style.calOffMonthFontSize' : goStyle['OffDay'].fontSize = style.calOffMonthFontSize break case 'style.calOffMonthFontWeight' : goStyle['OffDay'].fontWeight = style.calOffMonthFontWeight break case 'style.calOffMonthTextAlign' : goStyle['OffDay'].textAlign = style.calOffMonthTextAlign break case 'style.calOffMonthVerticalAlign' : goStyle['OffDay'].verticalAlign = style.calOffMonthVerticalAlign break
case 'style.calCurrentMonthBackgroundColor' : goStyle['Day'].backgroundColor = style.calCurrentMonthBackgroundColor break case 'style.calCurrentMonthColor' : goStyle['Day'].color = style.calCurrentMonthColor break case 'style.calCurrentMonthFontFamily' : goStyle['Day'].fontFamily = style.calCurrentMonthFontFamily break case 'style.calCurrentMonthFontSize' : goStyle['Day'].fontSize = style.calCurrentMonthFontSize break case 'style.calCurrentMonthFontWeight' : goStyle['Day'].fontWeight = style.calCurrentMonthFontWeight break case 'style.calCurrentMonthTextAlign' : goStyle['Day'].textAlign = style.calCurrentMonthTextAlign break case 'style.calCurrentMonthVerticalAlign' : goStyle['Day'].verticalAlign = style.calCurrentMonthVerticalAlign break
case 'style.calSelectedDayBackgroundColor' : goStyle['DaySelected'].backgroundColor = style.calSelectedDayBackgroundColor break case 'style.calSelectedDayColor' : goStyle['DaySelected'].color = style.calSelectedDayColor break case 'style.calSelectedDayFontFamily' : goStyle['DaySelected'].fontFamily = style.calSelectedDayFontFamily break case 'style.calSelectedDayFontSize' : goStyle['DaySelected'].fontSize = style.calSelectedDayFontSize break case 'style.calSelectedDayFontWeight' : goStyle['DaySelected'].fontWeight = style.calSelectedDayFontWeight break case 'style.calSelectedDayTextAlign' : goStyle['DaySelected'].textAlign = style.calSelectedDayTextAlign break case 'style.calSelectedDayVerticalAlign' : goStyle['DaySelected'].verticalAlign = style.calSelectedDayVerticalAlign break } } }
// ********************************************************************** // HELPER FUNCTIONS // **********************************************************************
//------------------------------------------------------------------------ // // Function: fnFireOnPropertyChange // // Synopsis: // // Arguments: // // Returns: // // Notes: // //------------------------------------------------------------------------
function fnFireOnPropertyChange(name1, value1) { var evObj = createEventObject() evObj.setAttribute(name1, value1) onPropertyChange.fire(evObj) }
//------------------------------------------------------------------------ // // Function: fnUpdateGridColors // // Synopsis: This is a helper function for the calendar grid rendering // properties. It handles setting the style rules to create // the desired effects. // // Arguments: none // // Returns: none // // Notes: none // //------------------------------------------------------------------------
function fnUpdateGridColors() { switch (gsGridCellEffect) { case "raised" : goStyle['OffDay'].borderLeftColor = 'white' goStyle['OffDay'].borderTopColor = 'white' goStyle['OffDay'].borderRightColor = 'black' goStyle['OffDay'].borderBottomColor = 'black'
goStyle['Day'].borderLeftColor = 'white' goStyle['Day'].borderTopColor = 'white' goStyle['Day'].borderRightColor = 'black' goStyle['Day'].borderBottomColor = 'black'
goStyle['DaySelected'].borderLeftColor = 'white' goStyle['DaySelected'].borderTopColor = 'white' goStyle['DaySelected'].borderRightColor = 'black' goStyle['DaySelected'].borderBottomColor = 'black'
break case "flat" : goStyle['OffDay'].borderLeftColor = goStyle['OffDay'].backgroundColor goStyle['OffDay'].borderTopColor = goStyle['OffDay'].backgroundColor goStyle['OffDay'].borderRightColor = (gbShowVerticalGrid) ? gsGridLinesColor : goStyle['Day'].backgroundColor goStyle['OffDay'].borderBottomColor = (gbShowHorizontalGrid) ? gsGridLinesColor : goStyle['Day'].backgroundColor
goStyle['Day'].borderLeftColor = goStyle['Day'].backgroundColor goStyle['Day'].borderTopColor = goStyle['Day'].backgroundColor goStyle['Day'].borderRightColor = (gbShowVerticalGrid) ? gsGridLinesColor : goStyle['Day'].backgroundColor goStyle['Day'].borderBottomColor = (gbShowHorizontalGrid) ? gsGridLinesColor : goStyle['Day'].backgroundColor
goStyle['DaySelected'].borderLeftColor = goStyle['DaySelected'].backgroundColor goStyle['DaySelected'].borderTopColor = goStyle['DaySelected'].backgroundColor goStyle['DaySelected'].borderRightColor = (gbShowVerticalGrid) ? gsGridLinesColor : goStyle['Day'].backgroundColor goStyle['DaySelected'].borderBottomColor = (gbShowHorizontalGrid) ? gsGridLinesColor : goStyle['Day'].backgroundColor
break case "sunken" : goStyle['OffDay'].borderLeftColor = 'black' goStyle['OffDay'].borderTopColor = 'black' goStyle['OffDay'].borderRightColor = 'white' goStyle['OffDay'].borderBottomColor = 'white'
goStyle['Day'].borderLeftColor = 'black' goStyle['Day'].borderTopColor = 'black' goStyle['Day'].borderRightColor = 'white' goStyle['Day'].borderBottomColor = 'white'
goStyle['DaySelected'].borderLeftColor = 'black' goStyle['DaySelected'].borderTopColor = 'black' goStyle['DaySelected'].borderRightColor = 'white' goStyle['DaySelected'].borderBottomColor = 'white'
break default : throw 450 } }
</script>
<public:property put=fnPutDayName get=fnGetDayName name="dayName"> <public:property put=fnPutMonthName get=fnGetMonthName name="monthName"> <public:property put=fnPutDay get=fnGetDay name="day"> <public:property put=fnPutMonth get=fnGetMonth name="month"> <public:property put=fnPutYear get=fnGetYear name="year"> <public:property put=fnPutMonthLength get=fnGetMonthLength name="monthLength"> <public:property put=fnPutDayLength get=fnGetDayLength name="dayLength"> <public:property put=fnPutFirstDay get=fnGetFirstDay name="firstDay"> <public:property put=fnPutGridCellEffect get=fnGetGridCellEffect name="gridCellEffect"> <public:property put=fnPutGridLinesColor get=fnGetGridLinesColor name="gridLinesColor"> <public:property put=fnPutShowDateSelectors get=fnGetShowDateSelectors name="showDateSelectors"> <public:property put=fnPutShowDays get=fnGetShowDays name="showDays"> <public:property put=fnPutShowTitle get=fnGetShowTitle name="showTitle"> <public:property put=fnPutShowVerticalGrid get=fnGetShowVerticalGrid name="showVerticalGrid"> <public:property put=fnPutShowHorizontalGrid get=fnGetShowHorizontalGrid name="showHorizontalGrid"> <public:property put=fnPutValue get=fnGetValue name="value"> <public:property put=fnPutValueIsNull get=fnGetValueIsNull name="valueIsNull"> <public:property put=fnPutReadOnly get=fnGetReadOnly name="readOnly"> <public:property put=fnSetMinDate name="minDate"> <public:property put=fnSetMaxDate name="maxDate"> <public:property put=fnAddValidDate name="addValidDate">
<public:event id="onChange" name="onchange"> <public:event id="onPropertyChange" name="onpropertychange"> <public:event id="onError" name="onerror">
|