/**
* @fileoverview
* This script will automatically style special tooltips and balloon callouts for links on the page. 
*
* Documentation: http://webdev.paypal.com/standards/code-library/interface-elements/tooltips-and-balloon-callouts
*
* TOOLTIPS:
* A tooltip is a simple bit of text that is displayed in a balloon when the user hovers over the link
* to explain it's purpose.  THIS CAN ONLY BE USED ON LINKS WHICH HAVE A VALID URL IN THE HREF AND GO SOMEWHERE.
*
* Implementation: Sdd the class "autoTooltip" and put the balloon content in the title attribute:
*
*	<a href="foo.html" title="Hello World" class="autoTooltip">My First Tooltip</a>
*
* BALLOON CALLOUTS:
* These are more complex balloons which can contain markup.
*
* Implementation: 
*	+ Create a link with the class "balloonControl"
*	+ Create a div with the class "balloonCallout" and a unique ID
*	+ Add the balloon content to the div
*	+ Add the div's ID to the link's href attribute
*
*	<a href="#myBalloonContent" class="balloonControl">Show panel1</a> 
*
*	<div id="myBalloonContent" class="balloonCallout">
*		<h4>The Porterhouse</h4>
*		<p>
*			This is the king of steaks-two steaks in one actually. Cut from the hip end of the short loin, our dry-aged Porterhouse contains a full portion of the shell, or strip, and a hearty portion of the filet, separated by the characteristic T-shaped bone.
*			Porterhose steak is best grilled, pan-seared, or pan-roasted.
*		</p>
*		<p>
*			<a href="#" id="calltoaction">See all steaks</a>
*		</p>
*	</div>
*
* @requires YAHOO.util.Dom, YAHOO.util.Event, YAHOO.util.Panel
*/


PAYPAL.namespace("widget");

/**
 * Automatically go through the anchors on the page to add a
 * stylized look to the tooltips and balloon callouts.
 */
