diff --git a/.idea/workspace.xml b/.idea/workspace.xml
index f828a9fb0f0..0c6727619f0 100644
--- a/.idea/workspace.xml
+++ b/.idea/workspace.xml
@@ -6,11 +6,25 @@
-
+
+
+
+
+
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -35,7 +49,20 @@
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -88,78 +115,9 @@
-
+
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
@@ -189,14 +147,46 @@
-
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
-
+
@@ -204,10 +194,32 @@
-
-
+
+
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -215,10 +227,66 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
-
+
@@ -226,70 +294,19 @@
-
-
+
+
-
-
-
-
-
-
-
-
-
-
-
-
+
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+
@@ -311,22 +328,22 @@
@@ -463,6 +480,50 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -554,7 +615,7 @@
-
+
@@ -577,17 +638,17 @@
-
+
-
+
-
-
-
-
-
-
+
+
+
+
+
+
@@ -595,21 +656,17 @@
-
-
-
-
-
-
+
+
-
+
-
+
@@ -622,7 +679,7 @@
-
+
@@ -651,13 +708,13 @@
-
+
-
-
+
+
@@ -670,13 +727,11 @@
-
+
-
-
@@ -755,10 +810,10 @@
-
-
+
+
-
+
localhost
@@ -800,24 +855,24 @@
-
-
-
+
+
+
-
+
-
+
-
-
-
+
+
+
-
+
-
+
@@ -848,7 +903,7 @@
-
+
@@ -871,6 +926,7 @@
+
@@ -880,132 +936,130 @@
-
+
-
+
+
+
+
+
+
+
+
-
+
-
+
-
+
-
+
-
-
-
-
-
-
-
-
+
-
+
-
-
-
-
+
+
+
+
+
+
+
+
+
-
+
-
+
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/js/src/com/google/dart/compiler/backend/js/ast/JsBlock.java b/js/src/com/google/dart/compiler/backend/js/ast/JsBlock.java
index 3d927a2bf7d..10973593ecc 100644
--- a/js/src/com/google/dart/compiler/backend/js/ast/JsBlock.java
+++ b/js/src/com/google/dart/compiler/backend/js/ast/JsBlock.java
@@ -12,38 +12,44 @@ import java.util.List;
*/
public class JsBlock extends JsStatement {
- private final List stmts = new ArrayList();
+ private final List stmts = new ArrayList();
- public JsBlock() {
- }
-
- public JsBlock(JsStatement stmt) {
- stmts.add(stmt);
- }
-
- public List getStatements() {
- return stmts;
- }
-
- public void addStatement(JsStatement statement) {
- assert statement != null;
- stmts.add(statement);
- }
-
- public boolean isGlobalBlock() {
- return false;
- }
-
- @Override
- public void traverse(JsVisitor v, JsContext ctx) {
- if (v.visit(this, ctx)) {
- v.acceptWithInsertRemove(stmts);
+ public JsBlock() {
+ }
+
+ public JsBlock(JsStatement stmt) {
+ stmts.add(stmt);
+ }
+
+ public List getStatements() {
+ return stmts;
+ }
+
+ public void addStatement(JsStatement statement) {
+ assert statement != null;
+ stmts.add(statement);
+ }
+
+ public boolean isGlobalBlock() {
+ return false;
+ }
+
+ @Override
+ public void traverse(JsVisitor v, JsContext ctx) {
+ if (v.visit(this, ctx)) {
+ v.acceptWithInsertRemove(stmts);
+ }
+ v.endVisit(this, ctx);
+ }
+
+ @Override
+ public NodeKind getKind() {
+ return NodeKind.BLOCK;
+ }
+
+ public void setStatements(List statements) {
+ assert this.stmts.isEmpty() : "Already contains statements.";
+ this.stmts.addAll(statements);
}
- v.endVisit(this, ctx);
- }
- @Override
- public NodeKind getKind() {
- return NodeKind.BLOCK;
- }
}
diff --git a/js/src/com/google/dart/compiler/backend/js/ast/JsInvocation.java b/js/src/com/google/dart/compiler/backend/js/ast/JsInvocation.java
index 6704234df29..40cb649319c 100644
--- a/js/src/com/google/dart/compiler/backend/js/ast/JsInvocation.java
+++ b/js/src/com/google/dart/compiler/backend/js/ast/JsInvocation.java
@@ -59,4 +59,10 @@ public final class JsInvocation extends JsExpression implements HasArguments {
public NodeKind getKind() {
return NodeKind.INVOKE;
}
+
+ // Pavel Talanov
+ public void setArguments(List arguments) {
+ assert this.args.isEmpty() : "Arguments already set.";
+ this.args.addAll(arguments);
+ }
}
diff --git a/translator/src/org/jetbrains/k2js/declarations/DeclarationExtractor.java b/translator/src/org/jetbrains/k2js/declarations/DeclarationExtractor.java
index e49124a4590..492f80c6fd2 100644
--- a/translator/src/org/jetbrains/k2js/declarations/DeclarationExtractor.java
+++ b/translator/src/org/jetbrains/k2js/declarations/DeclarationExtractor.java
@@ -1,5 +1,6 @@
package org.jetbrains.k2js.declarations;
+import com.google.dart.compiler.backend.js.ast.JsName;
import com.google.dart.compiler.backend.js.ast.JsScope;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor;
@@ -13,6 +14,8 @@ import java.util.Map;
public final class DeclarationExtractor {
private final Map descriptorToScopeMap
= new HashMap();
+ private final Map descriptorToNameMap
+ = new HashMap();
public DeclarationExtractor() {
@@ -30,7 +33,18 @@ public final class DeclarationExtractor {
return scope;
}
- /*package*/ void put(@NotNull DeclarationDescriptor descriptor, @NotNull JsScope scope) {
+ @NotNull
+ public JsName getName(@NotNull DeclarationDescriptor descriptor) {
+ JsName name = descriptorToNameMap.get(descriptor);
+ assert name != null : "Unknown declaration";
+ return name;
+ }
+
+ /*package*/ void putScope(@NotNull DeclarationDescriptor descriptor, @NotNull JsScope scope) {
descriptorToScopeMap.put(descriptor, scope);
}
+
+ /*package*/ void putName(@NotNull DeclarationDescriptor descriptor, @NotNull JsName name) {
+ descriptorToNameMap.put(descriptor, name);
+ }
}
diff --git a/translator/src/org/jetbrains/k2js/declarations/ExtractionVisitor.java b/translator/src/org/jetbrains/k2js/declarations/ExtractionVisitor.java
index c69cc8f0f17..1fbea825abb 100644
--- a/translator/src/org/jetbrains/k2js/declarations/ExtractionVisitor.java
+++ b/translator/src/org/jetbrains/k2js/declarations/ExtractionVisitor.java
@@ -1,8 +1,6 @@
package org.jetbrains.k2js.declarations;
-import com.google.dart.compiler.backend.js.ast.JsName;
import com.google.dart.compiler.backend.js.ast.JsScope;
-import com.intellij.codeInspection.ex.Descriptor;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.jet.lang.descriptors.*;
import org.jetbrains.k2js.translate.Namer;
@@ -20,11 +18,11 @@ public final class ExtractionVisitor extends DeclarationDescriptorVisitor(), AstUtil.convertToBlock(returnExpression));
}
+ //TODO rewrite
@NotNull
private JsName declareOrGetBackingFieldName(@NotNull String propertyName, @NotNull TranslationContext context) {
String backingFieldName = Namer.getBackingFieldNameForProperty(propertyName);
@@ -113,6 +115,7 @@ public final class ClassBodyVisitor extends TranslatorVisitor initializerStatements = classDeclaration.accept(initializerVisitor,
+ translationContext().newClass(classDeclaration));
+ JsBlock block = new JsBlock();
+ block.setStatements(initializerStatements);
+ return AstUtil.newFunction(translationContext().enclosingScope(), null, null, block);
}
diff --git a/translator/src/org/jetbrains/k2js/translate/ExpressionTranslator.java b/translator/src/org/jetbrains/k2js/translate/ExpressionTranslator.java
index 6bbf698f72a..934f33ebce6 100644
--- a/translator/src/org/jetbrains/k2js/translate/ExpressionTranslator.java
+++ b/translator/src/org/jetbrains/k2js/translate/ExpressionTranslator.java
@@ -9,7 +9,7 @@ import org.jetbrains.jet.lang.psi.JetExpression;
*/
public final class ExpressionTranslator extends AbstractTranslator {
- final private ExpressionVisitor visitor = new ExpressionVisitor();
+ final private ExpressionVisitor visitor = new ExpressionVisitor(translationContext());
public ExpressionTranslator(@NotNull TranslationContext context) {
super(context);
diff --git a/translator/src/org/jetbrains/k2js/translate/ExpressionVisitor.java b/translator/src/org/jetbrains/k2js/translate/ExpressionVisitor.java
index 1de62d25e08..7259463428d 100644
--- a/translator/src/org/jetbrains/k2js/translate/ExpressionVisitor.java
+++ b/translator/src/org/jetbrains/k2js/translate/ExpressionVisitor.java
@@ -5,7 +5,6 @@ import com.google.dart.compiler.backend.js.ast.JsExpression;
import com.google.dart.compiler.backend.js.ast.*;
import com.google.dart.compiler.backend.js.ast.JsReturn;
import com.google.dart.compiler.util.AstUtil;
-import com.sun.xml.internal.bind.v2.runtime.reflect.opt.Const;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.jet.lang.descriptors.CallableDescriptor;
@@ -17,6 +16,7 @@ import org.jetbrains.jet.lang.resolve.constants.CompileTimeConstant;
import org.jetbrains.jet.lexer.JetToken;
import java.util.ArrayList;
+import java.util.Arrays;
import java.util.List;
/**
@@ -24,6 +24,8 @@ import java.util.List;
*/
public final class ExpressionVisitor extends TranslatorVisitor {
+ public ExpressionVisitor(TranslationContext context) {
+ }
//TODO method too long
@Override
@@ -87,13 +89,39 @@ public final class ExpressionVisitor extends TranslatorVisitor {
@NotNull
public JsNode visitBinaryExpression(@NotNull JetBinaryExpression expression,
@NotNull TranslationContext context) {
+ JsInvocation setterCall = translateAsSetterCall(expression, context);
+ if (setterCall != null) {
+ return setterCall;
+ }
+ return translateAsBinaryOperation(expression, context);
+ }
+
+ @Nullable
+ public JsInvocation translateAsSetterCall(@NotNull JetBinaryExpression expression,
+ @NotNull TranslationContext context) {
+ JetToken jetOperationToken = (JetToken)expression.getOperationToken();
+ if (!OperationTranslator.isAssignment(jetOperationToken)) {
+ return null;
+ }
+ PropertyAccessTranslator translator = new PropertyAccessTranslator(context);
+ JetExpression leftExpression = expression.getLeft();
+ JsInvocation setterCall = translator.resolveAsPropertySet(leftExpression);
+ if (setterCall == null) {
+ return null;
+ }
+ JetExpression rightExpression = expression.getRight();
+ assert rightExpression != null : "Selector should not be null";
+ JsExpression right = AstUtil.convertToExpression(rightExpression.accept(this, context));
+ setterCall.setArguments(Arrays.asList(right));
+ return setterCall;
+ }
+
+ @NotNull
+ private JsNode translateAsBinaryOperation(@NotNull JetBinaryExpression expression, @NotNull TranslationContext context) {
JsExpression left = AstUtil.convertToExpression(expression.getLeft().accept(this, context));
JetExpression rightExpression = expression.getRight();
- if (rightExpression == null) {
- throw new AssertionError("BinaryExpression with no right parameter");
- }
+ assert rightExpression != null : "Selector should not be null";
JsExpression right = AstUtil.convertToExpression(rightExpression.accept(this, context));
- //TODO cast dangerous?
JetToken jetOperationToken = (JetToken)expression.getOperationToken();
return new JsBinaryOperation(OperationTranslator.getBinaryOperator(jetOperationToken), left, right);
}
@@ -281,6 +309,25 @@ public final class ExpressionVisitor extends TranslatorVisitor {
@NotNull
public JsNode visitDotQualifiedExpression(@NotNull JetDotQualifiedExpression expression,
@NotNull TranslationContext context) {
+ JsInvocation getterCall = translateAsGetterCall(expression, context);
+ if (getterCall != null) {
+ return getterCall;
+ }
+ return translateAsQualifiedExpression(expression, context);
+ }
+
+ @Nullable
+ private JsInvocation translateAsGetterCall(@NotNull JetDotQualifiedExpression expression,
+ @NotNull TranslationContext context) {
+ JsInvocation result;
+ PropertyAccessTranslator translator = new PropertyAccessTranslator(context);
+ result = translator.resolveAsPropertyGet(expression);
+ return result;
+ }
+
+ @NotNull
+ private JsNode translateAsQualifiedExpression(@NotNull JetDotQualifiedExpression expression,
+ @NotNull TranslationContext context) {
JsExpression receiver = AstUtil.convertToExpression(expression.getReceiverExpression().accept(this, context));
JetExpression jetSelector = expression.getSelectorExpression();
assert jetSelector != null : "Selector should not be null in dot qualified expression.";
@@ -288,18 +335,27 @@ public final class ExpressionVisitor extends TranslatorVisitor {
assert (selector instanceof JsNameRef || selector instanceof JsInvocation)
: "Selector should be a name reference or a method invocation in dot qualified expression.";
if (selector instanceof JsInvocation) {
- JsInvocation result = (JsInvocation)selector;
- JsExpression qualifier = result.getQualifier();
- JsNameRef nameRef = (JsNameRef)qualifier;
- nameRef.setQualifier(receiver);
- return result;
+ return translateAsQualifiedInvocation(receiver, (JsInvocation) selector);
} else {
- JsNameRef result = (JsNameRef)selector;
- result.setQualifier(receiver);
- return result;
+ return translateAsQualifiedNameReference(receiver, (JsNameRef) selector);
}
}
+ @NotNull
+ private JsNode translateAsQualifiedNameReference(@NotNull JsExpression receiver, @NotNull JsNameRef selector) {
+ JsNameRef result = (JsNameRef)selector;
+ result.setQualifier(receiver);
+ return result;
+ }
+
+ @NotNull
+ private JsNode translateAsQualifiedInvocation(@NotNull JsExpression receiver, @NotNull JsInvocation selector) {
+ JsInvocation result = (JsInvocation)selector;
+ JsExpression qualifier = result.getQualifier();
+ JsNameRef nameRef = (JsNameRef)qualifier;
+ nameRef.setQualifier(receiver);
+ return result;
+ }
}
diff --git a/translator/src/org/jetbrains/k2js/translate/InitializerVisitor.java b/translator/src/org/jetbrains/k2js/translate/InitializerVisitor.java
new file mode 100644
index 00000000000..834a2c801bf
--- /dev/null
+++ b/translator/src/org/jetbrains/k2js/translate/InitializerVisitor.java
@@ -0,0 +1,69 @@
+package org.jetbrains.k2js.translate;
+
+import com.google.dart.compiler.backend.js.ast.*;
+import com.google.dart.compiler.util.AstUtil;
+import org.jetbrains.annotations.NotNull;
+import org.jetbrains.jet.lang.descriptors.DeclarationDescriptorVisitor;
+import org.jetbrains.jet.lang.psi.*;
+
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+
+/**
+ * @author Talanov Pavel
+ *
+ * This visitor collects all initializers from a given class in a list of statements.
+ * Note: we do use this to preserve the order in which initializers are executed.
+ */
+public class InitializerVisitor extends TranslatorVisitor> {
+
+ @Override
+ @NotNull
+ public List visitClass(@NotNull JetClass expression, @NotNull TranslationContext context) {
+ List initializerStatements = new ArrayList();
+ for (JetDeclaration declaration : expression.getDeclarations()) {
+ initializerStatements.addAll(declaration.accept(this, context));
+ }
+ return initializerStatements;
+ }
+
+ @Override
+ @NotNull
+ public List visitProperty(@NotNull JetProperty expression, @NotNull TranslationContext context) {
+ JetExpression initializer = expression.getInitializer();
+ if (initializer == null) {
+ return new ArrayList();
+ }
+ ExpressionTranslator translator = new ExpressionTranslator(context);
+ JsExpression initExpression = AstUtil.convertToExpression(translator.translate(initializer));
+ return Arrays.asList(assignmentToBackingField(expression, initExpression, context));
+ }
+
+ @NotNull
+ JsStatement assignmentToBackingField(@NotNull JetProperty property, @NotNull JsExpression initExpression,
+ @NotNull TranslationContext context) {
+ JsName backingFieldName = context.classScope()
+ .findExistingName(Namer.getBackingFieldNameForProperty(property.getName()));
+ assert backingFieldName != null : "Class scope should contain backing field names";
+ JsNameRef backingFieldRef = backingFieldName.makeRef();
+ backingFieldRef.setQualifier(new JsThisRef());
+ return AstUtil.convertToStatement(AstUtil.newAssignment(backingFieldRef, initExpression));
+ }
+
+ //TODO : implement
+ @Override
+ @NotNull
+ public List visitAnonymousInitializer(@NotNull JetClassInitializer initializer,
+ @NotNull TranslationContext context) {
+ return new ArrayList();
+ }
+
+ @Override
+ @NotNull
+ // Not interested in other types of declarations, they do not contain initializers.
+ public List visitDeclaration(@NotNull JetDeclaration expression, @NotNull TranslationContext context) {
+ return new ArrayList();
+ }
+
+}
diff --git a/translator/src/org/jetbrains/k2js/translate/Namer.java b/translator/src/org/jetbrains/k2js/translate/Namer.java
index d7324fd6add..55b20c5aec6 100644
--- a/translator/src/org/jetbrains/k2js/translate/Namer.java
+++ b/translator/src/org/jetbrains/k2js/translate/Namer.java
@@ -20,9 +20,9 @@ public final class Namer {
public static final String INITIALIZE_METHOD_NAME = "initialize";
private static final String CLASS_OBJECT_NAME = "Class";
//private static final String CLASS_CREATE_METHOD_NAME = "create";
- private static final String SETTER_PREFIX = "_set_";
- private static final String GETTER_PREFIX = "_get_";
- private static final String BACKING_FIELD_PREFIX = "_$_";
+ private static final String SETTER_PREFIX = "set_";
+ private static final String GETTER_PREFIX = "get_";
+ private static final String BACKING_FIELD_PREFIX = "_";
// public static final String DEFAULT_SETTER_PARAM_NAME = "val";
public static String getClassObjectName() {
diff --git a/translator/src/org/jetbrains/k2js/translate/OperationTranslator.java b/translator/src/org/jetbrains/k2js/translate/OperationTranslator.java
index 845c49fced6..871783f72ed 100644
--- a/translator/src/org/jetbrains/k2js/translate/OperationTranslator.java
+++ b/translator/src/org/jetbrains/k2js/translate/OperationTranslator.java
@@ -27,6 +27,7 @@ public final class OperationTranslator {
map.put(JetTokens.LT, JsBinaryOperator.LT);
map.put(JetTokens.LTEQ, JsBinaryOperator.LTE);
map.put(JetTokens.EQEQ, JsBinaryOperator.EQ);
+ map.put(JetTokens.ANDAND, JsBinaryOperator.AND);
}
public static JsBinaryOperator getBinaryOperator(JetToken token) {
@@ -38,5 +39,8 @@ public final class OperationTranslator {
throw new AssertionError("Invalid map: should contain token: " + token.toString());
}
+ public static boolean isAssignment(JetToken token) {
+ return (token == JetTokens.EQ);
+ }
}
diff --git a/translator/src/org/jetbrains/k2js/translate/PropertyAccessTranslator.java b/translator/src/org/jetbrains/k2js/translate/PropertyAccessTranslator.java
new file mode 100644
index 00000000000..9a118369366
--- /dev/null
+++ b/translator/src/org/jetbrains/k2js/translate/PropertyAccessTranslator.java
@@ -0,0 +1,105 @@
+package org.jetbrains.k2js.translate;
+
+import com.google.dart.compiler.backend.js.ast.*;
+import com.google.dart.compiler.util.AstUtil;
+import org.jetbrains.annotations.NotNull;
+import org.jetbrains.annotations.Nullable;
+import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor;
+import org.jetbrains.jet.lang.descriptors.PropertyDescriptor;
+import org.jetbrains.jet.lang.descriptors.PropertyGetterDescriptor;
+import org.jetbrains.jet.lang.descriptors.PropertySetterDescriptor;
+import org.jetbrains.jet.lang.psi.JetDotQualifiedExpression;
+import org.jetbrains.jet.lang.psi.JetExpression;
+import org.jetbrains.jet.lang.resolve.BindingContext;
+import org.jetbrains.jet.lang.resolve.calls.ResolvedCall;
+
+/**
+ * @author Talanov Pavel
+ */
+//TODO ask for code review. Class has messy code.
+public final class PropertyAccessTranslator extends AbstractTranslator {
+
+ public PropertyAccessTranslator(@NotNull TranslationContext context) {
+ super(context);
+ }
+
+ @Nullable
+ public JsInvocation resolveAsPropertyGet(@NotNull JetDotQualifiedExpression expression) {
+ if (!(expression instanceof JetDotQualifiedExpression)) {
+ return null;
+ }
+ JetDotQualifiedExpression dotQualifiedExpression = (JetDotQualifiedExpression)expression;
+ JetExpression selectorExpression = dotQualifiedExpression.getSelectorExpression();
+ assert selectorExpression != null : "Selector should not be null.";
+ JsName getterName = getPropertyGetterName(selectorExpression);
+ if (getterName == null) {
+ return null;
+ }
+ return translateReceiverAndReturnAccessorInvocation(dotQualifiedExpression, getterName);
+ }
+
+ @NotNull
+ private JsInvocation translateReceiverAndReturnAccessorInvocation
+ (@NotNull JetDotQualifiedExpression dotQualifiedExpression, @NotNull JsName accessorName) {
+ ExpressionTranslator translator = new ExpressionTranslator(translationContext());
+ JsNode node = translator.translate(dotQualifiedExpression.getReceiverExpression());
+ JsNameRef result = accessorName.makeRef();
+ result.setQualifier(AstUtil.convertToExpression(node));
+ return AstUtil.newInvocation(result);
+ }
+
+ @Nullable
+ public JsInvocation resolveAsPropertySet(@NotNull JetExpression expression) {
+ if (!(expression instanceof JetDotQualifiedExpression)) {
+ return null;
+ }
+ JetDotQualifiedExpression dotQualifiedExpression = (JetDotQualifiedExpression)expression;
+ JetExpression selectorExpression = dotQualifiedExpression.getSelectorExpression();
+ assert selectorExpression != null : "Selector should not be null.";
+ JsName getterName = getPropertySetterName(selectorExpression);
+ if (getterName == null) {
+ return null;
+ }
+ return translateReceiverAndReturnAccessorInvocation(dotQualifiedExpression, getterName);
+ }
+
+ @Nullable
+ public JsName getPropertyGetterName(@NotNull JetExpression expression) {
+ PropertyDescriptor property = getPropertyDescriptor(expression);
+ if (property == null) {
+ return null;
+ }
+ PropertyGetterDescriptor getter = property.getGetter();
+ if (getter == null) {
+ return null;
+ }
+ return translationContext().declarations().getName(getter);
+ }
+
+ @Nullable
+ public JsName getPropertySetterName(@NotNull JetExpression expression) {
+ PropertyDescriptor property = getPropertyDescriptor(expression);
+ if (property == null) {
+ return null;
+ }
+ PropertySetterDescriptor setter = property.getSetter();
+ if (setter == null) {
+ return null;
+ }
+ return translationContext().declarations().getName(setter);
+ }
+
+ @Nullable
+ private PropertyDescriptor getPropertyDescriptor(@NotNull JetExpression expression) {
+ ResolvedCall> resolvedCall =
+ translationContext().bindingContext().get(BindingContext.RESOLVED_CALL, expression);
+ if (resolvedCall != null) {
+ DeclarationDescriptor descriptor = resolvedCall.getCandidateDescriptor();
+ if (descriptor instanceof PropertyDescriptor) {
+ return (PropertyDescriptor)descriptor;
+ }
+ }
+ return null;
+ }
+
+}
diff --git a/translator/src/org/jetbrains/k2js/translate/TranslationContext.java b/translator/src/org/jetbrains/k2js/translate/TranslationContext.java
index 056f3c7f847..69c9f0c271a 100644
--- a/translator/src/org/jetbrains/k2js/translate/TranslationContext.java
+++ b/translator/src/org/jetbrains/k2js/translate/TranslationContext.java
@@ -152,4 +152,9 @@ public final class TranslationContext {
assert descriptor != null : "Element should have a descriptor";
return getScopeForDescriptor(descriptor);
}
+
+ @NotNull
+ public DeclarationExtractor declarations() {
+ return extractor;
+ }
}
diff --git a/translator/test/org/jetbrains/k2js/test/ClassTest.java b/translator/test/org/jetbrains/k2js/test/ClassTest.java
index 7ddc07e7a00..cfbf4814da8 100644
--- a/translator/test/org/jetbrains/k2js/test/ClassTest.java
+++ b/translator/test/org/jetbrains/k2js/test/ClassTest.java
@@ -57,4 +57,19 @@ public final class ClassTest extends TranslationTest {
testFooBoxIsTrue("accessToInstanceProperty.kt");
}
+ @Test
+ public void twoClassesWithProperties() throws Exception {
+ testFooBoxIsTrue("twoClassesWithProperties.kt");
+ }
+
+ @Test
+ public void setter() throws Exception {
+ performTest("setter.kt", "foo", "f", 99.0);
+ }
+
+ @Test
+ public void constructorWithParameter() throws Exception {
+ testFooBoxIsTrue("constructorWithParameter.kt");
+ }
+
}
diff --git a/translator/test_files/test_cases/accessToInstanceProperty.kt b/translator/test_files/test_cases/accessToInstanceProperty.kt
index 340dee70671..3b210ee773d 100644
--- a/translator/test_files/test_cases/accessToInstanceProperty.kt
+++ b/translator/test_files/test_cases/accessToInstanceProperty.kt
@@ -1,10 +1,11 @@
namespace foo
class Test() {
- val a : Int = 1
+ var a : Int = 100
}
fun box() : Boolean {
var test = Test()
- return (test.a == 1)
+ test.a = 1
+ return (1 == test.a)
}
\ No newline at end of file
diff --git a/translator/test_files/test_cases/constructorWithParameter.kt b/translator/test_files/test_cases/constructorWithParameter.kt
new file mode 100644
index 00000000000..a735b048b43
--- /dev/null
+++ b/translator/test_files/test_cases/constructorWithParameter.kt
@@ -0,0 +1,9 @@
+namespace foo
+
+class Test(var a : Int) {
+}
+
+fun box() : Boolean {
+ var test = Test(1)
+ return (test.a == 1)
+}
\ No newline at end of file
diff --git a/translator/test_files/test_cases/setter.kt b/translator/test_files/test_cases/setter.kt
new file mode 100644
index 00000000000..ac6b99f7272
--- /dev/null
+++ b/translator/test_files/test_cases/setter.kt
@@ -0,0 +1,12 @@
+namespace foo
+
+class Test() {
+ var a : Int = 1
+}
+
+fun f() : Int {
+ var a = Test()
+ var b = Test()
+ b.a = 100
+ return (b.a - a.a)
+}
\ No newline at end of file
diff --git a/translator/test_files/test_cases/twoClassesWithProperties.kt b/translator/test_files/test_cases/twoClassesWithProperties.kt
new file mode 100644
index 00000000000..7c6a8f57da0
--- /dev/null
+++ b/translator/test_files/test_cases/twoClassesWithProperties.kt
@@ -0,0 +1,13 @@
+namespace foo
+
+class A() {
+ val a : Int = 1
+}
+
+class B() {
+ val b : Int = 2
+}
+
+fun box() : Boolean {
+ return ((A().a == 1) && (B().b == 2);
+}
\ No newline at end of file