﻿// global environment
var tucenv_IMGBASE = tucenv_STATICBASE + 'images/';
var tucenv_STYLEBASE = tucenv_STATICBASE + 'themes/';

addLoadEvent(common_load);

function debug(txt) {
	$('tuc_debug').update(txt);
}

function common_load() {
	// common load function

	// first we add events for nav items
	var navseq = $('tuc_nav_seq');
	if(!navseq) return false;
	var navhrefs = navseq.getElementsByTagName('a');
	for (var i = 0; i < navhrefs.length; i++) {
		navhrefs[i].id = 'tuc_nav_' + i;
		navhrefs[i].onmouseover = tuc_movein;
		navhrefs[i].onmouseout = tuc_cancel_movein;
	}
	
	// now we add events for nav expanders
	var navexp = $('tuc_nav_exps');
	if(!navexp) return false;
	var curritem = navexp.getElementsByTagName('div')[0];
    var i = 0;
    while(curritem) {
        if(curritem.className == 'tuc_nav_expander') {
        	curritem.id = 'tuc_nav_' + i + '_exp';
        	curritem.onmouseover = cancel_hide_nav;
        	curritem.onmouseout = tuc_moveout;
        	curritem.style.display = 'none';
        	i++;
        }
        curritem = curritem.nextSibling;
    }
    
    // let's create expander tip boxes
    var tipdiv = document.createElement('div');
    tipdiv.id = 'tuc_nav_exp_tip';
    tipdiv.onmouseover = cancel_hide_nav;
    tipdiv.onmouseout = tuc_moveout;
    document.body.insertBefore(tipdiv, navexp.nextSibling);
    var tipborderdiv = document.createElement('div');
    tipborderdiv.id = 'tuc_nav_exp_tip_border';
    document.body.insertBefore(tipborderdiv, navexp);

	// for perms
	var perms = document.getElementsByClassName('tuc_perm');
	for(var i = 0; i < perms.length; i++) {
		var permlevel = perms[i].value;
		var permlink = Builder.build('<a href="#" id="tuc_permlink_' + perms[i].id + '" title="' + tucsz_CHANGEPERM + '">' + tucsz_PERM[tucenv_BOOKTYPE][permlevel] + '</a>');
		Event.observe(permlink, 'click', tuc_changePermBox);
		perms[i].up().insertBefore(permlink, perms[i]);
	}
	
	// for notifications
	var notifys = $('tuc_notifications');
	var notlink = $('tuc_notifications_link');
	if (notlink && notifys) {
		Event.observe(notlink, 'click', tuc_show_notifications);
		Event.observe(notifys, 'mouseout', function() {
			tuc_gHideNotifTimer = setTimeout('tuc_hide_notifications()', 500);
		});
		Event.observe(notifys, 'mouseover', function() {
			clearTimeout(tuc_gHideNotifTimer);
		});
		tuc_addevent_notifications(notifys);
	}
	
	// for fckeditor
	var htmleditors = tuc_htmleditorelements.length;
	for(var i = 0; i < htmleditors; i++) {
		// from fckeditor docs
		var oFCKeditor = new FCKeditor( tuc_htmleditorelements[i] );
		oFCKeditor.BasePath = tucenv__STATICBASE + "fckeditor/";
		oFCKeditor.Config["CustomConfigurationsPath"] = tucenv_STATICBASE + "fckfull.js";
		oFCKeditor.Config["EditorAreaCSS"] = tucenv_STATICBASE + "themes/" + tuc_gStyleName + "/editor.css";
		oFCKeditor.Config["EditorAreaStyles"] = '';
		var textarea = $(tuc_htmleditorelements[i]);
		oFCKeditor.Width = textarea.offsetWidth;
		oFCKeditor.Height = textarea.offsetHeight;
		oFCKeditor.ReplaceTextarea();
	}
}

