2 * Copyright 2000-2009 JetBrains s.r.o.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
16 package com
.intellij
.refactoring
.rename
.naming
;
18 import com
.intellij
.lang
.ASTNode
;
19 import com
.intellij
.openapi
.util
.text
.StringUtil
;
20 import com
.intellij
.psi
.*;
21 import com
.intellij
.psi
.codeStyle
.JavaCodeStyleManager
;
22 import com
.intellij
.psi
.impl
.source
.tree
.JavaElementType
;
23 import com
.intellij
.psi
.impl
.source
.tree
.StdTokenSets
;
24 import com
.intellij
.psi
.impl
.source
.tree
.TreeUtil
;
25 import com
.intellij
.psi
.util
.PsiTreeUtil
;
26 import com
.intellij
.refactoring
.RefactoringBundle
;
27 import com
.intellij
.usageView
.UsageInfo
;
28 import com
.intellij
.util
.containers
.HashSet
;
30 import java
.util
.Collection
;
31 import java
.util
.List
;
33 import java
.util
.ArrayList
;
38 public class AutomaticVariableRenamer
extends AutomaticRenamer
{
39 private final Set
<PsiNamedElement
> myToUnpluralize
= new HashSet
<PsiNamedElement
>();
41 public AutomaticVariableRenamer(PsiClass aClass
, String newClassName
, Collection
<UsageInfo
> usages
) {
42 for (final UsageInfo info
: usages
) {
43 final PsiElement element
= info
.getElement();
44 if (!(element
instanceof PsiJavaCodeReferenceElement
)) continue;
45 final PsiDeclarationStatement statement
= PsiTreeUtil
.getParentOfType(element
, PsiDeclarationStatement
.class);
46 if (statement
!= null) {
47 for(PsiElement declaredElement
: statement
.getDeclaredElements()) {
48 if (declaredElement
instanceof PsiVariable
) {
49 checkRenameVariable(element
, (PsiVariable
) declaredElement
);
54 PsiVariable variable
= PsiTreeUtil
.getParentOfType(element
, PsiVariable
.class);
55 if (variable
!= null) {
56 checkRenameVariable(element
, variable
);
57 if (variable
instanceof PsiField
) {
58 for(PsiField field
: getFieldsInSameDeclaration((PsiField
) variable
)) {
59 checkRenameVariable(element
, field
);
65 suggestAllNames(aClass
.getName(), newClassName
);
68 private static List
<PsiField
> getFieldsInSameDeclaration(final PsiField variable
) {
69 List
<PsiField
> result
= new ArrayList
<PsiField
>();
70 ASTNode node
= variable
.getNode();
73 ASTNode comma
= TreeUtil
.skipElements(node
.getTreeNext(), StdTokenSets
.WHITE_SPACE_OR_COMMENT_BIT_SET
);
74 if (comma
== null || comma
.getElementType() != JavaTokenType
.COMMA
) break;
75 ASTNode nextField
= TreeUtil
.skipElements(comma
.getTreeNext(), StdTokenSets
.WHITE_SPACE_OR_COMMENT_BIT_SET
);
76 if (nextField
== null || nextField
.getElementType() != JavaElementType
.FIELD
) break;
77 result
.add((PsiField
) nextField
.getPsi());
84 private void checkRenameVariable(final PsiElement element
, final PsiVariable variable
) {
85 final PsiTypeElement typeElement
= variable
.getTypeElement();
86 if (typeElement
== null) return;
87 final PsiJavaCodeReferenceElement ref
= typeElement
.getInnermostComponentReferenceElement();
88 if (ref
== null) return;
89 if (ref
.equals(element
)) {
90 myElements
.add(variable
);
91 if (variable
.getType() instanceof PsiArrayType
) {
92 myToUnpluralize
.add(variable
);
96 PsiType collectionType
= JavaPsiFacade
.getInstance(variable
.getProject()).getElementFactory()
97 .createTypeByFQClassName("java.util.Collection", variable
.getResolveScope());
98 if (!collectionType
.isAssignableFrom(variable
.getType())) return;
99 final PsiTypeElement
[] typeParameterElements
= ref
.getParameterList().getTypeParameterElements();
100 for (PsiTypeElement typeParameterElement
: typeParameterElements
) {
101 final PsiJavaCodeReferenceElement parameterRef
= typeParameterElement
.getInnermostComponentReferenceElement();
102 if (parameterRef
!= null && parameterRef
.equals(element
)) {
103 myElements
.add(variable
);
104 myToUnpluralize
.add(variable
);
111 public String
getDialogTitle() {
112 return RefactoringBundle
.message("rename.variables.title");
115 public String
getDialogDescription() {
116 return RefactoringBundle
.message("rename.variables.with.the.following.names.to");
119 public String
entityName() {
120 return RefactoringBundle
.message("entity.name.variable");
123 public String
nameToCanonicalName(String name
, PsiNamedElement psiVariable
) {
124 final JavaCodeStyleManager codeStyleManager
= JavaCodeStyleManager
.getInstance(psiVariable
.getProject());
125 final String propertyName
= codeStyleManager
.variableNameToPropertyName(name
, codeStyleManager
.getVariableKind((PsiVariable
)psiVariable
));
126 if (myToUnpluralize
.contains(psiVariable
)) {
127 final String singular
= StringUtil
.unpluralize(propertyName
);
128 if (singular
!= null) return singular
;
129 myToUnpluralize
.remove(psiVariable
); // no need to pluralize since it was initially in singular form
134 public String
canonicalNameToName(String canonicalName
, PsiNamedElement psiVariable
) {
135 final JavaCodeStyleManager codeStyleManager
= JavaCodeStyleManager
.getInstance(psiVariable
.getProject());
136 final String variableName
=
137 codeStyleManager
.propertyNameToVariableName(canonicalName
, codeStyleManager
.getVariableKind((PsiVariable
)psiVariable
));
138 if (myToUnpluralize
.contains(psiVariable
)) return StringUtil
.pluralize(variableName
);