/**
 * Initialise the calendar
 */

var MONTH_NAMES = ["January","February","March","April","May","June","July","August","September","October","November","December"];
var calendar_throbber = $('<div style="padding:20px;margin:0 auto;"><img style="float:left" hspace="5" src="/_template/images/throbber.gif">Loading...</div>');
var __isDebug = false;

function __debugLog(){
	if(__isDebug && window.console) console.log(arguments);
}

$(document).ready(function(){
	var calendarelement = ".glow-calendar";
	var calendarnav = ".glow-calendar-nav";
	var calendarbody = ".glow-calendar-body";
	
	// look at each calendar element
	$(calendarelement).each(function(i,cal){
		__debugLog("init calendar");
		
		// get calendar identifier
		var calendarId = $(cal).attr('id');
		
		// get calendar params from url and store in data field 'searchparams'
		var params = glow_getCalendarParams(calendarId);
		__debugLog(params);
		var calendarForm = $("form[name=" + calendarId + "]", cal);
		$(cal).data('searchparams',params);
		$(cal).data('form',calendarForm);
		$(cal).data('id',calendarId);
		
		// configure navigation
		glow_calendarNavInit(cal);
		
		// get search results (body content)
		glow_getCalendarBodyContent(cal,params);
		
		// dump the marker cookie
		//$.cookie("eg_cal" + $(cal).data('id'),null);
	});	
});



/**
 * get the URL params for a calendar
 * @param {Object} calendarId
 */ 
function glow_getCalendarParams(calendarId){
	__debugLog("glow_getCalendarParams");
	var objParams = {};
	objParams.calendarId = calendarId.split("-")[1];
	var p = $.getURLParam(calendarId) ;
	if(p==null) return objParams;
	
	var aParams = unescape(p).split('^');
	for(var i=0;i<aParams.length;i++){
		var param = aParams[i].split("|");
		if(param.length = 2){
			objParams[param[0]] = param[1];
		}
	}
	return objParams;
}

/**
 * serialise a parameter object into something we can send back as a query  
 */
function glow_serialiseParams(objParams) {
	__debugLog("glow_serialiseParams");
	var strParams = "";
	var aParams = [];
	try{
		for(var o in objParams) {
			aParams.push(o + '|' + objParams[o]);			
		}
		strParams = aParams.join("^");
	}catch(e){
		return "";
	}
	return strParams;
}

/**
 * submit a query for this calendar
 * @param {Object} cal
 * @param {Object} params
 */
function glow_sendCalendarQuery(cal, params) {
	__debugLog("glow_sendCalendarQuery");
	var value = glow_serialiseParams(params);
	var calendarForm = $(cal).data('form');
	$("input.submitvalue",calendarForm).val(value);
	$(calendarForm).submit();	
}

/**
 * get body content for a given calendar and inject into 
 * content region
 * @param {Object} cal
 */
