//get the raw xml 
function getPrecisXML(thisurl){
	//call the right constructor for the browser being used
	if (window.ActiveXObject)
		xhr = new ActiveXObject("Microsoft.XMLHTTP");
	else if (window.XMLHttpRequest)
		xhr = new XMLHttpRequest();
	else
		alert("Your web browser does not support this. It may need updating.");

	//prepare the xmlhttprequest object
	url=thisurl; 
	//append date
	var d = new Date();
	var time = d.getTime();
	url= url + '?prevent_cache='+ time;
	
	xhr.open("GET",url,true);
	xhr.setRequestHeader("Cache-Control", "no-cache");
	xhr.setRequestHeader("Pragma", "no-cache");
	
	
	xhr.onreadystatechange = function() {
		if (xhr.readyState == 4){
			if (xhr.status == 200){
				if (xhr.responseText != null){
				    //glean and format content
					processXML(xhr.responseXML);
				}
				else{
					precisHandlers.errorMessage();
					return false;
				}
			}
			else{precisHandlers.errorMessage();}
		}
	}
	//send the request
	xhr.send(null);
}


var dateTime = {	
//methods = doDate, getDayName, getMonthName, ampm

	doDate: function(timestamp){
		//eg '2008-09-05T06:00:00+10:00';
		var pattern=/\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\+\d{2}:\d{2}/ ;		
	    if(timestamp.match(pattern)){
            var year='';
            var month='';
            var day='';
            var hours='';
            var minutes='';
            year=parseInt(timestamp.substring(0, 4), 10 );
            month=parseInt(timestamp.substring(5, 7)-1, 10); 
            day=parseInt(timestamp.substring(8, 10),10);
            hours=parseInt(timestamp.substring(11, 13),10);
            minutes=parseInt(timestamp.substring(14, 16),10);
            var thisDate=new Date(year, month, day, hours, minutes);
            return thisDate;
		} 
		else{return false;}
	},
	
	
	stillValidTime: function(issueDate){
		var dateThen = issueDate.getUTCDate(); 
		var hoursThen=issueDate.getUTCHours();
		var timeNow = new Date();
		var dateNow = timeNow.getUTCDate();
		var hoursNow = timeNow.getUTCHours();
		if(dateNow - dateThen >1){
			return false; 
		}
		else if((dateNow - dateThen == 1) && (hoursNow + (24-hoursThen) > 23)){
			//17 temporarily changed to allow for later pushed issues
			return false; 										 
		}
		else{return true;}
	},
	
    getDayName: function(thisDate){
        var week = ["Sunday","Monday","Tuesday","Wednesday","Thursday","Friday","Saturday"];
        var dayName = thisDate.getDay();
        dayName = week[dayName];
        return dayName;
    },

   getMonthName: function(thisDate){
       var months = ["January","February","March","April","May","June","July","August","September","October","November","December"];
       var monthName = thisDate.getMonth();
       monthName = months[monthName];
       return monthName;
   },
	
   ampm: function(hour, mins){
       var ap = "am";
       if (hour   > 11) { ap = "pm";        }
       if (hour   > 12) { hour = hour - 12; }
       if (hour   == 0) { hour = 12;        }
	  
	   mins=':' + validateData.pad(mins,2); 
	   var time = hour  + mins + ' ' + ap;
	   return time;
   }
  
};

