Groovy: fix inline in GString, replaceWithExpression
[fedora-idea.git] / plugins / groovy / src / org / jetbrains / plugins / groovy / refactoring / inline / GroovyInlineVariableUtil.java
blob9020f226140976cc2683ab12edc76e2fa8ff7fa3
1 /*
2 * Copyright 2000-2007 JetBrains s.r.o.
3 * Licensed under the Apache License, Version 2.0 (the "License");
4 * you may not use this file except in compliance with the License.
5 * You may obtain a copy of the License at
7 * http://www.apache.org/licenses/LICENSE-2.0
9 * Unless required by applicable law or agreed to in writing, software
10 * distributed under the License is distributed on an "AS IS" BASIS,
11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12 * See the License for the specific language governing permissions and
13 * limitations under the License.
16 package org.jetbrains.plugins.groovy.refactoring.inline;
18 import com.intellij.lang.refactoring.InlineHandler;
19 import com.intellij.openapi.application.Application;
20 import com.intellij.openapi.application.ApplicationManager;
21 import com.intellij.openapi.editor.Editor;
22 import com.intellij.openapi.fileEditor.FileEditorManager;
23 import com.intellij.openapi.project.Project;
24 import com.intellij.openapi.wm.WindowManager;
25 import com.intellij.psi.PsiElement;
26 import com.intellij.psi.PsiReference;
27 import com.intellij.psi.search.searches.ReferencesSearch;
28 import com.intellij.refactoring.HelpID;
29 import com.intellij.refactoring.util.CommonRefactoringUtil;
30 import com.intellij.refactoring.util.RefactoringMessageDialog;
31 import com.intellij.usageView.UsageInfo;
32 import org.jetbrains.annotations.Nullable;
33 import org.jetbrains.plugins.groovy.lang.psi.GroovyPsiElementFactory;
34 import org.jetbrains.plugins.groovy.lang.psi.api.statements.GrVariable;
35 import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrAssignmentExpression;
36 import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrExpression;
37 import org.jetbrains.plugins.groovy.lang.psi.api.statements.expressions.GrParenthesizedExpression;
38 import org.jetbrains.plugins.groovy.refactoring.GroovyRefactoringBundle;
39 import org.jetbrains.plugins.groovy.refactoring.GroovyRefactoringUtil;
41 import java.util.ArrayList;
42 import java.util.Collection;
43 import java.util.HashMap;
44 import java.util.Map;
46 /**
47 * @author ilyas
49 public class GroovyInlineVariableUtil {
51 public static final String REFACTORING_NAME = GroovyRefactoringBundle.message("inline.variable.title");
53 private GroovyInlineVariableUtil() {
57 /**
58 * Creates new inliner for local variable occurences
60 static InlineHandler.Inliner createInlinerForLocalVariable(final GrVariable variable) {
61 return new InlineHandler.Inliner() {
63 @Nullable
64 public Map<PsiElement, String> getConflicts(PsiReference reference, PsiElement referenced) {
65 Map<PsiElement, String> conflicts = new HashMap<PsiElement, String>();
66 GrExpression expr = (GrExpression) reference.getElement();
67 if (expr.getParent() instanceof GrAssignmentExpression) {
68 GrAssignmentExpression parent = (GrAssignmentExpression) expr.getParent();
69 if (expr.equals(parent.getLValue())) {
70 conflicts.put(expr, GroovyRefactoringBundle.message("local.varaible.is.lvalue"));
73 return conflicts;
76 public void inlineUsage(final UsageInfo usage, final PsiElement referenced) {
77 GrExpression exprToBeReplaced = (GrExpression)usage.getElement();
78 if (exprToBeReplaced == null) return;
79 assert variable.getInitializerGroovy() != null;
80 GrExpression initializerGroovy = variable.getInitializerGroovy();
81 assert initializerGroovy != null;
82 GrExpression tempExpr = initializerGroovy;
83 while (tempExpr instanceof GrParenthesizedExpression) {
84 tempExpr = ((GrParenthesizedExpression)tempExpr).getOperand();
86 Project project = variable.getProject();
87 GroovyPsiElementFactory factory = GroovyPsiElementFactory.getInstance(project);
88 GrExpression newExpr;
89 newExpr = factory.createExpressionFromText(tempExpr.getText());
90 newExpr = exprToBeReplaced.replaceWithExpression(newExpr, true);
91 FileEditorManager manager = FileEditorManager.getInstance(project);
92 Editor editor = manager.getSelectedTextEditor();
93 GroovyRefactoringUtil.highlightOccurrences(project, editor, new PsiElement[]{newExpr});
94 WindowManager.getInstance().getStatusBar(project)
95 .setInfo(GroovyRefactoringBundle.message("press.escape.to.remove.the.highlighting"));
101 * Returns Settings object for referenced definition in case of local variable
103 @Nullable
104 static InlineHandler.Settings inlineLocalVariableSettings(final GrVariable variable, Editor editor, boolean invokedOnReference) {
105 final String localName = variable.getName();
106 final Project project = variable.getProject();
107 final Collection<PsiReference> refs = ReferencesSearch.search(variable).findAll();
108 ArrayList<PsiElement> exprs = new ArrayList<PsiElement>();
109 for (PsiReference ref : refs) {
110 exprs.add(ref.getElement());
113 GroovyRefactoringUtil.highlightOccurrences(project, editor, exprs.toArray(new PsiElement[exprs.size()]));
114 if (variable.getInitializerGroovy() == null) {
115 String message = GroovyRefactoringBundle.message("cannot.find.a.single.definition.to.inline.local.var");
116 CommonRefactoringUtil.showErrorHint(variable.getProject(), editor, message, REFACTORING_NAME, HelpID.INLINE_VARIABLE);
117 return null;
119 if (refs.isEmpty()) {
120 String message = GroovyRefactoringBundle.message("variable.is.never.used.0", variable.getName());
121 CommonRefactoringUtil.showErrorHint(variable.getProject(), editor, message, REFACTORING_NAME, HelpID.INLINE_VARIABLE);
122 return null;
125 return inlineDialogResult(localName, project, refs);
129 * Shows dialog with question to inline
131 @Nullable
132 private static InlineHandler.Settings inlineDialogResult(String localName, Project project, Collection<PsiReference> refs) {
133 Application application = ApplicationManager.getApplication();
134 if (!application.isUnitTestMode()) {
135 final String question = GroovyRefactoringBundle.message("inline.local.variable.prompt.0.1", localName, refs.size());
136 RefactoringMessageDialog dialog = new RefactoringMessageDialog(
137 REFACTORING_NAME,
138 question,
139 HelpID.INLINE_VARIABLE,
140 "OptionPane.questionIcon",
141 true,
142 project);
143 dialog.show();
144 if (!dialog.isOK()) {
145 WindowManager.getInstance().getStatusBar(project).setInfo(GroovyRefactoringBundle.message("press.escape.to.remove.the.highlighting"));
146 return null;
150 return new InlineHandler.Settings() {
151 public boolean isOnlyOneReferenceToInline() {
152 return false;