From 53e3a67a7fd3cb970ea7f7c8be876dd16ffcef0a Mon Sep 17 00:00:00 2001 From: Valentin Kipyatkov Date: Wed, 20 Apr 2016 15:22:44 +0300 Subject: [PATCH] Better formatting in some cases --- .../intentions/loopToCallChain/interfaces.kt | 9 +++++--- .../loopToCallChain/matchAndConvert.kt | 10 +++++---- .../result/AddToCollectionTransformation.kt | 3 +++ .../result/FindAndAssignTransformation.kt | 3 +++ .../result/FindAndReturnTransformation.kt | 3 +++ .../idea/intentions/loopToCallChain/utils.kt | 21 ++++++++++++------- .../loopToCallChain/firstOrNull_let.kt.after | 4 +++- .../loopToCallChain/firstOrNull_let2.kt.after | 4 +++- .../firstOrNull_letOrNotNull.kt.after | 4 +++- .../firstOrNull_returnExpression.kt.after | 4 +++- ...tOrNull_returnExpressionOrNotNull.kt.after | 4 +++- .../firstOrNull_safeDotExpression.kt.after | 4 +++- 12 files changed, 53 insertions(+), 20 deletions(-) diff --git a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/interfaces.kt b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/interfaces.kt index d00e3507309..a0afcd1dc80 100644 --- a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/interfaces.kt +++ b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/interfaces.kt @@ -30,7 +30,7 @@ interface ChainedCallGenerator { /** * @param pattern pattern string for generating the part of the call to the right from the dot */ - fun generate(pattern: String, vararg args: Any): KtExpression + fun generate(pattern: String, vararg args: Any, receiver: KtExpression = this.receiver, safeCall: Boolean = false): KtExpression } /** @@ -42,7 +42,7 @@ interface Transformation { val presentation: String - open fun buildPresentation(prevTransformationsPresentation: String?): String { + fun buildPresentation(prevTransformationsPresentation: String?): String { return if (prevTransformationsPresentation != null) prevTransformationsPresentation + "." + presentation else @@ -50,6 +50,10 @@ interface Transformation { } fun generateCode(chainedCallGenerator: ChainedCallGenerator): KtExpression + + + val chainCallCount: Int + get() = 1 } /** @@ -59,7 +63,6 @@ interface SequenceTransformation : Transformation { fun mergeWithPrevious(previousTransformation: SequenceTransformation): SequenceTransformation? = null val affectsIndex: Boolean - } /** diff --git a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/matchAndConvert.kt b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/matchAndConvert.kt index 77c1e3f7ee5..07ce921e72f 100644 --- a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/matchAndConvert.kt +++ b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/matchAndConvert.kt @@ -169,7 +169,8 @@ private fun ResultTransformationMatch.generateCallChain(loop: KtForExpression): sequenceTransformations = sequenceTransformations.dropLast(1) } - val lineBreak = if (sequenceTransformations.isNotEmpty()) "\n" else "" + val chainCallCount = sequenceTransformations.sumBy { it.chainCallCount } + resultTransformation.chainCallCount + val lineBreak = if (chainCallCount > 1) "\n" else "" var callChain = loop.loopRange!! @@ -178,9 +179,10 @@ private fun ResultTransformationMatch.generateCallChain(loop: KtForExpression): override val receiver: KtExpression get() = callChain - override fun generate(pattern: String, vararg args: Any): KtExpression { - val newPattern = "\$${args.size}$lineBreak.$pattern" - return psiFactory.createExpressionByPattern(newPattern, *args, callChain) + override fun generate(pattern: String, vararg args: Any, receiver: KtExpression, safeCall: Boolean): KtExpression { + val dot = if (safeCall) "?." else "." + val newPattern = "$" + args.size + lineBreak + dot + pattern + return psiFactory.createExpressionByPattern(newPattern, *args, receiver) } } diff --git a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/AddToCollectionTransformation.kt b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/AddToCollectionTransformation.kt index 1c2d5d70268..3374df3fb56 100644 --- a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/AddToCollectionTransformation.kt +++ b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/AddToCollectionTransformation.kt @@ -65,6 +65,9 @@ class AddToCollectionTransformation( "+=" } + override val chainCallCount: Int + get() = 0 + override fun generateCode(chainedCallGenerator: ChainedCallGenerator): KtExpression { return KtPsiFactory(loop).createExpressionByPattern("$0 += $1", targetCollection, chainedCallGenerator.receiver) } diff --git a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/FindAndAssignTransformation.kt b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/FindAndAssignTransformation.kt index d43a12ebb22..bc1cfa4f235 100644 --- a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/FindAndAssignTransformation.kt +++ b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/FindAndAssignTransformation.kt @@ -43,6 +43,9 @@ class FindAndAssignTransformation( override val presentation: String get() = generator.functionName + (if (filter != null) "{}" else "()") + override val chainCallCount: Int + get() = generator.chainCallCount + override fun generateCode(chainedCallGenerator: ChainedCallGenerator): KtExpression { return generator.generate(chainedCallGenerator, filter) } diff --git a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/FindAndReturnTransformation.kt b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/FindAndReturnTransformation.kt index aa4ecf9370e..cc403ff8c75 100644 --- a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/FindAndReturnTransformation.kt +++ b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/result/FindAndReturnTransformation.kt @@ -47,6 +47,9 @@ class FindAndReturnTransformation( override val presentation: String get() = generator.functionName + (if (filter != null) "{}" else "()") + override val chainCallCount: Int + get() = generator.chainCallCount + override fun generateCode(chainedCallGenerator: ChainedCallGenerator): KtExpression { return generator.generate(chainedCallGenerator, filter) } diff --git a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/utils.kt b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/utils.kt index c4573b41272..5365cf8a6cc 100644 --- a/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/utils.kt +++ b/idea/src/org/jetbrains/kotlin/idea/intentions/loopToCallChain/utils.kt @@ -114,7 +114,11 @@ fun KtProperty.hasWriteUsages(): Boolean { interface FindOperatorGenerator { val functionName: String + fun generate(chainedCallGenerator: ChainedCallGenerator, filter: KtExpression?): KtExpression + + val chainCallCount: Int + get() = 1 } fun buildFindOperationGenerator( @@ -150,10 +154,7 @@ fun buildFindOperationGenerator( // we cannot use ?: if found value can be null if (inputVariableCanHoldNull) return null - return object: FindOperatorGenerator { - override val functionName: String - get() = this@useElvisOperatorIfNeeded.functionName - + return object: FindOperatorGenerator by this { override fun generate(chainedCallGenerator: ChainedCallGenerator, filter: KtExpression?): KtExpression { val generated = this@useElvisOperatorIfNeeded.generate(chainedCallGenerator, filter) return KtPsiFactory(generated).createExpressionByPattern("$0 ?: $1", generated, valueIfNotFound) @@ -184,9 +185,12 @@ fun buildFindOperationGenerator( override val functionName: String get() = "firstOrNull" + override val chainCallCount: Int + get() = 2 + override fun generate(chainedCallGenerator: ChainedCallGenerator, filter: KtExpression?): KtExpression { val findFirstCall = generateChainedCall(functionName, chainedCallGenerator, filter) - return KtPsiFactory(findFirstCall).createExpressionByPattern("$0?.$1", findFirstCall, selector) + return chainedCallGenerator.generate("$0", selector, receiver = findFirstCall, safeCall = true) } }.useElvisOperatorIfNeeded() } @@ -197,12 +201,15 @@ fun buildFindOperationGenerator( return object: FindOperatorGenerator { override val functionName: String - get() = "firstOrNull" //TODO + get() = "firstOrNull" + + override val chainCallCount: Int + get() = 2 // also includes "let" override fun generate(chainedCallGenerator: ChainedCallGenerator, filter: KtExpression?): KtExpression { val findFirstCall = generateChainedCall(functionName, chainedCallGenerator, filter) val letBody = generateLambda(inputVariable, valueIfFound) - return KtPsiFactory(findFirstCall).createExpressionByPattern("$0?.let $1:'{}'", findFirstCall, letBody) + return chainedCallGenerator.generate("let $0:'{}'", letBody, receiver = findFirstCall, safeCall = true) } }.useElvisOperatorIfNeeded() } diff --git a/idea/testData/intentions/loopToCallChain/firstOrNull_let.kt.after b/idea/testData/intentions/loopToCallChain/firstOrNull_let.kt.after index 8bea49b813d..bdf7a3cbc0d 100644 --- a/idea/testData/intentions/loopToCallChain/firstOrNull_let.kt.after +++ b/idea/testData/intentions/loopToCallChain/firstOrNull_let.kt.after @@ -1,7 +1,9 @@ // WITH_RUNTIME // INTENTION_TEXT: "Replace with 'firstOrNull{}'" fun foo(list: List) { - val result: String? = list.firstOrNull { it.length > 0 }?.let { bar(it) } + val result: String? = list + .firstOrNull { it.length > 0 } + ?.let { bar(it) } } fun bar(s: String): String = s diff --git a/idea/testData/intentions/loopToCallChain/firstOrNull_let2.kt.after b/idea/testData/intentions/loopToCallChain/firstOrNull_let2.kt.after index 2eda11a721c..28fab70bc11 100644 --- a/idea/testData/intentions/loopToCallChain/firstOrNull_let2.kt.after +++ b/idea/testData/intentions/loopToCallChain/firstOrNull_let2.kt.after @@ -1,7 +1,9 @@ // WITH_RUNTIME // INTENTION_TEXT: "Replace with 'firstOrNull{}'" fun foo(list: List) { - val result: String? = list.firstOrNull { it.length > 0 }?.let { it.substring(0, it.length - 1) } + val result: String? = list + .firstOrNull { it.length > 0 } + ?.let { it.substring(0, it.length - 1) } } fun bar(s: String): String = s diff --git a/idea/testData/intentions/loopToCallChain/firstOrNull_letOrNotNull.kt.after b/idea/testData/intentions/loopToCallChain/firstOrNull_letOrNotNull.kt.after index a452fe5e3e5..e653bbbff70 100644 --- a/idea/testData/intentions/loopToCallChain/firstOrNull_letOrNotNull.kt.after +++ b/idea/testData/intentions/loopToCallChain/firstOrNull_letOrNotNull.kt.after @@ -1,7 +1,9 @@ // WITH_RUNTIME // INTENTION_TEXT: "Replace with 'firstOrNull{}'" fun foo(list: List) { - val result = list.firstOrNull { it.length > 0 }?.let { bar(it) } ?: "" + val result = list + .firstOrNull { it.length > 0 } + ?.let { bar(it) } ?: "" } fun bar(s: String): String = s diff --git a/idea/testData/intentions/loopToCallChain/firstOrNull_returnExpression.kt.after b/idea/testData/intentions/loopToCallChain/firstOrNull_returnExpression.kt.after index 459c4048fab..26ed81335e7 100644 --- a/idea/testData/intentions/loopToCallChain/firstOrNull_returnExpression.kt.after +++ b/idea/testData/intentions/loopToCallChain/firstOrNull_returnExpression.kt.after @@ -1,5 +1,7 @@ // WITH_RUNTIME // INTENTION_TEXT: "Replace with 'firstOrNull{}'" fun foo(list: List): Int? { - return list.firstOrNull { it.isNotEmpty() }?.length + return list + .firstOrNull { it.isNotEmpty() } + ?.length } \ No newline at end of file diff --git a/idea/testData/intentions/loopToCallChain/firstOrNull_returnExpressionOrNotNull.kt.after b/idea/testData/intentions/loopToCallChain/firstOrNull_returnExpressionOrNotNull.kt.after index bf4e8bfc9e2..a77bef0eddf 100644 --- a/idea/testData/intentions/loopToCallChain/firstOrNull_returnExpressionOrNotNull.kt.after +++ b/idea/testData/intentions/loopToCallChain/firstOrNull_returnExpressionOrNotNull.kt.after @@ -1,5 +1,7 @@ // WITH_RUNTIME // INTENTION_TEXT: "Replace with 'firstOrNull{}'" fun foo(list: List): Int { - return list.firstOrNull { it.isNotEmpty() }?.length ?: -1 + return list + .firstOrNull { it.isNotEmpty() } + ?.length ?: -1 } \ No newline at end of file diff --git a/idea/testData/intentions/loopToCallChain/firstOrNull_safeDotExpression.kt.after b/idea/testData/intentions/loopToCallChain/firstOrNull_safeDotExpression.kt.after index d8c8fbaf6c0..00603d87727 100644 --- a/idea/testData/intentions/loopToCallChain/firstOrNull_safeDotExpression.kt.after +++ b/idea/testData/intentions/loopToCallChain/firstOrNull_safeDotExpression.kt.after @@ -1,5 +1,7 @@ // WITH_RUNTIME // INTENTION_TEXT: "Replace with 'firstOrNull{}'" fun foo(list: List) { - val result: String? = list.firstOrNull { it != "" }?.substring(1) + val result: String? = list + .firstOrNull { it != "" } + ?.substring(1) }