var ITcraft = {
	is_debug: false,
	showDebug: function(msg){
		if(this.is_debug == true){
			alert(msg);
		}
	},
	apply: function(o, c, defaults){
		if(defaults){
			ITcraft.apply(o, defaults);
		}
		if(o && c && typeof c == 'object'){
			for(var p in c){
				o[p] = c[p];
			}
		}
		return o;
	},
	_mask_remover: function(el) {
		if(el && el.mask_element_exist){
			el.mask_element_exist = null;
			el.mask_element.remove();
		}
	},
	_loadMask: function(el, load){
		if(Prototype.Browser.IEVersion == 6){
			return false;
		}
		this.mask_prefix = "";
		if(typeof el != "object"){
			el = $(el);
		}
		if(!el){
			ITcraft.showDebug("FATAL - Element not found");
		}
		if(load){
			if(!el.mask_element_exist)	{
				var element_loader=new Element("div");
				el.mask_element = element_loader;
				el.mask_element_exist = true;
				var h = el.getHeight();
				var w = el.getWidth();
				element_loader.setStyle({
					'height':h+"px",
					'width':w+"px",
					'text-align':'center',
					'background':'#EEEEEE',
					'position':'absolute',
					'top':'0px',
					'left':'0px',
					'filter':'alpha(opacity=10)',
					'-moz-opacity':'0.5',
					'zIndex': '1000',
					'opacity':'0.5'
				});
				h = h/2;
				element_loader.update('<img style="margin: 0 auto; display: block; margin-top:'+(h)+'px;" src="images/blue-loading.gif" alt="Load..." />');
				el.insert(element_loader);
			}
		} else {
			setTimeout(this._mask_remover.bind(this, el), 500);
		}
	},
	clearErrors: function(){
		var errors = document.getElementsByClassName(UserAction.class_errors_name);
		errors._each(function(item){
			item.innerHTML = "";
			item.style.height = "14px";
			var input = item.id.replace(/err_/, "");
			if($(input))$(input).className = UserAction.class_without_errors;
		});
	},
	changeField:function(event){
		var element = Event.element(event);
		element.stopObserving();
		if($("err_"+element.id))$("err_"+element.id).innerHTML = "";
		if($(element.id))$(element.id).className = UserAction.class_without_errors;
	},
	showAlert: function(msg, title, handler, scope, width, height){
		if(typeof msg == 'undefined'){
			var msg = 'Hello World!';
		}
		if(typeof title == 'undefined'){
			var title = 'Message';
		}
		var _width = width ? width : 450;
		var _height = height ? height : 240;
		
		if(this.alert_id){
			this.alert_id++;
		}else{
			this.alert_id=1;
		}

		var alert_win = ITcraft.ut.getDialog({
			id: 'alert_'+this.alert_id,
			width: _width,
			height: _height
			//className: 'gopa'
		},{
			content: '<div class="title">'+title+'</div><div class="alert_content_container">'+msg+'</div><div class="alert_buttons_container"><input type="button" class="btn_sm" value="Close" onclick="ITcraft.CloseAlertWin(this);" id="alert_btn_close" /></div>' 
		});
		
		
		/*var alert_win = new UI.Window({
				id: 'alert_'+this.alert_id,
				shadow:true,
				width: _width,
				height: _height,
				//draggable: false,
				className: 'gopa'
		});*/
		//var html = ;
		//alert_win.setContent(html);
		//alert_win.setHeader(title);
		//alert_win.setZIndexWithShadow(3000);
		//alert_win.center().show();
		//alert_win.activate();
		//if (handler) {
		alert_win.show();
		alert_win._CloseHandler = handler;
		alert_win._CloseScope = scope;
		//}
		if($('alert_btn_close')){
			$('alert_btn_close').focus();
		}
	},
	CloseAlertWin: function(el){
		var w = UI.defaultWM.getWindow(el);
		if (typeof w._CloseHandler == 'function') {
			if (w._CloseScope) {
				w._CloseHandler.apply(w._CloseScope);
			} else {
				w._CloseHandler();
			}
		}
		w.destroy();
	},
	showConfirm: function(msg, title, okAction, scope, handler, btns){
		if(typeof msg == 'undefined'){
			var msg = '';
		}
		if(!title){
			var title = 'Confirm';
		}
		var buttons = {
			ok: 'Ok',
			cancel: 'Cancel'
		};
		if (btns) {
			ITcraft.apply(buttons, btns);
		}
		if(!this.confirm_id){
			this.confirm_id++;
		}
		var confirm_win = new UI.Window({
			id: 'conf_'+this.confirm_id,
			shadow:true,
			width: 450,
			draggable: true,
			height: 210
		});
		confirm_win.setContent('<div class="title">'+title+'</div><div class="alert_content_container">'+msg+'</div><div class="conf_buttons_container">'+
			'<input type="button" class="btn_sm" value="' + buttons.ok + '" onclick="ITcraft.CloseConfirmWin(true, this);" />&nbsp;<input type="button" class="btn_sm" value="' + buttons.cancel + '" onclick="ITcraft.CloseConfirmWin(false, this);" /></div>'
		);
		//confirm_win.setHeader(title);
		confirm_win.setZIndexWithShadow(3000);
		confirm_win.center().show();
		confirm_win.activate();
//TODO change
		confirm_win._OkHandler = okAction;
		confirm_win._CloseHandler = handler;
		confirm_win._CloseScope = scope;
	},

	CloseConfirmWin: function(btn, el){
		var w = UI.defaultWM.getWindow(el);
		var f = null;
		if (btn && w._OkHandler) {
			f = w._OkHandler;
		} else if (w._CloseHandler){
			f = w._CloseHandler;
		}
		if (typeof f == 'function') {
			if (w._CloseScope) {
				f.apply(w._CloseScope);
			} else {
				f();
			}
		}
		w.close();
	},

	getWinLeftPosition: function(shift){
		if(typeof shift == 'undefined'){
			shift = 0;
		}
		return  document.body.getWidth() - shift;
	},

	rList: [],

	onReady: function(fn, scope) {
		if (scope) {
			this.rList.push(fn.bind(scope));
		} else {
			this.rList.push(fn);
		};
	},
	_onPLoad: function() {
		for(var i=0; i<this.rList.length; i++) {
			this.rList[i]();
		}
	},
	request: function(url, params){
		if(!url || url == ''){
			ITcraft.showAlert('FATAL - URL not found');
			return false;
		}
		function _onRequestComplete(jsonObj, response){
			if (jsonObj) {
				var msg_text = null;
				if (jsonObj.messages) {
					var m = jsonObj.messages;
					if (m instanceof Array) {
						msg_text = m.join('<br />');
					}
				}
				if (msg_text) {
					if (jsonObj.is_error) {
						ITcraft.showAlert(msg_text, 'Error',
							_internalOnFail.bind(this, jsonObj, response)
						);
					} else {
						ITcraft.showAlert(msg_text, 'Message',
							_internalOnSuccess.bind(this, jsonObj, response)
						);
					}
				}else{
					if (jsonObj.is_error && !params.withoutJSON) {
						_internalOnFail(jsonObj, response);
					} else {
						_internalOnSuccess(jsonObj, response);
					}
				}
			}else if(response){
				_internalOnSuccess(false, response);
			}else{
				var req_fail = 'This request has failed.  Please try later.';
				//ITcraft.showAlert(req_fail, 'Error',
				//	_internalOnFail.bind(this, jsonObj, response)
				//);
			}
		}

		function _internalOnSuccess(result, response) {
			if (!params || !params['onSuccess']) return false;
			var f = params['onSuccess'] ? params['onSuccess'] : null;
			if (f && typeof f == 'function') {
				if (params['scope']) {
					f.apply(params['scope'], arguments);
				} else {
					f(result, response);
				}
			}
		};

		function _internalOnFail(result, response) {
			if (!params || !params['onFail']) return false;
			var f = params['onFail'] ? params['onFail'] : null;
			if (f && typeof f == 'function') {
				var scope = params['fscope'] ? params['fscope'] : (params['scope'] ? params['scope'] : null);
				if (scope) {
					f.apply(scope, arguments);
				} else {
					f(result, response);
				}
			}
		};

		var p = (params && params.parameters) ? params.parameters : {};

		var requestData = new Ajax.Request(url,{
			method: 'post',
			parameters: p,
			onComplete: function(transport, json) {
				if(transport.responseText == 'LOGOUT'){
					document.location = '/login/';
				}
				_onRequestComplete(json, transport.responseText);
			}
		})
	},
	getCookie: function(name) {
		var prefix = name + '=';
		var cookieStartIndex = document.cookie.indexOf(prefix);
		if (cookieStartIndex == -1) {
			return null;
		}
		var cookieEndIndex = document.cookie.indexOf(';', cookieStartIndex + prefix.length);
		if (cookieEndIndex == -1) {
			cookieEndIndex = document.cookie.length;
		}
		return unescape(document.cookie.substring(cookieStartIndex + prefix.length, cookieEndIndex));
	},
	
	setCookie: function( name, value, expires, path, domain, secure )
	{
		// set time, it's in milliseconds
		var today = new Date();
		today.setTime(today.getTime());

		/*
		if the expires variable is set, make the correct
		expires time, the current script below will set
		it for x number of days, to make it for hours,
		delete * 24, for minutes, delete * 60 * 24
		*/
		if (expires) {
			expires = expires * 1000 * 60 * 60 * 24;
		}
		var expires_date = new Date(today.getTime() + (expires));

		document.cookie = name + '=' +escape( value ) +
		( ( expires ) ? ';expires=' + expires_date.toGMTString() : '' ) +
		( ( path ) ? ';path=' + path : '' ) +
		( ( domain ) ? ';domain=' + domain : '' ) +
		( ( secure ) ? ';secure' : '' );
	}
};

