diff --git a/moonscript/compile.lua b/moonscript/compile.lua index 98e0f44..f76cfae 100644 --- a/moonscript/compile.lua +++ b/moonscript/compile.lua @@ -154,13 +154,6 @@ Block = (function() end return "Block<" .. tostring(h) .. "> <- " .. tostring(self.parent) end, - bubble = function(self, other) - if other == nil then - other = self.parent - end - local has_varargs = self.has_varargs and not self:has_name("...") - other.has_varargs = other.has_varargs or has_varargs - end, line_table = function(self) return self._posmap end, @@ -173,6 +166,9 @@ Block = (function() listen = function(self, name, fn) self._listeners[name] = fn end, + unlisten = function(self, name) + self._listeners[name] = nil + end, send = function(self, name, ...) do local fn = self._listeners[name] diff --git a/moonscript/compile.moon b/moonscript/compile.moon index f5648f4..f3d0439 100644 --- a/moonscript/compile.moon +++ b/moonscript/compile.moon @@ -112,11 +112,6 @@ class Block else @indent = 0 - -- bubble properties into parent - bubble: (other=@parent) => - has_varargs = @has_varargs and not @has_name "..." - other.has_varargs = other.has_varargs or has_varargs - line_table: => @_posmap @@ -129,6 +124,9 @@ class Block listen: (name, fn) => @_listeners[name] = fn + unlisten: (name) => + @_listeners[name] = nil + send: (name, ...) => if fn = @_listeners[name] fn self, ... diff --git a/moonscript/compile/value.lua b/moonscript/compile/value.lua index d8fce5f..77cb60c 100644 --- a/moonscript/compile/value.lua +++ b/moonscript/compile/value.lua @@ -298,7 +298,7 @@ value_compile = { return self:value(sup(self)) end if value == "..." then - self.has_varargs = true + self:send("varargs") end return tostring(value) end diff --git a/moonscript/compile/value.moon b/moonscript/compile/value.moon index c9d43c9..8c57812 100644 --- a/moonscript/compile/value.moon +++ b/moonscript/compile/value.moon @@ -192,6 +192,6 @@ value_compile = return @value sup self if value == "..." - @has_varargs = true + @send "varargs" tostring value diff --git a/moonscript/transform.lua b/moonscript/transform.lua index c9618dd..2d28877 100644 --- a/moonscript/transform.lua +++ b/moonscript/transform.lua @@ -1453,6 +1453,12 @@ Value = Transformer({ fndef = function(self, node) smart_node(node) node.body = apply_to_last(node.body, implicitly_return(self)) + node.body = { + Run(function(self) + return self:listen("varargs", function() end) + end), + unpack(node.body) + } return node end, ["if"] = function(self, node) @@ -1549,16 +1555,19 @@ Value = Transformer({ local _, body = unpack(node) local fn = nil local arg_list = { } - insert(body, Run(function(self) - if self.has_varargs then - insert(arg_list, "...") - return insert(fn.args, { - "..." - }) - end - end)) fn = smart_node(build.fndef({ - body = body + body = { + Run(function(self) + return self:listen("varargs", function() + insert(arg_list, "...") + insert(fn.args, { + "..." + }) + return self:unlisten("varargs") + end) + end), + unpack(body) + } })) return build.chain({ base = { diff --git a/moonscript/transform.moon b/moonscript/transform.moon index b44330d..ca295ff 100644 --- a/moonscript/transform.moon +++ b/moonscript/transform.moon @@ -765,6 +765,11 @@ Value = Transformer { fndef: (node) => smart_node node node.body = apply_to_last node.body, implicitly_return self + node.body = { + Run => @listen "varargs", -> -- capture event + unpack node.body + } + node if: (node) => build.block_exp { node } @@ -823,12 +828,16 @@ Value = Transformer { fn = nil arg_list = {} - insert body, Run => - if @has_varargs - insert arg_list, "..." - insert fn.args, {"..."} + fn = smart_node build.fndef body: { + Run => + @listen "varargs", -> + insert arg_list, "..." + insert fn.args, {"..."} + @unlisten "varargs" + + unpack body + } - fn = smart_node build.fndef body: body build.chain { base: {"parens", fn}, {"call", arg_list} } } diff --git a/tests/outputs/bubbling.lua b/tests/outputs/bubbling.lua index 9cbcd00..d657bea 100644 --- a/tests/outputs/bubbling.lua +++ b/tests/outputs/bubbling.lua @@ -46,7 +46,7 @@ local j = (function() end)() local m m = function(...) - return (function() + return (function(...) local _accum_0 = { } local _len_0 = 0 local _list_0 = { @@ -60,7 +60,7 @@ m = function(...) end end return _accum_0 - end)() + end)(...) end local x = (function(...) local _accum_0 = { } @@ -114,7 +114,7 @@ local a = (function(...) end return _accum_0 end)(...) -local b = (function(...) +local b = (function() local _accum_0 = { } local _len_0 = 0 for i = 1, 10 do @@ -128,4 +128,4 @@ local b = (function(...) end end return _accum_0 -end)(...) \ No newline at end of file +end)() \ No newline at end of file diff --git a/todo b/todo index 666baca..3b80bc6 100644 --- a/todo +++ b/todo @@ -43,11 +43,6 @@ x = for x in y * any/every keywords for comprehensions? (what about iterators) -not working right: - - double_args = (...) -> - [x * 2 for x in *{...}] - * let array items in table be defined without {} when indented