// set some default ajax handlers
handlers["success_old"] = handlers["success"];
handlers["success"] = function(request) {
    if (request.target)
    	handlers["success_old"](request);
    else {
    	if (request.responseText != 'false') {
//    		alert(request.responseText);
    		var parsed = JSON.parse(request.responseText);
    		if (parsed["error"])
    			alert(parsed["error"]);
    	}
    }
}

var game = {
	created: 0,
	zone_selection: 1,
	unit_selection: 2,
	skill_selection: 10,
	started: 20,
	ended: 30
}

var player_status = {
	not_ready: 0,
	units_selected: 1,
	skills_selected: 10,
	done: 30
}

/**
 * z-index: the higher, the more to the front
 * The z-indexes are as follows:
 * 		10: the tile image
 * 		20: grid image
 * 		40: highlight image
 * 		60: object
 * 		80: unit
 * 		100: unit/object stats
 */

// contains all the data for the game, runtime updates are merged into this array
var data = [];

// contains the ratio at which everything is drawn, if for example set to 0.5, everything will be at half size
if (!ratio)
	var ratio = 1;

var drag_selected = null;

// the list of units you can select
var unit_selection_list = [];

// whether or not to show the grid, can be toggled
var grid = false;

// keeps track of how long the game has been inactive, if too long, it will slow down requests and eventually stop requesting from the server
// the user can resume the game by clicking the "resume" button
var inactivity_counter = 0;

var settings = {
	// by how much the inactivity counter is divided to reflect in the re-request time
	inactivity_ratio: 120,
	// at which point the game is considered suspended
	inactivity_threshold: 15000
}

// anywhere on the page you release, the selected will be reset
document.onmouseup = function(e) {
	drag_selected = null;
}

// the initial load gets all the static information about the game
function load_static() {
	hide_information();
	$("unit_actions").style.display = "none";
	ajax({url:'game.php?action=static', success: function(response) {
		if (response.responseText != 'false') {
//			$("debug").innerHTML = response.responseText;
			var parsed = JSON.parse(response.responseText);
			if (parsed["error"])
				alert("An error occurred: " + parsed["error"]);
			else {
				data = JSON.parse(response.responseText);
				draw_interface_statistics();
				// for all but unit selection the map has to be drawn
				if (parsed["status"] != 2 || get_player_status() == 1)
					draw_map();
				else
					draw_unit_selection();
				draw_interface_players();
				// for the first two stages, draw the map zones
				if (data["status"] == 0 || data["status"] == 1)
					draw_zones();
				load_dynamic();
				load_log();
				draw_actions();
			}
		}
		else
			load_dynamic();
	}});
}

function get_player_status() {
	for (var player in data["players"]) {
		if (data["players"][player]["user"] == data["user"])
			return data["players"][player]["status"];
	}
	return 0;
}

function load_log() {
	// only do this if the game is still active
	if (inactivity_counter > settings.inactivity_threshold)
		draw_actions();
	else {
		ajax({url:"game.php?action=log", success: function(response) {
			if (response.responseText != 'false') {
				var parsed = JSON.parse(response.responseText);
				if (parsed["error"])
					alert(parsed["error"]);
				else {
					load_log_data(parsed);
				}
			}
			setTimeout("load_log()", 1000);
		}});
	}
}

function load_log_data(parsed) {
	for(var message in parsed) {
		// all messages generated by the system are set at player 0
		if (parsed[message]["player"] == 0)
			add_to_log(parsed[message]["timestamp"] + " <span class='important'>" + parsed[message]["message"] + "</span>");
		// negative player numbers are actions linked to the player
		else if (parsed[message]["player"] < 0) {
			var player_number = Math.abs(parsed[message]["player"]);
			for (var player in data["players"]) {
				if (data["players"][player]["id"] == player_number) {
					player_number = player;
					break;
				}
			}
			add_to_log(parsed[message]["timestamp"] + " <span class='player player" + player_number + "'>" + parsed[message]["message"] + "</span>");
		}
		else {
			var player_name = "Unknown";
			for (var player in data["players"]) {
				if (data["players"][player]["id"] == parsed[message]["player"]) {
					player_name = data["players"][player]["name"];
					break;
				}
			}
			add_to_log(parsed[message]["timestamp"] + " [<b>" + player_name + "</b>]: " + parsed[message]["message"]);
		}
	}
}


function add_to_log(message) {
	$("log_content").innerHTML += message + "<br/>";
	$("log_content").scrollTop = $("log_content").scrollHeight;
}

