// Seraphiel
// version 0.95
// 2010-03-07
// Copyright (c) 2006+, Joel Rein (Jivlain)
// Contact: joel@motheyes.com
// Homepage: http://seraphiel.motheyes.com
//
// Released under the GPL (v2) license
// http://www.gnu.org/copyleft/gpl.html
//
// This program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public License
// as published by the Free Software Foundation; either version 2
// of the License, or (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.

// ==UserScript==
// @name           Seraphiel
// @namespace      http://seraphiel.motheyes.com
// @description    User interface improvements for Utopia
// @include        http://utopia-game.com/wol/game/*
// @include        http://utopia-game.com/wol/kingdom_forum/*
// @include        http://utopia-game.com/wol/war_forum/*
// @include        http://utopia-game.com/wol/mail/*
// @include        http://utopia-game.com/wol/sit/game/*
// @include        http://utopia-game.com/wol/sit/kingdom_forum/*
// @include        http://utopia-game.com/wol/sit/war_forum/*
// @include        http://utopia-game.com/wol/sit/mail/*
// ==/UserScript==

//***UTILITY FUNCTIONS***
function trim(str){ return ltrim(rtrim(str)); } 
function ltrim(str) {	return str.replace(new RegExp("^[\\s]+", "g"), ""); }
function rtrim(str) {	return str.replace(new RegExp("[\\s]+$", "g"), ""); }
function getValue(name){ return document.getElementById(name).value; }
function getHTML(name){ return document.getElementById(name).innerHTML; }
function nanParseInt(str, def){ var i=parseInt(str); return isNaN(i)?def:i; }
function GM_getInt(name){ return nanParseInt(GM_getValue(name)); }
function GM_getBool(name){ return new Boolean(GM_getValue(name)); }

//simplistic string formatter 
//eg format("{0} * {1} = {2} = {1} * {0}", 3, "five", 15) returns "3 * five = 15 = five * 3"
//based on .NET's String.Format, but much much lazier (no special formatters, padding, etc)
function format(){
	var str=arguments[0];
	for(i=0;i<arguments.length-1;i++)
		str=str.replace(new RegExp('\\{'+i+'\\}', 'gi'), arguments[i+1]);
	return str;
}

//***CSS STYLES***
GM_addStyle('.seraBanner{position:fixed;top:0px;left:0px;height:1.2em;width:100%;background-color:green;color:white;}');
GM_addStyle('.seraBanner a{color:#aaaaff;}');
GM_addStyle('.seraButton{position:fixed;right:0em;height:2.5em;width:6em;}');
GM_addStyle('.seraCalculator{position:fixed;bottom:0px;left:0px;height:1.2em;width:98%;color:white;text-align:right;}');

//***ADD LINKS***
function addNavLinks(){
	var nav=document.getElementById("navigation");
	var lis=nav.getElementsByTagName("li");
	var kd=GM_getValue('tag_kingdom');
	var is=GM_getValue('tag_island');
	if(kd!=undefined&&is!=undefined)
		lis[1].innerHTML+=format(' <a href="/wol/game/kingdom_details/{0}/{1}">[{0}:{1}]</a>', kd, is);
	lis[2].innerHTML+=' [<a href="/wol/game/kingdom_news">Kd</a>]';
	var council='<li>[<a href="/wol/game/council_state">C</a>/';
	council+='<a href="/wol/game/council_military">M</a>/';
	council+='<a href="/wol/game/council_internal">B</a>/';
	council+='<a href="/wol/game/council_science">S</a>/';
	council+='<a href="/wol/game/council_spells">W</a>/';
	council+='<a href="/wol/game/council_history">H</a>';
	lis[7].innerHTML+=' / <a href="http://utopia-game.com/wol/game/council_spells">Spells</a>';
	lis[8].innerHTML='<a href="http://utopia-game.com/wol/game/enchantment">Magic</a> / <a href="/wol/game/sorcery">Sorcery</a>';
	var lists=nav.getElementsByTagName("ul");
	lists[0].innerHTML+=council+']</li>';
	lists[5].removeChild(lists[5].getElementsByTagName("li")[1]);
}
function addHelpLink(){
	var links=document.getElementById("header-account-links");
	var span=document.createElement('span');
	span.innerHTML='|<span><a href="http://wiki.utopia-game.com/index.php">Wiki</a></span>';
	span.innerHTML+='|<span><a href="http://utopia-game.com/wol/gift/">Gift Credits</a></span>';
	links.appendChild(span);
}

