var PartyController = {
	SessionId : '',
	CurrentSecret : '',
	PreviousInfo : null,
	LeaveGame : false,
	StartGame : false,
	UpdatePollRef : null,
	
	UpdateInterval : 1500,

	Create : function(cmd, gameVersion, sameTeam)
	{
		if (!IsAvailable())
			return ShowUnavailableLightbox();

		cmd = GetCompleteSearchCommand(cmd, gameVersion);
		
		PartyController.Reset();
		
		// Show Waiting Screen
		$('PartyStatus').innerHTML = "Creating party...";
		$('PartyInformation').hide();
		$('PartyInGameConnectWarning').hide();
		ShowLightbox('PartyLightbox');
		
		var req = CreateAjaxRequest();
		req.onreadystatechange = function() {
			if (req.readyState != 4)
				return;
			
			var bits = req.responseText.split('\t');
			switch(bits[0]) {
				case 'ACK':
					PartyController.Join(bits[1]);
					break;
				default:
				case 'NAK':
					alert("Create party failed");
					break;
			}
		};

		req.open("POST", "/party.php?command=create&cmd=" + escape(cmd) + '&game=' + gameVersion + '&sameteam=' + (sameTeam ? 1 : 0) + '&cb=' + GetRandomNumber(), true);
		req.send(null);
	},
	
	CancelUpdate : function() {
		if (!PartyController.UpdatePollRef)
			return;

		window.clearTimeout(PartyController.UpdatePollRef);
		PartyController.UpdatePollRef = null;
	},
	
	Reset : function() {
		PartyController.CancelUpdate();

		PartyController.LeaveGame = false;
		PartyController.StartGame = false;
		PartyController.PreviousInfo = null;
		PartyController.SessionId = '';
		PartyController.CurrentSecret = '';

		$('PartyBusy').hide();
	},
	
	Start : function() {
		$('PartyStatus').innerHTML = "Starting the game...";
		$('PartyStatusStartButton').hide();
		$('PartyBusy').src = "/images/search.gif";
		$('PartyBusy').show();
		$('PartyInviteControls').hide();
		$('PartyInviteClosed').show();
		PartyController.StartGame = true;
	},

	Leave : function() {
		PartyController.LeaveGame = true;
		
		// Re-run our join logic which will pickup our leave request immediately
		PartyController.CancelUpdate();
		PartyController.Join(PartyController.CurrentSecret);
		
		HideLightbox();
	},
	
	ScheduleUpdate : function() {
		PartyController.UpdatePollRef = window.setTimeout('PartyController.Join("' + PartyController.CurrentSecret + '")', PartyController.UpdateInterval);
	},
	
	Join : function(secret) {
		PartyController.CurrentSecret = secret;
		
		if (PartyController.PreviousInfo == null) {
			$('PartyStatus').innerHTML = "Joining party...";
			$('PartyBusy').src = "/images/search.gif";
			$('PartyBusy').show();
			$('PartyInformation').hide();
			$('PartyInviteUrlContainer').hide();
			$('PartyLeaveButton').innerHTML = "Leave Party";
			ShowLightbox('PartyLightbox');
		}
		
		var partyStatus = $('PartyStatus');
		var req = CreateAjaxRequest();
		req.onreadystatechange = function() {
			if (req.readyState != 4)
				return;
			
			var bits = req.responseText.split('\t');
			switch(bits[0]) {
				case 'LEFT':
					// Successfully left the game
					PartyController.Reset();
					break;
				case 'STATUS':
					// STATUS State PlayerCount MaxPlayers IsHost SessionId Description
					var newInfo = {
						state: bits[1],
						playerCount: bits[2],
						maxPlayers: bits[3],
						isHost: bits[4] == 1,
						sessionId: bits[5],
						description: bits[6]
					};
					
					// Update party status
					var status;

					// Discard this response if we've just clicked 'Start Game' and have been mid update
					if (newInfo.state == 1 && PartyController.StartGame) {
						PartyController.ScheduleUpdate();
						return;
					}
					
					var shouldFocusInviteUrl = false;
					if (newInfo.state == 1) {
						// Open
						$('PartyStatusStartButton').style.display = newInfo.isHost && newInfo.playerCount > 1 ? 'block' : 'none';
						$('PartyStatusStartButtonDisabled').style.display = newInfo.isHost && newInfo.playerCount <= 1 ? 'block' : 'none';

						if (newInfo.isHost) {
							status = "Click Start when your friends have arrived and you are ready to play.";
							$('PartyBusy').hide();
							
							var partyInviteUrl = $('PartyInviteUrl');
							var inviteUrl = "http://www.play4dead.com/?party=" + secret;

							if (partyInviteUrl.value != inviteUrl) {
								shouldFocusInviteUrl = true;
								partyInviteUrl.value = inviteUrl;
							}

							// Copy link function only works under IE browsers due to security settings								
							if (Prototype.Browser.IE)
								$('PartyInviteUrlCopyLink').show();

							$('PartyInviteControls').show();
							$('PartyInviteClosed').hide();
							$('PartyInviteUrlContainer').show();
						} else {
							status = "Waiting for host to start the game.";
							$('PartyBusy').src = "/images/wait.gif";
							$('PartyBusy').show();
						}
					} else {
						// Closed / Searching
						$('PartyBusy').src = "/images/search.gif";
						$('PartyBusy').show();
						status = "Game started; searching for optimal game server...";
					}
					
					partyStatus.innerHTML = status;
					$('PartyStatusPlayerCount').innerHTML = newInfo.playerCount + ' player' + (newInfo.playerCount == 1 ? '' : 's') + ' (' + newInfo.maxPlayers + ' max)';
					$('PartyStatusDescription').innerHTML = newInfo.description;
					
					if (PartyController.PreviousInfo == null) {
						$('PartyInformation').show();
					} else {
						// Has a player just joined/left?
						if (PartyController.PreviousInfo.playerCount != newInfo.playerCount) {
							new Effect.Highlight('PartyStatusPlayerCount', { startcolor: '#99CCFF', endcolor: '#ffffff' });
							PlaySound('join');
						}
					}

					PartyController.PreviousInfo = newInfo;
					PartyController.SessionId = newInfo.sessionId;

					if (shouldFocusInviteUrl) {
						partyInviteUrl.focus();
						partyInviteUrl.select();
					}
					
					// Schedule another party update in a moment
					PartyController.ScheduleUpdate();
					break;
				case 'START':
					if (PartyController.LeaveGame)
						return;

					// Connecting to server
					// START Description ConnectUrl
					partyStatus.innerHTML = 'Connecting to ' + bits[1];
					$('PartyBusy').src = "/images/search.gif";
					$('PartyBusy').show();
					$('PartyLeaveButton').innerHTML = "Close Window";

					if (ShowJoinRetryInfo())
						$('PartyInGameConnectWarning').show();

					JoinServerAndUpdateUI(bits[2]);
					break;
				case 'NAK':
					// Failed to join party
					// NAK ErrorCode
					$('PartyStatus').innerHTML = "Sorry, failed to join party: " + bits[1];
					window.setTimeout('PartyController.Leave()', 3000);
					break;
				default:
					alert("An unknown error occurred during this party session");
					break;
			}
		};
		
		if (PartyController.LeaveGame)
			req.open("POST", "/party.php?command=leave&secret=" + escape(secret) + "&sid=" + escape(PartyController.SessionId) + '&cb=' + GetRandomNumber());
		else
			req.open("POST", "/party.php?command=join&secret=" + escape(secret) + "&sid=" + escape(PartyController.SessionId) + "&start=" + (PartyController.StartGame ? 1 : 0) + '&cb=' + GetRandomNumber());

		req.send(null);
	}
};