var tuc_gChangePermId;
var tuc_gChangePermHandler = null;
function tuc_changePermBox(event) {
	Event.stop(event);
	var itemid = Event.element(event).id.substring(13);
	tuc_gChangePermId = itemid;
	TucWindow.enable(tucsz_CHANGEPERM, tucenv__STATICBASE + 'perm.htm', {width: 400, height: 250});
}

function tuc_changePerm(newvalue) {
	var permitem = $(tuc_gChangePermId);
	if (permitem.value != newvalue) {
		permitem.previous().update(tucsz_PERM[tucenv_BOOKTYPE][newvalue]);
		permitem.value = newvalue;
		if (tuc_gChangePermHandler) {
			tuc_gChangePermHandler(permitem);
		}
	}
}

var tuc_gMoveinTimer;
function tuc_movein() {
    clearTimeout(tuc_gMoveinTimer);
    hide_nav();
    tuc_gMoveinTimer = setTimeout('tuc_showlist(\'' + this.id + '\')', 500);
}

function tuc_cancel_movein() {
    clearTimeout(tuc_gMoveinTimer);
}

// current nav expander's id
var curr_nav_id = '';

function tuc_showlist(thisid) {
    clearTimeout(tuc_gMoveinTimer);
    hide_nav();
    
    var thisitem = $(thisid);
    // first, check the existence of the item
    if(! thisitem) return false;
    if(! $(thisid + '_exp')) return false;
    var targetelem = $(thisid + '_exp');
    // find the position of current item
    var newpos = findPos(thisitem);
    
    // get the UL list
    var curritem = targetelem.getElementsByTagName('ul')[0].firstChild;
    var itemoffset = 0;
    var itemheight = 0;
    
    // assign text-tip function to mouseover event
    var i = 0;
    while(curritem) {
        if(curritem.tagName == 'LI') {
            if(curritem.className == 'tuc_sel') {
                itemoffset = i;
            }
            curritem.onmouseover = tuc_nav_tip;
            i++;
        }
        curritem = curritem.nextSibling;
    }
    
    var newtop = newpos[1] - itemoffset * 18;
    targetelem.style.left = newpos[0] + 'px';
    targetelem.style.top = newtop + 'px';
    targetelem.style.width = (thisitem.offsetWidth - 2) + 'px';
    targetelem.style.display = 'block';

    curr_nav_id = thisid;
    
    if(newtop < 0) {
        setTimeout('tuc_exp_scroll(\'' + thisid + '_exp\',' + newtop + ')', 200);
    }
}

function tuc_exp_scroll(scrollitem, newtop) {
    tuc_nav_hide_tip();
    newtop = newtop + 9;
    $(scrollitem).style.top = newtop + 'px';
    if(newtop < 0) {
        setTimeout('tuc_exp_scroll(\'' + scrollitem + '\',' + newtop + ')', 20);
    }
}

var tuc_gMoveoutTimer;
function tuc_moveout() {
    tuc_gMoveoutTimer = setTimeout('hide_nav()', 500);
}

function cancel_hide_nav() {
    clearTimeout(tuc_gMoveoutTimer);
}

function hide_nav() {
    tuc_nav_hide_tip();
    if(curr_nav_id != '') {
        var targetelem = $(curr_nav_id + '_exp');
        if(targetelem) {
	        targetelem.style.display = 'none';
	    }
    }
}

function tuc_nav_tip() {
    if(this.className != 'tuc_sel') {
        var targetelem = $('tuc_nav_exp_tip');
        var targetelem2 = $('tuc_nav_exp_tip_border');
        var newpos = findPos(this);

        // i really really don't like browser sniffing, but Firefox 2 has a quirk here.
        if(isFirefox2) {
            // the absolute position is less 1 than the actual value
            newpos[0]++;    newpos[1]++;
        }
        
        targetelem.style.left = (newpos[0] + 1) + 'px';
        targetelem.style.top = (newpos[1] + 1) + 'px';
        targetelem.innerHTML = this.innerHTML;
        targetelem.style.display = 'block';
        targetelem2.style.left = (newpos[0]) + 'px';
        targetelem2.style.top = (newpos[1]) + 'px';
        targetelem2.innerHTML = this.innerHTML;
        targetelem2.style.display = 'block';
        debug(targetelem.offsetWidth);
    }
}

