/* Start Positions */
/* ---------------------------------------------------------------------- */
var ballStartX = 439;
var ballStartY = 190;
var playerTwoX = 864;
var playerTwoY = 165;
var playerOneX = 23;
var playerOneY = 165;

/* Grid Deminsions */
/* ---------------------------------------------------------------------- */
var gridHeight = 0;
var gridWidth = 0;
var gridMaxLeft = 0;
var gridMaxRight = 0;
var gridMaxTop = 0;

/* Object Deminsions */
/* ---------------------------------------------------------------------- */
var ballSize = 34;
var paddleWidth= 26;
var paddleHeight = 128;

/* Miscellaneous */
/* ---------------------------------------------------------------------- */
var playingGame, username, ballAng, speed, ping, pong, wallPong, mouseSpeed, mousePrevY, gameScore, isPaused, ballMov;
var frameRate = 10;
var startGameTimer = 5;
var ballFade = false;
var comments = Array('Meh.', 'Not bad.', 'Good job.', 'Excellent!', 'OMG.');
var usernameDefault = 'Player Name';

var prevX = null;
var prevOneY = null;
var prevTwoY = null;


/* Set Defaults */
/* ---------------------------------------------------------------------- */
// Reset at the end of each game
/* ---------------------------------------------------------------------- */

function setDefaults() {
	ballAng = 180; // angle the ball is currently moves, this starts out at 180
	speed = 10; // ai speed
	ping = 10; // game speed, when pong reaches 5, ping increments by 1
	pong = 0; // incremented on each successive volley
	wallPong = 0; // counts the number of times the ball has hit a wall, the angle will adjust if the ball hits the wall too much
	mouseSpeed = 0;
	mousePrevY = 0;
	gameScore = 0;
	isPaused = false;
	ballMov = Array(-8,0);
}


/* Set GRID */
/* ---------------------------------------------------------------------- */
// Re-aligns the background grid so it lines up with the logo and paddles
// Resize the top margin of the grid to resize for browser height
/* ---------------------------------------------------------------------- */

function setGrid() { 

	bodyHeight = document.viewport.getDimensions().height;	
	$('body').style.marginTop = ((bodyHeight-535)/2)+'px';
	
	$('grid').style.backgroundPosition = $('court').cumulativeOffset().left+'px 0px';

	gridHeight = $('grid').getDimensions().height;
	gridWidth = document.body.getDimensions().width;
	gridMaxLeft = -$('court').cumulativeOffset().left;
	gridMaxTop = $('grid').cumulativeOffset().top;
	gridMaxRight = gridWidth;
}


/* Set Overlay */
/* ---------------------------------------------------------------------- */
// Shows and hides the black backdrop on site load and game end
/* ---------------------------------------------------------------------- */

function setOverlay(status) {
	
	// Show Overlay
	if(status == 1) {

		$('body').style.backgroundColor = '#252525';
		$('bttm').style.color = '#fff';
		$('logo').select('a')[0].style.backgroundImage = 'url(images/logo_overlay.gif)';
		$('score').style.display = 'none';
		$('overlay').style.display = 'block';
		$('hint').innerHTML = '';
	
		items = $('bttm').select('a');
		for (x=0; x<items.length; x++)
		{
			items[x].style.color = '#fff';
		}
	
	// Hide Overlay	
	} else {

		$('body').style.backgroundColor = '#fff';
		$('bttm').style.color = '#999';
		$('logo').select('a')[0].style.backgroundImage = 'url(images/logo.gif)';
		$('score').style.display = 'block';
		$('overlay').fade();
		$('hint').innerHTML = 'Playing as '+username;
	
		items = $('bttm').select('a');
		for (x=0; x<items.length; x++)
		{
			items[x].style.color = '#999';
		}
	}
}


/* Set Sign In */
/* ---------------------------------------------------------------------- */
// Shows and hides the initial sign in on site load
/* ---------------------------------------------------------------------- */

function setSignIn(status) {
	
	// Show Sign In
	if(status == 1) {
	
		$('welcome').appear();
	
		$('username_input').value = usernameDefault;
	
		Event.observe($('username_input'), 'focus', function(){
		if($('username_input').value == usernameDefault)
			$('username_input').value = '';
		});
	
		Event.observe($('username_input'), 'blur', function(){
			if($('username_input').value == '')
				$('username_input').value = usernameDefault;
		});
		
		// Stop Preview and Start Game when user clicks here
		Event.observe($('signin'), 'submit', function(){
			if($('username_input').value == usernameDefault || $('username_input').value == '')
				$('signin').shake();
			else {
				username = $('username_input').value;
				stopPreview();
				setOverlay(0);
				setSignIn(0);
				startGame();
			}
		});
	
		$('signin').onsubmit = function(){return false;};
	
	// Hide Sign In
	} else {
		$('welcome').fade(); 
	}
}

