104 lines
1.9 KiB
JavaScript
104 lines
1.9 KiB
JavaScript
var Class = ( function( extending )
|
|
{
|
|
var C = function( dfn )
|
|
{
|
|
// extend from an empty base
|
|
return C.extend( null, dfn );
|
|
};
|
|
|
|
C.extend = function( base, dfn )
|
|
{
|
|
base = base || function() {};
|
|
|
|
// prevent ctor invocation
|
|
extending = true;
|
|
|
|
var ctor = function()
|
|
{
|
|
// do nothing if extending
|
|
if ( extending )
|
|
{
|
|
return;
|
|
}
|
|
|
|
// call "actual" constructor
|
|
this.__construct &&
|
|
this.__construct.apply(
|
|
this, arguments
|
|
);
|
|
};
|
|
|
|
ctor.prototype = new base();
|
|
ctor.prototype.constructor = ctor;
|
|
|
|
copyTo( ctor.prototype, dfn );
|
|
|
|
// done extending; clear flag to
|
|
// ensure ctor can be invoked
|
|
extending = false;
|
|
|
|
return ctor;
|
|
};
|
|
|
|
function copyTo( dest, members )
|
|
{
|
|
var hasOwn = Object.prototype
|
|
.hasOwnProperty;
|
|
|
|
for ( var member in members )
|
|
{
|
|
if ( !hasOwn.call( members, member ) )
|
|
{
|
|
continue;
|
|
}
|
|
|
|
dest[ member ] = members[ member ];
|
|
}
|
|
}
|
|
|
|
return C;
|
|
} )( false );
|
|
|
|
var Foo = Class(
|
|
{
|
|
__construct: function( name )
|
|
{
|
|
if ( !name )
|
|
{
|
|
throw TypeError( "Name required" );
|
|
}
|
|
|
|
this._name = ''+( name );
|
|
},
|
|
|
|
getName: function()
|
|
{
|
|
return this._name;
|
|
}
|
|
} );
|
|
|
|
var SubFoo = Class.extend( Foo,
|
|
{
|
|
setName: function( name )
|
|
{
|
|
this._name = ''+( name );
|
|
}
|
|
} );
|
|
|
|
|
|
var myfoo = new Foo( "Foo" ),
|
|
mysub = new SubFoo( "SubFoo" );
|
|
|
|
myfoo.getName(); // "Foo"
|
|
mysub.getName(); // "SubFoo"
|
|
|
|
mysub.setName( "New Name" );
|
|
mysub.getName(); // "New Name"
|
|
|
|
// parent Foo does not define setName()
|
|
myfoo.setName( "Error" ); // TypeError
|
|
|
|
// our name will be required, since we
|
|
// are not extending
|
|
new Foo(); // TypeError
|