function load_dynamic() {
	// only do this if the game is still active
	if (inactivity_counter > settings.inactivity_threshold)
		draw_actions();
	else {
		ajax({url:"game.php?action=dynamic", success: function(response) {
			// no activity
			if (response.responseText == "[]")
				inactivity_counter++;
			else {
				if (response.responseText != 'false') {
		//			$("debug").innerHTML = response.responseText;
					var parsed = JSON.parse(response.responseText);
					if (parsed["error"])
						alert("An error occurred: " + parsed["error"]);
					else
						load_dynamic_data(parsed);
				}
			}
//			var inactivity = Math.floor(inactivity_counter / settings.inactivity_ratio);
//			setTimeout("load_dynamic()", 1000 * (inactivity == 0 ? 1 : inactivity));
			setTimeout("load_dynamic()", 1000);
		}});
	}
}

function load_dynamic_data(parsed) {
	var prev_state = data["status"];
	// update the data array
	data = merge(data, parsed);
	// if the update contained player information, redraw them
	if (parsed["players"])
		draw_interface_players();
	if (prev_state != data["status"]) {
		// if it's unit selection time and you haven't selected yet...
		if (parsed["status"] == game.unit_selection && get_player_status() < player_status.units_selected)
			draw_unit_selection();
		// the game is over
		if (prev_state == game.started)
			// do nothing, used to be an alert here, but got annoying tbh
			;
		// the previous stage was unit selection, but that has been reset (probably because someone left)
		else if (prev_state == game.unit_selection && parsed["status"] == game.created)
			draw_map();
	}
	// update the game status
	draw_interface_status();
	// only draw the units & objects if you actually have a map, this should be in all stages EXCEPT unit/skill selection when the player hasn't selected yet
	if ((parsed["status"] != game.unit_selection || data["players"][get_player_sequence()]["status"] >= player_status.units_selected) && (parsed["status"] != game.skill_selection || data["players"][get_player_sequence()]["status"] >= player_status.skills_selected)) {
		if (parsed["units"])
			draw_units();
		if (parsed["objects"])
			draw_objects();
		unhighlight();
		draw_unit_actions();
	}
	draw_actions();
	$("game_round").innerHTML = data["round"];
	$("game_turn").innerHTML = data["turn"];
}

function draw_unit_actions() {
	if (is_your_turn() && data["status"] != game.ended) {
		var html = "<h1>Unit Actions</h1><ul>" +
			"<li><input type='button' value='Defend' onclick='defend()'/></li>" +
			"<li><input type='button' value='Wait' onclick='wait()'/></li>" +
			"</ul>";
		$("unit_actions").innerHTML = html;
		$("unit_actions").style.display = "block";
	}
	else
		$("unit_actions").style.display = "none";
}

function send_log_if_necessary(event) {
	if (!event || event.keyCode == 13) { 
		ajax({url:"game.php?action=talk", method:"post", params:{"message": $("log_text").value}, success:function(response) {
			if (!response.reponseText != 'false') {
				var parsed = JSON.parse(response.responseText);
				if (parsed["error"])
					alert(parsed["error"]);
				else
					load_log_data(parsed);
			}
		}});
		$("log_text").value = "";
	}
}

function hide_information() {
	// hide the information window
	$("information").style.display = "none";
}

function show_information(info) {
	$("information").innerHTML = info;
	$("information").style.display = "block";
}

function merge(arr1, arr2) {
	for (var key in arr2)
		arr1[key] = arr2[key];
	return arr1;
}

function resume_game() {
	if (inactivity_counter > settings.inactivity_threshold) {
		inactivity_counter = 0;
		load_dynamic();
		load_log();
		draw_actions();
	}
}

function draw_actions() {
	// draw game statistics
	var html = "<h1>Actions</h1><ul>" +
			"<li><b>Zoom: </b><input type='text' size='3' value='" + Math.round(ratio * 100) + "' onchange='zoom_if_possible(this.value)'/>%</li>" +
			"<li><input type='button' value='Toggle Grid' onclick='toggle_grid()'/></li>";

	// offer a way to resume if you have been inactive too long
	if (inactivity_counter > settings.inactivity_threshold)
		html += "<li><b>Game is paused: </b><input type='button' value='Resume Game' onclick='resume_game()'/></li>";
	
	// offer way to get out of game while it is not in progress
	if (data["status"] != game.started)
		html += "<li><input type='button' value='Exit Game' onclick='stop()'/></li>";
	else
		html += "<li><input type='button' value='Forfeit Game' onclick='forfeit()'/></li>";
	
	// if we are at the zone placing stage
	if (data["status"] == game.zone_selection && data["owner"] == data["user"]) {
		// and all the players are assigned a zone
		var all_assigned = true;
		for (var player in data["players"]) {
			if (data["players"][player]["zone"] == -1) {
				all_assigned=false;
				break;
			}
		}
		if (all_assigned)
			html += "<li><b>Next stage: </b><input type='button' value='Unit Selection' onclick='start_unit_selection()'/></li>";
	}
	// if we are at the unit choosing stage..
	if (data["status"] == game.unit_selection && data["owner"] == data["user"]) {
		// and all players have chosen their units
		var all_chosen = true;
		for (var player in data["players"]) {
			if (data["players"][player]["status"] < player_status.units_selected) {
				all_chosen = false;
				break;
			}
		}
		if (all_chosen)
			html += "<li><b>Next stage: </b><input type='button' value='Start Game' onclick='start_game()'/></li>";
	}
	html += "</ul>";
	$("actions").innerHTML = html;
}

