Skip to content
This repository has been archived by the owner on Dec 24, 2023. It is now read-only.

Commit

Permalink
Added static typing
Browse files Browse the repository at this point in the history
  • Loading branch information
deathbeam committed May 17, 2016
1 parent 17cd839 commit 62ceb64
Show file tree
Hide file tree
Showing 6 changed files with 26 additions and 12 deletions.
4 changes: 3 additions & 1 deletion examples/classes.spoon
Original file line number Diff line number Diff line change
@@ -1,10 +1,12 @@
#!/usr/bin/env coffee

class Person
name as String

new = name ->
@name = name

greet = ->
print "Hello, #{@name}!"
trace "Hello, #{@name}!"

Person("Tomas").greet!
14 changes: 7 additions & 7 deletions lib/spoon/compiler.rb
Original file line number Diff line number Diff line change
Expand Up @@ -202,22 +202,22 @@ def compile
left = children.shift
right = children.shift

if @node.option :is_assign
if @node.option(:is_assign) || @node.option(:is_typed)
if left.option :is_array
assign_name = "__assign#{@@assign_counter}"
@content << "var #{assign_name} = #{compile_next(right)};\n"
@content << "var #{assign_name} #{operator} #{compile_next(right)};\n"
@@assign_counter += 1

left.children.each_with_index do |child, index|
child_name = compile_next(child)
@content << @parent.tab
scope_name(child)
@content << "#{child_name} = #{assign_name}[#{index}]"
@content << "#{child_name} #{operator} #{assign_name}[#{index}]"
@content << ";\n" unless child.equal? left.children.last
end
elsif left.option :is_hash
assign_name = "__assign#{@@assign_counter}"
@content << "var #{assign_name} = #{compile_next(right)};\n"
@content << "var #{assign_name} #{operator} #{compile_next(right)};\n"
@@assign_counter += 1

left.children.each do |child|
Expand All @@ -228,7 +228,7 @@ def compile
child_name = compile_next(child_children.shift)
@content << @parent.tab
scope_name(child_alias_node)
@content << "#{child_alias} = #{assign_name}.#{child_name}"
@content << "#{child_alias} #{operator} #{assign_name}.#{child_name}"
@content << ";\n" unless child.equal? left.children.last
end
elsif @parent.parent.node.type == :class
Expand All @@ -247,7 +247,7 @@ def compile
value = value.sub("return {", "{") if name == "new"
value[8] = " #{name}"
else
value = "var #{name} = #{value}"
value = "var #{name} #{operator} #{value}"
end

value = "static #{value}" if is_this
Expand Down Expand Up @@ -301,7 +301,7 @@ def scope_name(node)
end
elsif node.type == :value
if @compiler.scope.push content
content << "var "
content = "var " << content
end
end

Expand Down
9 changes: 8 additions & 1 deletion lib/spoon/parser.rb
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,8 @@ def initialize
:do,
:while,
:import,
:class
:class,
:as
]
end

Expand Down Expand Up @@ -127,6 +128,7 @@ def initialize
literal |
self_call |
this_call |
typed |
ident |
type
}
Expand Down Expand Up @@ -168,6 +170,11 @@ def initialize
whitespace.maybe >> str(']')
}

# Matches typed word
rule(:typed) {
ident.as(:l) >> trim(AS().as(:o)) >> type.as(:r)
}

# Matches word
rule(:ident) {
skip_key >>
Expand Down
8 changes: 5 additions & 3 deletions lib/spoon/transformer.rb
Original file line number Diff line number Diff line change
Expand Up @@ -96,11 +96,13 @@ class Transformer < Parslet::Transform
operator = op.to_op

if operator == "="
AST::Node.new :op, [ op.to_op, left, right ], :operation => :infix, :is_assign => true
AST::Node.new :op, [ operator, left, right ], :operation => :infix, :is_assign => true
elsif operator == "."
AST::Node.new :op, [ op.to_op, left, right ], :operation => :infix, :is_chain => true
AST::Node.new :op, [ operator, left, right ], :operation => :infix, :is_chain => true
elsif op == "as"
AST::Node.new :op, [ operator, left, right ], :operation => :infix, :is_typed => true
else
AST::Node.new :op, [ op.to_op, left, right ], :operation => :infix
AST::Node.new :op, [ operator, left, right ], :operation => :infix
end
}

Expand Down
1 change: 1 addition & 0 deletions lib/spoon/util/ast_extensions.rb
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,7 @@ def to_b
def to_op
str = trim

return ":" if str == "as"
return "..." if str == ".."
return "!" if str == "not"
return "&&" if str == "and"
Expand Down
2 changes: 2 additions & 0 deletions lib/spoon/util/parser_literals.rb
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,8 @@ class Spoon::Util::IndentParser

rule(:CLASS) { key :class }

rule(:AS) { key :as }

####################################
# Special characters
####################################
Expand Down

0 comments on commit 62ceb64

Please sign in to comment.