//local functions ==> 
var precisHandlers ={
//methods = doTimeStamp, doIcon, display, errorMessage, hide, show, changeLinks

//constants
targetId: 'm_vic_town_precis',
tag: 'area',
path: '/fwo/IDV10753/IDV10753.',	

    doTimeStamp: function(issueTime, atz){
        var localDate=dateTime.doDate(issueTime);
		if(!dateTime.stillValidTime(localDate)){
			//alert('Diagnostic - out of date'); //diagnostic only
			return false;
		}
		else {
            var dotime= dateTime.ampm(localDate.getHours(), localDate.getMinutes());
            var timeStamp='<p class="date">Issued at ' + dotime  + ' ' + atz + ' on '+ dateTime.getDayName(localDate)+ ' '+ localDate.getDate()+ ' ' + dateTime.getMonthName(localDate) + ' ' + localDate.getFullYear() + '</p>\n';
            return timeStamp;
		}
    },
	
    
	//	
    doIcon: function(val){
		if(!validateData.isNumber(val)){return false;}
		else{
            var imId='id'+ val;
            var images={id0:'blank.png', id1:'sunny.png', id2:'clear.png', id3:'partly-cloudy.png',id4:'cloudy.png', id6:'haze.png', id8:'light-rain.png', id9:'wind.png', id10:'fog.png', id11:'showers.png', id12:'rain.png', id13:'dust.png', id14:'frost.png', id15:'snow.png', id16:'storm.png', id17:'light-showers.png'};
        
            if(!images[imId]){return false;}
		    else{
                var img = images[imId];
                var imgPath='/weather-services/images/symbols/large/';
                var imgTag='<p><img src="' + imgPath + img + '" alt="" /></p>\n';
                return imgTag;
		    }
		}
    },
	
	//whole precis/errorMessage block
	display: function(block, numDays){	
	   var scaleFactor = numDays || 7; //7 days= default
	   var targetId=document.getElementById('precis');
	   var targetSelect = document.getElementById('ptowns');
	   targetId.style.width= 84*scaleFactor +'px';
	   scaleFactor<8? targetSelect.style.visibility = 'visible': targetSelect.style.visibility = 'hidden' ;
		   
	   targetId.innerHTML=block; 
	   targetId.style.display='block';	
    },
	
	//if no xml file, over 18 hours, or missing data/days
    errorMessage: function(){
	    var message='Information for this location is currently unavailable.';	
	    var block ='<a href="#" onclick="precisHandlers.hide(\'precis\'); return false;" id="close"><img src="/weather-services/images/symbols/close.gif" alt="close" title="close" /></a>\n';
	    block += '<h2 class="alert">' + message + '</h2>';
	    precisHandlers.display(block);	
     },

    //form elements and imagemap links
    hide: function(id){
        document.getElementById(id).style.display="none";
		//show if explicitly hidden for 8 days;
	    if(document.getElementById('ptowns').style.visibility='hidden'){document.getElementById('ptowns').style.visibility='visible'};
    },
    
	//tab controls, show hide map locations
    show: function(id_ref) {
         if(document.getElementById('precis')){ 
	        document.getElementById('precis').style.display='none';
			//if visibility hidden for 8 days, make visible
		    if(document.getElementById('ptowns').style.visibility='hidden'){document.getElementById('ptowns').style.visibility='visible'};
		    for(var i=0;i<2;i++){
			    var selectedaid='m'+ id_ref.substring(3);
				document.getElementById('map'+i).style.display='none';
			    document.getElementById(id_ref).style.display='block';
			    //tabber display
				document.getElementById('m'+i).parentNode.className='';
			    document.getElementById(selectedaid).parentNode.className='tabberactive';
		   }
	   }else{return;}
    },

    //change precis imagemap hrefs
    changeLinks: function (){
    var path= precisHandlers.path;
    if(document.getElementById('m_vic-forecast-map-7-day-all').getElementsByTagName('area')){
        var refs = document.getElementById('m_vic-forecast-map-7-day-all').getElementsByTagName('area');   
	    var ref='';	
	    for( var i=0;i<refs.length;i++){
		    ref=refs[i].getAttribute('href');
		    ref=ref.replace(/.*(PT\d{3})/,"$1"); //for ie
	        XMLUrl= path + ref + '.xml';
		    jref='javascript:getPrecisXML(\''+ XMLUrl +'\');\n';
		    refs[i].setAttribute('href', jref);
	    }
        } else{return;}
    },
	
    //town forecast select
    doTownForecast: function (){
        if(document.forms.tforecasts.towns){
            townURL=document.getElementById('towns').value; 
			if(townURL=='null'){alert('Please select a location');return;}
	        window.location = townURL;
            townURL='';
        } 
    },
	
    // town precis select
    doTownPrecis: function (){
		var path=precisHandlers.path;
        if(document.forms.tprecis.ptowns){
            var townID=document.getElementById('ptowns').value; 
			if(townID=='null'){alert('Please select a location');return;}
		    XMLUrl= path + townID + '.xml';		
		    getPrecisXML(XMLUrl);	
        }
    }
};

window.onLoad=addEvent(window, 'load', precisHandlers.changeLinks);
//generic
function addEvent(obj,evt,fn){
 if(obj.addEventListener)
	obj.addEventListener(evt, fn, false);
	else if(obj.attachEvent)
		obj.attachEvent('on' + evt,fn);
}

var errors=false;
//validation

