//globals
var doc;
var can_switch_view = true;
var docElement;

/* the location of the scripts  */
var ScriptLocation   = "";
var ViewInfoLocation = "";
var WebLiveLocation = "";

/* this actually starts up the needed external scripts */
function runscriptfromsrc(src) {
	document.write(unescape("%3Cscript src='" + src + "' type='text/javascript'%3E%3C/script%3E"));
}
function runscriptinline(fn) {
	document.write(unescape("%3Cscript type='text/javascript'%3E "+fn+" %3C/script%3E"));
}

/* utility functions for checking/adding/removing classes of elements */
function hasClass(ele,cls) {
	return ele.className && ele.className.match(new RegExp('(\\s|^)'+cls+'(\\s|$)'));
}
function addClass(ele,cls) {
	if (ele && !hasClass(ele,cls)) ele.className += " "+cls;
}
function removeClass(ele,cls) {
	if (ele && hasClass(ele,cls)) {
		var reg = new RegExp('(\\s|^)'+cls+'(\\s|$)');
		ele.className=ele.className.replace(reg,' ');
	}
}

// constructor
function magnaviewweblive(config) {
	this.ScriptLocation = ScriptLocation;

	runscriptfromsrc(this.ScriptLocation+'wz_jsgraphics.js');
	this.elements     = new Object();
	this.translations = new Object();
	this.viewinfo     = new Object();
	this.events       = new Object();
	this.mouse        = new Object();
	this.translations.overview = "Overview";

	this.thisview  = 0;
	if( /[&\?]v=/.test(location.search) ) {
		this.thisview =  /[&\?]v=([^&]*)/.exec(location.search)[1];
	}

	this.scriptuid = 0;

	this.settings = new Object();

	this.settings.overviewshowing     = true;
	this.settings.Loading             = (this.settings.ShowLoadingScreen || (this.settings.pagetype == 2));

	this.graphics = new Array();	

	this.curviewinfo = -1;
	this.prevviewinfo = -1;
	this.viewinfolist = new Array();

	//this.mode = 2; obsolete

	this.oldcurnodes         = new Array();
	this.dynloadingnodes = false;
	this.showhintdelayed = false;
	this.lastx = -1;
	this.lasty = -1;

	window.mv_object = this;

	attachEventFunction(window, 'unload', function() { window.mv_object.unload(); } );
	
	if (config) { // dynamic version
		var sUrl = this.createurl({'type':'settings', 'data':config}); //settings url contruction
		var args = window.location.search.substring(1).split("&") || [""]; //querystring arguments
		for(var i=0 ; i<args.length; i++) { //add full querystring to url, except specified keywords
			if (!(args[i].split("=")[0] in {"content-type":'','type':'','data':'','view':''})) sUrl+='&'+args[i]; 
		}
		runscriptfromsrc(sUrl);
	} else {
		runscriptfromsrc(ViewInfoLocation+'settings.js');
	}

	/*call initialisation.
	this method is used so all scripts are executed in correct order. The init
	function depends on the settings script loaded just before */
	//runscriptinline("window.mv_object.init()");

}

magnaviewweblive.prototype.setElement = function(name, eltid) {
	this.elements[name] = document.getElementById(eltid);
}	

magnaviewweblive.prototype.init = function() {

	/* initialise globals */
	doc = document;
	docElement = (typeof doc.compatMode != "undefined" && doc.compatMode != "BackCompat")? "documentElement" : "body"

	/* initialise buttons */
	if (this.elements.overview) {
		this.settings.thumbnailsoverview = true;
		this.elements.overview.onclick = function() { 
			this.mvobj.selectoverview();
			hide(this.mvobj.elements.overview);
			show(this.mvobj.elements.curview);
		};
		this.elements.overview.mvobj = this;
		
		if(this.elements.curview) {
			this.elements.curview.mvobj = this;
			hide(this.elements.curview);
			this.elements.curview.onclick = function() {
				var toview = this.mvobj.prevviewinfo;
				if(toview==-1) { //initial
					if(this.mvobj.viewinfolist.length>1) { toview = 1; }
				}
				this.mvobj.selectview(toview);
				hide(this.mvobj.elements.curview);
				show(this.mvobj.elements.overview);
			}
		}
	}
	
	if (this.elements.pdf) {
		this.elements.pdf.href = this.createurl({'type':'pdf','table':'false','allviews':'true','view':0});
	}
	
	if (this.elements.nextview) {
		this.elements.nextview.onclick = function() { this.mvobj.nextview() };
		this.elements.nextview.mvobj = this;
	}
	if (this.elements.prevview) {
		this.elements.prevview.onclick = function() { this.mvobj.prevview() };
		this.elements.prevview.mvobj = this;
	}
	if (this.elements.moredetail) {
		this.elements.moredetail.onclick = function() { this.mvobj.moredetail() };
		this.elements.moredetail.mvobj = this;
	}
	if (this.elements.zoomout) {
		this.elements.zoomout.onclick = function() { this.mvobj.zoomout() };
		this.elements.zoomout.mvobj = this;
	}
	if (this.elements.lessdetail) {
		this.elements.lessdetail.onclick = function() { this.mvobj.lessdetail() };
		this.elements.lessdetail.mvobj = this;
	}
	if (this.elements.hideselection) {
		this.elements.hideselection.onclick = function() {this.mvobj.hideselection() };
		this.elements.hideselection.mvobj = this;
	}
	if (this.elements.showselection) {
		this.elements.showselection.onclick = function() {this.mvobj.showselection() };
		this.elements.showselection.mvobj = this;
	}
	if (this.elements.showall) {
		this.elements.showall.onclick = function() {this.mvobj.showall() };
		this.elements.showall.mvobj = this;
	}
	
	if (this.elements.nodeinfo) {
		disableSelection(this.elements.nodeinfo);
	}

	if (this.elements.selectview)
		this.fillselector(this.elements.selectview);
	if (this.elements.thumbnails)
		this.fillthumbs(this.elements.thumbnails);

	/* Generate main view div html */
	if(this.elements.main) {
		viewareadiv = this.elements.main;
		disableSelection(viewareadiv);
	} else {
		viewareadiv = false;
	}

	var drawdiv = document.createElement('div');
	this.elements.draw = drawdiv;
	drawdiv.className = 'draw';
	drawdiv.style.position = 'relative';
	drawdiv.style.width    = '100%';
	drawdiv.style.height   = '100%';

	var drawimage = document.createElement('img');
	drawimage.className = 'drawimg';
	drawimage.border = 0;
	drawimage.style.visibility = 'hidden';
	this.elements.drawimage = drawimage;
	if (this.pagetype == 1) {
		drawimage.width = this.settings.TreemapWidth;
		drawimage.height = this.settings.TreemapHeight;
	}
	
	// Mouse vars
	this.mouse.nodesselected    = false;
	this.mouse.nodeshidden      = false;
	this.mouse.zoomedin         = false;
	this.mouse.candrop          = false;
	this.mouse.clickobj         = {};
	this.mouse.dragObj          = {};
	this.mouse.selectaction     = '';
	this.mouse.expectedaction   = '';
	this.mouse.source           = '';
	this.mouse.attributeBranch  = 0;
	this.mouse.startX           = 0;
	this.mouse.startY           = 0;
	
	if (viewareadiv) {
		pos = getElementPosition(viewareadiv);
		this.mouse.offsetX      = pos.Left;
		this.mouse.offsetY      = pos.Top;
	} else {
		this.mouse.offsetX      = 0;
		this.mouse.offsetY      = 0;
	}
	
  document.ondragstart = function(e) { return false; }
	document.body.onmousedown = function(evt) { window.mv_object.onmousedown(evt) };
	document.body.onmouseup   = function(evt) { window.mv_object.onmouseup(evt) };
	
	var selectdiv = document.createElement('div');
	this.elements.select = selectdiv;
	selectdiv.className = 'drawselect';
	selectdiv.style.position = 'absolute';
	selectdiv.style.visibility = 'hidden';
	drawdiv.appendChild(selectdiv);
	
	this.elements.draw.mvobj = this;

	drawdiv.appendChild(drawimage);

	for (var i = 0; i < this.settings.allmaxdepth; ++i) {
		var drawarea = document.createElement('div');
		drawarea.id = 'adrawarea'+i;
		drawarea.style.position = 'absolute';
		drawarea.style.top      = '0';
		drawarea.style.bottom   = '0';
		drawarea.style.left     = '0';
		drawarea.style.right    = '0';
		drawdiv.appendChild(drawarea);
	}

	if(viewareadiv){
		viewareadiv.appendChild(drawdiv);
	}
	
	if (this.elements.attributes) {
		this.elements.attributes.innerHTML = this.viewinfo.attributesString;
		disableSelection(this.elements.attributes);
	}

	/* From HTML script */
	for (var i = 0; i < this.settings.allmaxdepth; ++i) {
		this.graphics[i] = new jsGraphics('adrawarea'+i);
	}

	this.settings.mv_width    = this.settings.TreemapWidth;
	this.settings.mv_height   = this.settings.TreemapHeight;
	this.settings.ASPMode     = 0;
	this.settings.NoRight     = 0;
	this.settings.NoHeader    = 0;

	/* From body.onload = initialize */
	this.init_buttons();
	this.settings.screenh = document.getElementsByTagName("body")[0].innerHeight;

	{this.init_mousemove();};
    	window.onresize=resizehandler;

	this.initposition('0');
	
	/* add keyboard shortcuts */
	attachEventFunction(document, 'keydown', this.shortcuts.handle);

	//load the overview or the first view
	// if i do this directly, the nodes request will return something not matching the image, no idea why...
	// possibly concurrency issues within the COM object? returning node info for a previously rendered view?
	// ( seems to be the node info for a 600x600 image )
	if(!( /[&\?]v=/.test(location.search) )) { //no viewnumber defined
		this.thisview = 0;
	}
	window.setTimeout('window.mv_object.selectview('+this.thisview+')', 1)
}

magnaviewweblive.prototype.fillselector = function(selector) {
	selector.mvobj = this;
	selector.onchange = function() { this.mvobj.selectview(this.selectedIndex); };
	
	if (this.settings.thumbnailsoverview) {
		this.viewinfolist.unshift(new Array("overview"));
		var option = document.createElement('option');
		option.innerHTML = this.translations.overview;
		selector.appendChild(option);
	}

	var groups = new Array();
	for (var i = 0; i < this.groupinfolist.length; ++i) {
		groups[i] = document.createElement('optgroup');
		groups[i].label = (i+1) + '. ' + this.groupinfolist[i];
		selector.appendChild(groups[i]);
	}

	for (var i = 0; i < this.viewinfolist.length; ++i)
	if (this.viewinfolist[i][0] == "group") {
		var option = document.createElement('option');
		option.innerHTML = (this.viewinfolist[i][1]+1) + '. Title View';
		groups[this.viewinfolist[i][1]].appendChild(option);
	} else if (this.viewinfolist[i][0] == "view") {
		var option = document.createElement('option');
		option.innerHTML = (this.viewinfolist[i][3]+1) + '.' + (this.viewinfolist[i][4]+1) + '. ' +this.viewinfolist[i][1];
		groups[this.viewinfolist[i][3]].appendChild(option);
	}
}

