YAHOO.namespace("p3g.form");

/**
 * Event fired on form submit
 */
YAHOO.p3g.form.formSubmitEvent = new YAHOO.util.CustomEvent("formSubmitEvent");

/**
 * Default form submit method... Use this instead of form.submit() because this will fire a formSubmitEvent
 */
YAHOO.p3g.form.submit = function(theForm) {
	YAHOO.p3g.form.formSubmitEvent.fire(theForm);
	theForm.submit();
}

/**
 * Submit a form webflow with specifed eventId
 */
YAHOO.p3g.form.submitFlow = function(theForm, eventIdValue) {
	theForm._eventId.value = eventIdValue;
	YAHOO.p3g.form.submit(theForm);
}

/**
 * Cancel a form (support webflow form)
 */
YAHOO.p3g.form.cancel = function(theForm) {
	var eventId = theForm._eventId;
	if (eventId === undefined) {
		YAHOO.p3g.form.createHiddenInput(theForm, "_cancel", "_cancel", "true");
	} else {
		eventId.value = "cancel";
	}
	YAHOO.p3g.form.submit(theForm);
}

/**
 * Create and append a new hidden input to the form
 */
YAHOO.p3g.form.createHiddenInput = function(theForm, id, name, value) {
		var newInput = document.createElement("input");
		newInput.setAttribute("type", "hidden");
		newInput.setAttribute("id", id);
		newInput.setAttribute("name", name);
		newInput.setAttribute("value", value);
		theForm.appendChild(newInput);	
}

/** 
 * Radio with checkbox
 */
YAHOO.p3g.form.RadioCheckbox = function(onId, offId, onValue, offValue, value) {
	this.onId = onId;
	this.offId = offId;
	if (onValue == value) $(onId).checked = true;
	if (offValue == value) $(offId).checked = true;
	YAHOO.util.Event.onAvailable(this.offId, this.addClickHandler, this, true);
}

YAHOO.p3g.form.RadioCheckbox.prototype.addClickHandler = function () {
	YAHOO.util.Event.addListener(this.onId, "click", this.onCallback, this, true);
	YAHOO.util.Event.addListener(this.offId, "click", this.offCallback, this, true);
}

YAHOO.p3g.form.RadioCheckbox.prototype.onCallback = function () {
	if ($(this.onId).checked) $(this.offId).checked = false;
}

YAHOO.p3g.form.RadioCheckbox.prototype.offCallback = function () {
	if ($(this.offId).checked) $(this.onId).checked = false;
}

/**
 * Radio with n checkboxes
 */
YAHOO.p3g.form.RadioCheckboxes = function() {
	this.checkboxes = [];
	this.listeners = [];
}
YAHOO.p3g.form.RadioCheckboxes.prototype.addCheckbox = function (checkboxId) {
	var check = $(checkboxId);
	this.checkboxes.push(check);
	YAHOO.util.Event.addListener(check, "click", this.clickCallback, check, this);
}
YAHOO.p3g.form.RadioCheckboxes.prototype.addListener = function (fn) {
	this.listeners.push(fn);
}
YAHOO.p3g.form.RadioCheckboxes.prototype.clickCallback = function (e, clickedCheckbox) {
	if(clickedCheckbox.checked) {
		for (var i=0, len=this.checkboxes.length; i<len; ++i) {
			if(this.checkboxes[i].id != clickedCheckbox.id) {
				this.checkboxes[i].checked = false;
			}
		}
	}
	for (var i=0, len=this.listeners.length; i<len; ++i) {
		this.listeners[i]();
	}
}

/** 
 * Radio yes/no/unknown with specify text
 */
YAHOO.p3g.form.RadioSpecify = function(path) {
	this.path = path;
	YAHOO.util.Event.onContentReady(path + "_wrapper", this.init, this, true);	
}

YAHOO.p3g.form.RadioSpecify.prototype.getOnId = function () {
	return this.path + ".bool_true";
}

YAHOO.p3g.form.RadioSpecify.prototype.getOffId = function () {
	return this.path + ".bool_false";
}

YAHOO.p3g.form.RadioSpecify.prototype.getUnknownId = function () {
	return this.path + ".bool_unknown";
}