ITcraft.format = {
	money: function(v){
		v = (Math.round((v-0)*100))/100;
		v = (v == Math.floor(v)) ? v + '.00' : ((v*10 == Math.floor(v*10)) ? v + '0' : v);
		v = String(v);
		var ps = v.split('.');
		var whole = ps[0];
		var sub = ps[1] ? '.'+ ps[1] : '.00';
		var r = /(\d+)(\d{3})/;
		while (r.test(whole)) {
			whole = whole.replace(r, '$1' + ',' + '$2');
		}
		v = whole + sub;
		if(v.charAt(0) == '-'){
			return '-' + v.substr(1);
		}
		return v;
	}
}

ITcraft.ajaxForm = function(config) {
	ITcraft.apply(this, config);
	this.init();
};

ITcraft.ajaxForm.prototype = {

	form: null,

	with_multiselect: false,

	multi_select_name: 'f[categories]',

	inputErrorClass: 'field-invalid',

	invalidClass: '',

	divErrorClass: 'error',

	listeners: null,

	mask_element: null,

	alert_title: 'Information',
	
	use_error_flags: true,

	init: function() {
		var f = $(this.form);
		if (!f) {
			ITcraft.showDebug('FATAL - FORM element not found!!');
			return false;
		}
		if(!this.mask_element){
			this.mask_element = this.form;
		}

		f.onsubmit = this._onSubmit.bind(this);
		this.form = f;
	},
	_onSubmit: function() {
		ITcraft._loadMask(this.mask_element, true);
		if(this.with_multiselect == false){
			this.form.request({
				onComplete: this._onRequestComplete.bind(this)
			});
		}else{
			var url = this.form.action;
			var data = this.form.serialize(true);
			var categories = null;
			data[this.multi_select_name]._each(function(item){
				if(categories == null){
					categories = item;
				}else{
					categories += ','+item;
				}
			}.bind(this));
			data[this.multi_select_name] = categories;
			var requestData = new Ajax.Request(url,{
				method: 'post',
				parameters: data,
				onComplete: this._onRequestComplete.bind(this)
			})
		}
		return false;
	},
	_onRequestComplete: function(response, jsonObj) {
		if (jsonObj) {
			var msg_text = null;
			var errors_obj = {};
			if (jsonObj.messages) {
				var m = jsonObj.messages;
				if (m instanceof Array) {
					msg_text = m.join('<br />');
				} else {
					errors_obj = m;
				}
			}
			
			if (jsonObj.is_error) {
				this._setupErrors(errors_obj);
			} else {
				this.resetErrors();
			}

			if (msg_text) {
				if (jsonObj.is_error) {
					ITcraft.showAlert(msg_text, 'Error',
						this._internalOnFail.bind(this, jsonObj, response)
					);
				} else {
					ITcraft.showAlert(msg_text, this.alert_title,
						this._internalOnSuccess.bind(this, jsonObj, response)
					);
				}
			} else {
				if (jsonObj.is_error) {
					this._internalOnFail(jsonObj, response);
				} else {
					this._internalOnSuccess(jsonObj, response);
				}
			}
		} else {
			var req_fail = 'Request has Failed. Please, try later.';
			ITcraft.showAlert(req_fail, 'Error',
				this._internalOnFail.bind(this, jsonObj, response)
			);
		}
		ITcraft._loadMask(this.mask_element, false);
	},
	_internalOnSuccess: function(result, response) {
		if (!this.listeners) return false;
		var f = this.listeners['onSuccess'] ? this.listeners['onSuccess'] : null;
		if (f && typeof f == 'function') {
			if (this.listeners['scope']) {
				f.apply(this.listeners['scope'], arguments);
			} else {
				f(result, response);
			}
		}
	},
	_internalOnFail: function(result, response) {
		if (!this.listeners) return false;
		var f = this.listeners['onFail'] ? this.listeners['onFail'] : null;
		if (f && typeof f == 'function') {
			if (this.listeners['scope']) {
				f.apply(this.listeners['scope'], arguments);
			} else {
				f(result, response);
			}
		}
	},
	_setFieldState: function(field, is_valid, mes) {
		if (!is_valid) {
			if (!field.error_div) {
				var p = field.parentNode;
				var d = document.createElement('div');
				d.className = this.divErrorClass;
				p.appendChild(d);
				field.error_div = d;
			} else {
				field.error_div.style.display = '';
			}
			field.error_div.innerHTML = mes;
			if(!field.is_invalid){
				field.begining_class = field.className;
				field.className += ' '+this.inputErrorClass+this.invalidClass;
				field.is_invalid = true;
			}
			if (this.use_error_flags && field.error_flag_div) {
				field.error_flag_div.className = 'flag error';
			}
		} else if(field.is_invalid) {
			field.is_invalid = false;
			field.error_div.style.display = 'none';
			field.className = field.begining_class;
			if (this.use_error_flags && field.error_flag_div) {
				field.error_flag_div.className = 'flag ok';
			}
		}
	},
	_getFieldsMap: function() {
		if (!this.fieldsMap) {
			var m = this.form.elements;
			var map = {};
			var error_div_id, error_div, flag_div_id, flag_div;
			for(var i=0; i<m.length; i++) {

				//if (m[i].type == 'hidden' || m[i].type == 'button' || m[i].type == 'submit' || m[i].type == 'image') {
				if ( m[i].type == 'button' || m[i].type == 'submit' || m[i].type == 'image') {
					continue;
				}

				var data_key = this.getFieldDataKey(m[i]);
				if (data_key) {
					if (map[data_key]) {
						ITcraft.showDebug('already_set' + data_key);
					} else {
						map[data_key] = m[i];
						error_div_id = m[i].getAttribute('error_div_id');
						if (error_div_id) {
							error_div = document.getElementById(error_div_id);
							if (error_div) {
								m[i].error_div = error_div;
							}
						}
						//m[i].onfocus = this._setFieldState.bind(this, m[i], true);
						if (this.use_error_flags) {
							flag_div_id = m[i].getAttribute('error_flag_id');
							if (flag_div_id) {
								var flag_div = document.getElementById(flag_div_id);
								if (flag_div) {
									m[i].error_flag_div = flag_div;
								}
							}
						}
					}
				} else {
					ITcraft.showDebug('Cant get ' + m[i].name + m[i].type);
				}
			}
			this.fieldsMap = map;
		}
		return this.fieldsMap;
	},
	
	resetFieldsMap: function() {
		if (this.fieldsMap) {
			this.fieldsMap = null;
		}
	},

	_getRealFieldSet: function(){
		if (!this.realFieldsMap) {
			var m = this.form.elements;
			var map = {};
			for(var i=0; i<m.length; i++) {
				if (m[i].type == 'button' || m[i].type == 'submit' || m[i].type == 'image' || m[i].type == 'radio') {
					continue;
				}
				var data_key = this.getFieldDataKey(m[i]);
				if (data_key) {
					if (map[data_key]) {
						ITcraft.showDebug('already_set' + data_key);
					} else {
						map[data_key] = m[i];
						var error_div_id = m[i].getAttribute('error_div_id');
						if (error_div_id) {
							var error_div = document.getElementById(error_div_id);
							if (error_div) {
								m[i].error_div = error_div;
							}
						}
						//m[i].onfocus = this._setFieldState.bind(this, m[i], true);
					}
				} else {
					ITcraft.showDebug('Cant get ' + m[i].name + m[i].type);
				}
			}
			this.realFieldsMap = map;
		}
		return this.realFieldsMap;
	},

	getFieldDataKey: function(field) {
		var res = field.getAttribute('_dataIndex');
		if (!res) {
			res = field.name.replace(/(?:.*\[)(.*)(?:\])/, '$1');
		}
		return res;
	},
	setValues: function(formValues){
		/*for (var i in formValues){
			Form.Element.setValue(i,formValues[i].toString());
		}*/
		var map = this._getRealFieldSet();
		var keys = Object.keys(formValues);
		keys.each(function(val){
			var f = map[val];
			var v = formValues[val];
			if (f) f.setValue(v);
		});
	},
	resetErrors: function() {
		this._setupErrors({});
	},
	reset: function() {
		this.form.reset();
		this._setupErrors({});
	},
	_setupErrors: function(mesages){
		var m = this._getFieldsMap();
		for(var name in m) {
			if (mesages[name]) {
				this._setFieldState(m[name], false, mesages[name]);
			} else {
				this._setFieldState(m[name], true);
			}
		}
	},
	submit: function() {
		this._onSubmit();
	}
};