magnaviewweblive.prototype.fillthumbs = function(obj)
{
	//TODO: this function could be simplified!
	var lastgroup = -1;
	var ul = document.createElement('ul');
	for (var i = 0; i < this.viewinfolist.length; ++i) {
		if (this.viewinfolist[i][0] == "view") {
			if (lastgroup != this.viewinfolist[i][3]) {
				lastgroup = this.viewinfolist[i][3];
				var grouphdr = document.createElement('li');
				grouphdr.className = 'header';
				grouphdr.innerHTML = (this.viewinfolist[i][3]+1) + '. ' + this.groupinfolist[this.viewinfolist[i][3]];
				ul.appendChild(grouphdr);
			}

			var viewnum = this.viewinfolist[i][2];
			var li = document.createElement('li');
			var thumbdiv = document.createElement('div');
			var thumbimgdiv = document.createElement('div');

			var thumbimg = document.createElement('img');
			thumbimg.alt = this.viewinfolist[i][1];
			thumbimg.className = "thumbimg";
			if (this.settings.pagetype == 2) {
				thumbimg.src = this.createurl({'type':'thumbnails','view':viewnum,'th':78,'tw':115});
			} else {
				thumbimg.src = 'T_view_'+viewnum+'.png?r='+Math.round(Math.random()*999999);
			}
			thumbimg.mvobj = this;
			thumbimg.selnum = i;
			thumbimg.onclick = function() { this.mvobj.selectview(this.selnum); };

			thumbimgdiv.className = "thumb";
			thumbimgdiv.appendChild(thumbimg);
			thumbdiv.appendChild(thumbimgdiv);

			var thumbtxt = document.createElement('span');
			thumbtxt.innerHTML = (this.viewinfolist[i][3]+1) + '.' + (this.viewinfolist[i][4]+1) + '. ' + this.viewinfolist[i][1];		
			thumbdiv.appendChild(thumbtxt);

			li.appendChild(thumbdiv);
			ul.appendChild(li);
			
		} else if (this.viewinfolist[i][0] == "group") {
			lastgroup = this.viewinfolist[i][1];
			var grouphdr = document.createElement('li');
			grouphdr.className = 'header';
			grouphdr.innerHTML = (this.viewinfolist[i][1]+1) + '. ' + this.groupinfolist[this.viewinfolist[i][1]];
			ul.appendChild(grouphdr);

			var groupnum = this.viewinfolist[i][2];
			var li = document.createElement('li');
			var thumbdiv = document.createElement('div');
			var thumbimgdiv = document.createElement('div');
			
			var thumbimg = document.createElement('img');
			thumbimg.alt = this.viewinfolist[i][1];
			thumbimg.className = "thumb";
			if (this.settings.pagetype == 2) {
				thumbimg.src = this.createurl({'type':'groupthumbnail','group':groupnum,'th':78,'tw':115});
			} else {
				thumbimg.src = 'T_group_'+groupnum+'.png?r='+Math.round(Math.random()*999999);
			}
			thumbimg.mvobj = this;
			thumbimg.selnum = i;
			thumbimg.onclick = function() { this.mvobj.selectview(this.selnum); };

			thumbimgdiv.className = "thumb";
			thumbimgdiv.appendChild(thumbimg);
			thumbdiv.appendChild(thumbimgdiv);

			var thumbtxt = document.createElement('span');
			thumbtxt.innerHTML = (this.viewinfolist[i][1]+1) + '. Group Image';
			thumbdiv.appendChild(thumbtxt);

			li.appendChild(thumbdiv);
			ul.appendChild(li);
		}
	}
	obj.appendChild(ul);
}


magnaviewweblive.prototype.selectview = function(index) {
	if (index == -1) return;
	if (index >= this.viewinfolist.length) return;
	this.prevviewinfo = this.curviewinfo;
	this.curviewinfo = index;
	if (this.elements.selectview) {
		this.elements.selectview.selectedIndex = this.curviewinfo;
	}

	this.settings.overviewshowing = (this.viewinfolist[this.curviewinfo][0] == "overview");

	if (this.viewinfolist[this.curviewinfo][0] == "overview") {
		this.overview();
		addClass(this.elements.thumbnails, 'overview');
	} else if (this.viewinfolist[this.curviewinfo][0] == "view") {
		this.changeview(this.viewinfolist[this.curviewinfo][2]);
		removeClass(this.elements.thumbnails, 'overview');
	} else if (this.viewinfolist[this.curviewinfo][0] == "group") {
		this.changegroup(this.viewinfolist[this.curviewinfo][2]);
		removeClass(this.elements.thumbnails, 'overview');
	}

	if(typeof(this.changecallback)=='function') {
		this.changecallback();
	}
}

// navigates to the view designated by its view index
magnaviewweblive.prototype.gotoviewbyindex = function(index) {
	for(var i = 0; i < this.viewinfolist.length; ++i) {
		if (this.viewinfolist[i][0] == "view" && this.viewinfolist[i][2] == index) {
			this.selectview(i);
			return;
		}
	}
}

// navigates to the group designated by its group index
magnaviewweblive.prototype.gotogroupbyindex = function(index) {
	for(var i = 0; i < this.viewinfolist.length; ++i) {
		if (this.viewinfolist[i][0] == "group" && this.viewinfolist[i][2] == index) {
			this.selectview(i);
			return;
		}
	}
}

magnaviewweblive.prototype.initposition = function(_nr) {
//this function sets the correct offset for the treemap image
//needed for relative positioning

	//TODO: check for IE7
	var agent = navigator.userAgent;
	var vers = "";
	doc.onmousemove = mousemove;

	//IE: currentStyle
	//moz: getComputedStyle
	var drawarea = this.elements.draw;

	if (this.ASPMode==0)	{
		if(doc.defaultView){ //w3c DOM
			var drawstyle = doc.defaultView.getComputedStyle(drawarea, null);
			var divOffsetY = drawstyle.getPropertyValue('top').split('px');
			var divOffsetX = drawstyle.getPropertyValue('left').split('px');
		}
		else if (drawarea.currentStyle) { //IE
			var divOffsetY = drawarea.currentStyle.top.split('px');
			var divOffsetX = drawarea.currentStyle.left.split('px');
		}
		this.settings.TreemapTop  = parseInt(divOffsetY[0]) ;
		this.settings.TreemapLeft = parseInt(divOffsetX[0]) ;
	} else {
		this.settings.TreemapLeft = findPosX(drawarea);
		this.settings.TreemapTop  = findPosY(drawarea);
	}
	if (this.settings.pagetype == 2) {
		resizehandler();
	}
};

magnaviewweblive.prototype.init_buttons = function() {
/*	initialize the 'buttons' that are needed for the navigation. Enabling of
	certain elements is dependent on displaydepth, zoomdepth and viewnumber */
	setenabled(this.elements.lessdetail		, this.viewinfo.depth != 1);
	setenabled(this.elements.moredetail		, this.viewinfo.depth != (this.viewinfo.maximumdepth-this.viewinfo.zoomdepth));
	setenabled(this.elements.print     		, !this.settings.thumbnailsoverview);
	setvisible(this.elements.zoomout   		, this.mouse.zoomedin);
	setvisible(this.elements.hideselection, false);
	setvisible(this.elements.showselection, false);
	setvisible(this.elements.showall			, false);

	setenabled(this.elements.prevview, this.curviewinfo>0);
	setenabled(this.elements.nextview, this.curviewinfo<this.viewinfolist.length-1);
	setenabled(this.elements.overview, this.settings.thumbnailsoverview);
};

magnaviewweblive.prototype.update_buttons = function() {
/*	this function updates the state of the 'buttons' of the navigation */
	var isview = this.viewinfolist[this.curviewinfo][0] == "view";
	setenabled(this.elements.lessdetail, isview && this.viewinfo.depth != 1);
	setenabled(this.elements.moredetail, isview && this.viewinfo.depth != (this.viewinfo.maximumdepth-this.viewinfo.zoomdepth));
  setvisible(this.elements.zoomout			, isview && this.mouse.zoomedin);
	setvisible(this.elements.hideselection, isview && this.mouse.nodesselected);
	setvisible(this.elements.showselection, isview && this.mouse.nodesselected);
	setvisible(this.elements.showall			, isview && this.mouse.nodeshidden);


	if (this.settings.thumbnailsoverview){
		if(this.settings.overviewshowing) {
			disable(this.elements.print);
			if (this.elements.print) {
				this.elements.print.onclick = function() {};
			}
		} else {
			enable(this.elements.print);
			if (this.elements.print) {
				this.elements.print.onclick = function() {window.print()};
			}
		}
	}

	setenabled(this.elements.prevview, this.curviewinfo>0);
	setenabled(this.elements.nextview, this.curviewinfo<this.viewinfolist.length-1);
	if(this.settings.overviewshowing) {
		hide(this.elements.overview);
		show(this.elements.curview);
	} else {
		show(this.elements.overview);
		hide(this.elements.curview);
	}
};

magnaviewweblive.prototype.shortcuts = {
	all: {
		219 : function() { window.mvobj.prevview(); } ,   // [
		221 : function() { window.mvobj.nextview() } ,    // ]
		123: function() { window.mvobj.selectoverview() },// F12
		107: function() { window.mvobj.moredetail() },    // +
		109: function() { window.mvobj.lessdetail() }     // -
	},
	add : function(code, fn) {
		this.all[code] = fn;
	},
	remove: function(code) {
		delete(this.all[code]);
	},
	handle : function(e) {
		e = e || window.event;
		if (e.keyCode) code = e.keyCode;
		else if (e.which) code = e.which;
		//if(e.shiftKey) { code += 1000 }
		if(typeof(window.mvobj.shortcuts.all[code]) == 'function') {
			window.mvobj.shortcuts.all[code]();
		}
	}
};

magnaviewweblive.prototype.overview = function() {
//  this function hides the current view and shows the overview
	this.settings.overviewshowing = true;
	
	this.update_buttons();
	this.ChangeFilter();

	this.hideloadingscreen();
}

magnaviewweblive.prototype.showloadingscreenforscript = function(js) {
	// be sure we make the loading div visible first
	this.showloadingscreen();
	// call the real function with 1ms delay, so the browser gets a chance
	// to rerender and actually show the loading div
	window.mvobj = this;
	window.setTimeout(js, 1)
};

magnaviewweblive.prototype.hideloadingscreen = function () {
	if (this.elements.loadingscreen) {
		this.elements.loadingscreen.style.display = 'none';
		this.elements.loadingscreen.style.visibility = 'hidden';
	}
}

magnaviewweblive.prototype.showloadingscreen = function() {
	if (this.elements.loadingscreen) {
		this.elements.loadingscreen.style.display = '';
		this.elements.loadingscreen.style.visibility = 'visible';
	}
};

magnaviewweblive.prototype.changeview = function(url) {
	//this.showloadingscreenforscript('window.mvobj.do_changeview('+url+')');
	//does't seem to be needed anymore? test in IE6/8 etc
	this.showloadingscreen();
	this.do_changeview(url);
}

magnaviewweblive.prototype.do_changeview = function(url) {
	this.thisview = url;
	this.disabledrawing();
	this.settings.displayoverlay = false;
	this.settings.overviewshowing = false;
	this.changeNodes(url,"","","",false);
	this.switchview(url);
}

