// Inspired by base2 and Prototype
// Adapted from Resig's simple inheritance
var Class = (function(){
	var initializing = false,
	fnTest = /xyz/.test(function(){xyz;}) ? /\b_super\b/ : /.*/;
	
	var rootClass = function(){};
	
	rootClass.create_prototype = function(base) {
		initializing = true;
		var prototype = new base();
		initializing = false;
		return prototype;
	};
	
	rootClass.extend_props = function(dest, base, props, excludes, super_name) {
		super_name = super_name || "_super";
		excludes = excludes || [];
		
		var excludes_dict = {};
		for (var i=0; i<excludes.length; i++)
			excludes_dict[excludes[i]] = true;
		
		for (var name in props) {
			if (excludes_dict[name])
				continue;
			
			if (typeof props[name] == "function") {
				if (fnTest.test(props[name])) {
					if (typeof base[name] == "function") {
						// The function uses _super to reference the method
						// from the parent, so add a closure to temporarily
						// set 'this._super' to the parent's method.
						dest[name] = (function(name, fn) {
							return function() {
								var tmp = this[super_name];
								this[super_name] = base[name];
								var ret = fn.apply(this, arguments);
								this[super_name] = tmp;
								return ret;
							};
						})(name, props[name]);
					} else {
						// If the function uses _super but no _super method is
						// defined, so use an empty function.
						dest[name] = (function(name, fn) {
							return function() {
								var tmp = this[super_name];
								this[super_name] = function(){};
								var ret = fn.apply(this, arguments);
								this[super_name] = tmp;
								return ret;
							};
						})(name, props[name]);
					}
				} else {
					// The value is a function but doesn't use _super,
					// so do nothing
					dest[name] = props[name];
				}
			} else {
				// The value is a non-function, so do nothing
				dest[name] = props[name];
			}
		}
		return dest;
	};
	
	// Create a new Class that inherits from this class
	rootClass.create = function(iprops, cprops) {
		
		// The dummy class constructor
		function Class() {
			// All construction is actually done in the init method
			if ( !initializing ) { //&& this.__init ) {
				var ret;
				if ( this instanceof Class )
					ret = this;
				else {
					initializing = true;
					var ret = new Class();
					initializing = false;
				}
				
				if ( ret.__init )
					ret.__init.apply(ret, arguments);
				
				return ret;
			}
		}
		
		function create() {
			//return Class.apply(this, arguments);
			initializing = true;
			var ret = new this();
			initializing = false;
			
			if (ret.__init)
				ret.__init.apply(ret, arguments);
			
			return ret;
		}
		
		if (this == rootClass) {
			Class.extend = rootClass.create;
			Class.create = create;
			rootClass.extend_props(Class, {}, cprops || {});
		} else {
			for (var name in this) {
				Class[name] = this[name];
			}
			rootClass.extend_props(Class, this, cprops || {});
		}
		
		Class.prototype = rootClass.create_prototype(this);
		Class.prototype.constructor = Class;
		rootClass.extend_props(Class.prototype, this.prototype, iprops || {});
		
		if (Class.__classinit && typeof Class.__classinit == "function")
			Class.__classinit(this, cprops);
		
		return Class;
	};
	
	return rootClass;
})();

