/*  Common JavaScript library  */
/*    1) Small DOM helpers     */
/*    2) Content loader (CL)   */

var IE = document.all ? 1 : 0;

$$ = function(element) {
    if (arguments.length > 1) {
        for (var i = 0, elements = [], length = arguments.length; i < length; i++)
            elements.push($$(arguments[i]));
        return elements;
    } else {
        return document.getElementById(element);
    }
}

$new = function(params,parent) {
    var tag = params['tag'] || 'div';
    var newEl = document.createElement(tag);
    for (var paramName in params) {
        if ((paramName != 'tag') && (paramName != 'text') && (!paramName.match(/^on\w+/))) { newEl[paramName] = params[paramName]; }
        if (paramName.match(/^on(\w+)/)) {
            var eventName = RegExp.$1;
            $attachEvent(newEl, eventName, params[paramName]);
        }
    }
    if (params['text'] != null) { newEl.appendChild($text(params['text'])); }
    if (parent!=null) { parent.appendChild(newEl); }
    return newEl;
}

$text = function(string) {
    return document.createTextNode(string);
}

$clearDOM = function(el) {
    while (el.childNodes.length>0) { el.removeChild(el.firstChild); }
}

$addClass = function(node, className) {
    $removeClass(node, className);
    node.className += ' '+className;
}

$removeClass = function(node, className) {
    var classes = node.className.split(' ');
    for (var i=0; i<classes.length; i++) {
        if (classes[i] == className) {
            classes.splice(i, 1);
        }
    }
    node.className = classes.join(' ');
}

$style = function(node, args) {
    for (var arg in args) {
        if ((arg == 'left') || (arg == 'top') || (arg == 'width') || (arg == 'height') || (arg == 'right') || (arg == 'bottom')) args[arg] += 'px';
        node.style[arg] = args[arg];
    }
}

$point = function(x, y) { this.x = x; this.y = y; }
$position = function(node, toNode) {
    var el = node;
    var x = 0; var y = 0;
    while ((el)&&(el!=toNode)) {
        if (el.offsetLeft) { x += el.offsetLeft; }
        if (el.offsetTop) { y += el.offsetTop; }
        el = el.offsetParent;
    }
    return new $point(x, y);
}
$attachEvent = function(object, event, method, methodId) {
    if (!methodId) { methodId = ''; }
    object['event_'+event+methodId] = function(event) { method.apply(object, [event]); };
    if (typeof(object['addEventListener']) == 'function') {
        object.addEventListener(event, object['event_'+event+methodId], false);
    } else {
        object.attachEvent('on'+event, object['event_'+event+methodId]);
    }
}

$detachEvent = function(object, event, methodId) {
    if (!methodId) { methodId = ''; }
    if (typeof(object['removeEventListener']) == 'function') {
        object.removeEventListener(event, object['event_'+event+methodId], false);
    } else {
        object.detachEvent('on'+event, object['event_'+event+methodId]);
    }
}
JS = new Object();
// Browser checking
//TODO: write more if need
JS.agent = navigator.userAgent;
if (JS.agent.match(/MSIE\s+(\d+)/)) {
    JS.IE = true;
    JS.IE_Version = RegExp.$1;
    if (JS.IE_Version < 7) JS.IE_OLD = true;
}

JS.KHTML = JS.agent.match(/KHTML/);
JS.Opera = JS.agent.match(/Opera/);
JS.Gecko = (!JS.KHTML && JS.agent.match(/Gecko/));
JS.DOM = document.getElementById ? true : false;

/* array copy ----------- */
function $A(source) {
    var ret = [];
    ret = source.slice(0, source.length);
    return ret;
}

/* Ajax Loader */
CL = new Object();
CL.READY_STATE_UNINITIALIZED = 0;
CL.READY_STATE_LOADING = 1;
CL.READY_STATE_LOADED = 2;
CL.READY_STATE_INTERACTIVE = 3;
CL.READY_STATE_COMPLETE = 4;

CL.loader = function(component, url, method, requestParams) {
    this.component = component;
    this.url = url;
    this.requestParams = requestParams;
    this.method = method;
}

CL.loader.prototype = {
    getTransport: function() {
        var transport;
        if (window.XMLHttpRequest) {
            transport = new XMLHttpRequest();
        } else if (window.ActiveXObject) {
            try {
                transport = new ActiveXObject('Msxml2.XMLHTTP');
            } catch(err) {
                transport = new ActiveXObject('Microsoft.XMLHTTP');
            }
        }
        return transport;
    },
    sendRequest: function() {
        var requestParams = [];
        for (var i=0; i<arguments.length; i++) {
            requestParams.push(arguments[i]);
        }
        var request = this.getTransport();
        request.open(this.method, this.url, true);
        request.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
        var oThis = this;
        request.onreadystatechange = function() {
            oThis.handleAjaxResponse(request);
        }
        request.send(this.queryString(requestParams));
    },
    queryString: function(args) {
        var requestParams = [];
        for (var i=0; i<this.requestParams.length; i++) {
            requestParams.push(this.requestParams[i]);
        }
        for (var i=0; i<args.length; i++) {
            requestParams.push(args[i]);
        }
        var queryString = "";
        if (requestParams && requestParams.length > 0) {
            for (var i=0; i<requestParams.length; i++) {
                queryString += requestParams[i] + '&';
            }
            queryString = queryString.substring(0, queryString.length-1);
        }
        return queryString;
    },
    handleAjaxResponse: function(request) {
        if (request.readyState == CL.READY_STATE_COMPLETE) {
            if (this.isSuccess(request)) {
                this.component.ajaxUpdate(request);
            } else {
                this.component.handleError(request);
            }
        }
        if (request.readyState == CL.READY_STATE_LOADING) {
            if (typeof(this.component.ajaxLoading)=='function') {
                this.component.ajaxLoading(request);
            }
        }
    },
    isSuccess: function(request) {
        return request.status == 0 || (request.status >= 200 && request.status < 300);
    }
};

CL.xmlSet = function(xmlElement) {
    var len = xmlElement.childNodes.length;
    for (var i=0; i<len; i++) {
        var attrName = xmlElement.childNodes[i].tagName;
        var attrValue = CL.textContent(xmlElement.childNodes[i]);
        this[attrName] = attrValue;
    }
}

CL.textContent = function(xmlElement) {
    if (xmlElement.text != undefined) return xmlElement.text;
    else if (xmlElement.textContent != undefined) return xmlElement.textContent;
    else if (xmlElement.firstChild != undefined) return xmlElement.firstChild.nodeValue;
}

// escape setup (for cp1251 character encoding) -- remove this block if use utf8
CL.setupEscape = function() {
    var trans = [];
    var utrans = [];
    for (var i = 0x410; i <= 0x44F; i++) { // А-Яа-я
        trans[i] = i - 0x350; 
        utrans[i - 0x350] = i;
    }
    trans[0x401] = 0xA8; trans[0xA8] = 0x401;    // Ё
    trans[0x451] = 0xB8; trans[0xB8] = 0x451;    // ё
    var escapeOrig = window.escape;
    var unescapeOrig = window.unescape;
    window.escape = function(str) {
        str = str.toString();
        var ret = [];
        for (var i = 0; i < str.length; i++) {
            var n = str.charCodeAt(i);
            if (typeof trans[n] != 'undefined') n = trans[n];
            if (n <= 0xFF) ret.push(n);
        }
        return escapeOrig(String.fromCharCode.apply(null, ret));
    }
    window.unescape = function(str) {
        s = unescapeOrig(str);
        var ret = [];
        for (var i = 0; i < s.length; i++) {
            var n = s.charCodeAt(i);
            if (typeof utrans[n] != 'undefined') n = utrans[n];
            ret.push(n);
        }
        return String.fromCharCode.apply(null, ret);
        
    }
}
CL.setupEscape();

newURL = function(action, ParamNames, ParamValues) {
    var URL = '/' + action;
    var s = '?';
    for (var i = 0; i < ParamNames.length; i++) {
        URL += s + ParamNames[i] + '=' + escape(ParamValues[i]);
        s = '&';
    }
    return URL;
}

function SetDialogWindowUp(e,diaWin) {           // модальность диалогового окна путём фокуса в него (Mozilla)
    if (diaWin && !diaWin.closed) {
        if(e) e.preventDefault();
        diaWin.focus();
        return false;
    }
}

function Pack(arr){
    var resStr, key;
    resStr = '';
    for(key in arr) resStr += escape(key) + "=" + escape(arr[key]) + "&";
    return resStr;
}

function UnPack(str){
    var resArr, pairsArr, onePairArr, i;

    resArr = new Array();
    if(str) {
        pairsArr = str.split("&");
        onePairArr = new Array();
        for(i = 0; i < pairsArr.length; i++) {
            onePairArr = pairsArr[i].split("=");
            resArr[unescape(onePairArr[0])] = unescape(onePairArr[1]);
        }
    }
    return resArr;
}