magnaviewweblive.prototype.changegroup = function(group) {
	this.showloadingscreen();
	this.thisview = -1;

	this.disabledrawing();
	this.settings.displayoverlay = false;

	this.settings.overviewshowing = false;

	if (can_switch_view) {
		if (this.settings.pagetype == 2) {
			this.calcImageSize();
			var ImageArea = this.createurl({'type':'groupimage','group':group});
		} else {
			var ImageArea = 'group_'+group+'.png?r='+Math.round(Math.random()*999999);
		}
		this.changeImage(ImageArea);
	}

	if (this.elements.legend)
		this.elements.legend.innerHTML = '';
	if (this.elements.nodeinfo)
		this.givenodeinfo(-1);
	if (this.elements.filter)
		this.elements.filter.innerHTML = '';
	if (this.elements.comment)
		this.elements.comment.innerHTML = '';

	this.update_buttons();
	this.hideloadingscreen();
	if(this.elements.totalview) 
		this.elements.totalview.style.visibility = "visible";

}

magnaviewweblive.prototype.disabledrawing = function() {
	this.HideLinesJS();
};

magnaviewweblive.prototype.HideLinesJS = function () {
	var olddepth = this.viewinfo.depth;
	for(var j=0; j<=olddepth; j++) {
		if (this.graphics[j]) {
			this.graphics[j].clear();
		}
		this.oldcurnodes[j] = -1;
		if(this.settings.GenerateNodeinfo && this.elements.nodeinfo){
			//clear the nodeinfo
			var nodeinfofield = this.elements.nodeinfo;
			this.givenodeinfo(-1);
		}
		//'hack' for IE, to resolve the >100% problem
		if (!(self.innerHeight) && this.graphics[j]) {
			this.graphics[j].setStroke(0);
			this.graphics[j].drawLine(0,0,0,0);
			this.graphics[j].paint();
		}
	}
};

magnaviewweblive.prototype.switchview = function(url) {
//this function changes the image area
	if (can_switch_view) {
		if (this.settings.pagetype == 2) {
			this.calcImageSize();
			var ImageArea = this.createurl({'type':'image','view':url});
		} else {
			var ImageArea = 'view_'+url+'.png?r='+Math.round(Math.random()*999999);
		}
		this.changeImage(ImageArea);
	}
}

magnaviewweblive.prototype.calcImageSize = function() {
	if(this.elements.main) {
		imageArea = this.elements.main.parentNode;
		var hiddenfix = (imageArea.style.display == 'none');
		if (hiddenfix) {
			imageArea.style.display = '';
			imageArea.style.visibility = 'hidden';
		}
		

		var neww = this.elements.main.clientWidth;
		if (neww > 0 && imageArea.offsetWidth != imageArea.clientWidth) {
			neww = neww + (imageArea.offsetWidth - imageArea.clientWidth);
		}

		var newh = this.elements.main.clientHeight;
		if (newh > 0 && imageArea.offsetHeight != imageArea.clientWidth) {
			newh = newh + (imageArea.offsetHeight - imageArea.clientHeight);
		}

		if (neww < 0 || newh < 0) {
		  neww = parseFloat(this.elements.main.style.width);
		  newh = parseFloat(this.elements.main.style.height);
		}
		
		mvobj.settings.TreemapTop  = findPosY(mvobj.elements.draw);
		mvobj.settings.TreemapLeft = findPosX(mvobj.elements.draw);
		
		if (hiddenfix) {
			imageArea.style.display = 'none';
			imageArea.style.visibility = '';
		}
	}

	if ((neww > 0) && (newh > 0) && ((neww!=mvobj.settings.mv_width) || (newh!=mvobj.settings.mv_height)) ){
			this.settings.mv_width  = neww;
			this.settings.mv_height = newh;
			return true;
	}
	return false
}


// IE 6 version of calcImageSize
if(/MSIE 6\.0/.test(navigator.appVersion)) {
	magnaviewweblive.prototype.calcImageSize = function () {
		if(this.elements.main) {
		  neww = parseFloat(this.elements.main.style.width);
		  newh = parseFloat(this.elements.main.style.height);
		}

		if ((neww > 0) && (newh > 0) && ((neww!=mvobj.settings.mv_width) || (newh!=mvobj.settings.mv_height)) ){
				this.settings.mv_width  = neww;
				this.settings.mv_height = newh;
				return true;
		}
		return false
	}
}

magnaviewweblive.prototype.changeImage = function(url) {
	if (this.curviewinfo != this.prevviewinfo) {
	  this.elements.main.parentNode.scrollLeft = 0;
	  this.elements.main.parentNode.scrollTop  = 0;
	}
	this.elements.drawimage.src = url;
	this.elements.drawimage.style.visibility = 'visible';
};

magnaviewweblive.prototype.changeNodes = function(number, attribute, value, hide, listbox) {
// removes the old nodes file out the source and replaces it by the current files
	var el = document.getElementById("js_variables");
	if (el)
		el.parentNode.removeChild(el);
	var script   = document.createElement('script');
	script.type  = 'text/javascript';
	script.id    = 'js_variables';
	script.defer = true;
	if (this.settings.pagetype ==1) {
		script.src = 'nodes_'+number+'.js';
	} else {
		// note: hide parameter is always '', so we ignore it...
		script.src = this.createurl({
			'type':'nodes',
			'view':number,
			'attribute':attribute,
			'Listbox': (listbox ? value : ''),
			'value': (!listbox ? value : ''),
			'select': this.mouse.selectaction
		});
	}
	document.getElementsByTagName("head")[0].appendChild(script);
};

magnaviewweblive.prototype.ShowView = function(){
	if (!this.settings.overviewshowing && this.elements.totalview) {
		this.elements.totalview.style.visibility = "visible";
	}
	var imageArea = this.elements.main.parentNode;
	if (imageArea) {
		if (mvobj.viewinfo.customwidth > 0 || mvobj.viewinfo.customheight > 0) {
			imageArea.style.overflow = 'auto';
		} else {
			imageArea.style.overflow = 'hidden';
		}
	}
}

var resizeTimeout = 0;
function resizehandler() {
	
	function doResize(mvobj) {
		if (mvobj.calcImageSize()) {
			//if IE7 and in iframe do not showloadingscreen, as this will cause the browser to fire many resize events
			if (!(window.XMLHttpRequest) || (top.location == self.location)) {
				mvobj.showloadingscreen();
			}
			mvobj.selectview(mvobj.curviewinfo);
		} 
	}

	var mvobj = window.mv_object;

	//IE fires the onresize event continiously, Firefox only after user is ready.
	//force IE to update the screen only once!
	if (mvobj.settings.pagetype ==2){
		if (self.innerHeight)	{ //not IE
			doResize(mvobj);
		} else {
			if (resizeTimeout!=0) {
				window.clearTimeout(resizeTimeout);
			}
			resizeTimeout = window.setTimeout(function(){
				resizeTimeout = 0;
				doResize(mvobj);
			},200);
		}
	}
};

magnaviewweblive.prototype.nextview = function() {
	if(this.curviewinfo<this.viewinfolist.length-1){
		this.selectview(this.curviewinfo+1);
	}
};

magnaviewweblive.prototype.prevview = function() {
	if(this.curviewinfo>0 && !this.settings.overviewshowing){
		this.selectview(this.curviewinfo-1);
	}
};

magnaviewweblive.prototype.selectoverview = function() {
	if (!this.settings.thumbnailsoverview) return;
	this.selectview(0); // overview always at 0 if it exists
}

magnaviewweblive.prototype.lessdetail = function() {
	if (this.viewinfo.depth >= 2) {
		this.viewinfo.depth--;
		this.update_buttons();
		this.changeImage(this.createurl({'type':'image','detail':'less'}));
	}
}

magnaviewweblive.prototype.moredetail = function() {
	if (this.viewinfo.depth < (this.viewinfo.maximumdepth-this.viewinfo.zoomdepth)) {
		this.viewinfo.depth++;
		this.update_buttons();
		this.changeImage(this.createurl({'type':'image','detail':'more'}));
	}
}

magnaviewweblive.prototype.hideselection = function() {
	if (this.mouse.nodesselected) {
		this.mouse.nodesselected = false;
		this.mouse.nodeshidden   = true;
		this.mouse.selectaction  = 'hide';

    this.selectview(mvobj.curviewinfo);
    
    this.mouse.selectaction  = '';
	}
}

magnaviewweblive.prototype.showselection = function() {
	if (this.mouse.nodesselected) {
		this.mouse.nodesselected = false;
		this.mouse.nodeshidden   = true;
		this.mouse.selectaction  = 'showonly';
		
		this.selectview(mvobj.curviewinfo);

    this.mouse.selectaction  = '';
	}
}

magnaviewweblive.prototype.showall = function () {
	if (this.mouse.nodeshidden) {
		this.mouse.nodeshidden = false;
		this.mouse.selectaction  = 'showall';
		
		this.selectview(mvobj.curviewinfo);

    this.mouse.selectaction  = '';
	}
}

magnaviewweblive.prototype.getMousePos = function(e) {
	// get mouseposition
	var X = e? e.clientX : window.event.clientX;
	var Y = e? e.clientY : window.event.clientY;
	
	X += document[docElement].scrollLeft;
	Y += document[docElement].scrollTop;
	
	if( (X <  this.settings.TreemapLeft) ||  
		(X > (this.settings.TreemapLeft + this.settings.mv_width)) ||
		(Y <  this.settings.TreemapTop) ||
		(Y > (this.settings.TreemapTop  + this.settings.mv_height))    ) {
		return null;
	}
	
	var pos = new Object();
	pos.x = X - this.settings.TreemapLeft;
	pos.y = Y - this.settings.TreemapTop;
	
	return pos;	
}

magnaviewweblive.prototype.mousemovedrag = function(evt) {
	var e = evt? evt : window.event;
	var tgt = e.target? e.target : e.srcElement;
	
	if (
	  tgt &&
	  tgt.parentNode &&
	  (
      tgt.parentNode.className == 'draw' ||
      tgt.parentNode.className == 'actionoverlay' ||
      (
        tgt.parentNode.parentNode &&
				tgt.parentNode.parentNode.parentNode &&
			  tgt.parentNode.parentNode.parentNode.className == 'draw'
      )
		)
	) {
		var area = this.elements.main.parentNode;
		var shift =
			(e.shiftKey	? '1':'0') +
			(e.ctrlKey	? '1':'0') +
			(e.altKey		? '1':'0');

		this.execScript({
			'type': 'actionhover',
			'X': e.clientX - this.mouse.offsetX + area.scrollLeft,
			'Y': e.clientY - this.mouse.offsetY + area.scrollTop,
			'shift': shift,
			'source': this.mouse.source
		});
	} else {
		if(this.mouse.expectedaction == 'Drag') {
		  doc.onmousemove = mousemovedrag;
		} else {
			doc.onmousemove = mousemove;
		}
	}
}

magnaviewweblive.prototype.dropFeedback = function(action) {
	if (action == 'Drop') {
		this.changeCursor('drop');
		this.mouse.candrop = true;
	} else {
		this.changeCursor('nodrop');
		this.mouse.candrop = false;
	}
	
	if(this.mouse.expectedaction == 'Drag') {
	  doc.onmousemove = mousemovedrag;
	} else {
		doc.onmousemove = mousemove;
	}
}

