fp = {
	// *********************** Product rating properties ************************* //
	// Parent div ID for rating container
	ratingContainer: 'rate_product_js',
	// Hidden input field to store rating
	ratinginputID :'product_review_rating',
	// Images for active and inactive rating containers
	fullStarSRC : '/templates/images/star-full.gif',
	noStarSRC : '/templates/images/star-empty.gif',
	// Define array that stores rating text which appears next to stars
	// NOTE: To make this more efficient, consider using the stars alt text to generate the test displayed next to the image!
	ratingTextArray : new Array('I hate it','I don\'t like it','It\'s ok','I like it','I love it'),
	// *********************** Product rating properties ************************* //
	// *********************** Image Popup properties ************************* //
	// Page section IDs
	boundaryId:'interface',
	// Container id for popup image
	popImageContainer:'product-details-container-right',
	// ID of generated popup image container
	popunderId:'popunder',
	// Used for the image popup
	hideClass:'hide', 
	// Set variables for link text
	closeLabel : 'Close window',
	openLabel : 'Open window',
	//global parameters
	closelink:null,
	// *********************** Image Popup properties ************************* //
	// *********************** Dynamic form field properties ************************* //
	counter:null,
	containerID:'dynamic-form-field',
	fieldName:'Friends Email: ',
	buildLinkText:'Inform Your Friend(s) ',
	deleteLinkText:'remove friend',	
	helpTextLink:'Whats this?',
	helpText: 'Use this link to add more friend boxes to your form. This enables you to inform your friends about the site so that they can also register their interest. Remember you need a minimum of 4 friends for a chance to win free champagne.',
	// *********************** Dynamic form field properties ************************* /

	init:function()
	{
		// Check to see if W3C DOM is available - if not terminate script
		if(!document.getElementById || !document.createTextNode){return;}
		// Check to see if the ratingContainer is available
		var container_js = document.getElementById(fp.ratingContainer);
		// If ratingContainer exists (were on product-review page)
		if(container_js)
		{
			// Remove hide style to show rating (we dont want to show the ratings for browsers that aint DOM 1 complient - it wont work!)
			fp.cssjs('remove', container_js, "hide_form");
			
			// Add the mouseover event behaviour to ratingContainer (displays active styles onmouseover)
			fp.addEvent(container_js, 'mouseover', fp.initialiseHover, false);
			
			// Check if a rating value exists (if the page has been posted and returned errors)
			var ratingContainer = document.getElementById(fp.ratinginputID);
			if (ratingContainer.value!='')
			{	
				// Store rating value in a variable rating
				fp.rating = ratingContainer.value;
				// Use function to set the rating
				fp.setRating();
			}
		}
		// Initialise popup image function (for viewing large images on the product details page etc)
		fp.initWin();
		// Initialise dynamic form fields
		fp.initDynamicFormfield();
	},
	// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Popup image
	// Check to see if a popup win is available
  	initWin:function()
	{
		// Get image container
		var container=document.getElementById(fp.popImageContainer);
		// Check to see if image container exists
		if(container)
		{
			// Create div element to store image
		    fp.popunder=document.createElement('div');
		    // Assign id to new div
			fp.popunder.id=fp.popunderId;
			// Add hideclass to the new div (containing image)
			fp.cssjs('add',fp.popunder,fp.hideClass);
			// Add the new div as a child to the main page
			document.getElementById(fp.boundaryId).appendChild(fp.popunder);
			
			/****************** Build close image link ****************************/
			
			// Build links for each image by looping through each link from the 
			// image container
			var links=container.getElementsByTagName('a');
			
			// Create link element and assign to variable
			var closeLink=document.createElement('a');
			// Use the setAttribute method to set the href attribute to '#'
			closeLink.setAttribute('href','#');
			// Set text of link
			closeLink.innerHTML=fp.closeLabel;
			// Add an event to the link (closewindo event)
			fp.addEvent(closeLink,'click',fp.closeWin,false);
			fp.fixSafari(closeLink);
			// Apply the new link to the image div so the user can shut the window
			fp.popunder.appendChild(closeLink);
			
			// Loop through links and assign the click event with the openwin method
			for(var i=0;i<links.length;i++)
			{
				fp.addEvent(links[i],'click',fp.openWin,false);
				//alert(links[i].href);
			}
		}
	},
	
	// Function thats applied to links to open windows
	openWin:function(e)
	{
		var linkElement = fp.getTarget(e);
		// alert(linkElement.parentNode);
		//alert(fp.getTarget(e).href);
		// if there is no image in popup yet, create one.
		if(!fp.popunder.getElementsByTagName('img')[0])
		{
			// create image element
			var shot=document.createElement('img');
			// Get the link element for the small image using the fp.getTarget function 
			// (we use the link element to obtain the href value which is the source of the image)
			// var bigpic=fp.getTarget(e);
			// set large image src attribute to the href value of the small image link
			shot.setAttribute('src',linkElement.parentNode);
			// Append the image element to the div element (popunderId)
			fp.popunder.appendChild(shot);
			// Apply close functionality to image
			fp.addEvent(shot,'click',fp.closeWin,false);
			//
			fp.fixSafari(shot);
		}
		// Remove the fp.hideclss so we can show the large image
		fp.cssjs('remove',fp.popunder,fp.hideClass);
		// Stop link from being followed and 'event bubbling' by using the cancelClick() method
		fp.cancelClick(e);
	},
	
	// Function used by the popup window to close large image container
	// Note: When we use the addEvent function the event listener function (fp.closeWin)
	// has an object applied which can be used to obtain specific properties
	// e is used to obtain these parameters.
	// A very important one is 'target' (the element that has the eventhandler attatched to it - in this case 'closeLink')
	closeWin:function(e)
	{
		// hide popunder div (large image container) and don't follow link
		fp.cssjs('add',fp.popunder,fp.hideClass);
		// To eliminate 'event bubbling' (starts all events for parent elements of the current element?!?!)
		// use the cancelclickk function
		fp.cancelClick(e);
	},
	// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Popup image
	
	// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Dynamic form field (add delete form fileds on the fly
	initDynamicFormfield:function()
	{
		var container = document.getElementById(fp.containerID);
		//var container3 = document.getElementById("additional_number");
		if(container)
		{
			// Create link
			var liElement = document.createElement("li");
			var linkElement = document.createElement("a");
			linkElement.setAttribute('href','');
			fp.addEvent(linkElement, 'click', fp.buildFormField, false);
			var textNode = document.createTextNode(fp.buildLinkText);
			linkElement.appendChild(textNode);
			liElement.appendChild(linkElement);
			
			/////////////// ++++++++++++++++++++ IF SUHAN DOESNT LIKE COMMENT IT OUT
			// +++++++++++++++++++++++++++++++++++++ Hidden div
			var linkElement = document.createElement("a");
			linkElement.setAttribute('href','');
			fp.addEvent(linkElement, 'click', fp.displayHelp, false);
			var textNode = document.createTextNode(fp.helpTextLink);
			linkElement.className='whats-this';
			linkElement.appendChild(textNode);
			
			liElement.appendChild(linkElement);
			
			var hiddenDiv = document.createElement("div");
			hiddenDiv.setAttribute('id','hidden-div');
			hiddenDiv.className='hide';
			var textNode = document.createTextNode(fp.helpText);
			hiddenDiv.appendChild(textNode);

			liElement.appendChild(hiddenDiv);
			// +++++++++++++++++++++++++++++++++++++ Hidden div
			/////////////// ++++++++++++++++++++ IF SUHAN DOESNT LIKE COMMENT IT OUT
			container.appendChild(liElement);
			// Create link
			
			// If the form is posted back to itsefl, we need to check for additional friedns so we can build the fields and keep preentered values
			var container = document.getElementById("number_of_friends");
			if(container.value>0)
			{
				fp.preBuildFormField(container.value);
			}

		}
	},
	
	displayHelp:function(e)
	{
		//alert('test');
		container = document.getElementById("hidden-div");
		if (container.className == '')
		{
			fp.cssjs('add',container,'hide');
		}else
		{
			fp.cssjs('remove',container,'hide');
		}
		fp.cancelClick(e);
	},
	
	// Method to build form field when its clicked
	buildFormField:function(e)
	{
		if (!fp.counter)
		{
			fp.counter = 1;	
		}else
		{
			// Increment counter
			fp.counter = fp.counter+1;
		}
		// Create form input field
		var liElement = document.createElement("li");
		var nametext = document.createTextNode(fp.fieldName);
		var labelElement = document.createElement("label");
		labelElement.appendChild(nametext);
		labelElement.setAttribute('for',"friends_email_"+fp.counter);
		liElement.appendChild(labelElement);
		var formFieldElement = document.createElement("input");
		formFieldElement.setAttribute("id", "friends_email_"+fp.counter);
		formFieldElement.setAttribute("name", "friends_email_"+fp.counter);
		liElement.appendChild(formFieldElement);
		// Create form input field
		
		// Create delete link
		var linkElement = document.createElement('a');
		linkElement.setAttribute('href','');
		//linkElement.setAttribute('className','delete');
		linkElement.className='delete';
		fp.addEvent(linkElement, 'click', fp.deleteFormField, false);
		var textNode = document.createTextNode(fp.deleteLinkText);
		linkElement.appendChild(textNode);
		liElement.appendChild(linkElement);
		// Create delete link
				
		// Insert field before link
		var container = document.getElementById(fp.containerID);
		var linkElement =  container.getElementsByTagName('li');
		container.insertBefore(liElement, linkElement[0]);
		
		// VERY IMPORTANT. cancelClick() method stops the link from being followed (we dont use # as it takes the user to the top of the page)
		fp.cancelClick(e);
	},
	
	deleteFormField:function(e)
	{
		var target = fp.getTarget(e);
		var liElement = target.parentNode;
		while (liElement.firstChild) 
		{
			liElement.removeChild(liElement.firstChild);
		}
		var container = document.getElementById(fp.containerID);
		container.removeChild(liElement);
		fp.cancelClick(e);
	},
	
	// Method to pre build form field when the form is submitted BUT contains errors
	preBuildFormField:function(loop_number)
	{
		// Obtain friends emails to pupulate form fields
		var email_value = document.getElementById('friend_emails').value;
		// Split email
		var email_array=email_value.split(" ");
		// Reverse array so names populate correct boxes
		var emails = email_array.reverse();
		
		// Set the counter so the browser knows what number to make the next form field
		fp.counter = loop_number;
		// Loop through and build each field
		for(i=1; i <= loop_number; i++)
		{
			// Create form input field
			var liElement = document.createElement("li");
			var nametext = document.createTextNode(fp.fieldName);
			var labelElement = document.createElement("label");
			labelElement.appendChild(nametext);
			labelElement.setAttribute('for',"friends_email_"+i);
			liElement.appendChild(labelElement);
			var formFieldElement = document.createElement("input");
			formFieldElement.setAttribute("id", "friends_email_"+i);
			formFieldElement.setAttribute("name", "friends_email_"+i);
			formFieldElement.setAttribute("value", emails[i]);
			liElement.appendChild(formFieldElement);
			// Create form input field
			
			// Create delete link
			var linkElement = document.createElement('a');
			linkElement.setAttribute('href','');
			linkElement.className='delete';
			fp.addEvent(linkElement, 'click', fp.deleteFormField, false);
			var textNode = document.createTextNode(fp.deleteLinkText);
			linkElement.appendChild(textNode);
			liElement.appendChild(linkElement);
			// Create delete link
					
			// Insert field before link
			var container = document.getElementById(fp.containerID);
			var linkElement =  container.getElementsByTagName('li');
			container.insertBefore(liElement, linkElement[0]);
		}
	},

	
	// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Dynamic form field (add delete form fileds on the fly
																						  
	// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Product rating
	// Initialis hover function
	initialiseHover:function()
	{
		var container_js = document.getElementById(fp.ratingContainer);
		var img_element = container_js.getElementsByTagName('img');
		// Loop through images and assign the displayStar event
		for(var i=0; i<img_element.length; i++)
		{
			fp.addEvent(img_element[i],'mouseover',fp.displayStar,false);
		}
	},
	// Activate/deactive fonts
	displayStar:function(e)
	{
		var target = fp.getTarget(e);		
		var container_js = document.getElementById(fp.ratingContainer);
		var img_element = container_js.getElementsByTagName('img');
		// Loop through rating images, setting the relevant img source
		// Get rating container (hidden form filed that stores the rating, ready for update)
		var ratingContainer = document.getElementById(fp.ratinginputID);
		
		for(var i=0; i<img_element.length; i++)
		{
			// To determine the current img element we use the attribute value (the img element has no id attribute)
			// If img is equal to star user is hovering on, set all stars above this image to noStarSRC and set i to length of img_element(Stops loop)
			if (img_element[i].alt == target.alt)
			{
				// Set other stars to noStarSRC image
				for(var j=i; j<img_element.length; j++)
				{
					img_element[j].setAttribute('src',fp.noStarSRC);
				}
				// Set hovered star
				target.setAttribute('src',fp.fullStarSRC);
				
				// Check if a p tag exists (stores the rating text)
				var para_element = container_js.getElementsByTagName('p');	
				if (!para_element.length)
				{
					var parElement=document.createElement('p');
					var text = document.createTextNode(fp.ratingTextArray[i]);
					parElement.appendChild(text);
					container_js.appendChild(parElement);
				}else
				{
					// Loop through paragraph node deleting children (deletes current text, ready for adding new stuff)
					while (para_element[0].firstChild) 
					{
						para_element[0].removeChild(para_element[0].firstChild);
					}
					var text = document.createTextNode(fp.ratingTextArray[i]);
					para_element[0].appendChild(text);
				}
				
				// Set hidden form field for rating to rating number
				ratingContainer.value=i+1;
				// Set i to img_element.length (stops loop)
				i = img_element.length;
			}else
			{
				// Set star to 'active' image
				img_element[i].setAttribute('src',fp.fullStarSRC);
			}
		}
	},

	// Activate rating stars
	setRating:function()
	{	
		// Get parent
		var container_js = document.getElementById(fp.ratingContainer);
		// Get img elements
		var img_element = container_js.getElementsByTagName('img');	
		// Run loop setting the img src (loop argument is based on value of the forms ratinginputID (hidden field)
		for(var i=0; i<fp.rating; i++)
		{
			// Set star to 'active' image
			img_element[i].setAttribute('src',fp.fullStarSRC);
		}
	},
	// ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Product rating

	/************************************* helper methods ********************************************************/
	addEvent: function(elm, evType, fn, useCapture)
	{
		if (elm.addEventListener) 
		{
			elm.addEventListener(evType, fn, useCapture);
			return true;
		} else if (elm.attachEvent) {
			var r = elm.attachEvent('on' + evType, fn);
			return r;
		} else {
			elm['on' + evType] = fn;
		}
	},
	
	// cssjs mthod that adds, removes or swaps classes
	// see http://www.onlinetools.org/articles/unobtrusivejavascript/cssjsseparation.html
	cssjs:function(a,o,c1,c2)
	{
		switch (a)
		{
			case 'swap':
				o.className=!fp.cssjs('check',o,c1)?o.className.replace(c2,c1):o.className.replace(c1,c2);
			break;
			case 'add':
				if(!fp.cssjs('check',o,c1)){o.className+=o.className?' '+c1:c1;}
			break;
			case 'remove':
				var rep=o.className.match(' '+c1)?' '+c1:c1;
				o.className=o.className.replace(rep,'');
			break;
			case 'check':
				return new RegExp("(^|\\s)" + c1 + "(\\s|$)").test(o.className)
			break;
		}
	},
	// Use cancelClick method to cancel 'event bubbling' and default actions associated to elements
	cancelClick:function(e)
	{
		if (window.event)
		{
			window.event.cancelBubble = true;
			window.event.returnValue = false;
			return;
		}
		if (e)
		{
			e.stopPropagation();
			e.preventDefault();
		}
	},
	// New getTargetFunction (http://lists.evolt.org/archive/Week-of-Mon-20060717/183797.html)
	getTarget:function(e)
	{
		var target = window.event ? window.event.srcElement : e ? e.target : null;
		if (!target){return false;}
		while(target.nodeType!=1 && target.nodeName.toLowerCase()!='body')
		{
			target=target.parentNode;
		}
		return target;
	},
	
	fixSafari:function(node)
	{
//		node.onclick = function() { return false; }; // Safari
	}
}
// addEvent is a method used to sort of stack functions up after the page has loaded.
// On this page this method is watching the window and waiting till its loaded.
// After which the fp.init object is initialized
fp.addEvent(window, 'load', fp.init, false);