mirror of
https://github.com/jashkenas/coffeescript.git
synced 2022-11-09 12:23:24 -05:00
adding class methods to class definition syntax, using '@'
This commit is contained in:
parent
711dacae5f
commit
177ec92c39
7 changed files with 180 additions and 167 deletions
|
@ -127,6 +127,8 @@
|
|||
return new AssignNode(new ValueNode($1), $3, 'object');
|
||||
}), o("AlphaNumeric ASSIGN Expression", function() {
|
||||
return new AssignNode(new ValueNode($1), $3, 'object');
|
||||
}), o("ThisProperty ASSIGN Expression", function() {
|
||||
return new AssignNode(new ValueNode($1), $3, 'this');
|
||||
}), o("Comment")
|
||||
],
|
||||
// A return statement from a function body.
|
||||
|
|
10
lib/nodes.js
10
lib/nodes.js
|
@ -833,7 +833,7 @@
|
|||
// equivalent syntax tree and compile that, in pieces. You can see the
|
||||
// constructor, property assignments, and inheritance getting built out below.
|
||||
ClassNode.prototype.compile_node = function compile_node(o) {
|
||||
var _a, _b, _c, applied, construct, extension, func, prop, props, returns, val;
|
||||
var _a, _b, _c, access, applied, construct, extension, func, prop, props, pvar, returns, val;
|
||||
extension = this.parent && new ExtendsNode(this.variable, this.parent);
|
||||
constructor = null;
|
||||
props = new Expressions();
|
||||
|
@ -841,13 +841,15 @@
|
|||
_b = this.properties;
|
||||
for (_a = 0, _c = _b.length; _a < _c; _a++) {
|
||||
prop = _b[_a];
|
||||
if (prop.variable && prop.variable.base.value === 'constructor') {
|
||||
pvar = prop.variable;
|
||||
if (pvar && pvar.base.value === 'constructor') {
|
||||
func = prop.value;
|
||||
func.body.push(new ReturnNode(literal('this')));
|
||||
constructor = new AssignNode(this.variable, func);
|
||||
} else {
|
||||
if (prop.variable) {
|
||||
val = new ValueNode(this.variable, [new AccessorNode(prop.variable, 'prototype')]);
|
||||
if (pvar) {
|
||||
access = prop.context === 'this' ? pvar.base.properties[0] : new AccessorNode(pvar, 'prototype');
|
||||
val = new ValueNode(this.variable, [access]);
|
||||
prop = new AssignNode(val, prop.value);
|
||||
}
|
||||
props.push(prop);
|
||||
|
|
306
lib/parser.js
306
lib/parser.js
File diff suppressed because one or more lines are too long
|
@ -304,10 +304,10 @@
|
|||
// In order to accomplish this, move outdents that follow closing parens
|
||||
// inwards, safely. The steps to accomplish this are:
|
||||
// 1. Check that all paired tokens are balanced and in order.
|
||||
// 2. Rewrite the stream with a stack: if you see an '(' or INDENT, add it
|
||||
// to the stack. If you see an ')' or OUTDENT, pop the stack and replace
|
||||
// 2. Rewrite the stream with a stack: if you see an `EXPRESSION_START`, add it
|
||||
// to the stack. If you see an `EXPRESSION_END`, pop the stack and replace
|
||||
// it with the inverse of what we've just popped.
|
||||
// 3. Keep track of "debt" for tokens that we fake, to make sure we end
|
||||
// 3. Keep track of "debt" for tokens that we manufacture, to make sure we end
|
||||
// up balanced in the end.
|
||||
Rewriter.prototype.rewrite_closing_parens = function rewrite_closing_parens() {
|
||||
var _a, debt, key, stack, val;
|
||||
|
|
|
@ -140,6 +140,7 @@ grammar: {
|
|||
AssignObj: [
|
||||
o "Identifier ASSIGN Expression", -> new AssignNode new ValueNode($1), $3, 'object'
|
||||
o "AlphaNumeric ASSIGN Expression", -> new AssignNode new ValueNode($1), $3, 'object'
|
||||
o "ThisProperty ASSIGN Expression", -> new AssignNode new ValueNode($1), $3, 'this'
|
||||
o "Comment"
|
||||
]
|
||||
|
||||
|
@ -194,7 +195,7 @@ grammar: {
|
|||
Splat: [
|
||||
o "Expression . . .", -> new SplatNode $1
|
||||
]
|
||||
|
||||
|
||||
# Variables and properties that can be assigned to.
|
||||
SimpleAssignable: [
|
||||
o "Identifier", -> new ValueNode $1
|
||||
|
@ -202,7 +203,7 @@ grammar: {
|
|||
o "Invocation Accessor", -> new ValueNode $1, [$2]
|
||||
o "ThisProperty"
|
||||
]
|
||||
|
||||
|
||||
# Everything that can be assigned to.
|
||||
Assignable: [
|
||||
o "SimpleAssignable"
|
||||
|
@ -313,7 +314,7 @@ grammar: {
|
|||
o "THIS", -> new ValueNode new LiteralNode 'this'
|
||||
o "@", -> new ValueNode new LiteralNode 'this'
|
||||
]
|
||||
|
||||
|
||||
# A reference to a property on *this*.
|
||||
ThisProperty: [
|
||||
o "@ Identifier", -> new ValueNode new LiteralNode('this'), [new AccessorNode($2)]
|
||||
|
|
|
@ -628,14 +628,16 @@ exports.ClassNode: class ClassNode extends BaseNode
|
|||
o.top: true
|
||||
|
||||
for prop in @properties
|
||||
if prop.variable and prop.variable.base.value is 'constructor'
|
||||
pvar: prop.variable
|
||||
if pvar and pvar.base.value is 'constructor'
|
||||
func: prop.value
|
||||
func.body.push(new ReturnNode(literal('this')))
|
||||
constructor: new AssignNode(@variable, func)
|
||||
else
|
||||
if prop.variable
|
||||
val: new ValueNode(@variable, [new AccessorNode(prop.variable, 'prototype')])
|
||||
prop: new AssignNode(val, prop.value)
|
||||
if pvar
|
||||
access: if prop.context is 'this' then pvar.base.properties[0] else new AccessorNode(pvar, 'prototype')
|
||||
val: new ValueNode(@variable, [access])
|
||||
prop: new AssignNode(val, prop.value)
|
||||
props.push prop
|
||||
|
||||
if not constructor
|
||||
|
|
|
@ -1,6 +1,9 @@
|
|||
class Base
|
||||
func: (string) ->
|
||||
'zero/' + string
|
||||
"zero/$string"
|
||||
|
||||
@static: (string) ->
|
||||
"static/$string"
|
||||
|
||||
class FirstChild extends Base
|
||||
func: (string) ->
|
||||
|
@ -21,6 +24,7 @@ class ThirdChild extends SecondChild
|
|||
result: (new ThirdChild()).func 'four'
|
||||
|
||||
ok result is 'zero/one/two/three/four'
|
||||
ok Base.static('word') is 'static/word'
|
||||
|
||||
|
||||
class TopClass
|
||||
|
|
Loading…
Reference in a new issue