Chromium Code Reviews| Index: editor/tools/plugins/com.google.dart.tools.core/src/com/google/dart/tools/core/utilities/bindings/BindingUtils.java |
| diff --git a/editor/tools/plugins/com.google.dart.tools.core/src/com/google/dart/tools/core/utilities/bindings/BindingUtils.java b/editor/tools/plugins/com.google.dart.tools.core/src/com/google/dart/tools/core/utilities/bindings/BindingUtils.java |
| index 087b9e47e450d846f656e5d2dfb966f940c08b12..910dfeaab4f9c0717ed6dc9574de14a4734425b2 100644 |
| --- a/editor/tools/plugins/com.google.dart.tools.core/src/com/google/dart/tools/core/utilities/bindings/BindingUtils.java |
| +++ b/editor/tools/plugins/com.google.dart.tools.core/src/com/google/dart/tools/core/utilities/bindings/BindingUtils.java |
| @@ -25,6 +25,7 @@ import com.google.dart.compiler.ast.DartNode; |
| import com.google.dart.compiler.ast.DartUnit; |
| import com.google.dart.compiler.ast.LibraryUnit; |
| import com.google.dart.compiler.common.SourceInfo; |
| +import com.google.dart.compiler.resolver.ClassAliasElement; |
| import com.google.dart.compiler.resolver.ClassElement; |
| import com.google.dart.compiler.resolver.ConstructorElement; |
| import com.google.dart.compiler.resolver.Element; |
| @@ -44,6 +45,7 @@ import com.google.dart.tools.core.internal.model.PackageLibraryManagerProvider; |
| import com.google.dart.tools.core.internal.util.ResourceUtil; |
| import com.google.dart.tools.core.model.CompilationUnit; |
| import com.google.dart.tools.core.model.CompilationUnitElement; |
| +import com.google.dart.tools.core.model.DartClassTypeAlias; |
| import com.google.dart.tools.core.model.DartElement; |
| import com.google.dart.tools.core.model.DartFunction; |
| import com.google.dart.tools.core.model.DartFunctionTypeAlias; |
| @@ -64,7 +66,6 @@ import java.net.URI; |
| import java.util.ArrayList; |
| import java.util.HashMap; |
| import java.util.HashSet; |
| -import java.util.Iterator; |
| import java.util.List; |
| import java.util.Map; |
| import java.util.Set; |
| @@ -97,6 +98,12 @@ public class BindingUtils { |
| private HashMap<String, List<DartFunctionTypeAlias>> functionTypeAliasMap = new HashMap<String, List<DartFunctionTypeAlias>>(); |
| /** |
| + * A table mapping class type alias names to a list of class type aliases defined with that |
| + * name. |
| + */ |
| + private HashMap<String, List<DartClassTypeAlias>> classTypeAliasMap = new HashMap<String, List<DartClassTypeAlias>>(); |
| + |
| + /** |
| * A table mapping function names to a list of top-level functions defined with that name. |
| */ |
| private HashMap<String, List<DartFunction>> functionMap = new HashMap<String, List<DartFunction>>(); |
| @@ -314,6 +321,35 @@ public class BindingUtils { |
| } |
| /** |
| + * Return the Dart model element corresponding to the given resolved class alias. |
| + * |
| + * @param library the library containing the compilation unit in which the class alias is declared |
| + * @param aliasBinding the resolved function alias used to locate the model element |
| + * @return the Dart model element corresponding to the resolved class alias |
| + */ |
| + public static DartClassTypeAlias getDartElement(DartLibrary library, |
| + ClassAliasElement aliasBinding) { |
| + if (aliasBinding == null) { |
| + return null; |
| + } else if (library == null) { |
| + return null; |
| + } |
| + ClassElement element = aliasBinding.getType().getElement(); |
| + String typeName = element.getName(); |
| + LibraryElement declaringLibraryElement = element.getLibrary(); |
| + if (declaringLibraryElement == null) { |
| + DartCore.logError("Could not access declaring library for type " + typeName, new Throwable()); |
| + return null; |
| + } |
| + DartLibrary declaringLibrary = getDartElement(library, declaringLibraryElement); |
| + List<DartClassTypeAlias> matchingTypes = getClassTypeAliases(declaringLibrary, typeName); |
| + if (matchingTypes.size() == 1) { |
| + return matchingTypes.get(0); |
| + } |
| + return null; |
| + } |
| + |
| + /** |
| * Return the Dart model element corresponding to the given type element. |
| * |
| * @param library the library containing the type in which the method is declared |
| @@ -358,6 +394,8 @@ public class BindingUtils { |
| public static DartElement getDartElement(DartLibrary library, Element element) { |
| if (element instanceof FunctionAliasElement) { |
| return getDartElement(library, (FunctionAliasElement) element); |
| + } else if (element instanceof ClassAliasElement) { |
| + return getDartElement(library, (ClassAliasElement) element); |
| } else if (element instanceof ClassElement) { |
| return getDartElement(library, ((ClassElement) element).getType()); |
| } else if (element instanceof FieldElement) { |
| @@ -833,53 +871,53 @@ public class BindingUtils { |
| return null; |
| } |
| - /** |
| - * Search the supertypes of the given method's declaring type for any types that define a method |
| - * that is overridden by the given method. Return an array containing all of the overridden |
| - * methods, or an empty array if there are no overridden methods. The methods in the array are not |
| - * guaranteed to be in any particular order. |
| - * <p> |
| - * The result will contain only immediately overridden methods. For example, given a class |
| - * <code>A</code>, a class <code>B</code> that extends <code>A</code>, and a class <code>C</code> |
| - * that extends <code>B</code>, all three of which define a method <code>m</code>, asking the |
| - * method defined in class <code>C</code> for it's overridden methods will return an array |
| - * containing only the method defined in <code>B</code>. |
| - * |
| - * @param methodElement the method that overrides the methods to be returned |
| - * @return an array containing all of the methods declared in supertypes of the given method's |
| - * declaring type that are overridden by the given method |
| - */ |
| - public static MethodElement[] getOverriddenMethods(MethodElement methodElement) { |
| - List<MethodElement> overriddenMethods = new ArrayList<MethodElement>(); |
| - String methodName = methodElement.getName(); |
| - Element enclosingElement = methodElement.getEnclosingElement(); |
| - if (enclosingElement instanceof ClassElement) { |
| - Set<ClassElement> visitedTypes = new HashSet<ClassElement>(); |
| - List<ClassElement> targetTypes = new ArrayList<ClassElement>(); |
| - targetTypes.add((ClassElement) enclosingElement); |
| - while (!targetTypes.isEmpty()) { |
| - ClassElement targetType = targetTypes.remove(0); |
| - for (InterfaceType supertype : getImmediateSupertypes(targetType)) { |
| - if (supertype != null) { |
| - ClassElement supertypeElement = supertype.getElement(); |
| - Iterator<? extends Element> members = supertypeElement.getMembers().iterator(); |
| - if (members.hasNext()) { |
| - while (members.hasNext()) { |
| - Element member = members.next(); |
| - if (member instanceof MethodElement && member.getName().equals(methodName)) { |
| - overriddenMethods.add((MethodElement) member); |
| - } |
| - } |
| - } else if (!visitedTypes.contains(supertypeElement)) { |
| - visitedTypes.add(supertypeElement); |
| - targetTypes.add(supertypeElement); |
| - } |
| - } |
| - } |
| - } |
| - } |
| - return overriddenMethods.toArray(new MethodElement[overriddenMethods.size()]); |
| - } |
| +// /** |
| +// * Search the supertypes of the given method's declaring type for any types that define a method |
| +// * that is overridden by the given method. Return an array containing all of the overridden |
| +// * methods, or an empty array if there are no overridden methods. The methods in the array are not |
| +// * guaranteed to be in any particular order. |
| +// * <p> |
| +// * The result will contain only immediately overridden methods. For example, given a class |
| +// * <code>A</code>, a class <code>B</code> that extends <code>A</code>, and a class <code>C</code> |
| +// * that extends <code>B</code>, all three of which define a method <code>m</code>, asking the |
| +// * method defined in class <code>C</code> for it's overridden methods will return an array |
| +// * containing only the method defined in <code>B</code>. |
| +// * |
| +// * @param methodElement the method that overrides the methods to be returned |
| +// * @return an array containing all of the methods declared in supertypes of the given method's |
| +// * declaring type that are overridden by the given method |
| +// */ |
| +// public static MethodElement[] getOverriddenMethods(MethodElement methodElement) { |
| +// List<MethodElement> overriddenMethods = new ArrayList<MethodElement>(); |
| +// String methodName = methodElement.getName(); |
| +// Element enclosingElement = methodElement.getEnclosingElement(); |
| +// if (enclosingElement instanceof ClassElement) { |
| +// Set<ClassElement> visitedTypes = new HashSet<ClassElement>(); |
| +// List<ClassElement> targetTypes = new ArrayList<ClassElement>(); |
| +// targetTypes.add((ClassElement) enclosingElement); |
| +// while (!targetTypes.isEmpty()) { |
| +// ClassElement targetType = targetTypes.remove(0); |
| +// for (InterfaceType supertype : getImmediateSupertypes(targetType)) { |
| +// if (supertype != null) { |
| +// ClassElement supertypeElement = supertype.getElement(); |
| +// Iterator<? extends Element> members = supertypeElement.getMembers().iterator(); |
| +// if (members.hasNext()) { |
| +// while (members.hasNext()) { |
| +// Element member = members.next(); |
| +// if (member instanceof MethodElement && member.getName().equals(methodName)) { |
| +// overriddenMethods.add((MethodElement) member); |
| +// } |
| +// } |
| +// } else if (!visitedTypes.contains(supertypeElement)) { |
| +// visitedTypes.add(supertypeElement); |
| +// targetTypes.add(supertypeElement); |
| +// } |
| +// } |
| +// } |
| +// } |
| +// } |
| +// return overriddenMethods.toArray(new MethodElement[overriddenMethods.size()]); |
| +// } |
| /** |
| * Return <code>true</code> if the given method is an abstract method (either explicitly declared |
| @@ -949,6 +987,34 @@ public class BindingUtils { |
| } |
| /** |
| + * Traverse the given library looking for all of the class type aliases with the given name. |
| + * |
| + * @param matchingAliases the list to which matching class type aliases are to be added |
| + * @param library the library containing the class type aliases to be returned |
| + * @param typeName the name of the class type aliases to be returned |
| + */ |
| + private static void addImmediateClassTypeAliasesUncached( |
| + List<DartClassTypeAlias> matchingAliases, DartLibrary library, String typeName) { |
| + try { |
| + for (CompilationUnit unit : library.getCompilationUnits()) { |
| + try { |
| + for (DartClassTypeAlias type : unit.getClassTypeAliases()) { |
| + if (type.getElementName().equals(typeName)) { |
| + matchingAliases.add(type); |
| + } |
| + } |
| + } catch (DartModelException exception) { |
| +// DartCore.logInformation("Could not get function type aliases defined in " + unit.getElementName(), |
| +// exception); |
| + } |
| + } |
| + } catch (DartModelException exception) { |
| +// DartCore.logInformation( |
| +// "Could not get compilation units defined in " + library.getElementName(), exception); |
| + } |
| + } |
| + |
| + /** |
| * Traverse the given library looking for all of the function type aliases with the given name. |
| * |
| * @param matchingAliases the list to which matching function type aliases are to be added |
| @@ -1187,6 +1253,33 @@ public class BindingUtils { |
| return libraries; |
| } |
| + /** |
| + * Traverse the entire workspace looking for all of the function type aliases with the given name. |
| + * |
| + * @param matchingTypes the list to which matching types are to be added |
| + * @param library the library containing the type in which the method is declared |
| + * @param typeName the name of the types to be returned |
| + */ |
| + private static List<DartClassTypeAlias> getClassTypeAliases(DartLibrary library, String typeName) { |
| + if (library == null) { |
| + return new ArrayList<DartClassTypeAlias>(); |
| + } |
| + CacheEntry entry = getLibraryCache(library); |
| + if (entry == null) { |
| + return new ArrayList<DartClassTypeAlias>(); |
| + } |
| + HashMap<String, List<DartClassTypeAlias>> typeMap = entry.classTypeAliasMap; |
| + if (typeMap != null) { |
| + List<DartClassTypeAlias> typeList = typeMap.get(typeName); |
| + if (typeList != null) { |
| + return typeList; |
| + } |
| + } |
| + List<DartClassTypeAlias> matchingAliases = new ArrayList<DartClassTypeAlias>(); |
| + addImmediateClassTypeAliasesUncached(matchingAliases, library, typeName); |
| + return matchingAliases; |
| + } |
| + |
| private static DartLibrary getDartElement0(LibraryElement library) { |
| if (library == null) { |
| return null; |
| @@ -1308,21 +1401,22 @@ public class BindingUtils { |
| return matchingFunctions; |
| } |
| - /** |
| - * Return the immediate supertypes of the given class element. |
| - * |
| - * @param targetType the type whose supertypes are to be returned. |
| - * @return the immediate supertypes of the given class element |
| - */ |
| - private static Set<InterfaceType> getImmediateSupertypes(ClassElement targetType) { |
| - Set<InterfaceType> supertypes = new HashSet<InterfaceType>(); |
| - InterfaceType supertype = targetType.getSupertype(); |
| - if (supertype != null) { |
| - supertypes.add(supertype); |
| - } |
| - supertypes.addAll(targetType.getInterfaces()); |
| - return supertypes; |
| - } |
| +// /** |
| +// * Return the immediate supertypes of the given class element. |
| +// * |
| +// * @param targetType the type whose supertypes are to be returned. |
| +// * @return the immediate supertypes of the given class element |
| +// */ |
| +// private static Set<InterfaceType> getImmediateSupertypes(ClassElement targetType) { |
| +// Set<InterfaceType> supertypes = new HashSet<InterfaceType>(); |
| +// InterfaceType supertype = targetType.getSupertype(); |
| +// if (supertype != null) { |
| +// supertypes.add(supertype); |
| +// } |
| +// supertypes.addAll(targetType.getInterfaces()); |
| +// supertypes.addAll(targetType.getMixins()); |
|
Brian Wilkerson
2013/01/09 16:17:41
Please add a comment that adding the mixins might
|
| +// return supertypes; |
| +// } |
| /** |
| * Traverse the entire workspace looking for all of the types with the given name. |