// Email Validation
function validateMail(email) {
	var reg = /^([A-Za-z0-9_\-\.])+\@([A-Za-z0-9_\-\.])+\.([A-Za-z]{2,4})$/;
	if(reg.test(email) == false)
		return false;
	else
		return true;
}


/* Set Court */
/* ---------------------------------------------------------------------- */

function setCourt() {
	$('score_current').innerHTML = gameScore;
	
	$('ball').style.left = ballStartX+'px';
	$('ball').style.top = ballStartY+'px';
	$('playerOne').style.left = playerOneX+'px';
	$('playerOne').style.top = playerOneY+'px';
	$('playerTwo').style.left = playerTwoX+'px';
	$('playerTwo').style.top = playerTwoY+'px';
}


/* Start Preview */
/* ---------------------------------------------------------------------- */

function startPreview() {

	setCourt();
	setDefaults();
	previewingGame = setInterval("previewGame();", frameRate);
}


/* Stop Preview */
/* ---------------------------------------------------------------------- */

function stopPreview() {
	
	clearInterval(previewingGame);
}


/* Start Game */
/* ---------------------------------------------------------------------- */

function startGame(i) {

	if(i == null)
	{	
		setCourt();
		i = startGameTimer;
		Event.observe($('grid'), 'mousemove', movePaddle);
		$('ball').innerHTML = startGameTimer;
	}
	
	if(i > 0) {	
		$('ball').innerHTML = i;
		i--;
		setTimeout("startGame("+i+")",1000);
	} else {

		$('ball').innerHTML = '';
		setDefaults();
		if(playingGame)
			clearInterval(playingGame);
			
		calcMov( $('ball'), ballAng, ping);	
		playingGame = setInterval("playGame();", frameRate);
		Event.observe($('grid'), 'click', pauseGame);
	}
}


/* Stop Game */
/* ---------------------------------------------------------------------- */

function stopGame() {

	if(playingGame)
		clearInterval(playingGame);
		
	setCourt();
	saveScore();
	
	$('finished').appear();
	$('finished_score').innerHTML = gameScore;
	setOverlay(1);
	
	if(gameScore < 10)
		$('finished_comment').innerHTML = comments[0];
	else if(gameScore >= 10 && gameScore < 30)
		$('finished_comment').innerHTML = comments[1];
	else if(gameScore >= 30 && gameScore < 70)
		$('finished_comment').innerHTML = comments[2];
	else if(gameScore >= 70 && gameScore < 120)
		$('finished_comment').innerHTML = comments[3];
	else if(gameScore > 120)
		$('finished_comment').innerHTML = comments[4];
	
	Event.observe($('finished_again'), 'click', function(){
		$('finished').fade();
		setOverlay(0);
		startGame(null);
	});
}


/* Pause Game */
/* ---------------------------------------------------------------------- */

function pauseGame() {
	
	if(isPaused == false) {
		Event.stopObserving(window, 'mousemove', movePaddle);
		clearInterval(playingGame);
		isPaused = true;
	} else {
		Event.observe(window, 'mousemove', movePaddle);
		playingGame = setInterval("playGame();", frameRate);
		isPaused = false;
	}
}


/* Save Score */
/* ---------------------------------------------------------------------- */

function saveScore() {
	
	if(gameScore > $('score_best').innerHTML)
		$('score_best').innerHTML = gameScore;
}


/* Update Score */
/* ---------------------------------------------------------------------- */

function updateScore() {

	gameScore++;
	$('score_current').innerHTML = gameScore;
}


/* Play Game */
/* ---------------------------------------------------------------------- */

