/*
* Copyright (c) 2006 Jonathan Weiss <jw@innerewut.de>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/


/* tooltip-0.2.js - Small tooltip library on top of Prototype
* by Jonathan Weiss <jw@innerewut.de> distributed under the BSD license.
*
* This tooltip library works in two modes. If it gets a valid DOM element
* or DOM id as an argument it uses this element as the tooltip. This
* element will be placed (and shown) near the mouse pointer when a trigger-
* element is moused-over.
* If it gets only a text as an argument instead of a DOM id or DOM element
* it will create a div with the classname 'tooltip' that holds the given text.
* This newly created div will be used as the tooltip. This is usefull if you
* want to use tooltip.js to create popups out of title attributes.
*
*
* Usage:
*   <script src="/javascripts/prototype.js" type="text/javascript"></script>
*   <script src="/javascripts/tooltip.js" type="text/javascript"></script>
*   <script type="text/javascript">
*     // with valid DOM id
*     var my_tooltip = new Tooltip('id_of_trigger_element', 'id_of_tooltip_to_show_element')
*
*     // with text
*     var my_other_tooltip = new Tooltip('id_of_trigger_element', 'a nice description')
*
*     // create popups for each element with a title attribute
*    Event.observe(window,"load",function() {
*      $$("*").findAll(function(node){
*        return node.getAttribute('title');
*      }).each(function(node){
*        new Tooltip(node,node.title);
*        node.removeAttribute("title");
*      });
*    });
*
*   </script>
*
* Now whenever you trigger a mouseOver on the `trigger` element, the tooltip element will
* be shown. On o mouseOut the tooltip disappears.
*
* Example:
*
*   <script src="/javascripts/prototype.js" type="text/javascript"></script>
*   <script src="/javascripts/scriptaculous.js" type="text/javascript"></script>
*   <script src="/javascripts/tooltip.js" type="text/javascript"></script>
*
*   <div id='tooltip' style="display:none; margin: 5px; background-color: red;">
*     Detail infos on product 1....<br />
*   </div>
*
*   <div id='product_1'>
*     This is product 1
*   </div>
*
*   <script type="text/javascript">
*     var my_tooltip = new Tooltip('product_1', 'tooltip')
*   </script>
*
* You can use my_tooltip.destroy() to remove the event observers and thereby the tooltip.
*/

var Tooltip = Class.create();
Tooltip.prototype = {
	initialize: function(element, tool_tip) {
		var options = Object.extend({
			default_css: false,
			margin: "0px",
			padding: "5px",
			backgroundColor: "#d6d6fc",
			min_distance_x: 5,
			min_distance_y: 5,
			delta_x: 0,
			delta_y: 0,
			zindex: 19
		}, arguments[2] || {});

		this.element      = $(element);

		this.options      = options;

		// use the supplied tooltip element or create our own div
		if($(tool_tip)) {
			this.tool_tip = $(tool_tip);
		} else {
			this.tool_tip = $(document.createElement("div"));
			document.body.appendChild(this.tool_tip);
			this.tool_tip.addClassName("tooltip");
			this.tool_tip.appendChild(document.createTextNode(tool_tip));
		}

		// hide the tool-tip by default
		this.tool_tip.hide();

		this.eventMouseOver = this.showTooltip.bindAsEventListener(this);
		this.eventMouseOut   = this.hideTooltip.bindAsEventListener(this);
		this.eventMouseMove  = this.moveTooltip.bindAsEventListener(this);

		this.registerEvents();
	},

	destroy: function() {
		Event.stopObserving(this.element, "mouseover", this.eventMouseOver);
		Event.stopObserving(this.element, "mouseout", this.eventMouseOut);
		Event.stopObserving(this.element, "mousemove", this.eventMouseMove);
	},

	registerEvents: function() {
		Event.observe(this.element, "mouseover", this.eventMouseOver);
		Event.observe(this.element, "mouseout", this.eventMouseOut);
		Event.observe(this.element, "mousemove", this.eventMouseMove);
	},
	
	tt_GetScrollY: function()
		{
			//return(window.pageYOffset || (tt_db ? (tt_db.scrollTop || 0) : 0));
		},

	moveTooltip: function(event){
		Event.stop(event);
		// get Mouse position
		var mouse_x = Event.pointerX(event);
		var mouse_y = Event.pointerY(event);

		// decide if wee need to switch sides for the tooltip
		var dimensions = Element.getDimensions( this.tool_tip );
		var element_width = dimensions.width;
		var element_height = dimensions.height;

		if ( (element_width + mouse_x) >= ( this.getWindowWidth() - this.options.min_distance_x) ){ // too big for X
			mouse_x = mouse_x - element_width;
			// apply min_distance to make sure that the mouse is not on the tool-tip
			mouse_x = mouse_x - this.options.min_distance_x;
		} else {
			mouse_x = mouse_x + this.options.min_distance_x;
		}
		
		if ( (element_height + mouse_y) >= ( this.getWindowHeight() + this.tt_GetScrollY() + this.options.min_distance_y) ){ // too big for Y
			mouse_y = this.getWindowHeight() + this.tt_GetScrollY() - this.options.min_distance_y - element_height;
		// apply min_distance to make sure that the mouse is not on the tool-tip
			mouse_y = mouse_y - this.options.min_distance_y;
		} else
		if ( (mouse_y - element_height) <=0 ){ // too big for Y
			mouse_y = mouse_y + element_height;
			// apply min_distance to make sure that the mouse is not on the tool-tip
			mouse_y = mouse_y + this.options.min_distance_y;
		}
		else {
			mouse_y = mouse_y + this.options.min_distance_y;
		}



		// now set the right styles
		this.setStyles(mouse_x, mouse_y);
	},


	showTooltip: function(event) {
		Event.stop(event);
		this.moveTooltip(event);
		new Element.show(this.tool_tip);
	},

	setStyles: function(x, y){
		// set the right styles to position the tool tip
		Element.setStyle(this.tool_tip, { position:'absolute',
		top:y + this.options.delta_y + "px",
		left:x + this.options.delta_x + "px",
		zindex:this.options.zindex
		});

		// apply default theme if wanted
		if (this.options.default_css){
			Element.setStyle(this.tool_tip, { margin:this.options.margin,
			padding:this.options.padding,
			backgroundColor:this.options.backgroundColor,
			zindex:this.options.zindex
			});
		}
	},

	hideTooltip: function(event){
		new Element.hide(this.tool_tip);
	},

	getWindowHeight: function(){
		var innerHeight;
		if (navigator.appVersion.indexOf('MSIE')>0) {
			innerHeight = document.body.clientHeight;
		} else {
			innerHeight = window.innerHeight;
		}
		return innerHeight;
	},

	getWindowWidth: function(){
		var innerWidth;
		if (navigator.appVersion.indexOf('MSIE')>0) {
			innerWidth = document.body.clientWidth;
		} else {
			innerWidth = window.innerWidth;
		}
		return innerWidth;
	}

}
