The second return is necessary because otherwise we will lose any return value from the bound function.
You may already know this, but doesn't hurt to mention. If we don't wrap fn.apply
inside another function, then we are directly calling the function fn
which is sub-optimal, as bind
is only supposed to set the execution context (what should this
refer to inside the function), and not invoke it.
Javascript methods can be invoked by calling the call
or apply
method on them. Here's a small example:
function example() {
alert("useless example");
}
example.apply() // or example.call(), alerts "useless example";
The outer function in Prototype's bind() is supposed to work like an invisible wrapper around the bound function. Thus any arguments that are passed to the wrapper should be passed to the bound function as well, and it must return any value that the bound function returns, which is why the return statement is there.
The reason for doing args.concat inside fn.apply is different and it's not optional. bind
in Prototype allows you to prepend arguments to the bound function.
args
represents the arguments that were passed when we called bind
on the function. arguments
represents the arguments that were passed when we called the bound function. We're basically concatenating two arrays there.
From the above example:
var obj = { x: 'prop x' };
var boundExample = example.bind(obj, 12, 23); // args => 12, 23
boundExample(36, 49); // arguments => 36, 49
// arguments that our example() function receives => 12, 23, 36, 49