function tuc_nav_hide_tip() {
    $('tuc_nav_exp_tip').style.display = 'none';
    $('tuc_nav_exp_tip_border').style.display = 'none';
}

function tuc_cacheimage(url) {
	var cache = $('tuc_imagecache');
	var newimg = Builder.node('img', {src: url, alt: 'cached image'});
	cache.appendChild(cache);
}

var tuc_gHideNotifTimer = 0;
function tuc_show_notifications(event) {
	Event.stop(event);
	var notifylink = $('tuc_notifications_link');
	var notifys = $('tuc_notifications');
	if (notifys.style.display == 'block') {
		return;
	}
	var childs = notifys.down('ul').immediateDescendants();
	var newremain = 0;	// currently new message count
	if (childs.length == 1) {	// show 'no notifys' message
		childs[0].style.display = 'block';
	} else if (childs.length > 1) {
		var allread = 1;
		for (var i = 0; i < childs.length - 1; i++) {
			if(! childs[i].hasClassName('tuc_q')) {
				allread = 0;
				newremain++;
			}
		}
		if (allread) {
			childs[childs.length - 1].style.display = 'block';
		}
	}
	var notifnum = notifylink.down('span.tuc_number');
	if (notifnum) {
		if (newremain == 0) {
			notifnum.style.display = 'none';
		} else {
			notifnum.update('(' + newremain + ')');
		}
	}

	var pos = findPos(notifylink);
	var size = notifylink.getDimensions();
	var boxwidth = notifys.getWidth();
	if (isQuirkIE && boxwidth > 300) {
		boxwidth = 300;
		notifys.style.width = 300;
	}
	notifys.style.left = (pos[0] + size.width - boxwidth - 2) + 'px';
	notifys.style.top = (pos[1] + size.height - 1) + 'px';
	notifys.style.display = 'block';
	notifylink.addClassName('tuc_selected');
}

function tuc_hide_notifications() {
	clearTimeout(tuc_gHideNotifTimer);
	$('tuc_notifications_link').removeClassName('tuc_selected');
	$('tuc_notifications').style.display = 'none';
}

function tuc_redirect_notification(event) {
	var el = Event.element(event);
	if (el.href) {
		var li = el.up('li');
		if (li.hasClassName('tuc_q')) {
			return;	// no need to redirect
		}
		var id = li.className.substring(13);
		var spaceindex = id.indexOf(' ');
		if (spaceindex > 0) {
			id = id.substring(0, spaceindex);
		}
		el.href = $('tuc_notifications_link').href + 'r/'+ id + '/?url=' + encodeURIComponent(el.href);
	}
}

function tuc_accept_notification(event) {
	Event.stop(event);
	var el = Event.element(event);
	var li = el.up('li');
	if (li.hasClassName('tuc_q')) {
		return;	// no need to accept
	}
	var id = li.className.substring(13);
	var spaceindex = id.indexOf(' ');
	if (spaceindex > 0) {
		id = id.substring(0, spaceindex);
	}
	alert(id);

/*	if (el.href) {
		var itemid = el.className.substring(29);
		el.href = $('tuc_notifications_link').href + 'r/'+ itemid + '/?url=' + encodeURIComponent(el.href);
	}*/
}