function glow_getCalendarBodyContent(cal, myParams){
	__debugLog("glow_getCalendarBodyContent");
	var contentRegion = $(".glow-calendar-body",cal);
	var defaultParams = {
		module		: "calendar",
		contentType : "sessionlist"
	}
	var params = $.extend( defaultParams, 
							myParams );

	$(contentRegion).html(calendar_throbber);

	if(params.event != undefined) params.mode = "event";

	// get the XSL mode
	params.xslmode = $(':input[name=xslmode]', $(cal).data('form')).val();
	
	var mode = "eventlist";
	$.ajax({url:"/index.cfm", type:"GET", data:params, success: function(html){
		__debugLog("glow_getCalendarBodyContent - AJAX SUCCESS");
		// nothing to do
		$(contentRegion).html(html);
		//
		// This replaces the page heading with the heading inside the calendar body.
		//
		// if content-main has an h1 and contentRegion has an h1 then replace
		// the content-main h1 with the text from the first contentRegion h1 and
		// then remove the first h1 from the contentRegion
		var contentMain = $("#content-main");
	 	if ($("h1", contentMain).size()-$("h1", contentRegion).size() >= 1) {
			var myHeading = $("h1:first",contentRegion).text();
			$("h1:first", contentRegion).remove();
			$("h1:first").text(myHeading);    
		}		
		$(".gmt2ampm",contentRegion).each(function(){
			var timetext = $(this).text();
			var aText = timetext.split("-");
			var aTime = aText[1].split(":");
			timetext = aText[0] + " - ";
			if(aTime[0] >= 13){
				timetext = timetext + Number(aTime[0]-12) + ":" + aTime[1] + " pm";
			} else {
				if(aTime[0] == 12){
					timetext = timetext + Number(aTime[0]) + ":" + aTime[1] + " pm";
				} else {
					timetext = timetext + Number(aTime[0]) + ":" + aTime[1] + " am";
				}
			}
			$(this).text(timetext);
		})

  		switch(mode) {
			case "event" :
				break;
			case "eventlist" : 
				initCalendarEventList(cal);
				break;
		}
		
		// redo any styles required
		glow_initStyles();
		// set the calendar marker current month cookie
		// this allows us to return to the correct calendar on
		// refresh
		if( myParams.contentId==undefined ){
			var dNow = new Date()
			var currentMarker = dNow.getFullYear() + "-" + Number(dNow.getMonth()+1);
		} else {
			var currentMarker = myParams.contentId;
		}
		
		__debugLog("reset marker cookie to ", currentMarker);		
		$.cookie("eg_cal" + $(cal).data('id'),currentMarker);
	}});
}

/**
 * Configure search forms for a single calendar instance
 * @param {Object} cal
 * @param {Object} calendarId
 */
function glow_calendarNavInit(cal) {
	__debugLog("glow_calendarNavInit");
	var searchParams = $(cal).data('searchparams');
	
	// keyword form
	var keywordForm = $(".glow-calendar-nav .calendar-keywordform", cal);
	$("input:button",keywordForm).click(function(){
		var params = {keyword: $("input:text",keywordForm).val()};
		glow_sendCalendarQuery(cal, params);		
	});	

	// category form
	var eventTypeForm = $(".glow-calendar-nav .calendar-eventtypeform", cal);	
	setSelect(eventTypeForm,"eventtype","config","eventtype",searchParams.eventtype);
	
	// populate the select list with options
	$("input:button",eventTypeForm).click(function(){
		var params = {eventtype: $("select option:selected",eventTypeForm).val()};
		glow_sendCalendarQuery(cal, params);
	});	
		
	// location form
	var locationForm = $(".glow-calendar-nav .calendar-locationform", cal);
	setSelect(locationForm,"location","field","vchCalendarEventLocation_c",searchParams.location);
	$("input:button",locationForm).click(function(){
		var params = {location: $("select option:selected",locationForm).val()};
		glow_sendCalendarQuery(cal, params);		
	});	
	
		
	// calendar markers
	var params = $(cal).data('searchparams');
	var y;
	var m;
	try {
		if( params.date) {
			var dateParts = params.date.split('-');
			y = dateParts[0];
			m = dateParts[1]-1;
			__debugLog("dateParts,y,m",dateParts,y,m);
		} else {
			if (params.markers) {
				var markerParts = params.markers.split('-');
				y = markerParts[0];
				m = parseInt(markerParts[1]) - 1;
				__debugLog("markerParts,y,m",markerParts,y,m);
			} else {
				var currentMarker = $.cookie("eg_cal" + $(cal).data('id'));
				__debugLog("currentMarker",currentMarker);
				if( currentMarker != null ){
					var aCurrentMarker = currentMarker.split("-");
					y = aCurrentMarker[0];
					m = parseInt(aCurrentMarker[1])-1;
					__debugLog("aCurrentMarker,y,m",aCurrentMarker,y,m);
				}
			}
		}
	}catch(e){
		y=undefined; 
		m=undefined;
	}
	__debugLog("about to call initCalendarMarkers(cal,m,y)",cal,m,y);
	initCalendarMarkers(cal,m,y);	
}