function playGame() {

	var ballX = parseInt($('ball').style.left);
	var ballY = parseInt($('ball').style.top);
	var playerOneX = parseInt( $('playerOne').style.left );
	var playerOneY = parseInt( $('playerOne').style.top );
	var playerTwoX = parseInt( $('playerTwo').style.left );
	var playerTwoY = parseInt( $('playerTwo').style.top );
	
	// Bounce off PlayerOne
	if( ballY >= (playerOneY - ballSize) && ballY <= (playerOneY + paddleHeight + ballSize) && ballX >= playerOneX && ballX <= (playerOneX + paddleWidth) ) {
		
		if( pong == 5 ) {
			ping++;
			pong = 0;
		} else {
			pong++;
		}

		$('ball').style.left = playerOneX+ballSize + "px";
		
		if(prevOneY == ballY)
			ballAng = ballAng + 5;
		else
			ballAng = 180 - ballAng - mouseSpeed;
		
		prevOneY = ballY;
		wallPong = 0;
		
		updateScore();
		
		calcMov( $('ball'), ballAng, ping);
		
	// Bounce off PlayerTwo
	} else if( ballY >= (playerTwoY - ballSize) && ballY <= (playerTwoY + paddleHeight + ballSize) && ballX+ballSize >= playerTwoX && ballX <= (playerTwoX + paddleWidth) ) {
		
		if( pong == 5 ) {
			ping++;
			pong = 0;
		} else {
			pong++;
		}

		$('ball').style.left = playerTwoX-ballSize + "px";
		
		
		if(prevTwoY == ballY)
			ballAng = ballAng + 5;
		else
			ballAng = 180 - ballAng;
		prevTwoY = ballY;
		wallPong = 0;
		
		updateScore();
		
		calcMov( $('ball'), ballAng, ping);
	}

	// Bounce off wall
	if( ballY <= 0 || ballY >= gridHeight-ballSize ) {
	
		$('ball').style.top = (ballY <= 0)?0+"px":(gridHeight-ballSize)+"px";
		if(prevX == ballX)
			ballAng = ballAng - 5;
		else
			ballAng = 360 - ballAng - wallPong;
			
		wallPong = wallPong - 2;
		
		calcMov( $('ball'), ballAng, ping);
	}
	
	// Fix angle
	if(ballAng > 360)
		ballAng = ballAng-360
	else if(ballAng < 0)
		ballAng = ballAng+360

	// Move AI depending on direction
	moveAI( $('playerTwo'), ballY );
	
	// Move the ball
	moveBall( $('ball'), ballAng, ping);
	
	// Save previous ball coordinates
	prevX = ballX
	
	//if( (ballX < 0 || ballX > gridWidth) && !ballFade )
	//	ballFade = Effect.Fade('ball', { duration: .3, afterFinish: function(){stopGame();} });
	
	if( ballX < 0 || ballX > gridWidth )
		stopGame();
}


/* Preview Game */
/* ---------------------------------------------------------------------- */

function previewGame() {

	var ballX = parseInt($('ball').style.left);
	var ballY = parseInt($('ball').style.top);
	var playerOneX = parseInt( $('playerOne').style.left );
	var playerOneY = parseInt( $('playerOne').style.top );
	var playerTwoX = parseInt( $('playerTwo').style.left );
	var playerTwoY = parseInt( $('playerTwo').style.top );
	
	// Bounce off PlayerOne
	if( ballY >= (playerOneY - ballSize) && ballY <= (playerOneY + paddleHeight + ballSize) && ballX >= playerOneX && ballX <= (playerOneX + paddleWidth) ) {
		$('ball').style.left = playerOneX+ballSize + "px";
		
		if(prevOneY == ballY)
			ballAng = ballAng + 5;
		else
			ballAng = 180 - ballAng - mouseSpeed;
		
		prevOneY = ballY;
		wallPong = 0;
		
		calcMov( $('ball'), ballAng, ping);
	
	// Bounce off PlayerTwo
	}else if( ballY >= (playerTwoY - ballSize) && ballY <= (playerTwoY + paddleHeight + ballSize) && ballX+ballSize >= playerTwoX && ballX <= (playerTwoX + paddleWidth) ) {
		$('ball').style.left = playerTwoX-ballSize + "px";
		
		if(prevTwoY == ballY)
			ballAng = ballAng + 5;
		else
			ballAng = 180 - ballAng;
		prevTwoY = ballY;
		wallPong = 0;
		
		calcMov( $('ball'), ballAng, ping);
	}

	// Bounce off wall
	if( ballY <= 0 || ballY >= gridHeight-ballSize ) {
	
		$('ball').style.top = (ballY <= 0)?0+"px":(gridHeight-ballSize)+"px";
		if(prevX == ballX)
			ballAng = ballAng - 5;
		else
			ballAng = 360 - ballAng - wallPong;
			
		wallPong = wallPong - 2;
		
		calcMov( $('ball'), ballAng, ping);
	}
	
	// Fix angle
	if(ballAng > 360)
		ballAng = ballAng-360
	else if(ballAng < 0)
		ballAng = ballAng+360

	// Move AI depending on ball direction
	if(prevX-ballX < 0)
		moveAI( $('playerTwo'), ballY );
	else
		moveAI( $('playerOne'), ballY );
	
	// Move the ball
	moveBall( $('ball') );
	
	// Save previous ball coordinates
	prevX = ballX
}