magnaviewweblive.prototype.mousemoveselect = function(evt) {
	var e = evt? evt : window.event;
	var area = this.elements.main.parentNode;
	
	var x1 = parseFloat(e.clientX) 					- this.mouse.offsetX + area.scrollLeft;
	var x2 = parseFloat(this.mouse.startX);
	var y1 = parseFloat(e.clientY) 					- this.mouse.offsetY + area.scrollTop;
	var y2 = parseFloat(this.mouse.startY);
	
	var left   = 0;
	var right  = 0;
	var bottom = 0;
	var top    = 0;
	
	if (x1 > x2) {
	  left   = Math.max(x2, 0);
		right  = Math.min(x1, this.viewinfo.actualWidth);
	} else {
	  left   = Math.max(x1 + 2, 0);
		right  = Math.min(x2, this.viewinfo.actualWidth);
	}
	
	if (y1 > y2) {
	  top    = Math.max(y2, 0);
		bottom = Math.min(y1, this.viewinfo.actualHeight);
	} else {
	  top    = Math.max(y1 + 2, 0);
		bottom = Math.min(y2, this.viewinfo.actualHeight);
	}
	
	//window.console.log('[(' + x1 + ', ' + y1 + '), (' + x2 + ', ' + y2 + ')]');
	
	this.elements.select.style.left  	= left + 'px';
	this.elements.select.style.width 	= Math.max(right - left - 2, 0) + 'px';
	this.elements.select.style.top   	= top + 'px';
	this.elements.select.style.height = Math.max(bottom - top - 2, 0) + 'px';
  this.elements.select.style.visibility = 'visible';
  this.changeCursor('select');
  //document.body.style.cursor = 'crosshair';
	this.mouse.expectedaction = 'Select';
}

magnaviewweblive.prototype.initiateMouseMove = function(X, Y, shift, action, source, fn) {
	this.mouse.startX = X;
	this.mouse.startY = Y;
	this.mouse.source = source;
	this.mouse.expectedaction = action;
	doc.onmousemove = fn;
	if (action == 'Drag') {
		this.changeCursor('nodrop');
		//document.body.style.cursor = 'pointer';
	}
	
	this.elements.select.className 			= 'drawselect';
	this.elements.select.style.left 		= (X  - 2) + 'px';
	this.elements.select.style.top 			= (Y  - 2) + 'px';
	this.elements.select.style.width 		= '0px';
	this.elements.select.style.height 	= '0px';
	
	//window.console.log('(' + X + ', ' + Y + ')[' + shift + ']: ' + action + ' (' + source + ')');
}

magnaviewweblive.prototype.onmousedown = function(evt) {
	var e = evt? evt : window.event;
	var tgt = e.target? e.target : e.srcElement;

	var shift =
		(e.shiftKey	? '1':'0') +
		(e.ctrlKey	? '1':'0') +
		(e.altKey		? '1':'0');

	if (tgt && tgt.parentNode) {
		if (
      tgt.parentNode.className == 'draw' ||
      tgt.parentNode.className == 'actionoverlay' ||
      (
        tgt.parentNode.parentNode &&
				tgt.parentNode.parentNode.parentNode &&
			  tgt.parentNode.parentNode.parentNode.className == 'draw'
      )
		){
			// in view, check underlaying actions, if any
			var drawPos = getElementPosition(this.elements.draw);

			this.execScript({
				'type': 'getaction',
				'x': e.clientX + this.elements.main.parentNode.scrollLeft - drawPos.Left,
				'y': e.clientY + this.elements.main.parentNode.scrollTop - drawPos.Top,
				'shift': shift,
				'source': ''
			});
		} else if (tgt.className == 'AttributeLabel') {
			// start attribute map close action
			this.mouse.attributeBranch += 1;
			setTimeout('window.mv_object.mouse.attributeBranch = 0;', 300);
		} else if (
		  tgt.className == 'Attribute' ||
		  tgt.className == 'nodeinfoattr'
		) {
			// start attribute drag action
			this.mouse.dragObj.source = 'Drag|ATTR|' + tgt.id.substr(7);
			this.execScript({
				'type': 'getaction',
				'x': -1,
				'y': -1,
				'shift': shift,
				'source': this.mouse.dragObj.source
			});
			//this.changeCursor('nodrop');
			//document.body.style.cursor = 'pointer';
		} /* else {
			// test
			window.console.log('ignored mouse down: [' + tgt.className+'] ' + tgt.id);
		}*/
	}
	
	return false;
}

magnaviewweblive.prototype.changeCursor = function(ctype) {
	if (ctype == 'drop') {
		document.body.style.cursor = 'url(images/Drag.cur), default';
	} else if (ctype == 'nodrop') {
	  document.body.style.cursor = 'url(images/NoDrag.cur), default';
	} else if (ctype == 'select') {
	  document.body.style.cursor = 'crosshair';
	} else {
		document.body.style.cursor = 'default';
	}
}

magnaviewweblive.prototype.execScript = function(urlObj) {
	var script   = document.createElement('script');
	script.type  = 'text/javascript';
	script.id = this.scriptuid++;
	urlObj.cleanscript = script.id;
	script.src = this.createurl(urlObj);

	document.getElementsByTagName("head")[0].appendChild(script);
}

magnaviewweblive.prototype.performclick = function () {
	if(this.mouse.clickobj.action) {
		this.execScript(this.mouse.clickobj);
		
		this.mouse.clickobj = {};
	}
}

magnaviewweblive.prototype.do_performclick = function(urlObj) {
	doc.onmousemove = mousemove;

	if (this.mouse.clickobj.action) {
    // double click
		this.mouse.clickobj.action = 'DoubleClick';
	} else {
    // single click
		this.mouse.clickobj = urlObj;
		this.mouse.clickobj.action = 'Click';

		setTimeout('window.mv_object.performclick();', 300);
	}
}

magnaviewweblive.prototype.handleSelect = function(X, Y, shift, drawPos) {
	if (
		Math.abs(this.mouse.startX - X) < 4 ||
		Math.abs(this.mouse.startY - Y) < 4
	) {
		// handle view click action
		this.mouse.expectedaction = "Click";

		this.do_performclick({
			'type':'onclick',
			'x':X,
			'y':Y,
			'shift': shift
		});
	} else {
    // handle selection rectagle action
		var x1  = this.mouse.startX;
		var x2 	= X;
		var y1  = this.mouse.startY;
		var y2	= Y;

		this.elements.select.className = 'drawselectdone';
		doc.onmousemove = mousemove;

		this.execScript({
			'type':		'select',
			'left': 	Math.min(x1, x2),
			'top':  	Math.min(y1, y2),
			'right':	Math.max(x1, x2),
			'bottom':	Math.max(y1, y2),
			'shift':  shift
		});
	}
}

magnaviewweblive.prototype.onmouseup = function(evt) {
	var e = evt ? evt : window.event;
	var tgt = e.target? e.target : e.srcElement;
	
	var drawPos = getElementPosition(this.elements.draw);
	var shift =
		(e.shiftKey	? '1':'0') +
		(e.ctrlKey	? '1':'0') +
		(e.altKey		? '1':'0');

	if (this.mouse.attributeBranch >  1) {
		if (tgt.className == 'AttributeLabel') {
			// handle attribute map close action
			var attrs = tgt.nextSibling;
			if (attrs.style.display == 'none'){
				attrs.style.display = '';
			} else {
				attrs.style.display = 'none';
			}
		}
	
		this.mouse.attributeBranch = 0;
	} else if (
		tgt &&
		tgt.parentNode &&
		(
		  tgt.parentNode.className == 'draw' ||
		  tgt.parentNode.className == 'actionoverlay' ||
		  tgt.className == 'actionoverlay'
		)
	) {
		// in view, adjust for custom sizes
		var X = e.clientX + this.elements.main.parentNode.scrollLeft - drawPos.Left;
		var Y = e.clientY + this.elements.main.parentNode.scrollTop  - drawPos.Top;

		if (this.mouse.candrop) {
			if (this.mouse.dragObj.source) {
				// handle drag action on view
				this.execScript({
					'type': 'onclick',
					'x':X,
					'y':Y,
					'shift': shift,
					'action': this.mouse.dragObj.source
				});

		    this.mouse.dragObj = {};
			} else if (this.mouse.expectedaction == 'Drag') {
				this.execScript({
					'type': 'onclick',
					'x': X,
					'y': Y,
					'shift': shift,
					'action': 'Drop'
				});
			}
			this.mouse.candrop = false;
		} else if (this.mouse.expectedaction == 'Select') {
			// selecting an area of tiles within the view
			this.handleSelect(X, Y, shift, drawPos);
		} else if (this.mouse.expectedaction == 'Click') {
			// handle direct click action (from view icons)
			this.do_performclick({
				'type':'onclick',
				'x':(this.mouse.startX),
				'y':(this.mouse.startY),
				'shift': shift
			});
		}
	} else if (this.mouse.expectedaction == 'Select') {
		// selecting an area of tiles, but stopping outside of the view.
		this.handleSelect(
			e.clientX + this.elements.main.parentNode.scrollLeft - drawPos.Left,
			e.clientY + this.elements.main.parentNode.scrollTop  - drawPos.Top,
			shift, drawPos
		);
	} /* else {
		// test
		window.console.log('ignored mouse up: [' + tgt.className+'] ' + tgt.id);
	}	//*/
	
	this.mouse.expectedaction = '';
	doc.onmousemove = mousemove;
	this.changeCursor('default');
	//document.body.style.cursor = 'default';
	return false;
}

magnaviewweblive.prototype.init_mousemove = function() {
	//initialilze handling of mousemove event
	if(doc.layers) doc.captureEvents(Event.MOUSEMOVE);
	for(var i=0;i<this.oldcurnodes.length;i++) this.oldcurnodes[i] = -1
	//if (HandleClicks=="1"){
		//initialize right mouseclick (*add the context menu to the right mouseclick)
		//TODO: better handling of contextmenu
		//document.getElementById("draw").oncontextmenu = ItemSelMenu;
	//}
	//HandleClicks++
	this.elements.draw.ondblclick = handle_events;
	this.elements.draw.object = this;
	doc.mousemove = mousemove;
};

function disableSelection(target){
	if (typeof target.onselectstart!="undefined") //IE route
		target.onselectstart=function(){return false}
	else if (typeof target.style.MozUserSelect!="undefined") //Firefox route
		target.style.MozUserSelect="none"
	else //All other route (ie: Opera)
		target.onmousedown=function(){return false};
}

function handle_events(evt) {
	// pass event to associated object
	this.object.handle_events(evt);
}

function mousemoveselect(evt) {
/*	For performance reasons the eventhandler is temporarily unhooked, so the
	number of calls is limited. */

	doc.onmousemove = null;

	window.mv_object.mousemoveselect(evt);

	//setup the mousemove eventhandler again
	if(window.mv_object.mouse.expectedaction == 'Select') {
	  doc.onmousemove = mousemoveselect;
	} else {
		doc.onmousemove = mousemove;
	}
}

function mousemovedrag(evt) {
	doc.onmousemove = null;
	
	window.mv_object.mousemovedrag(evt);
	
}

function mousemove(evt) {
/*	For performance reasons the eventhandler is temporarily unhooked, so the
	number of calls is limited. */

	doc.onmousemove = null;

	window.mv_object.mousemove(evt);

	//setup the mousemove eventhandler again
	doc.onmousemove = mousemove;
}

magnaviewweblive.prototype.mousemove = function(e) {
/*	this function handles the mousemove event.
	The mousecoordinates are determined and then another function is calles that
	will display the overlay based on the coordinates relative to the treemap */

	var pos = this.getMousePos(e);
	if(this.settings.overviewshowing || !pos) {
		if (this.settings.overviewshowing) {
		  this.elements.nodeinfo.innerHTML = '';
		} else {
			this.givenodeinfo(-1);
		}
	  return;
	}

	var X = pos.x;
	var Y = pos.y;
	
	//X -= 5;//correct for shadows -- now in CSS
	//Y -= 3;//correct for shadows -- now in CSS

	//display the treemap overlay for the coordinates relative to the treemap
	//if(move=="1")
	if (this.settings.displayoverlay) {
		this.displaytreemapoverlay(X,Y,e);
	}
};

