client/resources/util.inherit.js
( function () {
'use strict';
/**
* Extends an object with the attributes of another object.
*
* @ignore
*
* @param {Object} target
* @param {Object} source
* @return {Object}
*/
function extend( target, source ) {
for ( var v in source ) {
// eslint-disable-next-line no-prototype-builtins
if ( source.hasOwnProperty( v ) ) {
target[ v ] = source[ v ];
}
}
return target;
}
/**
* Helper to create a function which will execute a given function.
*
* @ignore
*
* @param {Function} [originalFn=function() {}] Optional function which will be executed by new
* function.
* @return {Function}
*/
function createFunction( originalFn ) {
return originalFn
? function () { originalFn.apply( this, arguments ); }
: function () {};
}
/**
* Helper for prototypical inheritance.
*
* @license GPL-2.0+
* @author Daniel Werner < daniel.a.r.werner@gmail.com >
*
* @param {string|Function} [nameOrBase] The name of the new constructor (currently not used).
* This is handy for debugging purposes since instances of the constructor might be
* displayed under that name.
* If a function is provided, it is assumed to be the constructor to be used for the
* prototype chain (see next argument).
* @param {Function} [baseOrConstructor] Constructor which will be used for the prototype
* chain. This function will not be the constructor returned by the function but will be
* called by it.
* If no name is provided, this argument is assumed to be a constructor (see next
* argument).
* @param {Function|Object} [constructorOrMembers] Constructor to overwriting the base
* constructor with.
* If no name is provided, this argument is assumed to be an object with new prototype
* members (see next argument).
* @param {Object} [members={}] Properties overwriting or extending those of the base.
* @return {Function} Constructor of the new, extended type.
*
* @throws {Error} in case a malicious function name is given or a reserved word is used.
*/
var inherit = function ( nameOrBase, baseOrConstructor, constructorOrMembers, members ) {
var base = baseOrConstructor,
constructor = constructorOrMembers;
if ( typeof nameOrBase !== 'string' ) {
members = constructorOrMembers;
constructor = baseOrConstructor;
base = nameOrBase;
}
// allow to omit constructor since it can be inherited directly. But if given, require it as
// second parameter for readability. If no constructor, second parameter is the prototype
// extension object.
if ( !members ) {
if ( typeof constructor === 'function' ) {
members = {};
} else {
members = constructor || {};
constructor = false;
}
}
// function we execute in our real constructor
var NewConstructor = createFunction( constructor || base );
// new constructor for avoiding direct use of base constructor and its potential
// side-effects
var NewPrototype = createFunction();
NewPrototype.prototype = base.prototype;
NewConstructor.prototype = extend(
new NewPrototype(),
members
);
// Set "constructor" property properly, allow explicit overwrite via member definition.
// NOTE: in IE < 9, overwritten "constructor" properties are still set as not enumerable,
// so don't do this as part of the extend above.
// eslint-disable-next-line no-prototype-builtins
NewConstructor.prototype.constructor = members.hasOwnProperty( 'constructor' ) ?
members.constructor : NewConstructor;
return NewConstructor;
};
module.exports = inherit;
}() );