function start_unit_selection() {
	if (data["owner"] == data["user"])
		ajax({url: "game.php?action=start_unit_selection"});
}

function stop() {
	if (data["status"] != game.started) {
		// suspend the game refresh in case it's timed badly
		inactivity_counter = settings.inactivity_threshold + 1;
		
		// process the stop request
		ajax({url: "game.php?action=stop", success:function(response) {
	    	// reload the page
	    	reload();
		}});
	}
}

function forfeit() {
	if (data["status"] == game.started) {
		// process the forfeit request
		ajax({url: "game.php?action=forfeit", success:function(response) {
			if (!response.reponseText != 'false') {
				var parsed = JSON.parse(response.responseText);
				if (parsed["error"])
					alert(parsed["error"]);
				else
					load_dynamic_data(parsed);
			}
		}});
	}	
}

function reload() {
	window.location.reload(true);
}

function zoom_if_possible(zoom) {
	zoom = parseInt(zoom);
	if (zoom && !isNaN(zoom)) {
		if (zoom < 1000 && zoom > 0) {
			ratio = zoom / 100;
			draw_map();
			if (data["status"] <= game.zone_selection)
				draw_zones();
			draw_objects();
			draw_units();
			highlight_active();
			// toggle twice to redraw hehe
			toggle_grid();
			toggle_grid();
		}
	}
}

function draw_interface_status() {
	if (data["status"] == game.created) {
		$("game_status").innerHTML = "Waiting for players to join...";
		document.title = "Nabu: Waiting for players to join...";
	}
	else if (data["status"] == game.zone_selection) {
		$("game_status").innerHTML = "Waiting for zone designation...";
		document.title = "Nabu: Waiting for zone designation...";
	}
	else if (data["status"] == game.unit_selection) {
		$("game_status").innerHTML = "Waiting for unit selection...";
		document.title = "Nabu: Waiting for unit selection...";
	}
	else if (data["status"] == game.skill_selection) {
		$("game_status").innerHTML = "Waiting for skill selection...";
		document.title = "Nabu: Waiting for skill selection...";
	}
	else if (data["status"] == game.ended) {
		$("game_status").innerHTML = "Game is over";
		document.title = "Nabu: Game is over";
	}
	else {
		$("game_status").innerHTML = "Playing...";
		document.title = "Nabu: Playing...";
	}
}

function draw_interface_players() {
	// draw the player list
	var players = "<h1>Players</h1><ul>";
	for(var player in data["players"]) {
		var owner = false;
		if (data["players"][player]["user"] == data["owner"])
			owner = true;
		players += "<li style='cursor:pointer' onmousedown=\"drag_if_possible(" + data["players"][player]["id"] + ", event)\" onmouseover=\"draw_player_information(" + data["players"][player]["id"] + ")\" onmouseout=\"draw_player_information()\">" + (owner ? "<b>" : "") + data["players"][player]["name"]  + (owner ? "</b>" : "") + (data["teams"] ? " (" + data["players"][player]["team"] + ")" : "") + " <span id='player_highlight_" + data["players"][player]["id"] + "'></span></li>";
	}
	players += "</ul>";
	$("players").innerHTML = players;
}

function draw_interface_statistics() {
	// draw game statistics
	var statistics = "<h1>Game Stats</h1><ul>" +
			"<li><b>Name: </b>" + data["name"] + "</li>" +
			"<li><b>Created: </b>" + data["created"] + "</li>" +
			"<li><b>Ranked: </b>" + (data["ranked"] ? "yes" : "no") + "</li>" +
			"<li><b>Teams: </b>" + (data["teams"] ? "yes" : "no") + "</li>" +
			"<li><b>Max Players: </b>" + data["max_players"] + "</li>" +
			"<li><b>Status: </b><span id='game_status'></span></li>" +
			"<li><b>Round: </b><span id='game_round'></span></li>" +
			"<li><b>Turn: </b><span id='game_turn'></span></li>" +
			"</ul>";
	$("statistics").innerHTML = statistics;
}

// this draws a map that can be scaled
function draw_map() {
	var html = "";
	var width = data["map"]["tile_size"] * ratio;
	var height = data["map"]["tile_size"] * ratio;
	for (var y = 0; y < data["map"]["height"]; y++) {
		for (var x = 0; x < data["map"]["width"]; x++) {
			var tile_image = "";
			var counter = 0;
			for(var tile in data["map"]["tiles"]) {
				if (data["map"]["tiles"][tile]["x"] == x && data["map"]["tiles"][tile]["y"] == y) {
					tile_image += "<img src='data/tiles/" + data["map"]["tiles"][tile]["image"] + "' style='position:absolute;top:0px;left:0px;width:" + width + "px;height:" + height + "px'/>";
					counter++;
				}
			}
			// if no tile images for that specific spot, take the default one
			if (tile_image == "")
				tile_image = "<img src='data/tiles/" + data["map"]["tile_default"] + "' style='position:absolute;top:0px;left:0px;width:" + width + "px;height:" + height + "px'/>";
			
			// calculate the positions etc
			var top = (y * data["map"]["tile_size"] + (x % 2 == 0 ? data["map"]["tile_top"] : 0)) * ratio;
			var left = (x * data["map"]["tile_left"]) * ratio;
			
			// need to create multiple layers at different z-indexes
			html += "<div onmouseout=\"clear_unit_info()\" onclick='move_if_possible(" + x + ", " + y + ")' onmouseover=\"draw_unit_info(" + x + ", " + y + ")\" style='z-index:1;position:absolute;top:" + top + "px;left:" + left + "px;width:" + width + "px;height:" + height + "px'>"
					// 100: the first contains the tile image, the reason this is not simply a background image is because of resizing
					+ "<div id='cell_tile_" + x + "." + y + "' style='z-index:10'>" + tile_image + "</div>"
					// 90: the second contains the (optional) grid image
					+ "<div id='cell_grid_" + x + "." + y + "' style='position:absolute;left:0px;top:0px;z-index:20'></div>"
					// 80: highlight
					+ "<div id='cell_highlight_" + x + "." + y + "' style='position:absolute;left:0px;top:0px;z-index:40'></div>"
					// objects at 60
					+ "<div id='cell_object_" + x + "." + y + "' style='position:absolute;top:0px;left:0px;z-index:60'></div>"
					// 20: units
					+ "<div id='cell_unit_" + x + "." + y + "' style='position:absolute;left:0px;top:0px;z-index:80'></div>"
					// 1: unit (/object) statistics (health etc)
					+ "<div id='cell_stats_" + x + "." + y + "' style='position:absolute;left:0px;top:0px;z-index:100'></div>"
				+ "</div>";		// close main div
				// add the objects, but since objects can be bigger then tiles, we do not want to "stretch" the original div, so place it outside
				// 60: objects

		}
		html += "<div style='clear:both'></div>";
	}

	// calculate border things
	var leftright_top = 0;
	var topbottom_left= (data["map"]["tile_size"] * ratio) / 2;
	var left_left = (data["map"]["tile_size"] * ratio) / 2;
	var right_left = data["map"]["width"] * data["map"]["tile_left"] * ratio;
	var leftright_width = (data["map"]["tile_size"] * ratio) / 2;
	var leftright_height = (((data["map"]["height"] * data["map"]["tile_size"]) + data["map"]["tile_top"])  * ratio)  - 1;
	var topbottom_height = (data["map"]["tile_size"] * ratio) / 2;
	var topbottom_width = data["map"]["width"] * data["map"]["tile_left"] * ratio;
	var bottom_top = data["map"]["height"] * data["map"]["tile_size"] * ratio;
	
	html += "<div id='game_border_top' style='position:absolute;left:" + topbottom_left + "px;top:0px;z-index:70;width:" + topbottom_width + "px;height:" + topbottom_height + "px;border:solid 1px #000000;border-style:solid none none none;background-image:url(\"data/misc/frame_bg.png\")'></div>"+
		"<div id='game_border_right' style='position:absolute;left:" + right_left + "px;top:0px;z-index:70;width:" + leftright_width + "px;height:" + leftright_height + "px;border:solid 1px #000000;border-style:solid solid solid none;background-image:url(\"data/misc/frame_bg.png\");'></div>"+
		"<div id='game_border_left' style='position:absolute;left:0px;top:0px;z-index:70;width:" + leftright_width + "px;height:" + leftright_height + "px;border:solid 1px #000000;border-style:solid none solid solid;background-image:url(\"data/misc/frame_bg.png\")'></div>"+
		"<div id='game_border_bottom' style='position:absolute;left:" + topbottom_left + "px;top:" + bottom_top + "px;z-index:70;width:" + topbottom_width + "px;height:" + topbottom_height + "px;border:solid 1px #000000;border-style:none none solid none;background-image:url(\"data/misc/frame_bg.png\")'></div>";

	$("game").innerHTML = html;
}

function draw_unit_info(x, y) {
	// draw the moves
	highlight_moves(x, y);
	var found = false;
	for (var unit in data["units"]) {
		if (data["units"][unit]["x"] == x && data["units"][unit]["y"] == y) {
			found = true;
			var owner = null;
			for (var player in data["players"]) {
				if (data["players"][player]["id"] == data["units"][unit]["player"]) {
					owner = data["players"][player]["name"];
					break;
				}
			}
			
			var description = null;
			for (var tmp in data["unit_descriptions"]) {
				if (data["unit_descriptions"][tmp]["id"] == data["units"][unit]["unit"]) {
					description = tmp;
					break;
				}
			}

			var info = "<h1>Unit Information</h1><ul>" +
				"<li><b>Name: </b>" + data["units"][unit]["name"] + "</li>" + 
				"<li><b>Health: </b>" + data["units"][unit]["health"] + "/" + data["units"][unit]["initial_health"] + "</li>" +
				"<li><b>Turn: </b>" + (data["units"][unit]["turn"] == -1 ? "Unknown" : data["units"][unit]["turn"]) + "</li>" +
				"<li><b>Amount: </b>" + data["units"][unit]["amount"] + "/" + data["units"][unit]["initial_amount"] + "</li>" + 
				(owner != null ? "<li><b>Owner: </b>" + owner + "</li>" : "");
			
			if (description != null) {
				info += "<li><b>Can fly: </b>" + (data["unit_descriptions"][description]["flying"] ? "yes" : "no");
				for (var tmp in data["unit_descriptions"][description]["attributes"])
					info += "<li><b>" + data["unit_descriptions"][description]["attributes"][tmp]["name"] + ": </b>" + data["unit_descriptions"][description]["attributes"][tmp]["value"]; 
			}
			else
				info += "<li><b>Stats: </b>You are unfamiliar with this unit</li>";
			
			info += "</ul>";
			show_information(info);
		}
	}
	if (!found) {
		// check if there is an object
		for (var object in data["objects"]) {
			if (data["objects"][object]["x"] == x && data["objects"][object]["y"] == y) {
				var owner = null;
				if (data["objects"][object]["player"] != null && data["objects"][object]["player"] > 0) {
					for (var player in data["players"]) {
						if (data["players"][player]["id"] == data["objects"][object]["player"]) {
							owner = data["players"][player]["name"];
							break;
						}
					}
				}
				var info = "<h1>Object Information</h1><ul>" +
					"<li><b>Name: </b>" + data["objects"][object]["name"] + "</li>" + 
					"<li><b>Health: </b>" + data["objects"][object]["health"] + "/" + data["objects"][object]["initial_health"] + "</li>" +
					(owner != null ? "<li><b>Owner: </b>" + owner + "</li>" : "") +
				"</ul>";
				show_information(info);			
			}
		}
	}
}

function clear_unit_info() {
	unhighlight();
//	hide_information();
}

function drag_if_possible(id, event) {
	if (data["status"] <= game.zone_selection) {
		// only the game owner can do this
		if (data["owner"] == data["user"]) {
			drag_selected = id;
			if (event) {
				event.stopPropagation();
				event.preventDefault();
			}
		}
	}
}

function select_zone_if_possible(id) {
	if (data["status"] <= game.zone_selection) {
		// only the game owner can do this
		if (data["owner"] == data["user"] && drag_selected != null) {
			ajax({url: "game.php?action=assign&player=" + drag_selected + "&zone=" + id});
			drag_selected = null;
		}
	}
}

function clear_highlights() {
	for (var y = 0; y < data["map"]["height"]; y++) {
		for (var x = 0; x < data["map"]["width"]; x++)
			$("cell_highlight_" + x + "." + y).innerHTML = "";
	}
}

function draw_player_information(id) {
	if (id) {
		draw_zone_if_placed(id);
		for (var player in data["players"]) {
			if (data["players"][player]["id"] == id) {
				var player_zone_penalty = 0;
				if (data["players"][player]["zone"] != -1) {
					for (var zone in data["map"]["zones"]) {
						if (data["map"]["zones"][zone]["id"] == data["players"][player]["zone"]) {
							player_zone_penalty = data["map"]["zones"][zone]["leadership_penalty"];
							break;
						}
					}
				}
				var html = "<h1>" + data["players"][player]["name"] + (!data["players"][player]["active"] ? " <i>(Inactive)</i>" : "") + "</h1><ul>" +
					"<li><b>Leadership: </b>" + (data["ranked"] ? data["players"][player]["leadership"] : data["map"]["leadership"]) + "</li>" +
					"<li><b>Zone Penalty: </b>" + player_zone_penalty + "%</li>" +
					"<li><b>Status: </b>" + (data["players"][player]["status"] == 0 ? "Not ready" : "Ready") + "</li>" +
					"<li><b>Team: </b>" + data["players"][player]["team"] + "</li>" + 
					"<li><b>Total Experience: </b>" + data["players"][player]["total_experience"] + "</li>" +
					"<li><b>Color: </b><span style='width:20px;height:8px' class='player" + player + "'>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</span>";
				"</ul>";
				show_information(html);
			}
		}
	}
	else {
		draw_zones();
		hide_information();
	}
}

