mirror of
https://github.com/jashkenas/coffeescript.git
synced 2022-11-09 12:23:24 -05:00
Refactoring scope to use an array instead of an object, to make the IE bugfix significantly tidier.
This commit is contained in:
parent
7342058e64
commit
8fff6e9baf
5 changed files with 275 additions and 79 deletions
206
lib/nodes.js
206
lib/nodes.js
|
@ -6,6 +6,168 @@
|
||||||
child.prototype = new ctor;
|
child.prototype = new ctor;
|
||||||
if (typeof parent.extended === "function") parent.extended(child);
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
child.__super__ = parent.prototype;
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
|
}, __extends = function(child, parent) {
|
||||||
|
function ctor() { this.constructor = child; }
|
||||||
|
ctor.prototype = parent.prototype;
|
||||||
|
child.prototype = new ctor;
|
||||||
|
if (typeof parent.extended === "function") parent.extended(child);
|
||||||
|
child.__super__ = parent.prototype;
|
||||||
};
|
};
|
||||||
Scope = require('./scope').Scope;
|
Scope = require('./scope').Scope;
|
||||||
_ref = require('./helpers'), compact = _ref.compact, flatten = _ref.flatten, merge = _ref.merge, del = _ref.del, include = _ref.include, starts = _ref.starts, ends = _ref.ends, last = _ref.last;
|
_ref = require('./helpers'), compact = _ref.compact, flatten = _ref.flatten, merge = _ref.merge, del = _ref.del, include = _ref.include, starts = _ref.starts, ends = _ref.ends, last = _ref.last;
|
||||||
|
@ -250,6 +412,7 @@
|
||||||
exports.Literal = (function() {
|
exports.Literal = (function() {
|
||||||
Literal = (function() {
|
Literal = (function() {
|
||||||
function Literal(_arg) {
|
function Literal(_arg) {
|
||||||
|
var _arg;
|
||||||
this.value = _arg;
|
this.value = _arg;
|
||||||
Literal.__super__.constructor.call(this);
|
Literal.__super__.constructor.call(this);
|
||||||
return this;
|
return this;
|
||||||
|
@ -287,6 +450,7 @@
|
||||||
exports.Return = (function() {
|
exports.Return = (function() {
|
||||||
Return = (function() {
|
Return = (function() {
|
||||||
function Return(_arg) {
|
function Return(_arg) {
|
||||||
|
var _arg;
|
||||||
this.expression = _arg;
|
this.expression = _arg;
|
||||||
Return.__super__.constructor.call(this);
|
Return.__super__.constructor.call(this);
|
||||||
return this;
|
return this;
|
||||||
|
@ -322,6 +486,7 @@
|
||||||
exports.Value = (function() {
|
exports.Value = (function() {
|
||||||
Value = (function() {
|
Value = (function() {
|
||||||
function Value(_arg, _arg2, tag) {
|
function Value(_arg, _arg2, tag) {
|
||||||
|
var _arg, _arg2;
|
||||||
this.properties = _arg2;
|
this.properties = _arg2;
|
||||||
this.base = _arg;
|
this.base = _arg;
|
||||||
Value.__super__.constructor.call(this);
|
Value.__super__.constructor.call(this);
|
||||||
|
@ -443,6 +608,7 @@
|
||||||
exports.Comment = (function() {
|
exports.Comment = (function() {
|
||||||
Comment = (function() {
|
Comment = (function() {
|
||||||
function Comment(_arg) {
|
function Comment(_arg) {
|
||||||
|
var _arg;
|
||||||
this.comment = _arg;
|
this.comment = _arg;
|
||||||
Comment.__super__.constructor.call(this);
|
Comment.__super__.constructor.call(this);
|
||||||
return this;
|
return this;
|
||||||
|
@ -460,6 +626,7 @@
|
||||||
exports.Call = (function() {
|
exports.Call = (function() {
|
||||||
Call = (function() {
|
Call = (function() {
|
||||||
function Call(variable, _arg, _arg2) {
|
function Call(variable, _arg, _arg2) {
|
||||||
|
var _arg, _arg2;
|
||||||
this.soakNode = _arg2;
|
this.soakNode = _arg2;
|
||||||
this.args = _arg;
|
this.args = _arg;
|
||||||
Call.__super__.constructor.call(this);
|
Call.__super__.constructor.call(this);
|
||||||
|
@ -598,6 +765,7 @@
|
||||||
exports.Extends = (function() {
|
exports.Extends = (function() {
|
||||||
Extends = (function() {
|
Extends = (function() {
|
||||||
function Extends(_arg, _arg2) {
|
function Extends(_arg, _arg2) {
|
||||||
|
var _arg, _arg2;
|
||||||
this.parent = _arg2;
|
this.parent = _arg2;
|
||||||
this.child = _arg;
|
this.child = _arg;
|
||||||
Extends.__super__.constructor.call(this);
|
Extends.__super__.constructor.call(this);
|
||||||
|
@ -617,6 +785,7 @@
|
||||||
exports.Accessor = (function() {
|
exports.Accessor = (function() {
|
||||||
Accessor = (function() {
|
Accessor = (function() {
|
||||||
function Accessor(_arg, tag) {
|
function Accessor(_arg, tag) {
|
||||||
|
var _arg;
|
||||||
this.name = _arg;
|
this.name = _arg;
|
||||||
Accessor.__super__.constructor.call(this);
|
Accessor.__super__.constructor.call(this);
|
||||||
this.prototype = tag === 'prototype' ? '.prototype' : '';
|
this.prototype = tag === 'prototype' ? '.prototype' : '';
|
||||||
|
@ -639,6 +808,7 @@
|
||||||
exports.Index = (function() {
|
exports.Index = (function() {
|
||||||
Index = (function() {
|
Index = (function() {
|
||||||
function Index(_arg) {
|
function Index(_arg) {
|
||||||
|
var _arg;
|
||||||
this.index = _arg;
|
this.index = _arg;
|
||||||
Index.__super__.constructor.call(this);
|
Index.__super__.constructor.call(this);
|
||||||
return this;
|
return this;
|
||||||
|
@ -661,6 +831,7 @@
|
||||||
exports.Range = (function() {
|
exports.Range = (function() {
|
||||||
Range = (function() {
|
Range = (function() {
|
||||||
function Range(_arg, _arg2, tag) {
|
function Range(_arg, _arg2, tag) {
|
||||||
|
var _arg, _arg2;
|
||||||
this.to = _arg2;
|
this.to = _arg2;
|
||||||
this.from = _arg;
|
this.from = _arg;
|
||||||
Range.__super__.constructor.call(this);
|
Range.__super__.constructor.call(this);
|
||||||
|
@ -749,6 +920,7 @@
|
||||||
exports.Slice = (function() {
|
exports.Slice = (function() {
|
||||||
Slice = (function() {
|
Slice = (function() {
|
||||||
function Slice(_arg) {
|
function Slice(_arg) {
|
||||||
|
var _arg;
|
||||||
this.range = _arg;
|
this.range = _arg;
|
||||||
Slice.__super__.constructor.call(this);
|
Slice.__super__.constructor.call(this);
|
||||||
return this;
|
return this;
|
||||||
|
@ -781,7 +953,7 @@
|
||||||
__extends(ObjectLiteral, Base);
|
__extends(ObjectLiteral, Base);
|
||||||
ObjectLiteral.prototype.children = ['properties'];
|
ObjectLiteral.prototype.children = ['properties'];
|
||||||
ObjectLiteral.prototype.compileNode = function(o) {
|
ObjectLiteral.prototype.compileNode = function(o) {
|
||||||
var _i, _len, _ref2, _result, i, indent, join, lastNoncom, nonComments, obj, prop, props, top;
|
var _i, _len, _len2, _ref2, _ref3, _result, _result2, i, indent, join, lastNoncom, nonComments, obj, prop, props, top;
|
||||||
top = del(o, 'top');
|
top = del(o, 'top');
|
||||||
o.indent = this.idt(1);
|
o.indent = this.idt(1);
|
||||||
nonComments = (function() {
|
nonComments = (function() {
|
||||||
|
@ -796,10 +968,10 @@
|
||||||
}).call(this);
|
}).call(this);
|
||||||
lastNoncom = last(nonComments);
|
lastNoncom = last(nonComments);
|
||||||
props = (function() {
|
props = (function() {
|
||||||
_result = [];
|
_result2 = [];
|
||||||
for (i = 0, _len = (_ref2 = this.properties).length; i < _len; i++) {
|
for (i = 0, _len2 = (_ref3 = this.properties).length; i < _len2; i++) {
|
||||||
prop = _ref2[i];
|
prop = _ref3[i];
|
||||||
_result.push((function() {
|
_result2.push((function() {
|
||||||
join = i === this.properties.length - 1 ? '' : (prop === lastNoncom || prop instanceof Comment ? '\n' : ',\n');
|
join = i === this.properties.length - 1 ? '' : (prop === lastNoncom || prop instanceof Comment ? '\n' : ',\n');
|
||||||
indent = prop instanceof Comment ? '' : this.idt(1);
|
indent = prop instanceof Comment ? '' : this.idt(1);
|
||||||
if (prop instanceof Value && prop.tags["this"]) {
|
if (prop instanceof Value && prop.tags["this"]) {
|
||||||
|
@ -810,7 +982,7 @@
|
||||||
return indent + prop.compile(o) + join;
|
return indent + prop.compile(o) + join;
|
||||||
}).call(this));
|
}).call(this));
|
||||||
}
|
}
|
||||||
return _result;
|
return _result2;
|
||||||
}).call(this);
|
}).call(this);
|
||||||
props = props.join('');
|
props = props.join('');
|
||||||
obj = ("{" + (props ? '\n' + props + '\n' + this.idt() : '') + "}");
|
obj = ("{" + (props ? '\n' + props + '\n' + this.idt() : '') + "}");
|
||||||
|
@ -831,6 +1003,7 @@
|
||||||
exports.ArrayLiteral = (function() {
|
exports.ArrayLiteral = (function() {
|
||||||
ArrayLiteral = (function() {
|
ArrayLiteral = (function() {
|
||||||
function ArrayLiteral(_arg) {
|
function ArrayLiteral(_arg) {
|
||||||
|
var _arg;
|
||||||
this.objects = _arg;
|
this.objects = _arg;
|
||||||
ArrayLiteral.__super__.constructor.call(this);
|
ArrayLiteral.__super__.constructor.call(this);
|
||||||
this.objects || (this.objects = []);
|
this.objects || (this.objects = []);
|
||||||
|
@ -876,6 +1049,7 @@
|
||||||
exports.Class = (function() {
|
exports.Class = (function() {
|
||||||
Class = (function() {
|
Class = (function() {
|
||||||
function Class(variable, _arg, _arg2) {
|
function Class(variable, _arg, _arg2) {
|
||||||
|
var _arg, _arg2;
|
||||||
this.properties = _arg2;
|
this.properties = _arg2;
|
||||||
this.parent = _arg;
|
this.parent = _arg;
|
||||||
Class.__super__.constructor.call(this);
|
Class.__super__.constructor.call(this);
|
||||||
|
@ -974,6 +1148,7 @@
|
||||||
exports.Assign = (function() {
|
exports.Assign = (function() {
|
||||||
Assign = (function() {
|
Assign = (function() {
|
||||||
function Assign(_arg, _arg2, _arg3) {
|
function Assign(_arg, _arg2, _arg3) {
|
||||||
|
var _arg, _arg2, _arg3;
|
||||||
this.context = _arg3;
|
this.context = _arg3;
|
||||||
this.value = _arg2;
|
this.value = _arg2;
|
||||||
this.variable = _arg;
|
this.variable = _arg;
|
||||||
|
@ -1107,6 +1282,7 @@
|
||||||
exports.Code = (function() {
|
exports.Code = (function() {
|
||||||
Code = (function() {
|
Code = (function() {
|
||||||
function Code(_arg, _arg2, tag) {
|
function Code(_arg, _arg2, tag) {
|
||||||
|
var _arg, _arg2;
|
||||||
this.body = _arg2;
|
this.body = _arg2;
|
||||||
this.params = _arg;
|
this.params = _arg;
|
||||||
Code.__super__.constructor.call(this);
|
Code.__super__.constructor.call(this);
|
||||||
|
@ -1123,7 +1299,7 @@
|
||||||
__extends(Code, Base);
|
__extends(Code, Base);
|
||||||
Code.prototype.children = ['params', 'body'];
|
Code.prototype.children = ['params', 'body'];
|
||||||
Code.prototype.compileNode = function(o) {
|
Code.prototype.compileNode = function(o) {
|
||||||
var _i, _len, _len2, _ref2, _ref3, _result, close, code, comm, empty, func, i, open, param, params, sharedScope, splat, top, value;
|
var _i, _j, _len, _len2, _len3, _ref2, _ref3, _result, close, code, comm, empty, func, i, open, param, params, sharedScope, splat, top, value;
|
||||||
sharedScope = del(o, 'sharedScope');
|
sharedScope = del(o, 'sharedScope');
|
||||||
top = del(o, 'top');
|
top = del(o, 'top');
|
||||||
o.scope = sharedScope || new Scope(o.scope, this.body, this);
|
o.scope = sharedScope || new Scope(o.scope, this.body, this);
|
||||||
|
@ -1171,8 +1347,8 @@
|
||||||
if (!(empty || this.noReturn)) {
|
if (!(empty || this.noReturn)) {
|
||||||
this.body.makeReturn();
|
this.body.makeReturn();
|
||||||
}
|
}
|
||||||
for (_i = 0, _len2 = params.length; _i < _len2; _i++) {
|
for (_j = 0, _len3 = params.length; _j < _len3; _j++) {
|
||||||
param = params[_i];
|
param = params[_j];
|
||||||
(o.scope.parameter(param));
|
(o.scope.parameter(param));
|
||||||
}
|
}
|
||||||
comm = this.comment ? this.comment.compile(o) + '\n' : '';
|
comm = this.comment ? this.comment.compile(o) + '\n' : '';
|
||||||
|
@ -1197,6 +1373,7 @@
|
||||||
exports.Param = (function() {
|
exports.Param = (function() {
|
||||||
Param = (function() {
|
Param = (function() {
|
||||||
function Param(_arg, _arg2, _arg3) {
|
function Param(_arg, _arg2, _arg3) {
|
||||||
|
var _arg, _arg2, _arg3;
|
||||||
this.splat = _arg3;
|
this.splat = _arg3;
|
||||||
this.attach = _arg2;
|
this.attach = _arg2;
|
||||||
this.name = _arg;
|
this.name = _arg;
|
||||||
|
@ -1465,6 +1642,7 @@
|
||||||
exports.In = (function() {
|
exports.In = (function() {
|
||||||
In = (function() {
|
In = (function() {
|
||||||
function In(_arg, _arg2) {
|
function In(_arg, _arg2) {
|
||||||
|
var _arg, _arg2;
|
||||||
this.array = _arg2;
|
this.array = _arg2;
|
||||||
this.object = _arg;
|
this.object = _arg;
|
||||||
In.__super__.constructor.call(this);
|
In.__super__.constructor.call(this);
|
||||||
|
@ -1503,6 +1681,7 @@
|
||||||
exports.Try = (function() {
|
exports.Try = (function() {
|
||||||
Try = (function() {
|
Try = (function() {
|
||||||
function Try(_arg, _arg2, _arg3, _arg4) {
|
function Try(_arg, _arg2, _arg3, _arg4) {
|
||||||
|
var _arg, _arg2, _arg3, _arg4;
|
||||||
this.ensure = _arg4;
|
this.ensure = _arg4;
|
||||||
this.recovery = _arg3;
|
this.recovery = _arg3;
|
||||||
this.error = _arg2;
|
this.error = _arg2;
|
||||||
|
@ -1539,6 +1718,7 @@
|
||||||
exports.Throw = (function() {
|
exports.Throw = (function() {
|
||||||
Throw = (function() {
|
Throw = (function() {
|
||||||
function Throw(_arg) {
|
function Throw(_arg) {
|
||||||
|
var _arg;
|
||||||
this.expression = _arg;
|
this.expression = _arg;
|
||||||
Throw.__super__.constructor.call(this);
|
Throw.__super__.constructor.call(this);
|
||||||
return this;
|
return this;
|
||||||
|
@ -1557,6 +1737,7 @@
|
||||||
exports.Existence = (function() {
|
exports.Existence = (function() {
|
||||||
Existence = (function() {
|
Existence = (function() {
|
||||||
function Existence(_arg) {
|
function Existence(_arg) {
|
||||||
|
var _arg;
|
||||||
this.expression = _arg;
|
this.expression = _arg;
|
||||||
Existence.__super__.constructor.call(this);
|
Existence.__super__.constructor.call(this);
|
||||||
return this;
|
return this;
|
||||||
|
@ -1576,6 +1757,7 @@
|
||||||
exports.Parens = (function() {
|
exports.Parens = (function() {
|
||||||
Parens = (function() {
|
Parens = (function() {
|
||||||
function Parens(_arg) {
|
function Parens(_arg) {
|
||||||
|
var _arg;
|
||||||
this.expression = _arg;
|
this.expression = _arg;
|
||||||
Parens.__super__.constructor.call(this);
|
Parens.__super__.constructor.call(this);
|
||||||
return this;
|
return this;
|
||||||
|
@ -1612,7 +1794,7 @@
|
||||||
exports.For = (function() {
|
exports.For = (function() {
|
||||||
For = (function() {
|
For = (function() {
|
||||||
function For(_arg, source, _arg2, _arg3) {
|
function For(_arg, source, _arg2, _arg3) {
|
||||||
var _ref2;
|
var _arg, _arg2, _arg3, _ref2;
|
||||||
this.index = _arg3;
|
this.index = _arg3;
|
||||||
this.name = _arg2;
|
this.name = _arg2;
|
||||||
this.body = _arg;
|
this.body = _arg;
|
||||||
|
@ -1771,6 +1953,7 @@
|
||||||
exports.Switch = (function() {
|
exports.Switch = (function() {
|
||||||
Switch = (function() {
|
Switch = (function() {
|
||||||
function Switch(_arg, _arg2, _arg3) {
|
function Switch(_arg, _arg2, _arg3) {
|
||||||
|
var _arg, _arg2, _arg3;
|
||||||
this.otherwise = _arg3;
|
this.otherwise = _arg3;
|
||||||
this.cases = _arg2;
|
this.cases = _arg2;
|
||||||
this.subject = _arg;
|
this.subject = _arg;
|
||||||
|
@ -1827,6 +2010,7 @@
|
||||||
exports.If = (function() {
|
exports.If = (function() {
|
||||||
If = (function() {
|
If = (function() {
|
||||||
function If(condition, _arg, tags) {
|
function If(condition, _arg, tags) {
|
||||||
|
var _arg;
|
||||||
this.body = _arg;
|
this.body = _arg;
|
||||||
this.tags = tags || (tags = {});
|
this.tags = tags || (tags = {});
|
||||||
this.condition = tags.invert ? condition.invert() : condition;
|
this.condition = tags.invert ? condition.invert() : condition;
|
||||||
|
@ -1962,7 +2146,7 @@
|
||||||
UTILITIES = {
|
UTILITIES = {
|
||||||
"extends": 'function(child, parent) {\n function ctor() { this.constructor = child; }\n ctor.prototype = parent.prototype;\n child.prototype = new ctor;\n if (typeof parent.extended === "function") parent.extended(child);\n child.__super__ = parent.prototype;\n}',
|
"extends": 'function(child, parent) {\n function ctor() { this.constructor = child; }\n ctor.prototype = parent.prototype;\n child.prototype = new ctor;\n if (typeof parent.extended === "function") parent.extended(child);\n child.__super__ = parent.prototype;\n}',
|
||||||
bind: 'function(func, context) {\n return function() { return func.apply(context, arguments); };\n}',
|
bind: 'function(func, context) {\n return function() { return func.apply(context, arguments); };\n}',
|
||||||
inArray: '(function() {\n var indexOf = Array.prototype.indexOf || function(item) {\n var i = this.length; while (i--) if (this[i] === item) return i;\n return -1;\n };\n return function(item, array) { return indexOf.call(array, item) > -1; };\n})();',
|
inArray: '(function() {\n var indexOf = Array.prototype.indexOf || function(item) {\n var i = this.length; while (i--) if (this[i] === item) return i;\n return -1;\n };\n return function(item, array) { return indexOf.call(array, item) > -1; };\n})()',
|
||||||
hasProp: 'Object.prototype.hasOwnProperty',
|
hasProp: 'Object.prototype.hasOwnProperty',
|
||||||
slice: 'Array.prototype.slice'
|
slice: 'Array.prototype.slice'
|
||||||
};
|
};
|
||||||
|
|
|
@ -8,6 +8,7 @@
|
||||||
return Rewriter;
|
return Rewriter;
|
||||||
})();
|
})();
|
||||||
exports.Rewriter.prototype.rewrite = function(_arg) {
|
exports.Rewriter.prototype.rewrite = function(_arg) {
|
||||||
|
var _arg;
|
||||||
this.tokens = _arg;
|
this.tokens = _arg;
|
||||||
this.adjustComments();
|
this.adjustComments();
|
||||||
this.removeLeadingNewlines();
|
this.removeLeadingNewlines();
|
||||||
|
|
104
lib/scope.js
104
lib/scope.js
|
@ -1,16 +1,19 @@
|
||||||
(function() {
|
(function() {
|
||||||
var Scope, _ref, extend, last;
|
var Scope, _ref, extend, last;
|
||||||
var __hasProp = Object.prototype.hasOwnProperty;
|
|
||||||
_ref = require('./helpers'), extend = _ref.extend, last = _ref.last;
|
_ref = require('./helpers'), extend = _ref.extend, last = _ref.last;
|
||||||
exports.Scope = (function() {
|
exports.Scope = (function() {
|
||||||
Scope = (function() {
|
Scope = (function() {
|
||||||
function Scope(_arg, _arg2, _arg3) {
|
function Scope(_arg, _arg2, _arg3) {
|
||||||
|
var _arg, _arg2, _arg3;
|
||||||
this.method = _arg3;
|
this.method = _arg3;
|
||||||
this.expressions = _arg2;
|
this.expressions = _arg2;
|
||||||
this.parent = _arg;
|
this.parent = _arg;
|
||||||
this.variables = {
|
this.variables = [
|
||||||
'arguments': 'arguments'
|
{
|
||||||
};
|
name: 'arguments',
|
||||||
|
type: 'arguments'
|
||||||
|
}
|
||||||
|
];
|
||||||
if (this.parent) {
|
if (this.parent) {
|
||||||
this.garbage = this.parent.garbage;
|
this.garbage = this.parent.garbage;
|
||||||
} else {
|
} else {
|
||||||
|
@ -26,13 +29,22 @@
|
||||||
return this.garbage.push([]);
|
return this.garbage.push([]);
|
||||||
};
|
};
|
||||||
Scope.prototype.endLevel = function() {
|
Scope.prototype.endLevel = function() {
|
||||||
var _i, _len, _ref2, _result, name, vars;
|
var _i, _len, _len2, _ref2, _result, garbage, i, v, vars;
|
||||||
vars = this.variables;
|
vars = this.variables;
|
||||||
_result = [];
|
_result = [];
|
||||||
for (_i = 0, _len = (_ref2 = this.garbage.pop()).length; _i < _len; _i++) {
|
for (_i = 0, _len = (_ref2 = this.garbage.pop()).length; _i < _len; _i++) {
|
||||||
name = _ref2[_i];
|
garbage = _ref2[_i];
|
||||||
if (vars[name] === 'var') {
|
if (this.type(garbage) === 'var') {
|
||||||
_result.push(vars[name] = 'reuse');
|
for (i = 0, _len2 = vars.length; i < _len2; i++) {
|
||||||
|
v = vars[i];
|
||||||
|
if (v.name === garbage.name) {
|
||||||
|
vars.splice(i, 1, {
|
||||||
|
name: garbage.name,
|
||||||
|
type: 'reuse'
|
||||||
|
});
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return _result;
|
return _result;
|
||||||
|
@ -41,25 +53,31 @@
|
||||||
if (this.check(name, options)) {
|
if (this.check(name, options)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
this.variables[name] = 'var';
|
this.variables.push({
|
||||||
|
name: name,
|
||||||
|
type: 'var'
|
||||||
|
});
|
||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
Scope.prototype.any = function(fn) {
|
Scope.prototype.any = function(fn) {
|
||||||
var _i, _len, _ref2, v;
|
var _i, _len, _ref2, v;
|
||||||
for (_i = 0, _len = (_ref2 = this.allVariables()).length; _i < _len; _i++) {
|
for (_i = 0, _len = (_ref2 = this.variables).length; _i < _len; _i++) {
|
||||||
v = _ref2[_i];
|
v = _ref2[_i];
|
||||||
if (fn(v[0], v[1])) {
|
if (fn(v.name, v.type)) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
};
|
};
|
||||||
Scope.prototype.parameter = function(name) {
|
Scope.prototype.parameter = function(name) {
|
||||||
return (this.variables[name] = 'param');
|
return this.variables.push({
|
||||||
|
name: name,
|
||||||
|
type: 'param'
|
||||||
|
});
|
||||||
};
|
};
|
||||||
Scope.prototype.check = function(name, options) {
|
Scope.prototype.check = function(name, options) {
|
||||||
var _ref2, immediate;
|
var _ref2, immediate;
|
||||||
immediate = Object.prototype.hasOwnProperty.call(this.variables, name);
|
immediate = !!this.type(name);
|
||||||
if (immediate || ((options != null) ? options.immediate : undefined)) {
|
if (immediate || ((options != null) ? options.immediate : undefined)) {
|
||||||
return immediate;
|
return immediate;
|
||||||
}
|
}
|
||||||
|
@ -68,46 +86,40 @@
|
||||||
Scope.prototype.temporary = function(type, index) {
|
Scope.prototype.temporary = function(type, index) {
|
||||||
return type.length > 1 ? '_' + type + (index > 1 ? index : '') : '_' + (index + parseInt(type, 36)).toString(36).replace(/\d/g, 'a');
|
return type.length > 1 ? '_' + type + (index > 1 ? index : '') : '_' + (index + parseInt(type, 36)).toString(36).replace(/\d/g, 'a');
|
||||||
};
|
};
|
||||||
|
Scope.prototype.type = function(name) {
|
||||||
|
var _i, _len, _ref2, v;
|
||||||
|
for (_i = 0, _len = (_ref2 = this.variables).length; _i < _len; _i++) {
|
||||||
|
v = _ref2[_i];
|
||||||
|
if (v.name === name) {
|
||||||
|
return v.type;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
};
|
||||||
Scope.prototype.freeVariable = function(type) {
|
Scope.prototype.freeVariable = function(type) {
|
||||||
var index, temp;
|
var index, temp;
|
||||||
index = 0;
|
index = 0;
|
||||||
while (this.check(temp = this.temporary(type, index)) && this.variables[temp] !== 'reuse') {
|
while (this.check(temp = this.temporary(type, index)) && this.type(temp) !== 'reuse') {
|
||||||
index++;
|
index++;
|
||||||
}
|
}
|
||||||
this.variables[temp] = 'var';
|
this.variables.push({
|
||||||
|
name: temp,
|
||||||
|
type: 'var'
|
||||||
|
});
|
||||||
if (this.garbage.length) {
|
if (this.garbage.length) {
|
||||||
last(this.garbage).push(temp);
|
last(this.garbage).push(temp);
|
||||||
}
|
}
|
||||||
return temp;
|
return temp;
|
||||||
};
|
};
|
||||||
Scope.prototype.assign = function(name, value) {
|
Scope.prototype.assign = function(name, value) {
|
||||||
return (this.variables[name] = {
|
return this.variables.push({
|
||||||
value: value,
|
name: name,
|
||||||
assigned: true
|
type: {
|
||||||
|
value: value,
|
||||||
|
assigned: true
|
||||||
|
}
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
Scope.prototype.allVariables = function() {
|
|
||||||
var _i, _len, _ref2, _result, k, v, vars;
|
|
||||||
vars = (function() {
|
|
||||||
_result = [];
|
|
||||||
for (v in _ref2 = this.variables) {
|
|
||||||
if (!__hasProp.call(_ref2, v)) continue;
|
|
||||||
k = _ref2[v];
|
|
||||||
_result.push([v, k]);
|
|
||||||
}
|
|
||||||
return _result;
|
|
||||||
}).call(this);
|
|
||||||
return v.__defineGetter__ ? vars : vars.concat((function() {
|
|
||||||
_result = [];
|
|
||||||
for (_i = 0, _len = (_ref2 = 'toString toLocaleString\nhasOwnProperty valueOf constructor propertyIsEnumerable\nisPrototypeOf'.split(' ')).length; _i < _len; _i++) {
|
|
||||||
v = _ref2[_i];
|
|
||||||
if (this.variables.hasOwnProperty(v)) {
|
|
||||||
_result.push([v, this.variables[v]]);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return _result;
|
|
||||||
}).call(this));
|
|
||||||
};
|
|
||||||
Scope.prototype.hasDeclarations = function(body) {
|
Scope.prototype.hasDeclarations = function(body) {
|
||||||
return body === this.expressions && this.any(function(k, val) {
|
return body === this.expressions && this.any(function(k, val) {
|
||||||
return (val === 'var' || val === 'reuse');
|
return (val === 'var' || val === 'reuse');
|
||||||
|
@ -122,10 +134,10 @@
|
||||||
var _i, _len, _ref2, _ref3, _result, v;
|
var _i, _len, _ref2, _ref3, _result, v;
|
||||||
return (function() {
|
return (function() {
|
||||||
_result = [];
|
_result = [];
|
||||||
for (_i = 0, _len = (_ref2 = this.allVariables()).length; _i < _len; _i++) {
|
for (_i = 0, _len = (_ref2 = this.variables).length; _i < _len; _i++) {
|
||||||
v = _ref2[_i];
|
v = _ref2[_i];
|
||||||
if (((_ref3 = v[1]) === 'var' || _ref3 === 'reuse')) {
|
if (((_ref3 = v.type) === 'var' || _ref3 === 'reuse')) {
|
||||||
_result.push(v[0]);
|
_result.push(v.name);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return _result;
|
return _result;
|
||||||
|
@ -134,10 +146,10 @@
|
||||||
Scope.prototype.assignedVariables = function() {
|
Scope.prototype.assignedVariables = function() {
|
||||||
var _i, _len, _ref2, _result, v;
|
var _i, _len, _ref2, _result, v;
|
||||||
_result = [];
|
_result = [];
|
||||||
for (_i = 0, _len = (_ref2 = this.allVariables()).length; _i < _len; _i++) {
|
for (_i = 0, _len = (_ref2 = this.variables).length; _i < _len; _i++) {
|
||||||
v = _ref2[_i];
|
v = _ref2[_i];
|
||||||
if (v[1].assigned) {
|
if (v.type.assigned) {
|
||||||
_result.push("" + (v[0]) + " = " + (v[1].value));
|
_result.push("" + (v.name) + " = " + (v.type.value));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return _result;
|
return _result;
|
||||||
|
|
|
@ -1679,7 +1679,7 @@ UTILITIES =
|
||||||
return -1;
|
return -1;
|
||||||
};
|
};
|
||||||
return function(item, array) { return indexOf.call(array, item) > -1; };
|
return function(item, array) { return indexOf.call(array, item) > -1; };
|
||||||
})();
|
})()
|
||||||
'''
|
'''
|
||||||
|
|
||||||
# Shortcuts to speed up the lookup time for native functions.
|
# Shortcuts to speed up the lookup time for native functions.
|
||||||
|
|
|
@ -18,7 +18,7 @@ exports.Scope = class Scope
|
||||||
# where it should declare its variables, and a reference to the function that
|
# where it should declare its variables, and a reference to the function that
|
||||||
# it wraps.
|
# it wraps.
|
||||||
constructor: (@parent, @expressions, @method) ->
|
constructor: (@parent, @expressions, @method) ->
|
||||||
@variables = {'arguments'}
|
@variables = [{name: 'arguments', type: 'arguments'}]
|
||||||
if @parent
|
if @parent
|
||||||
@garbage = @parent.garbage
|
@garbage = @parent.garbage
|
||||||
else
|
else
|
||||||
|
@ -33,30 +33,33 @@ exports.Scope = class Scope
|
||||||
# variables in current level from scope.
|
# variables in current level from scope.
|
||||||
endLevel: ->
|
endLevel: ->
|
||||||
vars = @variables
|
vars = @variables
|
||||||
(vars[name] = 'reuse') for name in @garbage.pop() when vars[name] is 'var'
|
for garbage in @garbage.pop() when @type(garbage) is 'var'
|
||||||
|
for v, i in vars when v.name is garbage.name
|
||||||
|
vars.splice(i, 1, {name: garbage.name, type: 'reuse'})
|
||||||
|
break
|
||||||
|
|
||||||
# Look up a variable name in lexical scope, and declare it if it does not
|
# Look up a variable name in lexical scope, and declare it if it does not
|
||||||
# already exist.
|
# already exist.
|
||||||
find: (name, options) ->
|
find: (name, options) ->
|
||||||
return true if @check name, options
|
return true if @check name, options
|
||||||
@variables[name] = 'var'
|
@variables.push {name, type: 'var'}
|
||||||
false
|
false
|
||||||
|
|
||||||
# Test variables and return true the first time fn(v, k) returns true
|
# Test variables and return true the first time fn(v, k) returns true
|
||||||
any: (fn) ->
|
any: (fn) ->
|
||||||
for v in @allVariables() when fn(v[0], v[1])
|
for v in @variables when fn v.name, v.type
|
||||||
return true
|
return true
|
||||||
return false
|
return false
|
||||||
|
|
||||||
# Reserve a variable name as originating from a function parameter for this
|
# Reserve a variable name as originating from a function parameter for this
|
||||||
# scope. No `var` required for internal references.
|
# scope. No `var` required for internal references.
|
||||||
parameter: (name) ->
|
parameter: (name) ->
|
||||||
@variables[name] = 'param'
|
@variables.push {name, type: 'param'}
|
||||||
|
|
||||||
# Just check to see if a variable has already been declared, without reserving,
|
# Just check to see if a variable has already been declared, without reserving,
|
||||||
# walks up to the root scope.
|
# walks up to the root scope.
|
||||||
check: (name, options) ->
|
check: (name, options) ->
|
||||||
immediate = Object::hasOwnProperty.call @variables, name
|
immediate = !!@type(name)
|
||||||
return immediate if immediate or options?.immediate
|
return immediate if immediate or options?.immediate
|
||||||
!!@parent?.check name
|
!!@parent?.check name
|
||||||
|
|
||||||
|
@ -66,29 +69,25 @@ exports.Scope = class Scope
|
||||||
'_' + type + if index > 1 then index else ''
|
'_' + type + if index > 1 then index else ''
|
||||||
else
|
else
|
||||||
'_' + (index + parseInt type, 36).toString(36).replace /\d/g, 'a'
|
'_' + (index + parseInt type, 36).toString(36).replace /\d/g, 'a'
|
||||||
|
|
||||||
|
# Gets the type of a variable.
|
||||||
|
type: (name) ->
|
||||||
|
for v in @variables when v.name is name then return v.type
|
||||||
|
null
|
||||||
|
|
||||||
# If we need to store an intermediate result, find an available name for a
|
# If we need to store an intermediate result, find an available name for a
|
||||||
# compiler-generated variable. `_var`, `_var2`, and so on...
|
# compiler-generated variable. `_var`, `_var2`, and so on...
|
||||||
freeVariable: (type) ->
|
freeVariable: (type) ->
|
||||||
index = 0
|
index = 0
|
||||||
index++ while @check(temp = @temporary type, index) and @variables[temp] isnt 'reuse'
|
index++ while @check(temp = @temporary type, index) and @type(temp) isnt 'reuse'
|
||||||
@variables[temp] = 'var'
|
@variables.push {name: temp, type: 'var'}
|
||||||
last(@garbage).push temp if @garbage.length
|
last(@garbage).push temp if @garbage.length
|
||||||
temp
|
temp
|
||||||
|
|
||||||
# Ensure that an assignment is made at the top of this scope
|
# Ensure that an assignment is made at the top of this scope
|
||||||
# (or at the top-level scope, if requested).
|
# (or at the top-level scope, if requested).
|
||||||
assign: (name, value) ->
|
assign: (name, value) ->
|
||||||
@variables[name] = value: value, assigned: true
|
@variables.push {name, type: { value: value, assigned: true }}
|
||||||
|
|
||||||
# Gets around a bug in IE where it won't enumerate over redefined prototype properties.
|
|
||||||
allVariables: ->
|
|
||||||
vars = [v, k] for v, k of @variables
|
|
||||||
if v.__defineGetter__ then vars
|
|
||||||
else vars.concat(for v in '''toString toLocaleString
|
|
||||||
hasOwnProperty valueOf constructor propertyIsEnumerable
|
|
||||||
isPrototypeOf'''.split(' ') when @variables.hasOwnProperty v
|
|
||||||
[v, @variables[v]])
|
|
||||||
|
|
||||||
# Does this scope reference any variables that need to be declared in the
|
# Does this scope reference any variables that need to be declared in the
|
||||||
# given function body?
|
# given function body?
|
||||||
|
@ -102,12 +101,12 @@ exports.Scope = class Scope
|
||||||
|
|
||||||
# Return the list of variables first declared in this scope.
|
# Return the list of variables first declared in this scope.
|
||||||
declaredVariables: ->
|
declaredVariables: ->
|
||||||
(v[0] for v in @allVariables() when v[1] in ['var', 'reuse']).sort()
|
(v.name for v in @variables when v.type in ['var', 'reuse']).sort()
|
||||||
|
|
||||||
# Return the list of assignments that are supposed to be made at the top
|
# Return the list of assignments that are supposed to be made at the top
|
||||||
# of this scope.
|
# of this scope.
|
||||||
assignedVariables: ->
|
assignedVariables: ->
|
||||||
"#{v[0]} = #{v[1].value}" for v in @allVariables() when v[1].assigned
|
"#{v.name} = #{v.type.value}" for v in @variables when v.type.assigned
|
||||||
|
|
||||||
# Compile the JavaScript for all of the variable declarations in this scope.
|
# Compile the JavaScript for all of the variable declarations in this scope.
|
||||||
compiledDeclarations: ->
|
compiledDeclarations: ->
|
||||||
|
|
Loading…
Add table
Reference in a new issue