
var TabInline = new JSTabInlineConstructor();

function JSTabInlineConstructor() {
    
	function GetElementsByClassName(className) { 
		var results = []; 
		walkTheDOM(document.body, function (node) { 
			var a, c = node.className, i; 
			if (c) { 
				a = c.split(' '); 
				for (i = 0; i < a.length; i += 1) { 
					if (a[i] === className) { 
						results.push(node); 
						break; 
					} 
				} 
			} 
		}); 
		return results; 
	}

	function walkTheDOM(node, func) {
		func(node); 
		node = node.firstChild; 
		while (node) { 
			walkTheDOM(node, func); 
			node = node.nextSibling; 
		} 
	}

	var that = {}; 

	that.SetTabIndexes = function() {
		var eEditables = GetElementsByClassName('editable'), i;

		for (i=0; i < eEditables.length; i++) {
			eEditables[i].tabIndex = i+1;
			if (document.attachEvent) { // IE needs to be shown were to tab to!
				var objWrite = document.getElementById(eEditables[i].id.replace('read','write')),
					eStrings = objWrite.getElementsByTagName('input'),
					eTextArea = objWrite.getElementsByTagName('textarea'),
					eSelects = objWrite.getElementsByTagName('select');

				if (eStrings.length > 0) {
					eStrings[0].onkeydown = that.KeyDownHandler;
				}
				if (eTextArea.length > 0) {
					eTextArea[0].onkeydown = that.KeyDownHandler;
				}
				if (eSelects.length > 0) {
					eSelects[0].onkeydown = that.KeyDownHandler;
				}
			}
			
			eEditables[i].onfocus = that.TabbedHere;
		}
	};

	that.TabbedHere = function(evt) {
		evt = evt || event;
		var target = evt.target || evt.srcElement;
		
		that.SwitchEdit(target.id.replace('read',''));
	};

	that.KeyDownHandler = function(evt) {
		evt = evt || event;
		var target = evt.target || evt.srcElement,
			keyCode = evt.keyCode || evt.which;

		if (keyCode == 13 || keyCode == 9) {
			// cancel the default event actions
			evt.returnValue = false;
			evt.cancel = true;
			evt.cancelBubble = true;

			var eEditables = GetElementsByClassName('editable'), i;
				
			for (i=0; i < eEditables.length; i+=1) {
				if (eEditables[i].id === target.parentNode.id.replace('write','read')) {
					eEditables[i].blur();
					if (i+1 < eEditables.length) {
						eEditables[i+1].click();
					}
					break;
				}
			}

			return false;
		}	
	};

	that.SwitchEdit = function(id) {
		var objRead = document.getElementById('read' + id),
			objWrite = document.getElementById('write' + id),
			eStrings = objWrite.getElementsByTagName('input'),
			eTextArea = objWrite.getElementsByTagName('textarea'),
			eSelects = objWrite.getElementsByTagName('select');

		if (objRead.style.display === 'none') {
			objRead.style.display = '';
			objWrite.style.display = 'none';
		}
		else {
			objRead.style.display = 'none';
			objWrite.style.display = '';
			
			if (eStrings.length > 0) {
				eStrings[0].focus();
			}
			if (eTextArea.length > 0) {
				eTextArea[0].focus();
			}
			if (eSelects.length > 0) {
				eSelects[0].focus();
			}
		}
	};

	that.SaveEdit = function(id) {
		var objRead = document.getElementById('read' + id),
			objWrite = document.getElementById('write' + id),
			eStrings = objWrite.getElementsByTagName('input'),
			eTextArea = objWrite.getElementsByTagName('textarea'),
			eSelects = objWrite.getElementsByTagName('select');

		if (eStrings.length > 0) {
			objRead.innerHTML = eStrings[0].value;
		}
		if (eTextArea.length > 0) {
			objRead.innerHTML = eTextArea[0].value;
		}
		if (eSelects.length > 0) {
			objRead.innerHTML = eSelects[0].options[eSelects[0].selectedIndex].text;//alert(objRead.innerHTML);
		}
	};
	
    return that;
}