function Dec2Hex(paramByte) {
    var hi, lo;

    hi = Math.floor(paramByte/16);
    lo = paramByte - hi*16;
    return "" + Hex.substr(hi,1) + Hex.substr(lo,1);
}

function Hex2Dec(paramStr) {
    var hi, lo;

    hi = Hex.search(paramStr.substr(0,1));
    lo = Hex.search(paramStr.substr(1,1));
    return hi*16 + lo;
}

function CancelEvent(e) {
    if(IE) window.event.result = false;
    else e.preventDefault();
    return false;
}

function GetHexColor(color) {
    var retColor, colorArray;

    retColor = '000000';
     if(color) {
        retColor = color.toUpperCase();
        if(retColor.search('RGB') >=0) {
            colorArray = new Array();
            retColor = retColor.replace('RGB','');
            retColor = retColor.replace('(','');
            retColor = retColor.replace(')','');
            colorArray = retColor.split(",");
            retColor = Dec2Hex(colorArray[0].replace(' ',''))+Dec2Hex(colorArray[1].replace(' ',''))+Dec2Hex(colorArray[2].replace(' ',''));
          } else {
            retColor = retColor.replace('#','');
            retColor = retColor.substr(0,6);
          }
          if(retColor.match(/[^0-9A-F]/)) retColor = '000000';
    }
    return retColor;
}

function SerializeForm(form) {
    var paramArray= new Array(), formElement, i;
    for(i = 0; i < form.elements.length; i++) {
        formElement = form.elements[i];
        if(formElement.type == "text" || formElement.type == "radio" || formElement.type == "checkbox" || formElement.type == "hidden" || formElement.type == "textarea") {
            paramArray[formElement.id] = formElement.value;
        } else if(formElement.type.search("select") != -1) {
           paramArray[formElement.id] = formElement.options[formElement.selectedIndex].value;
        }else continue;
    }
    return Pack(paramArray);
}

function CancelDialog() {
    window.returnValue = null;
    window.close();
}

function DoneDialog() {
    if(window.opener) window.opener.UnblockEvents();
}

function SubmitDialog(dialogValuesString) {
    if(window.ProcessDialog) window.ProcessDialog(dialogValuesString);
    window.close();
}

function ParseKeyPressed(e) {
    var event = IE ? window.event : e;
    if(event && (event.keyCode == 27)) CancelDialog();
}

function ReportError(msg, url, line) {
    return 0;
//TODO: Write error handler if need
}

function GetArguments() {
    return DialogArgumentsString;
}

function  trSLink(form) {
    var res = form['object_name'].value;
    var ru = [/ш/gi,/щ/gi,/п/gi,/д/gi,/ь/gi,/ч/gi,/е/gi,/в/gi,/б/gi,/у/gi,/а/gi,/й/gi,/р/gi,/к/gi,/т/gi,/н/gi,/ц/gi,/м/gi,/о/gi,/ж/gi,/з/gi,/и/gi,/ъ/gi,/с/gi,/ф/gi,/л/gi,/я/gi,/ё/gi,/г/gi,/х/gi,/э/gi,/ы/gi,/ю/gi];
    var en = ['sh','shh','p','d','','ch','e','v','b','u','a','j','r','k','t','n','c','m','o','zh','z','i','','s','f','l','ja','jo','g','kh','eh','y','ju'];
    for (var i=0; i<ru.length; i++) res = res.replace(ru[i], en[i]);
    res = res.replace(/\s+/g, '_');
    res = res.replace(/[^A-Za-z0-9_\-]/g, '');
    form['slink'].value = res;
}

function SmallSet(a) {
    if (a && (typeof a == 'array' || typeof a == 'object')) this.container = a.slice()
    else this.container = new Array();
    this.length = this.container.length;
}

SmallSet.prototype.contains = function(value) {
    for (var i=0; i<this.length; i++) if (value == this.container[i]) return true;
    return false;
}

SmallSet.prototype.add = function(value) {
    if(!this.contains(value)) { this.container.push(value); this.length = this.container.length; }
}

SmallSet.prototype.del = function(value) {
    for(var i=0; i<this.length; i++)
        if (value == this.container[i]) {
            this.container.splice(i,1);
            this.length = this.container.length;
            return;
        }
}
