var resize_timer= new Array(),		// setInterval id
	opacity_timer=new Array(),
	
	resize_stack= new Array(), 		// stacks - data for type of event indexed by id
	opacity_stack=new Array(),
	
	resize_state= new Array(),		// The direction, Opacity fade in or out. Size increase or decrease
	opacity_state=new Array(),
	
	resize_schedule= new Array(),	// List id id's that need to be faded or resized
	opacity_schedule=new Array(),
	
	orig_size=new Array(),	// A way of setting an image back after being reduce to zero
	size_step_speed = 4,	// Used for resizing, use values 1,10,100 typically, 1 fast, 100 slow. But must not exceed h or w
	size_step_inter = 10,	// Used for resizing, 1 fast, 100 slow

	opacity_job_running=false,	// Semiphore to controll sched_opacity()
	resize_job_running=false, 	// Semiphore to controll sched_resize()
	MS=(navigator.appName == "Microsoft Internet Explorer")?true:false,// save keep working out which browser
	opacity_sched_timer = null,
	resize_sched_timer =null;

function init_ids(){/* 1. Hides "effected" objects by either zero opacity or zero size, 
					   2. Creates 2 lists(opacity_schedule, resize_schedule) of id's for effects, OR runs the "effected" job straight away */

	var all=document.getElementsByTagName('*');
	for(var i=0; i<all.length; i++){
		// if(all[i].name)alert(all[i].name);
		if(all[i].id){ 
			var objId = all[i].id;
			var effect=objId.substring(0,5);
		}
		else{ continue; }											// Can't do effects without an id
		switch(effect){
			case 'OLATE':											// Set opacity to zero to hide for "manual" switch on later
				//alert(effect + "   " +  objId);
				my_init_op(objId);
				break;
			case 'ODLAY':	// Opacity Delay
				my_init_op(objId);									// 1. Set opacity to zero so to hide
				opacity_schedule.push(objId);						// 2. Push id onto opactity list. So it can be faded in later
				break;
			case 'OONLD':	// Opacity Onload
				my_init_op(objId);									// 1. Set opacity to zero so to hide
				my_fade(objId, 0, 'in', 4, 1);						// 2. Run straight away. last 2 parms = step,delay
				break
			case 'RDLAY':	// Resize Delay
				my_init_resize(objId);								// 1. Set size to zero so to hide
				resize_schedule.push(objId);						// 2. Push id onto resize list. So it can be enlarged later
				break;	
			case 'RONLD':	// Resize Onload
				my_init_resize(objId);								// 1. Set size to zero so to hide
				my_resize(objId,'L');								// 2. Run straight away
		}//end of switch
	}// end of for
	opacity_sched_timer=setInterval("sched_opacity()",10);
	resize_sched_timer =setInterval("sched_resize()",1000);
}//end of f()

/* ************************************************** Begin Resize Stuff ************************************* */ 

function sched_resize(){		// Called every 10ms, and if no other jobs runs my_resize(). If job list empty switches off
	if(resize_job_running)return;
	
	if(resize_schedule.length > 0){
		var objId=resize_schedule.shift()
		my_resize(objId,'L');
	}else{
		clearInterval(resize_sched_timer);	// after all jobs done, switch off this scheduler
	}
}

function my_init_resize(objId){	// Save the original size, and set size to zero
	var id=document.getElementById(objId);	
	var st=id.style;	//

	if (st.height==""){
		//alert("no Style  " +  id.clientHeight + "  " + id.height + " " + id.naturalHeight + " " + id.offsetHeight);
		var H=id.height;
		var W=id.width;
	}else{
		//alert("style");
		var H=get_h(st);
		var W=get_w(st);
	}
/*
	var str=new Array("\n");
	for(var i in id){
		if(i.match("eight")){
			// var kk=eval("document.write(id.i)");
			str.push("\n" + i);
		}
	}
	str.sort();
	
	for(var k=0; k<str.length;k++){
		document.write(str[k] + "<br>");
	}
	
	alert(id.clientHeight + "  " + id.height + " " + id.naturalHeight + " " + id.offsetHeight);
*/
	//var H = (st.height=="")?id.height:get_h(st);	// use style or dom
	//var W = (st.width=="") ?id.width :get_w(st);
	orig_size[objId]=[H,W];
	//alert(orig_size[objId]);
	st.height="0px"; st.width ="0px";				// add style if not already given - set to very small to hide
}

function get_h(obj_style){	// get the integer height
	var h=obj_style.height.split("p",1);
	return parseInt(h[0]);
}

function get_w(obj_style){	// get the integer width
	var w=obj_style.width.split("p",1);
	return parseInt(w[0]);
}

function my_size(objId){	// reduces or increase image. stops if limit reached
	var objId_style=document.getElementById(objId).style;		// short cut
	var direction=resize_stack[objId][0], step_h=resize_stack[objId][1], step_w=resize_stack[objId][2], limit_h=resize_stack[objId][3], limit_w=resize_stack[objId][4],//All constants, no need to resize_stack after. Also, done for readability
		h=get_h(objId_style),						// Current height
		w=get_w(objId_style);						// Current width	
		
	//alert("Id = "+objId+" Dir = "+direction+" Step_h = "+step_h+" Step_w = "+step_w+" Max_h = "+limit_h+" Max_w = "+limit_w+" h = "+h+" w= "+w );clearInterval(timer[objId]);return;

	if(direction == 'L'){	// make larger
		h=h+parseInt(step_h);						// h now adjustment
		w=w+parseInt(step_w);						// w now adjustment
		if (h > limit_h || w > limit_w){			// Stop when either w or h exceed limit
			opacity_job_running=false;						// Allows the "scheduler" to run another job
			return clearInterval(resize_timer[objId]);		// This will stop this f() being called 
		}
	}else {					// make smaller
		h=h-parseInt(step_h);
		w=w-parseInt(step_w);
		if (h < limit_h || w < limit_w){
			opacity_job_running=false;
			return clearInterval(resize_timer[objId]);
		}
	}
	// here if making the size adjustment
	objId_style.height=h+"px";
	objId_style.width =w+"px";
}