// Produced By Aleksey Prozhoga

ITcraft.starboxWidget = function(config){
	ITcraft.apply(this, config);
	this.init();
}
ITcraft.starboxWidget.prototype = {
	container: null,
	countStars: 5,
	classStar: 'star',
	classStarLeft_i: 'star star-left-i',
	classStarRight_i: 'star star-right-i',
	classStarLeft: 'star star-left',
	classStarRight: 'star star-right',
	classStarNotLoggedLeft: 'star star-not-logged-left',
	classStarNotLoggedRight: 'star star-not-logged-right',
	classPointer: 'star-pointer',
	duration: 40,   // in miliseconds
	count_rated: 0,
	url: null,
	parameters: null,
	rate: null,

	init: function(){
		if(!this.url){
			ITcraft.showDebug('FATAL - URL not found!!');
		}
		if(!this.parameters){
			ITcraft.showDebug('FATAL - Parameters not found!!');
		}
		this.c = $(this.container);
		if (!this.c) {
			ITcraft.showDebug('FATAL - Starbox container not found!!');
			return false;
		}
		if(!this.rate && this.rate != 'hide'){
			this.c.observe('mouseout', this.mouseOut.bind(this));

			// Show initial stars
			for(var i = 0; i < this.countStars*2; i++){
				var div = document.createElement('div');
				this['star_'+i] = $(div);
				if(i % 2 == 0){
					div.className = this.classPointer+' '+this.classStarLeft_i;
				}else{
					div.className = this.classPointer+' '+this.classStarRight_i;
				}
				div.position = i;
				this['star_'+i].observe('mouseover', this.mouseOver.bind(this));
				this['star_'+i].observe('click', this._onRate.bind(this));
				this.c.appendChild(div);
			}
		}else if(this.rate != 'hide'){
			for(var i = 0; i < this.countStars*2; i++){
				var div = document.createElement('div');
				if(i <= (this.rate)*2-1){
					if(i % 2 == 0){
						div.className = this.classStarLeft;
					}else{
						div.className = this.classStarRight;
					}
				}else{
					if(i % 2 == 0){
						div.className = this.classStarLeft_i;
					}else{
						div.className = this.classStarRight_i;
					}
				}
				this.c.appendChild(div);
			}
		}else{
			if($('starbox_container_parent')){
				$('starbox_container_parent').update('Log In or Sign Up to Rate');
			}else{
				for(var i = 0; i < this.countStars*2; i++){
					var div = document.createElement('div');
						if(i % 2 == 0){
							div.className = this.classStarNotLoggedLeft;
						}else{
							div.className = this.classStarNotLoggedRight;
						}
					this.c.appendChild(div);
				}
				this.c.observe('click',  UserAction.userLogin);
				this.c.className += ' pointer';
				// TODO change remove this
				//if(this.c.parentNode && this.c.parentNode.parentNode && this.c.parentNode.parentNode.parentNode){
				//	this.c.parentNode.parentNode.parentNode.innerHTML = 'Log In or Sign Up to Rate';
				//	this.c.parentNode.parentNode.parentNode.style.display = 'none';
				//}
			}
		}
	},
	mouseOver: function(el){
		clearTimeout(this.mouse_out_timeout);
		if(el.target.className == this.classStarLeft_i){
			el.target.className = this.classPointer+' '+this.classStarLeft;
		}else if(el.target.className == this.classStarRight_i){
			el.target.className = this.classPointer+' '+this.classStarRight;
		}
		for(var i = 0; i <= el.target.position; i++){
			if(i % 2 == 0){
				this['star_'+i].className =  this.classPointer+' '+this.classStarLeft;
			}else{
				this['star_'+i].className =  this.classPointer+' '+this.classStarRight;
			}
		}
		for(var i = this.countStars*2-1; i >el.target.position; i-- ){
			if(i % 2 == 0){
				this['star_'+i].className =  this.classPointer+' '+this.classStarLeft_i;
			}else{
				this['star_'+i].className =  this.classPointer+' '+this.classStarRight_i;
			}
		}
	},
	mouseOut: function(el){
		this.mouse_out_timeout = setTimeout(this.resetStars.bind(this), 500);
		this.currentStar = this.countStars*2-1;
	},
	resetStars: function(){

			if(this.currentStar % 2 == 0){
				this['star_'+this.currentStar].className = this.classPointer+' '+this.classStarLeft_i;
			}else{
				this['star_'+this.currentStar].className = this.classPointer+' '+this.classStarRight_i;
			}
			this.currentStar--;
			if(this.currentStar >= 0){
				 this.mouse_out_timeout = setTimeout(this.resetStars.bind(this), this.duration);
			}
	},
	_onRate: function(el){
		this.parameters['f[rate]'] = el.target.position;
		this.currentStar = el.target.position;
		this._removeListeners();
			var requestData = new Ajax.Request(this.url,{
			method: 'post',
			parameters: this.parameters,
				onSuccess: function(transport, json) {
					if(json.is_error == false){
						if($(this.average_rate_box) && json.rate){
							$(this.average_rate_box).innerHTML = json.rate;
							this.count_rated_box = $(this.count_rated_box);
							if(this.count_rated_box){
								this.count_rated_box.update((this.count_rated+1));
							}
						}
						ITcraft.showAlert(json.messages[0], 'Message');
					}else{
						ITcraft.showAlert(json.messages[0], 'Error');
					}
				}.bind(this)
			})
	},
	_removeListeners: function(){
		this.c.stopObserving();
		for(var i = 0; i < this.countStars*2; i++){
			this['star_'+i].stopObserving();
				if(i <= this.currentStar){
					if(i % 2 == 0){
						this['star_'+i].className = this.classStarLeft;
					}else{
						this['star_'+i].className = this.classStarRight;
					}
				}else{
					if(i % 2 == 0){
						this['star_'+i].className = this.classStarLeft_i;
					}else{
						this['star_'+i].className = this.classStarRight_i;
					}
				}
		}
	}
};