var validateData ={
//methods = isNull, isNumber, isText, pad, strip
	
	isNull: function(val){
		val=validateData.strip(val);
		val = val.replace(/^\s$|#/g, "");
		if(val.length==0){return true;}
	},
	
	isNumber: function(val){
		val=val.replace( /\s/g, "");
		if (!isNaN(parseInt(val))){return val;}
		else{return false;}
	},
	
	isText: function(val){
		if(!validateData.isNull(val)){
			val = validateData.strip(val);
			var re = /[^a-zA-Z,\.\s]/; 
			if (!re.test(val)){return val;}
			else{return false};
		}
		else{return false;}
		
	},
	
	pad: function(val, len) {
        val = String(val);
	    len = len || 2;
	    while (val.length < len) val = "0" + val;
	    return val;
    },
	
    strip: function(val){
	    //trim spaces from ends and multiple spaces
        val= val.replace(/^\s*|\s(?=\s)|\s*$|#/g, "");
	    return val;
	}
	
};

//construct precis 
function processXML(xml){
	var time='';
	var precis='';
	var iconNum='';
	var min_v='';
	var max_v='';
	var showErrorMessage=false;
	var targetId=document.getElementById('precis');
	
	//close button
	var block='<a href="#" onclick="precisHandlers.hide(\'precis\'); return false;" id="close"><img src="/weather-services/images/symbols/close.gif" alt="close" title="close" /></a>\n';
	//location name
	var areas=xml.getElementsByTagName("area");
	for(var i=0;i<areas.length;i++){
		if(areas[i].getAttribute('type')=='location'){
			var location = xml.getElementsByTagName("area")[i].getAttribute('description'); 
	        block +='<h2>' + location + '</h2>';
		}
		else{
			//showErrorMessage=true;
			precisHandlers.errorMessage(); 
	        return ;
		}
	}
	
	//issue time
	var issueTime = xml.getElementsByTagName("issue-time-local")[0].childNodes[0].nodeValue;
	var atz = xml.getElementsByTagName("issue-time-local")[0].getAttribute('tz');
	var ts = precisHandlers.doTimeStamp(issueTime, atz); 
	//!ts? showErrorMessage=true : block += ts;
	if(!ts){ return precisHandlers.errorMessage(); }
	else{block += ts; }

	/*block +='<hr class="clearfix" />'; // if needed for some browsers when font display significantly scaled */ 
	
    //each day
	var days=xml.getElementsByTagName('forecast-period');
	if(days.length<7){showErrorMessage='true';}
	else{
	var sortedDays =new Array();
	    for(var i=0;i<days.length;i++){
		        var dayId= days[i].getAttribute('index');
				sortedDays[dayId]=days[i];				
        }
		days = sortedDays;
		
		//do day block
		for( var i=0;i<days.length;i++){    
		    block+= '<div class="block">';
			var thisDate = dateTime.doDate(days[i].getAttribute('start-time-local'));
			var dayName = dateTime.getDayName(thisDate);
			block+= '<h3>'+ dayName + '</h3>\n' ; 
			
			var elTotal=days[i].getElementsByTagName('element').length; //use for min/max day 0
			for(var j=0;j< elTotal; j++){
				//test for empty elements
				if(days[i].getElementsByTagName('element')[j].childNodes[0]){
					
				switch(days[i].getElementsByTagName('element')[j].getAttribute('type')){
				    case 'forecast_icon_code': 
					    var iconNum= days[i].getElementsByTagName('element')[j].childNodes[0].nodeValue;
						if(!validateData.isNumber(iconNum)){
							showErrorMessage='true';
						}
						else{
							iconNum  = validateData.isNumber(iconNum)
							var img = precisHandlers.doIcon(iconNum);
							//addIcon
			                block += img;
						}
						break;
					case 'air_temperature_minimum': 
					     var min_v = days[i].getElementsByTagName('element')[j].childNodes[0].nodeValue;
						 !validateData.isNumber(min_v)?showErrorMessage='true':min_v = validateData.isNumber(min_v);
						 break;
					case 'air_temperature_maximum': 
					    var max_v= days[i].getElementsByTagName('element')[j].childNodes[0].nodeValue;
						!validateData.isNumber(max_v)?showErrorMessage='true':max_v= validateData.isNumber(max_v);
						break;
				}
				
				}else{showErrorMessage=true; break}
			}


            //doPrecis
			if(days[i].getElementsByTagName('text')[0].childNodes[0]){
			    precis = days[i].getElementsByTagName('text')[0].childNodes[0].nodeValue;
			}
			!validateData.isText(precis)?showErrorMessage='true': precis  = validateData.isText(precis);
			
			//wrap if two words		
			var words= precis.split(' ');
            if (words.length==2){ precis= precis.replace(' ' , '<br />'); }
		    block+= '<p class="precis">' + precis + '</p>\n';
			block+= '<p class="smaller">\n';
			
			//min and max temps
			if(elTotal>2){block += 'Min <span class="min">' + min_v + '</span>';}
			if(elTotal>1){block +=  ' Max <span class="max">' + max_v + '</span>\n';}
			block += '</p>\n';
		    block += '</div>';
	    }
    }//end if days<7
	
	//check error flags
	showErrorMessage? precisHandlers.errorMessage():precisHandlers.display(block, days.length);
}