KickJava   Java API By Example, From Geeks To Geeks.

Java > Open Source Codes > org > netbeans > modules > java > editor > rename > InstantRenameAction


1 /*
2  * The contents of this file are subject to the terms of the Common Development
3  * and Distribution License (the License). You may not use this file except in
4  * compliance with the License.
5  *
6  * You can obtain a copy of the License at http://www.netbeans.org/cddl.html
7  * or http://www.netbeans.org/cddl.txt.
8  *
9  * When distributing Covered Code, include this CDDL Header Notice in each file
10  * and include the License file at http://www.netbeans.org/cddl.txt.
11  * If applicable, add the following below the CDDL Header, with the fields
12  * enclosed by brackets [] replaced by your own identifying information:
13  * "Portions Copyrighted [year] [name of copyright owner]"
14  *
15  * The Original Software is NetBeans. The Initial Developer of the Original
16  * Software is Sun Microsystems, Inc. Portions Copyright 1997-2006 Sun
17  * Microsystems, Inc. All Rights Reserved.
18  */

19 package org.netbeans.modules.java.editor.rename;
20
21 import com.sun.source.util.TreePath;
22 import java.awt.event.ActionEvent JavaDoc;
23 import java.io.IOException JavaDoc;
24 import java.util.EnumSet JavaDoc;
25 import java.util.HashSet JavaDoc;
26 import java.util.Set JavaDoc;
27 import javax.lang.model.element.Element;
28 import javax.lang.model.element.ElementKind;
29 import javax.lang.model.element.ElementKind;
30 import javax.lang.model.element.ExecutableElement;
31 import javax.lang.model.util.ElementFilter;
32 import javax.swing.Action JavaDoc;
33 import javax.swing.text.BadLocationException JavaDoc;
34 import javax.swing.text.Document JavaDoc;
35 import javax.swing.text.JTextComponent JavaDoc;
36 import org.netbeans.api.java.source.CancellableTask;
37 import org.netbeans.api.java.source.CompilationController;
38 import org.netbeans.api.java.source.CompilationInfo;
39 import org.netbeans.api.java.source.JavaSource;
40 import org.netbeans.api.java.source.JavaSource.Phase;
41 import org.netbeans.editor.BaseAction;
42 import org.netbeans.editor.Utilities;
43 import org.netbeans.modules.editor.highlights.spi.Highlight;
44 import org.netbeans.modules.java.editor.semantic.ColoringAttributes;
45 import org.netbeans.modules.java.editor.semantic.FindLocalUsagesQuery;
46 import org.netbeans.modules.refactoring.api.ui.RefactoringActionsFactory;
47 import org.openide.DialogDisplayer;
48 import org.openide.ErrorManager;
49 import org.openide.NotifyDescriptor;
50 import org.openide.cookies.EditorCookie;
51 import org.openide.cookies.EditorCookie;
52 import org.openide.loaders.DataObject;
53 import org.openide.nodes.Node;
54 import org.openide.util.Lookup;
55 import org.openide.util.RequestProcessor;
56 import org.openide.util.lookup.AbstractLookup;
57 import org.openide.util.lookup.InstanceContent;
58
59 /**
60  *
61  * @author Jan Lahoda
62  */