ITcraft.colorBoxWidget = function(conf){
	ITcraft.apply(this, conf);
	this.init();
}

ITcraft.colorBoxWidget.prototype = {
	colors: Array(
		'000000', '993300', '333300', '003300', '003366', '000080', '333399', '333333',
		'800000', 'FF6600', '808000', '008000', '008080', '0000FF', '666699', '808080',
		'FF0000', 'FF9900', '99CC00', '339966', '33CCCC', '3366FF', '800080', '969696',
		'FF00FF', 'FFCC00', 'FFFF00', '00FF00', '00FFFF', '00CCFF', '993366', 'C0C0C0',
		'FF99CC', 'FFCC99', 'FFFF99', 'CCFFCC', 'CCFFFF', '99CCFF', 'CC99FF', 'FFFFFF'
	),
	container: null,
	selected_color_input_id: null,
	count_cols: 8,
	object_name: null,
	reset_link: 'reset_link',
	init_color: null,
	init: function(){
		var c = $(this.container);
		if(!c){
			ITcraft.showAlert('FATAL - Color Box container not found!');
			return false;
		}
		this.input = $(this.selected_color_input_id);
		this.reset_link = $(this.reset_link);
		if(this.reset_link){
			this.reset_link.observe('click', this.resetColor.bind(this));
			this.reset_link.hide();
		}
		this.input.readOnly = true;
		var row_start = '<div style="height:20px;overflow:hidden;">'
		var box_content = row_start;
		var count_in_row = 0;
		var _new_row = true;
		var _init_selected_color_id = '';
		for (var i = 0; i < this.colors.length; i++){
			if(this.count_cols <= count_in_row){
				box_content += '<div class="clear"></div></div>' + row_start;
				count_in_row = 0;
			}
			if(this.init_color && this.colors[i] == this.init_color){
				_init_selected_color_id = 'id="selected_color_id"';
			}
			box_content += '<div class="color_box_cell" _color="'+this.colors[i]+'" '+_init_selected_color_id+' onclick="'+this.object_name+'.setColor(\''+this.colors[i]+'\', this);" style="background-color: #'+this.colors[i]+';"></div>';
			count_in_row++;
		}
		c.update(box_content + '<div class="clear"></div></div>');

		if(this.init_color){
			function r(){
				this.setColor(this.init_color, $('selected_color_id'));
			};
			setTimeout(r.bind(this), 500);
		}
	},
	setColor: function(color, el){
		if(this.selected_el){
			this.selected_el.className = 'color_box_cell';
		}
		this.selected_el = el;
		if(el.className){
			el.className = 'color_box_cell-selected';
		}
		this.input.setStyle({
			//border: '1px solid  #c1c1c1',
			background: '#'+color,
			color:'#'+color
		});
		this.input.setValue(color);
		if(this.reset_link){
			this.reset_link.show();
		}
	},
	resetColor: function(){
		this.input.setValue('');
		if(this.selected_el){
			this.selected_el.className = 'color_box_cell';
		}
		this.input.setStyle({
			//border: '1px solid #c1c1c1',
			background: '#FFF'
		});
		if(this.reset_link){
			this.reset_link.hide();
		}
	}
}