magnaviewweblive.prototype.handle_events = function(e) {
//	this function handles click and double click
	var eventtype = e? e.type : window.event.type;
	
	clickX    =  e? e.clientX : window.event.clientX
	clickY    =  e? e.clientY : window.event.clientY;
	
	clickX += document[docElement].scrollLeft;
	clickY += document[docElement].scrollTop;
	
	clickX -= this.settings.TreemapLeft;
	clickY -= this.settings.TreemapTop;

	// todo: properly distinguish single and double clicks
	switch (eventtype) {
		case "click": 
			break;
		case "dblclick":
			if (this.events.ondoubleclick) this.events.ondoubleclick(clickX, clickY);
			break;
		default:
	}

	return;
	
	//save the mouseposition for the clickevent
	var eventtype = evt? evt.type : window.event.type;
	clickX    =  evt? evt.pageX : window.event.x;
	clickY    =  evt? evt.pageY : window.event.y;
	
	if(eventtype == 'dblclick') {
		//doDoubleClick(clickX, clickY);
		PopUp_activity(clickX-TreemapLeft,clickY-TreemapTop);
	}
	/*
	if(clickcounter == 0){
		clickcounter=1;
		tfClick = dclick.getTime();
		savTO = setTimeout("mouseclick(clickX, clickY)", dcTime);
	}
	else if(clickcounter == 1){
		clickcounter=0;
		tsClick = dclick.getTime();
		if (tsClick-tfClick < dcTime){
			clearTimeout(savTO);
			savTO=null;
			setTimeout("doDoubleClick(clickX, clickY)", dcTime);
		}
		tfClick=0;
		tsClick=0;
	}
	*/
};

magnaviewweblive.prototype.zoomin = function(X,Y) {
	this.changeImage(this.createurl({'type':'image','mode':'zoomin','x':X,'y':Y,'z':this.viewinfo.zoomdepth}));
	this.changeNodes(this.thisview,"","","",false);
}

magnaviewweblive.prototype.zoomout = function() {
	this.changeImage(this.createurl({'type':'image','mode':'zoomout','z':this.viewinfo.zoomdepth}));
	this.changeNodes(this.thisview,"","","",false);
}

magnaviewweblive.prototype.loadDynamicNodes = function(X, Y, curnode, j) {
	if (mvobj.dynloadingnodes) return;
	var script   = document.createElement('script');
	script.type  = 'text/javascript';
	script.id = this.scriptuid++;
	script.src = this.createurl({'type':'nodesxy','x':X,'y':Y,'curnode':curnode,'cleanscript':script.id});
	mvobj.dynloadingnodes = true;
	document.getElementsByTagName("head")[0].appendChild(script);
}

magnaviewweblive.prototype.displaytreemapoverlay = function(X,Y, evt) {
/*	this function will display the correct overlay rectangles and node
	information based on the (x,y) coordinate */

	var mv_width = this.settings.mv_width;
	var mv_height = this.settings.mv_height;
	var depth = this.viewinfo.depth;
	var graphics = this.graphics;
	var topnodes = this.viewinfo.topnodes;
	var nodes = this.viewinfo.nodes;
	
	X += this.elements.main.parentNode.scrollLeft;
	Y += this.elements.main.parentNode.scrollTop;
	
	this.lastx = X;
	this.lasty = Y;

	var found = false;
	var updatelevel = 0;
	var curnode = -2;
	var counter = 0;
	var curchild;
	var tmppoint = new TPoint(X, Y);
	var tmprect  = new TRect;

	//retrieve the updatelevel
	updatelevel = this.updatefrom(X, Y);
	if(updatelevel > this.viewinfo.updatefromlevel) {
		this.viewinfo.updatefromlevel++;
	} else {
		this.viewinfo.updatefromlevel = updatelevel;
	}

	//if the updatelevel is equal to the depth, then nothing has to be updated */
	if (this.viewinfo.updatefromlevel > depth) return true;
	
	curnode = 0; // node 0 is the root node

	if (0 >= this.viewinfo.updatefromlevel) {
		if (this.oldcurnodes[0] != 0) {
			graphics[0].clear();
			this.drawnode(curnode, 0);
			this.oldcurnodes[0] = 0;
		}
	}
	for(j=0; j<depth; j++) {
		nrChildnodes = nodes[curnode][2].length;
		found = false;
		var i = nrChildnodes;
		if (
		  i > 0 &&
			tmppoint.x >= nodes[curnode][8] &&
			tmppoint.x <= nodes[curnode][8] + nodes[curnode][10] &&
			tmppoint.y >= nodes[curnode][9] &&
			tmppoint.y <= nodes[curnode][9] + nodes[curnode][11]
		) {
			var hasnullchild = false;
			do {
				curchild = nodes[curnode][2][i-1];
				//if(curchild==null){curchild=this.oldcurnodes[j+1];}
				if (nodes[curchild] != null) {
					tmprect = this.getParentRect(curchild);

					if(counter == 0){
						tmppoint = this.CoordinateTransformUp(tmppoint.x, tmppoint.y, j, tmprect, curchild);
						counter  = 1;
					}

					if (
						tmppoint.x >= nodes[curchild][3] &&
						tmppoint.x <= nodes[curchild][3] + nodes[curchild][5] &&
						tmppoint.y >= nodes[curchild][4] &&
						tmppoint.y <= nodes[curchild][4] + nodes[curchild][6]
					) {
							// j + 1: we're drawing a child's overlays, so we are working one level below
							// the current node
							if(j+1 >= this.viewinfo.updatefromlevel) {
							  if (this.oldcurnodes[j+1] != curchild) {
									graphics[j+1].clear();
									this.drawnode(curchild, j+1);
									this.oldcurnodes[j+1] = curchild;
								}
							}
							found = true;
							curnode = curchild;
							i=1;
					}
				} else
					hasnullchild = true;
			}
			while (--i); //do (...) while(--i) loop for increase of speed
			if (!found && hasnullchild) {
				// Initiate dynamic loading if not doing so already;
				for(; j<depth; j++) {
					graphics[j+1].clear();
					this.oldcurnodes[j+1] = -1;
				}
				this.loadDynamicNodes(X, Y, curnode);
				return true;
			}
		} else {
			for(; j<depth; j++) {
				graphics[j+1].clear();
				this.oldcurnodes[j+1] = -1;
			}
			break;
		}
		counter=0;
	}

	//display the node information of the current node pointed at
	this.givenodeinfo(curnode);
	if((curchild-1) == curnode){
		this.HideLinesJS();
	}
	return true;
};

magnaviewweblive.prototype.updatefrom = function(X,Y) {
//this function tells, based on the current mousecoordinates which level
//(and the levels below) has to be updated
	var tmppoint2 = new TPoint;
	var tmprect2  = new TRect(
	  this.settings.RootMarginLeft,
		this.settings.RootMarginTop,
		this.settings.RootMarginLeft +
			this.settings.mv_width,
		this.settings.RootMarginTop +
			this.settings.mv_height
	);
	if((this.oldcurnodes[0])==null) {this.oldcurnodes[0]=-1;}
	for(i = 0; i <= this.viewinfo.depth; i++) {
		if(i > 0){
			tmprect2 = this.getParentRect(this.oldcurnodes[i]);
		}
		tmppoint2 = this.CoordinateTransformUp(X, Y, i, tmprect2, this.oldcurnodes[i]);
		if (
			!(
				this.oldcurnodes[i] > -1 &&
				tmppoint2.x >=  this.viewinfo.nodes[this.oldcurnodes[i]][3] &&
				tmppoint2.x <= (this.viewinfo.nodes[this.oldcurnodes[i]][3] + this.viewinfo.nodes[this.oldcurnodes[i]][5]) &&
				tmppoint2.y >=  this.viewinfo.nodes[this.oldcurnodes[i]][4] &&
				tmppoint2.y <= (this.viewinfo.nodes[this.oldcurnodes[i]][4] + this.viewinfo.nodes[this.oldcurnodes[i]][6])
			)
		) {
			return i;
		}
	}
	return this.viewinfo.depth + 1;
};

magnaviewweblive.prototype.CoordinateTransform = function(x, y, level, r, id) {
/*	this function will apply a coordinatetransformation, from rectangle to x */
	var transformedpoint = new TPoint;
	switch((this.viewinfo.leveltransformations[level + this.viewinfo.zoomdepth])) {
		case 2: //PolarXtoR
			transformedpoint = TreemapXY2PolarMapXYRectXtoR(x,y,r);
			break;
		case 3: //PolarYtoR
			transformedpoint = TreemapXY2PolarMapXYRectXtoR(y,x, new TRect(r.top,r.left,r.bottom,r.right));
			var temp = transformedpoint.x;
			transformedpoint.x = transformedpoint.y;
			transformedpoint.y = temp;
			break;
		case 4: //PyramidTop
			transformedpoint = PyramidTopTransform(x,y,r);
			break;
		case 5: //PyramidLeft
			transformedpoint = PyramidTopTransform(y,x,new TRect(r.top,r.left,r.bottom,r.right));
			var temp = transformedpoint.x;
			transformedpoint.x = transformedpoint.y;
			transformedpoint.y = temp;
			break;
		case 6: //PyramidRight
			transformedpoint = PyramidTopTransform(y,x,new TRect(r.top,r.left,r.bottom,r.right));
			var temp = transformedpoint.x;
			transformedpoint.x = transformedpoint.y;
			transformedpoint.y = temp;
			transformedpoint.x = r.right-(transformedpoint.x-r.left);
			break;
		case 7: //PyramidBottom
			transformedpoint   = PyramidTopTransform(x,y,r);
			transformedpoint.y = r.bottom-(transformedpoint.y-r.top);
			break;
		case 8: //mirror X
			transformedpoint.x = (r.right) - (x - r.left);
			transformedpoint.y = y;
			break;
		case 9: //mirror Y
			transformedpoint.x = x;
			transformedpoint.y = (r.bottom)-(y-r.top);
			break;
		default:
			transformedpoint.x = x;
			transformedpoint.y = y;
	}
	if (this.viewinfo.nodes[id][1] > 0) {
		par_id = this.viewinfo.nodes[id][1];
		par_rect = this.getParentRect(par_id);
		transformedpoint = this.CoordinateTransform(transformedpoint.x, transformedpoint.y, level-1, par_rect, par_id);
	}
	return transformedpoint;
};

