diff --git a/idea/idea-core/src/org/jetbrains/kotlin/idea/core/OptionalParametersHelper.kt b/idea/idea-core/src/org/jetbrains/kotlin/idea/core/OptionalParametersHelper.kt index a02e2744738..d61f800537c 100644 --- a/idea/idea-core/src/org/jetbrains/kotlin/idea/core/OptionalParametersHelper.kt +++ b/idea/idea-core/src/org/jetbrains/kotlin/idea/core/OptionalParametersHelper.kt @@ -30,6 +30,7 @@ import org.jetbrains.kotlin.psi.psiUtil.copied import org.jetbrains.kotlin.psi.psiUtil.forEachDescendantOfType import org.jetbrains.kotlin.resolve.BindingContext import org.jetbrains.kotlin.resolve.calls.callUtil.getParameterForArgument +import org.jetbrains.kotlin.resolve.calls.callUtil.getValueArgumentsInParentheses import org.jetbrains.kotlin.resolve.calls.model.ExpressionValueArgument import org.jetbrains.kotlin.resolve.calls.model.ResolvedCall import java.util.ArrayList @@ -50,11 +51,10 @@ public object OptionalParametersHelper { .toMap() if (parameterToDefaultValue.isEmpty()) return emptyList() - val arguments = resolvedCall.getCall().getValueArguments() + //TODO: drop functional literal out of parenthesis too + + val arguments = resolvedCall.getCall().getValueArgumentsInParentheses() val argumentsToDrop = ArrayList() - - //TODO: can drop arguments leaving last functional literal one (outside of parenthesis) - for (argument in arguments.reverse()) { if (!canDrop(argument) || !argument.matchesDefault(resolvedCall, parameterToDefaultValue)) { if (!argument.isNamed()) break else continue // for a named argument we can try to drop arguments before it as well diff --git a/idea/src/org/jetbrains/kotlin/idea/quickfix/DeprecatedSymbolUsageFixBase.kt b/idea/src/org/jetbrains/kotlin/idea/quickfix/DeprecatedSymbolUsageFixBase.kt index 40590e29d17..5d53052dc52 100644 --- a/idea/src/org/jetbrains/kotlin/idea/quickfix/DeprecatedSymbolUsageFixBase.kt +++ b/idea/src/org/jetbrains/kotlin/idea/quickfix/DeprecatedSymbolUsageFixBase.kt @@ -230,6 +230,9 @@ public abstract class DeprecatedSymbolUsageFixBase( // TODO: process introduced variables too introduceNamedArguments(result) + // TODO: process introduced variables too + restoreFunctionLiteralArguments(result) + //TODO: do this earlier dropArgumentsForDefaultValues(result) @@ -250,9 +253,6 @@ public abstract class DeprecatedSymbolUsageFixBase( // TODO: process introduced variables too simplifySpreadArrayOfArguments(result) - // TODO: process introduced variables too - restoreFunctionLiteralArguments(result) - // clean up user data //TODO: not correct - we do not process introduced declarations before!!! result.forEachDescendantOfType { @@ -541,6 +541,12 @@ public abstract class DeprecatedSymbolUsageFixBase( argument as JetValueArgument val argumentList = argument.getParent() as JetValueArgumentList argumentList.removeArgument(argument) + if (argumentList.getArguments().isEmpty()) { + val callExpression = argumentList.getParent() as JetCallExpression + if (callExpression.getFunctionLiteralArguments().isNotEmpty()) { + argumentList.delete() + } + } } } diff --git a/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/dropAll.kt b/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/dropAll.kt new file mode 100644 index 00000000000..8802cf805d7 --- /dev/null +++ b/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/dropAll.kt @@ -0,0 +1,12 @@ +// "Replace with 'newFun(p1, p2)'" "true" + +interface I { + @deprecated("", ReplaceWith("newFun(p1, p2)")) + fun oldFun(p1: String = "", p2: Int = 0) + + fun newFun(p1: String = "", p2: Int = 0, p3: Int = -1) +} + +fun foo(i: I) { + i.oldFun() +} diff --git a/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/dropAll.kt.after b/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/dropAll.kt.after new file mode 100644 index 00000000000..85ff939ee43 --- /dev/null +++ b/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/dropAll.kt.after @@ -0,0 +1,12 @@ +// "Replace with 'newFun(p1, p2)'" "true" + +interface I { + @deprecated("", ReplaceWith("newFun(p1, p2)")) + fun oldFun(p1: String = "", p2: Int = 0) + + fun newFun(p1: String = "", p2: Int = 0, p3: Int = -1) +} + +fun foo(i: I) { + i.newFun() +} diff --git a/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/functionalLiteralArgument.kt b/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/functionalLiteralArgument.kt new file mode 100644 index 00000000000..3dba3fdd91e --- /dev/null +++ b/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/functionalLiteralArgument.kt @@ -0,0 +1,12 @@ +// "Replace with 'newFun(p2, p1, handler)'" "true" + +interface I { + @deprecated("", ReplaceWith("newFun(p2, p1, handler)")) + fun oldFun(p1: String = "", p2: Int = 0, handler: () -> Unit) + + fun newFun(a: Int = 0, b: String = "", handler: () -> Unit) +} + +fun foo(i: I) { + i.oldFun { } +} diff --git a/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/functionalLiteralArgument.kt.after b/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/functionalLiteralArgument.kt.after new file mode 100644 index 00000000000..4e04c3b938b --- /dev/null +++ b/idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/functionalLiteralArgument.kt.after @@ -0,0 +1,12 @@ +// "Replace with 'newFun(p2, p1, handler)'" "true" + +interface I { + @deprecated("", ReplaceWith("newFun(p2, p1, handler)")) + fun oldFun(p1: String = "", p2: Int = 0, handler: () -> Unit) + + fun newFun(a: Int = 0, b: String = "", handler: () -> Unit) +} + +fun foo(i: I) { + i.newFun { } +} diff --git a/idea/tests/org/jetbrains/kotlin/idea/quickfix/QuickFixTestGenerated.java b/idea/tests/org/jetbrains/kotlin/idea/quickfix/QuickFixTestGenerated.java index 9fade75bff0..52ed50ba1ed 100644 --- a/idea/tests/org/jetbrains/kotlin/idea/quickfix/QuickFixTestGenerated.java +++ b/idea/tests/org/jetbrains/kotlin/idea/quickfix/QuickFixTestGenerated.java @@ -3219,6 +3219,18 @@ public class QuickFixTestGenerated extends AbstractQuickFixTest { JetTestUtils.assertAllTestsPresentByMetadata(this.getClass(), new File("idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters"), Pattern.compile("^([\\w\\-_]+)\\.kt$"), true); } + @TestMetadata("dropAll.kt") + public void testDropAll() throws Exception { + String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/dropAll.kt"); + doTest(fileName); + } + + @TestMetadata("functionalLiteralArgument.kt") + public void testFunctionalLiteralArgument() throws Exception { + String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/functionalLiteralArgument.kt"); + doTest(fileName); + } + @TestMetadata("namedArgument.kt") public void testNamedArgument() throws Exception { String fileName = JetTestUtils.navigationMetadata("idea/testData/quickfix/deprecatedSymbolUsage/optionalParameters/namedArgument.kt");