// *************************** Prototype  GRID **************************
/*
Example of use :

var config = {
	url : "ajax_search_users.php",
	content_container: "search_users_box",
	mask_element: "mask_container",
	limit: public_num_rows,
	template: new Template('<div class="f_l userbox">' +
		'<a href="#{username}"><div class="shadow"><div class="shadow_inner"><img src="#{picture}" alt="#{username}" /></div></div></a></div>')
};
	new ITcraft.grid(config);
*/

ITcraft.grid = function (config) {
	ITcraft.apply(this, config);
	this.init();
}

ITcraft.grid.prototype = {
	limit: 10, // Count records on the one page is displaying
	mask_element: null, // Default mask element applyed to general content container. If set "none" then mask does not applyed
	url: null, //REQUIRED
	params: {}, // Additional parameters for AJAX REQUEST
	pager_container: null,
	content_container: null, //REQUIRED:  ID of content container
	template: null, // Required Prototype Template. Example new Template("<img src='#{picture}' alt="#{name}" />");
	no_records: "No Records to Display.",
	init_page: 0,
	initdata: null,
	init: function(){
		if(!this.url){
			ITcraft.showAlert("FATAL - Url undefined!");
			return false;
		}
		this.params["limit"] = this.limit;
		this.content_container = $(this.content_container);
		if(!this.content_container){
			ITcraft.showAlert("FATAL -  Content container undefined!");
			return false;
		}
		if(this.pager_container != "none"){
			this.pager_container = $(this.pager_container);
		}
		if(!this.template || typeof this.template != "object"){
			ITcraft.showAlert("FATAL -  Template for Records not defined.<br> <a class='class_pointer' target='_blank' href='http://prototypejs.org/api/template'>See Doc</a>");
			return false;
		}
		if(!this.initdata){
			this._loadGrid(this.init_page);
		}else{
			this._mask(true);
			this.start = this.init_page*this.limit;
			this.page = this.init_page;
			this.params["start"] = this.start;
			var records = "";
			this.total = this.initdata.total;
			if(this.initdata.total > 0){
				records = this._getAllRecords(this.initdata.data);
			} else {
				records = this.no_records;
			}
			this.content_container.update(records);
			if(this.pager_container != "none"){
				if(this.pager_container){
					this.pager_container.update(this._getPager(this.initdata));
				} else {
					if(!this._internalPagerContainer){
						this._internalPagerContainer = new Element("div", {"class": "f_r"});
					}
					this.content_container.insert(this._internalPagerContainer);
					var dd =this._getPager(this.initdata);
					this._internalPagerContainer.update(dd);
				}
			}
			this._mask(false);
		}
	},
	_loadGrid: function(page){

		this._mask(true);

		this.start = page*this.limit;
		this.page = parseInt(page);
		this.params["start"] = this.start;

		ITcraft.request(this.url, {
			parameters: this.params,
			onSuccess: function(json, response){
				if(!json){
					eval("json = " + response);
				}
				var records = "";
				this.total = json.total;
				if(json.total > 0){
					records = this._getAllRecords(json.data);
				} else {
					records = this.no_records;
				}
				this.content_container.update(records);
				if(this.pager_container != "none"){
					if(this.pager_container){
						this.pager_container.update(this._getPager(json));
					} else {
						if(!this._internalPagerContainer){
							this._internalPagerContainer = new Element("div", {"class": "f_r"});
						}
						this.content_container.insert(this._internalPagerContainer);
						var dd =this._getPager(json);
						this._internalPagerContainer.update(dd);
					}
				}
				this._mask(false);
			},
			scope: this
		});
	},
	_getAllRecords: function(data){
			var content = '';
			data.each(function(item){
					content += this.template.evaluate(item);
			}.bind(this))
			content += '<div class="clear"></div>';
			return content;
	},
	getLastPage: function(){
		return this.last_page-1;
	},
	_getPager: function(d){
		var content = new Element("div",{"class": "pager"});
		if(d.total > this.limit){
			var count_pages = Math.round(0.4+(d.total / this.limit));
			this.last_page = count_pages;
			var a = {};
			if (this.start != 0){
				a = this._createPagerLinkWithListener(0, "<< First");
				content.insert(a);

				a = this._createPagerLinkWithListener((parseInt(this.page)-1), "< Previous");
				content.insert(a);
			}
			var left_dot = false;
			var right_dot = false;
			for(var i = 0 ; i <count_pages; i++){
				if(i >= 2 && i < count_pages-2){
					if(i > (parseInt(this.page) - 3) && i < (parseInt(this.page)+3)){
						if(parseInt(this.page) == i){
							content.insert(new Element('a', {"class": "current"}).update((i+1)));
						}else{
							a = this._createPagerLinkWithListener(i, (i+1));
							content.insert(a);
						}
					} else if(i <= (parseInt(this.page) - 3) && !left_dot){
							left_dot = true;
							content.insert(new Element('a').update("..."));
					} else if( i >= (parseInt(this.page)+3) && !right_dot){
						right_dot = true;
						content.insert(new Element('a').update("..."));
					}
				}else{
					if(parseInt(this.page) == i){
						content.insert(new Element('a', {"class": "current"}).update((i+1)));
					}else{
						a = this._createPagerLinkWithListener(i, (i+1));
						content.insert(a);
					}
				}
			}
			if(this.page < (count_pages-1)){
				a = this._createPagerLinkWithListener((parseInt(this.page)+1), "Next >");
				content.insert(a);

				a = this._createPagerLinkWithListener((parseInt(count_pages)-1), "Last >>");
				content.insert(a);
			}
		}
		return content;
	},
	_mask: function (show){
		if(this.mask_element != "none"){
			if(!this._ismask){
				this._ismask = this.mask_element;
			}
			if(this._ismask == null){
				this.mask_element = this.content_container;
			} else {
				this.mask_element = $(this.mask_element);
			}
			if(this.mask_element){
				ITcraft._loadMask(this.mask_element, show);
			}
		}
	},
	_createPagerLinkWithListener: function(param, name){
		var a = new Element("a",{"class": "class_pointer pager_link"});
		a.update(name);
		a.observe("click", this._loadGrid.bind(this, [parseInt(param)]));
		return a;
	},
	_getPagerWithRedirect: function(d){
		var content = new Element("div",{"class": "pager"});
		if(d.total > this.limit){
			var count_pages = Math.round(0.4+(d.total / this.limit));
			this.last_page = count_pages;
			var a = {};
			if (this.start != 0){
				a = this._createPagerLinkWithListener(0, "<< First");
				content.insert(a);

				a = this._createPagerLinkWithListener((parseInt(this.page)-1), "< Previous");
				content.insert(a);
			}
			var left_dot = false;
			var right_dot = false;
			for(var i = 0 ; i <count_pages; i++){
				if(i >= 2 && i < count_pages-2){
					if(i > (parseInt(this.page) - 3) && i < (parseInt(this.page)+3)){
						if(parseInt(this.page) == i){
							content.insert(new Element('a', {"class": "current"}).update((i+1)));
						}else{
							a = this._createPagerRedirectLinkWithListener(i, (i+1));
							content.insert(a);
						}
					}else if(i <= (parseInt(this.page) - 3) && !left_dot){
						left_dot = true;
						content.insert(new Element('a').update("..."));
					}else if( i >= (parseInt(this.page)+3) && !right_dot){
						right_dot = true;
						content.insert(new Element('a').update("..."));
					}
				}else{
					if(parseInt(this.page) == i){
						content.insert(new Element('a', {"class": "current"}).update((i+1)));
					}else{
						a = this._createPagerRedirectLinkWithListener(i, (i+1));
						content.insert(a);
					}
				}
			}
			if(this.page < (count_pages-1)){
				a = this._createPagerRedirectLinkWithListener((parseInt(this.page)+1), "Next >");
				content.insert(a);

				a = this._createPagerRedirectLinkWithListener((parseInt(count_pages)-1), "Last >>");
				content.insert(a);
			}
		}
		return content;
	},
	_createPagerRedirectLinkWithListener: function(param, name){
		var a = new Element("a",{"class": "class_pointer pager_link"});
		a.update(name);
		a.observe("click", function(params){
				this.params["start"] = this.start;
				location.href=this.url+'?'+Object.toQueryString(this.params);
			}.bind(this,parseInt(param))
		);
		return a;
	}
};