function tuc_ignore_notification(event) {
	Event.stop(event);
	var el = Event.element(event);
	var li = el.up('li');
	if (li.hasClassName('tuc_q')) {
		return;	// no need to accept
	}
	var id = li.className.substring(13);
	var spaceindex = id.indexOf(' ');
	if (spaceindex > 0) {
		id = id.substring(0, spaceindex);
	}
	alert(id);
/*	if (el.href) {
		var itemid = el.className.substring(29);
		el.href = $('tuc_notifications_link').href + 'r/'+ itemid + '/?url=' + encodeURIComponent(el.href);
	}*/
}

function tuc_addevent_notifications(conel) {
	var notitems = $(conel).getElementsBySelector('a.tuc_notifylinks');
	for (var i = 0; i < notitems.length; i++) {
		Event.observe(notitems[i], 'click', tuc_redirect_notification);
	}
	var accepts = $(conel).getElementsBySelector('button.tuc_accept');
	for (var i = 0; i < accepts.length; i++) {
		Event.observe(accepts[i], 'click', tuc_accept_notification);
	}
	var ignores = $(conel).getElementsBySelector('button.tuc_ignore');
	for (var i = 0; i < ignores.length; i++) {
		Event.observe(ignores[i], 'click', tuc_ignore_notification);
	}
}

var tuc_gLastBlockInfo;

function tuc_blockInfo(el) {
	var bcontent = el.down('div.tuc_block_content');
	var blockkey = bcontent.className;
	blockkey = blockkey.substring(27);
	var blockid = '';
	if (blockkey != 'error') {
		blockid = bcontent.id;
		if (blockid) {
			blockid = blockid.substring(11 + blockkey.length);
		}
	}
	tuc_gLastBlockInfo = [blockkey, blockid];
	return tuc_gLastBlockInfo;
}

function tuc_getBlockByInfo(blockinfo) {
	return $('tuc_block_' + blockinfo[0] + '_' + blockinfo[1]);
}

function tuc_createXML() {
	// from quirksmode.org
	var xmlDoc;
	if (document.implementation && document.implementation.createDocument)
	{
		xmlDoc = document.implementation.createDocument('', '', null);
	}
	else if (window.ActiveXObject)
	{
		xmlDoc = new ActiveXObject("Microsoft.XMLDOM");
	}
	else
	{
		return null;
	}
	return xmlDoc;
}

if (!window.TucWindow)
	var TucWindow = new Object();

