// JavaScriptMVC's Class plugin
// http://javascriptmvc.com/blog/?p=61
// based heavily on John Resig's Simple Class Inheritance
// http://ejohn.org/blog/simple-javascript-inheritance/
// Class is freely distributable under the terms of an MIT-style license.
// 1.0.1
(function(){
  var initializing = false, fnTest = /xyz/.test(function(){xyz;}) ? /\b_super\b/ : /.*/;
  // The base Class implementation (does nothing)
  
  Class = function(){};
  Class.init = function(){
	if (this.className) {
	  	var className = this.className.replace(/\w+/g,function(word){
			return word.charAt(0).toUpperCase()+word.substr(1).toLowerCase();
		}).replace(/_|-/g,'');
		window[className] = this;
		var i;
	}
  }
  // Create a new Class that inherits from this class
  Class.extend = function(className, klass, proto) {
    if(typeof className != 'string'){
        proto = klass;
        klass = className;
        className = null;
    }
    if(!proto){
        proto = klass;
        klass = null;
    }
    var _super_class = this;
    var _super = this.prototype;
    // Instantiate a base class (but only create the instance,
    // don't run the init constructor)
    initializing = true;
    var prototype = new this();
    initializing = false;
    // Copy the properties over onto the new prototype
    for (var name in proto) {
      // Check if we're overwriting an existing function
      prototype[name] = typeof proto[name] == "function" &&
        typeof _super[name] == "function" && fnTest.test(proto[name]) ?
        (function(name, fn){
          return function() {
            var tmp = this._super;
           
            // Add a new ._super() method that is the same method
            // but on the super-class
            this._super = _super[name];
           
            // The method only need to be bound temporarily, so we
            // remove it when we're done executing
            var ret = fn.apply(this, arguments);       
            this._super = tmp;
           
            return ret;
          };
        })(name, proto[name]) :
        proto[name];
    }
    // The dummy class constructor
    function Class() {
      // All construction is actually done in the init method
      if ( !initializing && this.init )
        this.init.apply(this, arguments);
    }
    // Populate our constructed prototype object
    Class.prototype = prototype;
    Class.prototype.Class = Class;
    Class.prototype.superclass = _super_class;
    // Enforce the constructor to be what we expect
    Class.constructor = Class;
    // And make this class extendable
    
    for(var name in this){
        if(this.hasOwnProperty(name) && name != 'prototype'){
            Class[name] = this[name];
        }
    }
    
    for (var name in klass) {
      Class[name] = typeof klass[name] == "function" &&
        typeof Class[name] == "function" && fnTest.test(klass[name]) ?
        (function(name, fn){
          return function() {
            var tmp = this._super;
            this._super = _super_class[name];
            var ret = fn.apply(this, arguments);       
            this._super = tmp;
            return ret;
          };
        })(name, klass[name]) :
        klass[name];
	};
    Class.extend = arguments.callee;
    if(className) Class.className = className;
    
    if(Class.init) Class.init(Class);
    if(_super_class.extended) _super_class.extended(Class) 
    
    return Class;
  };
})();