//***KINGDOM PAGE***	
function kingdom(){
	GM_addStyle(".heading{cursor:pointer;}");
	
	var table=document.getElementById("kingdom-details-provinces");
	var headings=table.getElementsByTagName("th");	
	for(var i=0;i<headings.length;i++)
		headings[i].className="heading";
		
	function AddSelectButton(nextURL, text, top){
		var kd=getValue('id_kingdom');
		var is=getValue('id_island');
		var str='<form method="POST" action="/wol/game/change_kingdom/">';
		str+='<input type="hidden" name="next_url" value="/wol/game/'+nextURL+'" id="id_next_url" />';
		str+='<input name="kingdom" value="{0}" type="hidden"/>'
		str+='<input name="island" value="{1}" type="hidden" />'
		str+='<input type="submit" value="{2}" name="change_kingdom" style="top:{3}em;" class="seraButton" id="btn{2}" /></form>';
		document.body.innerHTML+=format(str, kd, is, text, top);
	}
	function AddButton(name, top){		
		document.body.innerHTML+=format('<input type="button" id="btn{0}" value="{0}" style="top:{1}em;" class="seraButton"/>', name, top);
	}
	AddSelectButton('kingdom_details/{0}/{1}', 'Select', 2);
	AddSelectButton('sorcery', 'Sorcery', 4.5);
	AddSelectButton('thievery', 'Thievery', 7);
	
	AddButton('Bookmark', 9.5);
	AddButton('Previous', 12);
	AddButton('Next', 14.5);
		
	function Province(row){
		var cells=row.getElementsByTagName("td");
		var values=Array();
		for(var i=0;i<cells.length;i++)
			values[i]=trim(cells[i].innerHTML);
		values[cells.length]=row.className;
		return values;
	}
	
	function OrderVal(arr, orderby){
		switch(orderby){
			case 2:
			case 3:
			case 4:
				return parseInt(arr[orderby].replace(/,/g,""));
			case 5:
				var ranks=Array("DEAD", "Peasant", "Knight", "Lady", "Lord", "Noble Lady", "Baron", "Baroness",	"Viscount", 
					"Viscountess", "Marquis", "Marchioness", "Duke", "Duchess", "Prince", "Princess", "King", "Queen");
				for(var i=0;i<ranks.length;i++)
					if(arr[orderby]==ranks[i])
						return i;
				return 0;
			default: return arr[orderby];
		}
	}
	
	function Sort(arr, orderby){
		//yes, it's a BUBBLE sort. I'm lame. I can only defend myself by saying that n<=25.
		do{
			cont=false;
			for(i=arr.length-1;i>=1;i--){
				for(j=0;j<i;j++){
					if(OrderVal(arr[j], orderby)>OrderVal(arr[j+1], orderby)){
						var temp=arr[j];
						arr[j]=arr[j+1];
						arr[j+1]=temp;
						cont=true;
					}
				}
			}
		} while(cont);
		//if no exchanges were made, reverse the order (the kindgom page should be sortable in both directions).
		if(sortAsc&&sortCol==orderby)
			arr.reverse();
		sortAsc=(sortCol==orderby)?!sortAsc:true;
		sortCol=orderby;
		return arr;
	}
	
	function SortKd(orderby){
		var table=document.getElementById("kingdom-details-provinces");
		var rows=table.getElementsByTagName("tr");
		var provinces=Array();
		for(j=1;j<rows.length;j++)
			provinces[j-1]=Province(rows[j]);
		Sort(provinces, orderby);
		for(j=0;j<provinces.length;j++){
			cols=rows[j+1].getElementsByTagName("td");
			for(k=0;k<cols.length;k++)
				cols[k].innerHTML=provinces[j][k];
			rows[j+1].className=provinces[j][cols.length];
		}
	}
	
	var sortCol=GM_getInt('sortCol', -1);
	var sortAsc=!GM_getBool('sortAsc');
	if(sortCol>=0)
		SortKd(sortCol);
	GM_setValue('sortCol', -1);
	GM_setValue('sortAsc', false);
	
	function saveSortValues(){
		GM_setValue('sortCol', sortCol);
		GM_setValue('sortAsc', sortAsc);
	}	
	
	document.addEventListener('click', function(event) {
		var id=event.target.id;
		if(id.length==0){
			if(event.target.className=='previous')
				id='aPrevious';
			else if(event.target.className=='next')
				id='aNext';
			else if(event.target.innerHTML=='Random')
				id='aRandom';
		}
		switch(id){
			case 'btnBookmark': //bookmark kingdom
				var kd=getValue('id_kingdom');
				var is=getValue('id_island');
				if(GM_getValue('tag_kingdom')!=kd||GM_getValue('tag_island')!=is){
					GM_setValue('tag_kingdom', kd);
					GM_setValue('tag_island', is);
					var kdlink=document.getElementById('navigation').getElementsByTagName('li')[1];
					var kdlinks=kdlink.getElementsByTagName('a');
					kdlinks[0].innerHTML='Kd';
					for(i=1;i<kdlinks.length-1;i++)
						kdlink.removeChild(kdlinks[1]);
					if(kdlinks.length>1)
						kdlinks[1].innerHTML=kdlinks[1].innerHTML.substr(1, kdlinks[1].innerHTML.length-2);
					kdlink.innerHTML+=format(' <a href="http://utopia-game.com/wol/game/kingdom_details/{0}/{1}">{0}:{1}</a>', kd, is);
				}
				break;
			case 'aPrevious': case 'aNext': case 'aRandom': case 'btnSelect':
				saveSortValues();
				break;
			case 'btnPrevious':
				saveSortValues();
				location.search='?previous';
				break;
			case 'btnNext':
				saveSortValues();
				location.search='?next';
				break;
			default: //sort kingdom page
				var colNames=new Array("Province", "Race", "Land", "Net Worth", "Net Worth/Acre", "Nobility");
				for(var i=0;i<colNames.length;i++)
					if(colNames[i]==event.target.innerHTML)
						SortKd(i);
				break;
		}
	}, true);
}

