var Viewport =
{
    windowWidth: function() { return (document.documentElement && document.documentElement.clientWidth) || window.innerWidth || self.innerWidth || document.body.clientWidth },
    
    windowHeight: function()
                 {
                    if (self.innerHeight) // all except Explorer
                    {
	                    return self.innerHeight;
                    }
                    else if (document.documentElement && document.documentElement.clientHeight)
	                    // Explorer 6 Strict Mode
                    {
	                    return document.documentElement.clientHeight;
                    }
                    else if (document.body) // other Explorers
                    {
	                    return document.body.clientHeight;
                    }
                 },
    scrollX: function() 
                { 
                    if (self.pageYOffset) // all except Explorer
                    {
	                    return self.pageXOffset;
                    }
                    else if (document.documentElement && document.documentElement.scrollTop)
	                    // Explorer 6 Strict
                    {
	                    return document.documentElement.scrollLeft;
                    }
                    else if (document.body) // all other Explorers
                    {
	                    return document.body.scrollLeft;
                    }
                },
    scrollY: function() 
                { 
                    if (self.pageYOffset) // all except Explorer
                    {
	                    return self.pageYOffset;
                    }
                    else if (document.documentElement && document.documentElement.scrollTop)
	                    // Explorer 6 Strict
                    {
	                    return document.documentElement.scrollTop;
                    }
                    else if (document.body) // all other Explorers
                    {
	                    return document.body.scrollTop;
                    }
                },
    pageWidth: function() { return (document.documentElement && document.documentElement.scrollWidth) ? document.documentElement.scrollWidth : (document.body.scrollWidth > document.body.offsetWidth) ? document.body.scrollWidth : document.body.offsetWidth },
    pageHeight: function() { return (document.documentElement && document.documentElement.scrollHeight) ? document.documentElement.scrollHeight : (document.body.scrollHeight > document.body.offsetHeight) ? document.body.scrollHeight : document.body.offsetHeight }
}

function handleInputFocus(input)
{
	if ($(input).hasClass('enteredInput'))
	{
		return;
	}

	$(input).removeClass('unenteredInput');
	$(input).addClass('enteredInput');
	$(input).value = '';
}

function disableButton(id)
{
	$(id).addClass('disabledButton');
	$(id).title = "";
	$(id).onclick = function() { };
}

function handleCommentChange(id)
{
	if ($('submitComment' + id).hasShown != true)
	{
		$('submitComment' + id).hasShown = true;
		showContainer($('submitComment' + id));
	}
}

function showCommentEntry(id)
{	
	if ($('commentInput' + id).hasShown == true)
	{
		return;
	}
	$('commentInput' + id).hasShown = true;
	
	var startingWindowScrollY = Viewport.scrollY();
	
	showContainer($('commentInput' + id),
				  TrimPath.processDOMTemplate("comment_entry_form", { entry_id: id } ),
				  0,
				  function() 
					{ 
						// scroll to the the entry if the user hasn't already started scrolling
						if (startingWindowScrollY == Viewport.scrollY())
						{
							positionEntry(id); 
						}
					});
	
	disableButton('showCommentEntryButton' + id);
}

function showComments(entry_id)
{
	var jSonRequest = new Json.Remote("./ajax/getComments.php", { 
		onComplete: function(result) 
			{
				if ($('commentDisplay' + entry_id).innerHTML.trim() == "")
				{
					showContainer($('commentDisplay' + entry_id),
								  formatComments(result),
								  0);
				}
				else
				{
					moveAndFadeToHtml($('commentDisplay' + entry_id), 
									  $('commentDisplay' + entry_id), 
									  formatComments(result));
				}
				showCommentEntry(entry_id);								
			},
		onFailure: function(error)
			{
				alert("Remote Call Failed: " + error);
			}
		}).send( { 'entry_id': parseInt(entry_id) });
	disableButton('showCommentsButton' + entry_id);
}

function positionEntry(entry_id)
{
	// show the bottom of the entry - but if the whole entry will fit in the window,
	// show the top of the entry at the top of the window.
	// if the whole entry is already in the window, do nothing
	
	var entry = $('entry' + entry_id);
	var entryTop = entry.getTop();
	var entryHeight = entry.getSize().size.y;
	
	var windowHeight = Viewport.windowHeight();
	var scrollY = Viewport.scrollY();
	
	if ((entryTop >= scrollY) && (entryTop + entryHeight <= scrollY + windowHeight))
	{
		// already in view! do nothing!
		return;
	}
	else if (entryTop + entryHeight > scrollY + windowHeight)
	{
		getScroller().scrollTo(0, entryTop + entryHeight - windowHeight);
	}
}