/* Calculate Movement */
/* ---------------------------------------------------------------------- */

function calcMov( obj, ang, dist ) {

	ballMov[0] = ( dist * Math.cos( ang * (Math.PI/180) ) );
	ballMov[1]  = ( dist * Math.sin( ang * (Math.PI/180) ) );
}


/* Move Ball */
/* ---------------------------------------------------------------------- */

function moveBall( obj ) {
	with( obj.style ) {
		left = parseInt(left) + ballMov[0] + "px";
		top  = parseInt(top)  - ballMov[1] + "px";
	}
}


/* Move Paddle */
/* ---------------------------------------------------------------------- */

function movePaddle(e) {

	mouseY = Event.pointerY(e)-gridMaxTop;
	paddleTop = mouseY-paddleHeight/2;
	paddleBottom = mouseY+paddleHeight/2;
	if(paddleTop >= 10 && paddleBottom <= gridHeight-10) {
		$('playerOne').style.top = (paddleTop)+"px"
			
	} else if(paddleTop < 10) {
		$('playerOne').style.top = "10px"
			
	} else if(paddleBottom > gridHeight-10) {
		$('playerOne').style.top = (gridHeight-paddleHeight-10)+"px";
	}
		
	if( mousePrevY ) {
		mouseSpeed = Math.round((mouseY - mousePrevY) * 1.5);
		if( mouseSpeed == 0 ) mouseSpeed = 1;
	}
	mousePrevY = mouseY;
}


/* Move AI */
/* ---------------------------------------------------------------------- */

function moveAI( player, y ) {

	var AI = player;
	y = y - 10;
	y = parseInt(AI.style.top) + ((y - parseInt(AI.style.top)) / speed);
	if( y < 10 || y > gridHeight-paddleHeight-10 ) {
		if( y < 10 ) {
			y = 10;
		} else {
			y = gridHeight-paddleHeight-10;
		}
	}
	AI.style.top = y +"px";
}


/* On Load */
/* ---------------------------------------------------------------------- */

Event.observe(window, 'load', function() {
	setGrid();
	setDefaults();
	setSignIn(1);
	startPreview();
	
	// Score_Current Hint
	Event.observe($('score_current'), 'mouseover', function() {
		$('hint').style.display = 'none';
		$('hint').innerHTML = 'Your Current Score';
		$('hint').appear();
		$('score_current').style.color = '#000';
		$('score').style.color = '#ccc';
		$('hint').style.color = '#000';
	});
	
	Event.observe($('score_current'), 'mouseout', function() {
		$('hint').innerHTML = 'Playing as '+username;
		$('score_current').style.color = '';
		$('score').style.color = '';
		$('hint').style.color = '';
	});
	
	// Score_Best Hint
	Event.observe($('score_best'), 'mouseover', function() {
		$('hint').style.display = 'none';
		$('hint').innerHTML = 'Your Best Score';
		$('hint').appear();
		$('score_best').style.color = '#000';
		$('score').style.color = '#ccc';
		$('hint').style.color = '#000';
	});
	
	Event.observe($('score_best'), 'mouseout', function() {
		$('hint').innerHTML = 'Playing as '+username;
		$('score_best').style.color = '';
		$('score').style.color = '';
		$('hint').style.color = '';
	});
	
	// Score_Top Hint
	Event.observe($('score_top'), 'mouseover', function() {
		$('hint').style.display = 'none';
		$('hint').innerHTML = 'All Time Best Score';
		$('hint').appear();
		$('score_top').style.color = '#000';
		$('score').style.color = '#ccc';
		$('hint').style.color = '#000';
	});
	
	Event.observe($('score_top'), 'mouseout', function(){
		$('hint').innerHTML = 'Playing as '+username;
		$('score_top').style.color = '';
		$('score').style.color = '';
		$('hint').style.color = '';
	});
});


/* On Resize */
/* ---------------------------------------------------------------------- */

Event.observe(window, 'resize', function() { 
	setGrid();
});

