From 3f96e1dabc5db7973c49dc7bff3cba42d5a8a7e3 Mon Sep 17 00:00:00 2001 From: Toshiaki Kameyama Date: Fri, 2 Mar 2018 16:59:40 +0900 Subject: [PATCH] Move statement up/down fails for multiline declarations with lambdas (KT-21013) #KT-21013 Fixed --- .../upDownMover/KotlinExpressionMover.java | 16 +++++++++++----- .../multilineExpressionWithClosure1.kt | 6 ++++++ .../multilineExpressionWithClosure1.kt.after | 6 ++++++ .../multilineExpressionWithClosure2.kt | 8 ++++++++ .../multilineExpressionWithClosure2.kt.after | 8 ++++++++ .../moveUpDown/MoveStatementTestGenerated.java | 12 ++++++++++++ 6 files changed, 51 insertions(+), 5 deletions(-) create mode 100644 idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure1.kt create mode 100644 idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure1.kt.after create mode 100644 idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure2.kt create mode 100644 idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure2.kt.after diff --git a/idea/src/org/jetbrains/kotlin/idea/codeInsight/upDownMover/KotlinExpressionMover.java b/idea/src/org/jetbrains/kotlin/idea/codeInsight/upDownMover/KotlinExpressionMover.java index b865d8cc393..3cd704e18ee 100644 --- a/idea/src/org/jetbrains/kotlin/idea/codeInsight/upDownMover/KotlinExpressionMover.java +++ b/idea/src/org/jetbrains/kotlin/idea/codeInsight/upDownMover/KotlinExpressionMover.java @@ -209,7 +209,7 @@ public class KotlinExpressionMover extends AbstractKotlinUpDownMover { } @Nullable - private static KtBlockExpression getDSLLambdaBlock(@NotNull PsiElement element, boolean down) { + private static KtBlockExpression getDSLLambdaBlock(@NotNull Editor editor, @NotNull PsiElement element, boolean down) { KtCallExpression callExpression = (KtCallExpression) KtPsiUtil.getOutermostDescendantElement(element, down, IS_CALL_EXPRESSION); if (callExpression == null) return null; @@ -219,6 +219,11 @@ public class KotlinExpressionMover extends AbstractKotlinUpDownMover { KtLambdaExpression lambdaExpression = functionLiterals.get(0).getLambdaExpression(); if (lambdaExpression == null) return null; + + Document document = editor.getDocument(); + TextRange range = lambdaExpression.getTextRange(); + if (document.getLineNumber(range.getStartOffset()) == document.getLineNumber(range.getEndOffset())) return null; + return lambdaExpression.getBodyExpression(); } @@ -279,7 +284,7 @@ public class KotlinExpressionMover extends AbstractKotlinUpDownMover { else { PsiElement blockLikeElement; - KtBlockExpression dslBlock = getDSLLambdaBlock(sibling, down); + KtBlockExpression dslBlock = getDSLLambdaBlock(editor, sibling, down); if (dslBlock != null) { // Use JetFunctionLiteral (since it contains braces) blockLikeElement = dslBlock.getParent(); @@ -417,7 +422,8 @@ public class KotlinExpressionMover extends AbstractKotlinUpDownMover { return block.getLBrace() == null && block.getRBrace() == null; } - protected static PsiElement adjustSibling( + private static PsiElement adjustSibling( + @NotNull Editor editor, @NotNull LineRange sourceRange, @NotNull MoveInfo info, boolean down @@ -452,7 +458,7 @@ public class KotlinExpressionMover extends AbstractKotlinUpDownMover { if (sibling == null) { KtCallExpression callExpression = PsiTreeUtil.getParentOfType(element, KtCallExpression.class); if (callExpression != null) { - KtBlockExpression dslBlock = getDSLLambdaBlock(callExpression, down); + KtBlockExpression dslBlock = getDSLLambdaBlock(editor, callExpression, down); if (PsiTreeUtil.isAncestor(dslBlock, element, false)) { //noinspection ConstantConditions PsiElement blockParent = dslBlock.getParent(); @@ -510,7 +516,7 @@ public class KotlinExpressionMover extends AbstractKotlinUpDownMover { LineRange sourceRange = getSourceRange(firstElement, lastElement, editor, oldRange); if (sourceRange == null) return false; - PsiElement sibling = getLastNonWhiteSiblingInLine(adjustSibling(sourceRange, info, down), editor, down); + PsiElement sibling = getLastNonWhiteSiblingInLine(adjustSibling(editor, sourceRange, info, down), editor, down); // Either reached last sibling, or jumped over multi-line whitespace if (sibling == null) return true; diff --git a/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure1.kt b/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure1.kt new file mode 100644 index 00000000000..317d16ff75d --- /dev/null +++ b/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure1.kt @@ -0,0 +1,6 @@ +// MOVE: up +fun test() { + (0..10) + .map { it } + println() +} diff --git a/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure1.kt.after b/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure1.kt.after new file mode 100644 index 00000000000..f919a0b0101 --- /dev/null +++ b/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure1.kt.after @@ -0,0 +1,6 @@ +// MOVE: up +fun test() { + println() + (0..10) + .map { it } +} diff --git a/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure2.kt b/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure2.kt new file mode 100644 index 00000000000..cefb3cefcee --- /dev/null +++ b/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure2.kt @@ -0,0 +1,8 @@ +// MOVE: up +fun test() { + (0..10) + .map { + it + } + println() +} diff --git a/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure2.kt.after b/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure2.kt.after new file mode 100644 index 00000000000..64e90d0740c --- /dev/null +++ b/idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure2.kt.after @@ -0,0 +1,8 @@ +// MOVE: up +fun test() { + (0..10) + .map { + it + println() + } +} diff --git a/idea/tests/org/jetbrains/kotlin/idea/codeInsight/moveUpDown/MoveStatementTestGenerated.java b/idea/tests/org/jetbrains/kotlin/idea/codeInsight/moveUpDown/MoveStatementTestGenerated.java index 460042fd004..cafb74dcc67 100644 --- a/idea/tests/org/jetbrains/kotlin/idea/codeInsight/moveUpDown/MoveStatementTestGenerated.java +++ b/idea/tests/org/jetbrains/kotlin/idea/codeInsight/moveUpDown/MoveStatementTestGenerated.java @@ -1089,6 +1089,18 @@ public class MoveStatementTestGenerated extends AbstractMoveStatementTest { doTestExpression(fileName); } + @TestMetadata("multilineExpressionWithClosure1.kt") + public void testMultilineExpressionWithClosure1() throws Exception { + String fileName = KotlinTestUtils.navigationMetadata("idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure1.kt"); + doTestExpression(fileName); + } + + @TestMetadata("multilineExpressionWithClosure2.kt") + public void testMultilineExpressionWithClosure2() throws Exception { + String fileName = KotlinTestUtils.navigationMetadata("idea/testData/codeInsight/moveUpDown/expressions/multilineExpressionWithClosure2.kt"); + doTestExpression(fileName); + } + @TestMetadata("outOfClosure1.kt") public void testOutOfClosure1() throws Exception { String fileName = KotlinTestUtils.navigationMetadata("idea/testData/codeInsight/moveUpDown/expressions/outOfClosure1.kt");