function get_player_leadership(player_id) {
	var leadership = 0;
	if (!data["ranked"])
		leadership = data["map"]["leadership"];
	else {
		for (var player in data["players"]) {
			if ((player_id && data["players"][player]["id"] == player_id) || (!player_id && data["players"][player]["user"] == data["user"])) {
				leadership = data["players"][player]["leadership"];
				break;
			}
		}
	}
	
	var zone = 0;
	// check the players zone, he may have a penalty, floor it, otherwise it does not match the server calculations
	for (var player in data["players"]) {
		if ((player_id && data["players"][player]["id"] == player_id) || (!player_id && data["players"][player]["user"] == data["user"])) {
			zone = data["players"][player]["zone"];
			break;
		}
	}
	// get the zone
	for (var item in data["map"]["zones"]) {
		if (data["map"]["zones"][item]["id"] == zone) {
			if (data["map"]["zones"][item]["leadership_penalty"] != 0)
				leadership -= Math.floor((leadership * parseInt(data["map"]["zones"][item]["leadership_penalty"])) / 100);
			break;
		}
	}
	return leadership;
}

function draw_zone_if_placed(id) {
	// only do this in the first stages of the game
	if (data["status"] <= game.zone_selection) {
		for (var player in data["players"]) {
			if (data["players"][player]["id"] == id) {
				// if a zone was chosen, draw only that
				if (data["players"][player]["zone"] >= 0)
					draw_zones(data["players"][player]["zone"]);
				break;
			}
		}
	}
}

function draw_zones(id) {
	if (data["status"] <= game.zone_selection) {
		clear_highlights();
		var width = data["map"]["tile_size"] * ratio;
		var height = data["map"]["tile_size"] * ratio;
		// use the neutral highlight tile to draw the zones
		for(var zone in data["map"]["zones"]) {
			if (!id || id == data["map"]["zones"][zone]["id"]) {
				for (var y = data["map"]["zones"][zone]["top_left_y"]; y <= data["map"]["zones"][zone]["bottom_right_y"]; y++) {
					for (var x = data["map"]["zones"][zone]["top_left_x"]; x <= data["map"]["zones"][zone]["bottom_right_x"]; x++)
						$("cell_highlight_" + x + "." + y).innerHTML = "<img onmouseup=\"select_zone_if_possible(" + data["map"]["zones"][zone]["id"] + ")\" style='width:" + width + "px;height:" + height + "px' src='data/tiles/" + data["map"]["tile_highlight_enemy"] + "' title='Leadership penalty: " + data["map"]["zones"][zone]["leadership_penalty"] + "' alt='Leadership penalty: " + data["map"]["zones"][zone]["leadership_penalty"] + "'/>";
				}
			}
		}
	}
}

function draw_objects() {
	for (var x = 0; x < data["map"]["width"]; x++) {
		for (var y = 0; y < data["map"]["height"]; y++)
			$("cell_object_" + x + "." + y).innerHTML = "";
	}
	for (var object in data["objects"]) {
		var width = data["objects"][object]["width"] * ratio;
		var height = data["objects"][object]["height"] * ratio;
		$("cell_object_" + data["objects"][object]["x"] + "." + data["objects"][object]["y"]).innerHTML = "<img style='position:absolute;top:0px;left:0px;z-index:60;width:" + width + "px;height:" + height + "px' src='data/objects/" + data["objects"][object]["image"] + "'/>";
	}
}

function draw_units() {
	for (var x = 0; x < data["map"]["width"]; x++) {
		for (var y = 0; y < data["map"]["height"]; y++)
			$("cell_unit_" + x + "." + y).innerHTML = "";
	}
	var tile_width = data["map"]["tile_size"] * ratio;
	var tile_height = data["map"]["tile_size"] * ratio;
	for (var unit in data["units"]) {
		var width = data["units"][unit]["width"] * ratio;
		var height = data["units"][unit]["height"] * ratio;
		$("cell_unit_" + data["units"][unit]["x"] + "." + data["units"][unit]["y"]).innerHTML = "<img style='position:absolute;top:0px;left:0px;z-index:79;width:" + tile_width + "px;height:" + tile_height + "px' src='data/tiles/player" + get_player_sequence(data["units"][unit]["player"]) + ".png'/><img style='position:absolute;top:0px;left:0px;z-index:80;width:" + width + "px;height:" + height + "px' src='data/units/" + data["units"][unit]["image"] + "'/>";
	}
}