63 public class InstantRenameAction extends BaseAction {
64     
65     /** Creates a new instance of InstantRenameAction */
66     public InstantRenameAction() {
67         super("in-place-refactoring", ABBREV_RESET | MAGIC_POSITION_RESET | UNDO_MERGE_RESET
68         | SAVE_POSITION);
69     }
70     
71     public void actionPerformed(ActionEvent JavaDoc evt, final JTextComponent JavaDoc target) {
72         try {
73             final int caret = target.getCaretPosition();
74             String JavaDoc ident = Utilities.getIdentifier(Utilities.getDocument(target), caret);
75             
76             if (ident == null) {
77                 Utilities.setStatusBoldText(target, "Cannot perform instant rename here.");
78         return;
79             }
80             
81             DataObject od = (DataObject) target.getDocument().getProperty(Document.StreamDescriptionProperty);
82             JavaSource js = JavaSource.forFileObject(od.getPrimaryFile());
83             final boolean[] wasResolved = new boolean[1];
84             final Set JavaDoc<Highlight>[] changePoints = new Set JavaDoc[1];
85             
86             js.runUserActionTask(new CancellableTask<CompilationController>() {
87                 public void cancel() {
88                 }
89                 public void run(CompilationController controller) throws Exception JavaDoc {
90                     if (controller.toPhase(Phase.RESOLVED).compareTo(Phase.RESOLVED) < 0)
91                         return;
92                     
93                     changePoints[0] = computeChangePoints(controller, caret, wasResolved);
94                 }
95             }, true);
96             
97             if (wasResolved[0]) {
98                 if (changePoints[0] != null) {
99                     doInstantRename(changePoints[0], target, caret, ident);
100                 } else {
101                     doFullRename(od.getCookie(EditorCookie.class), od.getNodeDelegate());
102                 }
103             } else {
104                 Utilities.setStatusBoldText(target, "Cannot perform instant rename here.");
105             }
106         } catch (BadLocationException JavaDoc e) {
107             ErrorManager.getDefault().notify(e);
108         } catch (IOException JavaDoc ioe) {
109             ErrorManager.getDefault().notify(ioe);
110         }
111     }
112     
113     @Override JavaDoc
114     protected Class JavaDoc getShortDescriptionBundleClass() {
115         return InstantRenameAction.class;
116     }
117     
118     private void doInstantRename(Set JavaDoc<Highlight> changePoints, JTextComponent JavaDoc target, int caret, String JavaDoc ident) throws BadLocationException JavaDoc {
119         InstantRenamePerformer.performInstantRename(target, changePoints, caret);
120     }
121     
122     private void doFullRename(EditorCookie ec, Node n) {
123         
124         InstanceContent ic = new InstanceContent();
125         ic.add(ec);
126         ic.add(n);
127         Lookup actionContext = new AbstractLookup(ic);
128         
129         Action JavaDoc a = RefactoringActionsFactory.renameAction().createContextAwareInstance(actionContext);
130         a.actionPerformed(RefactoringActionsFactory.DEFAULT_EVENT);
131     }
132     
133     static Set JavaDoc<Highlight> computeChangePoints(CompilationInfo info, final int caret, final boolean[] wasResolved) throws IOException JavaDoc {
134         TreePath path = info.getTreeUtilities().pathFor(caret);
135         Element el = info.getTrees().getElement(path);
136         
137         if (el == null) {
138             wasResolved[0] = false;
139             return null;
140         }
141         
142         //#89736: if the caret is not in the resolved element's name, no rename:
143
final Highlight name = org.netbeans.modules.java.editor.semantic.Utilities.createHighlight(info.getCompilationUnit(), info.getTrees().getSourcePositions(), info.getDocument(), path, EnumSet.of(ColoringAttributes.MARK_OCCURRENCES), null);
144         
145         info.getDocument().render(new Runnable JavaDoc() {
146             public void run() {
147                 wasResolved[0] = name.getStart() <= caret && caret <= name.getEnd();
148             }
149         });
150         
151         if (!wasResolved[0])
152             return null;
153         
154         if (el.getKind() == ElementKind.CONSTRUCTOR) {
155             //for constructor, work over the enclosing class:
156
el = el.getEnclosingElement();
157         }
158         
159         if (allowInstantRename(el)) {
160             Set JavaDoc<Highlight> points = new HashSet JavaDoc<Highlight>(new FindLocalUsagesQuery().findUsages(el, info, info.getDocument()));
161             
162             if (el.getKind().isClass()) {
163                 //rename also the constructors:
164
for (ExecutableElement c : ElementFilter.constructorsIn(el.getEnclosedElements())) {
165                     TreePath t = info.getTrees().getPath(c);
166                     
167                     if (t != null) {
168                         Highlight h = org.netbeans.modules.java.editor.semantic.Utilities.createHighlight(info.getCompilationUnit(), info.getTrees().getSourcePositions(), info.getDocument(), t, EnumSet.of(ColoringAttributes.MARK_OCCURRENCES), null);
169                         
170                         if (h != null) {
171                             points.add(h);
172                         }
173                     }
174                 }
175             }
176             
177             return points;
178         }
179         
180         return null;
181     }
182     
183     private static boolean allowInstantRename(Element e) {
184         if (org.netbeans.modules.java.editor.semantic.Utilities.isPrivateElement(e)) {
185             return true;
186         }
187         
188         //#92160: check for local classes:
189
if (e.getKind() == ElementKind.CLASS) {//only classes can be local
190
Element enclosing = e.getEnclosingElement();
191             
192             return LOCAL_CLASS_PARENTS.contains(enclosing.getKind());
193         }
194         
195         return false;
196     }
197     
198     private static final Set JavaDoc<ElementKind> LOCAL_CLASS_PARENTS = EnumSet.of(ElementKind.CONSTRUCTOR, ElementKind.INSTANCE_INIT, ElementKind.METHOD, ElementKind.STATIC_INIT);
199     
200 }
201
Popular Tags