magnaviewweblive.prototype.CoordinateTransformUp = function(x, y, level, r, id) {
/*	this function will apply a coordinatetransformation, from x back to rectangle */
	var transformedpoint = new TPoint;
	switch(this.viewinfo.leveltransformations[level+this.viewinfo.zoomdepth]) {
		case 2: //PolarXtoR
			transformedpoint = PolarMapXY2TreemapXYrelRextXtoR(x,y,r);
			break;
		case 3: //PolarYtoR
			transformedpoint = PolarMapXY2TreemapXYrelRextXtoR(y,x,new TRect(r.top,r.left,r.bottom,r.right));
			var temp = transformedpoint.x;
			transformedpoint.x = transformedpoint.y;
			transformedpoint.y = temp;
			break;
		case 4: //PyramidTop
			transformedpoint = PyramidTopTransformUp(x,y,r);
			break;
		case 5: //PyramidLeft
			transformedpoint = PyramidTopTransformUp(y,x,new TRect(r.top,r.left,r.bottom,r.right));
			var temp = transformedpoint.x;
			transformedpoint.x = transformedpoint.y;
			transformedpoint.y = temp;
			break;
		case 6: //PyramidRight
			transformedpoint = PyramidTopTransformUp(y,r.right-(x-r.left),new TRect(r.top,r.left,r.bottom,r.right));
			var temp = transformedpoint.x;
			transformedpoint.x = transformedpoint.y;
			transformedpoint.y = temp;
			break;
		case 7: //PyramidBottom
			transformedpoint = PyramidTopTransformUp(x,r.bottom-(y-r.top),r);
			break;
		case 8: //mirror X
			transformedpoint.x = (r.right) - (x - r.left);
			transformedpoint.y = y;
			break;
		case 9: //mirror Y
			transformedpoint.x = x;
			transformedpoint.y = (r.bottom)-(y-r.top);
			break;
		default:
			transformedpoint.x = x;
			transformedpoint.y = y;
	}
	return transformedpoint;
};

magnaviewweblive.prototype.getParentRect = function(id) {
/* this function returns the parent rectangle (Trect) of node 'id' */
	if(this.viewinfo.nodes[id]!=null){
		if (this.viewinfo.nodes[id][1] <= 0) {
			var rect_left   = this.viewinfo.RootMarginLeft;
			var rect_top    = this.viewinfo.RootMarginTop;
			var rect_right  = this.settings.mv_width+this.viewinfo.RootMarginRight;
			var rect_bottom = this.settings.mv_height+this.viewinfo.RootMarginBottom;
		} else {
			var rect_left   = this.viewinfo.nodes[this.viewinfo.nodes[id][1]][8];
			var rect_top    = this.viewinfo.nodes[this.viewinfo.nodes[id][1]][9];
			var rect_right  = rect_left + this.viewinfo.nodes[this.viewinfo.nodes[id][1]][10];
			var rect_bottom = rect_top  + this.viewinfo.nodes[this.viewinfo.nodes[id][1]][11];
		}
		pr_rect = new TRect(rect_left, rect_top, rect_right, rect_bottom);
	}else{
		pr_rect = new TRect(0,0,this.settings.mv_width,this.settings.mv_height);
	}
	return pr_rect;
};

magnaviewweblive.prototype.givenodeinfo = function(node) {
/*	display the node information of the current node in the correct place. This
	function assumes a nodeinfo div */
	var n_info = "";
	var nodeinfofield = this.elements.nodeinfo;
	if(this.settings.GenerateNodeinfo && nodeinfofield){
		var isnodelevel = (node >= 0) && !this.viewinfo.nodes[node][9]; // no children means node level
		if (isnodelevel) {
			var varnum = this.viewinfo.nodes[node][8];
			if (this.variables[varnum] != undefined) {
				var varinfo = this.variables[varnum].split('\x00');
				for (i=0; i<this.viewinfo.var_ids.length ;i++ ) {
					n_info += "<div class='nodeinforow'>";
					n_info += "<div class='nodeinfoattr' id='mvnode_"+this.viewinfo.var_labels[i]+"'>";
					n_info += this.viewinfo.var_names[i];
					n_info += "</div>";
					n_info += "<div class='nodeinfovalue'>";
					n_info += varinfo[this.viewinfo.var_ids[i]];
					n_info += "</div>";
					n_info += "</div>";
				}
			} else {
				// variable info not known yet, request it
				var script   = document.createElement('script');
				script.type  = 'text/javascript';
				script.id = this.scriptuid++;
				script.src = this.createurl({'type':'variables','start':varnum,'stop':varnum+1,'other':'false','node':node,'cleanscript':script.id});
				document.getElementsByTagName("head")[0].appendChild(script);
				return;
			}
		} else  {
			if(this.viewinfo && this.viewinfo.var_ids){
				for (i=0; i<this.viewinfo.var_ids.length ;i++ ) {
					n_info += "<div class='nodeinforow'>";
					n_info += "<div class='nodeinfoattr' id='mvnode_"+this.viewinfo.var_labels[i]+"'>";
					n_info += this.viewinfo.var_names[i];
					n_info += "</div>";
					n_info += "<div class='nodeinfovalue'>&nbsp;</div>";
					n_info += "</div>";
				}
			}
		}
		nodeinfofield.innerHTML = n_info;
	}
};

magnaviewweblive.prototype.drawnode = function(id, level) {
/*	this function draws the node, i.e. the lines of the node and the label */
	//determine the depth of the node. A node should only be drawn if the level is correct. TODO: this should be a property of nodes array
	var l = 0;
	tmpid = id;
	if (tmpid != 0) {
		while (this.viewinfo.nodes[tmpid][1] != 0) {
			tmpid = this.viewinfo.nodes[tmpid][1];
			l++;
		}
		l++;
	}

	if(l==level) {
		this.drawNodeLines(id,level);
		this.drawNodeLabel(id,level);
		this.drawNodeIcon(id,level);
		if (this.graphics[level]) this.graphics[level].paint();
	}
};



magnaviewweblive.prototype.DrawLine = function(p1, p2, level, parent_rect, id){
	/*Draw a line between the points p1 and p2 using given transformation function.
		Stops when the line to draw and it's actual transformation have a maximum
		distance of MaxDist. i.e. low values of MaxDist => nicer line*/
	var mode = this.mode;

	var newp1 = new TPoint(0,0);
	var newp2 = new TPoint(0,0);
	var c     = new TPoint(0,0);
	var MaxDist = 0.2;
	var midp1p2;
	var d;
	var _arrx		= new Array();
	var _arry		= new Array();
	var _arr		= new Array();
	var temparray	= new Array();

	midp1p2 = Midpoint(p1,p2);
	newp1	= this.CoordinateTransform(p1.x, p1.y, level - 1, parent_rect, id);
	newp2	= this.CoordinateTransform(p2.x, p2.y, level - 1, parent_rect, id);
	c		= this.CoordinateTransform(midp1p2.x, midp1p2.y, level - 1, parent_rect, id);
	d		= Midpoint(newp1, newp2);
	if(PointDist(d,c) <= (MaxDist*MaxDist)){
		_arrx[_arrx.length] = Math.round(newp1.x);
		_arry[_arry.length] = Math.round(newp1.y);
		_arrx[_arrx.length] = Math.round(newp2.x);
		_arry[_arry.length] = Math.round(newp2.y);
	} else{
		temparray = this.DrawLine(p1, midp1p2, level, parent_rect, id);
		for(var k=0; k<temparray[0].length;k++){
			_arrx[_arrx.length] = temparray[0][k];
			_arry[_arry.length] = temparray[1][k];
		}
		_arrx[_arrx.length] = c.x;
		_arry[_arry.length] = c.y;
		temparray = this.DrawLine(midp1p2, p2, level, parent_rect, id);
		for(var k=0; k<temparray[0].length;k++){
			_arrx[_arrx.length] = temparray[0][k];
			_arry[_arry.length] = temparray[1][k];
		}
	}
	_arr[0] = _arrx;
	_arr[1] = _arry;
	return _arr;
};

magnaviewweblive.prototype.drawNodeLines = function(id, level) {
/*	this function will draw the lines of node 'id' on level  'level' */

	var overlay = this.viewinfo.overlay;
	var graphics = this.graphics;
	var nodes = this.viewinfo.nodes;
	var depth = this.viewinfo.depth;

	if (overlay.level[level]){
		if (overlay.level[level].Rectangle) {
			for (i=0;i<overlay.level[level].Rectangle.length ;i++ ) {
				var Rectangle = overlay.level[level].Rectangle[i];
				var temps = "";
				var temp2;
				var p1 = new TPoint(0,0);
				var p2 = new TPoint(0,0);
				var visible = true;
				graphics[level].setStroke(Rectangle.width);
				graphics[level].setColor(Rectangle.color);
				var temparray = new Array();
				var drawingx  = new Array();
				var drawingy  = new Array();
				var left, top, right, bottom;
				if (Rectangle.includemargins == 0 && nodes[id][10] && nodes[id][11]) {
					left    = nodes[id][8];//   + 3 ; //correct for shadows -- now in CSS
					top     = nodes[id][9];//   + 1 ; //correct for shadows -- now in CSS
					right   = left + nodes[id][10] ; //left + width
					bottom  = top  + nodes[id][11] ; //top + height
				} else {
					left    = nodes[id][3];//   + 3 ; //correct for shadows -- now in CSS
					top     = nodes[id][4];//   + 1 ; //correct for shadows -- now in CSS
					right   = left + nodes[id][5] ; //left + width
					bottom  = top  + nodes[id][6] ; //top + height
				}
				parent_rect = this.getParentRect(id);

				if(visible){
					p1.x = left  ;
					p1.y = top   ;
					p2.x = right ;
					p2.y = top   ;
					temparray = this.DrawLine(p1, p2, level, parent_rect, id);
					for(var k=0; k<temparray[0].length;k++){
						drawingx[drawingx.length] = temparray[0][k];
						drawingy[drawingy.length] = temparray[1][k];
					}

					p1.x = right;
					p1.y = top;
					p2.x = right;
					p2.y = bottom;
					temparray = this.DrawLine(p1, p2, level, parent_rect, id);
					for(var k=0; k<temparray[0].length;k++){
						drawingx[drawingx.length] = temparray[0][k];
						drawingy[drawingy.length] = temparray[1][k];
					}

					p1.x = right;
					p1.y = bottom;
					p2.x = left;
					p2.y = bottom;
					temparray = this.DrawLine(p1, p2, level, parent_rect, id);
					for(var k=0; k<temparray[0].length;k++){
						drawingx[drawingx.length] = temparray[0][k];
						drawingy[drawingy.length] = temparray[1][k];
					}

					p1.x = left;
					p1.y = bottom;
					p2.x = left;
					p2.y = top;
					temparray = this.DrawLine(p1, p2, level, parent_rect, id);
					for(var k=0; k<temparray[0].length;k++){
						drawingx[drawingx.length] = temparray[0][k];
						drawingy[drawingy.length] = temparray[1][k];
					}

					//graphics[level].drawPolyline(drawingx, drawingy);
					graphics[level].drawPolygon(drawingx, drawingy);
					if(Rectangle.action!='') {
						graphics[level].setColor("transparent");
						graphics[level].addClass("actionoverlay");
						graphics[level].fillPolygon(drawingx, drawingy);
						graphics[level].addClass("");
					}	
				}
			}//for
		}//if
	}
};