ITcraft.ut = {};
ITcraft.ut.charsCounter = function(conf) {
	if (conf) {
		ITcraft.apply(this, conf);
		
		this._init();
	}
};

ITcraft.ut.charsCounter.prototype = {
	field: null,
	counter_box: null,
	max_chars: 1000,
	
	_cctout: null,
	_init: function() {
		if (!this.counter_box || !this.field) {
			return;
		}
		
		var self = this;
		
		var listener = function(ev, el){
			if (!ev) {
				ev = event;
			}
			if (!el) {
				el = this;
			}
			var len = el.value.length;
			if(len == self.max_chars && ev.charCode > 0){
				return false;
			}

			var c_updater = function(){
				if (len > self.max_chars) {
					el.value = el.value.substr(0, self.max_chars);
					self.counter_box.update(0);
				} else {
					self.counter_box.update(self.max_chars - len);
				}
			};
			clearTimeout(self._cctout);
			self._cctout = setTimeout(c_updater, 300);
			return true;
		}
		
		
		
		this.field.onkeyup = listener;
		this.field.onkeypress = listener;
		
		listener({}, this.field);
	}
};
/*** text restorer [start] ***/
ITcraft.ut.resetText = function(el, def_text) {
	if (!el || el.resetTextInstance || (!def_text && !el.value)) return;
	var obj = {
		def_text: def_text ? def_text : el.value,
		el: el,
		isChanged: function() {
			return this.el.value != this.def_text;
		}
	};
	
	el.onclick = function(){
		if(!this.isChanged()){
			this.el.value = '';
		}
	}.bind(obj);
	
	el.onblur = function(){
		if(this.el.value == ''){
			this.el.value = this.def_text;
		}
	}.bind(obj);
	
	el.resetTextInstance = obj;
	el.onclick();
}
/*** text restorer [end] ***/

