/* Dom Manipulation Functions
 * 2007-10 Tim Igoe (tim@timigoe.co.uk)
 *
 *--------------------------------------------------------------------------*/

var framework = function(what, start)
{
  return framework.prototype.find(what, start);
}

framework.prototype.find = function(what, start)
{
  if (!what)
    return this;

  if (!start)
    start = document;

  this.elements = [];

  what = what.split(' ');

  if (what == 'body') // Body - hard coded
  {
    this.elements.push(document.body);
  }
  else
  { // Everything Else
    var idSelector = /^#([A-Za-z0-9-]+)$/;
    var match = idSelector.exec(what[0]);
    if (match && match[1])
    { // ID selector - #name
      if (what.length == 1)
        this.elements.push(start.getElementById(match[1]));
      else
      {
        delete what[0];
        return this.find(this.trim(what.join(' ')), start.getElementById(match[1]))
      }
    }
    else
    { // HTML Tag Selector - div
      var tagSelector = /^([A-Za-z]+)/;
      match = tagSelector.exec(what[0]);
      if (match && match[1])
      {
        var elements = start.getElementsByTagName(match[1])

        for (i = 0; i < elements.length; i++)
          this.elements.push(elements[i]);
      }
      else
      {
        // CSS Class Selector - .style
        var classSelector = /^.([A-Za-z0-9-]+)/;
        match = classSelector.exec(what[0]);
        if (match && match[1])
        {
          var elements = start.getElementsByTagName('*');

          var className;
          for (i = 0; i < elements.length; i++)
          {
            className = elements[i].getAttribute('class') || elements[i].getAttribute('className');

            if (className && className.search(match[1]) != -1)
              this.elements.push(elements[i]);
          }
        }
      }
    }
  }

  // Make it available for a for loop as well as more object manipulation
  this.length = this.elements.length;
  for (i = 0; i < this.length; i++)
    this[i] = this.elements[i];

  return this;
}

// Dimensions

// Visibility

framework.prototype.show = function()
{
  for (i = 0; i < this.elements.length; i++)
    this.elements[i].style.display = "block";
  return this;
}

framework.prototype.hide = function()
{
  for (i = 0; i < this.elements.length; i++)
    this.elements[i].style.display = "none";
  return this;
}

// String Manipulation
framework.prototype.trim = function(text)
{
  return text.replace(/^\s+|\s+$/g, '');
}

// CSS

// Effects - Fade

// Effects - Slide

// Effects - Move

/* Allow multiple things to hook into the Window.load function
 * 2007-10 Tim Igoe (tim@timigoe.co.uk)
 *
 *--------------------------------------------------------------------------*/

framework.event = new Object();

framework.event.observe = function(element, name, tocall)
{
  if (element.addEventListener)
    element.addEventListener(name, tocall, false);
  else if (element.attachEvent)
    element.attachEvent('on' + name, tocall);
}

framework.event.unobserve = function(element, name, tocall)
{
  if (element.removeEventListener)
    element.removeEventListener(name, tocall, false);
  else if (element.detachEvent)
    element.detachEvent('on' + name, tocall);
}

/* Ajax Callback Object
 * 2007-10 Tim Igoe (tim@timigoe.co.uk)
 *
 *--------------------------------------------------------------------------*/
framework.ajaxRequests = new Array();

framework.ajax = {
  load: function(url, params, callback)
  {
    if (!params)
    {
      if (url.indexOf("?") >= 0)
        url = url + "&r=" + (Math.random() * Date.parse(new Date()));
      else
        url = url + "?r=" + (Math.random() * Date.parse(new Date()));
    }
    this.callback = callback;
    
    if (window.XMLHttpRequest)         // Mozilla, Safari, ...
      this.req = new XMLHttpRequest();
    else if (window.ActiveXObject)     // IE
      this.req = new ActiveXObject("Microsoft.XMLHTTP");

    if (this.req)
    { // Try sending the message
      var self = this;
      this.req.onreadystatechange = function ()
      {
        self.loaded.call(self);
      }

      if (params)
      {
        this.req.open('POST', url, true);
        this.req.setRequestHeader("Content-type", "application/x-www-form-urlencoded");
        this.req.setRequestHeader("Content-length", params.length);
        this.req.setRequestHeader("Connection", "close");
      }
      else
        this.req.open('GET', url, true);
      this.req.send(params ? params : null);

      this.count = framework.ajaxRequests.length + 1;
      framework.ajaxRequests.push(this);
    }
  },
  loaded: function ()
  {
    var req = this.req;
    if (req.readyState == 4)
    {
      if (req.status == 200 || req.status == 0)
      {
        if (this.callback)
          this.callback.call(this);
      }
      else if (req.status == 404)
        if (this.callback)
          this.callback.call(this);
    }
  },
  abort: function ()
  {
    this.req.abort();
    delete framework.ajaxRequests[this.count];
  }
}

