From 1ceb02a5bcac40df2e69e467c75ce26905545af4 Mon Sep 17 00:00:00 2001 From: Ron Buckton Date: Tue, 16 Feb 2016 18:10:52 -0800 Subject: [PATCH] Added initial ES7 transformer --- src/compiler/transformers/es7.ts | 69 +++++++++++++++++++++++++++++++- 1 file changed, 67 insertions(+), 2 deletions(-) diff --git a/src/compiler/transformers/es7.ts b/src/compiler/transformers/es7.ts index e4d1e564cb8..9dca322c175 100644 --- a/src/compiler/transformers/es7.ts +++ b/src/compiler/transformers/es7.ts @@ -3,7 +3,6 @@ /*@internal*/ namespace ts { - // TODO(rbuckton): ES7->ES6 transformer export function transformES7(context: TransformationContext) { const { hoistVariableDeclaration } = context; @@ -26,7 +25,73 @@ namespace ts { } function visitorWorker(node: Node) { - return node; + switch (node.kind) { + case SyntaxKind.BinaryExpression: + return visitBinaryExpression(node); + } + + Debug.fail("Unexpected node kind."); + } + + function visitBinaryExpression(node: BinaryExpression): Expression { + // We are here because ES7 adds support for the exponentiation operator. + const left = visitNode(node.left, visitor, isExpression); + const right = visitNode(node.right, visitor, isExpression); + if (node.operatorToken.kind === SyntaxKind.AsteriskAsteriskEqualsToken) { + let target: Expression; + let value: Expression; + if (isElementAccessExpression(left)) { + // Transforms `a[x] **= b` into `(_a = a)[_x = x] = Math.pow(_a[_x], b)` + const expressionTemp = createTempVariable(); + hoistVariableDeclaration(expressionTemp); + + const argumentExpressionTemp = createTempVariable(); + hoistVariableDeclaration(argumentExpressionTemp); + + target = createElementAccess( + createAssignment(expressionTemp, left.expression, /*location*/ left.expression), + createAssignment(argumentExpressionTemp, left.argumentExpression, /*location*/ left.argumentExpression), + /*location*/ left + ); + + value = createElementAccess( + expressionTemp, + argumentExpressionTemp, + /*location*/ left + ); + } + else if (isPropertyAccessExpression(left)) { + // Transforms `a.x **= b` into `(_a = a).x = Math.pow(_a.x, b)` + const expressionTemp = createTempVariable(); + hoistVariableDeclaration(expressionTemp); + + target = createPropertyAccess( + createAssignment(expressionTemp, left.expression, /*location*/ left.expression), + left.name, + /*location*/ left + ); + + value = createPropertyAccess( + expressionTemp, + left.name, + /*location*/ left + ); + } + else { + // Transforms `a **= b` into `a = Math.pow(a, b)` + target = left; + value = left; + } + + return createAssignment(target, createMathPow(value, right, /*location*/ node), /*location*/ node); + } + else if (node.operatorToken.kind === SyntaxKind.AsteriskAsteriskToken) { + // Transforms `a ** b` into `Math.pow(a, b)` + return createMathPow(left, right, /*location*/ node); + } + else { + Debug.fail("Unexpected node kind."); + } } } } \ No newline at end of file