Index: lib/src/compiler/code_generator.dart |
diff --git a/lib/src/compiler/code_generator.dart b/lib/src/compiler/code_generator.dart |
index bfc7dc95e960e65c47c14f4b018e088ee168da51..a874a168fe5b5c8d8d76a3265eb98ec922d590df 100644 |
--- a/lib/src/compiler/code_generator.dart |
+++ b/lib/src/compiler/code_generator.dart |
@@ -115,6 +115,12 @@ class CodeGenerator extends GeneralizingAstVisitor |
String _buildRoot; |
+ /// Whether the current compilation unit being compiled is within the Dart |
+ /// SDK itself. |
+ // TODO(rnystrom): Get rid of this if we can treat class literals inside |
+ // the SDK the same way we do outside. |
+ bool _compilingSdkLibrary = false; |
Bob Nystrom
2016/05/02 22:19:09
This is kind of nasty, but it was the most expedie
Jennifer Messerly
2016/05/02 23:04:20
We already have another way to get this info, expl
|
+ |
CodeGenerator(AnalysisContext c, this.options, this._extensionTypes) |
: context = c, |
types = c.typeProvider, |
@@ -218,7 +224,6 @@ class CodeGenerator extends GeneralizingAstVisitor |
// Add implicit dart:core dependency so it is first. |
emitLibraryName(dartCoreLibrary); |
- // |
// Visit each compilation unit and emit its code. |
// |
// NOTE: declarations are not necessarily emitted in this order. |
@@ -336,6 +341,8 @@ class CodeGenerator extends GeneralizingAstVisitor |
void visitCompilationUnit(CompilationUnit unit) { |
_constField = new ConstFieldVisitor(types, unit.element.source); |
+ _compilingSdkLibrary = unit.element.source.uri.scheme == "dart"; |
Jennifer Messerly
2016/05/02 23:04:20
This won't work because we don't necessarily visit
Bob Nystrom
2016/05/03 20:50:47
Done.
|
+ |
for (var declaration in unit.declarations) { |
var element = declaration.element; |
if (element != null) { |
@@ -1965,7 +1972,25 @@ class CodeGenerator extends GeneralizingAstVisitor |
// type literal |
if (element is TypeDefiningElement) { |
- return _emitTypeName(fillDynamicTypeArgs(element.type)); |
+ // TODO(rnystrom): Treating core libraries specially is lame. The JS() |
+ // code templates often refer to core lib classes and expect that to emit |
+ // a reference directly to the JS class (i.e. its constructor), not a |
+ // Type object. Figure out how to handle these better. |
+ if (_compilingSdkLibrary || |
Jennifer Messerly
2016/05/02 23:04:20
Here's how this can be done better:
See where we
Bob Nystrom
2016/05/03 20:50:47
Took some doing, but done. Scoping it to just with
|
+ node.parent is MethodInvocation || |
Jennifer Messerly
2016/05/02 23:04:20
FYI: at some point I'd love to ditch parent pointe
Bob Nystrom
2016/05/03 20:50:47
Yeah, this is gross. Doing something more explicit
|
+ node.parent is PrefixedIdentifier || |
+ node.parent is PropertyAccess) { |
+ // A static member call. Emit the class itself. |
+ return _emitTypeName(fillDynamicTypeArgs(element.type)); |
+ } else { |
+ // A type literal expression. Emit the "Type" object that corresponds |
+ // to that type. |
+ var dynType = fillDynamicTypeArgs(element.type); |
+ var isGeneric = dynType is ParameterizedType && |
+ dynType.typeArguments.isNotEmpty; |
+ var genericInst = _emitTypeName(dynType, lowerGeneric: isGeneric); |
Jennifer Messerly
2016/05/02 23:04:20
you should never need to pass `lowerGeneric` expli
Bob Nystrom
2016/05/03 20:50:47
Done. I think at first I wasn't filling in the dyn
|
+ return js.call('dart.wrapType(#)', genericInst); |
+ } |
} |
// library member |
@@ -2112,7 +2137,8 @@ class CodeGenerator extends GeneralizingAstVisitor |
var parts = _emitFunctionTypeParts(type as FunctionType); |
return js.call('dart.functionType(#)', [parts]); |
} |
- // For now, reify generic method parameters as dynamic |
+ |
+ // For now, reify generic method parameters as dynamic. |
bool _isGenericTypeParameter(DartType type) => |
type is TypeParameterType && |
type.element.enclosingElement is! TypeDefiningElement; |
@@ -2127,7 +2153,7 @@ class CodeGenerator extends GeneralizingAstVisitor |
if (type is ParameterizedType) { |
var args = type.typeArguments; |
- Iterable jsArgs = null; |
+ Iterable jsArgs; |
if (args.any((a) => !a.isDynamic && !_isGenericTypeParameter(a))) { |
jsArgs = args.map(_emitTypeName); |
} else if (lowerGeneric) { |