//***MILITARY TRAINING***
function militaryTraining(){
	var calculator=document.createElement('div');
	calculator.setAttribute('class', 'seraCalculator');
	document.body.appendChild(calculator);
	document.addEventListener('keyup', function(event) {
		var table=document.getElementById('train-army-training');
		var rows=table.getElementsByTagName("tr");
		var totalNum=0, totalCost=0;
		for(i=0;i<rows.length-1;i++){
			var cost=nanParseInt(rows[i+1].getElementsByTagName("td")[2].innerHTML, 0);
			var qty=nanParseInt(document.getElementById('id_unit-quantity_'+i).value, 0);
			totalNum+=qty;
			totalCost+=cost*qty;
		}
		calculator.innerHTML=format('Training {0} troops at a cost of {1}gc', totalNum, totalCost);
	}, true);
}

//***MAGIC***
function magic(){
	document.addEventListener('click', function(event) {
		if(event.target.type=='submit'){
			var obj=document.getElementById('id_spell');
			if(obj!=null){
				var spell=obj.value;
				if(spell.length>0){
					spell=spell.toUpperCase().replace(/\ /g, '_');
					document.forms[document.forms.length-1].action='?s='+spell;
				}
			}
		}
	}, true);
}

function topics(){
	//add pages to topics page
	var rows=document.getElementsByTagName('tr');
	for(i=0;i<rows.length;i++){
		if(rows[i].className=='odd'||rows[i].className=='even'){
			var cells=rows[i].getElementsByTagName('td');
			var link=cells[0].getElementsByTagName('a')[0].href;
			var pages=Math.ceil(parseInt((cells[2].innerHTML-1)/10))+1;
			if(pages>1){
				var topic=cells[0].innerHTML.split('<br>');
				topic[0]+=' pages:';
				for(page=2;page<=pages;page++)
					topic[0]+=' <a href="'+link+'?page='+page+'">'+page+'</a>';
				cells[0].innerHTML=topic[0]+'<br>'+topic[1];
			}			
		}
	}
	//puts all actions on the same line (pages/monarchs only)
	for(i=0;i<document.forms.length-1;i++){
		var str='<div style="white-space:nowrap;right:0;padding:0">';
		str+=document.forms[i].innerHTML.replace(new RegExp("<br>", "g"), "")+'</div>';
		document.forms[i].innerHTML=str;
	}
}

//***MAIN***
GM_addStyle("#navigation{position:fixed;bottom:0px}");
addHelpLink();
addNavLinks();
if(location.href.indexOf('kingdom_details')>0)
	kingdom();
if(location.href.indexOf('train_army')>0)
	militaryTraining();
if(location.href.indexOf('forum/topics')>0)
	topics();
//if(location.href.indexOf('enchantment')>0||location.href.indexOf('sorcery'))
//	magic();