function setSelect(frm,contentid,fldtype,fld,defaultValue,nullMessage){
	__debugLog("setSelect");
	if(nullMessage==undefined) nullMessage="";

	var params = {
		nocache 	: 0,
		module		: "calendar",
		contentType : "picklist",
		contentId	: contentid,
		params		: JSON.stringify({
			metadata	: { type: fldtype, value: fld },
			pagesize	: "all"
		})
	}
	var xmlData = "";
	$.ajax({url:"/index.cfm?mode=getData", dataType:"xml", type:"GET", data:params, success: function(xmlData){
			var formSelect = $("select",frm);
			var opt = $("<option value='" + nullMessage + "'></option>");
			var stOpt = {};
			$(formSelect).append(opt);
			
			$(xmlData).find('listitem').each(function(){
				var value = $(this).find('id').text();
				var text = $(this).find('title').text();
				
				// add unique values
				if (stOpt[value] == undefined) {
					stOpt[value] = 1;	// flag that we've processed this value				
					opt = $('<option value="' + value + '">' + text + '</option>');
					if (defaultValue == value) 
						$(opt).attr('selected', '1');
					$(formSelect).append(opt);
				}
			});
			
		}, error: function(xmlData){
			__debugLog(xmlData);
		}
	});
	
}

/**
 * initialise the marker view
 * @param {Object} cal
 */
var markerUpdateTimeout;
var markerContentUpdateTimeout;
function initCalendarMarkers(cal, m, y, updateBody) {	
	__debugLog("initCalendarMarkers",m,y);
	var markerForm = $(".glow-calendar-nav .calendar-markers", cal);
	var dateMarkers = $('ul.dayofmonth', markerForm).empty();
	var monthHeader = $('.monthheader', markerForm);
	
	// INPUT PARAMS
	var thisMonth = m==undefined ? new Date().getMonth() : m;	
	var thisYear = y==undefined ? new Date().getFullYear() : y;
	__debugLog("thisYear",thisYear);
	
	var lastMonth = thisMonth==0 ? 11 : thisMonth-1;
	var lastYear = thisMonth==0 ? parseInt(thisYear)-1 : thisYear;	
	
	var nextMonth = thisMonth==11 ? 0 : thisMonth+1;
	var nextYear = thisMonth==11 ? parseInt(thisYear)+1 : thisYear;
	
	var startDate = new Date(thisYear, thisMonth, 1);	
	
	var daysThisMonth = daysInMonth(thisMonth, thisYear);
	var daysLastMonth = daysInMonth(lastMonth, lastYear);
	var daysNextMonth = daysInMonth(nextMonth, nextYear);
	
	var startDayOfWeek = startDate.getDay();
	var endDayOfWeek = new Date(thisYear, thisMonth, daysThisMonth).getDay();

	var i;
	
	// determine visible range
	var firstVisibleDate = new Date(lastYear, thisMonth, 1);
	__debugLog("firstVisibleDate",firstVisibleDate);
	var lastVisibleDate = new Date(nextYear, nextMonth, 7);
	
	if(startDayOfWeek != 0) {
		firstVisibleDate.setMonth(lastMonth);
		firstVisibleDate.setDate(daysLastMonth-startDayOfWeek+1);
	}
	
	if(endDayOfWeek != 6){		
		lastVisibleDate = new Date(nextYear, nextMonth, 7 - endDayOfWeek -1);		
	}
	
	// init header 
	var thisMonthName = MONTH_NAMES[thisMonth];
	$(".month",monthHeader).text(thisMonthName + ' ' + thisYear);
	
	$('.next',monthHeader)
				.unbind('click')
				.click(function(){		
		initCalendarMarkers(cal, nextMonth, nextYear, true);		
	});
	$('.back',monthHeader)
				.unbind('click')
				.click(function(){	
		initCalendarMarkers(cal, lastMonth, lastYear, true);		
	});
	$('.month',monthHeader)
				.unbind('click')
				.click(function(){	
		initCalendarMarkers(cal, thisMonth, thisYear, true);		
	});
	
	// fill dates from this month
	for( i=0; i<daysThisMonth; i++) {
		var newDate = initMarkerDate(cal, i+1, thisMonth, thisYear);			
		dateMarkers.append(newDate);		
	}
	
	// fill dates from previous month
	for( i=0; i<startDayOfWeek; i++ ) {
		var newDate = initMarkerDate(cal, daysLastMonth-i, lastMonth, lastYear, true);			
		dateMarkers.prepend(newDate);		
	}
	
	// fill dates from next month
	var cnt = 7 - $("li", dateMarkers).size() % 7;
	for( i=0; i<cnt; i++ ) {
		var newDate = initMarkerDate(cal, i+1, nextMonth, nextYear, true);			
		dateMarkers.append(newDate);
	}
	var contentId = (thisYear + "-" + (thisMonth+1));
	
	clearTimeout(markerUpdateTimeout);
	markerUpdateTimeout = setTimeout(function(){ 
		getMarkers(cal,contentId,firstVisibleDate, lastVisibleDate);
		// get body content for search
		if (updateBody) {
			var p = {
				datefrom: thisYear + '-' + (thisMonth + 1) + '-' + 1,
				dateto: thisYear + '-' + (thisMonth + 1) + '-' + daysThisMonth,
				contentId: thisYear + '-' + (thisMonth + 1)
			};
			//__debugLog('get this month')
			glow_getCalendarBodyContent(cal, p);
		} 
	}, 1000);
				
}

