Skip to content

Commit

Permalink
Fix ternery operators
Browse files Browse the repository at this point in the history
  • Loading branch information
acidbubbles committed May 16, 2024
1 parent 32d807c commit 96674ce
Show file tree
Hide file tree
Showing 2 changed files with 22 additions and 11 deletions.
27 changes: 18 additions & 9 deletions Scripter.Plugin/src/Lib/Parsing/Parser.cs
Original file line number Diff line number Diff line change
Expand Up @@ -346,6 +346,7 @@ private Expression ParseForStatement(ScopeLexicalContext lexicalContext)
initializer = ParseVariableDeclaration(loopLexicalContext, false);
else
initializer = ParseValueStatementExpression(loopLexicalContext);
Consume().Expect(TokenType.SemiColon);
var condition = ParseValueStatementExpression(loopLexicalContext);
Consume().Expect(TokenType.SemiColon);
var increment = ParseValueStatementExpression(loopLexicalContext);
Expand All @@ -370,7 +371,9 @@ private Expression ParseWhileStatement(ScopeLexicalContext lexicalContext)
private Expression ParseReturnStatement(ScopeLexicalContext lexicalContext)
{
MoveNext();
var value = !Peek().Match(TokenType.SemiColon) ? ParseValueStatementExpression(lexicalContext) : UndefinedExpression.Instance;
var value = !Peek().Match(TokenType.SemiColon)
? ParseValueOrTernaryExpression(lexicalContext)
: UndefinedExpression.Instance;
Consume().Expect(TokenType.SemiColon);
return new ReturnExpression(value, lexicalContext);
}
Expand All @@ -386,20 +389,26 @@ private VariableDeclarationExpression ParseVariableDeclaration(ScopeLexicalConte
if (next.Match(TokenType.Assignment))
{
MoveNext();
var initialValue = ParseValueStatementExpression(lexicalContext);
if (Peek().Match(TokenType.Ternary))
{
MoveNext();
initialValue = ParseTernaryRightExpression(lexicalContext, initialValue);
}
Consume().Expect(TokenType.SemiColon);
var initialValue = ParseValueOrTernaryExpression(lexicalContext);
return new VariableDeclarationExpression(nameToken.value, initialValue, lexicalContext);
}

Consume().Expect(TokenType.SemiColon);
return new VariableDeclarationExpression(nameToken.value, UndefinedExpression.Instance, lexicalContext);
}

private Expression ParseValueOrTernaryExpression(ScopeLexicalContext lexicalContext)
{
// TODO: This whole function is workaround for bad parsing of return a ? b : c
var initialValue = ParseValueStatementExpression(lexicalContext);
if (Peek().Match(TokenType.Ternary))
{
MoveNext();
initialValue = ParseTernaryRightExpression(lexicalContext, initialValue);
}
return initialValue;
}

private Expression ParseValueStatementExpression(ScopeLexicalContext lexicalContext, int precedence = 0)
{
var left = ParsePureValueExpression(lexicalContext);
Expand Down Expand Up @@ -649,7 +658,7 @@ private Expression ParseArrowFunctionExpression(ScopeLexicalContext lexicalConte
if (Peek().Match(TokenType.LeftBrace))
body = ParseFunctionBody(functionLexicalContext);
else
body = new CodeBlockExpression(new List<Expression> { ParseValueStatementExpression(functionLexicalContext) }, lexicalContext);
body = new CodeBlockExpression(new List<Expression> { ParseValueOrTernaryExpression(functionLexicalContext) }, lexicalContext);
var function = new FunctionDeclarationExpression(name, arguments, body, functionLexicalContext);
return function;
}
Expand Down
6 changes: 4 additions & 2 deletions Scripter.Tests/LanguageTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -225,10 +225,12 @@ public void Ternary()
var value = "true";
var first = value ? 'first' + '' : 'error';
var second = (!value) ? 'error' : ('second');
return first + ' ' + second;
function third() { return true ? 'third' : 'error'; }
const fourth = () => true ? 'fourth' : 'error';
return first + ' ' + second + ' ' + third() + ' ' + fourth();
""");
var result = _program.Run();
Assert.That(result.ToString(), Is.EqualTo("first second"));
Assert.That(result.ToString(), Is.EqualTo("first second third fourth"));
}

[Test]
Expand Down

0 comments on commit 96674ce

Please sign in to comment.