$.fn.extend({
	datechanger : function() {
		return this.each(function() {
			options = {};
			return $.DateChanger(this, options);
		});
	}
});
$.DateChanger = function(elem, options) {
	// TODO: options : dateFormat
	elem = $(elem);
	
	var readElem = $("input[name='"+ elem.attr("rel") +"']");
	var writeElem = $("input[name='"+ elem.attr("rev") +"']");
	var relation = elem.attr("href").replace("#", "");

	var relations = {
		defaultAction: function() {
			
			if (!validDate(readElem.val(), "dmy", "/")) { return false; }
			var dateChange = relation;

			var dateChanges = [];
			var dateChangeReg = /([\+\-])(\d+)\s(\w+)s?/g; // IMPROVE: Perhaps set this to match day|days|week|weeks|year|years
			var change;

			while (change = dateChangeReg.exec(dateChange)) {
				var objChange = {}
				objChange.direction = change[1];
				objChange.amount = change[2];
				objChange.type = change[3].replace("s", ""); // IMPROVE: This should be in the RegExp
				dateChanges.push(objChange);
			}
			var timeToAdd = 0;

			for (var i = 0, len = dateChanges.length; i < len; i++) {
				var dc = dateChanges[i];
				var sum = "";
				var days = 0;
				var timesBy = 60*60*60*24;
				   
				// TODO: Make this work with month and year
				switch (dc.type) {
					case "day":
						days = 1;
						break;

					case "week":
						days = 7;
						break;
				}
				// TODO: use the minus operator too
				timeToAdd += (days*24*60*60*1000)*dc.amount;
			}
			
			var curDate = setDateFromStr(readElem.val(), "dmy", "/");
			var newDate = new Date();
			newDate.setTime(curDate.getTime() + timeToAdd);
			var day = newDate.getDate()+1 < 10 ? "0"+ newDate.getDate() : newDate.getDate();
			var month = newDate.getMonth()+1 < 10 ? "0"+ (newDate.getMonth()+1) : newDate.getMonth()+1;
			newDate = day +"/"+ month +"/"+ (newDate.getFullYear()+"")/*.substr(2,2)*/;
			
			writeElem.val(newDate);
			return false;
		},
		today: function() {
			var today = new Date();
			var day = today.getDate()+1 < 10 ? "0"+ today.getDate() : today.getDate();
			var month = today.getMonth()+1 < 10 ? "0"+ (today.getMonth()+1) : today.getMonth()+1;
			today = day +"/"+ month +"/"+ (today.getFullYear()+"")/*.substr(2,2)*/;
			writeElem.val(today);
			return false;
		},
		tomorrow: function() {
			var today = new Date();
			today.setTime(today.getTime()+24*60*60*1000);
			
			var day = today.getDate()+1 < 10 ? "0"+ today.getDate() : today.getDate();
			var month = today.getMonth()+1 < 10 ? "0"+ (today.getMonth()+1) : today.getMonth()+1;
			today = day +"/"+ month +"/"+ (today.getFullYear()+"")/*.substr(2,2)*/;
			
			writeElem.val(today);
			return false;
		},
		same: function() {
			if (!validDate(readElem.val(), "dmy", "/")) { return false; }
			writeElem.val(readElem.val());
			return false;
		}
	}
	
	// elem.click(function() { return false; })	
	if (relations[relation] == undefined) {
		elem.click(relations["defaultAction"]);
	} else {
		elem.click(relations[relation]);
	}

	function validDate(value, order, delimeter) {
		// OPTIMISE: Use set setDateFromObj
		var datesAreEqual = true;
		var values = value.split(delimeter);
		var dateTypeOrder = order.split("");
		var dateObj = {}
		for (var i = 0, len = 3; i < len; i++) {
			var val = values[i];
			var date = dateTypeOrder[i];
			if (date == "y" && val.length == 2) {
				var year = (new Date().getYear()+1900)+"";
				val = year.substr(0,2)+val;
			}
			if (date != "y" && (val+"").substr(0,1) == 0) {
				val = (val+"").substr(1,1);
			}
			dateObj[date] = parseInt(val);
		}
		
		compareDate = new Date();
		compareDate.setFullYear(dateObj.y);
		compareDate.setMonth(dateObj.m-1);
		compareDate.setDate(dateObj.d);
		
		if (
			dateObj.y != compareDate.getFullYear() ||
			dateObj.m != compareDate.getMonth()+1 ||
			dateObj.d != compareDate.getDate()
		) {
			datesAreEqual = false;
		}

		return datesAreEqual;
	}
	
	function setDateFromStr(value, order, delimeter) {
		var values = value.split(delimeter);
		var datePartsOrder = order.split("");
		var dateObj = {}
		for (var i = 0, len = 3; i < len; i++) {
			var val = values[i];
			var datePart = datePartsOrder[i];
			if (datePart == "y" && val.length == 2) {
				var year = (new Date().getYear()+1900)+"";
				val = year.substr(0,2)+val;
			}
			if (datePart != "y" && (val+"").substr(0,1) == 0) {
				val = (val+"").substr(1,1);
			}
			dateObj[datePart] = val;
		}
		var date = new Date();
		date.setFullYear(dateObj.y);
		date.setMonth(dateObj.m-1);
		date.setDate(dateObj.d);
		date.setHours(0);
		date.setMinutes(0);
		date.setSeconds(0);
		date.setMilliseconds(0);
		
		return date;
	}
}
