//<SCRIPT LANGUAGE="Javascript">
/////////////////////////////////////////////////////////////
//
// Miscellaneous utilities
// Copyright (c) 2000 by Bob Clary, All Rights Reserved
//
/////////////////////////////////////////////////////////////

registerFile('bcUtils.js', 'oop.js');


function Contains(eOuter, eInner)
{
	var i;
	var result = false;
	
	if (!eOuter || !eInner)
		result = false;
	else if (eOuter == eInner)
		result = true;
	else
		for (i = 0; i < eOuter.childNodes.length; i++)
			if (Contains(eOuter.childNodes.item(i), eInner))
			{
				result = true;
				break;
			}
			
	//writeLogWindow('Contains(' + eOuter.nodeName + ':' + eOuter.getAttribute('id') + ', ' + eInner.nodeName + ':' + eInner.getAttribute('id') + ')==' + result );

	return result;
}

// dom core does not have this function
function GetElementById(This, elementId)
{
	var id = This.getAttribute('id');
	
	if (id == elementId)
		return This;
				
	var element = null;
	var node = null;
	var i;
			
	for (i = 0; i < This.childNodes.length; i++)
	{
		node = This.childNodes.item(i);
		// HACK: 
		var nodeType = 0;
		if (typeof(node.nodeType) != 'undefined')
			nodeType = node.nodeType;
		else if (typeof(node.getNodeType) != 'undefined')
			nodeType = node.getNodeType();

		if (nodeType == 1)
		{
			element = GetElementById(node, elementId);
			if (element != null)
				break;
		}
	}
	return element;
}

// getPosition returns object with left, top properties
// that correspond to the offsets from the offsetParent root
// of the page... typically BODY.
// this means it is the left,top coordinate of the the bounding
// box consisting of the margin, border, padding and content.
// 
// note IE places offsetLeft,offsetTop at the upper left corner of
// the border, while Mozilla places it at the upper left corder of 
// the padding.

// the following assumes all units are in px

function getPosition(elm)
{
	if (!elm)
		return null;

	var pos = new Object();
	
	pos.left = 0;
	pos.top  = 0;

	while (elm && /* fix for HTML.offsetParent */ elm != document.body.offsetParent)
	{
		if (elm.nodeType == 1)
		{
			if (is_ie5)
			{
				if (elm.style.left)
					pos.left += stringToNumber(elm.style.left);
				else
					pos.left += elm.offsetLeft - stringToNumber(elm.style.marginLeftWidth);
					
				if (elm.style.top)
					pos.top += stringToNumber(elm.style.top);
				else
					pos.top  += elm.offsetTop - stringToNumber(elm.style.marginTopWidth);
			}
			else
			{
				if (elm.style.left)
					pos.left += stringToNumber(elm.style.left);
				else
					pos.left += elm.offsetLeft - stringToNumber(elm.style.marginLeftWidth) - stringToNumber(elm.style.borderLeftWidth);

				if (elm.style.top)
					pos.top += stringToNumber(elm.style.top);
				else
					pos.top += elm.offsetTop - stringToNumber(elm.style.marginTopWidth) - stringToNumber(elm.style.borderTopWidth);
					
			}
		}
		elm = elm.offsetParent;
	}
	return pos;
}

function setPosition(elm, left, top)
{
	var parentPosition;
	
	if (!elm)
		throw(new bcException('Element can not be null', 'bcUtils.js', 'setPosition'));
		
	if (elm.nodeType != 1)
		throw(new bcException('Must be an Element', 'bcUtils.js', 'setPosition'));
		
	if (elm == document.body)
		throw(new bcException('Body Element not positionable', 'bcUtils.js', 'setPosition'));

	if (elm.offsetParent != null)
	{
		parentPosition = getPosition(elm.offsetParent);

		left -= parentPosition.left;
		top  -= parentPosition.top;
	}

	elm.style.left = left;
	elm.style.top  = top;
}

function getBoundary(elm)
{
	var boundary = new Object();
	if (elm.nodeType != 1)
		elm = elm.parentNode;
		
	var Style = elm.style;
		
	var pos = getPosition(elm);
		
	boundary.left   = pos.left;
	boundary.top    = pos.top;
	boundary.right  = pos.left + stringToNumber(elm.style.marginLeft) + elm.offsetWidth  + stringToNumber(elm.style.marginRight);
	boundary.bottom = pos.top  + stringToNumber(elm.style.marginTop)  + elm.offsetHeight + stringToNumber(elm.style.marginBottom);

	return boundary;
}

function getEventPosition(evt)
{
	var eventPos;
	
	if (evt.target.nodeType == 1)
		eventPos = getPosition(evt.target.offsetParent);
	else
		eventPos = getPosition(evt.target.parentNode);
	
	if (eventPos != null)
	{
		eventPos.left += evt.clientX;
		eventPos.top  += evt.clientY;
	}
	else
	{
		eventPos = new Object();
		eventPos.left = 0;
		eventPos.top = 0;
	}

	return eventPos;
}	
	
function ElementContainsEvent(elm, evt)
{
	var i;
	var result   = null;
	var boundary = getBoundary(elm);
	//var eventPos = getEventPosition(evt);

	
	if (!elm || !evt)
		result = null;
	else if (elm.nodeType != 1)
		result = null;
	else if (evt.clientX < boundary.left || evt.clientX > boundary.right  || evt.clientY < boundary.top || evt.clientY > boundary.bottom)
		result = null;
	else
	{
		for (i = 0; i < elm.childNodes.length; i++)
		{
			if (elm.nodeType == 1)
				result = ElementContainsEvent(elm.childNodes.item(i), evt);
			
			if (result != null)
				break;
		}
		
		if (result == null)
			result = elm;
	}
			
	return result;
}	

function ElementContainsPoint(elm, left, top)
{
	var i;
	var result   = null;
	var boundary = getBoundary(elm);
	
	if (!elm)
		result = null;
	else if (elm.nodeType != 1)
		result = null;
	else if (left < boundary.left || left > boundary.right  || top < boundary.top || top > boundary.bottom)
		result = null;
	else
	{
		for (i = 0; i < elm.childNodes.length; i++)
		{
			if (elm.nodeType == 1)
				result = ElementContainsPoint(elm.childNodes.item(i), left, top);
			
			if (result != null)
				break;
		}
		
		if (result == null)
			result = elm;
	}
			
	return result;
}	

//</SCRIPT>