function my_resize(objId,direction){	// front to my_size(), works out the w & h steps ans the w & h limits
	// Get w and h
	var obj_style = document.getElementById(objId).style, 
		h=get_h(obj_style),	w=get_w(obj_style);

	// Check here if coming from zero size to original size
	if (h == 0 || w == 0){
		h=orig_size[objId][0];
		w=orig_size[objId][1];
	}
	// Step increment base on dimension reduced by n
	var step_h=h/size_step_speed;
	var step_w=w/size_step_speed;
	// Limit for h and w according to direction
	var limit_h = (direction=='L') ? h:0;
	var limit_w = (direction=='L') ? w:0;

	resize_state[objId]=direction;
	resize_stack[objId]=[direction, step_h, step_w, limit_h, limit_w];
	resize_timer[objId]=setInterval("my_size('"+objId+"')",size_step_inter);	
}

/* ************************************************** End   Resize Stuff  ************************************* */ 
/* ************************************************** Begin Opacity Stuff ************************************* */

function sched_opacity(){		// Called every 10ms, and if no other jobs runs setInterval(my_op(),1). If job list empty switches off
	if(opacity_job_running)return;
	
	if(opacity_schedule.length > 0){
		var objId=opacity_schedule.shift(), opacity=0, direction='in', op_step=10, step_delay=1;	// readability
		opacity_job_running=true;
		opacity_state[objId]=direction;
		opacity_stack[objId]=[opacity,direction,op_step];
		opacity_timer[objId]=setInterval("my_op('"+objId+"')",step_delay);
	}else{
		clearInterval(opacity_sched_timer);	// after all jobs done, switch off this scheduler
	}
}

function my_init_op(objId){
	if(MS) document.getElementById(objId).style.filter  = "alpha(opacity="+0+")";
	else   document.getElementById(objId).style.opacity = 0;
}

function my_op(objId){

	//var op_step = opacity_stack[objId].pop(), direction = opacity_stack[objId].pop(), opacity = opacity_stack[objId].pop();
	var op_step = opacity_stack[objId][2], direction = opacity_stack[objId][1], opacity = opacity_stack[objId][0];
	var obj = document.getElementById(objId);
	// alert(objId  + "  " + opacity  + "  " + direction  + "  " + op_step);
	if (!obj) {alert('error ' + objId + " obj =  " + obj);}

	if ( (opacity >= 0) && (opacity <= 100) ) {
		if (MS){
			obj.style.filter = "alpha(opacity="+opacity+")";
			//opacity += op_step;		//IE seems much slower
		} else{
			obj.style.opacity = opacity/100;
		}	
		if (direction == 'in') {
			opacity += op_step;
		}else{
			opacity -= op_step;
		}
		//opacity_stack[objId].push(opacity,direction,op_step);
		opacity_stack[objId]=[opacity,direction,op_step];
	}else{
		clearInterval(opacity_timer[objId]);
		opacity_job_running=false;
		// opacity_timer[objId]=null;
	}
}
		
function my_fade(objId,opacity,direction,op_step,st_delay){	// id, initial opacity, direction=in|out, increments, time between increments
	// alert("In my_fade()" + objId);
	if (opacity_state[objId] != direction){				// only fade in the oppersite direction
		opacity_state[objId]=direction;
		opacity_stack[objId]=[opacity,direction,op_step];	// Can't use stack[objId].push 1st time 
		opacity_timer[objId]=setInterval("my_op('"+objId+"')",st_delay);
	}else
		alert("Ignoring same requests, i.e. fade in when already in");
	// alert(objId  + "  " + opacity  + "  " + direction  + "  " + op_step + " " + st_delay);	
}

/* ************************************************** End Opacity Stuff ************************************* */

function dump_data(){
	var s1="OPACITY TIMERS ", s2="RESIZE TIMERS ", s3="OPACITY STACK\n", s4="RESIZE STACK\n", s5="OPACITY STATE ", s6="RESIZE STATE ", e=" END\n", s= " ";
	
	for(var i in opacity_timer) s1+=s + opacity_timer[i];
	for(var i in  resize_timer) s2+=s +  resize_timer[i];
	for(var i in opacity_stack) s3+=s+i+s+"["+opacity_stack[i]+"]"+"\n";
	for(var i in  resize_stack) s4+=s+i+s+"["+resize_stack[i]+"]"+"\n";
	for(var i in opacity_state) s5+=s + opacity_state[i];
	for(var i in  resize_state) s6+=s +  resize_state[i]; 
	alert(s1 + " End \n" + s2 + " End\n" + s3 + "End\n" + s4 +"End\n" + s5 + " End\n" + s6 + " End\n");
}