/**
 * retrieve a set of content markers
 * @param {Object} cal
 * @param {Object} contentId
 * @param {Object} firstVisibleDate
 * @param {Object} lastVisibleDate
 */
function getMarkers(cal,contentId,firstVisibleDate,lastVisibleDate){
	__debugLog("getMarkers");
	__debugLog(firstVisibleDate);
	var params = {
		nocache 	: 0,
		module		: "calendar",
		contentType : "markers",
		contentId	: contentId,
		params		: JSON.stringify({
			datefrom	: firstVisibleDate.getFullYear() + '-' + (firstVisibleDate.getMonth()+1) + '-' + firstVisibleDate.getDate(),
			dateto		: lastVisibleDate.getFullYear() + '-' + (lastVisibleDate.getMonth()+1) + '-' + lastVisibleDate.getDate(),
			pagesize	: "all"
		})
	}
	
	var markerForm = $(".glow-calendar-nav .calendar-markers", cal);	
	var monthHeader = $('.monthheader', markerForm);
	
	var xmlData = "";
	$.ajax({url:"/index.cfm?mode=getData", dataType:"xml", type:"GET", data:params, success: function(xmlData){	
		__debugLog("getMarkers - AJAX SUCCESS");	
		$(xmlData).find("date").each(function(){
			var sDate = $(this).text();
			var marker = $("li[rel='" + sDate + "']", cal);
			//__debugLog('FOUND',sDate,marker)
			$(marker).addClass('marked'); 
			$('.next,.back',monthHeader).show();
		});		
	}, error: function(xmlData){
			__debugLog("getMarkers - AJAX FAIL");
			__debugLog('error loading markers: contentId,firstVisibleDate,lastVisibleDate',contentId,firstVisibleDate,lastVisibleDate);
			$('.next,.back',monthHeader).show();			
		}
	});	
}

/**
 * initialise a marker date
 * @param {Object} d
 * @param {Object} m
 * @param {Object} y
 * @param {Object} shaded
 */
