1 11 package org.eclipse.jdt.internal.corext.refactoring.util; 12 13 import java.util.ArrayList ; 14 import java.util.Iterator ; 15 import java.util.List ; 16 17 import org.eclipse.core.runtime.Assert; 18 import org.eclipse.core.runtime.CoreException; 19 20 import org.eclipse.ltk.core.refactoring.RefactoringStatus; 21 import org.eclipse.ltk.core.refactoring.RefactoringStatusContext; 22 23 import org.eclipse.jdt.core.ICompilationUnit; 24 import org.eclipse.jdt.core.ISourceRange; 25 import org.eclipse.jdt.core.JavaModelException; 26 import org.eclipse.jdt.core.dom.ASTNode; 27 import org.eclipse.jdt.core.dom.CatchClause; 28 import org.eclipse.jdt.core.dom.CompilationUnit; 29 import org.eclipse.jdt.core.dom.DoStatement; 30 import org.eclipse.jdt.core.dom.ForStatement; 31 import org.eclipse.jdt.core.dom.SwitchCase; 32 import org.eclipse.jdt.core.dom.SwitchStatement; 33 import org.eclipse.jdt.core.dom.SynchronizedStatement; 34 import org.eclipse.jdt.core.dom.TryStatement; 35 import org.eclipse.jdt.core.dom.WhileStatement; 36 37 import org.eclipse.jdt.internal.corext.SourceRange; 38 import org.eclipse.jdt.internal.corext.dom.ASTNodes; 39 import org.eclipse.jdt.internal.corext.dom.Selection; 40 import org.eclipse.jdt.internal.corext.dom.SelectionAnalyzer; 41 import org.eclipse.jdt.internal.corext.dom.TokenScanner; 42 import org.eclipse.jdt.internal.corext.refactoring.RefactoringCoreMessages; 43 import org.eclipse.jdt.internal.corext.refactoring.base.JavaStatusContext; 44 45 53 public class StatementAnalyzer extends SelectionAnalyzer { 54 55 protected ICompilationUnit fCUnit; 56 private TokenScanner fScanner; 57 private RefactoringStatus fStatus; 58 59 public StatementAnalyzer(ICompilationUnit cunit, Selection selection, boolean traverseSelectedNode) throws JavaModelException { 60 super(selection, traverseSelectedNode); 61 Assert.isNotNull(cunit); 62 fCUnit= cunit; 63 fStatus= new RefactoringStatus(); 64 fScanner= new TokenScanner(fCUnit); 65 } 66 67 protected void checkSelectedNodes() { 68 ASTNode[] nodes= getSelectedNodes(); 69 if (nodes.length == 0) 70 return; 71 72 ASTNode node= nodes[0]; 73 int selectionOffset= getSelection().getOffset(); 74 try { 75 int pos= fScanner.getNextStartOffset(selectionOffset, true); 76 if (pos == node.getStartPosition()) { 77 int lastNodeEnd= ASTNodes.getExclusiveEnd(nodes[nodes.length - 1]); 78 79 pos= fScanner.getNextStartOffset(lastNodeEnd, true); 80 int selectionEnd= getSelection().getInclusiveEnd(); 81 if (pos <= selectionEnd) { 82 ISourceRange range= new SourceRange(lastNodeEnd, pos - lastNodeEnd); 83 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_end_of_selection, JavaStatusContext.create(fCUnit, range)); 84 } 85 return; } 87 } catch (CoreException e) { 88 } 90 ISourceRange range= new SourceRange(selectionOffset, node.getStartPosition() - selectionOffset + 1); 91 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_beginning_of_selection, JavaStatusContext.create(fCUnit, range)); 92 } 93 94 public RefactoringStatus getStatus() { 95 return fStatus; 96 } 97 98 protected ICompilationUnit getCompilationUnit() { 99 return fCUnit; 100 } 101 102 protected TokenScanner getTokenScanner() { 103 return fScanner; 104 } 105 106 109 public void endVisit(CompilationUnit node) { 110 if (!hasSelectedNodes()) { 111 super.endVisit(node); 112 return; 113 } 114 ASTNode selectedNode= getFirstSelectedNode(); 115 Selection selection= getSelection(); 116 if (node != selectedNode) { 117 ASTNode parent= selectedNode.getParent(); 118 fStatus.merge(CommentAnalyzer.perform(selection, fScanner.getScanner(), parent.getStartPosition(), parent.getLength())); 119 } 120 if (!fStatus.hasFatalError()) 121 checkSelectedNodes(); 122 super.endVisit(node); 123 } 124 125 128 public void endVisit(DoStatement node) { 129 ASTNode[] selectedNodes= getSelectedNodes(); 130 if (doAfterValidation(node, selectedNodes)) { 131 if (contains(selectedNodes, node.getBody()) && contains(selectedNodes, node.getExpression())) { 132 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_do_body_expression); 133 } 134 } 135 super.endVisit(node); 136 } 137 138 141 public void endVisit(ForStatement node) { 142 ASTNode[] selectedNodes= getSelectedNodes(); 143 if (doAfterValidation(node, selectedNodes)) { 144 boolean containsExpression= contains(selectedNodes, node.getExpression()); 145 boolean containsUpdaters= contains(selectedNodes, node.updaters()); 146 if (contains(selectedNodes, node.initializers()) && containsExpression) { 147 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_for_initializer_expression); 148 } else if (containsExpression && containsUpdaters) { 149 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_for_expression_updater); 150 } else if (containsUpdaters && contains(selectedNodes, node.getBody())) { 151 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_for_updater_body); 152 } 153 } 154 super.endVisit(node); 155 } 156 157 160 public void endVisit(SwitchStatement node) { 161 ASTNode[] selectedNodes= getSelectedNodes(); 162 if (doAfterValidation(node, selectedNodes)) { 163 List cases= getSwitchCases(node); 164 for (int i= 0; i < selectedNodes.length; i++) { 165 ASTNode topNode= selectedNodes[i]; 166 if (cases.contains(topNode)) { 167 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_switch_statement); 168 break; 169 } 170 } 171 } 172 super.endVisit(node); 173 } 174 175 178 public void endVisit(SynchronizedStatement node) { 179 ASTNode firstSelectedNode= getFirstSelectedNode(); 180 if (getSelection().getEndVisitSelectionMode(node) == Selection.SELECTED) { 181 if (firstSelectedNode == node.getBody()) { 182 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_synchronized_statement); 183 } 184 } 185 super.endVisit(node); 186 } 187 188 191 public void endVisit(TryStatement node) { 192 ASTNode firstSelectedNode= getFirstSelectedNode(); 193 if (getSelection().getEndVisitSelectionMode(node) == Selection.AFTER) { 194 if (firstSelectedNode == node.getBody() || firstSelectedNode == node.getFinally()) { 195 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_try_statement); 196 } else { 197 List catchClauses= node.catchClauses(); 198 for (Iterator iterator= catchClauses.iterator(); iterator.hasNext();) { 199 CatchClause element= (CatchClause)iterator.next(); 200 if (element == firstSelectedNode || element.getBody() == firstSelectedNode) { 201 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_try_statement); 202 } else if (element.getException() == firstSelectedNode) { 203 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_catch_argument); 204 } 205 } 206 } 207 } 208 super.endVisit(node); 209 } 210 211 214 public void endVisit(WhileStatement node) { 215 ASTNode[] selectedNodes= getSelectedNodes(); 216 if (doAfterValidation(node, selectedNodes)) { 217 if (contains(selectedNodes, node.getExpression()) && contains(selectedNodes, node.getBody())) { 218 invalidSelection(RefactoringCoreMessages.StatementAnalyzer_while_expression_body); 219 } 220 } 221 super.endVisit(node); 222 } 223 224 private boolean doAfterValidation(ASTNode node, ASTNode[] selectedNodes) { 225 return selectedNodes.length > 0 && node == selectedNodes[0].getParent() && getSelection().getEndVisitSelectionMode(node) == Selection.AFTER; 226 } 227 228 protected void invalidSelection(String message) { 229 fStatus.addFatalError(message); 230 reset(); 231 } 232 233 protected void invalidSelection(String message, RefactoringStatusContext context) { 234 fStatus.addFatalError(message, context); 235 reset(); 236 } 237 238 private static List getSwitchCases(SwitchStatement node) { 239 List result= new ArrayList (); 240 for (Iterator iter= node.statements().iterator(); iter.hasNext(); ) { 241 Object element= iter.next(); 242 if (element instanceof SwitchCase) 243 result.add(element); 244 } 245 return result; 246 } 247 248 protected static boolean contains(ASTNode[] nodes, ASTNode node) { 249 for (int i = 0; i < nodes.length; i++) { 250 if (nodes[i] == node) 251 return true; 252 } 253 return false; 254 } 255 256 protected static boolean contains(ASTNode[] nodes, List list) { 257 for (int i = 0; i < nodes.length; i++) { 258 if (list.contains(nodes[i])) 259 return true; 260 } 261 return false; 262 } 263 } 264 | Popular Tags |