YAHOO.p3g.form.RadioSpecify.prototype.init = function () {
	this.showHideSpecify();
	YAHOO.util.Event.addListener(this.getOnId(), "click", this.showHideSpecify, this, true);
	YAHOO.util.Event.addListener(this.getOffId(), "click", this.showHideSpecify, this, true);
	YAHOO.util.Event.addListener(this.getUnknownId(), "click", this.showHideSpecify, this, true);
}

YAHOO.p3g.form.RadioSpecify.prototype.showHideSpecify = function () {
	var txt = $(this.path + ".specify_wrapper");
	if($(this.getOnId()).checked) {
		txt.show();
	} else {
		txt.hide();
	}
}

/** 
 * Double select
 */
YAHOO.p3g.form.DoubleSelect = function(onId, offId, selectAvailable) {
	this.onId = onId;
	this.offId = offId;
	this.selectAvailable = selectAvailable;
	YAHOO.util.Event.onAvailable([this.onId, this.offId, this.selectAvailable], this.init, this, true);
}

YAHOO.p3g.form.DoubleSelect.prototype.init = function () {
	this.form = $(this.onId).form;
	YAHOO.util.Event.onAvailable(this.onId, this.deselectAll, this.onId);
	YAHOO.util.Event.onAvailable(this.offId, this.deselectAll, this.offId);	
	YAHOO.util.Event.onAvailable(this.form, this.registerOnSubmitListener, this, true);
}

YAHOO.p3g.form.DoubleSelect.prototype.registerOnSubmitListener = function () {
	YAHOO.util.Event.addListener(this.form, 'submit', this.selectAll, this, true);
	YAHOO.p3g.form.formSubmitEvent.subscribe(this.selectAll, this, true);
}

YAHOO.p3g.form.DoubleSelect.prototype.selectAll = function () {
	this.selectAllOptions($(this.onId));
	if(this.selectAvailable) this.selectAllOptions($(this.offId));
}

YAHOO.p3g.form.DoubleSelect.prototype.deselectAll = function (selectId) {
	var inputSelect = $(selectId);
	if(inputSelect !== null) {
		for (i = 0, j = inputSelect.length; i < j; i++) {
			inputSelect.options[i].selected = false;
		}
	}	
}

YAHOO.p3g.form.DoubleSelect.prototype.selectAllOptions = function(inputSelect) {
	if(inputSelect !== null) {
		for (i = 0, j = inputSelect.length; i < j; i++) {
			inputSelect.options[i].selected = true;
		}
	}
}

YAHOO.p3g.form.DoubleSelect.prototype.moveToLeft = function() {
	YAHOO.p3g.form.DoubleSelect.move($(this.offId), $(this.onId));
}

YAHOO.p3g.form.DoubleSelect.prototype.moveToRight = function() {
	YAHOO.p3g.form.DoubleSelect.move($(this.onId), $(this.offId));
}

/**
 * Move selected option form 'selectFrom' to 'selectTo'
 */
YAHOO.p3g.form.DoubleSelect.move = function(selectFrom, selectTo) {
	if (selectFrom !== null || selectTo !== null) {
		for (i = selectFrom.length - 1; i >= 0; i--) {
			if (selectFrom.options[i].selected) {
				var option = new Option(selectFrom.options[i].text, selectFrom.options[i].value);
				selectTo.options[selectTo.length] = option;
				selectFrom[i] = null;
			}
		}
	}
}

/** 
 * Calendar input
 */
YAHOO.p3g.form.Calendar = function (inputId, buttonId, calName, calContainer) {
	this.inputId = inputId;
	this.buttonId = buttonId;
	this.calName = calName;
	this.calContainer = calContainer;
	this.visible = false;
}

YAHOO.p3g.form.Calendar.prototype.handleSelect = function(e, args) {
	var dates = args[0];
	var date = dates[0];
	var year = date[0], month = date[1], day = date[2];
	$(this.inputId).value = day + "/" + month + "/" + year;
	this.hide();
}

YAHOO.p3g.form.Calendar.prototype.updateCal =	function() {
	var txt = $(this.inputId);
	if (txt.value != "") {
		this.calendar.select(txt.value);
		var selectedDates = this.calendar.getSelectedDates();
		if (selectedDates.length > 0) {
			var date = selectedDates[0];
			this.calendar.cfg.setProperty("pagedate", (date.getMonth() + 1) + "/" + date.getFullYear());
			this.calendar.render();
		}
	}
}
	
YAHOO.p3g.form.Calendar.prototype.toggle = 	function() {
	this.visible ? this.hide() : this.show();
}

