KT-13043: fix translation of super call from secondary constructor when base constructor has default arguments
This commit is contained in:
@@ -71,4 +71,16 @@ public class DefaultArgumentsTest extends SingleFileTranslationTest {
|
||||
public void testDefaultArgumentsInFunctionWithExpressionAsBody() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testPrimarySuperConstructor() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testSecondarySuperConstructor() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
|
||||
public void testEnumSuperConstructor() throws Exception {
|
||||
checkFooBoxIsOk();
|
||||
}
|
||||
}
|
||||
|
||||
+3
-1
@@ -205,7 +205,9 @@ class ClassTranslator private constructor(
|
||||
|
||||
if (resolvedCall != null && !KotlinBuiltIns.isAny(delegationClassDescriptor!!)) {
|
||||
superCallGenerators += {
|
||||
it += CallTranslator.translate(context, resolvedCall).toInvocationWith(leadingArgs, thisNameRef).makeStmt()
|
||||
val delegationConstructor = resolvedCall.resultingDescriptor
|
||||
it += CallTranslator.translate(context, resolvedCall)
|
||||
.toInvocationWith(leadingArgs, delegationConstructor.valueParameters.size, thisNameRef).makeStmt()
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
+1
-1
@@ -168,7 +168,7 @@ public final class ClassInitializerTranslator extends AbstractTranslator {
|
||||
|
||||
if (classDeclaration instanceof KtEnumEntry) {
|
||||
JsExpression expression = CallTranslator.translate(context(), superCall, null);
|
||||
JsExpression fixedInvocation = AstUtilsKt.toInvocationWith(expression, Collections.<JsExpression>emptyList(),
|
||||
JsExpression fixedInvocation = AstUtilsKt.toInvocationWith(expression, Collections.<JsExpression>emptyList(), 0,
|
||||
JsLiteral.THIS);
|
||||
initializerStatements.add(0, fixedInvocation.makeStmt());
|
||||
}
|
||||
|
||||
@@ -56,22 +56,21 @@ fun JsNode.any(predicate: (JsNode) -> Boolean): Boolean {
|
||||
return visitor.matched
|
||||
}
|
||||
|
||||
fun JsExpression.toInvocationWith(leadingExtraArgs: List<JsExpression>, thisExpr: JsExpression): JsExpression {
|
||||
fun JsExpression.toInvocationWith(leadingExtraArgs: List<JsExpression>, parameterCount: Int, thisExpr: JsExpression): JsExpression {
|
||||
val qualifier: JsExpression
|
||||
val arguments: MutableList<JsExpression>
|
||||
fun padArguments(arguments: List<JsExpression>) = arguments + (1..(parameterCount - arguments.size))
|
||||
.map { Namer.getUndefinedExpression() }
|
||||
|
||||
when (this) {
|
||||
is JsNew -> {
|
||||
qualifier = Namer.getFunctionCallRef(constructorExpression)
|
||||
arguments = getArguments()
|
||||
// `new A(a, b, c)` -> `A.call($this, a, b, c)`
|
||||
return JsInvocation(qualifier, listOf(thisExpr) + leadingExtraArgs + arguments)
|
||||
}
|
||||
is JsInvocation -> {
|
||||
qualifier = getQualifier()
|
||||
arguments = getArguments()
|
||||
// `A(a, b, c)` -> `A(a, b, c, $this)`
|
||||
return JsInvocation(qualifier, leadingExtraArgs + arguments + thisExpr)
|
||||
return JsInvocation(qualifier, leadingExtraArgs + padArguments(arguments) + thisExpr)
|
||||
}
|
||||
else -> throw IllegalStateException("Unexpected node type: " + javaClass)
|
||||
}
|
||||
|
||||
@@ -0,0 +1,16 @@
|
||||
package foo
|
||||
|
||||
enum class A {
|
||||
B(2);
|
||||
|
||||
val c: Int
|
||||
|
||||
constructor (a: Int, b: Int = 3) {
|
||||
c = a + b
|
||||
}
|
||||
}
|
||||
|
||||
fun box(): String {
|
||||
assertEquals(5, A.B.c)
|
||||
return "OK"
|
||||
}
|
||||
@@ -0,0 +1,16 @@
|
||||
package foo
|
||||
|
||||
open class Base(a: Int, b: Int = 3) {
|
||||
val c: Int
|
||||
|
||||
init {
|
||||
c = a + b
|
||||
}
|
||||
}
|
||||
|
||||
class Derived(a: Int) : Base(a)
|
||||
|
||||
fun box(): String {
|
||||
assertEquals(5, Derived(2).c)
|
||||
return "OK"
|
||||
}
|
||||
+18
@@ -0,0 +1,18 @@
|
||||
package foo
|
||||
|
||||
open class Base {
|
||||
val c: Int
|
||||
|
||||
constructor(a: Int, b: Int = 3) {
|
||||
c = a + b
|
||||
}
|
||||
}
|
||||
|
||||
class Derived : Base {
|
||||
constructor(a: Int) : super(a)
|
||||
}
|
||||
|
||||
fun box(): String {
|
||||
assertEquals(5, Derived(2).c)
|
||||
return "OK"
|
||||
}
|
||||
Reference in New Issue
Block a user