function scrollToHeight(element, height, onCompleteCallback)
{
	this.fx = new Fx.Style(element, 
						   'height', 
							{ 
								wait: false, 
								duration: 500, 
								transition: Fx.Transitions.Sine.easeInOut, 
								onComplete: onCompleteCallback
							});
	this.fx.start(height);
}

function fadeToOpacity(element, opacity, onCompleteCallback)
{
	this.fx = new Fx.Style(element, 
						   'opacity', 
							{ 
								wait: false, 
								duration: 500, 
								transition: Fx.Transitions.Sine.easeInOut, 
								onComplete: onCompleteCallback
							});
	this.fx.start(opacity);
}

function moveAndFadeToHtml(source, destination, html, oncomplete)
{
	var startingHeight = source.getSize().size.y - 1;
	var desiredWidth = source.getSize().size.x;

	var fx = new Fx.Styles(source, 
							{ 
								wait: false, 
								duration: 1000, 
								transition: Fx.Transitions.Sine.easeInOut, 
								onComplete: function() 
								{
									source.innerHTML = "";
									source.setStyle('opacity', '1');
									showContainer(destination, html, startingHeight, oncomplete);
								}
							});
	fx.start({ 'opacity': 0 });
}

function showContainer(parent, html, startingHeight, oncomplete)
{
	var fadeContainerElement = document.createElement('div');

	if (startingHeight == null)
	{
		startingHeight = 0;
	}

	if (html == null)
	{
		fadeContainerElement = parent;
		html = fadeContainerElement.innerHTML;
		fadeContainerElement.innerHTML = "";
	}
	else
	{
		$(parent).removeClass('cHidden');
	}
	
	$(fadeContainerElement).addClass('fadeContainer');
	$(fadeContainerElement).setStyle('height', startingHeight + 'px');
	$(fadeContainerElement).setStyle('opacity', '0');
	$(fadeContainerElement).removeClass('cHidden');
	
	var innerElement = document.createElement('div');
	$(innerElement).addClass('clearfix');
	$(innerElement).innerHTML = html;
	$(fadeContainerElement).appendChild(innerElement);
	
	if (parent != fadeContainerElement)
	{
		parent.appendChild(fadeContainerElement);
	}

	var desiredHeight = innerElement.getSize().size.y - 1;
	var desiredWidth = $(innerElement).getSize().size.x;
			
	scrollToHeight(fadeContainerElement, desiredHeight, 
		function() { 
			$(fadeContainerElement).setStyle('opacity', '0');
			$(fadeContainerElement).setStyle('height', 'auto');
			
			var fx = new Fx.Styles(fadeContainerElement, 
									{ 
										wait: false, 
										duration: 1000, 
										transition: Fx.Transitions.Sine.easeInOut, 
										onComplete: function() 
										{
											if (oncomplete != null)
											{
												oncomplete();
											}
										}
									});
			fx.start({ 'opacity': 1 });
		});
}

function submitComment(entry_id)
{
	var jSonRequest = new Json.Remote("./ajax/submitComment.php", { 
		onComplete: function(result) 
			{
				$('commentInput' + entry_id).hasShown = false;
				
				moveAndFadeToHtml($('commentInput' + entry_id), 
								  $('commentDisplay' + entry_id), 
								  formatComments(result),
								  function() 
									{
										if ($('commentCount' + entry_id) != null)
										{
											$('commentCount' + entry_id).innerHTML = parseInt($('commentCount' + entry_id).innerHTML) + 1;
										}
										showCommentEntry(entry_id);
									});
			},
		onFailure: function(error)
			{
				alert("Remote Call Failed: " + error);
			}
		}).send( { 'author': $('commentAuthor' + entry_id).value, 'body': $('commentBody' + entry_id).value, 'entry_id': parseInt(entry_id) });
}

function formatComments(comments)
{
	var result = "";
	for (var i = 0; i < comments.length; i++)
	{
		result += TrimPath.processDOMTemplate("comment_display", { 
					author: comments[i].author, 
					date: comments[i].date, 
					body: comments[i].body });
	}
	return result;
}

var windowScroller = null;
function getScroller()
{
	if (windowScroller == null)
	{
		windowScroller = new Fx.Scroll(window, { wait: false,
		duration: 500,
		transition: Fx.Transitions.Quad.easeInOut });
	}
	return windowScroller;
}