IfThenToElvis & FoldInitializerAndIfToElvis should add new line for long expression

Relates to #KT-19643 #KT-16067
This commit is contained in:
Dmitry Gridin
2019-06-05 17:38:06 +07:00
parent 9c1ff75efc
commit 1ad7a50087
8 changed files with 57 additions and 6 deletions
@@ -5,6 +5,7 @@
package org.jetbrains.kotlin.idea.inspections
import com.intellij.application.options.CodeStyle
import com.intellij.codeInspection.ProblemHighlightType
import com.intellij.openapi.editor.Editor
import com.intellij.openapi.project.Project
@@ -19,6 +20,7 @@ import org.jetbrains.kotlin.idea.caches.resolve.analyze
import org.jetbrains.kotlin.idea.caches.resolve.resolveToDescriptorIfAny
import org.jetbrains.kotlin.idea.core.replaced
import org.jetbrains.kotlin.idea.core.setType
import org.jetbrains.kotlin.idea.intentions.branchedTransformations.elvisPattern
import org.jetbrains.kotlin.idea.intentions.branchedTransformations.expressionComparedToNull
import org.jetbrains.kotlin.idea.intentions.branchedTransformations.shouldBeTransformed
import org.jetbrains.kotlin.idea.intentions.branchedTransformations.textRange
@@ -83,10 +85,8 @@ class FoldInitializerAndIfToElvisInspection : AbstractApplicabilityBasedInspecti
val commentSaver = CommentSaver(childRangeBefore)
val childRangeAfter = childRangeBefore.withoutLastStatement()
val pattern = if (element.then?.hasComments() == true)
"$0\n?: $1"
else
"$0 ?: $1"
val margin = CodeStyle.getSettings(element.containingKtFile).defaultRightMargin
val pattern = elvisPattern(declaration.textLength + ifNullExpr.textLength + 5 >= margin || element.then?.hasComments() == true)
val elvis = factory.createExpressionByPattern(pattern, initializer, ifNullExpr) as KtBinaryExpression
if (typeReference != null) {
@@ -5,6 +5,7 @@
package org.jetbrains.kotlin.idea.inspections.branchedTransformations
import com.intellij.application.options.CodeStyle
import com.intellij.codeInspection.ProblemHighlightType
import com.intellij.codeInspection.ui.MultipleCheckboxOptionsPanel
import com.intellij.openapi.editor.Editor
@@ -63,14 +64,17 @@ class IfThenToElvisInspection(
val factory = KtPsiFactory(element)
val commentSaver = CommentSaver(element, saveLineBreaks = false)
val margin = CodeStyle.getSettings(element.containingKtFile).defaultRightMargin
val elvis = runWriteAction {
val replacedBaseClause = ifThenToSelectData.replacedBaseClause(factory)
val negatedClause = ifThenToSelectData.negatedClause!!
val newExpr = element.replaced(
factory.createExpressionByPattern(
"$0 ?: $1",
elvisPattern(replacedBaseClause.textLength + negatedClause.textLength + 5 >= margin),
replacedBaseClause,
ifThenToSelectData.negatedClause!!
negatedClause
)
)
@@ -177,6 +177,8 @@ fun KtExpression.isStableVal(context: BindingContext = this.analyze()): Boolean
return this.toDataFlowValue(context)?.kind == DataFlowValue.Kind.STABLE_VALUE
}
fun elvisPattern(newLine: Boolean): String = if (newLine) "$0\n?: $1" else "$0 ?: $1"
private fun KtExpression.toDataFlowValue(context: BindingContext): DataFlowValue? {
val expressionType = this.getType(context) ?: return null
val dataFlowValueFactory = this.getResolutionFacade().frontendService<DataFlowValueFactory>()
@@ -0,0 +1,13 @@
fun maybeFoo(): String? {
return "foo"
}
val xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx = maybeFoo()
fun main() {
val c = if (xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx != null)<caret> {
xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
} else {
"abcdfdfdfdfdfdfdfdfdfdfdfdfdfdfdfdfdfdfdfdf"
}
}
@@ -0,0 +1,10 @@
fun maybeFoo(): String? {
return "foo"
}
val xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx = maybeFoo()
fun main() {
val c = xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx
?: "abcdfdfdfdfdfdfdfdfdfdfdfdfdfdfdfdfdfdfdfdf"
}
@@ -0,0 +1,6 @@
fun foo(): Any {
val yyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyy = 7
val xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx = 24
if (xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx<caret> == null) return yyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyy
return 42
}
@@ -0,0 +1,6 @@
fun foo(): Any {
val yyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyy = 7
val xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx = 24
?: return yyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyy
return 42
}
@@ -332,6 +332,11 @@ public class LocalInspectionTestGenerated extends AbstractLocalInspectionTest {
runTest("idea/testData/inspectionsLocal/branched/ifThenToElvis/lhsNotEqualsNull.kt");
}
@TestMetadata("longLine.kt")
public void testLongLine() throws Exception {
runTest("idea/testData/inspectionsLocal/branched/ifThenToElvis/longLine.kt");
}
@TestMetadata("missingElseClause.kt")
public void testMissingElseClause() throws Exception {
runTest("idea/testData/inspectionsLocal/branched/ifThenToElvis/missingElseClause.kt");
@@ -3798,6 +3803,11 @@ public class LocalInspectionTestGenerated extends AbstractLocalInspectionTest {
runTest("idea/testData/inspectionsLocal/foldInitializerAndIfToElvis/IsSuperTypeFake.kt");
}
@TestMetadata("LongName.kt")
public void testLongName() throws Exception {
runTest("idea/testData/inspectionsLocal/foldInitializerAndIfToElvis/LongName.kt");
}
@TestMetadata("MultiStatementBlock.kt")
public void testMultiStatementBlock() throws Exception {
runTest("idea/testData/inspectionsLocal/foldInitializerAndIfToElvis/MultiStatementBlock.kt");