PAYPAL.widget.Balloons = {
	
	pageLoaded : false,
		
	/**
	* Initializes object and anchors on the page
	*/
	init : function(){
		YAHOO.widget.Module.CSS_HEADER = "header";
		YAHOO.widget.Module.CSS_BODY = "body";
		YAHOO.widget.Module.CSS_FOOTER = "footer";
		
		var lastBalloon = null;
		
		// Tooltips
		var tooltips = YAHOO.util.Dom.getElementsByClassName("autoTooltip", null, document);
		for(var i = 0; i < tooltips.length; i++){
			var id = "autoTooltip"+ i;
			var anchor = tooltips[i];
			
			// Construct balloon with the title content
			var content = anchor.getAttribute("title");
			lastBalloon = this._initBalloon(anchor, id, content);
			anchor.removeAttribute("title");
		}
		
		// Balloon Callouts
		var targets = YAHOO.util.Dom.getElementsByClassName("balloonControl", "a", document);
		for(var i = 0; i < targets.length; i++){
			var id = targets[i].href;
			
			if(id.indexOf("#") > -1){
				var panelId = id.split("#")[1];
				
				// Extract div content
				var callout = document.getElementById(panelId);
				var content = callout.innerHTML;
				
				// Legacy -- remove the body <div>
				var child = callout.firstChild;
				while(child){
					if(child.nodeName == "DIV" && YAHOO.util.Dom.hasClass(child, "body")){
						content = child.innerHTML
						break;
					}
					child = child.nextSibling;
				}
				
				// Empty div and construct balloon				
				callout.innerHTML = "";
				YAHOO.util.Dom.removeClass(callout, "accessAid");
				lastBalloon = this._initBalloon(targets[i], panelId, content);
				
			}
		}
		
		// Preload arrow images
		if(lastBalloon != null){
			lastBalloon = lastBalloon.body.parentNode;
			
			var img, cssClass;
			var arrows = ["posUnder", "posOver"];
			
			for(var i = 0; i < arrows.length; i++){
				cssClass = arrows[i];
				arrows[i] = new Image();
				
				// Add class and then get the arrow background image and preload it
				YAHOO.util.Dom.addClass(lastBalloon, cssClass);
				img = YAHOO.util.Dom.getStyle(lastBalloon, "backgroundImage");
				if(img = img.match(/url\(([^\)]*)\)/) ){
					arrows[i].src = img[1];
				}
				
				YAHOO.util.Dom.removeClass(lastBalloon, cssClass);
			}
		}
	},
	
	/**
	* Create a single balloon.  
	* This method is called from the main init method.
	* @param {DomNode} target The target element that opens the balloon.
	* @param {String} id The ID of the div the balloon should be created in.
	* @param {String} content The content (HTML and/or text) that goes in the balloon
	*/
	_initBalloon : function(target, id, content){
		
		// Instantiate the Panel  
		var callout = new YAHOO.widget.Panel(id, {	close: false, 
													visible: false, 
													zIndex: 17, 
													underlay: "none",
													draggable: false } );
		callout._target = target;
		callout.beforeShowEvent.subscribe(this.positionBalloon, callout, true);
		callout.setBody(content);
		callout.render(document.body);
		YAHOO.util.Dom.addClass(callout.element, "balloon");
		
		// Adding the listeners to the html elements
		YAHOO.util.Event.addListener([target, callout.element], "mouseover", callout.show, callout, true);
		YAHOO.util.Event.addListener([target, callout.element], "mouseout", function(evt){
			var evTarget = YAHOO.util.Event.getTarget(evt);
			
			// Mouse is still in target or balloon
			var related = YAHOO.util.Event.getRelatedTarget(evt);
			if(related == target || YAHOO.util.Dom.isAncestor(callout.element, related)){
				return;
			}
		
			//
			// Is mouse in between the target and balloon
			//
			var point = new YAHOO.util.Point(YAHOO.util.Event.getXY(evt));
			var targetReg = YAHOO.util.Region.getRegion(target);
			var balloonReg = YAHOO.util.Region.getRegion(callout.body);
			
			// Bottom balloon
			if(balloonReg.top > targetReg.top
				&& point.left > targetReg.left && point.right < targetReg.right && point.top > targetReg.top){
				return;
			}
			
			// Top balloon
			else if(balloonReg.top < targetReg.top 
				&& point.left > targetReg.left && point.right < targetReg.right && point.top < targetReg.bottom){
				return;	
			}
			
			// If we got this far, the cursor is out of the target and balloon
			callout.hide();
		
		}, this, true);
		
		// Hide/Show balloon with keyboard navigation
		YAHOO.util.Event.addListener(target, "focus", callout.show, callout, true);
		YAHOO.util.Event.addListener(target, "blur", callout.hide, callout, true);
		
		return callout;
	},
	
	/**
	 * Sets the position static to the context element and
	 * adds the posOver/posUnder class to the panel
	 * @param {String} type The custom event type 'onShow'
	 * @param {Array} args Custom event fire args
	 */
	positionBalloon : function(type, args, balloons){
		var balloon = this.element;
		var callout = this.body.parentNode;
		var context = this._target;
		var nav = document.getElementById("navPrimary");
		
		var viewport = PAYPAL.widget.Balloons.getViewportRegion();
		var contextRegion = YAHOO.util.Region.getRegion(context);
		var navRegion = (nav) ? YAHOO.util.Region.getRegion(nav) : null;
		
		YAHOO.util.Dom.removeClass(callout, "accessAid");
		
		// Default to bottom
		var top = contextRegion.top + context.offsetHeight;
		YAHOO.util.Dom.replaceClass(callout, "posOver", "posUnder");
		YAHOO.util.Dom.setY(callout, top);
		
		// Keep balloon in the viewport and under the nav
		if(contextRegion.bottom + balloon.offsetHeight > viewport.bottom 
				&& contextRegion.top - balloon.offsetHeight > viewport.top 
				&& (!nav || contextRegion.top - callout.offsetHeight > navRegion.bottom)){
			
			// Place balloon over anchor
			YAHOO.util.Dom.replaceClass(callout, "posUnder", "posOver");
			YAHOO.util.Dom.setY(callout, contextRegion.top - callout.offsetHeight);
		}
		
		// Set static position relative to context
		YAHOO.util.Dom.setX(callout, YAHOO.util.Dom.getX(context) - 10);
	},
	
	/**
	* Gets you the viewport region
	*/
	getViewportRegion : function(){
		var scrollTop = Math.max(document.documentElement.scrollTop, document.body.scrollTop);
		var scrollLeft = Math.max(document.documentElement.scrollLeft, document.body.scrollLeft);

		return new YAHOO.util.Region(scrollTop, 
									YAHOO.util.Dom.getViewportWidth() + scrollLeft, 
									YAHOO.util.Dom.getViewportHeight() + scrollTop, 
									scrollLeft);
	},
	
	
	/**
	 * Progressively hide the balloons as the page loads.
	 */
	jsEnabled : function(){
		YAHOO.util.Event.addListener(window, "load", function(){ PAYPAL.widget.Balloons.pageLoaded = true });
		
		var i = 0;
		var hideInterval;
		function hideCallouts(){
			if(i > 0 && PAYPAL.widget.Balloons.pageLoaded){
				clearInterval(hideInterval);
				return false;
			}
			
			// Get balloon callouts
			YAHOO.util.Dom.getElementsBy(function(elem){
					// Add accessAid class
					if(YAHOO.util.Dom.hasClass(elem, "balloonCallout") && !YAHOO.util.Dom.hasClass(elem, "accessAid")){
						YAHOO.util.Dom.addClass(elem, "accessAid");
					}
					return false;
				});
		
			i++;
		}
		
		// Hide callouts as they load
		hideInterval = setInterval(hideCallouts, 50);
	}
	
}

PAYPAL.widget.Balloons.jsEnabled();
YAHOO.util.Event.addListener(window, "load", PAYPAL.widget.Balloons.init, PAYPAL.widget.Balloons, true);
