1 9 10 package org.netbeans.modules.java.navigation; 11 import com.sun.source.tree.CompilationUnitTree; 12 import com.sun.source.tree.Tree; 13 import com.sun.source.util.SourcePositions; 14 import com.sun.source.util.SourcePositions; 15 import com.sun.source.util.TreePath; 16 import com.sun.source.util.Trees; 17 import java.util.ArrayList ; 18 import java.util.Iterator ; 19 import java.util.List ; 20 import javax.lang.model.element.Element; 21 import javax.lang.model.element.Element; 22 import javax.lang.model.element.ElementKind; 23 import javax.lang.model.element.ExecutableElement; 24 import javax.lang.model.element.PackageElement; 25 import javax.lang.model.element.TypeElement; 26 import javax.lang.model.element.TypeParameterElement; 27 import javax.lang.model.element.VariableElement; 28 import javax.lang.model.type.ArrayType; 29 import javax.lang.model.type.DeclaredType; 30 import javax.lang.model.type.DeclaredType; 31 import javax.lang.model.type.TypeKind; 32 import javax.lang.model.type.TypeMirror; 33 import javax.lang.model.type.TypeVariable; 34 import javax.lang.model.type.TypeVariable; 35 import javax.lang.model.type.WildcardType; 36 import javax.lang.model.util.ElementScanner6; 37 import org.netbeans.api.java.source.CancellableTask; 38 import org.netbeans.api.java.source.CompilationInfo; 39 import org.netbeans.api.java.source.ElementHandle; 40 import org.netbeans.modules.java.navigation.ElementNode.Description; 41 42 47 public class ElementScanningTask implements CancellableTask<CompilationInfo>{ 48 49 private ClassMemberPanelUI ui; 50 private FindChildrenElementVisitor scanner; 51 private volatile boolean canceled; 52 53 public ElementScanningTask( ClassMemberPanelUI ui ) { 54 this.ui = ui; 55 } 56 57 public void cancel() { 58 canceled = true; 60 if ( scanner != null ) { 61 scanner.cancel(); 62 } 63 } 64 65 public void run(CompilationInfo info) throws Exception { 66 67 canceled = false; 69 71 Description rootDescription = new Description( ui ); 72 rootDescription.fileObject = info.getFileObject(); 73 rootDescription.subs = new ArrayList <Description>(); 74 75 CompilationUnitTree cuTree = info.getCompilationUnit(); 77 List <? extends Tree> typeDecls = cuTree.getTypeDecls(); 78 List <Element> elements = new ArrayList <Element>( typeDecls.size() ); 79 TreePath cuPath = new TreePath( cuTree ); 80 for( Tree t : typeDecls ) { 81 TreePath p = new TreePath( cuPath, t ); 82 Element e = info.getTrees().getElement( p ); 83 if ( e != null ) { 84 elements.add( e ); 85 } 86 } 87 88 if ( !canceled ) { 89 scanner = new FindChildrenElementVisitor(info); 90 for (Element element : elements) { 91 scanner.scan(element, rootDescription); 92 } 93 } 94 95 if ( !canceled ) { 96 ui.refresh( rootDescription ); 97 98 } 99 } 100 101 private static class FindChildrenElementVisitor extends ElementScanner6<Void , ElementNode.Description> { 102 103 private CompilationInfo info; 104 105 private volatile boolean canceled = false; 106 107 public FindChildrenElementVisitor(CompilationInfo info) { 108 this.info = info; 109 } 110 111 void cancel() { 112 canceled = true; 113 } 114 115 public Void visitPackage(PackageElement e, Description p) { 116 return null; } 118 119 public Void visitType(TypeElement e, Description p) { 120 if ( !canceled && !info.getElementUtilities().isSynthetic(e) ) { 121 122 Description d = new Description(p.ui, e.getSimpleName().toString(), ElementHandle.create(e), e.getKind()); 123 d.modifiers = e.getModifiers(); 124 d.subs = new ArrayList <Description>(); 125 d.pos = getPosition( e ); 126 d.htmlHeader = createHtmlHeader( e, info.getElements().isDeprecated(e) ); 127 if ( d.pos == -1 ) { 128 return null; 129 } 130 super.visitType(e, d); 131 p.subs.add(d); 132 } 133 return null; 134 } 135 136 public Void visitVariable(VariableElement e, Description p) { 137 if ( !canceled && !info.getElementUtilities().isSynthetic(e) && 138 ( e.getKind() == ElementKind.FIELD || e.getKind() == ElementKind.ENUM_CONSTANT ) ) { 139 Description d = new Description(p.ui, e.getSimpleName().toString(), ElementHandle.create(e), e.getKind()); 140 d.modifiers = e.getModifiers(); 141 d.pos = getPosition( e ); 142 d.htmlHeader = createHtmlHeader( e, info.getElements().isDeprecated(e) ); 143 if ( d.pos == -1 ) { 144 return null; 145 } 146 super.visitVariable(e,d); 147 p.subs.add(d); 148 } 149 return null; 150 } 151 152 public Void visitExecutable(ExecutableElement e, Description p) { 153 if ( !canceled && !info.getElementUtilities().isSynthetic(e) ) { 154 Description d = new Description(p.ui, e.getSimpleName().toString(), ElementHandle.create(e), e.getKind()); 155 d.modifiers = e.getModifiers(); 156 d.pos = getPosition( e ); 157 if ( d.pos == -1 ) { 158 return null; 159 } 160 d.htmlHeader = createHtmlHeader(e, info.getElements().isDeprecated(e)); 161 super.visitExecutable(e, d); 162 p.subs.add(d); 163 } 164 return null; 165 } 166 167 168 public Void visitTypeParameter(TypeParameterElement e, Description p) { 169 return null; 170 } 171 172 private long getPosition( Element e ) { 173 Trees trees = info.getTrees(); 174 CompilationUnitTree cut = info.getCompilationUnit(); 175 Tree t = trees.getTree(e); 176 177 if ( t == null ) { 178 return -1; 180 } 181 182 SourcePositions sourcePositions = trees.getSourcePositions(); 183 184 return sourcePositions.getStartPosition(cut, t ); 185 } 186 187 188 189 private String createHtmlHeader( ExecutableElement e, boolean isDeprecated ) { 190 191 StringBuilder sb = new StringBuilder (); 192 if ( isDeprecated ) { 193 sb.append("<s>"); } 195 if ( e.getKind() == ElementKind.CONSTRUCTOR ) { 196 sb.append(e.getEnclosingElement().getSimpleName()); 197 } 198 else { 199 sb.append(e.getSimpleName()); 200 } 201 if ( isDeprecated ) { 202 sb.append("</s>"); } 204 205 sb.append("("); 207 List <? extends VariableElement> params = e.getParameters(); 208 for( Iterator <? extends VariableElement> it = params.iterator(); it.hasNext(); ) { 209 VariableElement param = it.next(); 210 sb.append(print( param.asType())); 211 sb.append(" "); sb.append(param.getSimpleName()); 213 if ( it.hasNext() ) { 214 sb.append(", "); } 216 } 217 218 219 sb.append(")"); 221 if ( e.getKind() != ElementKind.CONSTRUCTOR ) { 222 TypeMirror rt = e.getReturnType(); 223 if ( rt.getKind() != TypeKind.VOID ) { 224 sb.append(" : "); sb.append(print(e.getReturnType())); 226 } 227 } 228 229 return sb.toString(); 230 } 231 232 private String createHtmlHeader( VariableElement e, boolean isDeprecated ) { 233 234 StringBuilder sb = new StringBuilder (); 235 236 if ( isDeprecated ) { 237 sb.append("<s>"); } 239 sb.append(e.getSimpleName()); 240 if ( isDeprecated ) { 241 sb.append("</s>"); } 243 244 if ( e.getKind() != ElementKind.ENUM_CONSTANT ) { 245 sb.append( " : " ); sb.append(print(e.asType())); 247 } 248 249 return sb.toString(); 250 } 251 252 private String createHtmlHeader( TypeElement e, boolean isDeprecated ) { 253 254 StringBuilder sb = new StringBuilder (); 255 if ( isDeprecated ) { 256 sb.append("<s>"); } 258 sb.append(e.getSimpleName()); 259 if ( isDeprecated ) { 260 sb.append("</s>"); } 262 List <? extends TypeParameterElement> typeParams = e.getTypeParameters(); 264 265 267 if ( typeParams != null && !typeParams.isEmpty() ) { 268 sb.append("<"); 270 for( Iterator <? extends TypeParameterElement> it = typeParams.iterator(); it.hasNext(); ) { 271 TypeParameterElement tp = it.next(); 272 sb.append( tp.getSimpleName() ); 273 try { List <? extends TypeMirror> bounds = tp.getBounds(); 275 if ( !bounds.isEmpty() ) { 277 sb.append(printBounds(bounds)); 278 } 279 } 280 catch ( NullPointerException npe ) { 281 System.err.println("El " + e ); 282 npe.printStackTrace(); 283 } 284 if ( it.hasNext() ) { 285 sb.append(", "); } 287 } 288 289 sb.append(">"); } 291 return sb.toString(); 292 } 293 294 private String printBounds( List <? extends TypeMirror> bounds ) { 295 if ( bounds.size() == 1 && "java.lang.Object".equals( bounds.get(0).toString() ) ) { 296 return ""; 297 } 298 299 StringBuilder sb = new StringBuilder (); 300 301 sb.append( " extends " ); 303 for (Iterator <? extends TypeMirror> it = bounds.iterator(); it.hasNext();) { 304 TypeMirror bound = it.next(); 305 sb.append(print(bound)); 306 if ( it.hasNext() ) { 307 sb.append(" & " ); } 309 310 } 311 312 return sb.toString(); 313 } 314 315 private String print( TypeMirror tm ) { 316 StringBuilder sb; 317 318 switch ( tm.getKind() ) { 319 case DECLARED: 320 DeclaredType dt = (DeclaredType)tm; 321 sb = new StringBuilder ( dt.asElement().getSimpleName().toString() ); 322 List <? extends TypeMirror> typeArgs = dt.getTypeArguments(); 323 if ( !typeArgs.isEmpty() ) { 324 sb.append("<"); 325 326 for (Iterator <? extends TypeMirror> it = typeArgs.iterator(); it.hasNext();) { 327 TypeMirror ta = it.next(); 328 sb.append(print(ta)); 329 if ( it.hasNext() ) { 330 sb.append(", "); 331 } 332 } 333 sb.append(">"); 334 } 335 336 return sb.toString(); 337 case TYPEVAR: 338 TypeVariable tv = (TypeVariable)tm; 339 sb = new StringBuilder ( tv.asElement().getSimpleName().toString() ); 340 return sb.toString(); 341 case ARRAY: 342 ArrayType at = (ArrayType)tm; 343 sb = new StringBuilder ( print(at.getComponentType()) ); 344 sb.append("[]"); 345 return sb.toString(); 346 case WILDCARD: 347 WildcardType wt = (WildcardType)tm; 348 sb = new StringBuilder ("?"); 349 if ( wt.getExtendsBound() != null ) { 350 sb.append(" extends "); sb.append(print(wt.getExtendsBound())); 352 } 353 if ( wt.getSuperBound() != null ) { 354 sb.append(" super "); sb.append(print(wt.getSuperBound())); 356 } 357 return sb.toString(); 358 default: 359 return tm.toString(); 360 } 361 } 362 363 364 } 365 366 } 367 | Popular Tags |