Function soaks should preserve this. Fixes issue #692.

This commit is contained in:
Stéphan Kochen
2010-09-18 12:27:14 +02:00
parent 43f7f6c355
commit 72d7fe2f7a
3 changed files with 35 additions and 16 deletions

View File

@@ -497,40 +497,49 @@
})()); })());
}; };
CallNode.prototype.compileNode = function(o) { CallNode.prototype.compileNode = function(o) {
var _b, _c, _d, _e, _f, _g, _h, _i, arg, args, code, op; var _b, _c, _d, _e, _f, _g, _h, _i, _j, arg, args, code, methodAccessor, op;
if (!(o.chainRoot)) { if (!(o.chainRoot)) {
o.chainRoot = this; o.chainRoot = this;
} }
op = this.tags.operation; op = this.tags.operation;
if (this.exist) { if (this.exist) {
_b = this.variable.compileReference(o, { if (this.variable instanceof ValueNode && this.variable.properties[this.variable.properties.length - 1] instanceof AccessorNode) {
precompile: true methodAccessor = this.variable.properties.pop();
}); _b = this.variable.compileReference(o);
this.first = _b[0]; this.first = _b[0];
this.meth = _b[1]; this.meth = _b[1];
this.first = new ValueNode(this.first, [methodAccessor]).compile(o);
this.meth = new ValueNode(this.meth, [methodAccessor]).compile(o);
} else {
_c = this.variable.compileReference(o, {
precompile: true
});
this.first = _c[0];
this.meth = _c[1];
}
this.first = ("(typeof " + (this.first) + " === \"function\" ? "); this.first = ("(typeof " + (this.first) + " === \"function\" ? ");
this.last = " : undefined)"; this.last = " : undefined)";
} else if (this.variable) { } else if (this.variable) {
this.meth = this.variable.compile(o); this.meth = this.variable.compile(o);
} }
_d = this.args; _e = this.args;
for (_c = 0, _e = _d.length; _c < _e; _c++) { for (_d = 0, _f = _e.length; _d < _f; _d++) {
arg = _d[_c]; arg = _e[_d];
if (arg instanceof SplatNode) { if (arg instanceof SplatNode) {
code = this.compileSplat(o); code = this.compileSplat(o);
} }
} }
if (!code) { if (!code) {
args = (function() { args = (function() {
_f = []; _h = this.args; _g = []; _i = this.args;
for (_g = 0, _i = _h.length; _g < _i; _g++) { for (_h = 0, _j = _i.length; _h < _j; _h++) {
arg = _h[_g]; arg = _i[_h];
_f.push((function() { _g.push((function() {
arg.parenthetical = true; arg.parenthetical = true;
return arg.compile(o); return arg.compile(o);
})()); })());
} }
return _f; return _g;
}).call(this); }).call(this);
code = this.isSuper ? this.compileSuper(args.join(', '), o) : ("" + (this.first) + (this.prefix()) + (this.meth) + "(" + (args.join(', ')) + ")" + (this.last)); code = this.isSuper ? this.compileSuper(args.join(', '), o) : ("" + (this.first) + (this.prefix()) + (this.meth) + "(" + (args.join(', ')) + ")" + (this.last));
} }

View File

@@ -452,7 +452,13 @@ exports.CallNode = class CallNode extends BaseNode
o.chainRoot = this unless o.chainRoot o.chainRoot = this unless o.chainRoot
op = @tags.operation op = @tags.operation
if @exist if @exist
[@first, @meth] = @variable.compileReference o, precompile: yes if @variable instanceof ValueNode and @variable.properties[@variable.properties.length - 1] instanceof AccessorNode
methodAccessor = @variable.properties.pop()
[@first, @meth] = @variable.compileReference o
@first = new ValueNode(@first, [methodAccessor]).compile o
@meth = new ValueNode(@meth, [methodAccessor]).compile o
else
[@first, @meth] = @variable.compileReference o, precompile: yes
@first = "(typeof #{@first} === \"function\" ? " @first = "(typeof #{@first} === \"function\" ? "
@last = " : undefined)" @last = " : undefined)"
else if @variable then @meth = @variable.compile o else if @variable then @meth = @variable.compile o

View File

@@ -124,13 +124,17 @@ duration = if options?.animated then 150 else 0
ok duration is 0 ok duration is 0
# function soak # Function soaks.
plus1 = (x) -> x + 1 plus1 = (x) -> x + 1
obj = {
returnThis: -> this
}
ok plus1?(41) is 42 ok plus1?(41) is 42
ok (plus1? 41) is 42 ok (plus1? 41) is 42
ok plus2?(41) is undefined ok plus2?(41) is undefined
ok (plus2? 41) is undefined ok (plus2? 41) is undefined
ok obj.returnThis?() is obj
maybe_close = (f, arg) -> if typeof f is 'function' then () -> f(arg) else -1 maybe_close = (f, arg) -> if typeof f is 'function' then () -> f(arg) else -1