var goldenrod
if (!goldenrod) goldenrod = {}

/*Imported classes
var Dom = goldenrod.Dom;
*/

//Create a namespace - Animate with a constructor that sets FramesPerSec to 20 if the current Browser is Internet Explorer

goldenrod.Animate = new function() {
	this.FramesPerSec = 25;
	this.Delta = 1000/this.FramesPerSec;
}

goldenrod.Animate.setFrameRate = function(framesPerSec, ie_framesPerSec) {
	
	framesPerSec ? (this.FramesPerSec = framesPerSec) : (this.FramesPerSec = 25);
	if(goldenrod.Dom.isIE) {
		ie_framesPerSec ? (this.FramesPerSec = ie_framesPerSec): (this.FramesPerSec = 25);
	}
	this.Delta = 1000/this.FramesPerSec;
	
}

/**************************************************************************************************
*Animate.State - Holds the state of an on HTML Absolutely Positioned Element.
*
*eltBox - Style parameter for an absolutely positioned HTML elements box
*
*eltCLipBox - 	Style parameters for an absolutely positioned HTML elements clip rectangle
*
*Opacity - Style parameter for an HTML elements opactcity (0 - 100)
*
*Note:All data will be handled in point units for uniformity.
**************************************************************************************************/
goldenrod.Animate.Box = new goldenrod.Dom.Rectangle();		//Rectangle for temporary storage.


goldenrod.Animate.State = function(left, top, width, height, opacity, clipleft, cliptop, clipwidth, clipheight) {

	//alert("State Constructor");
	this.eltBox = new goldenrod.Dom.Rectangle();
	if(left != null) this.eltBox.Left = left;
	if(top != null) this.eltBox.Top = top;
	if(width != null) this.eltBox.Width = width;
	if(height != null) this.eltBox.Height = height;
	this.eltBox.adjustRB();
	
	if(opacity == null) this.Opacity = 100; else this.Opacity = opacity; //if opacity is null or undefined
	
	this.eltClipBox = new goldenrod.Dom.Rectangle();
	if(clipleft != null ) this.eltClipBox.Left = clipleft;
	if(cliptop != null ) this.eltClipBox.Top = cliptop;
	if(clipwidth != null ) this.eltClipBox.Width = clipwidth;
	if(clipheight != null ) this.eltClipBox.Height = clipheight;
	this.eltClipBox.adjustRB();
}
	
goldenrod.Animate.State.prototype.copy = function(state) {
	this.eltBox.copy(state.eltBox);
	this.Opacity = state.Opacity;
	this.eltClipBox.copy(state.eltClipBox);
}

goldenrod.Animate.State.prototype.add = function(state) {
	this.eltBox.addy(state.eltBox);
	this.Opacity += state.Opacity;
	this.eltClipBox.add(state.eltClipBox);
}


/**************************************************************************************************
*Animate.Event.Flag - constants
*
*Flag - A code that indicate what to do
*	1 - set node parameters, then append node and run event.
*	2 - run event and remove node.
*	3 - write "src" (which make be an file name of an image) and run event
*	4 - write text
**************************************************************************************************/
goldenrod.Animate.nothing = 0;
goldenrod.Animate.setnode = 1;
goldenrod.Animate.removenode = 2;
goldenrod.Animate.writesrc = 3;
goldenrod.Animate.writetext = 4;
goldenrod.Animate.user_routine = 5;
goldenrod.Animate.abhort = 6;

/**************************************************************************************************
*Animate.Event - Specifies an event
*
*Start - The starting state of an event
*End - The ending state of an event
*Id - the id text of an element
*
*Millesec - the duration of the event
*
*Flag - A code that indicate what to do
*
*onPlaying - an optional function that will be called periodically while the event is playing
*
*onFinish - an optional function that will be called when the event has finished playing.
**************************************************************************************************/
goldenrod.Animate.Event = function(id, start, end, duration, flag, flagref, parentnode, onplaying, onfinish){
	
	this.Start = new goldenrod.Animate.State(0,0,0,0,100);
	this.Start.copy(start);
	this.End = new goldenrod.Animate.State(0,0,0,0,100);
	this.End.copy(end);
	this.Id = id;
	this.Millisec = duration;
	if(flag == null ) this.Flag = goldenrod.Animate.nothing; else this.Flag = flag;
	if(flagref == null ) this.Flag_ref = 0; else this.Flag_ref = flagref;
	if(parentnode == null ) this.ParentNode = 0; else this.ParentNode = parentnode;
	this.onPlaying = onplaying;
	this.onFinish = onfinish;
	
	//this.Play = Animate.playEvent;
	}
	

/**************************************************************************************************
*Animate.Occurence - Specifies an occurence of an event
*
*eventItem - The event
*eventTime - The time since the previous event started
*eventCount - How many time the play the event when the event list loops. -1 means loop forever. 
**************************************************************************************************/
goldenrod.Animate.Occurence = function(event, time, count){
	this.eventItem = event;
	this.eventTime = time;	//time since previous event started
	if(count == null) this.eventCount = -1; else this.eventCount = count;
	}

goldenrod.Animate.setState = function(id, state) {
	
	returnvalue = true;
	var i, parameter, f, elt=document.getElementById(id);
	var statearray = [state.eltBox.Left, state.eltBox.Top, state.eltBox.Width, state.eltBox.Height,
					  state.Opacity,
					  state.eltClipBox.Left, state.eltClipBox.Top, state.eltClipBox.Width, state.eltClipBox.Height]
	
	
	for(i=0; i<goldenrod.Animate.setfunctionArray.length; i++) {
		parameter=statearray[i]; 
		f=goldenrod.Animate.setfunctionArray[i];
		if(parameter != "auto") f(elt, parameter);
		}
	return returnvalue;
	}
	



goldenrod.Animate.setfunctionNameArray = ["goldenrod.Animate.setLeft", "goldenrod.Animate.setTop", "goldenrod.Animate.setWidth", 
		 					"goldenrod.Animate.setHeight", "goldenrod.Animate.setOpacity",
							"goldenrod.Animate.setClipLeft", "goldenrod.Animate.setClipTop", 
							"goldenrod.Animate.setClipWidth", "goldenrod.Animate.setClipHeight" ];
	


/*************************************************************************************************
*Millisec = Total number of milli-secs for the move to complete (1000 milliseconds = 1 second)
**************************************************************************************************/
//Animate.playEvent = function(e) {}

goldenrod.Animate.Event.prototype.Play = function(){
	var e = this; 
	var elt = document.getElementById(e.Id), m = e.Millisec, node, playcount=0, image;
	var deltaState = new Array(9); 
	
	
	
	
	
	function execute() {
		var a, b, n=9, playcount=0, i, index, setInterval_id;
		
		function play() {
			var j;
			if(e.onPlaying && (!playcount) ) {	//call onPlaying (if it exists) every second.
				e.onPlaying();
			}
			if( ++playcount == 25)	playcount=0;
			
			if(n){
				for(j=0; j<9; j++){
					if(deltaState[j][3]) {
						if(deltaState[j][2] == "auto") {n--; deltaState[j][3] = 0;}
						else if( Math.abs(deltaState[j][1] - deltaState[j][0]) >= Math.abs(deltaState[j][2]) ){
							goldenrod.Animate.setfunctionArray[j](elt,deltaState[j][0]);
							deltaState[j][0]+=deltaState[j][2];
						} else {
							goldenrod.Animate.setfunctionArray[j](elt,deltaState[j][1]);
							deltaState[j][2] = "auto";
							n--;
							deltaState[j][3] = 0;
						}	
					}
				}	
			}
			else {
				if(e.onFinish) e.onFinish();
				clearInterval(setInterval_id);
			}
		}
		
		
		for(index=0; index<9; index++) {
			a = deltaState[index][0]; b = deltaState[index][1]; i = deltaState[index][2]
			if( (i != "auto") && (a != b) ) {
				if(i != 0 ) {
					deltaState[index][0] = a+i;
				} else {
					deltaState[index][2] = "auto"
					setTimeout(goldenrod.Animate.setfunctionNameArray[index] + "('" + elt + "', " + b + ")", m );		
				}
			}
		}
		setInterval_id = setInterval(play, goldenrod.Animate.Delta);
	}
		
	
	function executeall () {
		
		
		function setIncrement(prop1, prop2, index) {
			var a, b, i;
			if(prop2) {
				a = e.Start[prop1][prop2];
				b = e.End[prop1][prop2];
			} else {
				a = e.Start[prop1];
				b = e.End[prop1];
			}
			
			if( (a == "auto") || (b == "auto") || (a == b)) i = "auto";
			else {
				i = Math.round( ( ( b-a ) * goldenrod.Animate.Delta )/m ) ; //steps is always >= 1
			}
			
			deltaState[index] = [a, b, i, 1];
						
		}
		
		setIncrement('eltBox', 'Left', 0);
		setIncrement('eltBox', 'Top', 1);
		setIncrement('eltBox', 'Width', 2);
		setIncrement('eltBox', 'Height', 3);
		setIncrement('Opacity', null, 4);
		setIncrement('eltClipBox', 'Left', 5);
		setIncrement('eltClipBox', 'Top', 6);
		setIncrement('eltClipBox', 'Width', 7);
		setIncrement('eltClipBox', 'Height', 8);
		
		execute();
		
	}
	
	
	switch(e.Flag) {
		case goldenrod.Animate.nothing :
	
			goldenrod.myAlert("We are inside playEvent and Flag = nothing");
			executeall();
			break;
	
		case goldenrod.Animate.setnode :
			myAlert("We are inside playEvent and Flag = setnode");
			node = e.Flag_ref;
			node.id = e.Id; 
			node.style.left = state.eltBox.Left + "pt";
			node.style.top = state.eltBox.Top + "pt";
			node.style.width = state.eltBox.Width + "pt";
			node.style.height = state.eltBox.Height + "pt";
			goldenrod.Dom.setStyleOpacity(node, state.Opacity);
			goldenrod.Dom.setStyleClip(node, state.eltClipBox);
			e.ParentNode.appendChild(node);
			executeall();
			break;
	
		case goldenrod.Animate.removenode :
			myAlert("We are inside playEvent and Flag = removenode");
			executeall();
			e.ParentNode.removeChild(node);
			break;
	
		case goldenrod.Animate.writesrc : 
			myAlert("We are inside playEvent and Flag = writesrc");
			elt.src=e.Flag_ref; //Change photo
			executeall();
			break;
	
		case goldenrod.Animate.writetext :
			myAlert("We are inside playEvent and Flag = writetext");
			elt.innerHTML=e.Flag_ref;
			executeall();
			break;
			
		case goldenrod.Animate.user_routine :
			e.Flag_ref(e.ParentNode);		//Flag_ref is a user defined function that is executed before 
			executeall();
		
		case goldenrod.Animate.abhort : 
			break;
	}
	
	
	
	return;
}