magnaviewweblive.prototype.drawNodeLabel = function(id, level) {
/*	this function draws the label of node 'id' on level 'level' */
//There is no text alignment on the right side, because there was no way to determine the width of the string
//so all the "right" settings are using the "left" coordinates.

	var overlay = this.viewinfo.overlay;
	var graphics = this.graphics;
	var nodes = this.viewinfo.nodes;
	var depth = this.viewinfo.depth;
	var mv_width = this.settings.mv_width;
	var mv_height = this.settings.mv_height;

	var tmppoint3 = new TPoint(0,0);
	var tmprect3  = new TRect(0,0,mv_width,mv_height);
	var text_x, text_y, marge;
	var paintlabelx = false;
	var	paintlabely = false;
	if (overlay.level[level]) {
		if (overlay.level[level].Label) {
			for (i=0;i<overlay.level[level].Label.length ;i++ ) {
				var Label = overlay.level[level].Label[i]; //for loop for each level
				graphics[level].drawString(" ",0, 0);
				if (level<=depth) { //changed from depth-1 to depth since overlays weren't displayed
					text_w = nodes[id][5] - 2*Label.margin;
					marge  = Label.margin;
					labeltext = '';
					labelwidth = 0;
					labelfontheight = 0;
					text_x = text_y = text_x2 = text_y2 = 0;
					label_has_action= false;
					label_rectbg	= false;
					label_rectline	= false;
					if (nodes[id][7] && nodes[id][7][0] && nodes[id][7][0][i]) {
						labeltext = nodes[id][7][0][i][0];
						labelwidth = nodes[id][7][0][i][1];
						labelfontheight = nodes[id][7][0][i][2];
						text_x  = nodes[id][7][0][i][3] - 1; //left
						text_y  = nodes[id][7][0][i][4] - 1; //top
						text_x2 = nodes[id][7][0][i][5]; //right
						text_y2 = nodes[id][7][0][i][6]; //bottom
						label_has_action = (Label.action != '') || false; 
						label_rectbg   = (Label.showbackground ? Label.backgroundcolor : false);
						label_rectline = (Label.showoutline ? Label.outlinecolor : false);
					}
					
					if(label_rectbg) {
						if(label_rectline) {
							graphics[level].setStroke(1);
							graphics[level].setColor(label_rectline);
							graphics[level].drawRect(text_x-4, text_y-1, text_x2-text_x+6, text_y2-text_y+4);
						} 
						graphics[level].setColor(label_rectbg);
						graphics[level].fillRect(text_x-3, text_y, text_x2-text_x+5, text_y2-text_y+3);
					}

					graphics[level].setFont(Label.font,(labelfontheight+1)+"px",Label.fontstyle);
					if (Label.displayshadow) {
						graphics[level].setColor('black');
						graphics[level].drawStringRect(labeltext,text_x+1, text_y+1, text_x2-text_x, "center");
					}
					graphics[level].setColor(Label.color);
					graphics[level].drawStringRect(labeltext,text_x, text_y, text_x2-text_x, "center");
					
					//If action is available
					if(label_has_action) {
						graphics[level].setColor("transparent");
						graphics[level].addClass("actionoverlay");
						graphics[level].fillRect(text_x-3, text_y, text_x2-text_x+5, text_y2-text_y+3);
						graphics[level].addClass("");
					}					
				}
			} //for
		}
	}
};


magnaviewweblive.prototype.drawNodeIcon = function(id, level) {
/*	this function draws the label of node 'id' on level 'level' */
//There is no text alignment on the right side, because there was no way to determine the width of the string
//so all the "right" settings are using the "left" coordinates.
	var overlay		= this.viewinfo.overlay;
	var graphics	= this.graphics;
	var nodes		= this.viewinfo.nodes;
	var depth		= this.viewinfo.depth;
	var mv_width	= this.settings.mv_width;
	var mv_height	= this.settings.mv_height;

	if (level<=depth) { //changed from depth-1 to depth since overlays weren't displayed
		if (overlay.level[level]) {
			if (overlay.level[level].Icon)  {
				for (i=0;i<overlay.level[level].Icon.length ;i++ ) { //for loop for each level
					if(nodes[id][7] && nodes[id][7][1] && nodes[id][7][1][i]) {
						var gid = level + '-' + id;
						var Icon = overlay.level[level].Icon[i]; 
						//draw icon
						var icon_info = nodes[id][7][1][i][0]
						var icon_idx  = icon_info[0];
						var hinttext  = icon_info[5] || '';
						if (icon_idx >= 0) {
							var icon_url = this.createurl({'type':'overlayicon','level':Icon.level,'overlay':Icon.index,'index':icon_idx});
							this.drawPNGImage(graphics[level], icon_url, icon_info[1], icon_info[2], icon_info[3], icon_info[4],Icon.action, Icon.visibility=="mouse", hinttext, gid);
						}
						//draw Actionhover icon
						if(nodes[id][7][1][i][1]) {
							var icon_info = nodes[id][7][1][i][1]
							var icon_idx = icon_info[0];
							if (icon_idx >= 0) {
								var icon_url = this.createurl({'type':'overlayicon','level':Icon.level,'overlay':Icon.index,'index':icon_idx});
								this.drawPNGImage(graphics[level], icon_url, icon_info[1], icon_info[2], icon_info[3], icon_info[4],Icon.action, false, hinttext, gid + '_h');
							}
						}
					} 
				} //for
			} 
		}
	}
};


magnaviewweblive.prototype.drawhint = function(gfx, x, y, w, h,txt) {
	gfx.htm += '<div style="position:absolute;z-index:101;left:'+x+'px;top:'+y+'px;width:'+w+'px;height:'+h+'px;"'+
			' onmouseover="this.childNodes[0].style.display = \'block\';" '+
			' onmouseout="this.childNodes[0].style.display = \'none\';" '+
			' class="actionoverlay"><div class="mvhint" style="display:none;">'+txt+'</div><\/div>';
}

magnaviewweblive.prototype.drawPNGImage = function(gfx, imgSrc, x, y, w, h, action, visible, hinttext, id) {
	var pngfix = '';
	if (/MSIE (5\.5|6)/.test(navigator.userAgent) && typeof filters != 'unknown') {
		pngfix = 'behaviour:url('+ScriptLocation + 'pngfix/iepngfix.htc);';			
	}
	gfx.htm += '<div style="position:absolute;'+
			(action!=''?'z-index:100;':'') +
			'left:' + (x + 3) + 'px;'+
			'top:' + (y + 1) + 'px;'+
			'width:' +  w + 'px;'+
			'height:' + h + 'px;"' +
			(id!=''?' id="'+id+'"':'') +
			(action!=''?' class="actionoverlay" ':' ')+ 
			((!visible && action!='')?'onmouseover="this.style.cursor=\'pointer\';t=this.childNodes;show(t[1]);if(t[2]){showHintDelayed(t[2],800);};" ':'')+
			((!visible && action!='')?'onmouseout="t=this.childNodes;hide(t[1]);if(t[2]){hideHint(t[2]);};" ':'')+
			'>'+
			'<img src="pngfix/blank.gif" width="'+w+'" height="'+h+'"/>'+//fix for IE
			'<img style="position:absolute;top:0px;left:0px;'+(visible?'':'display:none;')+pngfix+'" src="' + imgSrc + '" width="' + w + '" height="' + h + '">'+
			(hinttext!=''?'<div style="position:absolute;z-index:101;left:'+10+'px;top:'+(h+5)+'px;display:none;" class="mvhint">'+hinttext+'<\/div>':'')+
			'<\/div>';
}

magnaviewweblive.prototype.ChangeFilter = function() {
// this function changes the HTML filter code
	var filtertag = this.elements.filter
	if (filtertag) {
    var isview = this.viewinfolist[this.curviewinfo][0] == "view";
    if (isview) {
      filtertag.innerHTML = this.viewinfo.filterString;
		} else {
			filtertag.innerHTML = '';
		}
		/*
		if (filtertag.style.display != 'none' && this.viewinfo.filterString != "") {
			filtertag.style.display = "block";
		} else {
			filtertag.style.display = "none";
		}*/

	}
}

magnaviewweblive.prototype.pdfdownload = function() {
	window.open(this.createurl({'type':'pdf','table':'false','allviews':'true'}));
}

magnaviewweblive.prototype.createurl = function(urlobj) {
	var x = this.ScriptLocation + 'weblive.asp';

	//add all parameters specified in call
	for (var i in urlobj) {
		x += ("&" + i + "=" + urlobj[i]);
	}

	//add default parameters
	if (this.settings.SessionID)
		x += "&ID="+this.settings.SessionID;
	if (this.settings.mv_height && this.settings.mv_height > 0)
		x += "&h="+this.settings.mv_height;
	if (this.settings.mv_width && this.settings.mv_width > 0)
		x += "&w="+this.settings.mv_width;

	//add content-type
	var contenttype = {
						'image'         : 'image/png',
						'nodes'         : 'application/x-javascript',
						'nodesxy'       : 'application/x-javascript',
						'variables'     : 'application/x-javascript',
						'settings'      : 'application/x-javascript',
						'onclick'       : 'application/x-javascript',
						'getaction'     : 'application/x-javascript',
						'select'        : 'application/x-javascript',
						'thumbnails'    : 'image/png',
						'groupimage'    : 'image/png',
						'groupthumbnail': 'image/png',
						'pdf'           : 'application/pdf',
						'logoff'        : 'text/html',
						'icons'         : 'image/JPEG',
						'overlayicon' :   'image/JPEG'
	}
	if (urlobj["type"]) {
		x += "&content-type="+contenttype[urlobj["type"]];
	}
	if (urlobj["type"] == 'nodes' && this.elements.filter) {
		var filterdiv = this.elements.filter; 
		var fposval = '';
		var node = filterdiv.firstChild;
		while (node) {
			var isfilternode = hasClass(node, 'FilterControls')
			if (isfilternode) {
				var name = node.id;
				var pos = node.scrollTop;
				if (!(pos === 0 || name == ''))
					fposval += ',' + name + ',' + pos;
			}

			if (!isfilternode && node.firstChild) {
				node = node.firstChild;
			} else {
				while (node != filterdiv && node.nextSibling == null)
					node = node.parentNode;
				if (node != filterdiv)
					node = node.nextSibling;
				else
					node = null;
			}
		}
		if (fposval != '') {
			x += '&filterpos=';
			x += fposval.substr(1);
		}
	}
	if(urlobj["view"] == undefined) { //only add view parameter if not existing
		x += "&view="+this.thisview;
	}
	x += "&r="+ ((urlobj["type"] == 'overlayicon') ? 0 : Math.round(Math.random()*999999));
	return x.replace(/&/, "?"); // replace first '&' with '?' to make a proper url
}

function checkboxClick(name){
// this function is changing a checkbox filter
	var checkbox = doc.getElementById(name);
	if (checkbox.checked){
		filter(name,true);
	} else {
		filter(name,false);
	}
}

function editboxfilter(obj) {
	window.mv_object.filter(obj.id, 'x' + obj.value);
}

function filter(attribute, value) {
	window.mv_object.filter(attribute, value);
}

magnaviewweblive.prototype.filter = function(attribute, value) {
//  this function changes the image and nodes file after calling a filter expression
	if (can_switch_view){
		this.changeImage(this.createurl({'type':'image','attribute':attribute,'value':value}));
		this.changeNodes(this.thisview, attribute, value,"", false);
		this.showloadingscreen();
	}
}


//TODO: call object method directly
function FilterListBox(name, bool) {
	window.mv_object.FilterListBox(doc.getElementById(name), bool);
}

magnaviewweblive.prototype.FilterListBox = function(Listbox, checkbox){
	var name=Listbox.id;

// gets a new image and nodes file after a listbox control is changed
	var truevalues	= new Array();
	if (checkbox){
		for (var i = 0 ;i<Listbox.childNodes.length ;i++ ){
			if (Listbox.childNodes[i].checked){
				truevalues[truevalues.length] = Math.round(i/3);
			}
		}
	}else{
		for (var i = 0 ;i<Listbox.childNodes.length ;i++ ){
			if (Listbox.childNodes[i].selected){
				truevalues[truevalues.length] = i;
			}
		}
	}

	if (truevalues == ''){
		truevalues = 'false';
	}

	this.changeImage(this.createurl({'type':'image','attribute':name,'Listbox':truevalues}));
	this.changeNodes(this.thisview,name,truevalues,"",true);
	this.showloadingscreen();
}