function get_player_sequence(player_id) {
	for (var player in data["players"]) {
		if ((player_id && data["players"][player]["id"] == player_id) || (!player_id && data["players"][player]["user"] == data["user"]))
			return player;
	}
	return null;
}

function draw_unit_selection() {
	unit_selection_list = data["unit_descriptions"];
	var html = "<div class='comment'>You have <span id='selection_total_leadership'>" + get_player_leadership() + "</span>/" + get_player_leadership() + " leadership remaining</div>";
	for (var key in unit_selection_list) {
		html += "<div class='unit'><div class='image'><img src='data/units/" + unit_selection_list[key]["image"] + "'/></div><div class='description'><h2>" + unit_selection_list[key]["name"] + " (" + unit_selection_list[key]["leadership"] + ")</h2><p>" + unit_selection_list[key]["description"] + "</p></div>";
		// add the attributes
		html += "<div class='stats'><ul>";
		// add health
		html += "<li><b>Health: </b>" + unit_selection_list[key]["health"] + "</li>";
		for (var attr in unit_selection_list[key]["attributes"])
			html += "<li><b>" + unit_selection_list[key]["attributes"][attr]["name"] + "</b>: " + unit_selection_list[key]["attributes"][attr]["value"] + "</li>";
		html += "</ul></div>";
		// add the choice element
		html += "<div class='choice'><span id='selection_unit_" + key + "'>0</span> <input type='button' onClick='select_unit_in_selection(" + key + ")' value='Select Amount'/></div>";
		html += "</div>";	// close unit
	}
	html += "<div class='select_units'><input type='button' onClick='submit_unit_selection()' value='Confirm Unit Selection'/></div>";
	$("game").innerHTML = html;
}


function select_unit_in_selection(unit) {
	var amount = parseInt(window.prompt("Enter an amount of units"));
	if (isNaN(amount))
		alert("Please select a valid amount");
	else {
		if((unit_selection_list[unit]["leadership"] * amount) + calculate_combined_leadership(unit) > get_player_leadership())
			alert("You do not have enough leadership for this");
		else
			$("selection_unit_" + unit).innerHTML = amount;
	}
	$("selection_total_leadership").innerHTML = get_player_leadership() - calculate_combined_leadership();
}

function calculate_combined_leadership(ignore) {
	var amount = 0;
	for(var key in unit_selection_list) {
		if (isNaN(ignore) || key != ignore) {
			var tmp = parseInt($("selection_unit_" + key).innerHTML);
			if (isNaN(tmp))
				$("selection_unit_" + key).innerHTML = "0";
			else
				amount += tmp * unit_selection_list[key]["leadership"];
		}
	}
	return amount;
}

function submit_unit_selection() {
	if (calculate_combined_leadership() > get_player_leadership())
		alert("You do not have enough leadership for this selection");
	else {
		var result = [];
		for (var key in unit_selection_list) {
			var tmp = parseInt($("selection_unit_" + key).innerHTML);
			// only the actual selections are relevant
			if (!isNaN(tmp) && tmp != 0)
				result[result.length] = {id: unit_selection_list[key]["id"], amount: tmp};
		}
	}
	ajax({url: 'game.php?action=choose_units', method:"POST", params: {"units": JSON.stringify(result)}, success: function(response) {
		var parsed = JSON.parse(response.responseText);
		if (parsed["error"])
			alert(parsed["error"]);
		else {
			// reset inner html
			$("game").innerHTML = "";
			draw_map();
			draw_objects();
			draw_units();
			load_dynamic_data(parsed);
		}
	}});
}

// start the game
function start_game() {
	ajax({url: 'game.php?action=start_game', success: function(response) {
		var parsed = JSON.parse(response.responseText);
		if (parsed["error"])
			alert(parsed["error"]);		
	}});
}

function toggle_grid() {
	// if the grid is on atm, turn it off
	if (grid) {
		for (var x = 0; x < data["map"]["width"]; x++) {
			for (var y = 0; y < data["map"]["height"]; y++)
				$("cell_grid_" + x + "." + y).innerHTML = "";
		}
		grid = false;
	}
	else {
		var size = data["map"]["tile_size"] * ratio;
		for (var x = 0; x < data["map"]["width"]; x++) {
			for (var y = 0; y < data["map"]["height"]; y++)
				$("cell_grid_" + x + "." + y).innerHTML = "<img style='position:absolute;width:" + size + "px;height:" + size + "px;top:0px;left:0px;z-index:20' src='data/tiles/" + data["map"]["tile_grid"] + "'/>";
		}		
		grid = true;
	}
}