function initMarkerDate(cal, d,m,y, shaded) {
	var newDate = $("<li><span>" + d + "</span></li>");
	if(shaded) newDate.addClass('shaded');
	
	// store a string representation of this date in the 'rel' attribute
	var sDate = y + "-" + zeroPad((m+1),2) + "-" + zeroPad(d,2);	
	newDate.attr('rel',sDate);
	
	newDate.data('day',d);
	newDate.data('month',m);
	newDate.data('year',y);	
	$(newDate).click(function(){
		var d = $(this);
		selectDate(cal,d.data('day'), d.data('month'), d.data('year'));
	});
	return newDate;	
}

// zero pad a numeric string
function zeroPad(val,len) {
	var newVal = "" + val;
	while(newVal.length < len) {
		newVal = "0" + newVal;
	}
	return newVal;
}

/**
 * send a request for events occurring on this date
 * @param {Object} day
 * @param {Object} month
 * @param {Object} year
 */
function selectDate(cal, day, month, year) {
	var calendarForm = $(cal).data('form');
	month = parseInt(month) + 1;
	year = parseInt(year);
	day = parseInt(day);
	//__debugLog('calendarForm', calendarForm);
	//__debugLog('day/month/year---', day, month, year);
	var value = "date|" + year + "-" + month + "-" + day;
	$("input.submitvalue",calendarForm).val(value);
	//return false;
	$(calendarForm).submit();
}

function initCalendarEventList(cal) {
	var params = $(cal).data('searchparams');
 
	/////////////////////////////////////////////
	// adjust padding on horizontal list2 landing page 
	var itemList = $('ul.landing-horizontal-list2', cal);
	$("li:nth-child(4n)", itemList).css("marginRight","0");  
	$("li:not(.processed)",itemList).each(function(){
		$(this).addClass('processed');
		// store items    
		var hdr = $("h2",this).remove();  
		var img = $("img",this).remove();
		var txt = $(this).html();
		var a = $("a:first",this).text("").remove();  
		// write back in the proper sequence  
		$(this).html("");  // blank it 
		$(this).append(hdr); // header comes first
		a.append(img);    // image goes inside link
		$(this).append(a)   // link goes in base  
		$(this).append("<span class='caption'>" + txt + "</span>"); // caption goes after link  
	});
 
	// load an event on click
	$(".calendar-event-item", cal).each(function(){
		$(".calendar-event-link",this).click(function(){   
			params.event = $(this).metadata().event;
			var paramsDate = $(this).metadata().date;
			var aParamsDate = paramsDate.split("-");
			params.date = aParamsDate[0]+"-"+aParamsDate[1];
			glow_sendCalendarQuery(cal, params);
			return false;
		}); 
	}); 
}

/* retrieve number of days in the current month */
function daysInMonth(iMonth, iYear) {
	return 32 - new Date(iYear, iMonth, 32).getDate();
}


/* Copyright (c) 2006 Mathias Bank (http://www.mathias-bank.de)
 * Dual licensed under the MIT (http://www.opensource.org/licenses/mit-license.php) 
 * and GPL (http://www.opensource.org/licenses/gpl-license.php) licenses.
 * 
 * Thanks to Hinnerk Ruemenapf - http://hinnerk.ruemenapf.de/ for bug reporting and fixing.
 */
jQuery.extend({
/**
* Returns get parameters.
*
* If the desired param does not exist, null will be returned
*
* @example value = $.getURLParam("paramName");
*/ 
 getURLParam: function(strParamName){
	  var strReturn = "";
	  var strHref = window.location.href;
	  var bFound=false;
	  
	  var cmpstring = strParamName + "=";
	  var cmplen = cmpstring.length;

	  if ( strHref.indexOf("?") > -1 ){
	    var strQueryString = strHref.substr(strHref.indexOf("?")+1);
	    var aQueryString = strQueryString.split("&");
	    for ( var iParam = 0; iParam < aQueryString.length; iParam++ ){
	      if (aQueryString[iParam].substr(0,cmplen)==cmpstring){
	        var aParam = aQueryString[iParam].split("=");
	        strReturn = aParam[1];
	        bFound=true;
	        break;
	      }
	      
	    }
	  }
	  if (bFound==false) return null;
	  return strReturn;
	}
});