TucWindow.Methods = {
	focusableElements: new Array,

	init: function() {
		this.disable = this.disable.bindAsEventListener(this);
		this.enable = this.enable.bind(this);

		this.barrier = Builder.node('div', { id: 'tuc_barrier' });
		// Event.observe(this.barrier, "click", this.disable);
		
		this.windowbox = Builder.node('div', { id: 'tuc_window' }, [
			Builder.node('div', { id: 'tuc_window_title' }, [
				this.closelink = Builder.node('a', {href: '', title: tucsz_CLOSE, className: 'tuc_button tuc_close_button'}, [
					Builder.build('<sub>&times;</sub>')
				]),
				this.titlebox = Builder.node('div')
			]),
			this.contentbox = Builder.node('div', { id: 'tuc_window_content' }),
		]);
		document.body.insertBefore(this.windowbox, document.body.childNodes[0]);
		document.body.insertBefore(this.barrier, document.body.childNodes[0]);

		this.barrier = $(this.barrier);
		this.windowbox = $(this.windowbox);
		this.titlebox = $(this.titlebox);
		this.contentbox = $(this.contentbox);
		this.closelink = $(this.closelink);
		
		Event.observe(this.closelink, "click", this.disable);	
	
		this.kbdHandler = this.kbdHandler.bindAsEventListener(this);
		
		this.enabled = false;
	},

	resize: function() {
		this.barrier.style.width = document.body.offsetWidth + 'px';
		this.barrier.style.height = document.body.offsetHeight + 'px';
		this._calcPosition();
		// set position
		this.windowbox.style.left = this.windowleft;
	},
	
	enable: function(title, url, options) {
		this.titlebox.update(title);
		this.url = url;
		this.setOptions(options);
		if(!this.enabled) {
			if(isQuirkIE) {
				// IE 6 and below don't support position: fixed, so we need to workaround.
				this.barrier.style.position = 'absolute';
		
				var bod = document.getElementsByTagName('body')[0];
				bod.style.height = '100%';
				bod.style.overflow = 'hidden';
		
				var htm = document.getElementsByTagName('html')[0];
				htm.style.height = '100%';
				htm.style.overflow = 'hidden';
			}
		 	this.barrier.setStyle({opacity: 0});
			this.barrier.style.display = 'block';
			this.windowbox.addClassName('tuc_window_loading');
			new Effect.Fade(this.barrier, {from: 0, to: 0.5, duration: 0.5, afterFinish: function() {
					this._show();
				}.bind(this)
			});
			Event.observe(document, "keypress", this.kbdHandler);
			this.enabled = true;
		} else {
			this._update();
		}
	},
	
	disable: function(event) {
		if(event) Event.stop(event);
		if(this.enabled) {
			if(isQuirkIE) {
				// IE 6 and below don't support position: fixed, so we need to workaround.
				this.barrier.style.position = 'absolute';
		
				var bod = document.getElementsByTagName('body')[0];
				bod.style.height = 'auto';
				bod.style.overflow = 'auto';
		
				var htm = document.getElementsByTagName('html')[0];
				htm.style.height = 'auto';
				htm.style.overflow = 'auto';
			}
			this._hide();
			Event.stopObserving(document, "keypress", this.kbdHandler);
			new Effect.Fade(this.barrier, {to: 0, duration: 0.5, afterFinish: function() {
					this.barrier.style.display = 'none';
				}.bind(this)
			});
			this.enabled = false;
		}
		return false;
	},
	
	setOptions: function(options) {
		this.options = {
			overlayClose: true, // Close modal box by clicking on overlay
			width: 400,
			height: 400,
			params: {}
		};
		Object.extend(this.options, options || {});
	},
	
	_show: function() {
		this._setWidth();
		this._calcPosition();
		this.windowbox.style.display = 'block';
		this.windowbox.style.left = this.windowleft + 'px';
		this.windowbox.style.top = (0 - this.options.height) + 'px';
		new Effect.Move(this.windowbox, {x: this.windowleft, y: 45, mode:'absolute', duration: 0.5, afterFinish: function() {
				this._loadContent();
			}.bind(this)
		});
	},
	
	_update: function() {
		this.contentbox.style.display = 'none';
		this.contentbox.update();
		this.windowbox.addClassName('tuc_window_loading');
		this._calcPosition();
		new Effect.ScaleBy(this.windowbox, 
			this.options.width - Element.getWidth(this.windowbox),
			this.options.height - Element.getHeight(this.windowbox),
			{ duration: 0.5, afterFinish: function() {
					this._loadContent();
				}.bind(this)
			});
	},
	
	_hide: function() {
		this.windowbox.style.display = 'none';
		this.contentbox.update();
		this.contentbox.style.display = 'none';
	},

	_setWidth: function() {
		//Set size
		this.windowbox.style.width = this.options.width + "px";
		this.windowbox.style.height = this.options.height + "px";
		//this.MBcontent.style.height = this.options.height - 42 + "px";
	},
	
	_calcPosition: function() {
		this.windowleft = Math.round((Element.getWidth(document.body) - Element.getWidth(this.windowbox)) / 2 );
	},
	
	_loadContent: function() {
		var myAjax = new Ajax.Request( this.url, { method: 'post', parameters: this.options.params, 
			onComplete: function(originalRequest) {
				this.windowbox.removeClassName('tuc_window_loading');
				this.contentbox.style.display = 'block';
				var response = new String(originalRequest.responseText);
				this.contentbox.innerHTML = response;
				response.extractScripts().map(function(script) { 
					return eval(script.replace("<!--", "").replace("// -->", ""));
				});
				this.focusableElements = this._findFocusableElements();
				this._moveFocus(); // Setting focus on first 'focusable' element in content (input, select, textarea, link or button)
			}.bind(this)
		});
	},
	
	_moveFocus: function() { // Setting focus to be looped inside current MB
		if(this.focusableElements.length > 0)
			this.focusableElements.first().focus(); // Focus on first focusable element except close button
		else
			this.closelink.focus(); // If no focusable elements exist focus on close button
	},
	
	_findFocusableElements: function(){ // Collect form elements or links from MB content
		return $A(this.contentbox.descendants()).findAll(function(node){
			return (["INPUT", "TEXTAREA", "SELECT", "A", "BUTTON"].include(node.tagName));
		});
	},

	kbdHandler: function(e) {
		var node = Event.element(e);
		switch(e.keyCode) {
			case Event.KEY_TAB:
				if(Event.element(e) == this.focusableElements.last()) {
					Event.stop(e);
					this._moveFocus();  // Find last element in MB to handle event on it. If no elements found, uses close ModalBox button
				}
			break;			
			case Event.KEY_ESC:
				this.disable(e);
			break;
			case Event.KEY_UP:
			case Event.KEY_DOWN:
			case Event.KEY_PAGEDOWN:
			case Event.KEY_PAGEUP:
			case Event.KEY_HOME:
			case Event.KEY_END:
				if(!["TEXTAREA", "SELECT"].include(node.tagName) || 
				(node.tagName == "INPUT" && (node.type == "submit" || node.type == "button")) ) Event.stop(e);
			break;
		}
	}
}


