/***************************************************************************
 * table.js
 *     :
 ***************************************************************************/
(function($)
{
$.fn.ModuleTable = function(settings)
{
// Private members:
	var config =
	{
	};
	if (settings)
	{	$.extend(config,settings);	}

// Per-node initialization:
/*	this.each(function()
	{
	}); */

/***************************************************************************
 * ModuleTable::AddRow(rowDef)
 *     : Add a row to the table using a JSON object.
 *
 * Parameters:
 *   rowDef =
 *   {
 *     attributes:
 *     {
 *       id: '', ...
 *     }
 *     cells:
 *     [
 *       {
 *         content   : '',
 *         attributes:
 *         {
 *           id: '', ...
 *         }
 *       }, ...
 *     ]
 *   }
 ***************************************************************************/
	this.AddRow = function(rowDef)
	{
	// Gather information.
		var cells = rowDef['cells'];
		var attrs = rowDef['attributes'];

	// Create a row.
		var rowNode = document.createElement('tr');

	// Add attributes to the row.
		for (var attrName in attrs)
		{
			var attrValue = attrs[attrName];
			$(rowNode).attr(attrName,attrValue);
		}

	// Add cells to the row.
		for (var i in cells)
		{
		// Gather (more information).
			var cellDef = cells[i];
			var attrs = cellDef['attributes'];

		// Create the cell.
			var cellNode = document.createElement('td');
			$(cellNode).append(cellDef['content']);

		// Add attributes to the cell.
			for (var attrName in attrs)
			{
				var attrValue = attrs[attrName];
				$(cellNode).attr(attrName,attrValue);
			}

		// Append the cell to the node.
			rowNode.appendChild(cellNode);
		}

	// Append the row to the node.
		this.children('tbody').append(rowNode);
	};

/***************************************************************************
 * ModuleTable::RemoveRow(selector)
 *     : Remove any row that matches a given selector.
 ***************************************************************************/
	this.RemoveRow = function(selector)
	{
	// TODO:
		this.find('> tbody > tr').each(function()
		{
			if ($(selector,this).length)
			{	$(this).remove();	}
		});
	};

// Return the jQuery object.
	return this;
}

})(jQuery);

/***************************************************************************
 * class ModuleTable
 ***************************************************************************/
function ModuleTable()
{
// Ensure this function is only called as a constructor.
	if (!(this instanceof ModuleTable))
	{	return new ModuleTable();	}
	return this;
}

// Inherit from class Object.
ModuleTable.prototype = new Object();

// Static members:

/***************************************************************************
 * ModuleTable::Init
 ***************************************************************************/
