	 /*constructor function for DynEl objects
	*window:  the window object of the dynamic element
	*id: the unique html id for the element
	*body: html text of the body
	*left: the optional initial x-coord
	*top: optional initial y-coord
	*width: optional width
	*This outputs a style sheet into the current document. 
	*Can only be called from the Head*/
	
	function DynEl(window, id, body, left, top, width) {
	// Remember some arguments
	this.window = window;
	this.id = id;
	this.body = body;
	//Output a css-p stylesheet for the element
	var d = window.document;
	d.writeln('<style type="text/css">')
	d.write('#'+ id + ' {position:absolute;');
	if(left) d.write('left:' + left + ';');
	if(top) d.write('top:' + top + ';');
	if(width) d.write('width:' + width + ';'); 
	d.writeln('}');
	d.writeln('</style>');
	
	/*
	*define methods for the DynEl class, one set for Nav and one for IE
	*/
	// first define the navigator methods
	if (navigator.appName.indexOf("Netscape") != -1) {
	
	DynEl.prototype.output = function() {
	var d = this.window.document; //shortcut variable
	//output the element with a <div> and specify its id
	d.writeln('<div id="' + this.id + '">');
	d.writeln(this.body);
	d.writeln("</div>");
	//Now, for convenience save a reference to the layer object
	//created by the element
	this.layer= d[this.id];
	}
	
	//Methods for moving, hiding, stacking etc.
	DynEl.prototype.moveTo = function(x,y) { this.layer.moveTo(x,y); }
	DynEl.prototype.moveBy = function(x,y) { this.layer.moveBy(x,y); }
	DynEl.prototype.show = function() { this.layer.visibility = "show"; }
	DynEl.prototype.hide = function() { this.layer.visibility = "hide"; }
	DynEl.prototype.setStackingOrder = function(z) { this.layer.zIndex = z; }
	DynEl.prototype.setBgColor = function(color) { this.layer.bgColor = color; }
	DynEl.prototype.setBgImage = function(image) { this.layer.background = image; }
	
	//these methods query position, size and other properties of element
	
	DynEl.prototype.getX = function() { return this.layer.left; }
	DynEl.prototype.getY = function() { return this.layer.top; }
	DynEl.prototype.getWidth = function() { return this.layer.width; }
	DynEl.prototype.getHeight = function() { return this.layer.height; } 
	DynEl.prototype.getStackingOrder = function() { return this.layer.zIndex; } 
	DynEl.prototype.isVisible = function() { return this.layer.visibility == "show"; }
	
	
	/*
	*following method to dynamically change contents of element.
	*Argument(s) should be HTML strings for body of element
	*/
	DynEl.prototype.setBody = function() { 
		for(var i = 0; i < arguments.length; i++)
			this.layer.document.writeln(arguments[i]);
		this.layer.document.close();
		
	}
	/*
	*Method registers a handler for the named event on the element.
	*Event name argument should be the name of an event handler property
	*such as "onmousedown" or "onkeypress". The handler is a function
	*that takes whatever action is necessary. Since Netscape and IE 
	*do not have compatible event objects, all event details are passed
	*as arguments to the handler function. When invoked, it will be passed
	*the following 9 arguments: 1) A reference to the DynEl object
	*2) A string containing the event type
	*3)X-coordinate of the mouse, relative to the DynEl
	*4)Y-coord of the mouse
	*5)Mouse button that was clicked, if any
	*6)Unicode code of the key that was pressed, if any
	*7)A boolean specifying whether the Shift key was down
	*8)A boolean on whether the Control key was down
	*9)A boolean on whether the Alt key was down
	*Event handlers not interested in these arguments do not need to
	*declare them all in their argument lists.
	*/
	DynEl.prototype.addEventHandler = function(eventname, handler) { 
    //arrange to capture events on this layer.
	this.layer.captureEvents(DynEl._eventmasks[eventname]);
	var dynel = this; //Current DynEl for use in the nested function.
	// Define an event handler that will invoke the specified handler
	// and pass it the nine arguments specified above.
	this.layer[eventname] = function(event) { 
		return handler(dynel, event.type, event.x, event.y, 
			event.which, event.which,
			((event.modifiers & Event.SHIFT_MASK) != 0),
			((event.modifiers & Event.CTRL_MASK) != 0),
			((event.modifiers & Event.ALT_MASK) != 0)); 
		}
	}
	
/*
*This method ungregisters the named event handler. It should be
*called with a single string argument such as "ONMOUSEOVER".
*/
DynEl.eventmasks = {
	onabort:Event.ABORT, onblur:Event.BLUR, onchange:Event.CHANGE, onclick:Event.CLICK, ondblclick:Event.DBLCLICK, 
	ondragdrop:Event.DRAGDROP, onerror:Event.ERROR, onfocus:Event.FOCUS, onkeydown:Event.KEYDOWN, onkeypress:Event.KEYPRESS,
	onkeyup:Event.KEYUP, onload:Event.LOAD, onmousedown:Event.MOUSEDOWN, onmousemove:Event.MOUSEMOVE, onmouseout:Event.MOUSEOUT,
	onmouseover:Event.MOUSEOVER, onmouseup:Event.MOUSEUP, onmove:Event.MOVE, onreset:Event.RESET, onresize:Event.RESIZE, 
	onselect:Event.SELECT, onsubmit:Event.SUBMIT, onunload:Event.UNLOAD
	};
}
/*
* Now define methods for Internet Explorer,
* These methods have identical APIs to the ones defined for Netscape above.
* Therefore, we will not repeat all the comments above.
*/
if (navigator.appName.indexOf("Microsoft Internet Explorer") != -1) {
	//The all-important output() method 
	DynEl.prototype.output = function() { 
		var d = this.window.document; //shortcut variable; saves typing
		
		//Output the element within a <DIV> tag. Specify the element id.
		d.writeln('<DIV ID="' + this.id + '">');
		d.writeln(this.body);
		d.writeln("</DIV>");
		
	//Now for convenience, save references to the <DIV> element we've created
	//and to its associated Style element. These will be used throughout the methods that follow.
	this.element = d.all[this.id];
	this.style = this.element.style;
}
	
// Methods to move the dynamic object
DynEl.prototype.moveTo = function(x,y) {
	this.style.pixelLeft = x;
	this.style.pixelTop = y;
}
DynEl.prototype.moveBy = function(x,y) {
	this.style.pixelLeft += x;
	this.style.pixelTop += y;
}

//Methods to set other attributes of the dynamic object
DynEl.prototype.show = function() { this.style.visibility = "visible"; }
DynEl.prototype.hide = function() { this.style.visibility = "hidden"; }
DynEl.prototype.setStackingOrder = function(z) { this.style.zindex = z; }
DynEl.prototype.setBgColor = function(color) { this.style.backgroundColor = color; }
DynEl.prototype.setBgImage = function(image) { this.style.backgroundImage = image; }
//Methods to query the dynamic object
DynEl.prototype.getX = function() { return this.style.pixelLeft; }
DynEl.prototype.getY = function() { return this.style.pixelTop; }
DynEl.prototype.getWidth =  function() { return this.style.width; }
DynEl.prototype.getHeight = function() { return this.style.height; }
DynEl.prototype.getStackingOrder =  function() { return this.style.zindex; }
DynEl.prototype.isVisible =  function() { return this.style.visibility == "visible"; }

//Change the contents of the dynamic element
DynEl.prototype.setBody = function() {
	var body = "";
	for(var i = 0; i < arguments.length; i++) { 
		body += arguments[i] + "\n";
	}
	this.element.innerHTML = body;
}

//Define an event handler.
DynEl.prototype.addEventHandler = function(eventname, handler) { 
	var dynel = this; //Current DynEl for use in the nested function
	//Set an IE4 event handler that invokes the specified handler with the appropriate nine arguments.
	this.element[eventname] = function() {
		var e = dynel.window.event;
		e.cancelBubble = true;
		return handler(dynel, e.type, e.x, e.y, e.button, e.keyCode, e.shiftKey, e.ctrlKey, e.altKey);
		}
	}
	//Remove an event handler.
	DynEl.prototype.removeEventHandler = function(eventname) { delete this.element[eventname]; }
}

}