Effect.ScaleBy = Class.create();
Object.extend(Object.extend(Effect.ScaleBy.prototype, Effect.Base.prototype), {
  initialize: function(element, byWidth, byHeight, options) {
    this.element = $(element)
    var options = Object.extend({
	  scaleFromTop: true,
      scaleMode: 'box',        // 'box' or 'contents' or {} with provided values
      scaleByWidth: byWidth,
	  scaleByHeight: byHeight
    }, arguments[3] || {});
    this.start(options);
  },
  setup: function() {
    this.elementPositioning = this.element.getStyle('position');
      
    this.originalTop  = this.element.offsetTop;
    this.originalLeft = this.element.offsetLeft;
	
    this.dims = null;
    if(this.options.scaleMode=='box')
      this.dims = [this.element.offsetHeight-5, this.element.offsetWidth-10];
	 if(/^content/.test(this.options.scaleMode))
      this.dims = [this.element.scrollHeight, this.element.scrollWidth];
    if(!this.dims)
      this.dims = [this.options.scaleMode.originalHeight,
                   this.options.scaleMode.originalWidth];
	  
	this.deltaY = this.options.scaleByHeight;
	this.deltaX = this.options.scaleByWidth;
  },
  update: function(position) {
    var currentHeight = this.dims[0] + (this.deltaY * position);
	var currentWidth = this.dims[1] + (this.deltaX * position);
	
    this.setDimensions(currentHeight, currentWidth);
  },

  setDimensions: function(height, width) {
    var d = {};
    d.width = width + 'px';
    d.height = height + 'px';
    
	var topd  = Math.round((height - this.dims[0])/2);
	var leftd = Math.round((width  - this.dims[1])/2);
	if(this.elementPositioning == 'absolute' || this.elementPositioning == 'fixed') {
		if(!this.options.scaleFromTop) d.top = this.originalTop-topd + 'px';
		d.left = this.originalLeft-leftd + 'px';
	} else {
		if(!this.options.scaleFromTop) d.top = -topd + 'px';
		d.left = -leftd + 'px';
	}
    this.element.setStyle(d);
  }
});

Object.extend(TucWindow, TucWindow.Methods);

addLoadEvent(TucWindow.init.bind(TucWindow));
addResizeEvent(TucWindow.resize.bind(TucWindow));