YAHOO.p3g.form.Calendar.prototype.show = 	function() {
	this.calendar.show();
	this.visible = true;
}

YAHOO.p3g.form.Calendar.prototype.hide = 	function() {
	this.calendar.hide();
	this.visible = false;
}

YAHOO.p3g.form.Calendar.prototype.init = 	function() {
	this.calendar = new YAHOO.widget.Calendar(this.calName, this.calContainer, { title: "Choose a date", close: true });
	this.calendar.cfg.setProperty("MDY_DAY_POSITION", 1); 
	this.calendar.cfg.setProperty("MDY_MONTH_POSITION", 2); 
	this.calendar.cfg.setProperty("MDY_YEAR_POSITION", 3); 	
	this.calendar.selectEvent.subscribe(this.handleSelect, this, true);
	this.hide();
	this.calendar.render();
	YAHOO.util.Event.addListener(this.inputId, "change", this.updateCal, this, true);
	YAHOO.util.Event.addListener(this.buttonId, "click",  this.toggle, this, true);
}

/**
 * List of input text
 */
YAHOO.p3g.form.List = function (listId, path, deleteImgSrc, deleteMsg, size) {
	this.listId = listId;
	this.path = path;
	this.deleteImgSrc = deleteImgSrc;
	this.deleteMsg = deleteMsg;
	this.size = size;
}	

YAHOO.p3g.form.List.prototype.addItem = function(e) {
	
	// check if we need to add a delete button to the first item when we add a new item
	var childrens = $(this.listId).getElementsByClassName('item');
	
	// check if childrens are not empty
	var hasNullChild = false;
	for (i = 0; i < childrens.length && !hasNullChild; i++) {
		var str = childrens[i].firstDescendant().value;
		hasNullChild = str == null || str.length === 0;
	}
	if(hasNullChild) return;
	
	if(childrens.length == 1) {
		var itemId = childrens[0].id;
		var deleteButtonId = "delete_" + itemId;
		var deleteButton = this.createDeleteButton(deleteButtonId); 
		$(itemId).appendChild(deleteButton);
		this.registerDeleteButton(deleteButtonId, itemId);
	}
	
	var itemId = this.path + "_"+ this.size;

	var newInput = document.createElement("input");
	newInput.setAttribute("type", "text");
	newInput.setAttribute("id", itemId);
	newInput.setAttribute("name", this.path);
	
	var deleteButtonId = "delete_" + itemId;
	var deleteButton = this.createDeleteButton(deleteButtonId); 
	
	var newDiv = document.createElement("div");
	newDiv.setAttribute("id", itemId);
	newDiv.setAttribute("class", "item");
	newDiv.appendChild(newInput);
	newDiv.appendChild(document.createTextNode(' '));
	newDiv.appendChild(deleteButton);
	
	$(this.listId).appendChild(newDiv);
	
	this.registerDeleteButton(deleteButtonId, itemId);
	
	this.size++;
}

YAHOO.p3g.form.List.prototype.createDeleteButton = function(deleteButtonId) {
	var deleteButton = document.createElement("button");
	deleteButton.setAttribute("type", "button");
	deleteButton.setAttribute("id", deleteButtonId);
	deleteButton.setAttribute("class", "small deleteButton");
	deleteButton.setAttribute("title", this.deleteMsg);
	
	var deleteImg = document.createElement("img");
	deleteImg.setAttribute("src", this.deleteImgSrc);
	
	deleteButton.appendChild(deleteImg);
	deleteButton.appendChild(document.createTextNode(' ' + this.deleteMsg + ' '));
	
	return deleteButton;
}

YAHOO.p3g.form.List.prototype.removeItem = function(e, itemId) {
	$(itemId).remove();	
	var childrens = $(this.listId).getElementsByClassName('deleteButton');
	if(childrens.length == 1) childrens[0].remove();
}

YAHOO.p3g.form.List.prototype.registerDeleteButton = function(deleteButtonId, itemId) {
	YAHOO.util.Event.addListener(deleteButtonId, "click", this.removeItem, itemId, this);	// this become the execution scope in callback
}

YAHOO.p3g.form.List.prototype.registerAddButton = function(addButtonId) {
	YAHOO.util.Event.addListener(addButtonId, "click", this.addItem, this, true); // this become the execution scope in callback
}