goldenrod.Animate.setLeft = function(Elt, L) {
	
	returnvalue = true;
	if(Elt.nodeType == 1) {
		if(L<0) L = -L;
		Elt.style.left = L + "pt";}
	else returnvalue = false;
	return returnvalue;
	}
	
goldenrod.Animate.setTop = function(Elt, T) {
	
	returnvalue = true;
	if(Elt.nodeType == 1) {
		if(T<0) T = -T;
		Elt.style.top = T + "pt";}
	else returnvalue = false

	return returnvalue;
	}
	
	
goldenrod.Animate.setWidth = function(Elt, W) {
	
	returnvalue = true;
	if(Elt.nodeType == 1)  {
		if(W<0) W = -W; 
		Elt.style.width = W + "pt";}
	else returnvalue = false
	return returnvalue;
	}
	
	
goldenrod.Animate.setHeight = function(Elt, H) {
	
	returnvalue = true;
	if(Elt.nodeType == 1)   {
		if(H<0) H = -H;
		Elt.style.height = H + "pt";}
	else returnvalue = false
	return returnvalue;
	}
	
goldenrod.Animate.setOpacity = function(Elt, O) {
	
	returnvalue = true;
	if(Elt.nodeType == 1)   {
		if(O<0) O = -O; 
		goldenrod.Dom.setStyleOpacity(Elt, O);}
	else returnvalue = false
	return returnvalue;
	}
	
goldenrod.Animate.setClipLeft = function(Elt, L) {
	
	returnvalue = true;
	var style = goldenrod.Dom.getStyle(Elt);
	goldenrod.Dom.getStyleClip(style, goldenrod.Animate.Box);
	if(Elt.nodeType == 1) {
		
		goldenrod.Animate.Box.Left = L;
		goldenrod.Animate.Box.adjustRB();
		goldenrod.Dom.setStyleClip(Elt, goldenrod.Animate.Box)}
	else returnvalue = false;
	return returnvalue;
	}
	
goldenrod.Animate.setClipTop = function(Elt, T) {
	
	returnvalue = true;
	var style = goldenrod.Dom.getStyle(Elt);
	goldenrod.Dom.getStyleClip(style, goldenrod.Animate.Box);
	if(Elt.nodeType == 1) {
		
		goldenrod.Animate.Box.Top = T;
		goldenrod.Animate.Box.adjustRB();
		goldenrod.Dom.setStyleClip(Elt, goldenrod.Animate.Box)}
	else returnvalue = false

	return returnvalue;
	}
	
	
goldenrod.Animate.setClipWidth = function(Elt, W) {
	
	returnvalue = true;
	var style = goldenrod.Dom.getStyle(Elt);
	goldenrod.Dom.getStyleClip(style, goldenrod.Animate.Box);
	if(Elt.nodeType == 1) {
		
		goldenrod.Animate.Box.Width = W;
		goldenrod.Animate.Box.adjustRB();
		goldenrod.Dom.setStyleClip(Elt, goldenrod.Animate.Box)}
	else returnvalue = false
	return returnvalue;
	}
	
	
goldenrod.Animate.setClipHeight = function(Elt, H) {
	
	returnvalue = true;
	var style = goldenrod.Dom.getStyle(Elt);
	goldenrod.Dom.getStyleClip(style, goldenrod.Animate.Box);
	if(Elt.nodeType == 1) {
		
		goldenrod.Animate.Box.Height = H;
		goldenrod.Animate.Box.adjustRB();
		goldenrod.Dom.setStyleClip(Elt, goldenrod.Animate.Box)}
	else returnvalue = false
	return returnvalue;
	}
	
	
goldenrod.Animate.setfunctionArray = [goldenrod.Animate.setLeft, goldenrod.Animate.setTop, goldenrod.Animate.setWidth, goldenrod.Animate.setHeight, 
							goldenrod.Animate.setOpacity,
							goldenrod.Animate.setClipLeft, goldenrod.Animate.setClipTop, 
							goldenrod.Animate.setClipWidth, goldenrod.Animate.setClipHeight ];
							
							
