// START of the library
if(typeof window.mx == "undefined") {

  /*

    MXD Manticore JavaScript library

    Author: Filip Oscadal <filip@mxd.biz>
    Homepage: http://mxd.biz

    Uses Firefox FireBug extension.
    Homepage: http://www.joehewitt.com/software/firebug

    Contains MD5 and SHA-1 implementations by Paul Johnston.
    Homepage: http://pajhome.org.uk

    Contains a modified implementation of AJAX by Matt Kruse.
    Homepage: http://www.ajaxtoolbox.com

    Contains a Browser Detect function by Peter-Paul Koch.
    Homepage: http://www.quirksmode.org

    Contains an implementation of Sortable Tables by Joost de Valk.
    Homepage: http://www.joostdevalk.nl/code/sortable-table

    Some parts of the library are inspired by the Prototype library by Sam Stephenson.
    Homepage: http://prototype.conio.net

    This library is free and published under the GNU GPL licence,
    some parts are published under their corresponding licences.

  */


  /*
    +++ DEBUG
  */


  var debug;
  if ((debug != 0) && (debug != 1)) debug = 0;
  if (!debug && ie) window.onerror = function()
  {
    return true;
  }

  function bug(x)
  {
    try
    {
      if (console) if (console.log) // check for the Firebug extension presence
      {
        console.log(x);
        return true;
      }
    } catch(e)
    {
      window.status = x;
    }
    return true;
  }



  /*
    +++ PROTOTYPE
  */


  // get the length of the array
  Array.prototype.size = function()
  {
    return this.length;
  }

  // clear the array
  Array.prototype.clear = function()
  {
    this.length = 0;
    return this;
  }

  // get the first element
  Array.prototype.first = function()
  {
    return this[0];
  }

  // get the last element
  Array.prototype.last = function()
  {
    return (this.length == 0) ? false : this[this.length - 1];
  }

  // get the index of the parameter
  Array.prototype.indexOf = function(x)
  {
    if (!x) return -1;
    if(this.join('').indexOf(x) == -1) return -1;
    for (var i = 0, l = this.length; i < l; i++) if (this[i] == x) return i;
    return -1;
  }

  // apply an iterator to elements of the array
  Array.prototype.each = function(iterator)
  {
    if(!iterator) return false;
    if(typeof iterator != 'function') return false;
    for (var i = 0, l = this.length; i < l; i++) iterator(this[i]);
    return this;
  }

  // shuffle the array elements
  Array.prototype.shuffle = function()
  {
    for (var i = 0, l = this.length; i < l; i++)
    {
      var r = parseInt(Math.random() * l);
      var o = this[i];
      var p = this[r];
      if(o == p) continue;
      this[i] = p;
      this[r] = o;
    }
    return this;
  }

  // convert array elements to uppercase
  Array.prototype.toUpperCase = function()
  {
    for (var i = 0, l = this.length; i < l; i++) this[i] = this[i].toUpperCase();
    return this;
  }

  // convert array elements to lowercase
  Array.prototype.toLowerCase = function()
  {
    for (var i = 0, l = this.length; i < l; i++) this[i] = this[i].toLowerCase();
    return this;
  }

  // capitalize the array elements
  Array.prototype.capitalize = function()
  {
    for (var i = 0, l = this.length; i < l; i++) this[i] = this[i].charAt(0).toUpperCase() + this[i].substring(1).toLowerCase();
    return this;
  }

  // copy the array to a unique one
  Array.prototype.clone = function()
  {
    return [].concat(this);
  }

  // get the maximal value of the array
  Array.prototype.max = function()
  {
    var max = this.first();
    for (var i = 0, l = this.length; i < l; i++) max = max > this[i] ? max : this[i];
    return max;
  }

  // get the minimal value of the array
  Array.prototype.min = function()
  {
    var min = this.first();
    for (var i = 0, l = this.length; i < l; i++) min = min < this[i] ? min : this[i];
    return min;
  }

  // new version of the concat method
  Array.prototype.concat = function()
  {
    var a = [];
    for (var i = 0, l = this.length; i < l; i++) a.push(this[i]);
    for (var i = 0, l = arguments.length; i < l; i++)
    {
      if(arguments[i].constructor == Array)
      {
        for (var j = 0, k = arguments[i].length; j < k; j++) a.push(arguments[i][j]);
      }
      else
      {
        a.push(arguments[i]);
      }
    }
    return a;
  }


  /*
    +++ FUNCTIONS
  */


  // get a pointer to a DOM element by its id (tries to get it even from the obsolete document.all)
  function $(x)
  {
    if (document.getElementById)
    {
      if (document.getElementById(x)) return document.getElementById(x);
    }
    if (document.all) if (document.all[x]) return document.all[x];
    return false;
  }

  // get a pointer to the element's style property
  function $$(x)
  {
    if ($(x))
    {
      if ($(x).style)
      {
        return $(x).style;
      }
    }
    return false;
  }

  var browserDetect =
  {
    init: function ()
    {
      this.browser = this.searchString(this.dataBrowser) || "An unknown browser";
      this.version = this.searchVersion(navigator.userAgent) || this.searchVersion(navigator.appVersion)
        || "an unknown version";
      this.os = this.searchString(this.dataOS) || "an unknown OS";
    },
    searchString: function (data)
    {
      for (var i = 0, l = data.length; i < l; i++)
      {
        var dataString = data[i].string;
        var dataProp = data[i].prop;
        this.versionSearchString = data[i].versionSearch || data[i].identity;
        if (dataString)
        {
          if (dataString.indexOf(data[i].subString) != -1) return data[i].identity;
        }
        else if (dataProp) return data[i].identity;
      }
      return false;
    },
    searchVersion: function (dataString)
    {
      var index = dataString.indexOf(this.versionSearchString);
      if (index == -1) return '';
      return parseFloat(dataString.substring(index + this.versionSearchString.length + 1));
    },
    dataBrowser:
    [
      {
        string: navigator.userAgent,
        subString: "OmniWeb",
        versionSearch: "OmniWeb/",
        identity: "OmniWeb"
      },
      {
        string: navigator.vendor,
        subString: "Apple",
        identity: "Safari"
      },
      {
        prop: window.opera,
        identity: "Opera"
      },
      {
        string: navigator.vendor,
        subString: "iCab",
        identity: "iCab"
      },
      {
        string: navigator.vendor,
        subString: "KDE",
        identity: "Konqueror"
      },
      {
        string: navigator.userAgent,
        subString: "Firefox",
        identity: "Firefox"
      },
      {
        string: navigator.vendor,
        subString: "Camino",
        identity: "Camino"
      },
      {
        string: navigator.userAgent,
        subString: "Netscape",
        identity: "Netscape"
      },
      {
        string: navigator.userAgent,
        subString: "MSIE",
        identity: "Explorer",
        versionSearch: "MSIE"
      },
      {
        string: navigator.userAgent,
        subString: "Gecko",
        identity: "Mozilla",
        versionSearch: "rv"
      },
      {
        string: navigator.userAgent,
        subString: "Mozilla",
        identity: "Netscape",
        versionSearch: "Mozilla"
      }
    ],
    dataOS :
    [
      {
        string: navigator.platform,
        subString: "Win",
        identity: "Windows"
      },
      {
        string: navigator.platform,
        subString: "Mac",
        identity: "Mac"
      },
      {
        string: navigator.platform,
        subString: "Linux",
        identity: "Linux"
      }
    ]
  };

  browserDetect.init();

  var locale, mx_site;

  var ns = document.layers ? 1 : 0;
  var ie = window.ActiveXObject ? 1 : 0;
  var ie5 = (ie && (parseInt(browserDetect.version) < 6)) ? 1 : 0;
  var ie6 = (ie && (parseInt(browserDetect.version) == 6)) ? 1 : 0;
  var ie7 = (ie && (parseInt(browserDetect.version) > 6)) ? 1 : 0;
  var opera = browserDetect.browser == 'Opera' ? 1: 0;
  var firefox = browserDetect.browser == 'Firefox' ? 1: 0;

  var dom = (document.getElementById && document.createElement) ? 1 : 0;

  /*
    +++ Manticore object START
  */


  var mx_prototype = function ()
  {


  /*
    +++ CONFIGURATION
  */


    this.config =
    {
      locale : (locale == undefined) ? 'cz' : locale,
      session_variable : 'PHPSESSID',
      loading_picture : 'matrix/loading.gif',
      manticore_picture : 'matrix/manticore.gif',
      transparent_picture : 'matrix/null.gif',
      manticore_picture_enabled : 1,
      onload_fix_msie : 1,
      picture_show_opacity : 1,
      truncate : 30,
      ajax_timeout : 20000,
      ajax_cache_enabled : 1,
      ajax_cache_timeout : 60,
      ajax_parse_javascript : 1,
      ajax_retry_send : 1,
      silent : 0
    }


  /*
    +++ LOCALE
  */


    this.locale =
    {
      en :
      {
        loading : 'Loading...',
        close_picture : 'click to close the picture',
        md5_vm_failed : 'JavaScript VM not working correctly, MD5 selftest failed.',
        sha1_vm_failed : 'JavaScript VM not working correctly, SHA-1 selftest failed.'
      },
      cz :
      {
        loading : 'Loading...',
        close_picture : 'kliknut&#xed;m zav&#x159;ete obr&#xe1;zek',
        md5_vm_failed : 'JavaScript VM nepracuje sprvn, MD5 selftest selhal.',
        sha1_vm_failed : 'JavaScript VM nepracuje sprvn, SHA-1 selftest selhal.'
      }
    }

    this.settings =
    {
      version : 'v2.8 build 007 2007-03-04',
      debug : (debug > 0) ? 1 : 0,
      ns : ns,
      ie : ie,
      ie5 : ie5,
      ie6 : ie6,
      ie7 : ie7,
      opera : opera,
      firefox : firefox,
      dom : dom,
      cookie : 0,
      ajax : (window.XMLHttpRequest || window.ActiveXObject) ? 1 : 0,
      locale : locale,
      mx_site : (mx_site == undefined) ? window.location.host.toLowerCase() : mx_site,
      framed : (window != top) ? 1 : 0,
      loaded : 0,
      loading : '',
      md5 : 0,
      sha1 : 0,
      onload : [],
      show : function()
      {
        var x = '';
        for (var i in mx.settings)
        {
          if ((typeof mx.settings[i] != 'function') && (typeof mx.settings[i] != 'object')) x += '[' + i + '] ' + mx.settings[i] + ' ';
        }
        return x;
      }
    }

    this.logs =
    {
      ajax_call : 0,
      ajax_get : 0,
      ajax_post : 0,
      ajax_fail : 0,
      ajax_resend : 0,
      ajax_speed : -1,
      pictures_showed : 0,
      pictures_failed : 0,
      alert_id : '',
      alert_stack : [],
      alert_count : 0,
      picture_id : '',
      events : {},
      show : function()
      {
        var x = '';
        for (var i in mx.logs)
        {
          if ((typeof mx.logs[i] != 'function') && (typeof mx.logs[i] != 'object')) x += '[' + i + '] ' + mx.logs[i] + ' ';
        }
        return x;
      }
    }

    this.url =
    {
      host : window.location.host,
      protocol : window.location.protocol.toLowerCase(),
      port : (window.location.port == '') ? ((window.location.protocol.toLowerCase() == 'https:') ? 443 : 80) : window.location.port,
      href : window.location.href.replace(/#([\x00-\xff\u0000-\uffff]+)/, ''),
      ssl : ((window.location.port == 443) || (window.location.protocol == 'https:')) ? 1 : 0,
      path : window.location.pathname,
      sid : '',
      query : function()
      {
        var a = window.location.href.split('#', 2);
        if (a.length != 2) return "";
        return a[1];
      },
      show : function()
      {
        var x = '';
        x += '[query] ' + mx.url.query() + ' ';
        for (var i in mx.url)
        {
          if (typeof mx.url[i] != 'function') x += '[' + i + '] ' + mx.url[i] + ' ';
        }
        return x;
      }
    }

    this.navigator =
    {
      name : window.navigator.appName,
      platform : window.navigator.platform,
      application : window.navigator.appCodeName,
      browser : browserDetect.browser,
      version : browserDetect.version,
      os : browserDetect.os,
      show : function()
      {
        var x = '';
        for (var i in mx.navigator)
        {
          if (typeof mx.navigator[i] != 'function') x += '[' + i + '] ' + mx.navigator[i] + ' ';
        }
        return x;
      }
    }

    this.screen =
    {
      width : function()
      {
        return window.screen.width;
      },
      height : function()
      {
        return window.screen.height;
      },
      depth : screen.colorDepth,
      colors : function()
      {
        if (screen.colorDepth < 1) return false;
        var x = 2;
        for (var i = 1, d = screen.colorDepth; i < d; i++) x *= 2;
        return x;
      },
      show : function()
      {
        var x = '';
        x += '[width] ' + mx.screen.width() + ' ';
        x += '[height] ' + mx.screen.height() + ' ';
        x += '[colors] ' + mx.screen.colors() + ' ';
        for (var i in mx.screen)
        {
          if (typeof mx.screen[i] != 'function') x += '[' + i + '] ' + mx.screen[i] + ' ';
        }
        return x;
      }
    }

    this.window =
    {
      width : function()
      {
        var x ;
        if (self.innerHeight)
        {
          x = self.innerWidth;
        }
        else if (document.documentElement && document.documentElement.clientHeight)
        {
          x = document.documentElement.clientWidth;
        }
        else if (document.body)
        {
          x = document.body.clientWidth;
        }
        return x;
      },
      height : function()
      {
        var x;
        if (self.innerHeight)
        {
          x = self.innerHeight;
        }
        else if (document.documentElement && document.documentElement.clientHeight)
        {
          x = document.documentElement.clientHeight;
        }
        else if (document.body)
        {
          x = document.body.clientHeight;
        }
        return x;
      },
      opener : window.opener,
      status : window.status,
      name : window.name,
      title : document.title,
      show : function()
      {
        var x = '';
        x += '[width] ' + mx.window.width() + ' ';
        x += '[height] ' + mx.window.height() + ' ';
        for (var i in mx.window)
        {
          if (typeof mx.window[i] != 'function') x += '[' + i + '] ' + mx.window[i] + ' ';
        }
        return x;
      }
    }

    this.data =
    {
      tick : {},
      ajax : []
    }


  /*
    +++ METHODS
  */


    // simply no operation :)
    this.nop = function()
    {
    }

    // !!! experimental !!!
    this.scriptFragment = '(?:<script.*?>)((\n|\r|.)*?)(?:<\/script>)';

    // !!! experimental !!!
    this.K = function(x)
    {
      return x;
    }

    // !!! experimental !!!
    this.stripScripts = function(x)
    {
      if (!x) return false;
      return x.replace(new RegExp(this.scriptFragment, 'img'), '');
    }

    // !!! experimental !!!
    this.update = function(element, html)
    {
      if (!element) return false;
      html = typeof html == 'undefined' ? '' : html.toString();
      $(element).innerHTML = this.stripScripts(html);
      return element;
    }

    // !!! experimental !!!
    this.getHeight = function(element)
    {
      return $(element).getDimensions().height;
    }

    // !!! experimental !!!
    this.getWidth = function(element)
    {
      return $(element).getDimensions().width;
    }

    // !!! experimental !!!
    this.getDimensions = function(element)
    {
      element = $(element);
      var display = $(element).display;
      if (display != 'none' && display != null) return {width: element.offsetWidth, height: element.offsetHeight};
      var els = element.style;
      var originalVisibility = els.visibility;
      var originalPosition = els.position;
      var originalDisplay = els.display;
      els.visibility = 'hidden';
      els.position = 'absolute';
      els.display = 'block';
      var originalWidth = element.clientWidth;
      var originalHeight = element.clientHeight;
      els.display = originalDisplay;
      els.position = originalPosition;
      els.visibility = originalVisibility;
      return {width: originalWidth, height: originalHeight};
    }

    // strip the string
    this.strip = function(x)
    {
      if (!x) return false;
      return x.replace(/^\s+/, '').replace(/\s+$/, '');
    }

    // strip tags off the string
    this.stripTags = function(x)
    {
      if (!x) return false;
      return x.replace(/<\/?[^>]+>/gi, '');
    }

    // truncate the string, length and truncation is optional
    this.truncate = function(x, length, truncation)
    {
      if (!x) return false;
      if (typeof x != 'string') return x;
      length = length || this.config.truncate;
      truncation = truncation === undefined ? '...' : truncation;
      return x.length > length ? x.slice(0, length - truncation.length) + truncation : x;
    }

    // escape the HTML content
    this.escapeHTML = function(x)
    {
      if (!x) return false;
      if (typeof x != 'string') return x;
      var div = document.createElement('div');
      var text = document.createTextNode(x);
      div.appendChild(text);
      return div.innerHTML;
    }

    // capitalize the string
    this.capitalize = function(x)
    {
      if (!x) return false;
      if (typeof x != 'string') return x;
      return x.charAt(0).toUpperCase() + x.substring(1).toLowerCase();
    }

    // convert the string to an array
    this.toArray = function(x) {
      if (!x) return false;
      if (typeof x != 'string') return x;
      return x.split('');
    }

    // get the size
    this.size = function(x) {
      if (!x) return 0;
      if (typeof x != 'string') return x;
      return this.toArray(x).length;
    }

    // check if the parameter is a valid email address
    this.isEmail = function(x)
    {
      if (!x) return false;
      if (typeof x != 'string') return x;
      var reg = /[A-Z0-9._%-]+@+[A-Z0-9.-]+\.[A-Z]{2,6}/;
      return reg.test(x.toUpperCase());
    }

    // check if the parameter is a valid domain address
    this.isDomain = function(x)
    {
      if (!x) return false;
      if (typeof x != 'string') return x;
      var reg = /[A-Z0-9.-]+\.[A-Z]{2,6}/;
      return reg.test(x.toUpperCase());
    }

    // check if the parameter is a valid IP address
    this.isIP = function(x)
    {
      if (!x) return false;
      if (typeof x != 'string') return x;
      var reg = /\b(?:\d{1,3}\.){3}\d{1,3}\b/;
      return reg.test(x);
    }

    // check if the parameter contains Unicode characters
    this.isUnicode = function(x)
    {
      var reg = /[\u0100-\uFFFD]/;
      return reg.test(x);
    }

    // clean the M$ Word extra markup
    this.cleanWord = function(x)
    {
      x = x.replace(new RegExp(String.fromCharCode(8216), 'g'), "'");
      x = x.replace(new RegExp(String.fromCharCode(8217), 'g'), "'");
      x = x.replace(new RegExp(String.fromCharCode(8218), 'g'), "'");
      x = x.replace(new RegExp(String.fromCharCode(8219), 'g'), "'");
      x = x.replace(new RegExp(String.fromCharCode(8220), 'g'), "\"");
      x = x.replace(new RegExp(String.fromCharCode(8221), 'g'), "\"");
      x = x.replace(new RegExp(String.fromCharCode(8222), 'g'), "\"");
      x = x.replace(new RegExp(String.fromCharCode(8223), 'g'), "\"");
      x = x.replace(/color="?[^" >]*"?/gi, '');
      x = x.replace(/([^-])color:[^;}"']+;?/gi, '$1');
      x = x.replace(/size="?[^" >]*"?/gi, '');
      x = x.replace(/font-size:[^;}"']+;?/gi, '');
      x = x.replace(/face="?[^" >]*"?/gi, '');
      x = x.replace(/font-family:[^;}"']+;?/gi, '');
      x = x.replace(/lang="?[^" >]*"?/gi, '');
      x = x.replace(/ class=[a-zA-Z]*/gi, '');
      x = x.replace(/ style="[^"]*"/gi, '');
      x = x.replace(/ face=[a-zA-Z]*/gi, '');
      x = x.replace(/ size=[a-zA-Z0-9]*/gi, '');
      x = x.replace(/ border=[a-zA-Z0-9]*/gi, '');
      x = x.replace(/ width=[a-zA-Z0-9]*/gi, '');
      x = x.replace(/ cellSpacing=[0-9]*/gi, '');
      x = x.replace(/ cellPadding=[0-9]*/gi, '');
      x = x.replace(/ align=[a-zA-Z]*/gi, '');
      x = x.replace(/ vAlign=[a-zA-Z]*/gi, '');
      x = x.replace(/<h([1-5]) [^>]*">/gi, '<h$1>');
      x = x.replace(/<font[^>]*>/gi, '');
      x = x.replace(/<\/font>/gi, '');
      x = x.replace(/<span[^>]*>/gi, '');
      x = x.replace(/<\/span>/gi, '');
      x = x.replace(/<p [^>]*>/gi, '<p>');
      x = x.replace(/<strong><\/strong>/gi, '');
      x = x.replace(/<p><\/p>/gi, '');
      x = x.replace(/<u><\/u>/gi, '');
      x = x.replace(/<i><\/i>/gi, '');
      x = x.replace(/<b><\/b>/gi, '');
      return x;
    }

    // get current scrolling offset X
    this.getScrollX = function()
    {
      var x;
      if (self.pageXOffset)
      {
        x = self.pageXOffset;
      }
      else if (document.documentElement && document.documentElement.scrollTop)
      {
        x = document.documentElement.scrollLeft;
      }
      else if (document.body)
      {
        x = document.body.scrollLeft;
      }
      return x;
    }

    // get current scrolling offset Y
    this.getScrollY = function()
    {
      var y;
      if (self.pageYOffset)
      {
        y = self.pageYOffset;
      }
      else if (document.documentElement && document.documentElement.scrollTop)
      {
        y = document.documentElement.scrollTop;
      }
      else if (document.body)
      {
        y = document.body.scrollTop;
      }
      return y;
    }

    // an alias for the document.write function
    this.write = function(x)
    {
      document.write(x);
    }

    // background ticking, data in the format "command1();...;commandX();|delay[ms]|"
    // id is optional
    // example: mx.doTick("nop()|250|")
    this.doTick = function(data, id)
    {
      if (!id) id = this.key();
      if (data)
      {
        if (data.substr(-1, 1) != '|') data += '|';
        if (!this.data.tick[id])
        {
          this.data.tick[id] = data;
        }
        else
        {
          this.data.tick[id] += data;
        }
      }
      var s = this.data.tick[id].split('|');
      if (s.length < 2) return false;
      var a = s.shift();
      var b = s.shift();
      this.data.tick[id] = s.join('|');
      try
      {
        eval(a);
      }
      catch(e)
      {
        mx.addLog("function doTick() crashed when executing:\r\n" + a + "\r\n" + e);
      }
      setTimeout('mx.doTick("", "' + id + '");', b);
      return true;
    }

    // removes tick data identified by the id (mandatory)
    this.removeTick = function(id)
    {
      if (!id) return false;
      this.data.tick[id] = '';
      return true;
    }

    // get object's id or set a random one if not defined
    // returns false if object not present
    this.getID = function(obj)
    {
      if (!obj) return false;
      if (!obj.id) obj.id = this.key();
      return obj.id;
    }

    // get random integer
    // parameter is optional and range defaults to 0 - 1
    this.rnd = function(x)
    {
      if (!x) return Number(Math.round(Math.random()));
      if (x < 2) x = 2;
      return Number(Math.round(Math.random() * (Math.round(x) - 1)) + 1);
    }

    // get current timestamp
    this.stamp = function()
    {
      var a = new Date();

      // a helper function
      function _stamp(x)
      {
        if (isNaN(x)) return x;
        if (x < 10) x = '0' + x;
        return x;
      }

      return a.getFullYear() + '/' + _stamp(a.getUTCMonth() + 1) + '/' + _stamp(a.getUTCDate())
        +  '-' + _stamp(a.getHours()) + ':' + _stamp(a.getMinutes()) + ':' + _stamp(a.getSeconds());
    }

    // add a string to the central log
    // filled string is mandatory
    this.addLog = function(str)
    {
      if (!str) return false;
      if (str == '') return false;
      this.logs.events[this.stamp()] = str;
      if (this.settings.debug) bug(str);
      return true;
    }

    // get current time in seconds
    this.seconds = function()
    {
      var a = new Date();
      return Math.round(a.valueOf() / 1000);
    }

    // get current time in miliseconds
    this.miliseconds = function()
    {
      var a = new Date();
      return a.valueOf();
    }

    // get a random password
    // type range 0 - 5, defaults to 2, 5 nearly impossible to remember
    this.getPassword = function(type)
    {
      if (!type) type = 2;
      var a1 =
      [
        'nA', 'Tou', 'SE', 'Bli', 'bE', 'cU', 'Ro', 'mE', 'da', 'sa', 'Dy', 'bi', 'EPi', 'LE', 'tI', 'kA', 'fRo', 'DA',
        'GE', 'Ro', 'ho', 'Ty', 'tO', 'cHu', 'Di', 'je', 'Ma', 'ko', 'pY', 'tO', 'ME', 'Mi', 'Ze', 'rA', 'nE', 'hLo', 'No',
        'mA', 'oPi', 'pA', 'gI', 'vE', 'lA', 'ra', 'Ri', 'rE', 'TU', 'Lu', 'MU', 'vi', 'zi', 'Go', 'WO', 'SOu', 'sTY', 'Lo', 'FO',
        'Ze', 'Eno', 'zU', 'fi', 'Go', 'Te', 'mY'
      ];
      var a2 =
      [
        0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9
      ];
      var a3 =
      [
        ',', '.', '@', '!', '_', '#', '$', '%', '&', '*', '^'
      ];
      switch(type)
      {
        default:
        case 0:
          a1.toLowerCase();
          a1.shuffle();
          return a1.shift() + a1.shift() + a1.shift();
        break;
        case 1:
          a1.toLowerCase();
          a1 = a1.concat(a2);
          a1.shuffle(1);
          return a1.shift() + a1.shift() + a1.shift();
        break;
        case 2:
          a1.toLowerCase();
          a1 = a1.concat(a2, a2);
          a1.shuffle(2);
          return a1.shift() + a1.shift() + a1.shift() + a1.shift();
        break;
        case 3:
          a1 = a1.concat(a2, a2);
          a1.shuffle(3);
          return a1.shift() + a1.shift() + a1.shift() + a1.shift();
        break;
        case 4:
          a1 = a1.concat(a2, a3, a2);
          a1.shuffle(4);
          return a1.shift() + a1.shift() + a1.shift() + a1.shift() + a1.shift();
        break;
        case 5:
          a1 = a1.concat(a2, a3, a2, a3);
          a1.shuffle(5);
          return a1.shift() + a1.shift() + a1.shift() + a1.shift() + a1.shift() + a1.shift();
        break;
      }
      return false;
    }

    // check the password strength 0 - 5 (0 = useless, 5 aka Manticore strength)
    this.passwordStrength = function(x)
    {
      var s = 0;
      if (x.length > 5) s++;
      if (x.length > 9) s++;
      var y = /[A-Z]/;
      if (y.test(x)) s++;
      var y = /[0-9]/;
      if (y.test(x)) s++;
      var y = /[,./';\[\]\\\- =`~!@#$%^&*()_+<>?:"|]/;
      if (y.test(x)) s += 2;
      var y = /[\x80-\xFF]/;
      if (y.test(x)) s++;
      var y = /[\u0100-\uFFFD]/;
      if (y.test(x)) s++;
      if (s > 5) s = 5;
      return s;
    }

    // return a random string
    // length is an optional parameter, defaults to 16
    this.key = function()
    {
      var a1 = 'abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ';
      var a2 = a1 + '0123456789';
      var b = [];
      var argv = arguments;
      var argc = arguments.length;
      var count = 'x';
      b.push(a1.substr(this.rnd(a1.length - 1), 1));
      if (argc > 0)
      {
        var count = parseInt(argv[0]);
      }
      if (isNaN(count)) count = 16;
      for (var i = 0; i < count; i++)
      {
        b.push(a2.substr(this.rnd(a2.length - 1), 1));
      }
      return b.join('');
    }

    // check the URL for a string parameter after #
    // parameter is case insensitive
    this.parseQuery = function(x)
    {
      if (!x) return false;
      var a = this.url.query();
      var reg = new RegExp(x + "=(\\w+)", 'gim');
      return a.replace(reg, "$1");
    }

    // get the object visibility status
    this.vis = function(id)
    {
      if (!$(id)) return false;
      if (!$$(id)) return false;
      if (!$$(id).visibility) $$(id).visibility = 'visible';
      return $$(id).visibility != 'none';
    }

    // set the object visibility status to VISIBLE
    this.visOn = function(id)
    {
      if (!$(id)) return false;
      if (!$$(id)) return false;
      $$(id).visibility = 'visible';
      return true;
    }

    // set the object visibility status to HIDDEN
    this.visOff = function(id)
    {
      if (!$(id)) return false;
      if (!$$(id)) return false;
      $$(id).visibility = 'hidden';
      return true;
    }

    // get the object display status
    this.dis = function(id)
    {
      if (!$(id)) return false;
      if (!$$(id)) return false;
      return $$(id).display != 'none';
    }

    // set the object display status to BLOCK
    this.disOn = function(id)
    {
      if (!$(id)) return false;
      if (!$$(id)) return false;
      $$(id).display = 'block';
      return true;
    }

    // set the object display status to NONE
    this.disOff = function(id)
    {
      if (!$(id)) return false;
      if (!$$(id)) return false;
      $$(id).display = 'none';
      return true;
    }

    // set the image source URL
    this.src = function(id, url)
    {
      if (!url) return false;
      if (!$(id)) return false;
      if (!$(id).src) return false;
      $(id).src = url;
      return true;
    }

    // set the location URL
    this.href = function(id, url)
    {
      if (!url) return false;
      if (!$(id)) return false;
      if (!$(id).href) return false;
      $(id).href = url;
      return true;
    }

    // set the HTML content
    this.setHTML = function(x, data)
    {
      if ($(x)) $(x).innerHTML = data;
    }

    // get the HTML content
    this.getHTML = function(x)
    {
      if ($(x)) return $(x).innerHTML;
      return false;
    }

    // prepend HTML content
    this.preHTML = function(id, data)
    {
      if ($(id))
      {
        this.setHTML(id, data + this.getHTML(id));
      }
    }

    // append HTML content
    this.postHTML = function(id, data)
    {
      if ($(id))
      {
        this.setHTML(id, this.getHTML(id) + data);
      }
    }

    // append HTML content
    this.appendHTML = function(id, data)
    {
      if ($(id))
      {
        this.setHTML(id, this.getHTML(id) + data);
      }
    }

    // convert decimal number to hexadecimal
    this.dec2hex = function(x)
    {
      if (!x) return false;
      var a = "0123456789ABCDEF";
      var b = a.substr(x & 15, 1);
      while (x > 15)
      {
        x >>= 4;
        b = a.substr(x & 15 ,1) + b;
      }
      return b;
    }

    // strip off CP1250 diacritics
    this.removeDiacritics = function(data)
    {
      var t1 = '؊ݎͼݎ';
      var t2 = 'acdeeinorstuuyzaacdeillnoorstuyzaouaeiooouuuACDEEINORSTUUYZAACDEILLNOORSTUYZAOUAEIOOOUUU';
      for (var i = 0, l = t1.length; i < l; i++)
      {
        var reg = new RegExp(t1.substr(i, 1), 'gm');
        data = data.replace(reg, t2.charAt(i));
      }
      return data;
    }

    // set the page title according to the original
    // the parameter is optional (sets the original title if not present)
    this.title = function(data)
    {
      if (!data)
      {
        document.title = this.window.title;
      }
      else
      {
        document.title = this.window.title + ': ' + data;
      }
      return document.title;
    }

    // set object color as a decimal RGB value
    this.color = function(id, R, G, B)
    {
      if (!$(id)) return false;
      if (!$$(id)) return false;
      if (arguments.length != 4) return false;
      try
      {
        $$(id).color = 'RGB(' + R + ',' + G + ',' + B + ')';
      }
      catch(e)
      {
        this.addLog("function color() crashed\r\n" + e);
        return false;
      }
      return true;
    }

    // set object background color as a decimal RGB value
    this.backgroundColor = function(id, R, G, B)
    {
      if (!$(id)) return false;
      if (!$$(id)) return false;
      if (arguments.length != 4) return false;
      try
      {
        $$(id).background = 'RGB(' + R + ',' + G + ',' + B + ')';
      }
      catch(e)
      {
        this.addLog("function backgroundColor() crashed\r\n" + e);
        return false;
      }
      return true;
    }

    // compute MD5 hash in pure JavaScript
    // (also makes first-run selfcheck of the virtual machine)
    this.md5 = function(x)
    {
      if (!this.settings.md5) if (!md5_vm_test())
      {
        if (mx.config.silent == 0) mx.alert(mx.locale[mx.config.locale].md5_vm_failed);
        return false;
      }
      else
      {
        this.settings.md5 = 1;
      }
      return hex_md5(x);
    }

    // compute SHA-1 hash in pure JavaScript
    // (also makes first-run selfcheck of the virtual machine)
    this.sha1 = function(x)
    {
      if (!this.settings.sha1) if (!sha1_vm_test())
      {
        if (mx.config.silent == 0) mx.alert(mx.locale[mx.config.locale].sha1_vm_failed);
        return false;
      }
      else
      {
        this.settings.sha1 = 1;
      }
      return hex_sha1(x);
    }

    // get BASE-64 encoded string
    // (removes any CP1250 diacritics, not working for Unicode characters)
    this.base64encode = function(str)
    {
      if (!str) return false;
      if (!str.length) return false;
      var base64EncodeChars =
      [
        'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X',
        'Y', 'Z', 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v',
        'w', 'x', 'y', 'z', '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '+', '/'
      ];
      str = this.removeDiacritics(str);
      if (this.isUnicode(str)) return false;
      var out, i, j, len;
      var c1, c2, c3;
      len = str.length;
      i = j = 0;
      out = [];
      while (i < len)
      {
        c1 = str.charCodeAt(i++) & 0xff;
        if (i == len)
        {
          out[j++] = base64EncodeChars[c1 >> 2];
          out[j++] = base64EncodeChars[(c1 & 0x3) << 4];
          out[j++] = '==';
          break;
        }
        c2 = str.charCodeAt(i++) & 0xff;
        if (i == len)
        {
          out[j++] = base64EncodeChars[c1 >> 2];
          out[j++] = base64EncodeChars[((c1 & 0x03) << 4) | ((c2 & 0xf0) >> 4)];
          out[j++] = base64EncodeChars[(c2 & 0x0f) << 2];
          out[j++] = '=';
          break;
        }
        c3 = str.charCodeAt(i++) & 0xff;
        out[j++] = base64EncodeChars[c1 >> 2];
        out[j++] = base64EncodeChars[((c1 & 0x03) << 4) | ((c2 & 0xf0) >> 4)];
        out[j++] = base64EncodeChars[((c2 & 0x0f) << 2) | ((c3 & 0xc0) >> 6)];
        out[j++] = base64EncodeChars[c3 & 0x3f];
      }
      return out.join('');
    }

    // get BASE-64 decoded string
    this.base64decode = function(str)
    {
      if (!str) return false;
      if (!str.length) return false;
      var base64DecodeChars =
      [
        -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1,
        -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 62, -1, -1, -1, 63, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, -1, -1, -1, -1, -1, -1,
        -1,  0,  1,  2,  3,  4,  5,  6,  7,  8,  9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, -1, -1, -1, -1, -1,
        -1, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, -1, -1, -1, -1, -1
      ];
      var c1, c2, c3, c4;
      var i, j, len, out;
      len = str.length;
      i = j = 0;
      out = [];
      while (i < len)
      {
        do
        {
          c1 = base64DecodeChars[str.charCodeAt(i++) & 0xff];
        } while (i < len && c1 == -1);
        if (c1 == -1) break;
        do
        {
          c2 = base64DecodeChars[str.charCodeAt(i++) & 0xff];
        } while (i < len && c2 == -1);
        if (c2 == -1) break;
        out[j++] = String.fromCharCode((c1 << 2) | ((c2 & 0x30) >> 4));
        do
        {
          c3 = str.charCodeAt(i++) & 0xff;
          if (c3 == 61) return out.join('');
          c3 = base64DecodeChars[c3];
        } while (i < len && c3 == -1);
        if (c3 == -1) break;
        out[j++] = String.fromCharCode(((c2 & 0x0f) << 4) | ((c3 & 0x3c) >> 2));
        do
        {
          c4 = str.charCodeAt(i++) & 0xff;
          if (c4 == 61) return out.join('');
          c4 = base64DecodeChars[c4];
        } while (i < len && c4 == -1);
        if (c4 == -1) break;
        out[j++] = String.fromCharCode(((c3 & 0x03) << 6) | c4);
      }
      return out.join('');
    }

    // set a document cookie
    // name and value are mandatory, optinal: expire[min.], path, domain, secure
    // (empty value removes that cookie!)
    this.setCookie = function(name, value)
    {
      if (!name) return false;
      if (!value) this.delCookie(name);
      var argv = arguments;
      var argc = arguments.length;
      var expires = (argc > 2) ? argv[2] : null;
      if (expires != null)
      {
        var exp = new Date();
        exp.setTime(exp.getTime() + (expires * 60 * 1000));
      }
      var path = (argc > 3) ? argv[3] : null;
      var domain = (argc > 4) ? argv[4] : null;
      var secure = (argc > 5) ? argv[5] : null;
      var x = name + '=' + escape(value) + ((expires == null) ? '' : ('; expires='
        + exp.toGMTString())) + ((path == null) ? '' : ('; path=' + path))
        + ((domain == null) ? '' : ('; domain=' + domain)) + ((secure == true) ? '; secure=' : '');
      document.cookie = x;
      return true;
    }

    // delete a document cookie
    this.delCookie = function(name)
    {
      if (!name) return false;
      if (!this.getCookie(name)) return false;
      var exp = new Date();
      exp.setTime(exp.getTime());
      this.setCookie(name, this.getCookie(name), -1);
      return true;
    }

    // delete a document cookie
    this.deleteCookie = function(name)
    {
      if (!name) return false;
      this.delCookie(name);
      return true;
    }

    // get a cookie value
    this.getCookie = function(name)
    {
      if (!name) return false;

      // a helper function
      function _getCookie(offset)
      {
        if (!offset) return false;
        var e = document.cookie.indexOf(';', offset);
        if (e == -1) e = document.cookie.length;
        return unescape(document.cookie.substring(offset, e));
      }

      if (!name) return false;
      var arg = name + '=';
      var alen = arg.length;
      var clen = document.cookie.length;
      var i = 0;
      while (i < clen)
      {
        var j = i + alen;
        if (document.cookie.substring(i, j) == arg) return _getCookie(j);
        i = document.cookie.indexOf(' ', i) + 1;
        if (i == 0) break;
      }
      return false;
    }

    // check if the AJAX is enabled
    this.isAjax = function()
    {
      return this.settings.ajax;
    }

    // modify the object HREF to cooperate with AJAX
    this.ajaxLink = function(obj) {
      if (this.settings.ajax)
      {
        if (!obj) return false;
        var a = /id=([0-9]*)/;
        var m = a.exec(obj.href);
        if (m) if (m.length)
        {
          obj.href = '#ajax-' + m[0];
          return true;
        }
        obj.href = '#blind-' + this.key();
        return true;
      }
      return false;
    }

    // reload the current window
    this.reloadURI = function()
    {
      location.href = location.href.replace(/#/, "");
    }

    // append an element to the DOM tree
    this.appendElement = function(el, html)
    {
      if (!el) return false;
      if (!document.getElementsByTagName('body')[0])
      { // not possible - try to call it later!
        return false;
      }
      var e = document.createElement(el);
      e.id = this.key(16) + this.miliseconds();
      if (html) e.innerHTML = html;
      e.style.display = 'none';
      try
      {
        document.getElementsByTagName('body')[0].appendChild(e);
      }
      catch(e)
      {
        this.addLog("function appendElement() crashed adding:\r\n" + html + "\r\n" + e);
        return false;
      }
      return e.id;
    }

    // remove an element from the DOM tree
    this.removeElement = function(id)
    {
      if (!id) return false;
      if (!$(id)) id = this.getID(id);
      try {
        $$(id).display = 'none';
        $$(id).opacity = 0;
        // Opera is sometimes crappy, we have to do it this stupid way
        setTimeout("try{$('" + id + "').parentNode.removeChild($('" + id + "'))} catch(e) {}", 1);
        return true;
      }
      catch(e)
      {
        this.addLog("function removeElement() crashed removing:\r\n" + el + "\r\n" + e);
        return false;
      }
    }

    // load an external javascript
    this.loadScript = function(url)
    {
      if (!url) return false;
      var e = document.createElement('script');
      e.src = url;
      e.type = 'text/javascript';
      e.language = 'JavaScript';
      if (!document.getElementsByTagName('head')[0])
      { // not possible - try to call it later!
        return false;
      }
      try
      {
        document.getElementsByTagName('head')[0].appendChild(e);
      }
      catch(e)
      {
        this.addLog("function loadScript() crashed loading:\r\n" + url + "\r\n" + e);
        return false;
      }
      return true;
    }

    // display the floating debug window
    this.debug = function()
    {
      if (!this.settings.md5) var x = this.md5('test');
      if (!this.settings.sha1) var x = this.sha1('test');
      var e = this.appendElement('debug', '');
      if (!e) return false;
      if (mx.settings.ie)
      {
        $$(e).position = 'absolute';
      }
      else
      {
        $$(e).position = 'fixed';
      }
      $$(e).top = -100;
      $$(e).left = 0;
      $$(e).zIndex = '10000';
      $$(e).border = '1px solid #3366cc';
      $$(e).backgroundColor = '#c3d9ff';
      $$(e).cursor = 'default';
      $$(e).display = 'block';
      var l = this.key();
      this.setHTML(e, '<span style="font-size: 11px; font-family: arial; font-weight: bold; background-color: #3366cc; color: white;">&nbsp;DEBUG&nbsp;</span><div style="padding: 5px; color: black;"><b>SETTINGS</b>: ' + mx.settings.show() + '<br><b>NAVIGATOR</b>: ' + mx.navigator.show() + '<br><b>SCREEN</b>: ' + mx.screen.show() + '<br><b>WINDOW</b>: ' + mx.window.show() + '<br><b>URL</b>: ' + mx.url.show() + '<br><b>LOGS</b>: ' + mx.logs.show() + '<div style="margin: 5px;" align=center><button id=' + l + ' style="cursor: pointer; font-size: 11px; font-family: arial; font-weight: bold; border: 2px solid white; color: white; background-color: #3366cc;" onclick="mx.removeElement(\'' + e + '\');">OK</button></div>');
      var s = [];
      for (var i = -90; i <= 0; i += 10) s.push('$$("' + e + '").top = "' + i + 'px"|1|');
      mx.doTick(s.join(''));
      try
      {
        $(l).focus();
      }
      catch(e) {}
      return true;
    }

    // display the floating IFRAME alert box; html is mandatory
    this.alert = function(html)
    {
      if (!html)
      {
        if (this.logs.alert_stack.length)
        {
          eval(this.logs.alert_stack.shift());
        }
        return true;
      }
      if (this.settings.framed)
      {
        try
        {
          parent.mx.alert(html);
          return true;
        }
        catch(e) {}
        return true;
      }
      if ((this.logs.alert_id) || (!this.settings.loaded))
      {
        this.logs.alert_stack.push('mx.alert("' + html.replace(/\"/g, "'") + '")');
        return false;
      }
      if (!document.getElementsByTagName('body')[0])
      {
        setTimeout('mx.alert("' + html + '");', 1000);
        return true;
      }
      if(this.settings.ie) {
        var e = this.appendElement('<iframe name=alertbox>', '');
      }
      else
      {
        var e = this.appendElement('iframe', '');
      }
      if (!e) return false;
      $$(e).position = 'fixed';
      if (this.settings.ie) $$(e).position = 'absolute';
      if (this.settings.ie)
      {
        $$(e).top = ((this.window.height() - 220) / 2) + this.getScrollY() + 'px';
        $$(e).left = ((this.window.width() - 400) / 2) + this.getScrollX() + 'px';
      }
      else
      {
        $$(e).top = ((this.window.height() - 220) / 2) + 'px';
        $$(e).left = ((this.window.width() - 400) / 2) + 'px';
      }
      this.logs.alert_id = e;
      this.logs.alert_count++;
      $(e).frameBorder = 0;
      $(e).name = e;
      $$(e).height = '220px';
      $$(e).width = '400px';
      $$(e).zIndex = '10000';
      $$(e).border = '1px solid #3366cc';
      $$(e).backgroundColor = '#c3d9ff';
      $$(e).display = 'block';
      if(this.settings.opera)
      {
        $(e).document.write("<html><head><title></title></head><body onclick='parent.mx.removeAlert();' id=body bgcolor=#c3d9ff><span style='position: absolute; top: 0; left: 0; font-size: 11px; font-family: arial; font-weight: bold; background-color: #3366cc; color: white;'>&nbsp;ALERT&nbsp;#&nbsp;" + this.logs.alert_count + '&nbsp;</span><br>'  + mx.stamp() + '<br><br><b>' + html + '</b><br>');
      }
      else
      {
        $(e).src = 'javascript: document.write("<html><head><title></title></head><body onclick=\'parent.mx.removeAlert();\' id=body bgcolor=#c3d9ff><span style=\'position: absolute; top: 0; left: 0; font-size: 11px; font-family: arial; font-weight: bold; background-color: #3366cc; color: white;\'>&nbsp;ALERT&nbsp;#&nbsp;' + this.logs.alert_count + '&nbsp;</span><br>'  + mx.stamp() + '<br><br><b>' + html + '</b><br>")';
      }
      return true;
    }

    // remove the IFRAME alert box
    this.removeAlert = function()
    {
      if (this.logs.alert_id)
      {
        this.removeElement(this.logs.alert_id);
        this.logs.alert_id = '';
        setTimeout("mx.alert()", 10);
      }
    }

    // display the Manticore floating logo; 'force' parameter is optional
    this.showManticore = function(force)
    {
      if (!force)
      {
        if (this.settings.framed) return false;
        if (this.url.ssl) return false;
        if (this.getCookie('manticore-logo-displayed') == 1) return false;
      }
      this.setCookie('manticore-logo-displayed', 1, 3600);
      var e = this.appendElement('img', '');
      if (this.settings.ie)
      {
        $$(e).position = 'absolute';
      }
      else
      {
        $$(e).position = 'fixed';
      }
      $$(e).bottom = '10px';
      $$(e).cursor = 'pointer';
      $$(e).left = '-100px';
      $$(e).zIndex = 10000;
      $(e).src = this.config.manticore_picture;
      $(e).onerror = function()
      {
        mx.removeElement("' + e + '");
      }
      $(e).onclick = function()
      {
        top.location.href = 'http://mxd.biz';
      }
      $(e).onload = function()
      {
        var a = 0;
        var s = [];
        s.push('mx.nop()|2000|');
        for (var i = -90; i <= 10; i += 5)
        {
          s.push('$$("' + e + '").left=' + i + ';|1|');
          if (!a) s.push('$$("' + e + '").display="block"|1|');
          a = 1;
        }
        s.push('mx.nop()|10000|');
        for (var i = 10; i >= 0; i--) s.push('$$("' + e + '").opacity=' + (i / 10) + ';|2|');
        s.push('mx.removeElement("' + e + '");|1');
        mx.doTick(s.join(''));
      }
      $$(e).display = 'block';
      if (mx.settings.ie) setTimeout('$("' + e + '").onload();', 250);
      return true;
    }

    // display the floating 'loading' notice
    this.showLoading = function(force)
    {
      if (this.settings.loading.length) return false;
      var e = this.appendElement('div', this.rounded('<div align=center style="padding: 2px; margin: 0; color: white; font-family: arial; font-weight: bold; font-size: 11px;">' + this.locale[this.config.locale].loading + '</div>', '#3366cc', 80));
      $$(e).border = '';
      $$(e).top = '5px';
      $$(e).right = '15px';
      $$(e).zIndex = 10000;
      $$(e).position = 'fixed';
      if (this.settings.ie) $$(e).position = 'absolute';
      mx.settings.loading = e;
      if (!force)
      {
        setTimeout('$$("' + e + '").display="block";', 5000);
      }
      else
      {
        setTimeout('$$("' + e + '").display="block";', 1);
      }
      return true;
    }

    // remove the floating 'loading' notice
    this.removeLoading = function()
    {
      this.removeElement(this.settings.loading);
      this.settings.loading = '';
    }

    // display the picture; 'url' is mandatory, text is optional
    this.showPicture = function(url, text)
    {
      if (!url) return false;
      if (!text) text = '';
      if (this.settings.framed)
      {
        try
        {
          parent.mx.showPicture(url, text);
          return true;
        }
        catch(e) {}
      }
      text = text.replace(/"/g, '');
      url = url.replace(/ /g, '%20');
      var e = this.appendElement('span', '');
      $$(e).position = 'absolute';
      $$(e).width = '150';
      $$(e).height = '50';
      $$(e).zIndex = '10000';
      $$(e).border = '0';
      $$(e).display = 'block';
      if (!this.settings.ie)
      {
        $$(e).background = 'url(' + this.config.loading_picture + ') top left no-repeat';
      }
      else
      {
        $$(e).background = 'url(' + this.config.loading_picture + ') middle center no-repeat';
      }
      $$(e).top = ((this.window.height() - 50) / 2) + this.getScrollY() + 'px';
      $$(e).left = ((this.window.width() - 150) / 2) + this.getScrollX() + 'px';
      $$(e).textAlign = 'center';
      var e2 = this.appendElement('span', '');
      $$(e2).position = 'absolute';
      $$(e2).width = '150';
      $$(e2).height = '50';
      $$(e2).zIndex = '10000';
      $$(e2).border = '0';
      $$(e2).display = 'block';
      $$(e2).top = ((this.window.height() - 50) / 2) + this.getScrollY() + 'px';
      $$(e2).left = ((this.window.width() - 150) / 2) + this.getScrollX() + 'px';
      $$(e2).textAlign = 'center';
      var k = this.key();
      this.setHTML(e2, '<img id=' + k + ' onload="mx.removeElement(\'' + e + '\'); mx.removeElement(mx.logs.picture_id); mx.logs.picture_id = \'' + e2 + '\'; mx._onloadPicture(this); mx.logs.pictures_showed++;" title="' + this.locale[this.config.locale].close_picture + '" style="z-index: 1000000; display: block; visibility: hidden; border: 0;cursor: pointer;" onerror="mx.removeElement(\'' + e + '\'); mx.removeElement(\'' + e2 + '\'); mx.logs.pictures_failed++;" onclick="mx.removeElement(\'' + e2 + '\');" alt="' + text + '" src="' + url + '"/>');
      return true;
    }

    // picture display helper
    this._onloadPicture = function(obj)
    {
      var x = ((mx.window.width() - obj.width) / 2)  + mx.getScrollX();
      var y = ((mx.window.height() - obj.height) / 2)  + mx.getScrollY();
      obj.style.opacity = 0;
      if (!mx.settings.ie) obj.parentNode.style.background = 'transparent';
      if (x < 20) x = 20;
      if (y < 20) y = 20;
      obj.parentNode.style.left = x + 'px';
      obj.parentNode.style.top = y + 'px';
      obj.style.zIndex = 100;
      if (!this.config.picture_show_opacity)
      {
        $$(obj.id).opacity = 1;
        $$(obj.id).filter = 'alpha(opacity=100)';
        $$(obj.id).visibility = 'visible';
        mx.disOn(obj.id);
        return true;
      }
      else
      {
        setTimeout("mx._showOpacity('" + obj.id + "', 0)", 100);
        return true;
      }
    }

    // picture display helper
    this._showOpacity = function(id, val)
    {
      $$(id).filter = 'alpha(opacity=' + (val * 100) + ')';
      if (val < 1)
      {
        val += 0.2;
        setTimeout("mx._showOpacity('" + id + "', " + val + ")", 1);
      }
      $$(id).opacity = val;
      $$(id).visibility = 'visible';
      mx.disOn(id);
      return true;
    }

    // display a rounded box; 'width' is optional (defaults to 250px)
    this.rounded = function(text, color, width)
    {
      if (!text) return false;
      if (!color) color = '#CCCCFF';
      if (!width) width = 250;
      var s = [];
      var size = 2;
      s.push('<div style="padding:1px;">');
      for (var i = size; i > 0; i--) s.push('<div style="padding:0px;height:1px;overflow:hidden;margin-left:' + i + 'px;margin-right:' + i + 'px;background-color:' + color + ';width:' + (width - (i * 2)) + 'px;"></div>');
      s.push('<div style="padding:0px;background-color:' + color + ';width:' + width + 'px"><div style="padding:5px;">' + text + '</div></div>');
      for (var i = 1; i <= size; i++) s.push('<div style="padding:0px;height:1px;overflow:hidden;margin-left:' + i + 'px;margin-right:' + i + 'px;background-color:' + color + ';width:' + (width   - (i * 2)) + 'px;"></div>');
      s.push('</div>');
      return s.join('');
    }

    // get elements by selector in an array
    this.getElementsBySelector = function(selector)
    {
      if (!selector) return [];
      var i;
      var s = [];
      var selid = '';
      var selclass = '';
      var tag = selector;
      var objlist = [];
      if (selector.indexOf(' ') > 0)
      {
        s = selector.split(' ');
        var fs = s[0].split('#');
        if (fs.length == 1) return objlist;
        return(document.getElementById(fs[1]).getElementsByTagName(s[1]));
      }
      if (selector.indexOf('#') > 0)
      {
        s = selector.split('#');
        tag = s[0];
        selid = s[1];
      }
      if (selid != '')
      {
        objlist.push(document.getElementById(selid));
        return objlist;
      }
      if (selector.indexOf('.') > 0)
      {
        s = selector.split('.');
        tag = s[0];
        selclass = s[1];
      }
      var v = document.getElementsByTagName(tag);
      if (selclass == '') return(v);
      for (var i = 0, l = v.length; i < l; i++)
      {
        if (v[i].className == selclass)
        {
          objlist.push(v[i]);
        }
      }
      return(objlist);
    }

    // AJAX GET - url is mandatory, action is optional, nocache is optional (1 prevents caching)
    // action uses two special characters: ` instead of ' and $ instead of the AJAX operation result
    // example: mx.ajaxGet('url.php', 'mx.setHTML(`results`, $)', 1)
    this.ajaxGet = function(url, action, nocache)
    {
      if (!this.settings.ajax) return false;
      var uid = this.key();
      if (!url) url = this.url.href;
      if (!action) action = '';
      if (!nocache) nocache = 0;
      if (this.config.ajax_cache_enabled != 1) nocache = 1;
      action = action.replace(/`/g, "'");
      if (nocache == 0)
      {
        if (this._cacheAjax(url, action) == true) return true;
      }
      var i = {};
      i.uid = uid;
      i.url = url;
      i.action = action;
      i.stamp = this.stamp();
      i.time = this.seconds();
      i.time_start = this.miliseconds();
      i.time_end = 0;
      i.nocache = nocache;
      i.valid = 0;
      i.size = 0;
      mx.data.ajax.push(i);
      delete i;
      this.logs.ajax_call++;
      this.logs.ajax_get++;
      ajax.get(
      {
        'url' : url,
        'UID' : uid,
        'timeout' : mx.config.ajax_timeout,
        'onSuccess' : function(req)
        {
          try
          {
            mx._execAjax(req);
          }
          catch(e)
          {
            mx.addLog("AJAX crashed in function 'ajaxGet'. [" + mx.stamp() + "]\r\n" + e);
          }
          return true;
        },
        'onTimeout' : function(req)
        {
          mx.addLog('AJAX GET request timeout. [' + req.url + ']');
          if ((mx.config.silent == 1) || (mx.config.ajax_retry_send == 0))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          if (!confirm('AJAX GET request timed out. Resend?'))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          mx._ajaxGetResend(req.url);
          return true;
        },
        'onError' : function(req)
        {
          mx.addLog('AJAX GET request error. [' + req.url + ']');
          if ((mx.config.silent == 1) || (mx.config.ajax_retry_send == 0))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          if (!confirm('AJAX GET request failed. Resend?'))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          mx._ajaxGetResend(req.url);
          return true;
        }
      });
      return true;
    }

    // AJAX POST - all parameters are optional
    // action uses two special characters: ` instead of ' and $ instead of the AJAX operation result
    // example: mx.ajaxPost('url.php', 'mx.setHTML(`results`, $)', form)
    this.ajaxPost = function(url, action, form)
    {
      if (!this.settings.ajax) return false;
      if (!url) url = this.url.href;
      if (!action) action = '';
      var uid = this.key();
      action = action.replace(/`/g, "'");
      var i = {};
      i.uid = uid;
      i.url = url;
      i.action = action;
      i.stamp = this.stamp();
      i.time = this.seconds();
      i.time_start = this.miliseconds();
      i.time_end = 0;
      i.nocache = 1;
      i.valid = 0;
      i.size = 0;
      mx.data.ajax.push(i);
      delete i;
      this.logs.ajax_call++;
      this.logs.ajax_post++;
      ajax.post(
      {
        'url' : url,
        'UID' : uid,
        'timeout' : mx.config.ajax_timeout,
        'queryString' : ajax.serializeForm(form),
        'onSuccess' : function(req)
        {
          try
          {
            mx._execAjax(req);
          }
          catch(e)
          {
            mx.addLog("AJAX crashed in function 'ajaxPost'. [" + mx.stamp() + "]\r\n" + e);
          }
          return true;
        },
        'onTimeout' : function(req)
        {
          mx.addLog('AJAX POST request timeout.');
          if ((mx.config.silent == 1) || (mx.config.ajax_retry_send == 0))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          if (!confirm('AJAX POST request timed out. Resend?'))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          mx._ajaxPostResend(req);
          return true;
        },
        'onError' : function(req)
        {
          mx.addLog('AJAX POST request error.');
          if ((mx.config.silent == 1) || (mx.config.ajax_retry_send == 0))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          if (!confirm('AJAX POST request failed. Resend?'))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          mx._ajaxPostResend(req);
          return true;
        }
      });
      return true;
    }

    // AJAX helper
    this._ajaxGetResend = function(url)
    {
      if (!url) return false;
      this.logs.ajax_call++;
      this.logs.ajax_resend++;
      url = url + '&AJAXRESEND=1';
      url = url.replace(/AJAXSEQ=(\w+)/g, '');
      url = url.replace(/PHPSESSID=(\w+)/g, '');
      url = url.replace(/&&/g, '&');
      url = url.replace(/\?&/, '?');
      ajax.get(
      {
        'url' : url,
        'timeout' : mx.config.ajax_timeout,
        'onTimeout' : function(req)
        {
          mx.addLog('AJAX GET request timeout. [' + req.url + ']');
          if ((mx.config.silent == 1) || (mx.config.ajax_retry_send == 0))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          if (!confirm('AJAX request timed out. Resend?'))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          mx._ajaxGetResend(req.url);
          return true;
        },
        'onError' : function(req)
        {
          mx.addLog('AJAX GET request error. [' + req.url + ']');
          if ((mx.config.silent == 1) || (mx.config.ajax_retry_send == 0))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          if (!confirm('AJAX request failed. Resend?'))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          mx._ajaxGetResend(req.url);
          return true;
        }
      });
      return true;
    }

    // AJAX helper
    this._ajaxPostResend = function(req)
    {
      if (!req) return false;
      this.logs.ajax_call++;
      this.logs.ajax_resend++;
      req.queryString = req.queryString + '&AJAXRESEND=1';
      req.queryString = req.queryString.replace(/PHPSESSID=(\w+)/g, '');
      req.queryString = req.queryString.replace(/&&/g, '&');
      ajax.post(
      {
        'url' : req.url,
        'queryString' : req.queryString,
        'timeout' : mx.config.ajax_timeout,
        'onTimeout' : function(req)
        {
          mx.addLog('AJAX POST request timeout.');
          if ((mx.config.silent == 1) || (mx.config.ajax_retry_send == 0))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          if (!confirm('AJAX POST request timed out. Resend?'))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          mx._ajaxPostResend(req);
          return true;
        },
        'onError' : function(req)
        {
          mx.addLog('AJAX POST request error.');
          if ((mx.config.silent == 1) || (mx.config.ajax_retry_send == 0))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          if (!confirm('AJAX request failed. Resend?'))
          {
            mx.logs.ajax_fail++;
            if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
            return false;
          }
          mx._ajaxPostResend(req);
          return true;
        }
      });
      return true;
    }

    // AJAX helper
    this._execAjax = function(req)
    {
      if (!req) return false;
      var reg = /UID=(\w+)/;
      if (!reg.test(req.responseText)) return false;
      var x = reg.exec(req.responseText);
      if (!x.length) return false;
      if (!x[1]) return false;
      var el = mx.data.ajax;
      for (var i in el)
      {
        if(typeof el[i] != 'function') if (el[i].uid == x[1])
        {
          if(this.settings.debug) bug(el[i]);
          el[i].data = req.responseText.replace(/UID=(\w+)/, '');
          el[i].valid = 1;
          el[i].time_end = mx.miliseconds();
          var action = el[i].action.replace(/\$/, 'mx.data.ajax[' + i + '].data');
          if ((el[i].time_end - el[i].time_start) != 0)
          {
            mx.logs.ajax_speed = Math.round(10 * (mx.logs.ajax_speed + (Math.round(10000 * action.length / (el[i].time_end - el[i].time_start)) / 10) / 2)) / 10;
          }
          el[i].size = action.length;
          if (action.length == 0)
          {
            mx.addLog('AJAX action processed (no data!): ' + el[i].action + ' [' + el[i].uid + ']');
            return true;
          }
          mx.addLog('AJAX action processed: ' + el[i].action + ' [' + el[i].uid + ']');
          try
          {
            eval(action);
          }
          catch(e)
          {
            mx.addLog("AJAX crashed in function '_execAjax'. [" + el[i].uid + "]\r\n" + e);
          }
          // an embedded Javascript execution follows
          if (mx.config.ajax_parse_javascript)
          {
            var r = new RegExp('(?:<script [a-zA-Z ="\'/]*>)([^\x00]*)(?:<\/script>)', 'i');
            var z = r.exec(el[i].data);
            if (z) if (z.length == 2)
            {
              var action = z[1];
              action = action.replace(/<script [a-zA-Z ="\'/]*>/, '');
              action = action.replace(/<\/script>/, '');
              mx.addLog('AJAX JS eval(): ' + action);
              try
              {
                eval(action);
              }
              catch(e)
              {
                mx.addLog('AJAX JS crashed when trying to eval(): ' + z[1] + "\r\n" + e);
              }
            }
          }
          return true;
        }
      }
      return false;
    }

    // AJAX helper
    this._cacheAjax = function(url, action)
    {
      if (!url) return false;
      if (!action) return false;
      var el = mx.data.ajax;
      var j = -1;
      for (var i = 0, l = el.length; i < l; i++) if ((el[i].nocache == 1)) delete el[i];
      for (var i = 0, l = el.length; i < l; i++) if ((el[i].url == url) && (el[i].action == action) && (el[i].valid == 1))
      {
        if ((el[i].time + mx.config.ajax_cache_timeout) < mx.seconds())
        {
          delete el[i];
          continue;
        }
        if (j >= 0) delete el[i];
        j = i;
      }
      for (var i = 0, l = el.length; i < l; i++) if ((el[i].url == url) && (el[i].action == action) && ((el[i].time + mx.config.ajax_cache_timeout) >= mx.seconds()) && (el[i].valid == 1))
      {
        action = el[i].action.replace(/\$/, 'mx.data.ajax[' + i + '].data');
        mx.addLog('AJAX processed from cache: ' + el[i].action + ' [' + el[i].uid + ']');
        try
        {
          eval(action);
        }
        catch(e)
        {
          mx.addLog("AJAX crashed in function '_cacheAjax'. [" + el[i].uid + "]\r\n" + e);
        }
        if (mx.config.ajax_parse_javascript)
        {
          var r = new RegExp('(?:<script [a-zA-Z ="\'/]*>)([^\x00]*)(?:<\/script>)', 'i');
          var z = r.exec(el[i].data);
          if (z) if (z.length == 2)
          {
            mx.addLog('AJAX JS eval(): ' + z[1]);
            try
            {
              eval(z[1]);
            }
            catch(e)
            {
              mx.addLog('AJAX JS crashed when trying to eval(): ' + z[1] + "\r\n" + e);
            }
          }
        }
        return true;
      }
      return false;
    }

    // dirty hack to hide any relative pictures in MSIE6 if framed
    this.fixIE = function()
    {
      if (this.settings.ie7) return false;
      if (!this.settings.ie) return false;
      if (this.config.onload_fix_msie == 1) if (this.settings.ie == 1) if (this.settings.framed == 1) {
        var a = document.getElementsByTagName('img');
        var c = 0;
        for (var i = 0, l = a.length; i < l; i++)
        {
          if (a[i].style.position == 'relative')
          {
            a[i].style.visibility = 'hidden';
            c++;
          }
        }
        this.addLog("Fixed relative pictures: " + c + "x");
      }
      return true;
    }

    // push a function to the stack for an execution after current page loads
    this.registerOnload = function(x)
    {
      if (x) this.settings.onload.push(x);
    }

    // an 'onload' event helper
    this._onload = function()
    {
      if (document.getElementsByTagName('body')[0])
      {
        try
        {
          mx.url.sid = eval(mx.config.session_variable);
        }
        catch(e)
        {
          // no session?
          if (this.settings.debug) bug('Session is not set.');
        }
        // fix relative framed pictures in MSIE6
        setTimeout("mx.settings.loaded = 1; mx.fixIE();", 1);
        // execute onload array
        setTimeout("eval(mx.settings.onload.join(';'))", 1);
        if (mx.config.manticore_picture_enabled)
        {
          // display Manticore logo
          setTimeout("mx.showManticore();", 1);
        }
      }
      else
      {
        setTimeout("mx._onload();", 250);
      }
    }

    // add listener handler
    this.addListener = function(obj, event, handler, data)
    {
      if (!obj) return false;
      if (!event) return false;
      if (!handler) return false;
      if (window.addEventListener)
      {
        obj.addEventListener(event, handler, false);
        if (data) obj.data = data;
      }
      else
      {
        obj.attachEvent('on' + event, handler);
        if (data) obj.data = data;
      }
      return true;
    }

    // remove listener handler
    this.removeListener = function(obj, event, handler)
    {
      if (!obj) return false;
      if (!event) return false;
      if (!handler) return false;
      if (window.removeEventListener)
      {
        obj.removeEventListener(event, handler, false);
      }
      else
      {
        obj.detachEvent('on' + event, handler);
      }
      return true;
    }

    // get current page selection range
    this.getSelection = function()
    {
      var t = '';
      if (window.getSelection)
      {
        t = window.getSelection();
      }
      else if (document.getSelection)
      {
        t = document.getSelection();
      }
      else if (document.selection)
      {
        t = document.selection.createRange().text;
      }
      return t;
    }

    // clear current page selection range
    this.clearSelection = function()
    {
      try
      {
        if (document.selection)
        {
          document.selection.empty();
        }
        else if (window.getSelection)
        {
          window.getSelection().removeAllRanges();
        }
      }
      catch(e)
      {
        if(this.settings.debug) bug('clearSelection failed!');
      }
    }


  /*
    +++ DATE PICKER
  */


    this.picker_id = '';
    this.picker_action = '';
    this.picker_separator = '/';
    this.picker_day = ['Ne', 'Po', 't', 'St', 't', 'P', 'So'];
    this.picker_month = ['Leden', 'nor', 'Bezen', 'Duben', 'Kvten', 'erven', 'ervenec', 'Srpen', 'Z', 'jen', 'Listopad', 'Prosinec'];
    this.picker_class = 'mxdp';

    // display a date picker connected to the 'id', action is optional (same format like for AJAX operations)
    this.picker_show = function(id, action)
    {
      if ($(id))
      {
        var obj = $(id);
      }
      else
      {
        var obj = id;
      }
      if (!obj) return false;
      if (!obj.id) obj.id = mx.key();
      if (action)
      {
        this.picker_action = action.replace(/`/g, "'");
      }
      else
      {
        this.picker_action = '';
      }
      var x = obj.offsetLeft;
      var y = obj.offsetTop + obj.offsetHeight;
      var parent = obj;
      while (parent.offsetParent)
      {
        parent = parent.offsetParent;
        x += parent.offsetLeft;
        y += parent.offsetTop ;
      }
      this.picker_draw(obj, x, y);
      return true;
    }

    // date picker helper
    this.picker_draw = function(obj, x, y)
    {
      var dt = this.picker_get_fd(obj.value);
      if (!$(this.picker_id))
      {
        this.picker_id = mx.key();
        var n = document.createElement("div");
        n.setAttribute("id", this.picker_id);
        n.setAttribute("class", this.picker_class + "div");
        n.setAttribute("style", "visibility: hidden;");
        document.body.appendChild(n);
      }
      var p = $$(this.picker_id);
      p.position = "absolute";
      p.left = x + "px";
      p.top = y + "px";
      p.visibility = (p.visibility == "visible" ? "hidden" : "visible");
      p.display = (p.display == "block" ? "none" : "block");
      p.zIndex = 10000;
      this.picker_refresh(obj.id, dt.getFullYear(), dt.getMonth(), dt.getDate());
    }

    // date picker helper
    this.picker_refresh = function(id, year, month, day)
    {
      var thisDay = new Date();
      if ((month >= 0) && (year > 0))
      {
        thisDay = new Date(year, month, 1);
      }
      else
      {
        day = thisDay.getDate();
        thisDay.setDate(1);
      }
      var crlf = "\r\n";
      var TABLE = "<table cols=7 class='" + this.picker_class + "table'>" + crlf;
      var xTABLE = "</table>" + crlf;
      var TR = "<tr class='" + this.picker_class + "tr'>";
      var TR_title = "<tr class='" + this.picker_class + "titletr'>";
      var TR_days = "<tr class='" + this.picker_class + "daytr'>";
      var TR_todaybutton = "<tr class='" + this.picker_class + "todaybuttontr'>";
      var xTR = "</tr>" + crlf;
      var TD = "<td class='" + this.picker_class + "td' onMouseOut='this.className=\"" + this.picker_class + "td\";' onMouseOver=' this.className=\"" + this.picker_class + "tdhover\";' ";
      var TD_title = "<td colspan=5 class='" + this.picker_class + "titletd'>";
      var TD_buttons = "<td class='" + this.picker_class + "buttontd'>";
      var TD_todaybutton = "<td colspan=7 class='" + this.picker_class + "todaybuttontd'>";
      var TD_days = "<td class='" + this.picker_class + "daytd'>";
      var TD_selected = "<td class='" + this.picker_class + "dayhighlighttd' onMouseOut='this.className=\"" + this.picker_class + "dayhighlighttd\";' onMouseOver='this.className=\"" + this.picker_class + "tdhover\";' ";
      var xTD = "</td>" + crlf;
      var DIV_title = "<div class='" + this.picker_class + "titletext'>";
      var DIV_selected = "<div class='" + this.picker_class + "dayhighlight'>";
      var xDIV = "</div>";
      var h = TABLE;
      h += TR_title;
      h += TD_buttons + this.picker_button(id, thisDay, -1, "&lt;") + xTD;
      h += TD_title + DIV_title + this.picker_month[thisDay.getMonth()] + " " + thisDay.getFullYear() + xDIV + xTD;
      h += TD_buttons + this.picker_button(id, thisDay, 1, "&gt;") + xTD;
      h += xTR;
      h += TR_days;
      for (var i = 0; i < this.picker_day.length; i++) h += TD_days + this.picker_day[i] + xTD;
      h += xTR;
      h += TR;
      for (var i = 0, l = thisDay.getDay(); i < l; i++) h += TD + "&nbsp;" + xTD;
      do
      {
        var dayNum = thisDay.getDate();
        var TD_onclick = " onclick=\"mx.picker_update_obj('" + id + "', '" + this.picker_get_ds(thisDay) + "');\">";
        if (dayNum == day)
        {
          h += TD_selected + TD_onclick + DIV_selected + dayNum + xDIV + xTD;
        }
        else
        {
          h += TD + TD_onclick + dayNum + xTD;
        }
        if (thisDay.getDay() == 6) h += xTR + TR;
        thisDay.setDate(thisDay.getDate() + 1);
      } while (thisDay.getDate() > 1)
      if (thisDay.getDay() > 0)
      {
        for (var i = 6, l = thisDay.getDay(); i > l; i--) h += TD + "&nbsp;" + xTD;
      }
      h += xTR;
      var today = new Date();
      h += TR_todaybutton + TD_todaybutton;
      h += "<button class='" + this.picker_class + "todaybutton' onClick='mx.picker_refresh(\"" + id + "\");'>dnes</button> ";
      h += xTD + xTR;
      h += xTABLE;
      $(this.picker_id).innerHTML = h;
    }

    // date picker helper
    this.picker_button = function(id, date, adjust, label)
    {
      var newMonth = (date.getMonth () + adjust) % 12;
      var newYear = date.getFullYear() + parseInt((date.getMonth() + adjust) / 12);
      if (newMonth < 0)
      {
        newMonth += 12;
        newYear += -1;
      }
      return "<button class='" + this.picker_class + "button' onClick='mx.picker_refresh(\"" + id + "\", " + newYear + ", " + newMonth + ");'>" + label + "</button>";
    }

    // date picker helper
    this.picker_get_ds = function(date)
    {
      var day = '00' + date.getDate();
      var month = '00' + (date.getMonth() + 1);
      day = day.substring(day.length - 2);
      month = month.substring(month.length - 2);
      return day + this.picker_separator + month + this.picker_separator + date.getFullYear();
    }

    // date picker helper
    this.picker_get_fd = function(s)
    {
      var date;
      var dArray;
      var d, m, y;
      try
      {
        dArray = this.picker_split_ds(s);
        if (dArray)
        {
          d = parseInt(dArray[0], 10);
          m = parseInt(dArray[1], 10) - 1;
          y = parseInt(dArray[2], 10);
          date = new Date(y, m, d);
        }
        else if (s)
        {
          date = new Date(s);
        }
        else
        {
          date = new Date();
        }
      }
      catch(e)
      {
        date = new Date();
      }
      return date;
    }

    // date picker helper
    this.picker_split_ds = function(s)
    {
      var dArray;
      if (s.indexOf('/') >= 0) dArray = s.split('/');
      else if (s.indexOf('.') >= 0) dArray = s.split('.');
      else if (s.indexOf('-') >= 0) dArray = s.split('-');
      else if (s.indexOf("\\") >= 0) dArray = s.split("\\");
      else dArray = false;
      return dArray;
    }

    // date picker helper
    this.picker_update_obj = function(id, s)
    {
      var obj = $(id);
      var p = $$(this.picker_id);
      p.visibility = 'hidden';
      p.display = 'none';
      try
      {
        obj.focus();
      }
      catch(e) {}
      if (!this.picker_action)
      {
        if (s) obj.value = s;
        return true;
      }
      if (this.picker_action.length == 0)
      {
        mx.addLog('DATEPICKER action processed (no data!)');
        return true;
      }
      mx.addLog('DATEPICKER action processed: ' + this.picker_action);
      try
      {
        eval(this.picker_action.replace(/\$/, s));
      }
      catch(e)
      {
        mx.addLog("DATEPICKER crashed in function '_picker_update_obj'.\r\n" + e);
      }
      return true;
    }
  }


  /*
    +++ Manticore object END
  */


  /*
    +++ HASHING ROUTINES
  */


  /*
   * A JavaScript implementation of the Secure Hash Algorithm, SHA-1, as defined
   * in FIPS PUB 180-1
   * Version 2.1a Copyright Paul Johnston 2000 - 2002.
   * Other contributors: Greg Holt, Andrew Kepert, Ydnar, Lostinet
   * Distributed under the BSD License
   * See http://pajhome.org.uk/crypt/md5 for details.
   */


  var hexcase = 0;  /* hex output format. 0 - lowercase; 1 - uppercase        */
  var b64pad  = ''; /* base-64 pad character. "=" for strict RFC compliance   */
  var chrsz   = 8;  /* bits per input character. 8 - ASCII; 16 - Unicode      */

  function hex_sha1(s){return binb2hex(core_sha1(str2binb(s),s.length * chrsz));}
  function b64_sha1(s){return binb2b64(core_sha1(str2binb(s),s.length * chrsz));}
  function str_sha1(s){return binb2str(core_sha1(str2binb(s),s.length * chrsz));}
  function hex_hmac_sha1(key, data){ return binb2hex(core_hmac_sha1(key, data));}
  function b64_hmac_sha1(key, data){ return binb2b64(core_hmac_sha1(key, data));}
  function str_hmac_sha1(key, data){ return binb2str(core_hmac_sha1(key, data));}

  function sha1_vm_test()
  {
    return hex_sha1("abc") == "a9993e364706816aba3e25717850c26c9cd0d89d";
  }

  function core_sha1(x, len)
  {
    x[len >> 5] |= 0x80 << (24 - len % 32);
    x[((len + 64 >> 9) << 4) + 15] = len;
    var w = Array(80);
    var a =  1732584193;
    var b = -271733879;
    var c = -1732584194;
    var d =  271733878;
    var e = -1009589776;
    for (var i = 0, l = x.length; i < l; i += 16)
    {
      var olda = a;
      var oldb = b;
      var oldc = c;
      var oldd = d;
      var olde = e;
      for (var j = 0; j < 80; j++)
      {
        if (j < 16) w[j] = x[i + j];
          else w[j] = rol(w[j-3] ^ w[j-8] ^ w[j-14] ^ w[j-16], 1);
        var t = safe_add(safe_add(rol(a, 5), sha1_ft(j, b, c, d)), safe_add(safe_add(e, w[j]), sha1_kt(j)));
        e = d;
        d = c;
        c = rol(b, 30);
        b = a;
        a = t;
      }
      a = safe_add(a, olda);
      b = safe_add(b, oldb);
      c = safe_add(c, oldc);
      d = safe_add(d, oldd);
      e = safe_add(e, olde);
    }
    return Array(a, b, c, d, e);
  }

  function sha1_ft(t, b, c, d)
  {
    if (t < 20) return (b & c) | ((~b) & d);
    if (t < 40) return b ^ c ^ d;
    if (t < 60) return (b & c) | (b & d) | (c & d);
    return b ^ c ^ d;
  }

  function sha1_kt(t)
  {
    return (t < 20) ?  1518500249 : (t < 40) ?  1859775393 : (t < 60) ? -1894007588 : -899497514;
  }

  function core_hmac_sha1(key, data)
  {
    var bkey = str2binb(key);
    if (bkey.length > 16) bkey = core_sha1(bkey, key.length * chrsz);
    var ipad = Array(16), opad = Array(16);
    for (var i = 0; i < 16; i++)
    {
      ipad[i] = bkey[i] ^ 0x36363636;
      opad[i] = bkey[i] ^ 0x5C5C5C5C;
    }
    var hash = core_sha1(ipad.concat(str2binb(data)), 512 + data.length * chrsz);
    return core_sha1(opad.concat(hash), 512 + 160);
  }

  function safe_add(x, y)
  {
    var lsw = (x & 0xFFFF) + (y & 0xFFFF);
    var msw = (x >> 16) + (y >> 16) + (lsw >> 16);
    return (msw << 16) | (lsw & 0xFFFF);
  }

  function rol(num, cnt)
  {
    return (num << cnt) | (num >>> (32 - cnt));
  }

  function str2binb(str)
  {
    var bin = Array();
    var mask = (1 << chrsz) - 1;
    for (var i = 0; i < str.length * chrsz; i += chrsz) bin[i >> 5] |= (str.charCodeAt(i / chrsz) & mask) << (32 - chrsz - i % 32);
    return bin;
  }

  function binb2str(bin)
  {
    var str = '';
    var mask = (1 << chrsz) - 1;
    for (var i = 0; i < bin.length * 32; i += chrsz) str += String.fromCharCode((bin[i>>5] >>> (32 - chrsz - i%32)) & mask);
    return str;
  }

  function binb2hex(binarray)
  {
    var hex_tab = hexcase ? "0123456789ABCDEF" : "0123456789abcdef";
    var str = '';
    for (var i = 0; i < binarray.length * 4; i++) {
      str += hex_tab.charAt((binarray[i>>2] >> ((3 - i % 4) * 8 + 4)) & 0xF) + hex_tab.charAt((binarray[i >> 2] >> ((3 - i % 4) * 8)) & 0xF);
    }
    return str;
  }

  function binb2b64(binarray)
  {
    var tab = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
    var str = '';
    for (var i = 0; i < binarray.length * 4; i += 3) {
      var triplet = (((binarray[i   >> 2] >> 8 * (3 -  i   %4)) & 0xFF) << 16) | (((binarray[i+1 >> 2] >> 8 * (3 - (i+1)%4)) & 0xFF) << 8 ) |  ((binarray[i+2 >> 2] >> 8 * (3 - (i+2)%4)) & 0xFF);
      for (var j = 0; j < 4; j++) {
        if (i * 8 + j * 6 > binarray.length * 32) str += b64pad;
        else str += tab.charAt((triplet >> 6*(3-j)) & 0x3F);
      }
    }
    return str;
  }


  /*
   * A JavaScript implementation of the RSA Data Security, Inc. MD5 Message
   * Digest Algorithm, as defined in RFC 1321.
   * Version 2.1 Copyright (C) Paul Johnston 1999 - 2002.
   * Other contributors: Greg Holt, Andrew Kepert, Ydnar, Lostinet
   * Distributed under the BSD License
   * See http://pajhome.org.uk/crypt/md5 for more info.
   */


  var hexcase = 0;  /* hex output format. 0 - lowercase; 1 - uppercase        */
  var b64pad  = ''; /* base-64 pad character. "=" for strict RFC compliance   */
  var chrsz   = 8;  /* bits per input character. 8 - ASCII; 16 - Unicode      */

  function hex_md5(s) {return binl2hex(core_md5(str2binl(s), s.length * chrsz));}
  function b64_md5(s) {return binl2b64(core_md5(str2binl(s), s.length * chrsz));}
  function str_md5(s) {return binl2str(core_md5(str2binl(s), s.length * chrsz));}
  function hex_hmac_md5(key, data) {return binl2hex(core_hmac_md5(key, data));}
  function b64_hmac_md5(key, data) {return binl2b64(core_hmac_md5(key, data));}
  function str_hmac_md5(key, data) {return binl2str(core_hmac_md5(key, data));}

  function md5_vm_test()
  {
    return hex_md5("abc") == "900150983cd24fb0d6963f7d28e17f72";
  }

  function core_md5(x, len)
  {
    x[len >> 5] |= 0x80 << ((len) % 32);
    x[(((len + 64) >>> 9) << 4) + 14] = len;

    var a =  1732584193;
    var b = -271733879;
    var c = -1732584194;
    var d =  271733878;

    for (var i = 0, l = x.length; i < l; i += 16)
    {
      var olda = a;
      var oldb = b;
      var oldc = c;
      var oldd = d;

      a = md5_ff(a, b, c, d, x[i+ 0], 7 , -680876936);
      d = md5_ff(d, a, b, c, x[i+ 1], 12, -389564586);
      c = md5_ff(c, d, a, b, x[i+ 2], 17,  606105819);
      b = md5_ff(b, c, d, a, x[i+ 3], 22, -1044525330);
      a = md5_ff(a, b, c, d, x[i+ 4], 7 , -176418897);
      d = md5_ff(d, a, b, c, x[i+ 5], 12,  1200080426);
      c = md5_ff(c, d, a, b, x[i+ 6], 17, -1473231341);
      b = md5_ff(b, c, d, a, x[i+ 7], 22, -45705983);
      a = md5_ff(a, b, c, d, x[i+ 8], 7 ,  1770035416);
      d = md5_ff(d, a, b, c, x[i+ 9], 12, -1958414417);
      c = md5_ff(c, d, a, b, x[i+10], 17, -42063);
      b = md5_ff(b, c, d, a, x[i+11], 22, -1990404162);
      a = md5_ff(a, b, c, d, x[i+12], 7 ,  1804603682);
      d = md5_ff(d, a, b, c, x[i+13], 12, -40341101);
      c = md5_ff(c, d, a, b, x[i+14], 17, -1502002290);
      b = md5_ff(b, c, d, a, x[i+15], 22,  1236535329);

      a = md5_gg(a, b, c, d, x[i+ 1], 5 , -165796510);
      d = md5_gg(d, a, b, c, x[i+ 6], 9 , -1069501632);
      c = md5_gg(c, d, a, b, x[i+11], 14,  643717713);
      b = md5_gg(b, c, d, a, x[i+ 0], 20, -373897302);
      a = md5_gg(a, b, c, d, x[i+ 5], 5 , -701558691);
      d = md5_gg(d, a, b, c, x[i+10], 9 ,  38016083);
      c = md5_gg(c, d, a, b, x[i+15], 14, -660478335);
      b = md5_gg(b, c, d, a, x[i+ 4], 20, -405537848);
      a = md5_gg(a, b, c, d, x[i+ 9], 5 ,  568446438);
      d = md5_gg(d, a, b, c, x[i+14], 9 , -1019803690);
      c = md5_gg(c, d, a, b, x[i+ 3], 14, -187363961);
      b = md5_gg(b, c, d, a, x[i+ 8], 20,  1163531501);
      a = md5_gg(a, b, c, d, x[i+13], 5 , -1444681467);
      d = md5_gg(d, a, b, c, x[i+ 2], 9 , -51403784);
      c = md5_gg(c, d, a, b, x[i+ 7], 14,  1735328473);
      b = md5_gg(b, c, d, a, x[i+12], 20, -1926607734);

      a = md5_hh(a, b, c, d, x[i+ 5], 4 , -378558);
      d = md5_hh(d, a, b, c, x[i+ 8], 11, -2022574463);
      c = md5_hh(c, d, a, b, x[i+11], 16,  1839030562);
      b = md5_hh(b, c, d, a, x[i+14], 23, -35309556);
      a = md5_hh(a, b, c, d, x[i+ 1], 4 , -1530992060);
      d = md5_hh(d, a, b, c, x[i+ 4], 11,  1272893353);
      c = md5_hh(c, d, a, b, x[i+ 7], 16, -155497632);
      b = md5_hh(b, c, d, a, x[i+10], 23, -1094730640);
      a = md5_hh(a, b, c, d, x[i+13], 4 ,  681279174);
      d = md5_hh(d, a, b, c, x[i+ 0], 11, -358537222);
      c = md5_hh(c, d, a, b, x[i+ 3], 16, -722521979);
      b = md5_hh(b, c, d, a, x[i+ 6], 23,  76029189);
      a = md5_hh(a, b, c, d, x[i+ 9], 4 , -640364487);
      d = md5_hh(d, a, b, c, x[i+12], 11, -421815835);
      c = md5_hh(c, d, a, b, x[i+15], 16,  530742520);
      b = md5_hh(b, c, d, a, x[i+ 2], 23, -995338651);

      a = md5_ii(a, b, c, d, x[i+ 0], 6 , -198630844);
      d = md5_ii(d, a, b, c, x[i+ 7], 10,  1126891415);
      c = md5_ii(c, d, a, b, x[i+14], 15, -1416354905);
      b = md5_ii(b, c, d, a, x[i+ 5], 21, -57434055);
      a = md5_ii(a, b, c, d, x[i+12], 6 ,  1700485571);
      d = md5_ii(d, a, b, c, x[i+ 3], 10, -1894986606);
      c = md5_ii(c, d, a, b, x[i+10], 15, -1051523);
      b = md5_ii(b, c, d, a, x[i+ 1], 21, -2054922799);
      a = md5_ii(a, b, c, d, x[i+ 8], 6 ,  1873313359);
      d = md5_ii(d, a, b, c, x[i+15], 10, -30611744);
      c = md5_ii(c, d, a, b, x[i+ 6], 15, -1560198380);
      b = md5_ii(b, c, d, a, x[i+13], 21,  1309151649);
      a = md5_ii(a, b, c, d, x[i+ 4], 6 , -145523070);
      d = md5_ii(d, a, b, c, x[i+11], 10, -1120210379);
      c = md5_ii(c, d, a, b, x[i+ 2], 15,  718787259);
      b = md5_ii(b, c, d, a, x[i+ 9], 21, -343485551);

      a = safe_add(a, olda);
      b = safe_add(b, oldb);
      c = safe_add(c, oldc);
      d = safe_add(d, oldd);
    }
    return Array(a, b, c, d);
  }

  function md5_cmn(q, a, b, x, s, t)
  {
    return safe_add(bit_rol(safe_add(safe_add(a, q), safe_add(x, t)), s),b);
  }

  function md5_ff(a, b, c, d, x, s, t)
  {
    return md5_cmn((b & c) | ((~b) & d), a, b, x, s, t);
  }

  function md5_gg(a, b, c, d, x, s, t)
  {
    return md5_cmn((b & d) | (c & (~d)), a, b, x, s, t);
  }

  function md5_hh(a, b, c, d, x, s, t)
  {
    return md5_cmn(b ^ c ^ d, a, b, x, s, t);
  }

  function md5_ii(a, b, c, d, x, s, t)
  {
    return md5_cmn(c ^ (b | (~d)), a, b, x, s, t);
  }

  function core_hmac_md5(key, data)
  {
    var bkey = str2binl(key);
    if (bkey.length > 16) bkey = core_md5(bkey, key.length * chrsz);
    var ipad = Array(16), opad = Array(16);
    for (var i = 0; i < 16; i++)
    {
      ipad[i] = bkey[i] ^ 0x36363636;
      opad[i] = bkey[i] ^ 0x5C5C5C5C;
    }
    var hash = core_md5(ipad.concat(str2binl(data)), 512 + data.length * chrsz);
    return core_md5(opad.concat(hash), 512 + 128);
  }

  function bit_rol(num, cnt)
  {
    return (num << cnt) | (num >>> (32 - cnt));
  }

  function str2binl(str)
  {
    var bin = Array();
    var mask = (1 << chrsz) - 1;
    for (var i = 0, l = str.length * chrsz; i < l; i += chrsz) bin[i >> 5] |= (str.charCodeAt(i / chrsz) & mask) << (i % 32);
    return bin;
  }

  function binl2str(bin)
  {
    var str = '';
    var mask = (1 << chrsz) - 1;
    for (var i = 0, l = bin.length * 32; i < l; i += chrsz) str += String.fromCharCode((bin[i >> 5] >>> (i % 32)) & mask);
    return str;
  }

  function binl2hex(binarray)
  {
    var hex_tab = hexcase ? "0123456789ABCDEF" : "0123456789abcdef";
    var str = '';
    for (var i = 0, l = binarray.length * 4; i < l; i++)
    {
      str += hex_tab.charAt((binarray[i >> 2] >> ((i % 4) * 8 + 4)) & 0xF) + hex_tab.charAt((binarray[i >> 2] >> ((i % 4) * 8)) & 0xF);
    }
    return str;
  }

  function binl2b64(binarray)
  {
    var tab = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
    var str = '';
    for (var i = 0, l = binarray.length * 4; i < l; i += 3)
    {
      var triplet = (((binarray[i >> 2] >> 8 * ( i   %4)) & 0xFF) << 16) | (((binarray[i+1 >> 2] >> 8 * ((i+1) % 4)) & 0xFF) << 8 ) |  ((binarray[i+2 >> 2] >> 8 * ((i+2)%4)) & 0xFF);
      for (var j = 0; j < 4; j++)
      {
        if (i * 8 + j * 6 > binarray.length * 32)
        {
          str += b64pad;
        }
        else
        {
          str += tab.charAt((triplet >> 6*(3-j)) & 0x3F);
        }
      }
    }
    return str;
  }


  /*
    +++ AJAX OBJECT
  */


  function ajax()
  {
    var req = new Object();
    req.timeout = null;
    req.generateUniqueUrl = true;
    req.url = window.location.href;
    req.method = "GET";
    req.async = true;
    req.username = null;
    req.password = null;
    req.parameters = {};

    if ((mx.url.sid) && (mx.config.session_variable)) req.parameters[mx.config.session_variable] = mx.url.sid;

    req.requestIndex = ajax.numAjaxRequests++;
    req.responseReceived = false;
    req.groupName = null;
    req.queryString = '';
    req.responseText = null;
    req.responseXML = null;
    req.status = null;
    req.statusText = null;
    req.aborted = false;
    req.xmlHttpRequest = null;
    req.onTimeout = null;
    req.onLoading = null;
    req.onLoaded = null;
    req.onInteractive = null;
    req.onComplete = null;
    req.onSuccess = null;
    req.onError = null;
    req.onGroupBegin = null;
    req.onGroupEnd = null;
    req.xmlHttpRequest = ajax.getXmlHttpRequest();

    if (req.xmlHttpRequest == null)
    {
      return null;
    }

    req.xmlHttpRequest.onreadystatechange = function()
    {
      if (req == null || req.xmlHttpRequest == null)
      {
        return;
      }
      if (req.xmlHttpRequest.readyState == 1)
      {
        req.onLoadingInternal(req);
      }
      if (req.xmlHttpRequest.readyState == 2)
      {
        req.onLoadedInternal(req);
      }
      if (req.xmlHttpRequest.readyState == 3)
      {
        req.onInteractiveInternal(req);
      }
      if (req.xmlHttpRequest.readyState == 4)
      {
        req.onCompleteInternal(req);
      }
    }

    req.onLoadingInternalHandled = false;
    req.onLoadedInternalHandled = false;
    req.onInteractiveInternalHandled = false;
    req.onCompleteInternalHandled = false;

    req.onLoadingInternal = function()
    {
      if (req.onLoadingInternalHandled)
      {
        return;
      }
      ajax.numActiveAjaxRequests++;
      if (ajax.numActiveAjaxRequests == 1 && typeof(window['AjaxRequestBegin']) == 'function')
      {
        AjaxRequestBegin();
      }
      if (req.groupName != null)
      {
        if (typeof(ajax.numActiveAjaxGroupRequests[req.groupName]) == "undefined")
        {
          ajax.numActiveAjaxGroupRequests[req.groupName] = 0;
        }
        ajax.numActiveAjaxGroupRequests[req.groupName]++;
        if (ajax.numActiveAjaxGroupRequests[req.groupName] == 1 && typeof(req.onGroupBegin) == 'function')
        {
          req.onGroupBegin(req.groupName);
        }
      }
      if (typeof(req.onLoading) == 'function')
      {
        req.onLoading(req);
      }
      req.onLoadingInternalHandled = true;
    }

    req.onLoadedInternal = function()
    {
      if (req.onLoadedInternalHandled)
      {
        return;
      }
      if (typeof(req.onLoaded) == 'function')
      {
        req.onLoaded(req);
      }
      req.onLoadedInternalHandled = true;
    }

    req.onInteractiveInternal = function()
    {
      if (req.onInteractiveInternalHandled)
      {
        return;
      }
      if (typeof(req.onInteractive) == 'function')
      {
        req.onInteractive(req);
      }
      req.onInteractiveInternalHandled = true;
    }

    req.onCompleteInternal = function()
    {
      if (req.onCompleteInternalHandled || req.aborted)
      {
        return;
      }
      req.onCompleteInternalHandled = true;
      ajax.numActiveAjaxRequests--;
      if (ajax.numActiveAjaxRequests == 0) mx.removeLoading();
      if (ajax.numActiveAjaxRequests == 0 && typeof(window['AjaxRequestEnd']) == 'function')
      {
        AjaxRequestEnd(req.groupName);
      }
      if (req.groupName != null)
      {
        ajax.numActiveAjaxGroupRequests[req.groupName]--;
        if (ajax.numActiveAjaxGroupRequests[req.groupName] == 0 && typeof(req.onGroupEnd) == 'function')
        {
          req.onGroupEnd(req.groupName);
        }
      }
      req.responseReceived = true;
      try
      {
        req.status = req.xmlHttpRequest.status;
        req.statusText = req.xmlHttpRequest.statusText;
        req.responseText = req.xmlHttpRequest.responseText;
        req.responseXML = req.xmlHttpRequest.responseXML;
        if (typeof(req.onComplete) == 'function')
        {
          req.onComplete(req);
        }
        if (req.xmlHttpRequest.status == 200 && typeof(req.onSuccess) == 'function')
        {
          req.onSuccess(req);
        }
        else if (typeof(req.onError) == 'function')
        {
          req.onError(req);
        }
        delete req.xmlHttpRequest['onreadystatechange'];
        req.xmlHttpRequest = null;
      }
      catch(e)
      {
        req.onError(req);
      }
    }

    req.onTimeoutInternal = function()
    {
      if (req != null && req.xmlHttpRequest != null && !req.onCompleteInternalHandled)
      {
        req.aborted = true;
        req.xmlHttpRequest.abort();
        ajax.numActiveAjaxRequests--;
        if (ajax.numActiveAjaxRequests == 0 && typeof(window['AjaxRequestEnd']) == 'function')
        {
          AjaxRequestEnd(req.groupName);
        }
        if (req.groupName != null)
        {
          ajax.numActiveAjaxGroupRequests[req.groupName]--;
          if (ajax.numActiveAjaxGroupRequests[req.groupName] == 0 && typeof(req.onGroupEnd) == 'function')
          {
            req.onGroupEnd(req.groupName);
          }
        }
        if (typeof(req.onTimeout) == 'function')
        {
          req.onTimeout(req);
        }
        delete req.xmlHttpRequest['onreadystatechange'];
        req.xmlHttpRequest = null;
      }
    }

    req.process = function()
    {
      if (req.xmlHttpRequest != null)
      {
        if (req.generateUniqueUrl && req.method == "GET")
        {
          req.parameters["AJAXSEQ"] = new Date().getTime() + '' + req.requestIndex;
        }
        var content = null;
        for (var i in req.parameters)
        {
          if (req.queryString.length > 0)
          {
            req.queryString += "&";
          }
          if (typeof req.parameters[i] == "function") continue;
          req.queryString += encodeURIComponent(i) + "=" + encodeURIComponent(req.parameters[i]);
        }
        if (req.method == "GET")
        {
          if (req.queryString.length > 0)
          {
            req.url += ((req.url.indexOf("?") > -1) ? "&" : "?") + req.queryString;
          }
        }
        req.url = req.url.replace(/\#/g, "%23");
        req.xmlHttpRequest.open(req.method, req.url, req.async, req.username, req.password);
        if (req.method == 'POST')
        {
          if (typeof(req.xmlHttpRequest.setRequestHeader) != 'undefined')
          {
            req.xmlHttpRequest.setRequestHeader('Content-type', 'application/x-www-form-urlencoded');
          }
          content = req.queryString;
        }
        if (req.timeout > 0)
        {
          setTimeout(req.onTimeoutInternal, req.timeout);
        }
        mx.showLoading();
        req.xmlHttpRequest.send(content);
      }
    }

    req.handleArguments = function(args)
    {
      for (var i in args) {
        if (typeof(req[i]) == 'undefined')
        {
          req.parameters[i] = args[i];
        }
        else
        {
          req[i] = args[i];
        }
      }
    }

    req.getAllResponseHeaders = function()
    {
      if (req.xmlHttpRequest!=null)
      {
        if (req.responseReceived)
        {
          return req.xmlHttpRequest.getAllResponseHeaders();
        }
      }
      return false;
    }
    req.getResponseHeader = function(headerName)
    {
      if (req.xmlHttpRequest!=null)
      {
        if (req.responseReceived)
        {
          return req.xmlHttpRequest.getResponseHeader(headerName);
        }
      }
      return false;
    }
    return req;
  }

  ajax.getXmlHttpRequest = function()
  {
    if (window.XMLHttpRequest)
    {
      return new XMLHttpRequest();
    }
    else if (window.ActiveXObject)
    {
      var msxmls = new Array('Msxml2.XMLHTTP.7.0', 'Msxml2.XMLHTTP.6.0', 'Msxml2.XMLHTTP.5.0', 'Msxml2.XMLHTTP.4.0', 'Msxml2.XMLHTTP.3.0', 'Msxml2.XMLHTTP','Microsoft.XMLHTTP');
      for (var i = 0, l = i < msxmls.length; l; i++)
      {
        try
        {
          return new ActiveXObject(msxmls[i]);
        }
        catch (e) {}
      }
      return null;
    }
    else
    {
      return null;
    }
    return false;
  }

  ajax.isActive = function()
  {
    return(ajax.numActiveAjaxRequests > 0);
  }

  ajax.get = function(args)
  {
    ajax.doRequest("GET", args);
  }

  ajax.post = function(args)
  {
    ajax.doRequest("POST", args);
  }

  ajax.doRequest = function(method, args)
  {
    if (typeof args != "undefined" && args != null)
    {
      var myRequest = new ajax();
      myRequest.method = method;
      myRequest.handleArguments(args);
      myRequest.process();
    }
  }

  ajax.submit = function(theform, args)
  {
    var myRequest = new ajax();
    if (myRequest == null) return false;
    var serializedForm = ajax.serializeForm(theform);
    myRequest.method = theform.method.toUpperCase();
    myRequest.url = theform.action;
    myRequest.handleArguments(args);
    myRequest.queryString = serializedForm;
    myRequest.process();
    return true;
  }

  ajax.serializeForm = function(theform)
  {
    if(!theform) return '';
    var queryString = '';
    var els = theform.elements;

    // a form serialize helper
    function _addField(name, value)
    {
      if (queryString.length > 0)
      {
        queryString += "&";
      }
      queryString += encodeURIComponent(name) + "=" + encodeURIComponent(value);
    }

    var len = els.length;
    for (var i = 0; i < len; i++)
    {
      var el = els[i];
      if (!el.disabled)
      {
        switch(el.type)
        {
          case 'text':
          case 'password':
          case 'hidden':
          case 'textarea':
            _addField(el.name, el.value);
          break;
          case 'select-one':
            if (el.selectedIndex >= 0)
            {
              _addField(el.name, el.options[el.selectedIndex].value);
            }
          break;
          case 'select-multiple':
            for (var j = 0, l = el.options.length; j < l; j++)
            {
              if (el.options[j].selected)
              {
                _addField(el.name, el.options[j].value);
              }
            }
          break;
          case 'checkbox':
          case 'radio':
            if (el.checked)
            {
              _addField(el.name, el.value);
            }
          break;
        }
      }
    }
    return queryString;
  }

  ajax.numActiveAjaxRequests = 0;
  ajax.numActiveAjaxGroupRequests = new Object();
  ajax.numAjaxRequests = 0;


  /*
    +++ SORTABLE TABLES
  */


/*
Table sorting script  by Joost de Valk, check it out at http://www.joostdevalk.nl/code/sortable-table/.
Based on a script from http://www.kryogenix.org/code/browser/sorttable/.
Distributed under the MIT license: http://www.kryogenix.org/code/browser/licence.html .

Copyright (c) 1997-2006 Stuart Langridge, Joost de Valk.

Version 1.5.6
*/


var image_path = "matrix/";
var image_up = "arrow-up.gif";
var image_down = "arrow-down.gif";
var image_none = "arrow-none.gif";
var europeandate = true;
var alternate_row_colors = true;
var SORT_COLUMN_INDEX;
var thead = false;

function sortables_init()
{
  if (!document.getElementsByTagName) return;
  var tbls = document.getElementsByTagName("table");
  for (var ti = 0, l = tbls.length; ti < l; ti++)
  {
    var thisTbl = tbls[ti];
    if (((' ' + thisTbl.className + ' ').indexOf("sortable") != -1) && (thisTbl.id))
    {
      ts_makeSortable(thisTbl);
    }
  }
}

function ts_makeSortable(t)
{
  if (t.rows && t.rows.length > 0)
  {
    if (t.tHead && t.tHead.rows.length > 0)
    {
      var firstRow = t.tHead.rows[t.tHead.rows.length - 1];
      thead = true;
    }
    else
    {
      var firstRow = t.rows[0];
    }
  }
  if (!firstRow) return;
  for (var i = 0, l = firstRow.cells.length; i < l; i++)
  {
    var cell = firstRow.cells[i];
    var txt = ts_getInnerText(cell);
    if (cell.className != "unsortable" && cell.className.indexOf("unsortable") == -1)
    {
      cell.innerHTML = '<span style="cursor: pointer" title="sortable" class="sortheader" onclick="ts_resortTable(this, '+i+');return false;">'+txt+'<span class="sortarrow">&nbsp;<img src="'+ image_path + image_none + '" alt="&darr;">&nbsp;</span></span>';
    }
  }
  if (alternate_row_colors)
  {
    alternate(t);
  }
}

function ts_getInnerText(el)
{
  if (typeof el == "string") return el;
  if (typeof el == "undefined") return el;
  if (el.innerText) return el.innerText;
  var str = "";
  var cs = el.childNodes;
  for (var i = 0, l = cs.length; i < l; i++)
  {
    switch (cs[i].nodeType)
    {
      case 1:
        str += ts_getInnerText(cs[i]);
      break;
      case 3:
        str += cs[i].nodeValue;
      break;
    }
  }
  return str;
}

function ts_resortTable(lnk, clid)
{
  var span;
  for (var ci = 0, l = lnk.childNodes.length; ci < l; ci++)
  {
    if (lnk.childNodes[ci].tagName && lnk.childNodes[ci].tagName.toLowerCase() == 'span') span = lnk.childNodes[ci];
  }
  var spantext = ts_getInnerText(span);
  var td = lnk.parentNode;
  var column = clid || td.cellIndex;
  var t = getParent(td, 'TABLE');
  if (t.rows.length <= 1) return;
  var itm = "";
  var i = 1;
  while (itm == "")
  {
    var itm = ts_getInnerText(t.tBodies[0].rows[i].cells[column]);
    itm = trim(itm);
    if (itm.substr(0, 4) == "<!--" || itm.length == 0)
    {
      itm = "";
    }
    i++;
  }
  var sortfn = ts_sort_caseinsensitive;
  if (itm.match(/^\d\d[\/\.-][a-zA-z][a-zA-Z][a-zA-Z][\/\.-]\d\d\d\d$/)) sortfn = ts_sort_date;
  if (itm.match(/^\d\d[\/\.-]\d\d[\/\.-]\d\d\d{2}?$/)) sortfn = ts_sort_date;
// ERROR?!
//  if (itm.match(/^-?(\d+[,\.]?)+(E[-+][\d]+)?+%?$/)) sortfn = ts_sort_numeric;
  SORT_COLUMN_INDEX = column;
  var firstRow = new Array();
  var newRows = new Array();
  for (var k = 0, l = t.tBodies.length; k < l; k++)
  {
    var q = t.tBodies[k].rows[0];
    if(q.length) for (var i = 0, m = q.length; i < m; i++)
    {
      firstRow[i] = t.tBodies[k].rows[0][i];
    }
  }
  for (var k = 0, l = t.tBodies.length; k < l; k++)
  {
    if (!thead)
    {
      for (var j = 1, m = t.tBodies[k].rows.length; j < m; j++)
      {
        newRows[j-1] = t.tBodies[k].rows[j];
      }
    }
    else
    {
      for (var j = 0, m = t.tBodies[k].rows.length; j < m; j++)
      {
        newRows[j] = t.tBodies[k].rows[j];
      }
    }
  }
  newRows.sort(sortfn);
  if (span.getAttribute("sortdir") == 'down')
  {
      var ARROW = '&nbsp;<img src="'+ image_path + image_down + '" alt="&darr;">&nbsp;';
      newRows.reverse();
      span.setAttribute('sortdir','up');
  }
  else
  {
      var ARROW = '&nbsp;<img src="' + image_path + image_up + '" alt="&uarr;">&nbsp;';
      span.setAttribute('sortdir','down');
  }
  for (var i = 0, n = newRows.length; i < n; i++)
  {
    if (!newRows[i].className || (newRows[i].className && (newRows[i].className.indexOf('sortbottom') == -1)))
    {
      t.tBodies[0].appendChild(newRows[i]);
    }
  }
  for (var i = 0, n = newRows.length; i < n; i++)
  {
    if (newRows[i].className && (newRows[i].className.indexOf('sortbottom') != -1)) t.tBodies[0].appendChild(newRows[i]);
  }
  var allspans = document.getElementsByTagName("span");
  for (var ci = 0, l = allspans.length; ci < l; ci++)
  {
    if (allspans[ci].className == 'sortarrow')
    {
      if (getParent(allspans[ci],"table") == getParent(lnk,"table"))
      {
        allspans[ci].innerHTML = '&nbsp;<img src="'+ image_path + image_none + '" alt="&darr;">&nbsp;';
      }
    }
  }
  span.innerHTML = ARROW;
  alternate(t);
}

function getParent(el, pTagName)
{
  if (el == null)
  {
    return null;
  }
  else if (el.nodeType == 1 && el.tagName.toLowerCase() == pTagName.toLowerCase())
  {
    return el;
  }
  else
  {
    return getParent(el.parentNode, pTagName);
  }
}

function sort_date(date)
{
  var dt = "00000000";
  if (date.length == 11)
  {
    var mtstr = date.substr(3, 3);
    mtstr = mtstr.toLowerCase();
    switch(mtstr)
    {
      case "jan":
        var mt = "01";
      break;
      case "feb":
        var mt = "02";
      break;
      case "mar":
        var mt = "03";
      break;
      case "apr":
        var mt = "04";
      break;
      case "may":
        var mt = "05";
      break;
      case "jun":
        var mt = "06";
      break;
      case "jul":
        var mt = "07";
      break;
      case "aug":
        var mt = "08";
      break;
      case "sep":
        var mt = "09";
      break;
      case "oct":
        var mt = "10";
      break;
      case "nov":
        var mt = "11";
      break;
      case "dec":
        var mt = "12";
      break;
    }
    dt = date.substr(7, 4) + mt + date.substr(0, 2);
    return dt;
  }
  else if (date.length == 10)
  {
    if (europeandate == false)
    {
      dt = date.substr(6, 4) + date.substr(0, 2) + date.substr(3, 2);
      return dt;
    }
    else
    {
      dt = date.substr(6, 4) + date.substr(3, 2) + date.substr(0, 2);
      return dt;
    }
  }
  else if (date.length == 8)
  {
    yr = date.substr(6, 2);
    if (parseInt(yr) < 50)
    {
      yr = '20' + yr;
    }
    else
    {
      yr = '19' + yr;
    }
    if (europeandate == true)
    {
      dt = yr + date.substr(3, 2) + date.substr(0, 2);
      return dt;
    }
    else
    {
      dt = yr + date.substr(0, 2) + date.substr(3, 2);
      return dt;
    }
  }
  return dt;
}

function ts_sort_date(a,b)
{
  var dt1 = sort_date(ts_getInnerText(a.cells[SORT_COLUMN_INDEX]));
  var dt2 = sort_date(ts_getInnerText(b.cells[SORT_COLUMN_INDEX]));
  if (dt1 == dt2)
  {
    return 0;
  }
  if (dt1 < dt2)
  {
    return -1;
  }
  return 1;
}

function ts_sort_numeric(a, b)
{
  var aa = ts_getInnerText(a.cells[SORT_COLUMN_INDEX]);
  aa = clean_num(aa);
  var bb = ts_getInnerText(b.cells[SORT_COLUMN_INDEX]);
  bb = clean_num(bb);
  return compare_numeric(aa, bb);
}

function compare_numeric(a, b)
{
  a = parseFloat(a);
  a = (isNaN(a) ? 0 : a);
  b = parseFloat(b);
  b = (isNaN(b) ? 0 : b);
  return a - b;
}

function ts_sort_caseinsensitive(a, b)
{
  var aa = ts_getInnerText(a.cells[SORT_COLUMN_INDEX]).toLowerCase();
  var bb = ts_getInnerText(b.cells[SORT_COLUMN_INDEX]).toLowerCase();
  if (aa == bb) {
    return 0;
  }
  if (aa < bb)
  {
    return -1;
  }
  return 1;
}

function ts_sort_default(a, b)
{
  aa = ts_getInnerText(a.cells[SORT_COLUMN_INDEX]);
  bb = ts_getInnerText(b.cells[SORT_COLUMN_INDEX]);
  if (aa == bb)
  {
    return 0;
  }
  if (aa < bb)
  {
    return -1;
  }
  return 1;
}

function addEvent(elm, evType, fn, useCapture)
{
  if (elm.addEventListener)
  {
    elm.addEventListener(evType, fn, useCapture);
    return true;
  }
  else if (elm.attachEvent)
  {
    var r = elm.attachEvent("on" + evType, fn);
    return r;
  }
  else
  {
    alert("Handler could not be removed!");
  }
  return null;
}

function clean_num(str)
{
  return str.replace(new RegExp(/[^-?0-9.]/g),"");
}

function trim(s)
{
  while (s.substring(0, 1) == ' ')
  {
    s = s.substring(1, s.length);
  }
  while (s.substring(s.length - 1, s.length) == ' ')
  {
    s = s.substring(0, s.length - 1);
  }
  return s;
}

function alternate(table)
{
  var tableBodies = table.getElementsByTagName("tbody");
  for (var i = 0, l = tableBodies.length; i < l; i++)
  {
    var tableRows = tableBodies[i].getElementsByTagName("tr");
    for (var j = 0, n = tableRows.length; j < n; j++)
    {
      if ((j % 2) == 0)
      {
        if (!(tableRows[j].className.indexOf('odd') == -1))
        {
          tableRows[j].className = tableRows[j].className.replace('odd', 'even');
        }
        else
        {
          if (tableRows[j].className.indexOf('even') == -1) tableRows[j].className += " even";
        }
      }
      else
      {
        if (!(tableRows[j].className.indexOf('even') == -1))
        {
          tableRows[j].className = tableRows[j].className.replace('even', 'odd');
        }
        else
        {
          if (tableRows[j].className.indexOf('odd') == -1) tableRows[j].className += " odd";
        }
      }
    }
  }
}


  /*
    +++ INITIALIZATION
  */


  var mx = new mx_prototype;
  var t1 = mx.key();
  var t2 = mx.key();
  mx.setCookie(t1, t2);
  if (mx.getCookie(t1) == t2)
  {
    mx.settings.cookie = 1;
  }
  mx.delCookie(t1);
  delete t1;
  delete t2;
  mx.registerOnload('sortables_init()');
  mx.registerOnload('mx.alert()');
  try
  {
    document.onreadystatechange = mx._onload();
  }
  catch(e) {}


/*
  +++ WRAPPERS (obsolete functions for compatibility reasons, not for new projects)

  !!! MAY BE REMOVED WITHOUT ANY PRIOR NOTICE !!! MAY BE REMOVED WITHOUT ANY PRIOR NOTICE !!!

*/


  function dwr(x) {return mx.write(x);}
  function obj(x) {return $(x);}
  function style(x) {return $$(x);}
  function rnd(x) {return mx.rnd(x);}
  function won(x) {return mx.visOn(x);}
  function woff(x) {return mx.visOff(x);}
  function ww(x) {return mx.vis(x);}
  function gstr(x) {return mx.getHTML(x);}
  function wstr(x, data) {return mx.setHTML(x, data);}
  function wstrpre(x, data) {return mx.preHTML(x, data);}
  function wstradd(x, data) {return mx.postHTML(x, data);}
  function wtop(x, pt) {return $$(x).top = pt + 'px';}
  function wleft(x, pl) {return $$(x).left = pl + 'px';}
  function wset(x, pt, pl) {wtop(x, pt); wleft(x, pl);return true;}
  function col(x, r, g, b) {return mx.color(x, r, g, b);}
  function cob(x, r, g, b) {return mx.backgroundColor(x, r, g, b);}
  function collapse(x) {return mx.disOff(x);}
  function recover(x) {return mx.disOn(x);}
  function iset(x, y, z) {$(x).width = y;$(x).height = z;}
  function isrc(x, y) {mx.src(x, y);}
  function ihref(x,y) {mx.href(x, y);}
  function setcookie(name, value) {mx.setCookie(name, value);}
  function delcookie(name) {mx.delCookie(name);}
  function getcookie(name) {mx.getCookie(name);}
  function expand(x) {(mx.dis(x)) ? mx.disOff(x) : mx.disOn(x);}
  function tik(data, typ) {mx.doTick(data, typ);}
  function rmtik() {mx.removeTick();}
  function wopen(url, name, w, h, t, l) {if (!w) w = 640;if (!h) h = 480;if (!t) t = 20;if (!l) l = 20;if (!name) name = mx.settings.mx_site;var a = window.open(url, name, 'width=' + w + ',height=' + h + ',status=yes,location=yes,toolbar=yes,scrollbars=yes,resizable=yes,top=' + t + ',left=' + l, true);return a;}
  function wopen2(url, name, w, h, res) {if (!w) w = 640;if (!h) h = 480;if (!name) name = mx.settings.mx_site;if (!res) res = 1;var a = window.open(url, name, 'width=' + w + ',height=' + h + ',location=no,menubar=no,titlebar=no,status=no,toolbar=no,scrollbars=no,resizable=' + res, true);return a;}
  function wopen3(url, name) {return wopen(url, name, 640, 480);}
  function obr(x, y) {if (!y) y = '';if (dom) mx.showPicture(x, y);else {if (!y) y = mx.settings.mx_site.toUpperCase();var z = '';z += '<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN"><html><head><title>' + y + '<\/title>';z += '<style type="text/css">body {cursor: hand;color:#ffffff;font: normal 15pt/normal Arial}<\/style>';z += '<script type="text/javascript" language="javascript1.5">function setWindow() {var a=document.getElementById("obr").width;var b=document.getElementById("obr").height;window.resizeTo(a + 30, b + 50);window.moveTo((screen.width - a - 10) / 2,(screen.height - b -10) / 2);}window.setTimeout("setWindow();", 250);<\/s';z += 'cript><\/head>';z += '<body bgcolor="#000000" style="margin-top:0;margin-bottom:0;margin-left:0;margin-right:0;background-image:url(\'matrix/loading.gif\');background-position:center center;background-repeat:no-repeat"><center>';z += '<table height="100%" width="100%" cellpadding=0 cellspacing=0><tr><td valign=middle align=center>';z += '<img onload="document.body.style.backgroundImage=\'\';document.getElementById(\'obr\').style.visibility=\'visible\';" src="' + x + '" alt="[ ' + mx.locale[mx.config.locale].close_picture + ' ]" border=0 id="obr" style="visibility:hidden" onclick="window.close();">';z += '<\/table><\/body><\/html>';var q = wopen2('', mx.key(), 320, 240, 0);q.window.moveTo((screen.width - 320 - 10) / 2, (screen.height - 240 - 10) / 2);q.document.writeln(z);q.setWindow();q.focus();}}

}

// END of the library