ModuleTable.prototype.Init =
function(tableNode)
{
// Parameter validation:
	if (tableNode == null)
	{	return false;	}

// Initialize the table row actions.
	jQuery('tr[action][action!=""]',tableNode).each(function(idx,nodeObj)
	{
	// Gather information.
		var action = nodeObj.getAttribute('action');

	// Apply the specified action.
		if (action == '#')
		{
		// Set the cursor.
			nodeObj.style.cursor = 'default';

		// Stop propagation of the event, but do not prevent the default handler.
			jQuery(nodeObj).click(function(eventObj)
			{	eventObj.stopPropagation();	});
			jQuery(nodeObj).mouseover(function(eventObj)
			{	eventObj.stopPropagation();	});
			jQuery(nodeObj).mouseout(function(eventObj)
			{	eventObj.stopPropagation();	});
		}
		else
		{
		// Set the cursor.
			nodeObj.style.cursor = 'pointer';

		// Define event handlers.
			jQuery(nodeObj).click(function(eventObj)
			{
			// Prevent the default handler.
			// TODO: Will this stop propagation, too?
				ModuleTable.prototype.OnClick(eventObj,this,action);
			});
			jQuery(nodeObj).mouseover(function(eventObj)
			{
			// Prevent the default handler.
			// TODO: Will this stop propagation, too?
				ModuleTable.prototype.OnMouseOver(eventObj,this);
			});
			jQuery(nodeObj).mouseout(function(eventObj)
			{
			// Prevent the default handler.
			// TODO: Will this stop propagation, too?
				ModuleTable.prototype.OnMouseOut(eventObj,this);
			});
		}
	});

// Initialize the table cell actions.
	jQuery('td[action][action!=""]',tableNode).each(function(idx,nodeObj)
	{
	// Gather information.
		var action = nodeObj.getAttribute('action');

	// Apply the specified action.
		if (action == '#')
		{
		// Set the cursor.
			nodeObj.style.cursor = 'default';

		// Stop propagation of the event, but do not prevent the default handler.
			jQuery(nodeObj).click(function(eventObj)
			{	eventObj.stopPropagation();	});
			jQuery(nodeObj).mouseover(function(eventObj)
			{	eventObj.stopPropagation();	});
			jQuery(nodeObj).mouseout(function(eventObj)
			{	eventObj.stopPropagation();	});
		}
		else
		{
		// Set the cursor.
			nodeObj.style.cursor = 'pointer';

		// Define event handlers.
			jQuery(nodeObj).click(function(eventObj)
			{
			// Prevent the default handler.
			// TODO: Will this stop propagation, too?
				ModuleTable.prototype.OnClick(eventObj,this,action);
			});
			jQuery(nodeObj).mouseover(function(eventObj)
			{
			// Prevent the default handler.
			// TODO: Will this stop propagation, too?
				ModuleTable.prototype.OnMouseOver(eventObj,this);
			});
			jQuery(nodeObj).mouseout(function(eventObj)
			{
			// Prevent the default handler.
			// TODO: Will this stop propagation, too?
				ModuleTable.prototype.OnMouseOut(eventObj,this);
			});
		}
	});
}

/***************************************************************************
 * ModuleTable::OnMouseOver
 ***************************************************************************/
ModuleTable.prototype.OnMouseOver =
function(eventObj,currentTarget)
{
// IE -> W3C:
	if (typeof(event) != 'undefined')
	{	eventObj = event;	}
	if (eventObj.target == null)
	{	eventObj.target  = eventObj.srcElement;	}
	if (eventObj.currentTarget == null)
	{	eventObj.currentTarget  = currentTarget;	}

	var domNode = eventObj.currentTarget;
	switch (domNode.className.trim())
	{
	case '' :
		domNode.className = 'highlight';
		break;
	case 'alt' :
		domNode.className = 'alt highlight';
		break;
	}
}

/***************************************************************************
 * ModuleTable::OnMouseOut
 ***************************************************************************/
ModuleTable.prototype.OnMouseOut =
function(eventObj,currentTarget)
{
// IE -> W3C:
	if (typeof(event) != 'undefined')
	{	eventObj = event;	}
	if (eventObj.target == null)
	{	eventObj.target         = eventObj.srcElement;	}
	if (eventObj.currentTarget == null)
	{	eventObj.currentTarget  = currentTarget;	}

	var domNode = eventObj.currentTarget;
	switch (domNode.className.trim())
	{
	case 'highlight' :
		domNode.className = '';
		break;
	case 'alt highlight' :
		domNode.className = 'alt';
		break;
	}
}

/***************************************************************************
 * ModuleTable::OnClick
 ***************************************************************************/
ModuleTable.prototype.OnClick =
function(eventObj,currentTarget,action)
{
// IE -> W3C:
	if (typeof(event) != 'undefined')
	{	eventObj = event;	}
	if (eventObj.target == null)
	{	eventObj.target         = eventObj.srcElement;	}
	if (eventObj.currentTarget == null)
	{	eventObj.currentTarget  = currentTarget;	}

	regEx = new RegExp('^javascript:(.*)$','i');
	if (matches = regEx.exec(action))
	{	eval(matches[1]);			}
	else
	{	document.location = action;	}

// Stop the event propagation.
/* TODO: IE does not support this.
	eventObj.stopPropagation();
*/
}

