From 797465a06bbfafb516c40397a6f76f663518fb90 Mon Sep 17 00:00:00 2001 From: Alexey Sedunov Date: Thu, 21 Apr 2016 14:57:53 +0300 Subject: [PATCH] Rename: Do not use Change Signature for parameter renaming --- .../rename/RenameKotlinParameterProcessor.kt | 54 +++++++------------ 1 file changed, 18 insertions(+), 36 deletions(-) diff --git a/idea/src/org/jetbrains/kotlin/idea/refactoring/rename/RenameKotlinParameterProcessor.kt b/idea/src/org/jetbrains/kotlin/idea/refactoring/rename/RenameKotlinParameterProcessor.kt index 7d0a7d466ca..ffdfecd736e 100644 --- a/idea/src/org/jetbrains/kotlin/idea/refactoring/rename/RenameKotlinParameterProcessor.kt +++ b/idea/src/org/jetbrains/kotlin/idea/refactoring/rename/RenameKotlinParameterProcessor.kt @@ -17,54 +17,36 @@ package org.jetbrains.kotlin.idea.refactoring.rename import com.intellij.psi.PsiElement +import com.intellij.psi.PsiMethod +import com.intellij.psi.PsiNamedElement +import com.intellij.psi.search.SearchScope import com.intellij.refactoring.listeners.RefactoringElementListener import com.intellij.usageView.UsageInfo -import com.intellij.util.xml.impl.GenericDomValueReference import org.jetbrains.kotlin.descriptors.FunctionDescriptor import org.jetbrains.kotlin.idea.caches.resolve.resolveToDescriptor -import org.jetbrains.kotlin.idea.refactoring.changeSignature.KotlinChangeSignatureConfiguration -import org.jetbrains.kotlin.idea.refactoring.changeSignature.KotlinMethodDescriptor -import org.jetbrains.kotlin.idea.refactoring.changeSignature.modify -import org.jetbrains.kotlin.idea.refactoring.changeSignature.runChangeSignature +import org.jetbrains.kotlin.idea.refactoring.getAffectedCallables +import org.jetbrains.kotlin.psi.KtCallableDeclaration import org.jetbrains.kotlin.psi.KtNamedFunction import org.jetbrains.kotlin.psi.KtParameter -import org.jetbrains.kotlin.psi.psiUtil.getElementTextWithContext import org.jetbrains.kotlin.resolve.OverrideResolver class RenameKotlinParameterProcessor : RenameKotlinPsiProcessor() { - override fun canProcessElement(element: PsiElement): Boolean { - return element is KtParameter && element.parent.parent is KtNamedFunction - } + override fun canProcessElement(element: PsiElement) = element is KtParameter && element.ownerFunction is KtNamedFunction - override fun renameElement(element: PsiElement, newName: String, usages: Array, listener: RefactoringElementListener?) { - // Workaround for usages in XML files - // TODO: Do not use Change Signature for parameter rename as it's less efficient and loses some usages - for (usage in usages) { - (usage.reference as? GenericDomValueReference<*>)?.handleElementRename(newName) - } + override fun prepareRenaming(element: PsiElement, newName: String, allRenames: MutableMap, scope: SearchScope) { + if (element !is KtParameter) return - val function = (element as KtParameter).parent.parent as KtNamedFunction - val paramIndex = function.valueParameters.indexOf(element) - assert(paramIndex != -1, { "couldn't find parameter in parent ${element.getElementTextWithContext()}" }) - - val functionDescriptor = function.resolveToDescriptor() as? FunctionDescriptor ?: return - val parameterDescriptor = functionDescriptor.valueParameters[paramIndex] - - val parameterNameChangedOnOverride = parameterDescriptor.overriddenDescriptors.any { - overriddenParameter -> OverrideResolver.shouldReportParameterNameOverrideWarning(parameterDescriptor, overriddenParameter) - } - - val changeSignatureConfiguration = object : KotlinChangeSignatureConfiguration { - override fun configure(originalDescriptor: KotlinMethodDescriptor): KotlinMethodDescriptor { - val paramInfoIndex = if (functionDescriptor.extensionReceiverParameter != null) paramIndex + 1 else paramIndex - return originalDescriptor.modify { it.renameParameter(paramInfoIndex, newName) } + val function = element.ownerFunction ?: return + val originalDescriptor = function.resolveToDescriptor() as FunctionDescriptor + val affectedCallables = getAffectedCallables(element.project, OverrideResolver.getDeepestSuperDeclarations(originalDescriptor)) + for (callable in affectedCallables) { + val parameter: PsiNamedElement? = when (callable) { + is KtCallableDeclaration -> callable.valueParameters.firstOrNull { it.name == element.name } + is PsiMethod -> callable.parameterList.parameters.firstOrNull { it.name == element.name } + else -> null } - - override fun performSilently(affectedFunctions: Collection) = true - - override fun forcePerformForSelectedFunctionOnly() = parameterNameChangedOnOverride + if (parameter == null) continue + allRenames[parameter] = newName } - - runChangeSignature(element.project, functionDescriptor, changeSignatureConfiguration, element, "Rename parameter") } }