ITcraft.ut.getDialog = function(w_options, additional_options) {
	if (!w_options) w_options = {};
	
	w_options = ITcraft.apply(w_options, {
		shadow: true,
		close: 'hide',
		minWidth: 400,
		minHeight: 160,
		
		zIndex: 220,
		autoHeigh: false,
		autoWidth: false,
		addWidth: 40,
		addHeight: 70,
		
		autoHeight: false
	});
	
	var w = new UI.Window(w_options);
	
	w.onSetContentListener = function(){
		/*if (this.options.autoHeigh || this.options.autoWidth) {
			var t = function() {
				var c = this.content;
				var o = this.options;
				var th = 0;
				var tw = 0;
				var h = o.autoHeight ? c.offsetHeight : o.height;
				var w = o.autoWidth ? c.offsetWidth : o.width;
				this.setSize(w, h);
				
			}.bind(this);
			t.defer(100);
		}*/
		
		var forms_c = this.content.getElementsByTagName('form');
		if (forms_c.length > 0) {
			var def_form_config = {
				form: forms_c[0],
				listeners: {
					onSuccess: function(d) {
						this.hide();
					},
					scope: this
				}
			};
			if (this.formConfig) {
				def_form_config = ITcraft.apply(def_form_config, this.formConfig);
			}
			this.form = new ITcraft.ajaxForm(def_form_config);
		}
		var btns = this.content.getElementsByClassName('btn cancel');
		if (btns.length) {
			var method = this.options.close && this[this.options.close] ? this.options.close : 'hide';
			btns[0].onclick = this[method].bind(this);
		};
		if (this.onContentUpdatedListener) {
			this.onContentUpdatedListener.apply(this, arguments);
		}
	};

	if (additional_options) {
		var ao = additional_options;
		if (ao.header) {
			w.setHeader(ao.header);
		}
		if (ao.onContentUpdatedListener) {
			w.onContentUpdatedListener = ao.onContentUpdatedListener;
		}
		if (ao.ajax_content) {
			var ajc = ao.ajax_content;
			w.setAjaxContent(
				ajc.url ? ajc.url : '/http/get_dialog.php',
				{
					parameters: ajc.parameters ? ajc.parameters : null,
					onComplete: w.onSetContentListener
				}
			);
		} else if (ao.content) {
			w.setContent(ao.content);
			w.onSetContentListener(ao.content, {});
		}
		if (ao.formConfig) {
			w.formConfig = ao.formConfig;
		};
	};

	w.show = function() {
		var o = this.options;
		if (o.zIndex) {
			this.setZIndexWithShadow(o.zIndex);
		}
		this.center();
		if (this.form) {
			this.form.reset();
		}
		UI.Window.prototype.show.apply(this);
		this.is_show = true;
		this.activate();
		return this;
	};
	w.hide = function(){
		UI.Window.prototype.hide.apply(this);
	};
	w.blur = function(){
		this.hide();
	};
	return w;
};