function highlight_moves(x, y, do_not_unhighlight) {
	var active = get_active_unit();
	// unhighlight anything else
	var id = x + "." + y;
	for (var unit in data["units"]) {
		if (data["units"][unit]["x"] == x && data["units"][unit]["y"] == y) {
			if (!do_not_unhighlight)
				unhighlight(true);
			if (data["units"][unit]["moves"]) {
				for (var move in data["units"][unit]["moves"]["movement"])
					$("cell_highlight_" + data["units"][unit]["moves"]["movement"][move]["x"] + "." + data["units"][unit]["moves"]["movement"][move]["y"]).innerHTML = "<img style='width:" + (data["map"]["tile_size"] * ratio) + "px;height:" + (data["map"]["tile_size"] * ratio) + "px' src='data/tiles/" + data["map"]["tile_highlight_neutral"] + "'/>";
				for (var move in data["units"][unit]["moves"]["attack"])
					$("cell_highlight_" + data["units"][unit]["moves"]["attack"][move]["x"] + "." + data["units"][unit]["moves"]["attack"][move]["y"]).innerHTML = "<img style='width:" + (data["map"]["tile_size"] * ratio) + "px;height:" + (data["map"]["tile_size"] * ratio) + "px' src='data/tiles/" + data["map"]["tile_highlight_enemy"] + "'/>";
			}
		}
	}
}

function highlight_active(skip_active_highlight) {
	var active = get_active_unit();
	if (active != null) {
		$("cell_highlight_" + data["units"][active]["x"] + "." + data["units"][active]["y"]).innerHTML = "<img style='width:" + (data["map"]["tile_size"] * ratio) + "px;height:" + (data["map"]["tile_size"] * ratio) + "px' src='data/tiles/" + data["map"]["tile_highlight_friend"] + "'/>";
		if (!skip_active_highlight)
			highlight_moves(data["units"][active]["x"], data["units"][active]["y"], true);
	}
}

function unhighlight(skip_active_highlight) {
	for (var x = 0; x < data["map"]["width"]; x++) {
		for (var y = 0; y < data["map"]["height"]; y++)
			$("cell_highlight_" + x + "." + y).innerHTML = "";
	}
	highlight_active(skip_active_highlight);
	draw_zones();
}

// the unit who's turn it is
function get_active_unit() {
	if (data["turn"] == null)
		return null;
	for (var unit in data["units"]) {
		if (data["units"][unit]["turn"] == data["turn"])
			return unit;
	}
	return null;
}

function defend() {
	if (is_your_turn() && data["status"] == game.started) {
		ajax({url: "game.php?action=defend", success: function(response) {
			var parsed = JSON.parse(response.responseText);
			if (parsed["error"])
				alert(parsed["error"]);
			else
				load_dynamic_data(parsed);
		}});
	}
}

function wait() {
	if (is_your_turn() && data["status"] == game.started) {
		ajax({url: "game.php?action=wait", success: function(response) {
			var parsed = JSON.parse(response.responseText);
			if (parsed["error"])
				alert(parsed["error"]);
			else
				load_dynamic_data(parsed);
		}});
	}
}

function move_if_possible(x, y) {
	if (data["status"] == game.started) {
		if (is_your_turn()) {
			var active = get_active_unit();
			if (active != null) {
				for (var move in data["units"][active]["moves"]["movement"]) {
					if (data["units"][active]["moves"]["movement"][move]["x"] == x && data["units"][active]["moves"]["movement"][move]["y"] == y) {
						ajax({url: "game.php?action=move&x=" + x + "&y=" + y, success:function(response) {
							var parsed = JSON.parse(response.responseText);
							if (parsed["error"])
								alert(parsed["error"]);
							else
								load_dynamic_data(parsed);
						}});
						return true;
					}
				}
				for (var move in data["units"][active]["moves"]["attack"]) {
					if (data["units"][active]["moves"]["attack"][move]["x"] == x && data["units"][active]["moves"]["attack"][move]["y"] == y) {
						ajax({url: "game.php?action=attack&x=" + x + "&y=" + y, success:function(response) {
							var parsed = JSON.parse(response.responseText);
							if (parsed["error"])
								alert(parsed["error"]);
							else
								load_dynamic_data(parsed);
						}});
						return true;
					}
				}
			}
		}
	}
}

function is_your_turn() {
	var active = get_active_unit();
	if (active !== null) {
		var player = get_player_sequence(data["units"][active]["player"]);
		if (data["players"][player]["user"] == data["user"])
			return true;
	}
	return false;
}