function itemselect(name, what) {
	var items = doc.getElementById(name);
	var total = items.childNodes.length;
	var value;
	var checklist = new RegExp('\\bFilterControlsChecklist\\b').test(items.className);
	
	if (what == "all") value = true;
	else if (what == "none") value = false;
	else if (what == "toggle") {
		var count = 0;
		for (var i = 0 ;i<total ;i++ ){
		if (checklist) {
			if (items.childNodes[i].tagName == "INPUT")
				count += 3 * items.childNodes[i].checked;
		} else
			count += items.childNodes[i].selected 
		}
		value = !(Boolean(Math.round(count/total)));
	}
	else return;

	var scrollpos = items.scrollTop;
	for (var i = 0 ;i<total ;i++ ){
		if (checklist) {
			if (items.childNodes[i].tagName == "INPUT")
				items.childNodes[i].checked = value;
		} else
			items.childNodes[i].selected = value
	}
	items.scrollTop = scrollpos;

	window.mv_object.FilterListBox(items, checklist);
}

magnaviewweblive.prototype.initcalender = function() {
	if (this.elements.calender) {
		this.elements.calender.style.display = 'none';
		return;
	}
	var divtable = document.createElement('div');
	divtable.position = 'absolute'

	var caltable = document.createElement('table');
	caltable.className = 'ds_box';
	caltable.cellpadding = 0;
	caltable.cellscpacing = 0;
	caltable.id = 'ds_conclass';
	caltable.style.display = 'none';
	caltable.style.position = 'absolute';

	var caltr = document.createElement('tr');
	var caltd = document.createElement('td');
	caltd.id = 'ds_calclass';

	caltr.appendChild(caltd);
	caltable.appendChild(caltr);

	//this is needed for IE, it won't render dynamically generated tables otherwise
	if (caltable.outerHTML)
		divtable.innerHTML = caltable.outerHTML;
	else
		divtable.appendChild(caltable);

	document.body.appendChild(divtable);

	var script = document.createElement('script');
	script.src = this.ScriptLocation+'dateselect.js';
	script.type  = 'text/javascript';
	document.getElementsByTagName("head")[0].appendChild(script);
	this.elements.calender = caltable;
}

magnaviewweblive.prototype.unload = function() {
	if (this.settings.pagetype != 2) return;
	var xmlhttp = init_xmlhttp();
	if (xmlhttp) {
		xmlhttp.open("GET",this.createurl({'type':'logoff'}));
		xmlhttp.send(null);
	}
};

magnaviewweblive.prototype.changeLegend = function() {
	var legend_doc = mvobj.elements.legend;  
	if (legend_doc !=null && legend_doc != null){
		legend_doc.innerHTML = legend_content;
	}
	if(typeof(changeLegendCallBack)=='function') {
		changeLegendCallBack();
	}
}

magnaviewweblive.prototype.changeComment = function() {
	var comment_doc = mvobj.elements.comment; 
	if (comment_doc != null && comment_doc != null){
		comment_doc.innerHTML = comment_content;
	}
	if(typeof(changeCommentCallBack)=='function') {
		changeCommentCallBack();
	}
}

magnaviewweblive.prototype.executefn = function(fn) {
	params	= [];
	for(var i = 1; i < arguments.length; i++) {
		params.push(arguments[i]);
	}
	if(typeof(fn) == 'function') {
		fn.apply(window, params);
	}
}

function findPosX(obj){
	var curleft = 0;
	if (obj.offsetParent){
		while (obj.offsetParent){
			curleft += obj.offsetLeft;
			obj = obj.offsetParent;
		}
	} else if (obj.x){
		curleft += obj.x;
	}
	return curleft;
};

function findPosY(obj){
	var curtop = 0;
	if (obj.offsetParent){
		while (obj.offsetParent){
			curtop += obj.offsetTop;
			obj = obj.offsetParent;
		}
	} else if (obj.y){
		curtop += obj.y;
	}
	return curtop;
};

function disable(obj) {
/*	this function disables an element referenced by with 'id', i.e.
	the opacity is decreased */
	if (obj){
		if (doc.all) { //Explorer
			obj.style.filter = "alpha(opacity=30)";
		}
		obj.style.opacity = "0.3";
	}
};

function enable(obj) {
/*	this function disables an element referenced by with 'id', i.e.
	the opacity is increased */
	if (obj){
		if (doc.all) { //Explorer
			obj.style.filter = "alpha(opacity=100)";
		}
		obj.style.opacity = "1";
	}
};

function setenabled(obj, state) {
	if(obj) {
		if (state)
			enable(obj);
		else
			disable(obj);
	}
}

function setvisible(obj, state) {
	if(obj) {
		if (state)
			show(obj);
		else
			hide(obj);
	}
}

function getElementPosition(theElement){

  var posX = 0;
  var posY = 0;

	baseElement = theElement;

  while(theElement != null){
    posX += theElement.offsetLeft;
    posY += theElement.offsetTop;
    theElement = theElement.offsetParent;
  }

   return {Left:posX, Top: posY, Right: posX + baseElement.clientWidth, Bottom: posY + baseElement.clientHeight};
}

function show(obj) {
	if(obj && obj.style) obj.style.display='inline';
}

function showHint(obj) {
	if(mvobj.showhintdelayed && obj && obj.style) {

		var pos = getElementPosition(obj);
		if (pos.Right > 0) {
			var rootnode = mvobj.viewinfo.nodes[0];
			if (pos.Right > rootnode[10]) {
				obj.style.left = (parseFloat(obj.style.left) - pos.Right + rootnode[10]) + 'px';
			}
			if (pos.Bottom > rootnode[11]) {
				obj.style.top = (- obj.clientHeight - 5) + 'px';
			}
		}

		obj.style.display='';
	 }
}

function hideHint(obj) {
  mvobj.showhintdelayed = false;
	if(obj && obj.style) obj.style.display='none';
}

function hide(obj) {
	if(obj && obj.style) obj.style.display='none';
}

function showHintDelayed(obj, delay) {
  mvobj.tmpdelayed = obj;
	mvobj.showhintdelayed = true;
	setTimeout('showHint(mvobj.tmpdelayed)', delay);
}

function showDelayed(obj, delay) {
	mvobj.tmpdelayed = obj;
	setTimeout('show(mvobj.tmpdelayed)', delay);
}

function TPoint(x,y) {
/*	this function creates a TPoint object */
	this.x = x;
	this.y = y;
};

function TRect(left, top, right, bottom) {
/*	this function creates a TRect object */
	this.left   = left;
	this.top    = top;
	this.right  = right;
	this.bottom = bottom;
};

function PyramidTopTransformUp(x,y,r){
	var f, cx, cy;
	var t = new TPoint;
	t.x   = (r.left + r.right)/2;
	t.y   = y;
	if(r.top==r.bottom){
		return t;
	}
	if(r.top==y){
		t.x = x;
		return t;
	}
	cx  = (r.right-r.left)/2;
	cy  = (r.bottom-r.top)/2;
	f   = cy * 2 / (y-r.top);
	t.x = f * (x-r.left-cx) + cx + r.left;
	t.y = (y-r.top)/(cy*2);
	t.y = t.y * t.y;
	t.y = t.y * cy * 2 + r.top;
	t.y = Math.min(y, t.y);
	return t;
};

function PyramidTopTransform(x,y,r){
	var t = new TPoint;
	var f, cx, cy;
	t.x = (r.left + r.right)/2;
	t.y = y;
	if(r.top==r.bottom){
		return t;
	}
	if(r.top==y){
		return t;
	}
	cx = (r.right-r.left)/2;
	cy = (r.bottom-r.top)/2;
	if(y<r.top){
		t.y = 0 - (Math.sqrt(-2*cy*(y-r.top)) + r.top);
	} else {
		t.y = Math.sqrt(2*cy*(y-r.top))+r.top;
	}
	f   = cy*2/(t.y-r.top);
	t.x = cx + (x-cx-r.left)/f+r.left;
	return t;
};

function PolarMapXY2TreemapXYrelXtoR(x,y,tx,ty,cx,cy,lx,ly){
	var a, r, mi, ma;
	var temp = new TPoint;
	if(x==0 && y<0) {x=1;}
	r = Math.sqrt(Math.pow(y,2)+Math.pow(x,2));
	if(x==0){
		if(y>0){
			a = Math.PI;
		}else{
			a = 2*Math.PI;
		}
	}else{
		if(x>0){
			a = Math.atan(y/x) + Math.PI/2;
		}else{
			a = Math.atan(y/x) + Math.PI/2 + Math.PI;
		}
	}
	if(lx<ly){
		mi = lx;
		ma=lx;
	}else{
		mi = ly;
		ma = lx;
	}
	if(x==0 && y<0){
		r  = Math.pow(r/mi,2)*ma;
		ty = 0-ly;
		tx = r*2-lx;
	}else{
		if(mi==0){mi=1;}
		r  = Math.pow(r/mi,2)*ma;
		ty = (cy)*a/Math.PI-ly;
		tx = r*2-lx;
	}
	temp.x = tx;
	temp.y = ty;
	return temp;
};


function TreemapXY2PolarMapXYRectXtoR(x,y,r){
	var cx,cy,mi,ma;
	var t = new TPoint;
	cx = (r.right - r.left)/2;
	cy = (r.bottom - r.top)/2;
	x  = x - r.left;
	y  = y - r.top;
	if (cx<cy) {
		mi = cx;
		ma = cx;
	} else {
		mi = cy;
		ma = cx;
	}
	if (ma == 0) ma = 1;
	cy==0 ? a = 0 : a=(y/(2*cy))*(2*Math.PI);
	ma==0 ? radius = 0 : radius=Math.sqrt(Math.abs(x/2)/ma)*mi;
	x   = radius*Math.sin(a);
	y   = radius*Math.cos(a);
	t.x = r.left + x + cx;
	t.y = r.top - y + cy;
	return t;
};


function PolarMapXY2TreemapXYrelRextXtoR(x,y,r){
	var cx,cy,inx,iny;
	var inv = new TPoint;
	var t = new TPoint;
	inv.x = x;
	inv.y = y;
	cx  = (r.right-r.left)/2;
	cy  = (r.bottom-r.top)/2;
	x   = x-r.left-cx;
	y   = y-r.top-cy;
	inv = PolarMapXY2TreemapXYrelXtoR(x,y,inv.x,inv.y,cx,cy,cx,cy);
	t.x = inv.x+cx+r.left;
	t.y = inv.y+cy+r.top;
	return t;
};

function Midpoint(a, b){
	var tmppoint = new TPoint;
	tmppoint.x = (a.x + b.x) / 2;
	tmppoint.y = (a.y + b.y) / 2;
	return tmppoint;
};

function PointDist(a, b){
	return Math.pow(b.x - a.x,2) + Math.pow(b.y - a.y,2);
};

function init_xmlhttp() {
/*	this function will setup xmlhttprequest.  */
	if (typeof window.XMLHttpRequest != 'undefined') { //w3c
		return new XMLHttpRequest();
	} else if (typeof window.ActiveXObject != 'undefined') { //IE
		return new ActiveXObject("Msxml2.XMLHTTP");
	} else return false;
};

function attachEventFunction(obj, evType, fn) {
	if (obj.addEventListener) {
		obj.addEventListener(evType, fn, false);
		return true;
	} else if (obj.attachEvent) {
		var r = obj.attachEvent("on"+evType, fn);
		return r;
	} else {
		return false;
	}
}

