Created
August 8, 2010 18:24
-
-
Save bga/514372 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
/** | |
@fn call function with <this> = <that> and <arguments> matched from <argMap> by names | |
@param that {Any} <this> for function call | |
@param argMap {Object} map argName -> argValue | |
@example | |
var _fn = function(a, b, c) | |
{ | |
console.log('a = ', a, 'b = ', b, 'с = ', c); | |
}; | |
_fn._jbNamedApply(null, {b: 1}); // a = undefined b = 1 с = undefined | |
_fn._jbNamedApply(null, {b: 1, a: 0}); // a = 0 b = 1 с = undefined | |
_fn._jbNamedApply.call(1, 1, {}); // TypeError: first argument must be function | |
_fn._jbNamedApply(null, 1); // TypeError: 3rd argument must not null | |
_fn._jbNamedApply(null, {b: 1, a: 0, d: 3}); // SyntaxError: function hasnt argument "d" | |
var _fn2 = function(){}; | |
_fn2._jbNamedApply(null, {b: 1, a: 0, d: 3}); // SyntaxError: function hasnt named arguments | |
@return result of function call | |
*/ | |
Function.prototype._jbNamedApply = function(that, argMap) | |
{ | |
var _fn = this; | |
if(typeof(_fn) != 'function') | |
throw new TypeError('first argument must be function'); | |
if(argMap == null) | |
throw new TypeError('3rd argument must not null'); | |
var argToPosMap = _fn.jbArgToPosMap_; | |
if(argToPosMap == null) | |
{ | |
var fnCode = '' + _fn; | |
var argString = fnCode.slice(fnCode.indexOf('(') + 1, fnCode.lastIndexOf(')', fnCode.indexOf('{'))). // get arguments string | |
replace(/\/\*[\s\S]*?\*\//g, ''). // and strip comments | |
replace(/\/\/[\s\S]*?\n/g, ''). | |
/*#if $jb.Deploy._const('support:String.prototype.trim') */ | |
/*## trim() */ | |
/*#else*/ | |
replace(/^\s+|\s+$/g, '') | |
/*#endif*/ | |
; | |
argToPosMap = _fn.jbArgToPosMap_ = {}; | |
if(argString) | |
{ | |
var argNames = argString.split(/\s*,\s*/); | |
var i = -1, len = argNames.length; while(++i < len) | |
argToPosMap[argNames[i]] = i; | |
} | |
else | |
{ | |
_fn.jbHasntArguments_ = true; | |
} | |
} | |
if(_fn.jbHasntArguments_) | |
{ | |
/*#if $jb.Deploy._const('support:Object.prototype.__count__') */ | |
/*## if(argMap.__count__) throw new SyntaxError('function hasnt named arguments'); */ | |
/*#else*/ | |
for(var name in argMap) | |
{ | |
if(argMap.hasOwnProperty(name)) | |
throw new SyntaxError('function hasnt named arguments') | |
} | |
/*#endif*/ | |
} | |
else | |
{ | |
var argValues = []; | |
for(var name in argMap) | |
{ | |
if(argMap.hasOwnProperty(name)) | |
{ | |
var pos = argToPosMap[name]; | |
if(pos == null) | |
throw new SyntaxError('function hasnt argument "' + name + '"') | |
argValues[pos] = argMap[name]; | |
} | |
} | |
return _fn.apply(that, argValues); | |
} | |
}; |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment