| OLD | NEW |
| 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 // This code was auto-generated, is not intended to be edited, and is subject to | 5 // This code was auto-generated, is not intended to be edited, and is subject to |
| 6 // significant change. Please see the README file for more information. | 6 // significant change. Please see the README file for more information. |
| 7 | 7 |
| 8 library engine.element; | 8 library engine.element; |
| 9 | 9 |
| 10 import 'dart:collection'; | 10 import 'dart:collection'; |
| 11 import 'java_core.dart'; | 11 import 'java_core.dart'; |
| 12 import 'java_engine.dart'; | 12 import 'java_engine.dart'; |
| 13 import 'utilities_collection.dart'; | 13 import 'utilities_collection.dart'; |
| 14 import 'source.dart'; | 14 import 'source.dart'; |
| 15 import 'scanner.dart' show Keyword; | 15 import 'scanner.dart' show Keyword; |
| 16 import 'ast.dart'; | 16 import 'ast.dart'; |
| 17 import 'sdk.dart' show DartSdk; | 17 import 'sdk.dart' show DartSdk; |
| 18 import 'html.dart' show XmlAttributeNode, XmlTagNode; | 18 import 'html.dart' show XmlAttributeNode, XmlTagNode; |
| 19 import 'engine.dart' show AnalysisContext, AnalysisEngine, AnalysisException; | 19 import 'engine.dart' show AnalysisContext, AnalysisEngine, AnalysisException; |
| 20 import 'constant.dart' show EvaluationResultImpl; | 20 import 'constant.dart' show EvaluationResultImpl; |
| 21 import 'utilities_dart.dart'; | 21 import 'utilities_dart.dart'; |
| 22 | 22 |
| 23 /** | 23 /** |
| 24 * Information about Angular application. |
| 25 */ |
| 26 class AngularApplication { |
| 27 final Source entryPoint; |
| 28 |
| 29 final Set<Source> _librarySources; |
| 30 |
| 31 final List<AngularElement> elements; |
| 32 |
| 33 final List<Source> elementSources; |
| 34 |
| 35 AngularApplication(this.entryPoint, this._librarySources, this.elements, this.
elementSources); |
| 36 |
| 37 /** |
| 38 * Checks if this application depends on the library with the given [Source]. |
| 39 */ |
| 40 bool dependsOn(Source librarySource) => _librarySources.contains(librarySource
); |
| 41 } |
| 42 |
| 43 /** |
| 44 * The interface `AngularControllerElement` defines the Angular component descri
bed by |
| 45 * <code>Component</code> annotation. |
| 46 */ |
| 47 abstract class AngularComponentElement implements AngularHasSelectorElement, Ang
ularHasTemplateElement { |
| 48 /** |
| 49 * Return an array containing all of the properties declared by this component
. |
| 50 */ |
| 51 List<AngularPropertyElement> get properties; |
| 52 |
| 53 /** |
| 54 * Return an array containing all of the scope properties set in the implement
ation of this |
| 55 * component. |
| 56 */ |
| 57 List<AngularScopePropertyElement> get scopeProperties; |
| 58 |
| 59 /** |
| 60 * Returns the CSS file URI. |
| 61 */ |
| 62 String get styleUri; |
| 63 |
| 64 /** |
| 65 * Return the offset of the [getStyleUri] in the [getSource]. |
| 66 * |
| 67 * @return the offset of the style URI |
| 68 */ |
| 69 int get styleUriOffset; |
| 70 } |
| 71 |
| 72 /** |
| 73 * Implementation of `AngularComponentElement`. |
| 74 */ |
| 75 class AngularComponentElementImpl extends AngularHasSelectorElementImpl implemen
ts AngularComponentElement { |
| 76 /** |
| 77 * The offset of the defining <code>Component</code> annotation. |
| 78 */ |
| 79 final int _annotationOffset; |
| 80 |
| 81 /** |
| 82 * The array containing all of the properties declared by this component. |
| 83 */ |
| 84 List<AngularPropertyElement> _properties = AngularPropertyElement.EMPTY_ARRAY; |
| 85 |
| 86 /** |
| 87 * The array containing all of the scope properties set by this component. |
| 88 */ |
| 89 List<AngularScopePropertyElement> _scopeProperties = AngularScopePropertyEleme
nt.EMPTY_ARRAY; |
| 90 |
| 91 /** |
| 92 * The the CSS file URI. |
| 93 */ |
| 94 String styleUri; |
| 95 |
| 96 /** |
| 97 * The offset of the [styleUri] in the [getSource]. |
| 98 */ |
| 99 int styleUriOffset = 0; |
| 100 |
| 101 /** |
| 102 * The HTML template URI. |
| 103 */ |
| 104 String templateUri; |
| 105 |
| 106 /** |
| 107 * The HTML template source. |
| 108 */ |
| 109 Source templateSource; |
| 110 |
| 111 /** |
| 112 * The offset of the [templateUri] in the [getSource]. |
| 113 */ |
| 114 int templateUriOffset = 0; |
| 115 |
| 116 /** |
| 117 * Initialize a newly created Angular component to have the given name. |
| 118 * |
| 119 * @param name the name of this element |
| 120 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 121 * declaration of this element |
| 122 */ |
| 123 AngularComponentElementImpl(String name, int nameOffset, this._annotationOffse
t) : super(name, nameOffset); |
| 124 |
| 125 @override |
| 126 accept(ElementVisitor visitor) => visitor.visitAngularComponentElement(this); |
| 127 |
| 128 @override |
| 129 ElementKind get kind => ElementKind.ANGULAR_COMPONENT; |
| 130 |
| 131 @override |
| 132 List<AngularPropertyElement> get properties => _properties; |
| 133 |
| 134 @override |
| 135 List<AngularScopePropertyElement> get scopeProperties => _scopeProperties; |
| 136 |
| 137 /** |
| 138 * Set an array containing all of the properties declared by this component. |
| 139 * |
| 140 * @param properties the properties to set |
| 141 */ |
| 142 void set properties(List<AngularPropertyElement> properties) { |
| 143 for (AngularPropertyElement property in properties) { |
| 144 encloseElement(property as AngularPropertyElementImpl); |
| 145 } |
| 146 this._properties = properties; |
| 147 } |
| 148 |
| 149 /** |
| 150 * Set an array containing all of the scope properties declared by this compon
ent. |
| 151 * |
| 152 * @param properties the properties to set |
| 153 */ |
| 154 void set scopeProperties(List<AngularScopePropertyElement> properties) { |
| 155 for (AngularScopePropertyElement property in properties) { |
| 156 encloseElement(property as AngularScopePropertyElementImpl); |
| 157 } |
| 158 this._scopeProperties = properties; |
| 159 } |
| 160 |
| 161 @override |
| 162 void visitChildren(ElementVisitor visitor) { |
| 163 safelyVisitChildren(_properties, visitor); |
| 164 safelyVisitChildren(_scopeProperties, visitor); |
| 165 super.visitChildren(visitor); |
| 166 } |
| 167 |
| 168 @override |
| 169 String get identifier => "AngularComponent@${_annotationOffset}"; |
| 170 } |
| 171 |
| 172 /** |
| 173 * The interface `AngularControllerElement` defines the Angular controller descr
ibed by |
| 174 * <code>Controller</code> annotation. |
| 175 */ |
| 176 abstract class AngularControllerElement implements AngularHasSelectorElement { |
| 177 } |
| 178 |
| 179 /** |
| 180 * Implementation of `AngularControllerElement`. |
| 181 */ |
| 182 class AngularControllerElementImpl extends AngularHasSelectorElementImpl impleme
nts AngularControllerElement { |
| 183 /** |
| 184 * Initialize a newly created Angular controller to have the given name. |
| 185 * |
| 186 * @param name the name of this element |
| 187 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 188 * declaration of this element |
| 189 */ |
| 190 AngularControllerElementImpl(String name, int nameOffset) : super(name, nameOf
fset); |
| 191 |
| 192 @override |
| 193 accept(ElementVisitor visitor) => visitor.visitAngularControllerElement(this); |
| 194 |
| 195 @override |
| 196 ElementKind get kind => ElementKind.ANGULAR_CONTROLLER; |
| 197 } |
| 198 |
| 199 /** |
| 200 * The interface `AngularDirectiveElement` defines the Angular controller descri
bed by |
| 201 * <code>Decorator</code> annotation. |
| 202 */ |
| 203 abstract class AngularDecoratorElement implements AngularHasSelectorElement { |
| 204 /** |
| 205 * Return an array containing all of the properties declared by this directive
. |
| 206 */ |
| 207 List<AngularPropertyElement> get properties; |
| 208 |
| 209 /** |
| 210 * Checks if this directive is implemented by the class with given name. |
| 211 */ |
| 212 bool isClass(String name); |
| 213 } |
| 214 |
| 215 /** |
| 216 * Implementation of `AngularDirectiveElement`. |
| 217 */ |
| 218 class AngularDecoratorElementImpl extends AngularHasSelectorElementImpl implemen
ts AngularDecoratorElement { |
| 219 /** |
| 220 * The offset of the annotation that defines this directive. |
| 221 */ |
| 222 final int _offset; |
| 223 |
| 224 /** |
| 225 * The array containing all of the properties declared by this directive. |
| 226 */ |
| 227 List<AngularPropertyElement> _properties = AngularPropertyElement.EMPTY_ARRAY; |
| 228 |
| 229 /** |
| 230 * Initialize a newly created Angular directive to have the given name. |
| 231 * |
| 232 * @param offset the offset of the annotation that defines this directive |
| 233 */ |
| 234 AngularDecoratorElementImpl(this._offset) : super(null, -1); |
| 235 |
| 236 @override |
| 237 accept(ElementVisitor visitor) => visitor.visitAngularDirectiveElement(this); |
| 238 |
| 239 @override |
| 240 String get displayName => selector.displayName; |
| 241 |
| 242 @override |
| 243 ElementKind get kind => ElementKind.ANGULAR_DIRECTIVE; |
| 244 |
| 245 @override |
| 246 List<AngularPropertyElement> get properties => _properties; |
| 247 |
| 248 @override |
| 249 bool isClass(String name) { |
| 250 Element enclosing = enclosingElement; |
| 251 return enclosing is ClassElement && enclosing.name == name; |
| 252 } |
| 253 |
| 254 /** |
| 255 * Set an array containing all of the properties declared by this directive. |
| 256 * |
| 257 * @param properties the properties to set |
| 258 */ |
| 259 void set properties(List<AngularPropertyElement> properties) { |
| 260 for (AngularPropertyElement property in properties) { |
| 261 encloseElement(property as AngularPropertyElementImpl); |
| 262 } |
| 263 this._properties = properties; |
| 264 } |
| 265 |
| 266 @override |
| 267 void visitChildren(ElementVisitor visitor) { |
| 268 safelyVisitChildren(_properties, visitor); |
| 269 super.visitChildren(visitor); |
| 270 } |
| 271 |
| 272 @override |
| 273 String get identifier => "Decorator@${_offset}"; |
| 274 } |
| 275 |
| 276 /** |
| 277 * The interface `AngularElement` defines the behavior of objects representing i
nformation |
| 278 * about an Angular specific element. |
| 279 */ |
| 280 abstract class AngularElement implements ToolkitObjectElement { |
| 281 /** |
| 282 * An empty array of Angular elements. |
| 283 */ |
| 284 static final List<AngularElement> EMPTY_ARRAY = new List<AngularElement>(0); |
| 285 |
| 286 /** |
| 287 * Returns the [AngularApplication] this element is used in. |
| 288 * |
| 289 * @return the [AngularApplication] this element is used in |
| 290 */ |
| 291 AngularApplication get application; |
| 292 } |
| 293 |
| 294 /** |
| 295 * Implementation of `AngularElement`. |
| 296 */ |
| 297 abstract class AngularElementImpl extends ToolkitObjectElementImpl implements An
gularElement { |
| 298 /** |
| 299 * The [AngularApplication] this element is used in. |
| 300 */ |
| 301 AngularApplication _application; |
| 302 |
| 303 /** |
| 304 * Initialize a newly created Angular element to have the given name. |
| 305 * |
| 306 * @param name the name of this element |
| 307 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 308 * declaration of this element |
| 309 */ |
| 310 AngularElementImpl(String name, int nameOffset) : super(name, nameOffset); |
| 311 |
| 312 @override |
| 313 AngularApplication get application => _application; |
| 314 |
| 315 /** |
| 316 * Set the [AngularApplication] this element is used in. |
| 317 */ |
| 318 void set application(AngularApplication application) { |
| 319 this._application = application; |
| 320 } |
| 321 } |
| 322 |
| 323 /** |
| 324 * The interface `AngularFormatterElement` defines the Angular formatter describ
ed by |
| 325 * <code>Formatter</code> annotation. |
| 326 */ |
| 327 abstract class AngularFormatterElement implements AngularElement { |
| 328 } |
| 329 |
| 330 /** |
| 331 * Implementation of `AngularFormatterElement`. |
| 332 */ |
| 333 class AngularFormatterElementImpl extends AngularElementImpl implements AngularF
ormatterElement { |
| 334 /** |
| 335 * Initialize a newly created Angular formatter to have the given name. |
| 336 * |
| 337 * @param name the name of this element |
| 338 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 339 * declaration of this element |
| 340 */ |
| 341 AngularFormatterElementImpl(String name, int nameOffset) : super(name, nameOff
set); |
| 342 |
| 343 @override |
| 344 accept(ElementVisitor visitor) => visitor.visitAngularFormatterElement(this); |
| 345 |
| 346 @override |
| 347 ElementKind get kind => ElementKind.ANGULAR_FORMATTER; |
| 348 } |
| 349 |
| 350 /** |
| 351 * [AngularSelectorElement] based on presence of attribute. |
| 352 */ |
| 353 abstract class AngularHasAttributeSelectorElement implements AngularSelectorElem
ent { |
| 354 } |
| 355 |
| 356 /** |
| 357 * [AngularSelectorElement] based on presence of a class. |
| 358 */ |
| 359 abstract class AngularHasClassSelectorElement implements AngularSelectorElement
{ |
| 360 } |
| 361 |
| 362 /** |
| 363 * Implementation of [AngularSelectorElement] based on presence of a class. |
| 364 */ |
| 365 class AngularHasClassSelectorElementImpl extends AngularSelectorElementImpl impl
ements AngularHasClassSelectorElement { |
| 366 AngularHasClassSelectorElementImpl(String name, int offset) : super(name, offs
et); |
| 367 |
| 368 @override |
| 369 bool apply(XmlTagNode node) { |
| 370 XmlAttributeNode attribute = node.getAttribute("class"); |
| 371 if (attribute != null) { |
| 372 String text = attribute.text; |
| 373 if (text != null) { |
| 374 String name = this.name; |
| 375 for (String className in StringUtils.split(text)) { |
| 376 if (className == name) { |
| 377 return true; |
| 378 } |
| 379 } |
| 380 } |
| 381 } |
| 382 return false; |
| 383 } |
| 384 |
| 385 @override |
| 386 void appendTo(JavaStringBuilder builder) { |
| 387 builder.append("."); |
| 388 builder.append(name); |
| 389 } |
| 390 } |
| 391 |
| 392 /** |
| 393 * The interface `AngularElement` defines the behavior of objects representing i
nformation |
| 394 * about an Angular element which is applied conditionally using some [AngularSe
lectorElement]. |
| 395 */ |
| 396 abstract class AngularHasSelectorElement implements AngularElement { |
| 397 /** |
| 398 * Returns the selector specified for this element. |
| 399 * |
| 400 * @return the [AngularSelectorElement] specified for this element |
| 401 */ |
| 402 AngularSelectorElement get selector; |
| 403 } |
| 404 |
| 405 /** |
| 406 * Implementation of `AngularSelectorElement`. |
| 407 */ |
| 408 abstract class AngularHasSelectorElementImpl extends AngularElementImpl implemen
ts AngularHasSelectorElement { |
| 409 /** |
| 410 * The selector of this element. |
| 411 */ |
| 412 AngularSelectorElement _selector; |
| 413 |
| 414 /** |
| 415 * Initialize a newly created Angular element to have the given name. |
| 416 * |
| 417 * @param name the name of this element |
| 418 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 419 * declaration of this element |
| 420 */ |
| 421 AngularHasSelectorElementImpl(String name, int nameOffset) : super(name, nameO
ffset); |
| 422 |
| 423 @override |
| 424 AngularSelectorElement get selector => _selector; |
| 425 |
| 426 /** |
| 427 * Set the selector of this selector-based element. |
| 428 * |
| 429 * @param selector the selector to set |
| 430 */ |
| 431 void set selector(AngularSelectorElement selector) { |
| 432 encloseElement(selector as AngularSelectorElementImpl); |
| 433 this._selector = selector; |
| 434 } |
| 435 |
| 436 @override |
| 437 void visitChildren(ElementVisitor visitor) { |
| 438 safelyVisitChild(_selector, visitor); |
| 439 super.visitChildren(visitor); |
| 440 } |
| 441 } |
| 442 |
| 443 /** |
| 444 * The interface `AngularHasTemplateElement` defines common behavior for |
| 445 * [AngularElement] that have template URI / [Source]. |
| 446 */ |
| 447 abstract class AngularHasTemplateElement implements AngularElement { |
| 448 /** |
| 449 * Returns the HTML template [Source], `null` if not resolved. |
| 450 */ |
| 451 Source get templateSource; |
| 452 |
| 453 /** |
| 454 * Returns the HTML template URI. |
| 455 */ |
| 456 String get templateUri; |
| 457 |
| 458 /** |
| 459 * Return the offset of the [getTemplateUri] in the [getSource]. |
| 460 * |
| 461 * @return the offset of the template URI |
| 462 */ |
| 463 int get templateUriOffset; |
| 464 } |
| 465 |
| 466 /** |
| 467 * The interface `AngularPropertyElement` defines a single property in |
| 468 * [AngularComponentElement]. |
| 469 */ |
| 470 abstract class AngularPropertyElement implements AngularElement { |
| 471 /** |
| 472 * An empty array of property elements. |
| 473 */ |
| 474 static final List<AngularPropertyElement> EMPTY_ARRAY = []; |
| 475 |
| 476 /** |
| 477 * Returns the field this property is mapped to. |
| 478 * |
| 479 * @return the field this property is mapped to. |
| 480 */ |
| 481 FieldElement get field; |
| 482 |
| 483 /** |
| 484 * Return the offset of the field name of this property in the property map, o
r `-1` if |
| 485 * property was created using annotation on [FieldElement]. |
| 486 * |
| 487 * @return the offset of the field name of this property |
| 488 */ |
| 489 int get fieldNameOffset; |
| 490 |
| 491 /** |
| 492 * Returns the kind of this property. |
| 493 * |
| 494 * @return the kind of this property |
| 495 */ |
| 496 AngularPropertyKind get propertyKind; |
| 497 } |
| 498 |
| 499 /** |
| 500 * Implementation of `AngularPropertyElement`. |
| 501 */ |
| 502 class AngularPropertyElementImpl extends AngularElementImpl implements AngularPr
opertyElement { |
| 503 /** |
| 504 * The [FieldElement] to which this property is bound. |
| 505 */ |
| 506 FieldElement field; |
| 507 |
| 508 /** |
| 509 * The offset of the field name in the property map. |
| 510 */ |
| 511 int fieldNameOffset = -1; |
| 512 |
| 513 AngularPropertyKind propertyKind; |
| 514 |
| 515 /** |
| 516 * Initialize a newly created Angular property to have the given name. |
| 517 * |
| 518 * @param name the name of this element |
| 519 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 520 * declaration of this element |
| 521 */ |
| 522 AngularPropertyElementImpl(String name, int nameOffset) : super(name, nameOffs
et); |
| 523 |
| 524 @override |
| 525 accept(ElementVisitor visitor) => visitor.visitAngularPropertyElement(this); |
| 526 |
| 527 @override |
| 528 ElementKind get kind => ElementKind.ANGULAR_PROPERTY; |
| 529 } |
| 530 |
| 531 /** |
| 532 * The enumeration `AngularPropertyKind` defines the different kinds of property
bindings. |
| 533 */ |
| 534 class AngularPropertyKind extends Enum<AngularPropertyKind> { |
| 535 /** |
| 536 * `@` - Map the DOM attribute string. The attribute string will be taken lite
rally or |
| 537 * interpolated if it contains binding {{}} syntax and assigned to the express
ion. (cost: 0 |
| 538 * watches) |
| 539 */ |
| 540 static const AngularPropertyKind ATTR = const AngularPropertyKind('ATTR', 0); |
| 541 |
| 542 /** |
| 543 * `&` - Treat the DOM attribute value as an expression. Assign a closure func
tion into the field. |
| 544 * This allows the component to control the invocation of the closure. This is
useful for passing |
| 545 * expressions into controllers which act like callbacks. (cost: 0 watches) |
| 546 */ |
| 547 static const AngularPropertyKind CALLBACK = const AngularPropertyKind('CALLBAC
K', 1); |
| 548 |
| 549 /** |
| 550 * `=>` - Treat the DOM attribute value as an expression. Set up a watch, whic
h will read the |
| 551 * expression in the attribute and assign the value to destination expression.
(cost: 1 watch) |
| 552 */ |
| 553 static const AngularPropertyKind ONE_WAY = const AngularPropertyKind('ONE_WAY'
, 2); |
| 554 |
| 555 /** |
| 556 * `=>!` - Treat the DOM attribute value as an expression. Set up a one time w
atch on expression. |
| 557 * Once the expression turns not null it will no longer update. (cost: 1 watch
es until not null, |
| 558 * then 0 watches) |
| 559 */ |
| 560 static const AngularPropertyKind ONE_WAY_ONE_TIME = const AngularPropertyKind(
'ONE_WAY_ONE_TIME', 3); |
| 561 |
| 562 /** |
| 563 * `<=>` - Treat the DOM attribute value as an expression. Set up a watch on b
oth outside as well |
| 564 * as component scope to keep the source and destination in sync. (cost: 2 wat
ches) |
| 565 */ |
| 566 static const AngularPropertyKind TWO_WAY = const AngularPropertyKind_TWO_WAY('
TWO_WAY', 4); |
| 567 |
| 568 static const List<AngularPropertyKind> values = const [ATTR, CALLBACK, ONE_WAY
, ONE_WAY_ONE_TIME, TWO_WAY]; |
| 569 |
| 570 /** |
| 571 * Returns `true` if property of this kind calls field getter. |
| 572 */ |
| 573 bool callsGetter() => false; |
| 574 |
| 575 /** |
| 576 * Returns `true` if property of this kind calls field setter. |
| 577 */ |
| 578 bool callsSetter() => true; |
| 579 |
| 580 const AngularPropertyKind(String name, int ordinal) : super(name, ordinal); |
| 581 } |
| 582 |
| 583 class AngularPropertyKind_TWO_WAY extends AngularPropertyKind { |
| 584 const AngularPropertyKind_TWO_WAY(String name, int ordinal) : super(name, ordi
nal); |
| 585 |
| 586 @override |
| 587 bool callsGetter() => true; |
| 588 } |
| 589 |
| 590 /** |
| 591 * The interface `AngularScopeVariableElement` defines the Angular <code>Scope</
code> |
| 592 * property. They are created for every <code>scope['property'] = value;</code>
code snippet. |
| 593 */ |
| 594 abstract class AngularScopePropertyElement implements AngularElement { |
| 595 /** |
| 596 * An empty array of scope property elements. |
| 597 */ |
| 598 static final List<AngularScopePropertyElement> EMPTY_ARRAY = []; |
| 599 |
| 600 /** |
| 601 * Returns the type of this property, not `null`, maybe <code>dynamic</code>. |
| 602 * |
| 603 * @return the type of this property. |
| 604 */ |
| 605 DartType get type; |
| 606 } |
| 607 |
| 608 /** |
| 609 * Implementation of `AngularScopePropertyElement`. |
| 610 */ |
| 611 class AngularScopePropertyElementImpl extends AngularElementImpl implements Angu
larScopePropertyElement { |
| 612 /** |
| 613 * The type of the property |
| 614 */ |
| 615 final DartType type; |
| 616 |
| 617 /** |
| 618 * Initialize a newly created Angular scope property to have the given name. |
| 619 * |
| 620 * @param name the name of this element |
| 621 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 622 * declaration of this element |
| 623 */ |
| 624 AngularScopePropertyElementImpl(String name, int nameOffset, this.type) : supe
r(name, nameOffset); |
| 625 |
| 626 @override |
| 627 accept(ElementVisitor visitor) => visitor.visitAngularScopePropertyElement(thi
s); |
| 628 |
| 629 @override |
| 630 ElementKind get kind => ElementKind.ANGULAR_SCOPE_PROPERTY; |
| 631 } |
| 632 |
| 633 /** |
| 634 * [AngularSelectorElement] is used to decide when Angular object should be appl
ied. |
| 635 * |
| 636 * This class is an [Element] to support renaming component tag names, which are
identifiers |
| 637 * in selectors. |
| 638 */ |
| 639 abstract class AngularSelectorElement implements AngularElement { |
| 640 /** |
| 641 * Checks if the given [XmlTagNode] matches this selector. |
| 642 * |
| 643 * @param node the [XmlTagNode] to check |
| 644 * @return `true` if the given [XmlTagNode] matches, or `false` otherwise |
| 645 */ |
| 646 bool apply(XmlTagNode node); |
| 647 } |
| 648 |
| 649 /** |
| 650 * Implementation of `AngularFormatterElement`. |
| 651 */ |
| 652 abstract class AngularSelectorElementImpl extends AngularElementImpl implements
AngularSelectorElement { |
| 653 /** |
| 654 * Initialize a newly created Angular selector to have the given name. |
| 655 * |
| 656 * @param name the name of this element |
| 657 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 658 * declaration of this element |
| 659 */ |
| 660 AngularSelectorElementImpl(String name, int nameOffset) : super(name, nameOffs
et); |
| 661 |
| 662 @override |
| 663 accept(ElementVisitor visitor) => visitor.visitAngularSelectorElement(this); |
| 664 |
| 665 @override |
| 666 ElementKind get kind => ElementKind.ANGULAR_SELECTOR; |
| 667 } |
| 668 |
| 669 /** |
| 670 * [AngularSelectorElement] based on tag name. |
| 671 */ |
| 672 abstract class AngularTagSelectorElement implements AngularSelectorElement { |
| 673 } |
| 674 |
| 675 /** |
| 676 * Implementation of [AngularSelectorElement] based on tag name. |
| 677 */ |
| 678 class AngularTagSelectorElementImpl extends AngularSelectorElementImpl implement
s AngularTagSelectorElement { |
| 679 AngularTagSelectorElementImpl(String name, int offset) : super(name, offset); |
| 680 |
| 681 @override |
| 682 bool apply(XmlTagNode node) { |
| 683 String tagName = name; |
| 684 return node.tag == tagName; |
| 685 } |
| 686 |
| 687 @override |
| 688 AngularApplication get application => (enclosingElement as AngularElementImpl)
.application; |
| 689 } |
| 690 |
| 691 /** |
| 692 * The interface `AngularViewElement` defines the Angular view defined using inv
ocation like |
| 693 * <code>view('views/create.html')</code>. |
| 694 */ |
| 695 abstract class AngularViewElement implements AngularHasTemplateElement { |
| 696 /** |
| 697 * An empty array of view elements. |
| 698 */ |
| 699 static final List<AngularViewElement> EMPTY_ARRAY = new List<AngularViewElemen
t>(0); |
| 700 } |
| 701 |
| 702 /** |
| 703 * Implementation of `AngularViewElement`. |
| 704 */ |
| 705 class AngularViewElementImpl extends AngularElementImpl implements AngularViewEl
ement { |
| 706 /** |
| 707 * The HTML template URI. |
| 708 */ |
| 709 final String templateUri; |
| 710 |
| 711 /** |
| 712 * The offset of the [templateUri] in the [getSource]. |
| 713 */ |
| 714 final int templateUriOffset; |
| 715 |
| 716 /** |
| 717 * The HTML template source. |
| 718 */ |
| 719 Source templateSource; |
| 720 |
| 721 /** |
| 722 * Initialize a newly created Angular view. |
| 723 */ |
| 724 AngularViewElementImpl(this.templateUri, this.templateUriOffset) : super(null,
-1); |
| 725 |
| 726 @override |
| 727 accept(ElementVisitor visitor) => visitor.visitAngularViewElement(this); |
| 728 |
| 729 @override |
| 730 ElementKind get kind => ElementKind.ANGULAR_VIEW; |
| 731 |
| 732 @override |
| 733 String get identifier => "AngularView@${templateUriOffset}"; |
| 734 } |
| 735 |
| 736 /** |
| 737 * For AST nodes that could be in both the getter and setter contexts ([IndexExp
ression]s and |
| 738 * [SimpleIdentifier]s), the additional resolved elements are stored in the AST
node, in an |
| 739 * [AuxiliaryElements]. Since resolved elements are either statically resolved o
r resolved |
| 740 * using propagated type information, this class is a wrapper for a pair of |
| 741 * [ExecutableElement]s, not just a single [ExecutableElement]. |
| 742 */ |
| 743 class AuxiliaryElements { |
| 744 /** |
| 745 * The element based on propagated type information, or `null` if the AST stru
cture has not |
| 746 * been resolved or if this identifier could not be resolved. |
| 747 */ |
| 748 final ExecutableElement propagatedElement; |
| 749 |
| 750 /** |
| 751 * The element associated with this identifier based on static type informatio
n, or `null` |
| 752 * if the AST structure has not been resolved or if this identifier could not
be resolved. |
| 753 */ |
| 754 final ExecutableElement staticElement; |
| 755 |
| 756 /** |
| 757 * Create the [AuxiliaryElements] with a static and propagated [ExecutableElem
ent]. |
| 758 * |
| 759 * @param staticElement the static element |
| 760 * @param propagatedElement the propagated element |
| 761 */ |
| 762 AuxiliaryElements(this.staticElement, this.propagatedElement); |
| 763 } |
| 764 |
| 765 /** |
| 766 * The unique instance of the class `BottomTypeImpl` implements the type `bottom
`. |
| 767 */ |
| 768 class BottomTypeImpl extends TypeImpl { |
| 769 /** |
| 770 * The unique instance of this class. |
| 771 */ |
| 772 static BottomTypeImpl _INSTANCE = new BottomTypeImpl(); |
| 773 |
| 774 /** |
| 775 * Return the unique instance of this class. |
| 776 * |
| 777 * @return the unique instance of this class |
| 778 */ |
| 779 static BottomTypeImpl get instance => _INSTANCE; |
| 780 |
| 781 /** |
| 782 * Prevent the creation of instances of this class. |
| 783 */ |
| 784 BottomTypeImpl() : super(null, "<bottom>"); |
| 785 |
| 786 @override |
| 787 bool operator ==(Object object) => identical(object, this); |
| 788 |
| 789 @override |
| 790 int get hashCode => 0; |
| 791 |
| 792 @override |
| 793 bool get isBottom => true; |
| 794 |
| 795 @override |
| 796 bool isSupertypeOf(DartType type) => false; |
| 797 |
| 798 @override |
| 799 BottomTypeImpl substitute2(List<DartType> argumentTypes, List<DartType> parame
terTypes) => this; |
| 800 |
| 801 @override |
| 802 bool internalEquals(Object object, Set<ElementPair> visitedElementPairs) => id
entical(object, this); |
| 803 |
| 804 @override |
| 805 bool internalIsMoreSpecificThan(DartType type, bool withDynamic, Set<TypeImpl_
TypePair> visitedTypePairs) => true; |
| 806 |
| 807 @override |
| 808 bool internalIsSubtypeOf(DartType type, Set<TypeImpl_TypePair> visitedTypePair
s) => true; |
| 809 } |
| 810 |
| 811 /** |
| 24 * The interface `ClassElement` defines the behavior of elements that represent
a class. | 812 * The interface `ClassElement` defines the behavior of elements that represent
a class. |
| 25 */ | 813 */ |
| 26 abstract class ClassElement implements Element { | 814 abstract class ClassElement implements Element { |
| 27 /** | 815 /** |
| 28 * Return an array containing all of the accessors (getters and setters) decla
red in this class. | 816 * Return an array containing all of the accessors (getters and setters) decla
red in this class. |
| 29 * | 817 * |
| 30 * @return the accessors declared in this class | 818 * @return the accessors declared in this class |
| 31 */ | 819 */ |
| 32 List<PropertyAccessorElement> get accessors; | 820 List<PropertyAccessorElement> get accessors; |
| 33 | 821 |
| (...skipping 273 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 307 * | 1095 * |
| 308 * @param setterName the name of the setter being looked up | 1096 * @param setterName the name of the setter being looked up |
| 309 * @param library the library with respect to which the lookup is being perfor
med | 1097 * @param library the library with respect to which the lookup is being perfor
med |
| 310 * @return the result of looking up the given setter in this class with respec
t to the given | 1098 * @return the result of looking up the given setter in this class with respec
t to the given |
| 311 * library | 1099 * library |
| 312 */ | 1100 */ |
| 313 PropertyAccessorElement lookUpSetter(String setterName, LibraryElement library
); | 1101 PropertyAccessorElement lookUpSetter(String setterName, LibraryElement library
); |
| 314 } | 1102 } |
| 315 | 1103 |
| 316 /** | 1104 /** |
| 1105 * Instances of the class `ClassElementImpl` implement a `ClassElement`. |
| 1106 */ |
| 1107 class ClassElementImpl extends ElementImpl implements ClassElement { |
| 1108 /** |
| 1109 * An array containing all of the accessors (getters and setters) contained in
this class. |
| 1110 */ |
| 1111 List<PropertyAccessorElement> _accessors = PropertyAccessorElementImpl.EMPTY_A
RRAY; |
| 1112 |
| 1113 /** |
| 1114 * An array containing all of the constructors contained in this class. |
| 1115 */ |
| 1116 List<ConstructorElement> _constructors = ConstructorElementImpl.EMPTY_ARRAY; |
| 1117 |
| 1118 /** |
| 1119 * An array containing all of the fields contained in this class. |
| 1120 */ |
| 1121 List<FieldElement> _fields = FieldElementImpl.EMPTY_ARRAY; |
| 1122 |
| 1123 /** |
| 1124 * An array containing all of the mixins that are applied to the class being e
xtended in order to |
| 1125 * derive the superclass of this class. |
| 1126 */ |
| 1127 List<InterfaceType> mixins = InterfaceTypeImpl.EMPTY_ARRAY; |
| 1128 |
| 1129 /** |
| 1130 * An array containing all of the interfaces that are implemented by this clas
s. |
| 1131 */ |
| 1132 List<InterfaceType> interfaces = InterfaceTypeImpl.EMPTY_ARRAY; |
| 1133 |
| 1134 /** |
| 1135 * An array containing all of the methods contained in this class. |
| 1136 */ |
| 1137 List<MethodElement> _methods = MethodElementImpl.EMPTY_ARRAY; |
| 1138 |
| 1139 /** |
| 1140 * The superclass of the class, or `null` if the class does not have an explic
it superclass. |
| 1141 */ |
| 1142 InterfaceType supertype; |
| 1143 |
| 1144 /** |
| 1145 * An array containing all of the toolkit objects attached to this class. |
| 1146 */ |
| 1147 List<ToolkitObjectElement> _toolkitObjects = ToolkitObjectElement.EMPTY_ARRAY; |
| 1148 |
| 1149 /** |
| 1150 * The type defined by the class. |
| 1151 */ |
| 1152 InterfaceType type; |
| 1153 |
| 1154 /** |
| 1155 * An array containing all of the type parameters defined for this class. |
| 1156 */ |
| 1157 List<TypeParameterElement> _typeParameters = TypeParameterElementImpl.EMPTY_AR
RAY; |
| 1158 |
| 1159 /** |
| 1160 * An empty array of class elements. |
| 1161 */ |
| 1162 static List<ClassElement> EMPTY_ARRAY = new List<ClassElement>(0); |
| 1163 |
| 1164 /** |
| 1165 * Initialize a newly created class element to have the given name. |
| 1166 * |
| 1167 * @param name the name of this element |
| 1168 */ |
| 1169 ClassElementImpl(Identifier name) : super.forNode(name); |
| 1170 |
| 1171 @override |
| 1172 accept(ElementVisitor visitor) => visitor.visitClassElement(this); |
| 1173 |
| 1174 /** |
| 1175 * Set the toolkit specific information objects attached to this class. |
| 1176 * |
| 1177 * @param toolkitObjects the toolkit objects attached to this class |
| 1178 */ |
| 1179 void addToolkitObjects(ToolkitObjectElement toolkitObject) { |
| 1180 (toolkitObject as ToolkitObjectElementImpl).enclosingElement = this; |
| 1181 _toolkitObjects = ArrayUtils.add(_toolkitObjects, toolkitObject); |
| 1182 } |
| 1183 |
| 1184 @override |
| 1185 List<PropertyAccessorElement> get accessors => _accessors; |
| 1186 |
| 1187 @override |
| 1188 List<InterfaceType> get allSupertypes { |
| 1189 List<InterfaceType> list = new List<InterfaceType>(); |
| 1190 _collectAllSupertypes(list); |
| 1191 return new List.from(list); |
| 1192 } |
| 1193 |
| 1194 @override |
| 1195 ElementImpl getChild(String identifier) { |
| 1196 // |
| 1197 // The casts in this method are safe because the set methods would have thro
wn a CCE if any of |
| 1198 // the elements in the arrays were not of the expected types. |
| 1199 // |
| 1200 for (PropertyAccessorElement accessor in _accessors) { |
| 1201 if ((accessor as PropertyAccessorElementImpl).identifier == identifier) { |
| 1202 return accessor as PropertyAccessorElementImpl; |
| 1203 } |
| 1204 } |
| 1205 for (ConstructorElement constructor in _constructors) { |
| 1206 if ((constructor as ConstructorElementImpl).identifier == identifier) { |
| 1207 return constructor as ConstructorElementImpl; |
| 1208 } |
| 1209 } |
| 1210 for (FieldElement field in _fields) { |
| 1211 if ((field as FieldElementImpl).identifier == identifier) { |
| 1212 return field as FieldElementImpl; |
| 1213 } |
| 1214 } |
| 1215 for (MethodElement method in _methods) { |
| 1216 if ((method as MethodElementImpl).identifier == identifier) { |
| 1217 return method as MethodElementImpl; |
| 1218 } |
| 1219 } |
| 1220 for (TypeParameterElement typeParameter in _typeParameters) { |
| 1221 if ((typeParameter as TypeParameterElementImpl).identifier == identifier)
{ |
| 1222 return typeParameter as TypeParameterElementImpl; |
| 1223 } |
| 1224 } |
| 1225 return null; |
| 1226 } |
| 1227 |
| 1228 @override |
| 1229 List<ConstructorElement> get constructors => _constructors; |
| 1230 |
| 1231 @override |
| 1232 FieldElement getField(String name) { |
| 1233 for (FieldElement fieldElement in _fields) { |
| 1234 if (name == fieldElement.name) { |
| 1235 return fieldElement; |
| 1236 } |
| 1237 } |
| 1238 return null; |
| 1239 } |
| 1240 |
| 1241 @override |
| 1242 List<FieldElement> get fields => _fields; |
| 1243 |
| 1244 @override |
| 1245 PropertyAccessorElement getGetter(String getterName) { |
| 1246 for (PropertyAccessorElement accessor in _accessors) { |
| 1247 if (accessor.isGetter && accessor.name == getterName) { |
| 1248 return accessor; |
| 1249 } |
| 1250 } |
| 1251 return null; |
| 1252 } |
| 1253 |
| 1254 @override |
| 1255 ElementKind get kind => ElementKind.CLASS; |
| 1256 |
| 1257 @override |
| 1258 MethodElement getMethod(String methodName) { |
| 1259 for (MethodElement method in _methods) { |
| 1260 if (method.name == methodName) { |
| 1261 return method; |
| 1262 } |
| 1263 } |
| 1264 return null; |
| 1265 } |
| 1266 |
| 1267 @override |
| 1268 List<MethodElement> get methods => _methods; |
| 1269 |
| 1270 @override |
| 1271 ConstructorElement getNamedConstructor(String name) { |
| 1272 for (ConstructorElement element in constructors) { |
| 1273 String elementName = element.name; |
| 1274 if (elementName != null && elementName == name) { |
| 1275 return element; |
| 1276 } |
| 1277 } |
| 1278 return null; |
| 1279 } |
| 1280 |
| 1281 @override |
| 1282 ClassDeclaration get node => getNodeMatching((node) => node is ClassDeclaratio
n); |
| 1283 |
| 1284 @override |
| 1285 PropertyAccessorElement getSetter(String setterName) { |
| 1286 // TODO (jwren) revisit- should we append '=' here or require clients to inc
lude it? |
| 1287 // Do we need the check for isSetter below? |
| 1288 if (!StringUtilities.endsWithChar(setterName, 0x3D)) { |
| 1289 setterName += '='; |
| 1290 } |
| 1291 for (PropertyAccessorElement accessor in _accessors) { |
| 1292 if (accessor.isSetter && accessor.name == setterName) { |
| 1293 return accessor; |
| 1294 } |
| 1295 } |
| 1296 return null; |
| 1297 } |
| 1298 |
| 1299 @override |
| 1300 List<ToolkitObjectElement> get toolkitObjects => _toolkitObjects; |
| 1301 |
| 1302 @override |
| 1303 List<TypeParameterElement> get typeParameters => _typeParameters; |
| 1304 |
| 1305 @override |
| 1306 ConstructorElement get unnamedConstructor { |
| 1307 for (ConstructorElement element in constructors) { |
| 1308 String name = element.displayName; |
| 1309 if (name == null || name.isEmpty) { |
| 1310 return element; |
| 1311 } |
| 1312 } |
| 1313 return null; |
| 1314 } |
| 1315 |
| 1316 @override |
| 1317 bool get hasNonFinalField { |
| 1318 List<ClassElement> classesToVisit = new List<ClassElement>(); |
| 1319 Set<ClassElement> visitedClasses = new Set<ClassElement>(); |
| 1320 classesToVisit.add(this); |
| 1321 while (!classesToVisit.isEmpty) { |
| 1322 ClassElement currentElement = classesToVisit.removeAt(0); |
| 1323 if (visitedClasses.add(currentElement)) { |
| 1324 // check fields |
| 1325 for (FieldElement field in currentElement.fields) { |
| 1326 if (!field.isFinal && !field.isConst && !field.isStatic && !field.isSy
nthetic) { |
| 1327 return true; |
| 1328 } |
| 1329 } |
| 1330 // check mixins |
| 1331 for (InterfaceType mixinType in currentElement.mixins) { |
| 1332 ClassElement mixinElement = mixinType.element; |
| 1333 classesToVisit.add(mixinElement); |
| 1334 } |
| 1335 // check super |
| 1336 InterfaceType supertype = currentElement.supertype; |
| 1337 if (supertype != null) { |
| 1338 ClassElement superElement = supertype.element; |
| 1339 if (superElement != null) { |
| 1340 classesToVisit.add(superElement); |
| 1341 } |
| 1342 } |
| 1343 } |
| 1344 } |
| 1345 // not found |
| 1346 return false; |
| 1347 } |
| 1348 |
| 1349 @override |
| 1350 bool get hasReferenceToSuper => hasModifier(Modifier.REFERENCES_SUPER); |
| 1351 |
| 1352 @override |
| 1353 bool get hasStaticMember { |
| 1354 for (MethodElement method in _methods) { |
| 1355 if (method.isStatic) { |
| 1356 return true; |
| 1357 } |
| 1358 } |
| 1359 for (PropertyAccessorElement accessor in _accessors) { |
| 1360 if (accessor.isStatic) { |
| 1361 return true; |
| 1362 } |
| 1363 } |
| 1364 return false; |
| 1365 } |
| 1366 |
| 1367 @override |
| 1368 bool get isAbstract => hasModifier(Modifier.ABSTRACT); |
| 1369 |
| 1370 @override |
| 1371 bool get isOrInheritsProxy => _safeIsOrInheritsProxy(this, new Set<ClassElemen
t>()); |
| 1372 |
| 1373 @override |
| 1374 bool get isProxy { |
| 1375 for (ElementAnnotation annotation in metadata) { |
| 1376 if (annotation.isProxy) { |
| 1377 return true; |
| 1378 } |
| 1379 } |
| 1380 return false; |
| 1381 } |
| 1382 |
| 1383 @override |
| 1384 bool get isTypedef => hasModifier(Modifier.TYPEDEF); |
| 1385 |
| 1386 @override |
| 1387 bool get isValidMixin => hasModifier(Modifier.MIXIN); |
| 1388 |
| 1389 @override |
| 1390 PropertyAccessorElement lookUpGetter(String getterName, LibraryElement library
) { |
| 1391 Set<ClassElement> visitedClasses = new Set<ClassElement>(); |
| 1392 ClassElement currentElement = this; |
| 1393 while (currentElement != null && !visitedClasses.contains(currentElement)) { |
| 1394 visitedClasses.add(currentElement); |
| 1395 PropertyAccessorElement element = currentElement.getGetter(getterName); |
| 1396 if (element != null && element.isAccessibleIn(library)) { |
| 1397 return element; |
| 1398 } |
| 1399 for (InterfaceType mixin in currentElement.mixins) { |
| 1400 ClassElement mixinElement = mixin.element; |
| 1401 if (mixinElement != null) { |
| 1402 element = mixinElement.getGetter(getterName); |
| 1403 if (element != null && element.isAccessibleIn(library)) { |
| 1404 return element; |
| 1405 } |
| 1406 } |
| 1407 } |
| 1408 InterfaceType supertype = currentElement.supertype; |
| 1409 if (supertype == null) { |
| 1410 return null; |
| 1411 } |
| 1412 currentElement = supertype.element; |
| 1413 } |
| 1414 return null; |
| 1415 } |
| 1416 |
| 1417 @override |
| 1418 MethodElement lookUpMethod(String methodName, LibraryElement library) { |
| 1419 Set<ClassElement> visitedClasses = new Set<ClassElement>(); |
| 1420 ClassElement currentElement = this; |
| 1421 while (currentElement != null && !visitedClasses.contains(currentElement)) { |
| 1422 visitedClasses.add(currentElement); |
| 1423 MethodElement element = currentElement.getMethod(methodName); |
| 1424 if (element != null && element.isAccessibleIn(library)) { |
| 1425 return element; |
| 1426 } |
| 1427 for (InterfaceType mixin in currentElement.mixins) { |
| 1428 ClassElement mixinElement = mixin.element; |
| 1429 if (mixinElement != null) { |
| 1430 element = mixinElement.getMethod(methodName); |
| 1431 if (element != null && element.isAccessibleIn(library)) { |
| 1432 return element; |
| 1433 } |
| 1434 } |
| 1435 } |
| 1436 InterfaceType supertype = currentElement.supertype; |
| 1437 if (supertype == null) { |
| 1438 return null; |
| 1439 } |
| 1440 currentElement = supertype.element; |
| 1441 } |
| 1442 return null; |
| 1443 } |
| 1444 |
| 1445 @override |
| 1446 PropertyAccessorElement lookUpSetter(String setterName, LibraryElement library
) { |
| 1447 Set<ClassElement> visitedClasses = new Set<ClassElement>(); |
| 1448 ClassElement currentElement = this; |
| 1449 while (currentElement != null && !visitedClasses.contains(currentElement)) { |
| 1450 visitedClasses.add(currentElement); |
| 1451 PropertyAccessorElement element = currentElement.getSetter(setterName); |
| 1452 if (element != null && element.isAccessibleIn(library)) { |
| 1453 return element; |
| 1454 } |
| 1455 for (InterfaceType mixin in currentElement.mixins) { |
| 1456 ClassElement mixinElement = mixin.element; |
| 1457 if (mixinElement != null) { |
| 1458 element = mixinElement.getSetter(setterName); |
| 1459 if (element != null && element.isAccessibleIn(library)) { |
| 1460 return element; |
| 1461 } |
| 1462 } |
| 1463 } |
| 1464 InterfaceType supertype = currentElement.supertype; |
| 1465 if (supertype == null) { |
| 1466 return null; |
| 1467 } |
| 1468 currentElement = supertype.element; |
| 1469 } |
| 1470 return null; |
| 1471 } |
| 1472 |
| 1473 /** |
| 1474 * Set whether this class is abstract to correspond to the given value. |
| 1475 * |
| 1476 * @param isAbstract `true` if the class is abstract |
| 1477 */ |
| 1478 void set abstract(bool isAbstract) { |
| 1479 setModifier(Modifier.ABSTRACT, isAbstract); |
| 1480 } |
| 1481 |
| 1482 /** |
| 1483 * Set the accessors contained in this class to the given accessors. |
| 1484 * |
| 1485 * @param accessors the accessors contained in this class |
| 1486 */ |
| 1487 void set accessors(List<PropertyAccessorElement> accessors) { |
| 1488 for (PropertyAccessorElement accessor in accessors) { |
| 1489 (accessor as PropertyAccessorElementImpl).enclosingElement = this; |
| 1490 } |
| 1491 this._accessors = accessors; |
| 1492 } |
| 1493 |
| 1494 /** |
| 1495 * Set the constructors contained in this class to the given constructors. |
| 1496 * |
| 1497 * @param constructors the constructors contained in this class |
| 1498 */ |
| 1499 void set constructors(List<ConstructorElement> constructors) { |
| 1500 for (ConstructorElement constructor in constructors) { |
| 1501 (constructor as ConstructorElementImpl).enclosingElement = this; |
| 1502 } |
| 1503 this._constructors = constructors; |
| 1504 } |
| 1505 |
| 1506 /** |
| 1507 * Set the fields contained in this class to the given fields. |
| 1508 * |
| 1509 * @param fields the fields contained in this class |
| 1510 */ |
| 1511 void set fields(List<FieldElement> fields) { |
| 1512 for (FieldElement field in fields) { |
| 1513 (field as FieldElementImpl).enclosingElement = this; |
| 1514 } |
| 1515 this._fields = fields; |
| 1516 } |
| 1517 |
| 1518 /** |
| 1519 * Set whether this class references 'super' to the given value. |
| 1520 * |
| 1521 * @param isReferencedSuper `true` references 'super' |
| 1522 */ |
| 1523 void set hasReferenceToSuper(bool isReferencedSuper) { |
| 1524 setModifier(Modifier.REFERENCES_SUPER, isReferencedSuper); |
| 1525 } |
| 1526 |
| 1527 /** |
| 1528 * Set the methods contained in this class to the given methods. |
| 1529 * |
| 1530 * @param methods the methods contained in this class |
| 1531 */ |
| 1532 void set methods(List<MethodElement> methods) { |
| 1533 for (MethodElement method in methods) { |
| 1534 (method as MethodElementImpl).enclosingElement = this; |
| 1535 } |
| 1536 this._methods = methods; |
| 1537 } |
| 1538 |
| 1539 /** |
| 1540 * Set whether this class is defined by a typedef construct to correspond to t
he given value. |
| 1541 * |
| 1542 * @param isTypedef `true` if the class is defined by a typedef construct |
| 1543 */ |
| 1544 void set typedef(bool isTypedef) { |
| 1545 setModifier(Modifier.TYPEDEF, isTypedef); |
| 1546 } |
| 1547 |
| 1548 /** |
| 1549 * Set the type parameters defined for this class to the given type parameters
. |
| 1550 * |
| 1551 * @param typeParameters the type parameters defined for this class |
| 1552 */ |
| 1553 void set typeParameters(List<TypeParameterElement> typeParameters) { |
| 1554 for (TypeParameterElement typeParameter in typeParameters) { |
| 1555 (typeParameter as TypeParameterElementImpl).enclosingElement = this; |
| 1556 } |
| 1557 this._typeParameters = typeParameters; |
| 1558 } |
| 1559 |
| 1560 /** |
| 1561 * Set whether this class is a valid mixin to correspond to the given value. |
| 1562 * |
| 1563 * @param isValidMixin `true` if this class can be used as a mixin |
| 1564 */ |
| 1565 void set validMixin(bool isValidMixin) { |
| 1566 setModifier(Modifier.MIXIN, isValidMixin); |
| 1567 } |
| 1568 |
| 1569 @override |
| 1570 void visitChildren(ElementVisitor visitor) { |
| 1571 super.visitChildren(visitor); |
| 1572 safelyVisitChildren(_accessors, visitor); |
| 1573 safelyVisitChildren(_constructors, visitor); |
| 1574 safelyVisitChildren(_fields, visitor); |
| 1575 safelyVisitChildren(_methods, visitor); |
| 1576 safelyVisitChildren(_toolkitObjects, visitor); |
| 1577 safelyVisitChildren(_typeParameters, visitor); |
| 1578 } |
| 1579 |
| 1580 @override |
| 1581 void appendTo(JavaStringBuilder builder) { |
| 1582 String name = displayName; |
| 1583 if (name == null) { |
| 1584 builder.append("{unnamed class}"); |
| 1585 } else { |
| 1586 builder.append(name); |
| 1587 } |
| 1588 int variableCount = _typeParameters.length; |
| 1589 if (variableCount > 0) { |
| 1590 builder.append("<"); |
| 1591 for (int i = 0; i < variableCount; i++) { |
| 1592 if (i > 0) { |
| 1593 builder.append(", "); |
| 1594 } |
| 1595 (_typeParameters[i] as TypeParameterElementImpl).appendTo(builder); |
| 1596 } |
| 1597 builder.append(">"); |
| 1598 } |
| 1599 } |
| 1600 |
| 1601 void _collectAllSupertypes(List<InterfaceType> supertypes) { |
| 1602 List<InterfaceType> typesToVisit = new List<InterfaceType>(); |
| 1603 List<ClassElement> visitedClasses = new List<ClassElement>(); |
| 1604 typesToVisit.add(this.type); |
| 1605 while (!typesToVisit.isEmpty) { |
| 1606 InterfaceType currentType = typesToVisit.removeAt(0); |
| 1607 ClassElement currentElement = currentType.element; |
| 1608 if (!visitedClasses.contains(currentElement)) { |
| 1609 visitedClasses.add(currentElement); |
| 1610 if (!identical(currentType, this.type)) { |
| 1611 supertypes.add(currentType); |
| 1612 } |
| 1613 InterfaceType supertype = currentType.superclass; |
| 1614 if (supertype != null) { |
| 1615 typesToVisit.add(supertype); |
| 1616 } |
| 1617 for (InterfaceType type in currentElement.interfaces) { |
| 1618 typesToVisit.add(type); |
| 1619 } |
| 1620 for (InterfaceType type in currentElement.mixins) { |
| 1621 ClassElement element = type.element; |
| 1622 if (!visitedClasses.contains(element)) { |
| 1623 supertypes.add(type); |
| 1624 } |
| 1625 } |
| 1626 } |
| 1627 } |
| 1628 } |
| 1629 |
| 1630 bool _safeIsOrInheritsProxy(ClassElement classElt, Set<ClassElement> visitedCl
assElts) { |
| 1631 if (visitedClassElts.contains(classElt)) { |
| 1632 return false; |
| 1633 } |
| 1634 visitedClassElts.add(classElt); |
| 1635 if (classElt.isProxy) { |
| 1636 return true; |
| 1637 } else if (classElt.supertype != null && _safeIsOrInheritsProxy(classElt.sup
ertype.element, visitedClassElts)) { |
| 1638 return true; |
| 1639 } |
| 1640 List<InterfaceType> supertypes = classElt.interfaces; |
| 1641 for (int i = 0; i < supertypes.length; i++) { |
| 1642 if (_safeIsOrInheritsProxy(supertypes[i].element, visitedClassElts)) { |
| 1643 return true; |
| 1644 } |
| 1645 } |
| 1646 supertypes = classElt.mixins; |
| 1647 for (int i = 0; i < supertypes.length; i++) { |
| 1648 if (_safeIsOrInheritsProxy(supertypes[i].element, visitedClassElts)) { |
| 1649 return true; |
| 1650 } |
| 1651 } |
| 1652 return false; |
| 1653 } |
| 1654 } |
| 1655 |
| 1656 /** |
| 317 * The interface `ClassMemberElement` defines the behavior of elements that are
contained | 1657 * The interface `ClassMemberElement` defines the behavior of elements that are
contained |
| 318 * within a [ClassElement]. | 1658 * within a [ClassElement]. |
| 319 */ | 1659 */ |
| 320 abstract class ClassMemberElement implements Element { | 1660 abstract class ClassMemberElement implements Element { |
| 321 /** | 1661 /** |
| 322 * Return the type in which this member is defined. | 1662 * Return the type in which this member is defined. |
| 323 * | 1663 * |
| 324 * @return the type in which this member is defined | 1664 * @return the type in which this member is defined |
| 325 */ | 1665 */ |
| 326 @override | 1666 @override |
| (...skipping 90 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 417 * Return `true` if this compilation unit defines a top-level function named | 1757 * Return `true` if this compilation unit defines a top-level function named |
| 418 * `loadLibrary`. | 1758 * `loadLibrary`. |
| 419 * | 1759 * |
| 420 * @return `true` if this compilation unit defines a top-level function named | 1760 * @return `true` if this compilation unit defines a top-level function named |
| 421 * `loadLibrary` | 1761 * `loadLibrary` |
| 422 */ | 1762 */ |
| 423 bool get hasLoadLibraryFunction; | 1763 bool get hasLoadLibraryFunction; |
| 424 } | 1764 } |
| 425 | 1765 |
| 426 /** | 1766 /** |
| 1767 * Instances of the class `CompilationUnitElementImpl` implement a |
| 1768 * [CompilationUnitElement]. |
| 1769 */ |
| 1770 class CompilationUnitElementImpl extends UriReferencedElementImpl implements Com
pilationUnitElement { |
| 1771 /** |
| 1772 * An empty array of compilation unit elements. |
| 1773 */ |
| 1774 static List<CompilationUnitElement> EMPTY_ARRAY = new List<CompilationUnitElem
ent>(0); |
| 1775 |
| 1776 /** |
| 1777 * The source that corresponds to this compilation unit. |
| 1778 */ |
| 1779 Source source; |
| 1780 |
| 1781 /** |
| 1782 * An array containing all of the top-level accessors (getters and setters) co
ntained in this |
| 1783 * compilation unit. |
| 1784 */ |
| 1785 List<PropertyAccessorElement> _accessors = PropertyAccessorElementImpl.EMPTY_A
RRAY; |
| 1786 |
| 1787 /** |
| 1788 * An array containing all of the top-level functions contained in this compil
ation unit. |
| 1789 */ |
| 1790 List<FunctionElement> _functions = FunctionElementImpl.EMPTY_ARRAY; |
| 1791 |
| 1792 /** |
| 1793 * A table mapping elements to associated toolkit objects. |
| 1794 */ |
| 1795 Map<Element, List<ToolkitObjectElement>> _toolkitObjects = {}; |
| 1796 |
| 1797 /** |
| 1798 * An array containing all of the function type aliases contained in this comp
ilation unit. |
| 1799 */ |
| 1800 List<FunctionTypeAliasElement> _typeAliases = FunctionTypeAliasElementImpl.EMP
TY_ARRAY; |
| 1801 |
| 1802 /** |
| 1803 * An array containing all of the types contained in this compilation unit. |
| 1804 */ |
| 1805 List<ClassElement> _types = ClassElementImpl.EMPTY_ARRAY; |
| 1806 |
| 1807 /** |
| 1808 * An array containing all of the variables contained in this compilation unit
. |
| 1809 */ |
| 1810 List<TopLevelVariableElement> _variables = TopLevelVariableElementImpl.EMPTY_A
RRAY; |
| 1811 |
| 1812 /** |
| 1813 * An array containing all of the Angular views contained in this compilation
unit. |
| 1814 */ |
| 1815 List<AngularViewElement> _angularViews = AngularViewElement.EMPTY_ARRAY; |
| 1816 |
| 1817 /** |
| 1818 * Initialize a newly created compilation unit element to have the given name. |
| 1819 * |
| 1820 * @param name the name of this element |
| 1821 */ |
| 1822 CompilationUnitElementImpl(String name) : super(name, -1); |
| 1823 |
| 1824 @override |
| 1825 accept(ElementVisitor visitor) => visitor.visitCompilationUnitElement(this); |
| 1826 |
| 1827 @override |
| 1828 bool operator ==(Object object) => object != null && runtimeType == object.run
timeType && source == (object as CompilationUnitElementImpl).source; |
| 1829 |
| 1830 @override |
| 1831 List<PropertyAccessorElement> get accessors => _accessors; |
| 1832 |
| 1833 @override |
| 1834 List<AngularViewElement> get angularViews => _angularViews; |
| 1835 |
| 1836 @override |
| 1837 ElementImpl getChild(String identifier) { |
| 1838 // |
| 1839 // The casts in this method are safe because the set methods would have thro
wn a CCE if any of |
| 1840 // the elements in the arrays were not of the expected types. |
| 1841 // |
| 1842 for (PropertyAccessorElement accessor in _accessors) { |
| 1843 if ((accessor as PropertyAccessorElementImpl).identifier == identifier) { |
| 1844 return accessor as PropertyAccessorElementImpl; |
| 1845 } |
| 1846 } |
| 1847 for (VariableElement variable in _variables) { |
| 1848 if ((variable as VariableElementImpl).identifier == identifier) { |
| 1849 return variable as VariableElementImpl; |
| 1850 } |
| 1851 } |
| 1852 for (ExecutableElement function in _functions) { |
| 1853 if ((function as ExecutableElementImpl).identifier == identifier) { |
| 1854 return function as ExecutableElementImpl; |
| 1855 } |
| 1856 } |
| 1857 for (FunctionTypeAliasElement typeAlias in _typeAliases) { |
| 1858 if ((typeAlias as FunctionTypeAliasElementImpl).identifier == identifier)
{ |
| 1859 return typeAlias as FunctionTypeAliasElementImpl; |
| 1860 } |
| 1861 } |
| 1862 for (ClassElement type in _types) { |
| 1863 if ((type as ClassElementImpl).identifier == identifier) { |
| 1864 return type as ClassElementImpl; |
| 1865 } |
| 1866 } |
| 1867 return null; |
| 1868 } |
| 1869 |
| 1870 @override |
| 1871 LibraryElement get enclosingElement => super.enclosingElement as LibraryElemen
t; |
| 1872 |
| 1873 @override |
| 1874 List<FunctionElement> get functions => _functions; |
| 1875 |
| 1876 @override |
| 1877 List<FunctionTypeAliasElement> get functionTypeAliases => _typeAliases; |
| 1878 |
| 1879 @override |
| 1880 ElementKind get kind => ElementKind.COMPILATION_UNIT; |
| 1881 |
| 1882 @override |
| 1883 CompilationUnit get node => unit; |
| 1884 |
| 1885 @override |
| 1886 List<TopLevelVariableElement> get topLevelVariables => _variables; |
| 1887 |
| 1888 @override |
| 1889 ClassElement getType(String className) { |
| 1890 for (ClassElement type in _types) { |
| 1891 if (type.name == className) { |
| 1892 return type; |
| 1893 } |
| 1894 } |
| 1895 return null; |
| 1896 } |
| 1897 |
| 1898 @override |
| 1899 List<ClassElement> get types => _types; |
| 1900 |
| 1901 @override |
| 1902 int get hashCode => source.hashCode; |
| 1903 |
| 1904 @override |
| 1905 bool get hasLoadLibraryFunction { |
| 1906 for (int i = 0; i < _functions.length; i++) { |
| 1907 if (_functions[i].name == FunctionElement.LOAD_LIBRARY_NAME) { |
| 1908 return true; |
| 1909 } |
| 1910 } |
| 1911 return false; |
| 1912 } |
| 1913 |
| 1914 /** |
| 1915 * Set the top-level accessors (getters and setters) contained in this compila
tion unit to the |
| 1916 * given accessors. |
| 1917 * |
| 1918 * @param the top-level accessors (getters and setters) contained in this comp
ilation unit |
| 1919 */ |
| 1920 void set accessors(List<PropertyAccessorElement> accessors) { |
| 1921 for (PropertyAccessorElement accessor in accessors) { |
| 1922 (accessor as PropertyAccessorElementImpl).enclosingElement = this; |
| 1923 } |
| 1924 this._accessors = accessors; |
| 1925 } |
| 1926 |
| 1927 /** |
| 1928 * Set the Angular views defined in this compilation unit. |
| 1929 * |
| 1930 * @param angularViews the Angular views defined in this compilation unit |
| 1931 */ |
| 1932 void set angularViews(List<AngularViewElement> angularViews) { |
| 1933 for (AngularViewElement view in angularViews) { |
| 1934 (view as AngularViewElementImpl).enclosingElement = this; |
| 1935 } |
| 1936 this._angularViews = angularViews; |
| 1937 } |
| 1938 |
| 1939 /** |
| 1940 * Set the top-level functions contained in this compilation unit to the given
functions. |
| 1941 * |
| 1942 * @param functions the top-level functions contained in this compilation unit |
| 1943 */ |
| 1944 void set functions(List<FunctionElement> functions) { |
| 1945 for (FunctionElement function in functions) { |
| 1946 (function as FunctionElementImpl).enclosingElement = this; |
| 1947 } |
| 1948 this._functions = functions; |
| 1949 } |
| 1950 |
| 1951 /** |
| 1952 * Set the top-level variables contained in this compilation unit to the given
variables. |
| 1953 * |
| 1954 * @param variables the top-level variables contained in this compilation unit |
| 1955 */ |
| 1956 void set topLevelVariables(List<TopLevelVariableElement> variables) { |
| 1957 for (TopLevelVariableElement field in variables) { |
| 1958 (field as TopLevelVariableElementImpl).enclosingElement = this; |
| 1959 } |
| 1960 this._variables = variables; |
| 1961 } |
| 1962 |
| 1963 /** |
| 1964 * Set the function type aliases contained in this compilation unit to the giv
en type aliases. |
| 1965 * |
| 1966 * @param typeAliases the function type aliases contained in this compilation
unit |
| 1967 */ |
| 1968 void set typeAliases(List<FunctionTypeAliasElement> typeAliases) { |
| 1969 for (FunctionTypeAliasElement typeAlias in typeAliases) { |
| 1970 (typeAlias as FunctionTypeAliasElementImpl).enclosingElement = this; |
| 1971 } |
| 1972 this._typeAliases = typeAliases; |
| 1973 } |
| 1974 |
| 1975 /** |
| 1976 * Set the types contained in this compilation unit to the given types. |
| 1977 * |
| 1978 * @param types types contained in this compilation unit |
| 1979 */ |
| 1980 void set types(List<ClassElement> types) { |
| 1981 for (ClassElement type in types) { |
| 1982 (type as ClassElementImpl).enclosingElement = this; |
| 1983 } |
| 1984 this._types = types; |
| 1985 } |
| 1986 |
| 1987 @override |
| 1988 void visitChildren(ElementVisitor visitor) { |
| 1989 super.visitChildren(visitor); |
| 1990 safelyVisitChildren(_accessors, visitor); |
| 1991 safelyVisitChildren(_functions, visitor); |
| 1992 safelyVisitChildren(_typeAliases, visitor); |
| 1993 safelyVisitChildren(_types, visitor); |
| 1994 safelyVisitChildren(_variables, visitor); |
| 1995 safelyVisitChildren(_angularViews, visitor); |
| 1996 } |
| 1997 |
| 1998 @override |
| 1999 void appendTo(JavaStringBuilder builder) { |
| 2000 if (source == null) { |
| 2001 builder.append("{compilation unit}"); |
| 2002 } else { |
| 2003 builder.append(source.fullName); |
| 2004 } |
| 2005 } |
| 2006 |
| 2007 @override |
| 2008 String get identifier => source.encoding; |
| 2009 |
| 2010 /** |
| 2011 * Returns the associated toolkit objects. |
| 2012 * |
| 2013 * @param element the [Element] to get toolkit objects for |
| 2014 * @return the associated toolkit objects, may be empty, but not `null` |
| 2015 */ |
| 2016 List<ToolkitObjectElement> _getToolkitObjects(Element element) { |
| 2017 List<ToolkitObjectElement> objects = _toolkitObjects[element]; |
| 2018 if (objects != null) { |
| 2019 return objects; |
| 2020 } |
| 2021 return ToolkitObjectElement.EMPTY_ARRAY; |
| 2022 } |
| 2023 |
| 2024 /** |
| 2025 * Sets the toolkit objects that are associated with the given [Element]. |
| 2026 * |
| 2027 * @param element the [Element] to associate toolkit objects with |
| 2028 * @param objects the toolkit objects to associate |
| 2029 */ |
| 2030 void _setToolkitObjects(Element element, List<ToolkitObjectElement> objects) { |
| 2031 _toolkitObjects[element] = objects; |
| 2032 } |
| 2033 } |
| 2034 |
| 2035 /** |
| 2036 * Instances of the class `ConstFieldElementImpl` implement a `FieldElement` for
a |
| 2037 * 'const' field that has an initializer. |
| 2038 */ |
| 2039 class ConstFieldElementImpl extends FieldElementImpl { |
| 2040 /** |
| 2041 * The result of evaluating this variable's initializer. |
| 2042 */ |
| 2043 EvaluationResultImpl _result; |
| 2044 |
| 2045 /** |
| 2046 * Initialize a newly created field element to have the given name. |
| 2047 * |
| 2048 * @param name the name of this element |
| 2049 */ |
| 2050 ConstFieldElementImpl(Identifier name) : super.con1(name); |
| 2051 |
| 2052 @override |
| 2053 EvaluationResultImpl get evaluationResult => _result; |
| 2054 |
| 2055 @override |
| 2056 void set evaluationResult(EvaluationResultImpl result) { |
| 2057 this._result = result; |
| 2058 } |
| 2059 } |
| 2060 |
| 2061 /** |
| 2062 * Instances of the class `ConstLocalVariableElementImpl` implement a |
| 2063 * `LocalVariableElement` for a local 'const' variable that has an initializer. |
| 2064 */ |
| 2065 class ConstLocalVariableElementImpl extends LocalVariableElementImpl { |
| 2066 /** |
| 2067 * The result of evaluating this variable's initializer. |
| 2068 */ |
| 2069 EvaluationResultImpl _result; |
| 2070 |
| 2071 /** |
| 2072 * Initialize a newly created local variable element to have the given name. |
| 2073 * |
| 2074 * @param name the name of this element |
| 2075 */ |
| 2076 ConstLocalVariableElementImpl(Identifier name) : super(name); |
| 2077 |
| 2078 @override |
| 2079 EvaluationResultImpl get evaluationResult => _result; |
| 2080 |
| 2081 @override |
| 2082 void set evaluationResult(EvaluationResultImpl result) { |
| 2083 this._result = result; |
| 2084 } |
| 2085 } |
| 2086 |
| 2087 /** |
| 2088 * Instances of the class `ConstTopLevelVariableElementImpl` implement a |
| 2089 * `TopLevelVariableElement` for a top-level 'const' variable that has an initia
lizer. |
| 2090 */ |
| 2091 class ConstTopLevelVariableElementImpl extends TopLevelVariableElementImpl { |
| 2092 /** |
| 2093 * The result of evaluating this variable's initializer. |
| 2094 */ |
| 2095 EvaluationResultImpl _result; |
| 2096 |
| 2097 /** |
| 2098 * Initialize a newly created top-level variable element to have the given nam
e. |
| 2099 * |
| 2100 * @param name the name of this element |
| 2101 */ |
| 2102 ConstTopLevelVariableElementImpl(Identifier name) : super.con1(name); |
| 2103 |
| 2104 @override |
| 2105 EvaluationResultImpl get evaluationResult => _result; |
| 2106 |
| 2107 @override |
| 2108 void set evaluationResult(EvaluationResultImpl result) { |
| 2109 this._result = result; |
| 2110 } |
| 2111 } |
| 2112 |
| 2113 /** |
| 427 * The interface `ConstructorElement` defines the behavior of elements represent
ing a | 2114 * The interface `ConstructorElement` defines the behavior of elements represent
ing a |
| 428 * constructor or a factory method defined within a type. | 2115 * constructor or a factory method defined within a type. |
| 429 */ | 2116 */ |
| 430 abstract class ConstructorElement implements ClassMemberElement, ExecutableEleme
nt { | 2117 abstract class ConstructorElement implements ClassMemberElement, ExecutableEleme
nt { |
| 431 /** | 2118 /** |
| 432 * Return the resolved [ConstructorDeclaration] node that declares this | 2119 * Return the resolved [ConstructorDeclaration] node that declares this |
| 433 * [ConstructorElement] . | 2120 * [ConstructorElement] . |
| 434 * | 2121 * |
| 435 * This method is expensive, because resolved AST might be evicted from cache,
so parsing and | 2122 * This method is expensive, because resolved AST might be evicted from cache,
so parsing and |
| 436 * resolving will be performed. | 2123 * resolving will be performed. |
| (...skipping 29 matching lines...) Expand all Loading... |
| 466 | 2153 |
| 467 /** | 2154 /** |
| 468 * Return `true` if this constructor represents a factory constructor. | 2155 * Return `true` if this constructor represents a factory constructor. |
| 469 * | 2156 * |
| 470 * @return `true` if this constructor represents a factory constructor | 2157 * @return `true` if this constructor represents a factory constructor |
| 471 */ | 2158 */ |
| 472 bool get isFactory; | 2159 bool get isFactory; |
| 473 } | 2160 } |
| 474 | 2161 |
| 475 /** | 2162 /** |
| 2163 * Instances of the class `ConstructorElementImpl` implement a `ConstructorEleme
nt`. |
| 2164 */ |
| 2165 class ConstructorElementImpl extends ExecutableElementImpl implements Constructo
rElement { |
| 2166 /** |
| 2167 * An empty array of constructor elements. |
| 2168 */ |
| 2169 static List<ConstructorElement> EMPTY_ARRAY = new List<ConstructorElement>(0); |
| 2170 |
| 2171 /** |
| 2172 * The constructor to which this constructor is redirecting. |
| 2173 */ |
| 2174 ConstructorElement redirectedConstructor; |
| 2175 |
| 2176 /** |
| 2177 * Initialize a newly created constructor element to have the given name. |
| 2178 * |
| 2179 * @param name the name of this element |
| 2180 */ |
| 2181 ConstructorElementImpl.forNode(Identifier name) : super.forNode(name); |
| 2182 |
| 2183 /** |
| 2184 * Initialize a newly created constructor element to have the given name. |
| 2185 * |
| 2186 * @param name the name of this element |
| 2187 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 2188 * declaration of this element |
| 2189 */ |
| 2190 ConstructorElementImpl(String name, int nameOffset) : super(name, nameOffset); |
| 2191 |
| 2192 @override |
| 2193 accept(ElementVisitor visitor) => visitor.visitConstructorElement(this); |
| 2194 |
| 2195 @override |
| 2196 ClassElement get enclosingElement => super.enclosingElement as ClassElement; |
| 2197 |
| 2198 @override |
| 2199 ElementKind get kind => ElementKind.CONSTRUCTOR; |
| 2200 |
| 2201 @override |
| 2202 ConstructorDeclaration get node => getNodeMatching((node) => node is Construct
orDeclaration); |
| 2203 |
| 2204 @override |
| 2205 bool get isConst => hasModifier(Modifier.CONST); |
| 2206 |
| 2207 @override |
| 2208 bool get isDefaultConstructor { |
| 2209 // unnamed |
| 2210 String name = this.name; |
| 2211 if (name != null && name.length != 0) { |
| 2212 return false; |
| 2213 } |
| 2214 // no required parameters |
| 2215 for (ParameterElement parameter in parameters) { |
| 2216 if (parameter.parameterKind == ParameterKind.REQUIRED) { |
| 2217 return false; |
| 2218 } |
| 2219 } |
| 2220 // OK, can be used as default constructor |
| 2221 return true; |
| 2222 } |
| 2223 |
| 2224 @override |
| 2225 bool get isFactory => hasModifier(Modifier.FACTORY); |
| 2226 |
| 2227 @override |
| 2228 bool get isStatic => false; |
| 2229 |
| 2230 /** |
| 2231 * Set whether this constructor represents a 'const' constructor to the given
value. |
| 2232 * |
| 2233 * @param isConst `true` if this constructor represents a 'const' constructor |
| 2234 */ |
| 2235 void set const2(bool isConst) { |
| 2236 setModifier(Modifier.CONST, isConst); |
| 2237 } |
| 2238 |
| 2239 /** |
| 2240 * Set whether this constructor represents a factory method to the given value
. |
| 2241 * |
| 2242 * @param isFactory `true` if this constructor represents a factory method |
| 2243 */ |
| 2244 void set factory(bool isFactory) { |
| 2245 setModifier(Modifier.FACTORY, isFactory); |
| 2246 } |
| 2247 |
| 2248 @override |
| 2249 void appendTo(JavaStringBuilder builder) { |
| 2250 builder.append(enclosingElement.displayName); |
| 2251 String name = displayName; |
| 2252 if (name != null && !name.isEmpty) { |
| 2253 builder.append("."); |
| 2254 builder.append(name); |
| 2255 } |
| 2256 super.appendTo(builder); |
| 2257 } |
| 2258 } |
| 2259 |
| 2260 /** |
| 2261 * Instances of the class `ConstructorMember` represent a constructor element de
fined in a |
| 2262 * parameterized type where the values of the type parameters are known. |
| 2263 */ |
| 2264 class ConstructorMember extends ExecutableMember implements ConstructorElement { |
| 2265 /** |
| 2266 * If the given constructor's type is different when any type parameters from
the defining type's |
| 2267 * declaration are replaced with the actual type arguments from the defining t
ype, create a |
| 2268 * constructor member representing the given constructor. Return the member th
at was created, or |
| 2269 * the base constructor if no member was created. |
| 2270 * |
| 2271 * @param baseConstructor the base constructor for which a member might be cre
ated |
| 2272 * @param definingType the type defining the parameters and arguments to be us
ed in the |
| 2273 * substitution |
| 2274 * @return the constructor element that will return the correctly substituted
types |
| 2275 */ |
| 2276 static ConstructorElement from(ConstructorElement baseConstructor, InterfaceTy
pe definingType) { |
| 2277 if (baseConstructor == null || definingType.typeArguments.length == 0) { |
| 2278 return baseConstructor; |
| 2279 } |
| 2280 FunctionType baseType = baseConstructor.type; |
| 2281 if (baseType == null) { |
| 2282 // TODO(brianwilkerson) We need to understand when this can happen. |
| 2283 return baseConstructor; |
| 2284 } |
| 2285 List<DartType> argumentTypes = definingType.typeArguments; |
| 2286 List<DartType> parameterTypes = definingType.element.type.typeArguments; |
| 2287 FunctionType substitutedType = baseType.substitute2(argumentTypes, parameter
Types); |
| 2288 if (baseType == substitutedType) { |
| 2289 return baseConstructor; |
| 2290 } |
| 2291 // TODO(brianwilkerson) Consider caching the substituted type in the instanc
e. It would use more |
| 2292 // memory but speed up some operations. We need to see how often the type is
being re-computed. |
| 2293 return new ConstructorMember(baseConstructor, definingType); |
| 2294 } |
| 2295 |
| 2296 /** |
| 2297 * Initialize a newly created element to represent a constructor of the given
parameterized type. |
| 2298 * |
| 2299 * @param baseElement the element on which the parameterized element was creat
ed |
| 2300 * @param definingType the type in which the element is defined |
| 2301 */ |
| 2302 ConstructorMember(ConstructorElement baseElement, InterfaceType definingType)
: super(baseElement, definingType); |
| 2303 |
| 2304 @override |
| 2305 accept(ElementVisitor visitor) => visitor.visitConstructorElement(this); |
| 2306 |
| 2307 @override |
| 2308 ConstructorElement get baseElement => super.baseElement as ConstructorElement; |
| 2309 |
| 2310 @override |
| 2311 ClassElement get enclosingElement => baseElement.enclosingElement; |
| 2312 |
| 2313 @override |
| 2314 ConstructorDeclaration get node => baseElement.node; |
| 2315 |
| 2316 @override |
| 2317 ConstructorElement get redirectedConstructor => from(baseElement.redirectedCon
structor, definingType); |
| 2318 |
| 2319 @override |
| 2320 bool get isConst => baseElement.isConst; |
| 2321 |
| 2322 @override |
| 2323 bool get isDefaultConstructor => baseElement.isDefaultConstructor; |
| 2324 |
| 2325 @override |
| 2326 bool get isFactory => baseElement.isFactory; |
| 2327 |
| 2328 @override |
| 2329 String toString() { |
| 2330 ConstructorElement baseElement = this.baseElement; |
| 2331 List<ParameterElement> parameters = this.parameters; |
| 2332 FunctionType type = this.type; |
| 2333 JavaStringBuilder builder = new JavaStringBuilder(); |
| 2334 builder.append(baseElement.enclosingElement.displayName); |
| 2335 String name = displayName; |
| 2336 if (name != null && !name.isEmpty) { |
| 2337 builder.append("."); |
| 2338 builder.append(name); |
| 2339 } |
| 2340 builder.append("("); |
| 2341 int parameterCount = parameters.length; |
| 2342 for (int i = 0; i < parameterCount; i++) { |
| 2343 if (i > 0) { |
| 2344 builder.append(", "); |
| 2345 } |
| 2346 builder.append(parameters[i]).toString(); |
| 2347 } |
| 2348 builder.append(")"); |
| 2349 if (type != null) { |
| 2350 builder.append(Element.RIGHT_ARROW); |
| 2351 builder.append(type.returnType); |
| 2352 } |
| 2353 return builder.toString(); |
| 2354 } |
| 2355 |
| 2356 @override |
| 2357 InterfaceType get definingType => super.definingType as InterfaceType; |
| 2358 } |
| 2359 |
| 2360 /** |
| 2361 * The interface `Type` defines the behavior of objects representing the declare
d type of |
| 2362 * elements in the element model. |
| 2363 */ |
| 2364 abstract class DartType { |
| 2365 /** |
| 2366 * Return the name of this type as it should appear when presented to users in
contexts such as |
| 2367 * error messages. |
| 2368 * |
| 2369 * @return the name of this type |
| 2370 */ |
| 2371 String get displayName; |
| 2372 |
| 2373 /** |
| 2374 * Return the element representing the declaration of this type, or `null` if
the type has |
| 2375 * not, or cannot, be associated with an element. The former case will occur i
f the element model |
| 2376 * is not yet complete; the latter case will occur if this object represents a
n undefined type. |
| 2377 * |
| 2378 * @return the element representing the declaration of this type |
| 2379 */ |
| 2380 Element get element; |
| 2381 |
| 2382 /** |
| 2383 * Return the least upper bound of this type and the given type, or `null` if
there is no |
| 2384 * least upper bound. |
| 2385 * |
| 2386 * @param type the other type used to compute the least upper bound |
| 2387 * @return the least upper bound of this type and the given type |
| 2388 */ |
| 2389 DartType getLeastUpperBound(DartType type); |
| 2390 |
| 2391 /** |
| 2392 * Return the name of this type, or `null` if the type does not have a name, s
uch as when |
| 2393 * the type represents the type of an unnamed function. |
| 2394 * |
| 2395 * @return the name of this type |
| 2396 */ |
| 2397 String get name; |
| 2398 |
| 2399 /** |
| 2400 * Return `true` if this type is assignable to the given type. A type <i>T</i>
may be |
| 2401 * assigned to a type <i>S</i>, written <i>T</i> ⇔ <i>S</i>, iff either <
i>T</i> <: <i>S</i> |
| 2402 * or <i>S</i> <: <i>T</i>. |
| 2403 * |
| 2404 * @param type the type being compared with this type |
| 2405 * @return `true` if this type is assignable to the given type |
| 2406 */ |
| 2407 bool isAssignableTo(DartType type); |
| 2408 |
| 2409 /** |
| 2410 * Return `true` if this type represents the bottom type. |
| 2411 * |
| 2412 * @return `true` if this type represents the bottom type |
| 2413 */ |
| 2414 bool get isBottom; |
| 2415 |
| 2416 /** |
| 2417 * Return `true` if this type represents the type 'Function' defined in the da
rt:core |
| 2418 * library. |
| 2419 * |
| 2420 * @return `true` if this type represents the type 'Function' defined in the d
art:core |
| 2421 * library |
| 2422 */ |
| 2423 bool get isDartCoreFunction; |
| 2424 |
| 2425 /** |
| 2426 * Return `true` if this type represents the type 'dynamic'. |
| 2427 * |
| 2428 * @return `true` if this type represents the type 'dynamic' |
| 2429 */ |
| 2430 bool get isDynamic; |
| 2431 |
| 2432 /** |
| 2433 * Return `true` if this type is more specific than the given type. |
| 2434 * |
| 2435 * @param type the type being compared with this type |
| 2436 * @return `true` if this type is more specific than the given type |
| 2437 */ |
| 2438 bool isMoreSpecificThan(DartType type); |
| 2439 |
| 2440 /** |
| 2441 * Return `true` if this type represents the type 'Object'. |
| 2442 * |
| 2443 * @return `true` if this type represents the type 'Object' |
| 2444 */ |
| 2445 bool get isObject; |
| 2446 |
| 2447 /** |
| 2448 * Return `true` if this type is a subtype of the given type. |
| 2449 * |
| 2450 * @param type the type being compared with this type |
| 2451 * @return `true` if this type is a subtype of the given type |
| 2452 */ |
| 2453 bool isSubtypeOf(DartType type); |
| 2454 |
| 2455 /** |
| 2456 * Return `true` if this type is a supertype of the given type. A type <i>S</i
> is a |
| 2457 * supertype of <i>T</i>, written <i>S</i> :> <i>T</i>, iff <i>T</i> is a subt
ype of <i>S</i>. |
| 2458 * |
| 2459 * @param type the type being compared with this type |
| 2460 * @return `true` if this type is a supertype of the given type |
| 2461 */ |
| 2462 bool isSupertypeOf(DartType type); |
| 2463 |
| 2464 /** |
| 2465 * Return `true` if this type represents the type 'void'. |
| 2466 * |
| 2467 * @return `true` if this type represents the type 'void' |
| 2468 */ |
| 2469 bool get isVoid; |
| 2470 |
| 2471 /** |
| 2472 * Return the type resulting from substituting the given arguments for the giv
en parameters in |
| 2473 * this type. The specification defines this operation in section 2: <blockquo
te> The notation |
| 2474 * <i>[x<sub>1</sub>, ..., x<sub>n</sub>/y<sub>1</sub>, ..., y<sub>n</sub>]E</
i> denotes a copy of |
| 2475 * <i>E</i> in which all occurrences of <i>y<sub>i</sub>, 1 <= i <= n</i> have
been replaced with |
| 2476 * <i>x<sub>i</sub></i>.</blockquote> Note that, contrary to the specification
, this method will |
| 2477 * not create a copy of this type if no substitutions were required, but will
return this type |
| 2478 * directly. |
| 2479 * |
| 2480 * @param argumentTypes the actual type arguments being substituted for the pa
rameters |
| 2481 * @param parameterTypes the parameters to be replaced |
| 2482 * @return the result of performing the substitution |
| 2483 */ |
| 2484 DartType substitute2(List<DartType> argumentTypes, List<DartType> parameterTyp
es); |
| 2485 } |
| 2486 |
| 2487 /** |
| 2488 * Instances of the class `DefaultFieldFormalParameterElementImpl` implement a |
| 2489 * `FieldFormalParameterElementImpl` for parameters that have an initializer. |
| 2490 */ |
| 2491 class DefaultFieldFormalParameterElementImpl extends FieldFormalParameterElement
Impl { |
| 2492 /** |
| 2493 * The result of evaluating this variable's initializer. |
| 2494 */ |
| 2495 EvaluationResultImpl _result; |
| 2496 |
| 2497 /** |
| 2498 * Initialize a newly created parameter element to have the given name. |
| 2499 * |
| 2500 * @param name the name of this element |
| 2501 */ |
| 2502 DefaultFieldFormalParameterElementImpl(Identifier name) : super(name); |
| 2503 |
| 2504 @override |
| 2505 EvaluationResultImpl get evaluationResult => _result; |
| 2506 |
| 2507 @override |
| 2508 void set evaluationResult(EvaluationResultImpl result) { |
| 2509 this._result = result; |
| 2510 } |
| 2511 } |
| 2512 |
| 2513 /** |
| 2514 * Instances of the class `DefaultParameterElementImpl` implement a `ParameterEl
ement` |
| 2515 * for parameters that have an initializer. |
| 2516 */ |
| 2517 class DefaultParameterElementImpl extends ParameterElementImpl { |
| 2518 /** |
| 2519 * The result of evaluating this variable's initializer. |
| 2520 */ |
| 2521 EvaluationResultImpl _result; |
| 2522 |
| 2523 /** |
| 2524 * Initialize a newly created parameter element to have the given name. |
| 2525 * |
| 2526 * @param name the name of this element |
| 2527 */ |
| 2528 DefaultParameterElementImpl(Identifier name) : super.con1(name); |
| 2529 |
| 2530 @override |
| 2531 EvaluationResultImpl get evaluationResult => _result; |
| 2532 |
| 2533 @override |
| 2534 void set evaluationResult(EvaluationResultImpl result) { |
| 2535 this._result = result; |
| 2536 } |
| 2537 } |
| 2538 |
| 2539 /** |
| 2540 * Instances of the class `DynamicElementImpl` represent the synthetic element r
epresenting |
| 2541 * the declaration of the type `dynamic`. |
| 2542 */ |
| 2543 class DynamicElementImpl extends ElementImpl { |
| 2544 /** |
| 2545 * Return the unique instance of this class. |
| 2546 * |
| 2547 * @return the unique instance of this class |
| 2548 */ |
| 2549 static DynamicElementImpl get instance => DynamicTypeImpl.instance.element as
DynamicElementImpl; |
| 2550 |
| 2551 /** |
| 2552 * The type defined by this element. |
| 2553 */ |
| 2554 DynamicTypeImpl type; |
| 2555 |
| 2556 /** |
| 2557 * Initialize a newly created instance of this class. Instances of this class
should <b>not</b> be |
| 2558 * created except as part of creating the type associated with this element. T
he single instance |
| 2559 * of this class should be accessed through the method [getInstance]. |
| 2560 */ |
| 2561 DynamicElementImpl() : super(Keyword.DYNAMIC.syntax, -1) { |
| 2562 setModifier(Modifier.SYNTHETIC, true); |
| 2563 } |
| 2564 |
| 2565 @override |
| 2566 accept(ElementVisitor visitor) => null; |
| 2567 |
| 2568 @override |
| 2569 ElementKind get kind => ElementKind.DYNAMIC; |
| 2570 } |
| 2571 |
| 2572 /** |
| 2573 * The unique instance of the class `DynamicTypeImpl` implements the type `dynam
ic`. |
| 2574 */ |
| 2575 class DynamicTypeImpl extends TypeImpl { |
| 2576 /** |
| 2577 * The unique instance of this class. |
| 2578 */ |
| 2579 static DynamicTypeImpl _INSTANCE = new DynamicTypeImpl(); |
| 2580 |
| 2581 /** |
| 2582 * Return the unique instance of this class. |
| 2583 * |
| 2584 * @return the unique instance of this class |
| 2585 */ |
| 2586 static DynamicTypeImpl get instance => _INSTANCE; |
| 2587 |
| 2588 /** |
| 2589 * Prevent the creation of instances of this class. |
| 2590 */ |
| 2591 DynamicTypeImpl() : super(new DynamicElementImpl(), Keyword.DYNAMIC.syntax) { |
| 2592 (element as DynamicElementImpl).type = this; |
| 2593 } |
| 2594 |
| 2595 @override |
| 2596 bool operator ==(Object object) => identical(object, this); |
| 2597 |
| 2598 @override |
| 2599 int get hashCode => 1; |
| 2600 |
| 2601 @override |
| 2602 bool get isDynamic => true; |
| 2603 |
| 2604 @override |
| 2605 bool isSupertypeOf(DartType type) => true; |
| 2606 |
| 2607 @override |
| 2608 DartType substitute2(List<DartType> argumentTypes, List<DartType> parameterTyp
es) { |
| 2609 int length = parameterTypes.length; |
| 2610 for (int i = 0; i < length; i++) { |
| 2611 if (parameterTypes[i] == this) { |
| 2612 return argumentTypes[i]; |
| 2613 } |
| 2614 } |
| 2615 return this; |
| 2616 } |
| 2617 |
| 2618 @override |
| 2619 bool internalEquals(Object object, Set<ElementPair> visitedElementPairs) => id
entical(object, this); |
| 2620 |
| 2621 @override |
| 2622 bool internalIsMoreSpecificThan(DartType type, bool withDynamic, Set<TypeImpl_
TypePair> visitedTypePairs) { |
| 2623 // T is S |
| 2624 if (identical(this, type)) { |
| 2625 return true; |
| 2626 } |
| 2627 // else |
| 2628 return withDynamic; |
| 2629 } |
| 2630 |
| 2631 @override |
| 2632 bool internalIsSubtypeOf(DartType type, Set<TypeImpl_TypePair> visitedTypePair
s) => true; |
| 2633 } |
| 2634 |
| 2635 /** |
| 476 * The interface `Element` defines the behavior common to all of the elements in
the element | 2636 * The interface `Element` defines the behavior common to all of the elements in
the element |
| 477 * model. Generally speaking, the element model is a semantic model of the progr
am that represents | 2637 * model. Generally speaking, the element model is a semantic model of the progr
am that represents |
| 478 * things that are declared with a name and hence can be referenced elsewhere in
the code. | 2638 * things that are declared with a name and hence can be referenced elsewhere in
the code. |
| 479 * | 2639 * |
| 480 * There are two exceptions to the general case. First, there are elements in th
e element model that | 2640 * There are two exceptions to the general case. First, there are elements in th
e element model that |
| 481 * are created for the convenience of various kinds of analysis but that do not
have any | 2641 * are created for the convenience of various kinds of analysis but that do not
have any |
| 482 * corresponding declaration within the source code. Such elements are marked as
being | 2642 * corresponding declaration within the source code. Such elements are marked as
being |
| 483 * <i>synthetic</i>. Examples of synthetic elements include | 2643 * <i>synthetic</i>. Examples of synthetic elements include |
| 484 * * default constructors in classes that do not define any explicit constructor
s, | 2644 * * default constructors in classes that do not define any explicit constructor
s, |
| 485 * * getters and setters that are induced by explicit field declarations, | 2645 * * getters and setters that are induced by explicit field declarations, |
| (...skipping 244 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 730 * Return `true` if this annotation marks the associated class as implementing
a proxy | 2890 * Return `true` if this annotation marks the associated class as implementing
a proxy |
| 731 * object. | 2891 * object. |
| 732 * | 2892 * |
| 733 * @return `true` if this annotation marks the associated class as implementin
g a proxy | 2893 * @return `true` if this annotation marks the associated class as implementin
g a proxy |
| 734 * object | 2894 * object |
| 735 */ | 2895 */ |
| 736 bool get isProxy; | 2896 bool get isProxy; |
| 737 } | 2897 } |
| 738 | 2898 |
| 739 /** | 2899 /** |
| 2900 * Instances of the class `ElementAnnotationImpl` implement an [ElementAnnotatio
n]. |
| 2901 */ |
| 2902 class ElementAnnotationImpl implements ElementAnnotation { |
| 2903 /** |
| 2904 * The element representing the field, variable, or constructor being used as
an annotation. |
| 2905 */ |
| 2906 final Element element; |
| 2907 |
| 2908 /** |
| 2909 * An empty array of annotations. |
| 2910 */ |
| 2911 static List<ElementAnnotationImpl> EMPTY_ARRAY = new List<ElementAnnotationImp
l>(0); |
| 2912 |
| 2913 /** |
| 2914 * The name of the class used to mark an element as being deprecated. |
| 2915 */ |
| 2916 static String _DEPRECATED_CLASS_NAME = "Deprecated"; |
| 2917 |
| 2918 /** |
| 2919 * The name of the top-level variable used to mark an element as being depreca
ted. |
| 2920 */ |
| 2921 static String _DEPRECATED_VARIABLE_NAME = "deprecated"; |
| 2922 |
| 2923 /** |
| 2924 * The name of the top-level variable used to mark a method as being expected
to override an |
| 2925 * inherited method. |
| 2926 */ |
| 2927 static String _OVERRIDE_VARIABLE_NAME = "override"; |
| 2928 |
| 2929 /** |
| 2930 * The name of the top-level variable used to mark a class as implementing a p
roxy object. |
| 2931 */ |
| 2932 static String PROXY_VARIABLE_NAME = "proxy"; |
| 2933 |
| 2934 /** |
| 2935 * Initialize a newly created annotation. |
| 2936 * |
| 2937 * @param element the element representing the field, variable, or constructor
being used as an |
| 2938 * annotation |
| 2939 */ |
| 2940 ElementAnnotationImpl(this.element); |
| 2941 |
| 2942 @override |
| 2943 bool get isDeprecated { |
| 2944 if (element != null) { |
| 2945 LibraryElement library = element.library; |
| 2946 if (library != null && library.isDartCore) { |
| 2947 if (element is ConstructorElement) { |
| 2948 ConstructorElement constructorElement = element as ConstructorElement; |
| 2949 if (constructorElement.enclosingElement.name == _DEPRECATED_CLASS_NAME
) { |
| 2950 return true; |
| 2951 } |
| 2952 } else if (element is PropertyAccessorElement && element.name == _DEPREC
ATED_VARIABLE_NAME) { |
| 2953 return true; |
| 2954 } |
| 2955 } |
| 2956 } |
| 2957 return false; |
| 2958 } |
| 2959 |
| 2960 @override |
| 2961 bool get isOverride { |
| 2962 if (element != null) { |
| 2963 LibraryElement library = element.library; |
| 2964 if (library != null && library.isDartCore) { |
| 2965 if (element is PropertyAccessorElement && element.name == _OVERRIDE_VARI
ABLE_NAME) { |
| 2966 return true; |
| 2967 } |
| 2968 } |
| 2969 } |
| 2970 return false; |
| 2971 } |
| 2972 |
| 2973 @override |
| 2974 bool get isProxy { |
| 2975 if (element != null) { |
| 2976 LibraryElement library = element.library; |
| 2977 if (library != null && library.isDartCore) { |
| 2978 if (element is PropertyAccessorElement && element.name == PROXY_VARIABLE
_NAME) { |
| 2979 return true; |
| 2980 } |
| 2981 } |
| 2982 } |
| 2983 return false; |
| 2984 } |
| 2985 |
| 2986 @override |
| 2987 String toString() => "@${element.toString()}"; |
| 2988 } |
| 2989 |
| 2990 /** |
| 2991 * The abstract class `ElementImpl` implements the behavior common to objects th
at implement |
| 2992 * an [Element]. |
| 2993 */ |
| 2994 abstract class ElementImpl implements Element { |
| 2995 /** |
| 2996 * The enclosing element of this element, or `null` if this element is at the
root of the |
| 2997 * element structure. |
| 2998 */ |
| 2999 ElementImpl _enclosingElement; |
| 3000 |
| 3001 /** |
| 3002 * The name of this element. |
| 3003 */ |
| 3004 String _name; |
| 3005 |
| 3006 /** |
| 3007 * The offset of the name of this element in the file that contains the declar
ation of this |
| 3008 * element. |
| 3009 */ |
| 3010 int nameOffset = 0; |
| 3011 |
| 3012 /** |
| 3013 * A bit-encoded form of the modifiers associated with this element. |
| 3014 */ |
| 3015 int _modifiers = 0; |
| 3016 |
| 3017 /** |
| 3018 * An array containing all of the metadata associated with this element. |
| 3019 */ |
| 3020 List<ElementAnnotation> metadata = ElementAnnotationImpl.EMPTY_ARRAY; |
| 3021 |
| 3022 /** |
| 3023 * A cached copy of the calculated hashCode for this element. |
| 3024 */ |
| 3025 int _cachedHashCode = 0; |
| 3026 |
| 3027 /** |
| 3028 * Initialize a newly created element to have the given name. |
| 3029 * |
| 3030 * @param name the name of this element |
| 3031 */ |
| 3032 ElementImpl.forNode(Identifier name) : this(name == null ? "" : name.name, nam
e == null ? -1 : name.offset); |
| 3033 |
| 3034 /** |
| 3035 * Initialize a newly created element to have the given name. |
| 3036 * |
| 3037 * @param name the name of this element |
| 3038 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 3039 * declaration of this element |
| 3040 */ |
| 3041 ElementImpl(String name, this.nameOffset) { |
| 3042 this._name = StringUtilities.intern(name); |
| 3043 } |
| 3044 |
| 3045 @override |
| 3046 String computeDocumentationComment() { |
| 3047 AnalysisContext context = this.context; |
| 3048 if (context == null) { |
| 3049 return null; |
| 3050 } |
| 3051 return context.computeDocumentationComment(this); |
| 3052 } |
| 3053 |
| 3054 @override |
| 3055 bool operator ==(Object object) { |
| 3056 if (identical(this, object)) { |
| 3057 return true; |
| 3058 } |
| 3059 if (object == null || hashCode != object.hashCode) { |
| 3060 return false; |
| 3061 } |
| 3062 return object.runtimeType == runtimeType && (object as Element).location ==
location; |
| 3063 } |
| 3064 |
| 3065 @override |
| 3066 Element getAncestor(Predicate<Element> predicate) { |
| 3067 Element ancestor = _enclosingElement; |
| 3068 while (ancestor != null && !predicate(ancestor)) { |
| 3069 ancestor = ancestor.enclosingElement; |
| 3070 } |
| 3071 return ancestor; |
| 3072 } |
| 3073 |
| 3074 /** |
| 3075 * Return the child of this element that is uniquely identified by the given i
dentifier, or |
| 3076 * `null` if there is no such child. |
| 3077 * |
| 3078 * @param identifier the identifier used to select a child |
| 3079 * @return the child of this element with the given identifier |
| 3080 */ |
| 3081 ElementImpl getChild(String identifier) => null; |
| 3082 |
| 3083 @override |
| 3084 AnalysisContext get context { |
| 3085 if (_enclosingElement == null) { |
| 3086 return null; |
| 3087 } |
| 3088 return _enclosingElement.context; |
| 3089 } |
| 3090 |
| 3091 @override |
| 3092 String get displayName => _name; |
| 3093 |
| 3094 @override |
| 3095 Element get enclosingElement => _enclosingElement; |
| 3096 |
| 3097 @override |
| 3098 LibraryElement get library => getAncestor((element) => element is LibraryEleme
nt); |
| 3099 |
| 3100 @override |
| 3101 ElementLocation get location => new ElementLocationImpl.con1(this); |
| 3102 |
| 3103 @override |
| 3104 String get name => _name; |
| 3105 |
| 3106 @override |
| 3107 AstNode get node => getNodeMatching((node) => node is AstNode); |
| 3108 |
| 3109 @override |
| 3110 Source get source { |
| 3111 if (_enclosingElement == null) { |
| 3112 return null; |
| 3113 } |
| 3114 return _enclosingElement.source; |
| 3115 } |
| 3116 |
| 3117 @override |
| 3118 CompilationUnit get unit => context.resolveCompilationUnit(source, library); |
| 3119 |
| 3120 @override |
| 3121 int get hashCode { |
| 3122 // TODO: We might want to re-visit this optimization in the future. |
| 3123 // We cache the hash code value as this is a very frequently called method. |
| 3124 if (_cachedHashCode == 0) { |
| 3125 int hashIdentifier = identifier.hashCode; |
| 3126 Element enclosing = enclosingElement; |
| 3127 if (enclosing != null) { |
| 3128 _cachedHashCode = hashIdentifier + enclosing.hashCode; |
| 3129 } else { |
| 3130 _cachedHashCode = hashIdentifier; |
| 3131 } |
| 3132 } |
| 3133 return _cachedHashCode; |
| 3134 } |
| 3135 |
| 3136 @override |
| 3137 bool isAccessibleIn(LibraryElement library) { |
| 3138 if (Identifier.isPrivateName(_name)) { |
| 3139 return library == this.library; |
| 3140 } |
| 3141 return true; |
| 3142 } |
| 3143 |
| 3144 @override |
| 3145 bool get isDeprecated { |
| 3146 for (ElementAnnotation annotation in metadata) { |
| 3147 if (annotation.isDeprecated) { |
| 3148 return true; |
| 3149 } |
| 3150 } |
| 3151 return false; |
| 3152 } |
| 3153 |
| 3154 @override |
| 3155 bool get isOverride { |
| 3156 for (ElementAnnotation annotation in metadata) { |
| 3157 if (annotation.isOverride) { |
| 3158 return true; |
| 3159 } |
| 3160 } |
| 3161 return false; |
| 3162 } |
| 3163 |
| 3164 @override |
| 3165 bool get isPrivate { |
| 3166 String name = displayName; |
| 3167 if (name == null) { |
| 3168 return true; |
| 3169 } |
| 3170 return Identifier.isPrivateName(name); |
| 3171 } |
| 3172 |
| 3173 @override |
| 3174 bool get isPublic => !isPrivate; |
| 3175 |
| 3176 @override |
| 3177 bool get isSynthetic => hasModifier(Modifier.SYNTHETIC); |
| 3178 |
| 3179 /** |
| 3180 * Set whether this element is synthetic to correspond to the given value. |
| 3181 * |
| 3182 * @param isSynthetic `true` if the element is synthetic |
| 3183 */ |
| 3184 void set synthetic(bool isSynthetic) { |
| 3185 setModifier(Modifier.SYNTHETIC, isSynthetic); |
| 3186 } |
| 3187 |
| 3188 @override |
| 3189 String toString() { |
| 3190 JavaStringBuilder builder = new JavaStringBuilder(); |
| 3191 appendTo(builder); |
| 3192 return builder.toString(); |
| 3193 } |
| 3194 |
| 3195 @override |
| 3196 void visitChildren(ElementVisitor visitor) { |
| 3197 } |
| 3198 |
| 3199 /** |
| 3200 * Append a textual representation of this type to the given builder. |
| 3201 * |
| 3202 * @param builder the builder to which the text is to be appended |
| 3203 */ |
| 3204 void appendTo(JavaStringBuilder builder) { |
| 3205 if (_name == null) { |
| 3206 builder.append("<unnamed "); |
| 3207 builder.append(runtimeType.toString()); |
| 3208 builder.append(">"); |
| 3209 } else { |
| 3210 builder.append(_name); |
| 3211 } |
| 3212 } |
| 3213 |
| 3214 /** |
| 3215 * Set this [Element] as an enclosing for given. |
| 3216 * |
| 3217 * @param element the element to enclose, must be [ElementImpl] |
| 3218 */ |
| 3219 void encloseElement(ElementImpl element) { |
| 3220 element.enclosingElement = this; |
| 3221 } |
| 3222 |
| 3223 /** |
| 3224 * Return an identifier that uniquely identifies this element among the childr
en of this element's |
| 3225 * parent. |
| 3226 * |
| 3227 * @return an identifier that uniquely identifies this element relative to its
parent |
| 3228 */ |
| 3229 String get identifier => name; |
| 3230 |
| 3231 /** |
| 3232 * Return the resolved [AstNode] of the given type enclosing [getNameOffset]. |
| 3233 */ |
| 3234 AstNode getNodeMatching(Predicate<AstNode> predicate) { |
| 3235 CompilationUnit unit = this.unit; |
| 3236 if (unit == null) { |
| 3237 return null; |
| 3238 } |
| 3239 int offset = nameOffset; |
| 3240 AstNode node = new NodeLocator.con1(offset).searchWithin(unit); |
| 3241 if (node == null) { |
| 3242 return null; |
| 3243 } |
| 3244 return node.getAncestor(predicate); |
| 3245 } |
| 3246 |
| 3247 /** |
| 3248 * Return `true` if this element has the given modifier associated with it. |
| 3249 * |
| 3250 * @param modifier the modifier being tested for |
| 3251 * @return `true` if this element has the given modifier associated with it |
| 3252 */ |
| 3253 bool hasModifier(Modifier modifier) => BooleanArray.getEnum(_modifiers, modifi
er); |
| 3254 |
| 3255 /** |
| 3256 * If the given child is not `null`, use the given visitor to visit it. |
| 3257 * |
| 3258 * @param child the child to be visited |
| 3259 * @param visitor the visitor to be used to visit the child |
| 3260 */ |
| 3261 void safelyVisitChild(Element child, ElementVisitor visitor) { |
| 3262 if (child != null) { |
| 3263 child.accept(visitor); |
| 3264 } |
| 3265 } |
| 3266 |
| 3267 /** |
| 3268 * Use the given visitor to visit all of the children in the given array. |
| 3269 * |
| 3270 * @param children the children to be visited |
| 3271 * @param visitor the visitor being used to visit the children |
| 3272 */ |
| 3273 void safelyVisitChildren(List<Element> children, ElementVisitor visitor) { |
| 3274 if (children != null) { |
| 3275 for (Element child in children) { |
| 3276 child.accept(visitor); |
| 3277 } |
| 3278 } |
| 3279 } |
| 3280 |
| 3281 /** |
| 3282 * Set the enclosing element of this element to the given element. |
| 3283 * |
| 3284 * @param element the enclosing element of this element |
| 3285 */ |
| 3286 void set enclosingElement(Element element) { |
| 3287 _enclosingElement = element as ElementImpl; |
| 3288 } |
| 3289 |
| 3290 /** |
| 3291 * Set whether the given modifier is associated with this element to correspon
d to the given |
| 3292 * value. |
| 3293 * |
| 3294 * @param modifier the modifier to be set |
| 3295 * @param value `true` if the modifier is to be associated with this element |
| 3296 */ |
| 3297 void setModifier(Modifier modifier, bool value) { |
| 3298 _modifiers = BooleanArray.setEnum(_modifiers, modifier, value); |
| 3299 } |
| 3300 } |
| 3301 |
| 3302 /** |
| 740 * The enumeration `ElementKind` defines the various kinds of elements in the el
ement model. | 3303 * The enumeration `ElementKind` defines the various kinds of elements in the el
ement model. |
| 741 */ | 3304 */ |
| 742 class ElementKind extends Enum<ElementKind> { | 3305 class ElementKind extends Enum<ElementKind> { |
| 743 static const ElementKind ANGULAR_FORMATTER = const ElementKind('ANGULAR_FORMAT
TER', 0, "Angular formatter"); | 3306 static const ElementKind ANGULAR_FORMATTER = const ElementKind('ANGULAR_FORMAT
TER', 0, "Angular formatter"); |
| 744 | 3307 |
| 745 static const ElementKind ANGULAR_COMPONENT = const ElementKind('ANGULAR_COMPON
ENT', 1, "Angular component"); | 3308 static const ElementKind ANGULAR_COMPONENT = const ElementKind('ANGULAR_COMPON
ENT', 1, "Angular component"); |
| 746 | 3309 |
| 747 static const ElementKind ANGULAR_CONTROLLER = const ElementKind('ANGULAR_CONTR
OLLER', 2, "Angular controller"); | 3310 static const ElementKind ANGULAR_CONTROLLER = const ElementKind('ANGULAR_CONTR
OLLER', 2, "Angular controller"); |
| 748 | 3311 |
| 749 static const ElementKind ANGULAR_DIRECTIVE = const ElementKind('ANGULAR_DIRECT
IVE', 3, "Angular directive"); | 3312 static const ElementKind ANGULAR_DIRECTIVE = const ElementKind('ANGULAR_DIRECT
IVE', 3, "Angular directive"); |
| (...skipping 135 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 885 /** | 3448 /** |
| 886 * Return an encoded representation of this location that can be used to creat
e a location that is | 3449 * Return an encoded representation of this location that can be used to creat
e a location that is |
| 887 * equal to this location. | 3450 * equal to this location. |
| 888 * | 3451 * |
| 889 * @return an encoded representation of this location | 3452 * @return an encoded representation of this location |
| 890 */ | 3453 */ |
| 891 String get encoding; | 3454 String get encoding; |
| 892 } | 3455 } |
| 893 | 3456 |
| 894 /** | 3457 /** |
| 3458 * Instances of the class `ElementLocationImpl` implement an [ElementLocation]. |
| 3459 */ |
| 3460 class ElementLocationImpl implements ElementLocation { |
| 3461 /** |
| 3462 * The path to the element whose location is represented by this object. |
| 3463 */ |
| 3464 List<String> _components; |
| 3465 |
| 3466 /** |
| 3467 * The character used to separate components in the encoded form. |
| 3468 */ |
| 3469 static int _SEPARATOR_CHAR = 0x3B; |
| 3470 |
| 3471 /** |
| 3472 * Initialize a newly created location to represent the given element. |
| 3473 * |
| 3474 * @param element the element whose location is being represented |
| 3475 */ |
| 3476 ElementLocationImpl.con1(Element element) { |
| 3477 List<String> components = new List<String>(); |
| 3478 Element ancestor = element; |
| 3479 while (ancestor != null) { |
| 3480 components.insert(0, (ancestor as ElementImpl).identifier); |
| 3481 ancestor = ancestor.enclosingElement; |
| 3482 } |
| 3483 this._components = new List.from(components); |
| 3484 } |
| 3485 |
| 3486 /** |
| 3487 * Initialize a newly created location from the given encoded form. |
| 3488 * |
| 3489 * @param encoding the encoded form of a location |
| 3490 */ |
| 3491 ElementLocationImpl.con2(String encoding) { |
| 3492 this._components = _decode(encoding); |
| 3493 } |
| 3494 |
| 3495 @override |
| 3496 bool operator ==(Object object) { |
| 3497 if (identical(this, object)) { |
| 3498 return true; |
| 3499 } |
| 3500 if (object is! ElementLocationImpl) { |
| 3501 return false; |
| 3502 } |
| 3503 ElementLocationImpl location = object as ElementLocationImpl; |
| 3504 List<String> otherComponents = location._components; |
| 3505 int length = _components.length; |
| 3506 if (otherComponents.length != length) { |
| 3507 return false; |
| 3508 } |
| 3509 for (int i = length - 1; i >= 2; i--) { |
| 3510 if (_components[i] != otherComponents[i]) { |
| 3511 return false; |
| 3512 } |
| 3513 } |
| 3514 if (length > 1 && !_equalSourceComponents(_components[1], otherComponents[1]
)) { |
| 3515 return false; |
| 3516 } |
| 3517 if (length > 0 && !_equalSourceComponents(_components[0], otherComponents[0]
)) { |
| 3518 return false; |
| 3519 } |
| 3520 return true; |
| 3521 } |
| 3522 |
| 3523 /** |
| 3524 * Return the path to the element whose location is represented by this object
. |
| 3525 * |
| 3526 * @return the path to the element whose location is represented by this objec
t |
| 3527 */ |
| 3528 List<String> get components => _components; |
| 3529 |
| 3530 @override |
| 3531 String get encoding { |
| 3532 JavaStringBuilder builder = new JavaStringBuilder(); |
| 3533 int length = _components.length; |
| 3534 for (int i = 0; i < length; i++) { |
| 3535 if (i > 0) { |
| 3536 builder.appendChar(_SEPARATOR_CHAR); |
| 3537 } |
| 3538 _encode(builder, _components[i]); |
| 3539 } |
| 3540 return builder.toString(); |
| 3541 } |
| 3542 |
| 3543 @override |
| 3544 int get hashCode { |
| 3545 int result = 1; |
| 3546 for (int i = 0; i < _components.length; i++) { |
| 3547 String component = _components[i]; |
| 3548 int componentHash; |
| 3549 if (i <= 1) { |
| 3550 componentHash = _hashSourceComponent(component); |
| 3551 } else { |
| 3552 componentHash = component.hashCode; |
| 3553 } |
| 3554 result = 31 * result + componentHash; |
| 3555 } |
| 3556 return result; |
| 3557 } |
| 3558 |
| 3559 @override |
| 3560 String toString() => encoding; |
| 3561 |
| 3562 /** |
| 3563 * Decode the encoded form of a location into an array of components. |
| 3564 * |
| 3565 * @param encoding the encoded form of a location |
| 3566 * @return the components that were encoded |
| 3567 */ |
| 3568 List<String> _decode(String encoding) { |
| 3569 List<String> components = new List<String>(); |
| 3570 JavaStringBuilder builder = new JavaStringBuilder(); |
| 3571 int index = 0; |
| 3572 int length = encoding.length; |
| 3573 while (index < length) { |
| 3574 int currentChar = encoding.codeUnitAt(index); |
| 3575 if (currentChar == _SEPARATOR_CHAR) { |
| 3576 if (index + 1 < length && encoding.codeUnitAt(index + 1) == _SEPARATOR_C
HAR) { |
| 3577 builder.appendChar(_SEPARATOR_CHAR); |
| 3578 index += 2; |
| 3579 } else { |
| 3580 components.add(builder.toString()); |
| 3581 builder.length = 0; |
| 3582 index++; |
| 3583 } |
| 3584 } else { |
| 3585 builder.appendChar(currentChar); |
| 3586 index++; |
| 3587 } |
| 3588 } |
| 3589 if (builder.length > 0) { |
| 3590 components.add(builder.toString()); |
| 3591 } |
| 3592 return new List.from(components); |
| 3593 } |
| 3594 |
| 3595 /** |
| 3596 * Append an encoded form of the given component to the given builder. |
| 3597 * |
| 3598 * @param builder the builder to which the encoded component is to be appended |
| 3599 * @param component the component to be appended to the builder |
| 3600 */ |
| 3601 void _encode(JavaStringBuilder builder, String component) { |
| 3602 int length = component.length; |
| 3603 for (int i = 0; i < length; i++) { |
| 3604 int currentChar = component.codeUnitAt(i); |
| 3605 if (currentChar == _SEPARATOR_CHAR) { |
| 3606 builder.appendChar(_SEPARATOR_CHAR); |
| 3607 } |
| 3608 builder.appendChar(currentChar); |
| 3609 } |
| 3610 } |
| 3611 |
| 3612 /** |
| 3613 * Return `true` if the given components, when interpreted to be encoded sourc
es with a |
| 3614 * leading source type indicator, are equal when the source type's are ignored
. |
| 3615 * |
| 3616 * @param left the left component being compared |
| 3617 * @param right the right component being compared |
| 3618 * @return `true` if the given components are equal when the source type's are
ignored |
| 3619 */ |
| 3620 bool _equalSourceComponents(String left, String right) { |
| 3621 // TODO(brianwilkerson) This method can go away when sources no longer have
a URI kind. |
| 3622 if (left == null) { |
| 3623 return right == null; |
| 3624 } else if (right == null) { |
| 3625 return false; |
| 3626 } |
| 3627 int leftLength = left.length; |
| 3628 int rightLength = right.length; |
| 3629 if (leftLength != rightLength) { |
| 3630 return false; |
| 3631 } else if (leftLength <= 1 || rightLength <= 1) { |
| 3632 return left == right; |
| 3633 } |
| 3634 return javaStringRegionMatches(left, 1, right, 1, leftLength - 1); |
| 3635 } |
| 3636 |
| 3637 /** |
| 3638 * Return the hash code of the given encoded source component, ignoring the so
urce type indicator. |
| 3639 * |
| 3640 * @param sourceComponent the component to compute a hash code |
| 3641 * @return the hash code of the given encoded source component |
| 3642 */ |
| 3643 int _hashSourceComponent(String sourceComponent) { |
| 3644 // TODO(brianwilkerson) This method can go away when sources no longer have
a URI kind. |
| 3645 if (sourceComponent.length <= 1) { |
| 3646 return sourceComponent.hashCode; |
| 3647 } |
| 3648 return sourceComponent.substring(1).hashCode; |
| 3649 } |
| 3650 } |
| 3651 |
| 3652 /** |
| 3653 * The class `ElementPair` is a pair of [Element]s. [Object#equals] and |
| 3654 * [Object#hashCode] so this class can be used in hashed data structures. |
| 3655 */ |
| 3656 class ElementPair { |
| 3657 /** |
| 3658 * The first [Element] |
| 3659 */ |
| 3660 final Element _first; |
| 3661 |
| 3662 /** |
| 3663 * The second [Element] |
| 3664 */ |
| 3665 final Element _second; |
| 3666 |
| 3667 /** |
| 3668 * The sole constructor for this class, taking two [Element]s. |
| 3669 * |
| 3670 * @param first the first element |
| 3671 * @param second the second element |
| 3672 */ |
| 3673 ElementPair(this._first, this._second); |
| 3674 |
| 3675 @override |
| 3676 bool operator ==(Object object) { |
| 3677 if (identical(object, this)) { |
| 3678 return true; |
| 3679 } |
| 3680 if (object is ElementPair) { |
| 3681 ElementPair elementPair = object; |
| 3682 return (_first == elementPair._first) && (_second == elementPair._second); |
| 3683 } |
| 3684 return false; |
| 3685 } |
| 3686 |
| 3687 /** |
| 3688 * Return the first element. |
| 3689 * |
| 3690 * @return the first element |
| 3691 */ |
| 3692 Element get firstElt => _first; |
| 3693 |
| 3694 /** |
| 3695 * Return the second element |
| 3696 * |
| 3697 * @return the second element |
| 3698 */ |
| 3699 Element get secondElt => _second; |
| 3700 |
| 3701 @override |
| 3702 int get hashCode => ObjectUtilities.combineHashCodes(_first.hashCode, _second.
hashCode); |
| 3703 } |
| 3704 |
| 3705 /** |
| 895 * The interface `ElementVisitor` defines the behavior of objects that can be us
ed to visit an | 3706 * The interface `ElementVisitor` defines the behavior of objects that can be us
ed to visit an |
| 896 * element structure. | 3707 * element structure. |
| 897 */ | 3708 */ |
| 898 abstract class ElementVisitor<R> { | 3709 abstract class ElementVisitor<R> { |
| 899 R visitAngularComponentElement(AngularComponentElement element); | 3710 R visitAngularComponentElement(AngularComponentElement element); |
| 900 | 3711 |
| 901 R visitAngularControllerElement(AngularControllerElement element); | 3712 R visitAngularControllerElement(AngularControllerElement element); |
| 902 | 3713 |
| 903 R visitAngularDirectiveElement(AngularDecoratorElement element); | 3714 R visitAngularDirectiveElement(AngularDecoratorElement element); |
| 904 | 3715 |
| (...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 970 abstract class EmbeddedHtmlScriptElement implements HtmlScriptElement { | 3781 abstract class EmbeddedHtmlScriptElement implements HtmlScriptElement { |
| 971 /** | 3782 /** |
| 972 * Return the library element defined by the content of the script tag. | 3783 * Return the library element defined by the content of the script tag. |
| 973 * | 3784 * |
| 974 * @return the library element (not `null`) | 3785 * @return the library element (not `null`) |
| 975 */ | 3786 */ |
| 976 LibraryElement get scriptLibrary; | 3787 LibraryElement get scriptLibrary; |
| 977 } | 3788 } |
| 978 | 3789 |
| 979 /** | 3790 /** |
| 3791 * Instances of the class `EmbeddedHtmlScriptElementImpl` implement an |
| 3792 * [EmbeddedHtmlScriptElement]. |
| 3793 */ |
| 3794 class EmbeddedHtmlScriptElementImpl extends HtmlScriptElementImpl implements Emb
eddedHtmlScriptElement { |
| 3795 /** |
| 3796 * The library defined by the script tag's content. |
| 3797 */ |
| 3798 LibraryElement _scriptLibrary; |
| 3799 |
| 3800 /** |
| 3801 * Initialize a newly created script element to have the specified tag name an
d offset. |
| 3802 * |
| 3803 * @param node the XML node from which this element is derived (not `null`) |
| 3804 */ |
| 3805 EmbeddedHtmlScriptElementImpl(XmlTagNode node) : super(node); |
| 3806 |
| 3807 @override |
| 3808 accept(ElementVisitor visitor) => visitor.visitEmbeddedHtmlScriptElement(this)
; |
| 3809 |
| 3810 @override |
| 3811 ElementKind get kind => ElementKind.EMBEDDED_HTML_SCRIPT; |
| 3812 |
| 3813 @override |
| 3814 LibraryElement get scriptLibrary => _scriptLibrary; |
| 3815 |
| 3816 /** |
| 3817 * Set the script library defined by the script tag's content. |
| 3818 * |
| 3819 * @param scriptLibrary the library or `null` if none |
| 3820 */ |
| 3821 void set scriptLibrary(LibraryElementImpl scriptLibrary) { |
| 3822 scriptLibrary.enclosingElement = this; |
| 3823 this._scriptLibrary = scriptLibrary; |
| 3824 } |
| 3825 |
| 3826 @override |
| 3827 void visitChildren(ElementVisitor visitor) { |
| 3828 safelyVisitChild(_scriptLibrary, visitor); |
| 3829 } |
| 3830 } |
| 3831 |
| 3832 /** |
| 980 * The interface `ExecutableElement` defines the behavior of elements representi
ng an | 3833 * The interface `ExecutableElement` defines the behavior of elements representi
ng an |
| 981 * executable object, including functions, methods, constructors, getters, and s
etters. | 3834 * executable object, including functions, methods, constructors, getters, and s
etters. |
| 982 */ | 3835 */ |
| 983 abstract class ExecutableElement implements Element { | 3836 abstract class ExecutableElement implements Element { |
| 984 /** | 3837 /** |
| 985 * Return an array containing all of the functions defined within this executa
ble element. | 3838 * Return an array containing all of the functions defined within this executa
ble element. |
| 986 * | 3839 * |
| 987 * @return the functions defined within this executable element | 3840 * @return the functions defined within this executable element |
| 988 */ | 3841 */ |
| 989 List<FunctionElement> get functions; | 3842 List<FunctionElement> get functions; |
| (...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1035 /** | 3888 /** |
| 1036 * Return `true` if this element is a static element. A static element is an e
lement that is | 3889 * Return `true` if this element is a static element. A static element is an e
lement that is |
| 1037 * not associated with a particular instance, but rather with an entire librar
y or class. | 3890 * not associated with a particular instance, but rather with an entire librar
y or class. |
| 1038 * | 3891 * |
| 1039 * @return `true` if this executable element is a static element | 3892 * @return `true` if this executable element is a static element |
| 1040 */ | 3893 */ |
| 1041 bool get isStatic; | 3894 bool get isStatic; |
| 1042 } | 3895 } |
| 1043 | 3896 |
| 1044 /** | 3897 /** |
| 3898 * The abstract class `ExecutableElementImpl` implements the behavior common to |
| 3899 * `ExecutableElement`s. |
| 3900 */ |
| 3901 abstract class ExecutableElementImpl extends ElementImpl implements ExecutableEl
ement { |
| 3902 /** |
| 3903 * An array containing all of the functions defined within this executable ele
ment. |
| 3904 */ |
| 3905 List<FunctionElement> _functions = FunctionElementImpl.EMPTY_ARRAY; |
| 3906 |
| 3907 /** |
| 3908 * An array containing all of the labels defined within this executable elemen
t. |
| 3909 */ |
| 3910 List<LabelElement> _labels = LabelElementImpl.EMPTY_ARRAY; |
| 3911 |
| 3912 /** |
| 3913 * An array containing all of the local variables defined within this executab
le element. |
| 3914 */ |
| 3915 List<LocalVariableElement> _localVariables = LocalVariableElementImpl.EMPTY_AR
RAY; |
| 3916 |
| 3917 /** |
| 3918 * An array containing all of the parameters defined by this executable elemen
t. |
| 3919 */ |
| 3920 List<ParameterElement> _parameters = ParameterElementImpl.EMPTY_ARRAY; |
| 3921 |
| 3922 /** |
| 3923 * The return type defined by this executable element. |
| 3924 */ |
| 3925 DartType returnType; |
| 3926 |
| 3927 /** |
| 3928 * The type of function defined by this executable element. |
| 3929 */ |
| 3930 FunctionType type; |
| 3931 |
| 3932 /** |
| 3933 * An empty array of executable elements. |
| 3934 */ |
| 3935 static List<ExecutableElement> EMPTY_ARRAY = new List<ExecutableElement>(0); |
| 3936 |
| 3937 /** |
| 3938 * Initialize a newly created executable element to have the given name. |
| 3939 * |
| 3940 * @param name the name of this element |
| 3941 */ |
| 3942 ExecutableElementImpl.forNode(Identifier name) : super.forNode(name); |
| 3943 |
| 3944 /** |
| 3945 * Initialize a newly created executable element to have the given name. |
| 3946 * |
| 3947 * @param name the name of this element |
| 3948 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 3949 * declaration of this element |
| 3950 */ |
| 3951 ExecutableElementImpl(String name, int nameOffset) : super(name, nameOffset); |
| 3952 |
| 3953 @override |
| 3954 ElementImpl getChild(String identifier) { |
| 3955 for (ExecutableElement function in _functions) { |
| 3956 if ((function as ExecutableElementImpl).identifier == identifier) { |
| 3957 return function as ExecutableElementImpl; |
| 3958 } |
| 3959 } |
| 3960 for (LabelElement label in _labels) { |
| 3961 if ((label as LabelElementImpl).identifier == identifier) { |
| 3962 return label as LabelElementImpl; |
| 3963 } |
| 3964 } |
| 3965 for (VariableElement variable in _localVariables) { |
| 3966 if ((variable as VariableElementImpl).identifier == identifier) { |
| 3967 return variable as VariableElementImpl; |
| 3968 } |
| 3969 } |
| 3970 for (ParameterElement parameter in _parameters) { |
| 3971 if ((parameter as ParameterElementImpl).identifier == identifier) { |
| 3972 return parameter as ParameterElementImpl; |
| 3973 } |
| 3974 } |
| 3975 return null; |
| 3976 } |
| 3977 |
| 3978 @override |
| 3979 List<FunctionElement> get functions => _functions; |
| 3980 |
| 3981 @override |
| 3982 List<LabelElement> get labels => _labels; |
| 3983 |
| 3984 @override |
| 3985 List<LocalVariableElement> get localVariables => _localVariables; |
| 3986 |
| 3987 @override |
| 3988 List<ParameterElement> get parameters => _parameters; |
| 3989 |
| 3990 @override |
| 3991 bool get isOperator => false; |
| 3992 |
| 3993 /** |
| 3994 * Set the functions defined within this executable element to the given funct
ions. |
| 3995 * |
| 3996 * @param functions the functions defined within this executable element |
| 3997 */ |
| 3998 void set functions(List<FunctionElement> functions) { |
| 3999 for (FunctionElement function in functions) { |
| 4000 (function as FunctionElementImpl).enclosingElement = this; |
| 4001 } |
| 4002 this._functions = functions; |
| 4003 } |
| 4004 |
| 4005 /** |
| 4006 * Set the labels defined within this executable element to the given labels. |
| 4007 * |
| 4008 * @param labels the labels defined within this executable element |
| 4009 */ |
| 4010 void set labels(List<LabelElement> labels) { |
| 4011 for (LabelElement label in labels) { |
| 4012 (label as LabelElementImpl).enclosingElement = this; |
| 4013 } |
| 4014 this._labels = labels; |
| 4015 } |
| 4016 |
| 4017 /** |
| 4018 * Set the local variables defined within this executable element to the given
variables. |
| 4019 * |
| 4020 * @param localVariables the local variables defined within this executable el
ement |
| 4021 */ |
| 4022 void set localVariables(List<LocalVariableElement> localVariables) { |
| 4023 for (LocalVariableElement variable in localVariables) { |
| 4024 (variable as LocalVariableElementImpl).enclosingElement = this; |
| 4025 } |
| 4026 this._localVariables = localVariables; |
| 4027 } |
| 4028 |
| 4029 /** |
| 4030 * Set the parameters defined by this executable element to the given paramete
rs. |
| 4031 * |
| 4032 * @param parameters the parameters defined by this executable element |
| 4033 */ |
| 4034 void set parameters(List<ParameterElement> parameters) { |
| 4035 for (ParameterElement parameter in parameters) { |
| 4036 (parameter as ParameterElementImpl).enclosingElement = this; |
| 4037 } |
| 4038 this._parameters = parameters; |
| 4039 } |
| 4040 |
| 4041 @override |
| 4042 void visitChildren(ElementVisitor visitor) { |
| 4043 super.visitChildren(visitor); |
| 4044 safelyVisitChildren(_functions, visitor); |
| 4045 safelyVisitChildren(_labels, visitor); |
| 4046 safelyVisitChildren(_localVariables, visitor); |
| 4047 safelyVisitChildren(_parameters, visitor); |
| 4048 } |
| 4049 |
| 4050 @override |
| 4051 void appendTo(JavaStringBuilder builder) { |
| 4052 if (this.kind != ElementKind.GETTER) { |
| 4053 builder.append("("); |
| 4054 String closing = null; |
| 4055 ParameterKind kind = ParameterKind.REQUIRED; |
| 4056 int parameterCount = _parameters.length; |
| 4057 for (int i = 0; i < parameterCount; i++) { |
| 4058 if (i > 0) { |
| 4059 builder.append(", "); |
| 4060 } |
| 4061 ParameterElementImpl parameter = _parameters[i] as ParameterElementImpl; |
| 4062 ParameterKind parameterKind = parameter.parameterKind; |
| 4063 if (parameterKind != kind) { |
| 4064 if (closing != null) { |
| 4065 builder.append(closing); |
| 4066 } |
| 4067 if (parameterKind == ParameterKind.POSITIONAL) { |
| 4068 builder.append("["); |
| 4069 closing = "]"; |
| 4070 } else if (parameterKind == ParameterKind.NAMED) { |
| 4071 builder.append("{"); |
| 4072 closing = "}"; |
| 4073 } else { |
| 4074 closing = null; |
| 4075 } |
| 4076 } |
| 4077 kind = parameterKind; |
| 4078 parameter.appendToWithoutDelimiters(builder); |
| 4079 } |
| 4080 if (closing != null) { |
| 4081 builder.append(closing); |
| 4082 } |
| 4083 builder.append(")"); |
| 4084 } |
| 4085 if (type != null) { |
| 4086 builder.append(Element.RIGHT_ARROW); |
| 4087 builder.append(type.returnType); |
| 4088 } |
| 4089 } |
| 4090 } |
| 4091 |
| 4092 /** |
| 4093 * The abstract class `ExecutableMember` defines the behavior common to members
that represent |
| 4094 * an executable element defined in a parameterized type where the values of the
type parameters are |
| 4095 * known. |
| 4096 */ |
| 4097 abstract class ExecutableMember extends Member implements ExecutableElement { |
| 4098 /** |
| 4099 * Initialize a newly created element to represent an executable element of th
e given |
| 4100 * parameterized type. |
| 4101 * |
| 4102 * @param baseElement the element on which the parameterized element was creat
ed |
| 4103 * @param definingType the type in which the element is defined |
| 4104 */ |
| 4105 ExecutableMember(ExecutableElement baseElement, InterfaceType definingType) :
super(baseElement, definingType); |
| 4106 |
| 4107 @override |
| 4108 ExecutableElement get baseElement => super.baseElement as ExecutableElement; |
| 4109 |
| 4110 @override |
| 4111 List<FunctionElement> get functions { |
| 4112 // |
| 4113 // Elements within this element should have type parameters substituted, jus
t like this element. |
| 4114 // |
| 4115 throw new UnsupportedOperationException(); |
| 4116 } |
| 4117 |
| 4118 @override |
| 4119 List<LabelElement> get labels => baseElement.labels; |
| 4120 |
| 4121 @override |
| 4122 List<LocalVariableElement> get localVariables { |
| 4123 // |
| 4124 // Elements within this element should have type parameters substituted, jus
t like this element. |
| 4125 // |
| 4126 throw new UnsupportedOperationException(); |
| 4127 } |
| 4128 |
| 4129 @override |
| 4130 List<ParameterElement> get parameters { |
| 4131 List<ParameterElement> baseParameters = baseElement.parameters; |
| 4132 int parameterCount = baseParameters.length; |
| 4133 if (parameterCount == 0) { |
| 4134 return baseParameters; |
| 4135 } |
| 4136 List<ParameterElement> parameterizedParameters = new List<ParameterElement>(
parameterCount); |
| 4137 for (int i = 0; i < parameterCount; i++) { |
| 4138 parameterizedParameters[i] = ParameterMember.from(baseParameters[i], defin
ingType); |
| 4139 } |
| 4140 return parameterizedParameters; |
| 4141 } |
| 4142 |
| 4143 @override |
| 4144 DartType get returnType => substituteFor(baseElement.returnType); |
| 4145 |
| 4146 @override |
| 4147 FunctionType get type => substituteFor(baseElement.type); |
| 4148 |
| 4149 @override |
| 4150 bool get isOperator => baseElement.isOperator; |
| 4151 |
| 4152 @override |
| 4153 bool get isStatic => baseElement.isStatic; |
| 4154 |
| 4155 @override |
| 4156 void visitChildren(ElementVisitor visitor) { |
| 4157 // TODO(brianwilkerson) We need to finish implementing the accessors used be
low so that we can |
| 4158 // safely invoke them. |
| 4159 super.visitChildren(visitor); |
| 4160 safelyVisitChildren(baseElement.functions, visitor); |
| 4161 safelyVisitChildren(labels, visitor); |
| 4162 safelyVisitChildren(baseElement.localVariables, visitor); |
| 4163 safelyVisitChildren(parameters, visitor); |
| 4164 } |
| 4165 } |
| 4166 |
| 4167 /** |
| 1045 * The interface `ExportElement` defines the behavior of objects representing in
formation | 4168 * The interface `ExportElement` defines the behavior of objects representing in
formation |
| 1046 * about a single export directive within a library. | 4169 * about a single export directive within a library. |
| 1047 */ | 4170 */ |
| 1048 abstract class ExportElement implements Element, UriReferencedElement { | 4171 abstract class ExportElement implements Element, UriReferencedElement { |
| 1049 /** | 4172 /** |
| 1050 * An empty array of export elements. | 4173 * An empty array of export elements. |
| 1051 */ | 4174 */ |
| 1052 static final List<ExportElement> EMPTY_ARRAY = new List<ExportElement>(0); | 4175 static final List<ExportElement> EMPTY_ARRAY = new List<ExportElement>(0); |
| 1053 | 4176 |
| 1054 /** | 4177 /** |
| 1055 * Return an array containing the combinators that were specified as part of t
he export directive | 4178 * Return an array containing the combinators that were specified as part of t
he export directive |
| 1056 * in the order in which they were specified. | 4179 * in the order in which they were specified. |
| 1057 * | 4180 * |
| 1058 * @return the combinators specified in the export directive | 4181 * @return the combinators specified in the export directive |
| 1059 */ | 4182 */ |
| 1060 List<NamespaceCombinator> get combinators; | 4183 List<NamespaceCombinator> get combinators; |
| 1061 | 4184 |
| 1062 /** | 4185 /** |
| 1063 * Return the library that is exported from this library by this export direct
ive. | 4186 * Return the library that is exported from this library by this export direct
ive. |
| 1064 * | 4187 * |
| 1065 * @return the library that is exported from this library | 4188 * @return the library that is exported from this library |
| 1066 */ | 4189 */ |
| 1067 LibraryElement get exportedLibrary; | 4190 LibraryElement get exportedLibrary; |
| 1068 } | 4191 } |
| 1069 | 4192 |
| 1070 /** | 4193 /** |
| 4194 * Instances of the class `ExportElementImpl` implement an [ExportElement]. |
| 4195 */ |
| 4196 class ExportElementImpl extends UriReferencedElementImpl implements ExportElemen
t { |
| 4197 /** |
| 4198 * The library that is exported from this library by this export directive. |
| 4199 */ |
| 4200 LibraryElement exportedLibrary; |
| 4201 |
| 4202 /** |
| 4203 * The combinators that were specified as part of the export directive in the
order in which they |
| 4204 * were specified. |
| 4205 */ |
| 4206 List<NamespaceCombinator> combinators = NamespaceCombinator.EMPTY_ARRAY; |
| 4207 |
| 4208 /** |
| 4209 * Initialize a newly created export element. |
| 4210 */ |
| 4211 ExportElementImpl() : super(null, -1); |
| 4212 |
| 4213 @override |
| 4214 accept(ElementVisitor visitor) => visitor.visitExportElement(this); |
| 4215 |
| 4216 @override |
| 4217 ElementKind get kind => ElementKind.EXPORT; |
| 4218 |
| 4219 @override |
| 4220 void appendTo(JavaStringBuilder builder) { |
| 4221 builder.append("export "); |
| 4222 (exportedLibrary as LibraryElementImpl).appendTo(builder); |
| 4223 } |
| 4224 |
| 4225 @override |
| 4226 String get identifier => exportedLibrary.name; |
| 4227 } |
| 4228 |
| 4229 /** |
| 1071 * The interface `ExternalHtmlScriptElement` defines the behavior of elements re
presenting a | 4230 * The interface `ExternalHtmlScriptElement` defines the behavior of elements re
presenting a |
| 1072 * script tag in an HTML file having a `source` attribute that references a Dart
library | 4231 * script tag in an HTML file having a `source` attribute that references a Dart
library |
| 1073 * source file. | 4232 * source file. |
| 1074 */ | 4233 */ |
| 1075 abstract class ExternalHtmlScriptElement implements HtmlScriptElement { | 4234 abstract class ExternalHtmlScriptElement implements HtmlScriptElement { |
| 1076 /** | 4235 /** |
| 1077 * Return the source referenced by this element, or `null` if this element doe
s not | 4236 * Return the source referenced by this element, or `null` if this element doe
s not |
| 1078 * reference a Dart library source file. | 4237 * reference a Dart library source file. |
| 1079 * | 4238 * |
| 1080 * @return the source for the external Dart library | 4239 * @return the source for the external Dart library |
| 1081 */ | 4240 */ |
| 1082 Source get scriptSource; | 4241 Source get scriptSource; |
| 1083 } | 4242 } |
| 1084 | 4243 |
| 1085 /** | 4244 /** |
| 4245 * Instances of the class `ExternalHtmlScriptElementImpl` implement an |
| 4246 * [ExternalHtmlScriptElement]. |
| 4247 */ |
| 4248 class ExternalHtmlScriptElementImpl extends HtmlScriptElementImpl implements Ext
ernalHtmlScriptElement { |
| 4249 /** |
| 4250 * The source specified in the `source` attribute or `null` if unspecified. |
| 4251 */ |
| 4252 Source scriptSource; |
| 4253 |
| 4254 /** |
| 4255 * Initialize a newly created script element to have the specified tag name an
d offset. |
| 4256 * |
| 4257 * @param node the XML node from which this element is derived (not `null`) |
| 4258 */ |
| 4259 ExternalHtmlScriptElementImpl(XmlTagNode node) : super(node); |
| 4260 |
| 4261 @override |
| 4262 accept(ElementVisitor visitor) => visitor.visitExternalHtmlScriptElement(this)
; |
| 4263 |
| 4264 @override |
| 4265 ElementKind get kind => ElementKind.EXTERNAL_HTML_SCRIPT; |
| 4266 } |
| 4267 |
| 4268 /** |
| 1086 * The interface `FieldElement` defines the behavior of elements representing a
field defined | 4269 * The interface `FieldElement` defines the behavior of elements representing a
field defined |
| 1087 * within a type. | 4270 * within a type. |
| 1088 */ | 4271 */ |
| 1089 abstract class FieldElement implements ClassMemberElement, PropertyInducingEleme
nt { | 4272 abstract class FieldElement implements ClassMemberElement, PropertyInducingEleme
nt { |
| 1090 } | 4273 } |
| 1091 | 4274 |
| 1092 /** | 4275 /** |
| 4276 * Instances of the class `FieldElementImpl` implement a `FieldElement`. |
| 4277 */ |
| 4278 class FieldElementImpl extends PropertyInducingElementImpl implements FieldEleme
nt { |
| 4279 /** |
| 4280 * An empty array of field elements. |
| 4281 */ |
| 4282 static List<FieldElement> EMPTY_ARRAY = new List<FieldElement>(0); |
| 4283 |
| 4284 /** |
| 4285 * Initialize a newly created field element to have the given name. |
| 4286 * |
| 4287 * @param name the name of this element |
| 4288 */ |
| 4289 FieldElementImpl.con1(Identifier name) : super.con1(name); |
| 4290 |
| 4291 /** |
| 4292 * Initialize a newly created synthetic field element to have the given name. |
| 4293 * |
| 4294 * @param name the name of this element |
| 4295 */ |
| 4296 FieldElementImpl.con2(String name) : super.con2(name); |
| 4297 |
| 4298 @override |
| 4299 accept(ElementVisitor visitor) => visitor.visitFieldElement(this); |
| 4300 |
| 4301 @override |
| 4302 ClassElement get enclosingElement => super.enclosingElement as ClassElement; |
| 4303 |
| 4304 @override |
| 4305 ElementKind get kind => ElementKind.FIELD; |
| 4306 |
| 4307 @override |
| 4308 bool get isStatic => hasModifier(Modifier.STATIC); |
| 4309 |
| 4310 /** |
| 4311 * Set whether this field is static to correspond to the given value. |
| 4312 * |
| 4313 * @param isStatic `true` if the field is static |
| 4314 */ |
| 4315 void set static(bool isStatic) { |
| 4316 setModifier(Modifier.STATIC, isStatic); |
| 4317 } |
| 4318 } |
| 4319 |
| 4320 /** |
| 1093 * The interface `FieldFormalParameterElement` defines the behavior of elements
representing a | 4321 * The interface `FieldFormalParameterElement` defines the behavior of elements
representing a |
| 1094 * field formal parameter defined within a constructor element. | 4322 * field formal parameter defined within a constructor element. |
| 1095 */ | 4323 */ |
| 1096 abstract class FieldFormalParameterElement implements ParameterElement { | 4324 abstract class FieldFormalParameterElement implements ParameterElement { |
| 1097 /** | 4325 /** |
| 1098 * Return the field element associated with this field formal parameter, or `n
ull` if the | 4326 * Return the field element associated with this field formal parameter, or `n
ull` if the |
| 1099 * parameter references a field that doesn't exist. | 4327 * parameter references a field that doesn't exist. |
| 1100 * | 4328 * |
| 1101 * @return the field element associated with this field formal parameter | 4329 * @return the field element associated with this field formal parameter |
| 1102 */ | 4330 */ |
| 1103 FieldElement get field; | 4331 FieldElement get field; |
| 1104 } | 4332 } |
| 1105 | 4333 |
| 1106 /** | 4334 /** |
| 4335 * Instances of the class `FieldFormalParameterElementImpl` extend |
| 4336 * [ParameterElementImpl] to provide the additional information of the [FieldEle
ment] |
| 4337 * associated with the parameter. |
| 4338 */ |
| 4339 class FieldFormalParameterElementImpl extends ParameterElementImpl implements Fi
eldFormalParameterElement { |
| 4340 /** |
| 4341 * The field associated with this field formal parameter. |
| 4342 */ |
| 4343 FieldElement field; |
| 4344 |
| 4345 /** |
| 4346 * Initialize a newly created parameter element to have the given name. |
| 4347 * |
| 4348 * @param name the name of this element |
| 4349 */ |
| 4350 FieldFormalParameterElementImpl(Identifier name) : super.con1(name); |
| 4351 |
| 4352 @override |
| 4353 accept(ElementVisitor visitor) => visitor.visitFieldFormalParameterElement(thi
s); |
| 4354 |
| 4355 @override |
| 4356 bool get isInitializingFormal => true; |
| 4357 } |
| 4358 |
| 4359 /** |
| 4360 * Instances of the class `FieldFormalParameterMember` represent a parameter ele
ment defined |
| 4361 * in a parameterized type where the values of the type parameters are known. |
| 4362 */ |
| 4363 class FieldFormalParameterMember extends ParameterMember implements FieldFormalP
arameterElement { |
| 4364 /** |
| 4365 * Initialize a newly created element to represent a parameter of the given pa
rameterized type. |
| 4366 * |
| 4367 * @param baseElement the element on which the parameterized element was creat
ed |
| 4368 * @param definingType the type in which the element is defined |
| 4369 */ |
| 4370 FieldFormalParameterMember(FieldFormalParameterElement baseElement, Parameteri
zedType definingType) : super(baseElement, definingType); |
| 4371 |
| 4372 @override |
| 4373 accept(ElementVisitor visitor) => visitor.visitFieldFormalParameterElement(thi
s); |
| 4374 |
| 4375 @override |
| 4376 FieldElement get field => (baseElement as FieldFormalParameterElement).field; |
| 4377 } |
| 4378 |
| 4379 /** |
| 4380 * Instances of the class `FieldMember` represent a field element defined in a p
arameterized |
| 4381 * type where the values of the type parameters are known. |
| 4382 */ |
| 4383 class FieldMember extends VariableMember implements FieldElement { |
| 4384 /** |
| 4385 * If the given field's type is different when any type parameters from the de
fining type's |
| 4386 * declaration are replaced with the actual type arguments from the defining t
ype, create a field |
| 4387 * member representing the given field. Return the member that was created, or
the base field if |
| 4388 * no member was created. |
| 4389 * |
| 4390 * @param baseField the base field for which a member might be created |
| 4391 * @param definingType the type defining the parameters and arguments to be us
ed in the |
| 4392 * substitution |
| 4393 * @return the field element that will return the correctly substituted types |
| 4394 */ |
| 4395 static FieldElement from(FieldElement baseField, InterfaceType definingType) { |
| 4396 if (baseField == null || definingType.typeArguments.length == 0) { |
| 4397 return baseField; |
| 4398 } |
| 4399 DartType baseType = baseField.type; |
| 4400 if (baseType == null) { |
| 4401 return baseField; |
| 4402 } |
| 4403 List<DartType> argumentTypes = definingType.typeArguments; |
| 4404 List<DartType> parameterTypes = definingType.element.type.typeArguments; |
| 4405 DartType substitutedType = baseType.substitute2(argumentTypes, parameterType
s); |
| 4406 if (baseType == substitutedType) { |
| 4407 return baseField; |
| 4408 } |
| 4409 // TODO(brianwilkerson) Consider caching the substituted type in the instanc
e. It would use more |
| 4410 // memory but speed up some operations. We need to see how often the type is
being re-computed. |
| 4411 return new FieldMember(baseField, definingType); |
| 4412 } |
| 4413 |
| 4414 /** |
| 4415 * Initialize a newly created element to represent a field of the given parame
terized type. |
| 4416 * |
| 4417 * @param baseElement the element on which the parameterized element was creat
ed |
| 4418 * @param definingType the type in which the element is defined |
| 4419 */ |
| 4420 FieldMember(FieldElement baseElement, InterfaceType definingType) : super(base
Element, definingType); |
| 4421 |
| 4422 @override |
| 4423 accept(ElementVisitor visitor) => visitor.visitFieldElement(this); |
| 4424 |
| 4425 @override |
| 4426 FieldElement get baseElement => super.baseElement as FieldElement; |
| 4427 |
| 4428 @override |
| 4429 ClassElement get enclosingElement => baseElement.enclosingElement; |
| 4430 |
| 4431 @override |
| 4432 PropertyAccessorElement get getter => PropertyAccessorMember.from(baseElement.
getter, definingType); |
| 4433 |
| 4434 @override |
| 4435 PropertyAccessorElement get setter => PropertyAccessorMember.from(baseElement.
setter, definingType); |
| 4436 |
| 4437 @override |
| 4438 bool get isStatic => baseElement.isStatic; |
| 4439 |
| 4440 @override |
| 4441 InterfaceType get definingType => super.definingType as InterfaceType; |
| 4442 } |
| 4443 |
| 4444 /** |
| 1107 * The interface `FunctionElement` defines the behavior of elements representing
a function. | 4445 * The interface `FunctionElement` defines the behavior of elements representing
a function. |
| 1108 */ | 4446 */ |
| 1109 abstract class FunctionElement implements ExecutableElement, LocalElement { | 4447 abstract class FunctionElement implements ExecutableElement, LocalElement { |
| 1110 /** | 4448 /** |
| 1111 * The name of the synthetic function defined for libraries that are deferred. | 4449 * The name of the synthetic function defined for libraries that are deferred. |
| 1112 */ | 4450 */ |
| 1113 static final String LOAD_LIBRARY_NAME = "loadLibrary"; | 4451 static final String LOAD_LIBRARY_NAME = "loadLibrary"; |
| 1114 | 4452 |
| 1115 /** | 4453 /** |
| 1116 * Return the resolved [FunctionDeclaration] node that declares this [Function
Element] | 4454 * Return the resolved [FunctionDeclaration] node that declares this [Function
Element] |
| 1117 * . | 4455 * . |
| 1118 * | 4456 * |
| 1119 * This method is expensive, because resolved AST might be evicted from cache,
so parsing and | 4457 * This method is expensive, because resolved AST might be evicted from cache,
so parsing and |
| 1120 * resolving will be performed. | 4458 * resolving will be performed. |
| 1121 * | 4459 * |
| 1122 * @return the resolved [FunctionDeclaration], not `null`. | 4460 * @return the resolved [FunctionDeclaration], not `null`. |
| 1123 */ | 4461 */ |
| 1124 @override | 4462 @override |
| 1125 FunctionDeclaration get node; | 4463 FunctionDeclaration get node; |
| 1126 } | 4464 } |
| 1127 | 4465 |
| 1128 /** | 4466 /** |
| 4467 * Instances of the class `FunctionElementImpl` implement a `FunctionElement`. |
| 4468 */ |
| 4469 class FunctionElementImpl extends ExecutableElementImpl implements FunctionEleme
nt { |
| 4470 /** |
| 4471 * The offset to the beginning of the visible range for this element. |
| 4472 */ |
| 4473 int _visibleRangeOffset = 0; |
| 4474 |
| 4475 /** |
| 4476 * The length of the visible range for this element, or `-1` if this element d
oes not have a |
| 4477 * visible range. |
| 4478 */ |
| 4479 int _visibleRangeLength = -1; |
| 4480 |
| 4481 /** |
| 4482 * An empty array of function elements. |
| 4483 */ |
| 4484 static List<FunctionElement> EMPTY_ARRAY = new List<FunctionElement>(0); |
| 4485 |
| 4486 /** |
| 4487 * Initialize a newly created function element to have the given name. |
| 4488 * |
| 4489 * @param name the name of this element |
| 4490 */ |
| 4491 FunctionElementImpl.forNode(Identifier name) : super.forNode(name); |
| 4492 |
| 4493 /** |
| 4494 * Initialize a newly created function element to have no name and the given o
ffset. This is used |
| 4495 * for function expressions, which have no name. |
| 4496 * |
| 4497 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 4498 * declaration of this element |
| 4499 */ |
| 4500 FunctionElementImpl.forOffset(int nameOffset) : super("", nameOffset); |
| 4501 |
| 4502 /** |
| 4503 * Initialize a newly created function element to have the given name and offs
et. |
| 4504 * |
| 4505 * @param name the name of this element |
| 4506 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 4507 * declaration of this element |
| 4508 */ |
| 4509 FunctionElementImpl(String name, int nameOffset) : super(name, nameOffset); |
| 4510 |
| 4511 @override |
| 4512 accept(ElementVisitor visitor) => visitor.visitFunctionElement(this); |
| 4513 |
| 4514 @override |
| 4515 ElementKind get kind => ElementKind.FUNCTION; |
| 4516 |
| 4517 @override |
| 4518 FunctionDeclaration get node => getNodeMatching((node) => node is FunctionDecl
aration); |
| 4519 |
| 4520 @override |
| 4521 SourceRange get visibleRange { |
| 4522 if (_visibleRangeLength < 0) { |
| 4523 return null; |
| 4524 } |
| 4525 return new SourceRange(_visibleRangeOffset, _visibleRangeLength); |
| 4526 } |
| 4527 |
| 4528 @override |
| 4529 bool get isStatic => enclosingElement is CompilationUnitElement; |
| 4530 |
| 4531 /** |
| 4532 * Set the visible range for this element to the range starting at the given o
ffset with the given |
| 4533 * length. |
| 4534 * |
| 4535 * @param offset the offset to the beginning of the visible range for this ele
ment |
| 4536 * @param length the length of the visible range for this element, or `-1` if
this element |
| 4537 * does not have a visible range |
| 4538 */ |
| 4539 void setVisibleRange(int offset, int length) { |
| 4540 _visibleRangeOffset = offset; |
| 4541 _visibleRangeLength = length; |
| 4542 } |
| 4543 |
| 4544 @override |
| 4545 void appendTo(JavaStringBuilder builder) { |
| 4546 String name = displayName; |
| 4547 if (name != null) { |
| 4548 builder.append(name); |
| 4549 } |
| 4550 super.appendTo(builder); |
| 4551 } |
| 4552 |
| 4553 @override |
| 4554 String get identifier => "${name}@${nameOffset}"; |
| 4555 } |
| 4556 |
| 4557 /** |
| 4558 * The interface `FunctionType` defines the behavior common to objects represent
ing the type |
| 4559 * of a function, method, constructor, getter, or setter. Function types come in
three variations: |
| 4560 * <ol> |
| 4561 * * The types of functions that only have required parameters. These have the g
eneral form |
| 4562 * <i>(T<sub>1</sub>, …, T<sub>n</sub>) → T</i>. |
| 4563 * * The types of functions with optional positional parameters. These have the
general form |
| 4564 * <i>(T<sub>1</sub>, …, T<sub>n</sub>, [T<sub>n+1</sub>, …, T<sub
>n+k</sub>]) → |
| 4565 * T</i>. |
| 4566 * * The types of functions with named parameters. These have the general form <
i>(T<sub>1</sub>, |
| 4567 * …, T<sub>n</sub>, {T<sub>x1</sub> x1, …, T<sub>xk</sub> xk}) &r
arr; T</i>. |
| 4568 * </ol> |
| 4569 */ |
| 4570 abstract class FunctionType implements ParameterizedType { |
| 4571 /** |
| 4572 * Return a map from the names of named parameters to the types of the named p
arameters of this |
| 4573 * type of function. The entries in the map will be iterated in the same order
as the order in |
| 4574 * which the named parameters were defined. If there were no named parameters
declared then the |
| 4575 * map will be empty. |
| 4576 * |
| 4577 * @return a map from the name to the types of the named parameters of this ty
pe of function |
| 4578 */ |
| 4579 Map<String, DartType> get namedParameterTypes; |
| 4580 |
| 4581 /** |
| 4582 * Return an array containing the types of the normal parameters of this type
of function. The |
| 4583 * parameter types are in the same order as they appear in the declaration of
the function. |
| 4584 * |
| 4585 * @return the types of the normal parameters of this type of function |
| 4586 */ |
| 4587 List<DartType> get normalParameterTypes; |
| 4588 |
| 4589 /** |
| 4590 * Return a map from the names of optional (positional) parameters to the type
s of the optional |
| 4591 * parameters of this type of function. The entries in the map will be iterate
d in the same order |
| 4592 * as the order in which the optional parameters were defined. If there were n
o optional |
| 4593 * parameters declared then the map will be empty. |
| 4594 * |
| 4595 * @return a map from the name to the types of the optional parameters of this
type of function |
| 4596 */ |
| 4597 List<DartType> get optionalParameterTypes; |
| 4598 |
| 4599 /** |
| 4600 * Return an array containing the parameters elements of this type of function
. The parameter |
| 4601 * types are in the same order as they appear in the declaration of the functi
on. |
| 4602 * |
| 4603 * @return the parameters elements of this type of function |
| 4604 */ |
| 4605 List<ParameterElement> get parameters; |
| 4606 |
| 4607 /** |
| 4608 * Return the type of object returned by this type of function. |
| 4609 * |
| 4610 * @return the type of object returned by this type of function |
| 4611 */ |
| 4612 DartType get returnType; |
| 4613 |
| 4614 /** |
| 4615 * Return `true` if this type is a subtype of the given type. |
| 4616 * |
| 4617 * A function type <i>(T<sub>1</sub>, …, T<sub>n</sub>) → T</i> is
a subtype of the |
| 4618 * function type <i>(S<sub>1</sub>, …, S<sub>n</sub>) → S</i>, if
all of the following |
| 4619 * conditions are met: |
| 4620 * * Either |
| 4621 * * <i>S</i> is void, or |
| 4622 * * <i>T ⇔ S</i>. |
| 4623 * |
| 4624 * * For all <i>i</i>, 1 <= <i>i</i> <= <i>n</i>, <i>T<sub>i</sub> ⇔ S<su
b>i</sub></i>. |
| 4625 * A function type <i>(T<sub>1</sub>, …, T<sub>n</sub>, [T<sub>n+1</sub
>, …, |
| 4626 * T<sub>n+k</sub>]) → T</i> is a subtype of the function type <i>(S<sub>
1</sub>, …, |
| 4627 * S<sub>n</sub>, [S<sub>n+1</sub>, …, S<sub>n+m</sub>]) → S</i>,
if all of the |
| 4628 * following conditions are met: |
| 4629 * * Either |
| 4630 * * <i>S</i> is void, or |
| 4631 * * <i>T ⇔ S</i>. |
| 4632 * |
| 4633 * * <i>k</i> >= <i>m</i> and for all <i>i</i>, 1 <= <i>i</i> <= <i>n+m</i>, <
i>T<sub>i</sub> |
| 4634 * ⇔ S<sub>i</sub></i>. |
| 4635 * A function type <i>(T<sub>1</sub>, …, T<sub>n</sub>, {T<sub>x1</sub>
x1, …, |
| 4636 * T<sub>xk</sub> xk}) → T</i> is a subtype of the function type <i>(S<su
b>1</sub>, …, |
| 4637 * S<sub>n</sub>, {S<sub>y1</sub> y1, …, S<sub>ym</sub> ym}) → S</
i>, if all of the |
| 4638 * following conditions are met: |
| 4639 * * Either |
| 4640 * * <i>S</i> is void, |
| 4641 * * or <i>T ⇔ S</i>. |
| 4642 * |
| 4643 * * For all <i>i</i>, 1 <= <i>i</i> <= <i>n</i>, <i>T<sub>i</sub> ⇔ S<su
b>i</sub></i>. |
| 4644 * * <i>k</i> >= <i>m</i> and <i>y<sub>i</sub></i> in <i>{x<sub>1</sub>, &hell
ip;, |
| 4645 * x<sub>k</sub>}</i>, 1 <= <i>i</i> <= <i>m</i>. |
| 4646 * * For all <i>y<sub>i</sub></i> in <i>{y<sub>1</sub>, …, y<sub>m</sub
>}</i>, |
| 4647 * <i>y<sub>i</sub> = x<sub>j</sub> => Tj ⇔ Si</i>. |
| 4648 * In addition, the following subtype rules apply: |
| 4649 * |
| 4650 * <i>(T<sub>1</sub>, …, T<sub>n</sub>, []) → T <: (T<sub>1</sub>,
…, |
| 4651 * T<sub>n</sub>) → T.</i><br> |
| 4652 * <i>(T<sub>1</sub>, …, T<sub>n</sub>) → T <: (T<sub>1</sub>, &he
llip;, |
| 4653 * T<sub>n</sub>, {}) → T.</i><br> |
| 4654 * <i>(T<sub>1</sub>, …, T<sub>n</sub>, {}) → T <: (T<sub>1</sub>,
…, |
| 4655 * T<sub>n</sub>) → T.</i><br> |
| 4656 * <i>(T<sub>1</sub>, …, T<sub>n</sub>) → T <: (T<sub>1</sub>, &he
llip;, |
| 4657 * T<sub>n</sub>, []) → T.</i> |
| 4658 * |
| 4659 * All functions implement the class `Function`. However not all function type
s are a |
| 4660 * subtype of `Function`. If an interface type <i>I</i> includes a method name
d |
| 4661 * `call()`, and the type of `call()` is the function type <i>F</i>, then <i>I
</i> is |
| 4662 * considered to be a subtype of <i>F</i>. |
| 4663 * |
| 4664 * @param type the type being compared with this type |
| 4665 * @return `true` if this type is a subtype of the given type |
| 4666 */ |
| 4667 @override |
| 4668 bool isSubtypeOf(DartType type); |
| 4669 |
| 4670 /** |
| 4671 * Return the type resulting from substituting the given arguments for this ty
pe's parameters. |
| 4672 * This is fully equivalent to `substitute(argumentTypes, getTypeArguments())`
. |
| 4673 * |
| 4674 * @param argumentTypes the actual type arguments being substituted for the ty
pe parameters |
| 4675 * @return the result of performing the substitution |
| 4676 */ |
| 4677 FunctionType substitute3(List<DartType> argumentTypes); |
| 4678 |
| 4679 @override |
| 4680 FunctionType substitute2(List<DartType> argumentTypes, List<DartType> paramete
rTypes); |
| 4681 } |
| 4682 |
| 4683 /** |
| 1129 * The interface `FunctionTypeAliasElement` defines the behavior of elements rep
resenting a | 4684 * The interface `FunctionTypeAliasElement` defines the behavior of elements rep
resenting a |
| 1130 * function type alias (`typedef`). | 4685 * function type alias (`typedef`). |
| 1131 */ | 4686 */ |
| 1132 abstract class FunctionTypeAliasElement implements Element { | 4687 abstract class FunctionTypeAliasElement implements Element { |
| 1133 /** | 4688 /** |
| 1134 * Return the compilation unit in which this type alias is defined. | 4689 * Return the compilation unit in which this type alias is defined. |
| 1135 * | 4690 * |
| 1136 * @return the compilation unit in which this type alias is defined | 4691 * @return the compilation unit in which this type alias is defined |
| 1137 */ | 4692 */ |
| 1138 @override | 4693 @override |
| (...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1173 | 4728 |
| 1174 /** | 4729 /** |
| 1175 * Return an array containing all of the type parameters defined for this type
. | 4730 * Return an array containing all of the type parameters defined for this type
. |
| 1176 * | 4731 * |
| 1177 * @return the type parameters defined for this type | 4732 * @return the type parameters defined for this type |
| 1178 */ | 4733 */ |
| 1179 List<TypeParameterElement> get typeParameters; | 4734 List<TypeParameterElement> get typeParameters; |
| 1180 } | 4735 } |
| 1181 | 4736 |
| 1182 /** | 4737 /** |
| 1183 * The interface `HideElementCombinator` defines the behavior of combinators tha
t cause some | 4738 * Instances of the class `FunctionTypeAliasElementImpl` implement a |
| 1184 * of the names in a namespace to be hidden when being imported. | 4739 * `FunctionTypeAliasElement`. |
| 1185 */ | 4740 */ |
| 1186 abstract class HideElementCombinator implements NamespaceCombinator { | 4741 class FunctionTypeAliasElementImpl extends ElementImpl implements FunctionTypeAl
iasElement { |
| 1187 /** | 4742 /** |
| 1188 * Return an array containing the names that are not to be made visible in the
importing library | 4743 * An array containing all of the parameters defined by this type alias. |
| 1189 * even if they are defined in the imported library. | 4744 */ |
| 1190 * | 4745 List<ParameterElement> _parameters = ParameterElementImpl.EMPTY_ARRAY; |
| 1191 * @return the names from the imported library that are hidden from the import
ing library | 4746 |
| 1192 */ | 4747 /** |
| 1193 List<String> get hiddenNames; | 4748 * The return type defined by this type alias. |
| 1194 } | 4749 */ |
| 1195 | 4750 DartType returnType; |
| 1196 /** | 4751 |
| 1197 * The interface `HtmlElement` defines the behavior of elements representing an
HTML file. | 4752 /** |
| 1198 */ | 4753 * The type of function defined by this type alias. |
| 1199 abstract class HtmlElement implements Element { | 4754 */ |
| 1200 /** | 4755 FunctionType type; |
| 1201 * Return the [CompilationUnitElement] associated with this Angular HTML file,
maybe | 4756 |
| 1202 * `null` if not an Angular file. | 4757 /** |
| 1203 */ | 4758 * An array containing all of the type parameters defined for this type. |
| 1204 CompilationUnitElement get angularCompilationUnit; | 4759 */ |
| 1205 | 4760 List<TypeParameterElement> _typeParameters = TypeParameterElementImpl.EMPTY_AR
RAY; |
| 1206 /** | 4761 |
| 1207 * Return an array containing all of the [PolymerTagHtmlElement]s defined in t
he HTML file. | 4762 /** |
| 1208 * | 4763 * An empty array of type alias elements. |
| 1209 * @return the [PolymerTagHtmlElement]s elements in the HTML file (not `null`, | 4764 */ |
| 1210 * contains no `null`s) | 4765 static List<FunctionTypeAliasElement> EMPTY_ARRAY = new List<FunctionTypeAlias
Element>(0); |
| 1211 */ | 4766 |
| 1212 List<PolymerTagHtmlElement> get polymerTags; | 4767 /** |
| 1213 | 4768 * Initialize a newly created type alias element to have the given name. |
| 1214 /** | 4769 * |
| 1215 * Return an array containing all of the script elements contained in the HTML
file. This includes | 4770 * @param name the name of this element |
| 1216 * scripts with libraries that are defined by the content of a script tag as w
ell as libraries | 4771 */ |
| 1217 * that are referenced in the {@core source} attribute of a script tag. | 4772 FunctionTypeAliasElementImpl(Identifier name) : super.forNode(name); |
| 1218 * | 4773 |
| 1219 * @return the script elements in the HTML file (not `null`, contains no `null
`s) | 4774 @override |
| 1220 */ | 4775 accept(ElementVisitor visitor) => visitor.visitFunctionTypeAliasElement(this); |
| 1221 List<HtmlScriptElement> get scripts; | 4776 |
| 1222 } | 4777 @override |
| 1223 | 4778 ElementImpl getChild(String identifier) { |
| 1224 /** | 4779 for (VariableElement parameter in _parameters) { |
| 1225 * The interface `HtmlScriptElement` defines the behavior of elements representi
ng a script | 4780 if ((parameter as VariableElementImpl).identifier == identifier) { |
| 1226 * tag in an HTML file. | 4781 return parameter as VariableElementImpl; |
| 1227 * | 4782 } |
| 1228 * @see EmbeddedHtmlScriptElement | 4783 } |
| 1229 * @see ExternalHtmlScriptElement | 4784 for (TypeParameterElement typeParameter in _typeParameters) { |
| 1230 */ | 4785 if ((typeParameter as TypeParameterElementImpl).identifier == identifier)
{ |
| 1231 abstract class HtmlScriptElement implements Element { | 4786 return typeParameter as TypeParameterElementImpl; |
| 1232 } | 4787 } |
| 1233 | 4788 } |
| 1234 /** | 4789 return null; |
| 1235 * The interface `ImportElement` defines the behavior of objects representing in
formation | 4790 } |
| 1236 * about a single import directive within a library. | 4791 |
| 1237 */ | 4792 @override |
| 1238 abstract class ImportElement implements Element, UriReferencedElement { | 4793 CompilationUnitElement get enclosingElement => super.enclosingElement as Compi
lationUnitElement; |
| 1239 /** | 4794 |
| 1240 * An empty array of import elements. | 4795 @override |
| 1241 */ | 4796 ElementKind get kind => ElementKind.FUNCTION_TYPE_ALIAS; |
| 1242 static final List<ImportElement> EMPTY_ARRAY = new List<ImportElement>(0); | 4797 |
| 1243 | 4798 @override |
| 1244 /** | 4799 FunctionTypeAlias get node => getNodeMatching((node) => node is FunctionTypeAl
ias); |
| 1245 * Return an array containing the combinators that were specified as part of t
he import directive | 4800 |
| 1246 * in the order in which they were specified. | 4801 @override |
| 1247 * | 4802 List<ParameterElement> get parameters => _parameters; |
| 1248 * @return the combinators specified in the import directive | 4803 |
| 1249 */ | 4804 @override |
| 1250 List<NamespaceCombinator> get combinators; | 4805 List<TypeParameterElement> get typeParameters => _typeParameters; |
| 1251 | 4806 |
| 1252 /** | 4807 /** |
| 1253 * Return the library that is imported into this library by this import direct
ive. | 4808 * Set the parameters defined by this type alias to the given parameters. |
| 1254 * | 4809 * |
| 1255 * @return the library that is imported into this library | 4810 * @param parameters the parameters defined by this type alias |
| 1256 */ | 4811 */ |
| 1257 LibraryElement get importedLibrary; | 4812 void set parameters(List<ParameterElement> parameters) { |
| 1258 | 4813 if (parameters != null) { |
| 1259 /** | 4814 for (ParameterElement parameter in parameters) { |
| 1260 * Return the prefix that was specified as part of the import directive, or `n
ull` if there | 4815 (parameter as ParameterElementImpl).enclosingElement = this; |
| 1261 * was no prefix specified. | 4816 } |
| 1262 * | 4817 } |
| 1263 * @return the prefix that was specified as part of the import directive | 4818 this._parameters = parameters; |
| 1264 */ | 4819 } |
| 1265 PrefixElement get prefix; | 4820 |
| 1266 | 4821 /** |
| 1267 /** | 4822 * Set the type parameters defined for this type to the given parameters. |
| 1268 * Return the offset of the prefix of this import in the file that contains th
is import directive, | 4823 * |
| 1269 * or `-1` if this import is synthetic, does not have a prefix, or otherwise d
oes not have | 4824 * @param typeParameters the type parameters defined for this type |
| 1270 * an offset. | 4825 */ |
| 1271 * | 4826 void set typeParameters(List<TypeParameterElement> typeParameters) { |
| 1272 * @return the offset of the prefix of this import | 4827 for (TypeParameterElement typeParameter in typeParameters) { |
| 1273 */ | 4828 (typeParameter as TypeParameterElementImpl).enclosingElement = this; |
| 1274 int get prefixOffset; | 4829 } |
| 1275 | 4830 this._typeParameters = typeParameters; |
| 1276 /** | 4831 } |
| 1277 * Return `true` if this import is for a deferred library. | 4832 |
| 1278 * | 4833 /** |
| 1279 * @return `true` if this import is for a deferred library | 4834 * Set the parameters defined by this type alias to the given parameters witho
ut becoming the |
| 1280 */ | 4835 * parent of the parameters. This should only be used by the [TypeResolverVisi
tor] when |
| 1281 bool get isDeferred; | 4836 * creating a synthetic type alias. |
| 1282 } | 4837 * |
| 1283 | 4838 * @param parameters the parameters defined by this type alias |
| 1284 /** | 4839 */ |
| 1285 * The interface `LabelElement` defines the behavior of elements representing a
label | 4840 void shareParameters(List<ParameterElement> parameters) { |
| 1286 * associated with a statement. | 4841 this._parameters = parameters; |
| 1287 */ | 4842 } |
| 1288 abstract class LabelElement implements Element { | 4843 |
| 1289 /** | 4844 /** |
| 1290 * Return the executable element in which this label is defined. | 4845 * Set the type parameters defined for this type to the given parameters witho
ut becoming the |
| 1291 * | 4846 * parent of the parameters. This should only be used by the [TypeResolverVisi
tor] when |
| 1292 * @return the executable element in which this label is defined | 4847 * creating a synthetic type alias. |
| 1293 */ | 4848 * |
| 1294 @override | 4849 * @param typeParameters the type parameters defined for this type |
| 1295 ExecutableElement get enclosingElement; | 4850 */ |
| 1296 } | 4851 void shareTypeParameters(List<TypeParameterElement> typeParameters) { |
| 1297 | 4852 this._typeParameters = typeParameters; |
| 1298 /** | 4853 } |
| 1299 * The interface `LibraryElement` defines the behavior of elements representing
a library. | 4854 |
| 1300 */ | 4855 @override |
| 1301 abstract class LibraryElement implements Element { | 4856 void visitChildren(ElementVisitor visitor) { |
| 1302 /** | 4857 super.visitChildren(visitor); |
| 1303 * Return the compilation unit that defines this library. | 4858 safelyVisitChildren(_parameters, visitor); |
| 1304 * | 4859 safelyVisitChildren(_typeParameters, visitor); |
| 1305 * @return the compilation unit that defines this library | 4860 } |
| 1306 */ | 4861 |
| 1307 CompilationUnitElement get definingCompilationUnit; | 4862 @override |
| 1308 | 4863 void appendTo(JavaStringBuilder builder) { |
| 1309 /** | 4864 builder.append("typedef "); |
| 1310 * Return the entry point for this library, or `null` if this library does not
have an entry | 4865 builder.append(displayName); |
| 1311 * point. The entry point is defined to be a zero argument top-level function
whose name is | 4866 int typeParameterCount = _typeParameters.length; |
| 1312 * `main`. | 4867 if (typeParameterCount > 0) { |
| 1313 * | 4868 builder.append("<"); |
| 1314 * @return the entry point for this library | 4869 for (int i = 0; i < typeParameterCount; i++) { |
| 1315 */ | 4870 if (i > 0) { |
| 1316 FunctionElement get entryPoint; | 4871 builder.append(", "); |
| 1317 | 4872 } |
| 1318 /** | 4873 (_typeParameters[i] as TypeParameterElementImpl).appendTo(builder); |
| 1319 * Return an array containing all of the libraries that are exported from this
library. | 4874 } |
| 1320 * | 4875 builder.append(">"); |
| 1321 * @return an array containing all of the libraries that are exported from thi
s library | 4876 } |
| 1322 */ | 4877 builder.append("("); |
| 1323 List<LibraryElement> get exportedLibraries; | 4878 int parameterCount = _parameters.length; |
| 1324 | 4879 for (int i = 0; i < parameterCount; i++) { |
| 1325 /** | 4880 if (i > 0) { |
| 1326 * Return an array containing all of the exports defined in this library. | 4881 builder.append(", "); |
| 1327 * | 4882 } |
| 1328 * @return the exports defined in this library | 4883 (_parameters[i] as ParameterElementImpl).appendTo(builder); |
| 1329 */ | 4884 } |
| 1330 List<ExportElement> get exports; | 4885 builder.append(")"); |
| 1331 | 4886 if (type != null) { |
| 1332 /** | 4887 builder.append(Element.RIGHT_ARROW); |
| 1333 * Return an array containing all of the libraries that are imported into this
library. This | 4888 builder.append(type.returnType); |
| 1334 * includes all of the libraries that are imported using a prefix (also availa
ble through the | 4889 } |
| 1335 * prefixes returned by [getPrefixes]) and those that are imported without a p
refix. | 4890 } |
| 1336 * | 4891 } |
| 1337 * @return an array containing all of the libraries that are imported into thi
s library | 4892 |
| 1338 */ | 4893 /** |
| 1339 List<LibraryElement> get importedLibraries; | 4894 * Instances of the class `FunctionTypeImpl` defines the behavior common to obje
cts |
| 1340 | 4895 * representing the type of a function, method, constructor, getter, or setter. |
| 1341 /** | 4896 */ |
| 1342 * Return an array containing all of the imports defined in this library. | 4897 class FunctionTypeImpl extends TypeImpl implements FunctionType { |
| 1343 * | 4898 /** |
| 1344 * @return the imports defined in this library | 4899 * Return `true` if all of the name/type pairs in the first map are equal to t
he |
| 1345 */ | 4900 * corresponding name/type pairs in the second map. The maps are expected to i
terate over their |
| 1346 List<ImportElement> get imports; | 4901 * entries in the same order in which those entries were added to the map. |
| 1347 | 4902 * |
| 1348 /** | 4903 * @param firstTypes the first map of name/type pairs being compared |
| 1349 * Return an array containing all of the imports that share the given prefix,
or an empty array if | 4904 * @param secondTypes the second map of name/type pairs being compared |
| 1350 * there are no such imports. | 4905 * @param visitedElementPairs a set of visited element pairs |
| 1351 * | 4906 * @return `true` if all of the name/type pairs in the first map are equal to
the |
| 1352 * @param prefixElement the prefix element shared by the returned imports | 4907 * corresponding name/type pairs in the second map |
| 1353 */ | 4908 */ |
| 1354 List<ImportElement> getImportsWithPrefix(PrefixElement prefixElement); | 4909 static bool _equals(Map<String, DartType> firstTypes, Map<String, DartType> se
condTypes, Set<ElementPair> visitedElementPairs) { |
| 1355 | 4910 if (secondTypes.length != firstTypes.length) { |
| 1356 /** | 4911 return false; |
| 1357 * Return the element representing the synthetic function `loadLibrary` that i
s implicitly | 4912 } |
| 1358 * defined for this library if the library is imported using a deferred import
. | 4913 JavaIterator<MapEntry<String, DartType>> firstIterator = new JavaIterator(ge
tMapEntrySet(firstTypes)); |
| 1359 */ | 4914 JavaIterator<MapEntry<String, DartType>> secondIterator = new JavaIterator(g
etMapEntrySet(secondTypes)); |
| 1360 FunctionElement get loadLibraryFunction; | 4915 while (firstIterator.hasNext) { |
| 1361 | 4916 MapEntry<String, DartType> firstEntry = firstIterator.next(); |
| 1362 /** | 4917 MapEntry<String, DartType> secondEntry = secondIterator.next(); |
| 1363 * Return an array containing all of the compilation units that are included i
n this library using | 4918 if (firstEntry.getKey() != secondEntry.getKey() || !(firstEntry.getValue()
as TypeImpl).internalEquals(secondEntry.getValue(), visitedElementPairs)) { |
| 1364 * a `part` directive. This does not include the defining compilation unit tha
t contains the | 4919 return false; |
| 1365 * `part` directives. | 4920 } |
| 1366 * | 4921 } |
| 1367 * @return the compilation units that are included in this library | 4922 return true; |
| 1368 */ | 4923 } |
| 1369 List<CompilationUnitElement> get parts; | 4924 |
| 1370 | 4925 /** |
| 1371 /** | 4926 * An array containing the actual types of the type arguments. |
| 1372 * Return an array containing elements for each of the prefixes used to `impor
t` libraries | 4927 */ |
| 1373 * into this library. Each prefix can be used in more than one `import` direct
ive. | 4928 List<DartType> typeArguments = TypeImpl.EMPTY_ARRAY; |
| 1374 * | 4929 |
| 1375 * @return the prefixes used to `import` libraries into this library | 4930 /** |
| 1376 */ | 4931 * Initialize a newly created function type to be declared by the given elemen
t and to have the |
| 1377 List<PrefixElement> get prefixes; | 4932 * given name. |
| 1378 | 4933 * |
| 1379 /** | 4934 * @param element the element representing the declaration of the function typ
e |
| 1380 * Return the class defined in this library that has the given name, or `null`
if this | 4935 */ |
| 1381 * library does not define a class with the given name. | 4936 FunctionTypeImpl.con1(ExecutableElement element) : super(element, element == n
ull ? null : element.name); |
| 1382 * | 4937 |
| 1383 * @param className the name of the class to be returned | 4938 /** |
| 1384 * @return the class with the given name that is defined in this library | 4939 * Initialize a newly created function type to be declared by the given elemen
t and to have the |
| 1385 */ | 4940 * given name. |
| 1386 ClassElement getType(String className); | 4941 * |
| 1387 | 4942 * @param element the element representing the declaration of the function typ
e |
| 1388 /** | 4943 */ |
| 1389 * Return an array containing all of the compilation units this library consis
ts of. This includes | 4944 FunctionTypeImpl.con2(FunctionTypeAliasElement element) : super(element, eleme
nt == null ? null : element.name); |
| 1390 * the defining compilation unit and units included using the `part` directive
. | 4945 |
| 1391 * | 4946 @override |
| 1392 * @return the compilation units this library consists of | 4947 bool operator ==(Object object) => internalEquals(object, new Set<ElementPair>
()); |
| 1393 */ | 4948 |
| 1394 List<CompilationUnitElement> get units; | 4949 @override |
| 1395 | 4950 String get displayName { |
| 1396 /** | 4951 String name = this.name; |
| 1397 * Return an array containing all directly and indirectly imported libraries. | 4952 if (name == null || name.length == 0) { |
| 1398 * | 4953 // TODO(brianwilkerson) Determine whether function types should ever have
an empty name. |
| 1399 * @return all directly and indirectly imported libraries | 4954 List<DartType> normalParameterTypes = this.normalParameterTypes; |
| 1400 */ | 4955 List<DartType> optionalParameterTypes = this.optionalParameterTypes; |
| 1401 List<LibraryElement> get visibleLibraries; | 4956 Map<String, DartType> namedParameterTypes = this.namedParameterTypes; |
| 1402 | 4957 DartType returnType = this.returnType; |
| 1403 /** | 4958 JavaStringBuilder builder = new JavaStringBuilder(); |
| 1404 * Return `true` if the defining compilation unit of this library contains at
least one | 4959 builder.append("("); |
| 1405 * import directive whose URI uses the "dart-ext" scheme. | 4960 bool needsComma = false; |
| 1406 */ | 4961 if (normalParameterTypes.length > 0) { |
| 1407 bool get hasExtUri; | 4962 for (DartType type in normalParameterTypes) { |
| 1408 | 4963 if (needsComma) { |
| 1409 /** | 4964 builder.append(", "); |
| 1410 * Return `true` if this library defines a top-level function named `loadLibra
ry`. | 4965 } else { |
| 1411 * | 4966 needsComma = true; |
| 1412 * @return `true` if this library defines a top-level function named `loadLibr
ary` | 4967 } |
| 1413 */ | 4968 builder.append(type.displayName); |
| 1414 bool get hasLoadLibraryFunction; | 4969 } |
| 1415 | 4970 } |
| 1416 /** | 4971 if (optionalParameterTypes.length > 0) { |
| 1417 * Return `true` if this library is created for Angular analysis. If this libr
ary has not | 4972 if (needsComma) { |
| 1418 * yet had toolkit references resolved, then `false` will be returned. | 4973 builder.append(", "); |
| 1419 * | 4974 needsComma = false; |
| 1420 * @return `true` if this library is created for Angular analysis | 4975 } |
| 1421 */ | 4976 builder.append("["); |
| 1422 bool get isAngularHtml; | 4977 for (DartType type in optionalParameterTypes) { |
| 1423 | 4978 if (needsComma) { |
| 1424 /** | 4979 builder.append(", "); |
| 1425 * Return `true` if this library is an application that can be run in the brow
ser. | 4980 } else { |
| 1426 * | 4981 needsComma = true; |
| 1427 * @return `true` if this library is an application that can be run in the bro
wser | 4982 } |
| 1428 */ | 4983 builder.append(type.displayName); |
| 1429 bool get isBrowserApplication; | 4984 } |
| 1430 | 4985 builder.append("]"); |
| 1431 /** | 4986 needsComma = true; |
| 1432 * Return `true` if this library is the dart:core library. | 4987 } |
| 1433 * | 4988 if (namedParameterTypes.length > 0) { |
| 1434 * @return `true` if this library is the dart:core library | 4989 if (needsComma) { |
| 1435 */ | 4990 builder.append(", "); |
| 1436 bool get isDartCore; | 4991 needsComma = false; |
| 1437 | 4992 } |
| 1438 /** | 4993 builder.append("{"); |
| 1439 * Return `true` if this library is the dart:core library. | 4994 for (MapEntry<String, DartType> entry in getMapEntrySet(namedParameterTy
pes)) { |
| 1440 * | 4995 if (needsComma) { |
| 1441 * @return `true` if this library is the dart:core library | 4996 builder.append(", "); |
| 1442 */ | 4997 } else { |
| 1443 bool get isInSdk; | 4998 needsComma = true; |
| 1444 | 4999 } |
| 1445 /** | 5000 builder.append(entry.getKey()); |
| 1446 * Return `true` if this library is up to date with respect to the given time
stamp. If any | 5001 builder.append(": "); |
| 1447 * transitively referenced Source is newer than the time stamp, this method re
turns false. | 5002 builder.append(entry.getValue().displayName); |
| 1448 * | 5003 } |
| 1449 * @param timeStamp the time stamp to compare against | 5004 builder.append("}"); |
| 1450 * @return `true` if this library is up to date with respect to the given time
stamp | 5005 needsComma = true; |
| 1451 */ | 5006 } |
| 1452 bool isUpToDate(int timeStamp); | 5007 builder.append(")"); |
| 1453 } | 5008 builder.append(Element.RIGHT_ARROW); |
| 1454 | 5009 if (returnType == null) { |
| 1455 /** | 5010 builder.append("null"); |
| 1456 * The interface `LocalElement` defines the behavior of elements that can be (bu
t are not | 5011 } else { |
| 1457 * required to be) defined within a method or function (an [ExecutableElement]). | 5012 builder.append(returnType.displayName); |
| 1458 */ | 5013 } |
| 1459 abstract class LocalElement implements Element { | 5014 name = builder.toString(); |
| 1460 /** | 5015 } |
| 1461 * Return a source range that covers the approximate portion of the source in
which the name of | 5016 return name; |
| 1462 * this element is visible, or `null` if there is no single range of character
s within which | 5017 } |
| 1463 * the element name is visible. | 5018 |
| 1464 * * For a local variable, this includes everything from the end of the variab
le's initializer | 5019 @override |
| 1465 * to the end of the block that encloses the variable declaration. | 5020 Map<String, DartType> get namedParameterTypes { |
| 1466 * * For a parameter, this includes the body of the method or function that de
clares the | 5021 LinkedHashMap<String, DartType> namedParameterTypes = new LinkedHashMap<Stri
ng, DartType>(); |
| 1467 * parameter. | 5022 List<ParameterElement> parameters = baseParameters; |
| 1468 * * For a local function, this includes everything from the beginning of the
function's body to | 5023 if (parameters.length == 0) { |
| 1469 * the end of the block that encloses the function declaration. | 5024 return namedParameterTypes; |
| 1470 * * For top-level functions, `null` will be returned because they are potenti
ally visible | 5025 } |
| 1471 * in multiple sources. | 5026 List<DartType> typeParameters = TypeParameterTypeImpl.getTypes(this.typePara
meters); |
| 1472 * | 5027 for (ParameterElement parameter in parameters) { |
| 1473 * @return the range of characters in which the name of this element is visibl
e | 5028 if (parameter.parameterKind == ParameterKind.NAMED) { |
| 1474 */ | 5029 namedParameterTypes[parameter.name] = parameter.type.substitute2(typeArg
uments, typeParameters); |
| 1475 SourceRange get visibleRange; | 5030 } |
| 1476 } | 5031 } |
| 1477 | 5032 return namedParameterTypes; |
| 1478 /** | 5033 } |
| 1479 * The interface `LocalVariableElement` defines the behavior common to elements
that represent | 5034 |
| 1480 * a local variable. | 5035 @override |
| 1481 */ | 5036 List<DartType> get normalParameterTypes { |
| 1482 abstract class LocalVariableElement implements LocalElement, VariableElement { | 5037 List<ParameterElement> parameters = baseParameters; |
| 1483 /** | 5038 if (parameters.length == 0) { |
| 1484 * Return an array containing all of the toolkit specific objects attached to
this variable. | 5039 return TypeImpl.EMPTY_ARRAY; |
| 1485 * | 5040 } |
| 1486 * @return the toolkit objects attached to this variable | 5041 List<DartType> typeParameters = TypeParameterTypeImpl.getTypes(this.typePara
meters); |
| 1487 */ | 5042 List<DartType> types = new List<DartType>(); |
| 1488 List<ToolkitObjectElement> get toolkitObjects; | 5043 for (ParameterElement parameter in parameters) { |
| 1489 } | 5044 if (parameter.parameterKind == ParameterKind.REQUIRED) { |
| 1490 | 5045 types.add(parameter.type.substitute2(typeArguments, typeParameters)); |
| 1491 /** | 5046 } |
| 1492 * The interface `MethodElement` defines the behavior of elements that represent
a method | 5047 } |
| 1493 * defined within a type. | 5048 return new List.from(types); |
| 1494 */ | 5049 } |
| 1495 abstract class MethodElement implements ClassMemberElement, ExecutableElement { | 5050 |
| 1496 /** | 5051 @override |
| 1497 * Return the resolved [MethodDeclaration] node that declares this [MethodElem
ent]. | 5052 List<DartType> get optionalParameterTypes { |
| 1498 * | 5053 List<ParameterElement> parameters = baseParameters; |
| 1499 * This method is expensive, because resolved AST might be evicted from cache,
so parsing and | 5054 if (parameters.length == 0) { |
| 1500 * resolving will be performed. | 5055 return TypeImpl.EMPTY_ARRAY; |
| 1501 * | 5056 } |
| 1502 * @return the resolved [MethodDeclaration], not `null`. | 5057 List<DartType> typeParameters = TypeParameterTypeImpl.getTypes(this.typePara
meters); |
| 1503 */ | 5058 List<DartType> types = new List<DartType>(); |
| 1504 @override | 5059 for (ParameterElement parameter in parameters) { |
| 1505 MethodDeclaration get node; | 5060 if (parameter.parameterKind == ParameterKind.POSITIONAL) { |
| 1506 | 5061 types.add(parameter.type.substitute2(typeArguments, typeParameters)); |
| 1507 /** | 5062 } |
| 1508 * Return `true` if this method is abstract. Methods are abstract if they are
not external | 5063 } |
| 1509 * and have no body. | 5064 return new List.from(types); |
| 1510 * | 5065 } |
| 1511 * @return `true` if this method is abstract | 5066 |
| 1512 */ | 5067 @override |
| 1513 bool get isAbstract; | 5068 List<ParameterElement> get parameters { |
| 1514 } | 5069 List<ParameterElement> baseParameters = this.baseParameters; |
| 1515 | 5070 // no parameters, quick return |
| 1516 /** | 5071 int parameterCount = baseParameters.length; |
| 1517 * The interface `MultiplyDefinedElement` defines the behavior of pseudo-element
s that | 5072 if (parameterCount == 0) { |
| 1518 * represent multiple elements defined within a single scope that have the same
name. This situation | 5073 return baseParameters; |
| 1519 * is not allowed by the language, so objects implementing this interface always
represent an error. | 5074 } |
| 1520 * As a result, most of the normal operations on elements do not make sense and
will return useless | 5075 // create specialized parameters |
| 1521 * results. | 5076 List<ParameterElement> specializedParameters = new List<ParameterElement>(pa
rameterCount); |
| 1522 */ | 5077 for (int i = 0; i < parameterCount; i++) { |
| 1523 abstract class MultiplyDefinedElement implements Element { | 5078 specializedParameters[i] = ParameterMember.from(baseParameters[i], this); |
| 1524 /** | 5079 } |
| 1525 * Return an array containing all of the elements that were defined within the
scope to have the | 5080 return specializedParameters; |
| 1526 * same name. | 5081 } |
| 1527 * | 5082 |
| 1528 * @return the elements that were defined with the same name | 5083 @override |
| 1529 */ | 5084 DartType get returnType { |
| 1530 List<Element> get conflictingElements; | 5085 DartType baseReturnType = this.baseReturnType; |
| 1531 | 5086 if (baseReturnType == null) { |
| 1532 /** | 5087 // TODO(brianwilkerson) This is a patch. The return type should never be n
ull and we need to |
| 1533 * Return the type of this element as the dynamic type. | 5088 // understand why it is and fix it. |
| 1534 * | 5089 return DynamicTypeImpl.instance; |
| 1535 * @return the type of this element as the dynamic type | 5090 } |
| 1536 */ | 5091 return baseReturnType.substitute2(typeArguments, TypeParameterTypeImpl.getTy
pes(typeParameters)); |
| 1537 DartType get type; | 5092 } |
| 1538 } | 5093 |
| 1539 | 5094 @override |
| 1540 /** | 5095 List<TypeParameterElement> get typeParameters { |
| 1541 * The interface [MultiplyInheritedExecutableElement] defines all of the behavio
r of an | 5096 Element element = this.element; |
| 1542 * [ExecutableElement], with the additional information of an array of | 5097 if (element is FunctionTypeAliasElement) { |
| 1543 * [ExecutableElement]s from which this element was composed. | 5098 return element.typeParameters; |
| 1544 */ | 5099 } |
| 1545 abstract class MultiplyInheritedExecutableElement implements ExecutableElement { | 5100 ClassElement definingClass = element.getAncestor((element) => element is Cla
ssElement); |
| 1546 /** | 5101 if (definingClass != null) { |
| 1547 * Return an array containing all of the executable elements defined within th
is executable | 5102 return definingClass.typeParameters; |
| 1548 * element. | 5103 } |
| 1549 * | 5104 return TypeParameterElementImpl.EMPTY_ARRAY; |
| 1550 * @return the elements defined within this executable element | 5105 } |
| 1551 */ | 5106 |
| 1552 List<ExecutableElement> get inheritedElements; | 5107 @override |
| 1553 } | 5108 int get hashCode { |
| 1554 | 5109 if (element == null) { |
| 1555 /** | 5110 return 0; |
| 1556 * The interface `NamespaceCombinator` defines the behavior common to objects th
at control how | 5111 } |
| 1557 * namespaces are combined. | 5112 // Reference the arrays of parameters |
| 1558 */ | 5113 List<DartType> normalParameterTypes = this.normalParameterTypes; |
| 1559 abstract class NamespaceCombinator { | 5114 List<DartType> optionalParameterTypes = this.optionalParameterTypes; |
| 1560 /** | 5115 Iterable<DartType> namedParameterTypes = this.namedParameterTypes.values; |
| 1561 * An empty array of namespace combinators. | 5116 // Generate the hashCode |
| 1562 */ | 5117 int hashCode = returnType.hashCode; |
| 1563 static final List<NamespaceCombinator> EMPTY_ARRAY = new List<NamespaceCombina
tor>(0); | 5118 for (int i = 0; i < normalParameterTypes.length; i++) { |
| 1564 } | 5119 hashCode = (hashCode << 1) + normalParameterTypes[i].hashCode; |
| 1565 | 5120 } |
| 1566 /** | 5121 for (int i = 0; i < optionalParameterTypes.length; i++) { |
| 1567 * The interface `ParameterElement` defines the behavior of elements representin
g a parameter | 5122 hashCode = (hashCode << 1) + optionalParameterTypes[i].hashCode; |
| 1568 * defined within an executable element. | 5123 } |
| 1569 */ | 5124 for (DartType type in namedParameterTypes) { |
| 1570 abstract class ParameterElement implements LocalElement, VariableElement { | 5125 hashCode = (hashCode << 1) + type.hashCode; |
| 1571 /** | 5126 } |
| 1572 * Return a source range that covers the portion of the source in which the de
fault value for this | 5127 return hashCode; |
| 1573 * parameter is specified, or `null` if there is no default value. | 5128 } |
| 1574 * | 5129 |
| 1575 * @return the range of characters in which the default value of this paramete
r is specified | 5130 @override |
| 1576 */ | 5131 bool internalIsMoreSpecificThan(DartType type, bool withDynamic, Set<TypeImpl_
TypePair> visitedTypePairs) { |
| 1577 SourceRange get defaultValueRange; | 5132 // trivial base cases |
| 1578 | 5133 if (type == null) { |
| 1579 /** | 5134 return false; |
| 1580 * Return the kind of this parameter. | 5135 } else if (identical(this, type) || type.isDynamic || type.isDartCoreFunctio
n || type.isObject) { |
| 1581 * | 5136 return true; |
| 1582 * @return the kind of this parameter | 5137 } else if (type is! FunctionType) { |
| 1583 */ | 5138 return false; |
| 1584 ParameterKind get parameterKind; | 5139 } else if (this == type) { |
| 1585 | 5140 return true; |
| 1586 /** | 5141 } |
| 1587 * Return an array containing all of the parameters defined by this parameter.
A parameter will | 5142 FunctionType t = this; |
| 1588 * only define other parameters if it is a function typed parameter. | 5143 FunctionType s = type as FunctionType; |
| 1589 * | 5144 List<DartType> tTypes = t.normalParameterTypes; |
| 1590 * @return the parameters defined by this parameter element | 5145 List<DartType> tOpTypes = t.optionalParameterTypes; |
| 1591 */ | 5146 List<DartType> sTypes = s.normalParameterTypes; |
| 1592 List<ParameterElement> get parameters; | 5147 List<DartType> sOpTypes = s.optionalParameterTypes; |
| 1593 | 5148 // If one function has positional and the other has named parameters, return
false. |
| 1594 /** | 5149 if ((sOpTypes.length > 0 && t.namedParameterTypes.length > 0) || (tOpTypes.l
ength > 0 && s.namedParameterTypes.length > 0)) { |
| 1595 * Return `true` if this parameter is an initializing formal parameter. | 5150 return false; |
| 1596 * | 5151 } |
| 1597 * @return `true` if this parameter is an initializing formal parameter | 5152 // named parameters case |
| 1598 */ | 5153 if (t.namedParameterTypes.length > 0) { |
| 1599 bool get isInitializingFormal; | 5154 // check that the number of required parameters are equal, and check that
every t_i is |
| 1600 } | 5155 // more specific than every s_i |
| 1601 | 5156 if (t.normalParameterTypes.length != s.normalParameterTypes.length) { |
| 1602 /** | 5157 return false; |
| 1603 * The interface `PrefixElement` defines the behavior common to elements that re
present a | 5158 } else if (t.normalParameterTypes.length > 0) { |
| 1604 * prefix used to import one or more libraries into another library. | 5159 for (int i = 0; i < tTypes.length; i++) { |
| 1605 */ | 5160 if (!(tTypes[i] as TypeImpl).isMoreSpecificThan2(sTypes[i], withDynami
c, visitedTypePairs)) { |
| 1606 abstract class PrefixElement implements Element { | 5161 return false; |
| 1607 /** | 5162 } |
| 1608 * Return the library into which other libraries are imported using this prefi
x. | 5163 } |
| 1609 * | 5164 } |
| 1610 * @return the library into which other libraries are imported using this pref
ix | 5165 Map<String, DartType> namedTypesT = t.namedParameterTypes; |
| 1611 */ | 5166 Map<String, DartType> namedTypesS = s.namedParameterTypes; |
| 1612 @override | 5167 // if k >= m is false, return false: the passed function type has more nam
ed parameter types than this |
| 1613 LibraryElement get enclosingElement; | 5168 if (namedTypesT.length < namedTypesS.length) { |
| 1614 | 5169 return false; |
| 1615 /** | 5170 } |
| 1616 * Return an array containing all of the libraries that are imported using thi
s prefix. | 5171 // Loop through each element in S verifying that T has a matching paramete
r name and that the |
| 1617 * | 5172 // corresponding type is more specific then the type in S. |
| 1618 * @return the libraries that are imported using this prefix | 5173 JavaIterator<MapEntry<String, DartType>> iteratorS = new JavaIterator(getM
apEntrySet(namedTypesS)); |
| 1619 */ | 5174 while (iteratorS.hasNext) { |
| 1620 List<LibraryElement> get importedLibraries; | 5175 MapEntry<String, DartType> entryS = iteratorS.next(); |
| 1621 } | 5176 DartType typeT = namedTypesT[entryS.getKey()]; |
| 1622 | 5177 if (typeT == null) { |
| 1623 /** | 5178 return false; |
| 1624 * The interface `PropertyAccessorElement` defines the behavior of elements repr
esenting a | 5179 } |
| 1625 * getter or a setter. Note that explicitly defined property accessors implicitl
y define a synthetic | 5180 if (!(typeT as TypeImpl).isMoreSpecificThan2(entryS.getValue(), withDyna
mic, visitedTypePairs)) { |
| 1626 * field. Symmetrically, synthetic accessors are implicitly created for explicit
ly defined fields. | 5181 return false; |
| 1627 * The following rules apply: | 5182 } |
| 1628 * * Every explicit field is represented by a non-synthetic [FieldElement]. | 5183 } |
| 1629 * * Every explicit field induces a getter and possibly a setter, both of which
are represented by | 5184 } else if (s.namedParameterTypes.length > 0) { |
| 1630 * synthetic [PropertyAccessorElement]s. | 5185 return false; |
| 1631 * * Every explicit getter or setter is represented by a non-synthetic | 5186 } else { |
| 1632 * [PropertyAccessorElement]. | 5187 // positional parameter case |
| 1633 * * Every explicit getter or setter (or pair thereof if they have the same name
) induces a field | 5188 int tArgLength = tTypes.length + tOpTypes.length; |
| 1634 * that is represented by a synthetic [FieldElement]. | 5189 int sArgLength = sTypes.length + sOpTypes.length; |
| 1635 */ | 5190 // Check that the total number of parameters in t is greater than or equal
to the number of |
| 1636 abstract class PropertyAccessorElement implements ExecutableElement { | 5191 // parameters in s and that the number of required parameters in s is grea
ter than or equal to |
| 1637 /** | 5192 // the number of required parameters in t. |
| 1638 * Return the accessor representing the getter that corresponds to (has the sa
me name as) this | 5193 if (tArgLength < sArgLength || sTypes.length < tTypes.length) { |
| 1639 * setter, or `null` if this accessor is not a setter or if there is no corres
ponding | 5194 return false; |
| 1640 * getter. | 5195 } |
| 1641 * | 5196 if (tOpTypes.length == 0 && sOpTypes.length == 0) { |
| 1642 * @return the getter that corresponds to this setter | 5197 // No positional arguments, don't copy contents to new array |
| 1643 */ | 5198 for (int i = 0; i < sTypes.length; i++) { |
| 1644 PropertyAccessorElement get correspondingGetter; | 5199 if (!(tTypes[i] as TypeImpl).isMoreSpecificThan2(sTypes[i], withDynami
c, visitedTypePairs)) { |
| 1645 | 5200 return false; |
| 1646 /** | 5201 } |
| 1647 * Return the accessor representing the setter that corresponds to (has the sa
me name as) this | 5202 } |
| 1648 * getter, or `null` if this accessor is not a getter or if there is no corres
ponding | 5203 } else { |
| 1649 * setter. | 5204 // Else, we do have positional parameters, copy required and positional
parameter types into |
| 1650 * | 5205 // arrays to do the compare (for loop below). |
| 1651 * @return the setter that corresponds to this getter | 5206 List<DartType> tAllTypes = new List<DartType>(sArgLength); |
| 1652 */ | 5207 for (int i = 0; i < tTypes.length; i++) { |
| 1653 PropertyAccessorElement get correspondingSetter; | 5208 tAllTypes[i] = tTypes[i]; |
| 1654 | 5209 } |
| 1655 /** | 5210 for (int i = tTypes.length, j = 0; i < sArgLength; i++, j++) { |
| 1656 * Return the field or top-level variable associated with this accessor. If th
is accessor was | 5211 tAllTypes[i] = tOpTypes[j]; |
| 1657 * explicitly defined (is not synthetic) then the variable associated with it
will be synthetic. | 5212 } |
| 1658 * | 5213 List<DartType> sAllTypes = new List<DartType>(sArgLength); |
| 1659 * @return the variable associated with this accessor | 5214 for (int i = 0; i < sTypes.length; i++) { |
| 1660 */ | 5215 sAllTypes[i] = sTypes[i]; |
| 1661 PropertyInducingElement get variable; | 5216 } |
| 1662 | 5217 for (int i = sTypes.length, j = 0; i < sArgLength; i++, j++) { |
| 1663 /** | 5218 sAllTypes[i] = sOpTypes[j]; |
| 1664 * Return `true` if this accessor is abstract. Accessors are abstract if they
are not | 5219 } |
| 1665 * external and have no body. | 5220 for (int i = 0; i < sAllTypes.length; i++) { |
| 1666 * | 5221 if (!(tAllTypes[i] as TypeImpl).isMoreSpecificThan2(sAllTypes[i], with
Dynamic, visitedTypePairs)) { |
| 1667 * @return `true` if this accessor is abstract | 5222 return false; |
| 1668 */ | 5223 } |
| 1669 bool get isAbstract; | 5224 } |
| 1670 | 5225 } |
| 1671 /** | 5226 } |
| 1672 * Return `true` if this accessor represents a getter. | 5227 DartType tRetType = t.returnType; |
| 1673 * | 5228 DartType sRetType = s.returnType; |
| 1674 * @return `true` if this accessor represents a getter | 5229 return sRetType.isVoid || (tRetType as TypeImpl).isMoreSpecificThan2(sRetTyp
e, withDynamic, visitedTypePairs); |
| 1675 */ | 5230 } |
| 1676 bool get isGetter; | 5231 |
| 1677 | 5232 @override |
| 1678 /** | 5233 bool isAssignableTo(DartType type) => isSubtypeOf2(type, new Set<TypeImpl_Type
Pair>()); |
| 1679 * Return `true` if this accessor represents a setter. | 5234 |
| 1680 * | 5235 @override |
| 1681 * @return `true` if this accessor represents a setter | 5236 FunctionTypeImpl substitute3(List<DartType> argumentTypes) => substitute2(argu
mentTypes, typeArguments); |
| 1682 */ | 5237 |
| 1683 bool get isSetter; | 5238 @override |
| 1684 } | 5239 FunctionTypeImpl substitute2(List<DartType> argumentTypes, List<DartType> para
meterTypes) { |
| 1685 | 5240 if (argumentTypes.length != parameterTypes.length) { |
| 1686 /** | 5241 throw new IllegalArgumentException("argumentTypes.length (${argumentTypes.
length}) != parameterTypes.length (${parameterTypes.length})"); |
| 1687 * The interface `PropertyInducingElement` defines the behavior of elements repr
esenting a | 5242 } |
| 1688 * variable that has an associated getter and possibly a setter. Note that expli
citly defined | 5243 if (argumentTypes.length == 0) { |
| 1689 * variables implicitly define a synthetic getter and that non-`final` explicitl
y defined | 5244 return this; |
| 1690 * variables implicitly define a synthetic setter. Symmetrically, synthetic fiel
ds are implicitly | 5245 } |
| 1691 * created for explicitly defined getters and setters. The following rules apply
: | 5246 Element element = this.element; |
| 1692 * * Every explicit variable is represented by a non-synthetic [PropertyInducing
Element]. | 5247 FunctionTypeImpl newType = (element is ExecutableElement) ? new FunctionType
Impl.con1(element) : new FunctionTypeImpl.con2(element as FunctionTypeAliasEleme
nt); |
| 1693 * * Every explicit variable induces a getter and possibly a setter, both of whi
ch are represented | 5248 newType.typeArguments = TypeImpl.substitute(typeArguments, argumentTypes, pa
rameterTypes); |
| 1694 * by synthetic [PropertyAccessorElement]s. | 5249 return newType; |
| 1695 * * Every explicit getter or setter is represented by a non-synthetic | 5250 } |
| 1696 * [PropertyAccessorElement]. | 5251 |
| 1697 * * Every explicit getter or setter (or pair thereof if they have the same name
) induces a | 5252 @override |
| 1698 * variable that is represented by a synthetic [PropertyInducingElement]. | 5253 void appendTo(JavaStringBuilder builder) { |
| 1699 */ | 5254 List<DartType> normalParameterTypes = this.normalParameterTypes; |
| 1700 abstract class PropertyInducingElement implements VariableElement { | 5255 List<DartType> optionalParameterTypes = this.optionalParameterTypes; |
| 1701 /** | 5256 Map<String, DartType> namedParameterTypes = this.namedParameterTypes; |
| 1702 * Return the getter associated with this variable. If this variable was expli
citly defined (is | 5257 DartType returnType = this.returnType; |
| 1703 * not synthetic) then the getter associated with it will be synthetic. | 5258 builder.append("("); |
| 1704 * | 5259 bool needsComma = false; |
| 1705 * @return the getter associated with this variable | 5260 if (normalParameterTypes.length > 0) { |
| 1706 */ | 5261 for (DartType type in normalParameterTypes) { |
| 1707 PropertyAccessorElement get getter; | 5262 if (needsComma) { |
| 1708 | 5263 builder.append(", "); |
| 1709 /** | 5264 } else { |
| 1710 * Return the setter associated with this variable, or `null` if the variable
is effectively | 5265 needsComma = true; |
| 1711 * `final` and therefore does not have a setter associated with it. (This can
happen either | 5266 } |
| 1712 * because the variable is explicitly defined as being `final` or because the
variable is | 5267 (type as TypeImpl).appendTo(builder); |
| 1713 * induced by an explicit getter that does not have a corresponding setter.) I
f this variable was | 5268 } |
| 1714 * explicitly defined (is not synthetic) then the setter associated with it wi
ll be synthetic. | 5269 } |
| 1715 * | 5270 if (optionalParameterTypes.length > 0) { |
| 1716 * @return the setter associated with this variable | 5271 if (needsComma) { |
| 1717 */ | 5272 builder.append(", "); |
| 1718 PropertyAccessorElement get setter; | 5273 needsComma = false; |
| 1719 | 5274 } |
| 1720 /** | 5275 builder.append("["); |
| 1721 * Return `true` if this element is a static element. A static element is an e
lement that is | 5276 for (DartType type in optionalParameterTypes) { |
| 1722 * not associated with a particular instance, but rather with an entire librar
y or class. | 5277 if (needsComma) { |
| 1723 * | 5278 builder.append(", "); |
| 1724 * @return `true` if this executable element is a static element | 5279 } else { |
| 1725 */ | 5280 needsComma = true; |
| 1726 bool get isStatic; | 5281 } |
| 1727 } | 5282 (type as TypeImpl).appendTo(builder); |
| 1728 | 5283 } |
| 1729 /** | 5284 builder.append("]"); |
| 1730 * The interface `ShowElementCombinator` defines the behavior of combinators tha
t cause some | 5285 needsComma = true; |
| 1731 * of the names in a namespace to be visible (and the rest hidden) when being im
ported. | 5286 } |
| 1732 */ | 5287 if (namedParameterTypes.length > 0) { |
| 1733 abstract class ShowElementCombinator implements NamespaceCombinator { | 5288 if (needsComma) { |
| 1734 /** | 5289 builder.append(", "); |
| 1735 * Return the offset of the character immediately following the last character
of this node. | 5290 needsComma = false; |
| 1736 * | 5291 } |
| 1737 * @return the offset of the character just past this node | 5292 builder.append("{"); |
| 1738 */ | 5293 for (MapEntry<String, DartType> entry in getMapEntrySet(namedParameterType
s)) { |
| 1739 int get end; | 5294 if (needsComma) { |
| 1740 | 5295 builder.append(", "); |
| 1741 /** | 5296 } else { |
| 1742 * Return the offset of the 'show' keyword of this element. | 5297 needsComma = true; |
| 1743 * | 5298 } |
| 1744 * @return the offset of the 'show' keyword of this element | 5299 builder.append(entry.getKey()); |
| 1745 */ | 5300 builder.append(": "); |
| 1746 int get offset; | 5301 (entry.getValue() as TypeImpl).appendTo(builder); |
| 1747 | 5302 } |
| 1748 /** | 5303 builder.append("}"); |
| 1749 * Return an array containing the names that are to be made visible in the imp
orting library if | 5304 needsComma = true; |
| 1750 * they are defined in the imported library. | 5305 } |
| 1751 * | 5306 builder.append(")"); |
| 1752 * @return the names from the imported library that are visible in the importi
ng library | 5307 builder.append(Element.RIGHT_ARROW); |
| 1753 */ | 5308 if (returnType == null) { |
| 1754 List<String> get shownNames; | 5309 builder.append("null"); |
| 1755 } | 5310 } else { |
| 1756 | 5311 (returnType as TypeImpl).appendTo(builder); |
| 1757 /** | 5312 } |
| 1758 * The interface `ToolkitObjectElement` defines the behavior of elements that re
present a | 5313 } |
| 1759 * toolkit specific object, such as Angular controller or component. These eleme
nts are not based on | 5314 |
| 1760 * the Dart syntax, but on some semantic agreement, such as a special annotation
. | 5315 /** |
| 1761 */ | 5316 * @return the base parameter elements of this function element, not `null`. |
| 1762 abstract class ToolkitObjectElement implements Element { | 5317 */ |
| 1763 /** | 5318 List<ParameterElement> get baseParameters { |
| 1764 * An empty array of toolkit object elements. | 5319 Element element = this.element; |
| 1765 */ | 5320 if (element is ExecutableElement) { |
| 1766 static final List<ToolkitObjectElement> EMPTY_ARRAY = new List<ToolkitObjectEl
ement>(0); | 5321 return element.parameters; |
| 1767 } | 5322 } else { |
| 1768 | 5323 return (element as FunctionTypeAliasElement).parameters; |
| 1769 /** | 5324 } |
| 1770 * The interface `TopLevelVariableElement` defines the behavior of elements repr
esenting a | 5325 } |
| 1771 * top-level variable. | 5326 |
| 1772 */ | 5327 @override |
| 1773 abstract class TopLevelVariableElement implements PropertyInducingElement { | 5328 bool internalEquals(Object object, Set<ElementPair> visitedElementPairs) { |
| 1774 } | 5329 if (object is! FunctionTypeImpl) { |
| 1775 | 5330 return false; |
| 1776 /** | 5331 } |
| 1777 * The interface `TypeParameterElement` defines the behavior of elements represe
nting a type | 5332 FunctionTypeImpl otherType = object as FunctionTypeImpl; |
| 1778 * parameter. | 5333 // If the visitedTypePairs already has the pair (this, type), use the elemen
ts to determine equality |
| 1779 */ | 5334 ElementPair elementPair = new ElementPair(element, otherType.element); |
| 1780 abstract class TypeParameterElement implements Element { | 5335 if (!visitedElementPairs.add(elementPair)) { |
| 1781 /** | 5336 return elementPair.firstElt == elementPair.secondElt; |
| 1782 * Return the type representing the bound associated with this parameter, or `
null` if this | 5337 } |
| 1783 * parameter does not have an explicit bound. | 5338 // Compute the result |
| 1784 * | 5339 bool result = TypeImpl.equalArrays(normalParameterTypes, otherType.normalPar
ameterTypes, visitedElementPairs) && TypeImpl.equalArrays(optionalParameterTypes
, otherType.optionalParameterTypes, visitedElementPairs) && _equals(namedParamet
erTypes, otherType.namedParameterTypes, visitedElementPairs) && (returnType as T
ypeImpl).internalEquals(otherType.returnType, visitedElementPairs); |
| 1785 * @return the type representing the bound associated with this parameter | 5340 // Remove the pair from our visited pairs list |
| 1786 */ | 5341 visitedElementPairs.remove(elementPair); |
| 1787 DartType get bound; | 5342 // Return the result |
| 1788 | 5343 return result; |
| 1789 /** | 5344 } |
| 1790 * Return the type defined by this type parameter. | 5345 |
| 1791 * | 5346 @override |
| 1792 * @return the type defined by this type parameter | 5347 bool internalIsSubtypeOf(DartType type, Set<TypeImpl_TypePair> visitedTypePair
s) { |
| 1793 */ | 5348 // trivial base cases |
| 1794 TypeParameterType get type; | 5349 if (type == null) { |
| 1795 } | 5350 return false; |
| 1796 | 5351 } else if (identical(this, type) || type.isDynamic || type.isDartCoreFunctio
n || type.isObject) { |
| 1797 /** | 5352 return true; |
| 1798 * The interface `UndefinedElement` defines the behavior of pseudo-elements that
represent | 5353 } else if (type is! FunctionType) { |
| 1799 * names that are undefined. This situation is not allowed by the language, so o
bjects implementing | 5354 return false; |
| 1800 * this interface always represent an error. As a result, most of the normal ope
rations on elements | 5355 } else if (this == type) { |
| 1801 * do not make sense and will return useless results. | 5356 return true; |
| 1802 */ | 5357 } |
| 1803 abstract class UndefinedElement implements Element { | 5358 FunctionType t = this; |
| 1804 } | 5359 FunctionType s = type as FunctionType; |
| 1805 | 5360 List<DartType> tTypes = t.normalParameterTypes; |
| 1806 /** | 5361 List<DartType> tOpTypes = t.optionalParameterTypes; |
| 1807 * The interface `UriReferencedElement` defines the behavior of objects included
into a | 5362 List<DartType> sTypes = s.normalParameterTypes; |
| 1808 * library using some URI. | 5363 List<DartType> sOpTypes = s.optionalParameterTypes; |
| 1809 */ | 5364 // If one function has positional and the other has named parameters, return
false. |
| 1810 abstract class UriReferencedElement implements Element { | 5365 if ((sOpTypes.length > 0 && t.namedParameterTypes.length > 0) || (tOpTypes.l
ength > 0 && s.namedParameterTypes.length > 0)) { |
| 1811 /** | 5366 return false; |
| 1812 * Return the offset of the character immediately following the last character
of this node's URI, | 5367 } |
| 1813 * or `-1` for synthetic import. | 5368 // named parameters case |
| 1814 * | 5369 if (t.namedParameterTypes.length > 0) { |
| 1815 * @return the offset of the character just past the node's URI | 5370 // check that the number of required parameters are equal, and check that
every t_i is |
| 1816 */ | 5371 // assignable to every s_i |
| 1817 int get uriEnd; | 5372 if (t.normalParameterTypes.length != s.normalParameterTypes.length) { |
| 1818 | 5373 return false; |
| 1819 /** | 5374 } else if (t.normalParameterTypes.length > 0) { |
| 1820 * Return the offset of the URI in the file, or `-1` if this element is synthe
tic. | 5375 for (int i = 0; i < tTypes.length; i++) { |
| 1821 * | 5376 if (!(tTypes[i] as TypeImpl).isAssignableTo2(sTypes[i], visitedTypePai
rs)) { |
| 1822 * @return the offset of the URI | 5377 return false; |
| 1823 */ | 5378 } |
| 1824 int get uriOffset; | 5379 } |
| 1825 | 5380 } |
| 1826 /** | 5381 Map<String, DartType> namedTypesT = t.namedParameterTypes; |
| 1827 * Return the URI that is used to include this element into the enclosing libr
ary, or `null` | 5382 Map<String, DartType> namedTypesS = s.namedParameterTypes; |
| 1828 * if this is the defining compilation unit of a library. | 5383 // if k >= m is false, return false: the passed function type has more nam
ed parameter types than this |
| 1829 * | 5384 if (namedTypesT.length < namedTypesS.length) { |
| 1830 * @return the URI that is used to include this element into the enclosing lib
rary | 5385 return false; |
| 1831 */ | 5386 } |
| 1832 String get uri; | 5387 // Loop through each element in S verifying that T has a matching paramete
r name and that the |
| 1833 } | 5388 // corresponding type is assignable to the type in S. |
| 1834 | 5389 JavaIterator<MapEntry<String, DartType>> iteratorS = new JavaIterator(getM
apEntrySet(namedTypesS)); |
| 1835 /** | 5390 while (iteratorS.hasNext) { |
| 1836 * The interface `VariableElement` defines the behavior common to elements that
represent a | 5391 MapEntry<String, DartType> entryS = iteratorS.next(); |
| 1837 * variable. | 5392 DartType typeT = namedTypesT[entryS.getKey()]; |
| 1838 */ | 5393 if (typeT == null) { |
| 1839 abstract class VariableElement implements Element { | 5394 return false; |
| 1840 /** | 5395 } |
| 1841 * Return a synthetic function representing this variable's initializer, or `n
ull` if this | 5396 if (!(typeT as TypeImpl).isAssignableTo2(entryS.getValue(), visitedTypeP
airs)) { |
| 1842 * variable does not have an initializer. The function will have no parameters
. The return type of | 5397 return false; |
| 1843 * the function will be the compile-time type of the initialization expression
. | 5398 } |
| 1844 * | 5399 } |
| 1845 * @return a synthetic function representing this variable's initializer | 5400 } else if (s.namedParameterTypes.length > 0) { |
| 1846 */ | 5401 return false; |
| 1847 FunctionElement get initializer; | 5402 } else { |
| 1848 | 5403 // positional parameter case |
| 1849 /** | 5404 int tArgLength = tTypes.length + tOpTypes.length; |
| 1850 * Return the resolved [VariableDeclaration] node that declares this [Variable
Element] | 5405 int sArgLength = sTypes.length + sOpTypes.length; |
| 1851 * . | 5406 // Check that the total number of parameters in t is greater than or equal
to the number of |
| 1852 * | 5407 // parameters in s and that the number of required parameters in s is grea
ter than or equal to |
| 1853 * This method is expensive, because resolved AST might be evicted from cache,
so parsing and | 5408 // the number of required parameters in t. |
| 1854 * resolving will be performed. | 5409 if (tArgLength < sArgLength || sTypes.length < tTypes.length) { |
| 1855 * | 5410 return false; |
| 1856 * @return the resolved [VariableDeclaration], not `null`. | 5411 } |
| 1857 */ | 5412 if (tOpTypes.length == 0 && sOpTypes.length == 0) { |
| 1858 @override | 5413 // No positional arguments, don't copy contents to new array |
| 1859 VariableDeclaration get node; | 5414 for (int i = 0; i < sTypes.length; i++) { |
| 1860 | 5415 if (!(tTypes[i] as TypeImpl).isAssignableTo2(sTypes[i], visitedTypePai
rs)) { |
| 1861 /** | 5416 return false; |
| 1862 * Return the declared type of this variable, or `null` if the variable did no
t have a | 5417 } |
| 1863 * declared type (such as if it was declared using the keyword 'var'). | 5418 } |
| 1864 * | 5419 } else { |
| 1865 * @return the declared type of this variable | 5420 // Else, we do have positional parameters, copy required and positional
parameter types into |
| 1866 */ | 5421 // arrays to do the compare (for loop below). |
| 1867 DartType get type; | 5422 List<DartType> tAllTypes = new List<DartType>(sArgLength); |
| 1868 | 5423 for (int i = 0; i < tTypes.length; i++) { |
| 1869 /** | 5424 tAllTypes[i] = tTypes[i]; |
| 1870 * Return `true` if this variable was declared with the 'const' modifier. | 5425 } |
| 1871 * | 5426 for (int i = tTypes.length, j = 0; i < sArgLength; i++, j++) { |
| 1872 * @return `true` if this variable was declared with the 'const' modifier | 5427 tAllTypes[i] = tOpTypes[j]; |
| 1873 */ | 5428 } |
| 1874 bool get isConst; | 5429 List<DartType> sAllTypes = new List<DartType>(sArgLength); |
| 1875 | 5430 for (int i = 0; i < sTypes.length; i++) { |
| 1876 /** | 5431 sAllTypes[i] = sTypes[i]; |
| 1877 * Return `true` if this variable was declared with the 'final' modifier. Vari
ables that are | 5432 } |
| 1878 * declared with the 'const' modifier will return `false` even though they are
implicitly | 5433 for (int i = sTypes.length, j = 0; i < sArgLength; i++, j++) { |
| 1879 * final. | 5434 sAllTypes[i] = sOpTypes[j]; |
| 1880 * | 5435 } |
| 1881 * @return `true` if this variable was declared with the 'final' modifier | 5436 for (int i = 0; i < sAllTypes.length; i++) { |
| 1882 */ | 5437 if (!(tAllTypes[i] as TypeImpl).isAssignableTo2(sAllTypes[i], visitedT
ypePairs)) { |
| 1883 bool get isFinal; | 5438 return false; |
| 1884 } | 5439 } |
| 1885 | 5440 } |
| 1886 /** | 5441 } |
| 1887 * The interface `AngularControllerElement` defines the Angular component descri
bed by | 5442 } |
| 1888 * <code>Component</code> annotation. | 5443 DartType tRetType = t.returnType; |
| 1889 */ | 5444 DartType sRetType = s.returnType; |
| 1890 abstract class AngularComponentElement implements AngularHasSelectorElement, Ang
ularHasTemplateElement { | 5445 return sRetType.isVoid || (tRetType as TypeImpl).isAssignableTo2(sRetType, v
isitedTypePairs); |
| 1891 /** | 5446 } |
| 1892 * Return an array containing all of the properties declared by this component
. | 5447 |
| 1893 */ | 5448 /** |
| 1894 List<AngularPropertyElement> get properties; | 5449 * Return the return type defined by this function's element. |
| 1895 | 5450 * |
| 1896 /** | 5451 * @return the return type defined by this function's element |
| 1897 * Return an array containing all of the scope properties set in the implement
ation of this | 5452 */ |
| 1898 * component. | 5453 DartType get baseReturnType { |
| 1899 */ | 5454 Element element = this.element; |
| 1900 List<AngularScopePropertyElement> get scopeProperties; | 5455 if (element is ExecutableElement) { |
| 1901 | 5456 return element.returnType; |
| 1902 /** | 5457 } else { |
| 1903 * Returns the CSS file URI. | 5458 return (element as FunctionTypeAliasElement).returnType; |
| 1904 */ | 5459 } |
| 1905 String get styleUri; | 5460 } |
| 1906 | |
| 1907 /** | |
| 1908 * Return the offset of the [getStyleUri] in the [getSource]. | |
| 1909 * | |
| 1910 * @return the offset of the style URI | |
| 1911 */ | |
| 1912 int get styleUriOffset; | |
| 1913 } | |
| 1914 | |
| 1915 /** | |
| 1916 * The interface `AngularControllerElement` defines the Angular controller descr
ibed by | |
| 1917 * <code>Controller</code> annotation. | |
| 1918 */ | |
| 1919 abstract class AngularControllerElement implements AngularHasSelectorElement { | |
| 1920 } | |
| 1921 | |
| 1922 /** | |
| 1923 * The interface `AngularDirectiveElement` defines the Angular controller descri
bed by | |
| 1924 * <code>Decorator</code> annotation. | |
| 1925 */ | |
| 1926 abstract class AngularDecoratorElement implements AngularHasSelectorElement { | |
| 1927 /** | |
| 1928 * Return an array containing all of the properties declared by this directive
. | |
| 1929 */ | |
| 1930 List<AngularPropertyElement> get properties; | |
| 1931 | |
| 1932 /** | |
| 1933 * Checks if this directive is implemented by the class with given name. | |
| 1934 */ | |
| 1935 bool isClass(String name); | |
| 1936 } | |
| 1937 | |
| 1938 /** | |
| 1939 * The interface `AngularElement` defines the behavior of objects representing i
nformation | |
| 1940 * about an Angular specific element. | |
| 1941 */ | |
| 1942 abstract class AngularElement implements ToolkitObjectElement { | |
| 1943 /** | |
| 1944 * An empty array of Angular elements. | |
| 1945 */ | |
| 1946 static final List<AngularElement> EMPTY_ARRAY = new List<AngularElement>(0); | |
| 1947 | |
| 1948 /** | |
| 1949 * Returns the [AngularApplication] this element is used in. | |
| 1950 * | |
| 1951 * @return the [AngularApplication] this element is used in | |
| 1952 */ | |
| 1953 AngularApplication get application; | |
| 1954 } | |
| 1955 | |
| 1956 /** | |
| 1957 * The interface `AngularFormatterElement` defines the Angular formatter describ
ed by | |
| 1958 * <code>Formatter</code> annotation. | |
| 1959 */ | |
| 1960 abstract class AngularFormatterElement implements AngularElement { | |
| 1961 } | |
| 1962 | |
| 1963 /** | |
| 1964 * [AngularSelectorElement] based on presence of attribute. | |
| 1965 */ | |
| 1966 abstract class AngularHasAttributeSelectorElement implements AngularSelectorElem
ent { | |
| 1967 } | |
| 1968 | |
| 1969 /** | |
| 1970 * [AngularSelectorElement] based on presence of a class. | |
| 1971 */ | |
| 1972 abstract class AngularHasClassSelectorElement implements AngularSelectorElement
{ | |
| 1973 } | |
| 1974 | |
| 1975 /** | |
| 1976 * The interface `AngularElement` defines the behavior of objects representing i
nformation | |
| 1977 * about an Angular element which is applied conditionally using some [AngularSe
lectorElement]. | |
| 1978 */ | |
| 1979 abstract class AngularHasSelectorElement implements AngularElement { | |
| 1980 /** | |
| 1981 * Returns the selector specified for this element. | |
| 1982 * | |
| 1983 * @return the [AngularSelectorElement] specified for this element | |
| 1984 */ | |
| 1985 AngularSelectorElement get selector; | |
| 1986 } | |
| 1987 | |
| 1988 /** | |
| 1989 * The interface `AngularHasTemplateElement` defines common behavior for | |
| 1990 * [AngularElement] that have template URI / [Source]. | |
| 1991 */ | |
| 1992 abstract class AngularHasTemplateElement implements AngularElement { | |
| 1993 /** | |
| 1994 * Returns the HTML template [Source], `null` if not resolved. | |
| 1995 */ | |
| 1996 Source get templateSource; | |
| 1997 | |
| 1998 /** | |
| 1999 * Returns the HTML template URI. | |
| 2000 */ | |
| 2001 String get templateUri; | |
| 2002 | |
| 2003 /** | |
| 2004 * Return the offset of the [getTemplateUri] in the [getSource]. | |
| 2005 * | |
| 2006 * @return the offset of the template URI | |
| 2007 */ | |
| 2008 int get templateUriOffset; | |
| 2009 } | |
| 2010 | |
| 2011 /** | |
| 2012 * The interface `AngularPropertyElement` defines a single property in | |
| 2013 * [AngularComponentElement]. | |
| 2014 */ | |
| 2015 abstract class AngularPropertyElement implements AngularElement { | |
| 2016 /** | |
| 2017 * An empty array of property elements. | |
| 2018 */ | |
| 2019 static final List<AngularPropertyElement> EMPTY_ARRAY = []; | |
| 2020 | |
| 2021 /** | |
| 2022 * Returns the field this property is mapped to. | |
| 2023 * | |
| 2024 * @return the field this property is mapped to. | |
| 2025 */ | |
| 2026 FieldElement get field; | |
| 2027 | |
| 2028 /** | |
| 2029 * Return the offset of the field name of this property in the property map, o
r `-1` if | |
| 2030 * property was created using annotation on [FieldElement]. | |
| 2031 * | |
| 2032 * @return the offset of the field name of this property | |
| 2033 */ | |
| 2034 int get fieldNameOffset; | |
| 2035 | |
| 2036 /** | |
| 2037 * Returns the kind of this property. | |
| 2038 * | |
| 2039 * @return the kind of this property | |
| 2040 */ | |
| 2041 AngularPropertyKind get propertyKind; | |
| 2042 } | |
| 2043 | |
| 2044 /** | |
| 2045 * The enumeration `AngularPropertyKind` defines the different kinds of property
bindings. | |
| 2046 */ | |
| 2047 class AngularPropertyKind extends Enum<AngularPropertyKind> { | |
| 2048 /** | |
| 2049 * `@` - Map the DOM attribute string. The attribute string will be taken lite
rally or | |
| 2050 * interpolated if it contains binding {{}} syntax and assigned to the express
ion. (cost: 0 | |
| 2051 * watches) | |
| 2052 */ | |
| 2053 static const AngularPropertyKind ATTR = const AngularPropertyKind('ATTR', 0); | |
| 2054 | |
| 2055 /** | |
| 2056 * `&` - Treat the DOM attribute value as an expression. Assign a closure func
tion into the field. | |
| 2057 * This allows the component to control the invocation of the closure. This is
useful for passing | |
| 2058 * expressions into controllers which act like callbacks. (cost: 0 watches) | |
| 2059 */ | |
| 2060 static const AngularPropertyKind CALLBACK = const AngularPropertyKind('CALLBAC
K', 1); | |
| 2061 | |
| 2062 /** | |
| 2063 * `=>` - Treat the DOM attribute value as an expression. Set up a watch, whic
h will read the | |
| 2064 * expression in the attribute and assign the value to destination expression.
(cost: 1 watch) | |
| 2065 */ | |
| 2066 static const AngularPropertyKind ONE_WAY = const AngularPropertyKind('ONE_WAY'
, 2); | |
| 2067 | |
| 2068 /** | |
| 2069 * `=>!` - Treat the DOM attribute value as an expression. Set up a one time w
atch on expression. | |
| 2070 * Once the expression turns not null it will no longer update. (cost: 1 watch
es until not null, | |
| 2071 * then 0 watches) | |
| 2072 */ | |
| 2073 static const AngularPropertyKind ONE_WAY_ONE_TIME = const AngularPropertyKind(
'ONE_WAY_ONE_TIME', 3); | |
| 2074 | |
| 2075 /** | |
| 2076 * `<=>` - Treat the DOM attribute value as an expression. Set up a watch on b
oth outside as well | |
| 2077 * as component scope to keep the source and destination in sync. (cost: 2 wat
ches) | |
| 2078 */ | |
| 2079 static const AngularPropertyKind TWO_WAY = const AngularPropertyKind_TWO_WAY('
TWO_WAY', 4); | |
| 2080 | |
| 2081 static const List<AngularPropertyKind> values = const [ATTR, CALLBACK, ONE_WAY
, ONE_WAY_ONE_TIME, TWO_WAY]; | |
| 2082 | |
| 2083 /** | |
| 2084 * Returns `true` if property of this kind calls field getter. | |
| 2085 */ | |
| 2086 bool callsGetter() => false; | |
| 2087 | |
| 2088 /** | |
| 2089 * Returns `true` if property of this kind calls field setter. | |
| 2090 */ | |
| 2091 bool callsSetter() => true; | |
| 2092 | |
| 2093 const AngularPropertyKind(String name, int ordinal) : super(name, ordinal); | |
| 2094 } | |
| 2095 | |
| 2096 class AngularPropertyKind_TWO_WAY extends AngularPropertyKind { | |
| 2097 const AngularPropertyKind_TWO_WAY(String name, int ordinal) : super(name, ordi
nal); | |
| 2098 | |
| 2099 @override | |
| 2100 bool callsGetter() => true; | |
| 2101 } | |
| 2102 | |
| 2103 /** | |
| 2104 * The interface `AngularScopeVariableElement` defines the Angular <code>Scope</
code> | |
| 2105 * property. They are created for every <code>scope['property'] = value;</code>
code snippet. | |
| 2106 */ | |
| 2107 abstract class AngularScopePropertyElement implements AngularElement { | |
| 2108 /** | |
| 2109 * An empty array of scope property elements. | |
| 2110 */ | |
| 2111 static final List<AngularScopePropertyElement> EMPTY_ARRAY = []; | |
| 2112 | |
| 2113 /** | |
| 2114 * Returns the type of this property, not `null`, maybe <code>dynamic</code>. | |
| 2115 * | |
| 2116 * @return the type of this property. | |
| 2117 */ | |
| 2118 DartType get type; | |
| 2119 } | |
| 2120 | |
| 2121 /** | |
| 2122 * [AngularSelectorElement] is used to decide when Angular object should be appl
ied. | |
| 2123 * | |
| 2124 * This class is an [Element] to support renaming component tag names, which are
identifiers | |
| 2125 * in selectors. | |
| 2126 */ | |
| 2127 abstract class AngularSelectorElement implements AngularElement { | |
| 2128 /** | |
| 2129 * Checks if the given [XmlTagNode] matches this selector. | |
| 2130 * | |
| 2131 * @param node the [XmlTagNode] to check | |
| 2132 * @return `true` if the given [XmlTagNode] matches, or `false` otherwise | |
| 2133 */ | |
| 2134 bool apply(XmlTagNode node); | |
| 2135 } | |
| 2136 | |
| 2137 /** | |
| 2138 * [AngularSelectorElement] based on tag name. | |
| 2139 */ | |
| 2140 abstract class AngularTagSelectorElement implements AngularSelectorElement { | |
| 2141 } | |
| 2142 | |
| 2143 /** | |
| 2144 * The interface `AngularViewElement` defines the Angular view defined using inv
ocation like | |
| 2145 * <code>view('views/create.html')</code>. | |
| 2146 */ | |
| 2147 abstract class AngularViewElement implements AngularHasTemplateElement { | |
| 2148 /** | |
| 2149 * An empty array of view elements. | |
| 2150 */ | |
| 2151 static final List<AngularViewElement> EMPTY_ARRAY = new List<AngularViewElemen
t>(0); | |
| 2152 } | |
| 2153 | |
| 2154 /** | |
| 2155 * The interface `PolymerAttributeElement` defines an attribute in | |
| 2156 * [PolymerTagHtmlElement]. | |
| 2157 * | |
| 2158 * <pre> | |
| 2159 * <polymer-element name="my-example" attributes='attrA attrB'> | |
| 2160 * </polymer-element> | |
| 2161 * </pre> | |
| 2162 */ | |
| 2163 abstract class PolymerAttributeElement implements PolymerElement { | |
| 2164 /** | |
| 2165 * An empty array of Polymer custom tag attributes. | |
| 2166 */ | |
| 2167 static final List<PolymerAttributeElement> EMPTY_ARRAY = new List<PolymerAttri
buteElement>(0); | |
| 2168 | |
| 2169 /** | |
| 2170 * Return the [FieldElement] associated with this attribute. Maybe `null` if | |
| 2171 * [PolymerTagDartElement] does not have a field associated with it. | |
| 2172 */ | |
| 2173 FieldElement get field; | |
| 2174 } | |
| 2175 | |
| 2176 /** | |
| 2177 * The interface `PolymerElement` defines the behavior of objects representing i
nformation | |
| 2178 * about a Polymer specific element. | |
| 2179 */ | |
| 2180 abstract class PolymerElement implements ToolkitObjectElement { | |
| 2181 /** | |
| 2182 * An empty array of Polymer elements. | |
| 2183 */ | |
| 2184 static final List<PolymerElement> EMPTY_ARRAY = new List<PolymerElement>(0); | |
| 2185 } | |
| 2186 | |
| 2187 /** | |
| 2188 * The interface `PolymerTagDartElement` defines a Polymer custom tag in Dart. | |
| 2189 * | |
| 2190 * <pre> | |
| 2191 * @CustomTag('my-example') | |
| 2192 * </pre> | |
| 2193 */ | |
| 2194 abstract class PolymerTagDartElement implements PolymerElement { | |
| 2195 /** | |
| 2196 * Return the [ClassElement] that is associated with this Polymer custom tag.
Not | |
| 2197 * `null`, because [PolymerTagDartElement]s are created for [ClassElement]s | |
| 2198 * marked with the `@CustomTag` annotation. | |
| 2199 */ | |
| 2200 ClassElement get classElement; | |
| 2201 | |
| 2202 /** | |
| 2203 * Return the [PolymerTagHtmlElement] part of this Polymer custom tag. Maybe `
null` if | |
| 2204 * it has not been resolved yet or there are no corresponding Dart part define
d. | |
| 2205 */ | |
| 2206 PolymerTagHtmlElement get htmlElement; | |
| 2207 } | |
| 2208 | |
| 2209 /** | |
| 2210 * The interface `PolymerTagHtmlElement` defines a Polymer custom tag in HTML. | |
| 2211 * | |
| 2212 * <pre> | |
| 2213 * <polymer-element name="my-example" attributes='attrA attrB'> | |
| 2214 * </polymer-element> | |
| 2215 * </pre> | |
| 2216 */ | |
| 2217 abstract class PolymerTagHtmlElement implements PolymerElement { | |
| 2218 /** | |
| 2219 * An empty array of [PolymerTagHtmlElement]s. | |
| 2220 */ | |
| 2221 static final List<PolymerTagHtmlElement> EMPTY_ARRAY = new List<PolymerTagHtml
Element>(0); | |
| 2222 | |
| 2223 /** | |
| 2224 * Return an array containing all of the attributes declared by this tag. | |
| 2225 */ | |
| 2226 List<PolymerAttributeElement> get attributes; | |
| 2227 | |
| 2228 /** | |
| 2229 * Return the [PolymerTagDartElement] part on this Polymer custom tag. Maybe `
null` if | |
| 2230 * it has not been resolved yet or there are no corresponding Dart part define
d. | |
| 2231 */ | |
| 2232 PolymerTagDartElement get dartElement; | |
| 2233 } | 5461 } |
| 2234 | 5462 |
| 2235 /** | 5463 /** |
| 2236 * Instances of the class `GeneralizingElementVisitor` implement an element visi
tor that will | 5464 * Instances of the class `GeneralizingElementVisitor` implement an element visi
tor that will |
| 2237 * recursively visit all of the elements in an element model (like instances of
the class | 5465 * recursively visit all of the elements in an element model (like instances of
the class |
| 2238 * [RecursiveElementVisitor]). In addition, when an element of a specific type i
s visited not | 5466 * [RecursiveElementVisitor]). In addition, when an element of a specific type i
s visited not |
| 2239 * only will the visit method for that specific type of element be invoked, but
additional methods | 5467 * only will the visit method for that specific type of element be invoked, but
additional methods |
| 2240 * for the supertypes of that element will also be invoked. For example, using a
n instance of this | 5468 * for the supertypes of that element will also be invoked. For example, using a
n instance of this |
| 2241 * class to visit a [MethodElement] will cause the method | 5469 * class to visit a [MethodElement] will cause the method |
| 2242 * [visitMethodElement] to be invoked but will also cause the methods | 5470 * [visitMethodElement] to be invoked but will also cause the methods |
| (...skipping 171 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2414 @override | 5642 @override |
| 2415 R visitTopLevelVariableElement(TopLevelVariableElement element) => visitProper
tyInducingElement(element); | 5643 R visitTopLevelVariableElement(TopLevelVariableElement element) => visitProper
tyInducingElement(element); |
| 2416 | 5644 |
| 2417 @override | 5645 @override |
| 2418 R visitTypeParameterElement(TypeParameterElement element) => visitElement(elem
ent); | 5646 R visitTypeParameterElement(TypeParameterElement element) => visitElement(elem
ent); |
| 2419 | 5647 |
| 2420 R visitVariableElement(VariableElement element) => visitElement(element); | 5648 R visitVariableElement(VariableElement element) => visitElement(element); |
| 2421 } | 5649 } |
| 2422 | 5650 |
| 2423 /** | 5651 /** |
| 2424 * Instances of the class `RecursiveElementVisitor` implement an element visitor
that will | 5652 * Implementation of [AngularSelectorElement] based on presence of attribute. |
| 2425 * recursively visit all of the element in an element model. For example, using
an instance of this | 5653 */ |
| 2426 * class to visit a [CompilationUnitElement] will also cause all of the types in
the | 5654 class HasAttributeSelectorElementImpl extends AngularSelectorElementImpl impleme
nts AngularHasAttributeSelectorElement { |
| 2427 * compilation unit to be visited. | 5655 HasAttributeSelectorElementImpl(String attributeName, int offset) : super(attr
ibuteName, offset); |
| 2428 * | 5656 |
| 2429 * Subclasses that override a visit method must either invoke the overridden vis
it method or must | 5657 @override |
| 2430 * explicitly ask the visited element to visit its children. Failure to do so wi
ll cause the | 5658 bool apply(XmlTagNode node) { |
| 2431 * children of the visited element to not be visited. | 5659 String attributeName = name; |
| 2432 */ | 5660 return node.getAttribute(attributeName) != null; |
| 2433 class RecursiveElementVisitor<R> implements ElementVisitor<R> { | |
| 2434 @override | |
| 2435 R visitAngularComponentElement(AngularComponentElement element) { | |
| 2436 element.visitChildren(this); | |
| 2437 return null; | |
| 2438 } | |
| 2439 | |
| 2440 @override | |
| 2441 R visitAngularControllerElement(AngularControllerElement element) { | |
| 2442 element.visitChildren(this); | |
| 2443 return null; | |
| 2444 } | |
| 2445 | |
| 2446 @override | |
| 2447 R visitAngularDirectiveElement(AngularDecoratorElement element) { | |
| 2448 element.visitChildren(this); | |
| 2449 return null; | |
| 2450 } | |
| 2451 | |
| 2452 @override | |
| 2453 R visitAngularFormatterElement(AngularFormatterElement element) { | |
| 2454 element.visitChildren(this); | |
| 2455 return null; | |
| 2456 } | |
| 2457 | |
| 2458 @override | |
| 2459 R visitAngularPropertyElement(AngularPropertyElement element) { | |
| 2460 element.visitChildren(this); | |
| 2461 return null; | |
| 2462 } | |
| 2463 | |
| 2464 @override | |
| 2465 R visitAngularScopePropertyElement(AngularScopePropertyElement element) { | |
| 2466 element.visitChildren(this); | |
| 2467 return null; | |
| 2468 } | |
| 2469 | |
| 2470 @override | |
| 2471 R visitAngularSelectorElement(AngularSelectorElement element) { | |
| 2472 element.visitChildren(this); | |
| 2473 return null; | |
| 2474 } | |
| 2475 | |
| 2476 @override | |
| 2477 R visitAngularViewElement(AngularViewElement element) { | |
| 2478 element.visitChildren(this); | |
| 2479 return null; | |
| 2480 } | |
| 2481 | |
| 2482 @override | |
| 2483 R visitClassElement(ClassElement element) { | |
| 2484 element.visitChildren(this); | |
| 2485 return null; | |
| 2486 } | |
| 2487 | |
| 2488 @override | |
| 2489 R visitCompilationUnitElement(CompilationUnitElement element) { | |
| 2490 element.visitChildren(this); | |
| 2491 return null; | |
| 2492 } | |
| 2493 | |
| 2494 @override | |
| 2495 R visitConstructorElement(ConstructorElement element) { | |
| 2496 element.visitChildren(this); | |
| 2497 return null; | |
| 2498 } | |
| 2499 | |
| 2500 @override | |
| 2501 R visitEmbeddedHtmlScriptElement(EmbeddedHtmlScriptElement element) { | |
| 2502 element.visitChildren(this); | |
| 2503 return null; | |
| 2504 } | |
| 2505 | |
| 2506 @override | |
| 2507 R visitExportElement(ExportElement element) { | |
| 2508 element.visitChildren(this); | |
| 2509 return null; | |
| 2510 } | |
| 2511 | |
| 2512 @override | |
| 2513 R visitExternalHtmlScriptElement(ExternalHtmlScriptElement element) { | |
| 2514 element.visitChildren(this); | |
| 2515 return null; | |
| 2516 } | |
| 2517 | |
| 2518 @override | |
| 2519 R visitFieldElement(FieldElement element) { | |
| 2520 element.visitChildren(this); | |
| 2521 return null; | |
| 2522 } | |
| 2523 | |
| 2524 @override | |
| 2525 R visitFieldFormalParameterElement(FieldFormalParameterElement element) { | |
| 2526 element.visitChildren(this); | |
| 2527 return null; | |
| 2528 } | |
| 2529 | |
| 2530 @override | |
| 2531 R visitFunctionElement(FunctionElement element) { | |
| 2532 element.visitChildren(this); | |
| 2533 return null; | |
| 2534 } | |
| 2535 | |
| 2536 @override | |
| 2537 R visitFunctionTypeAliasElement(FunctionTypeAliasElement element) { | |
| 2538 element.visitChildren(this); | |
| 2539 return null; | |
| 2540 } | |
| 2541 | |
| 2542 @override | |
| 2543 R visitHtmlElement(HtmlElement element) { | |
| 2544 element.visitChildren(this); | |
| 2545 return null; | |
| 2546 } | |
| 2547 | |
| 2548 @override | |
| 2549 R visitImportElement(ImportElement element) { | |
| 2550 element.visitChildren(this); | |
| 2551 return null; | |
| 2552 } | |
| 2553 | |
| 2554 @override | |
| 2555 R visitLabelElement(LabelElement element) { | |
| 2556 element.visitChildren(this); | |
| 2557 return null; | |
| 2558 } | |
| 2559 | |
| 2560 @override | |
| 2561 R visitLibraryElement(LibraryElement element) { | |
| 2562 element.visitChildren(this); | |
| 2563 return null; | |
| 2564 } | |
| 2565 | |
| 2566 @override | |
| 2567 R visitLocalVariableElement(LocalVariableElement element) { | |
| 2568 element.visitChildren(this); | |
| 2569 return null; | |
| 2570 } | |
| 2571 | |
| 2572 @override | |
| 2573 R visitMethodElement(MethodElement element) { | |
| 2574 element.visitChildren(this); | |
| 2575 return null; | |
| 2576 } | |
| 2577 | |
| 2578 @override | |
| 2579 R visitMultiplyDefinedElement(MultiplyDefinedElement element) { | |
| 2580 element.visitChildren(this); | |
| 2581 return null; | |
| 2582 } | |
| 2583 | |
| 2584 @override | |
| 2585 R visitParameterElement(ParameterElement element) { | |
| 2586 element.visitChildren(this); | |
| 2587 return null; | |
| 2588 } | |
| 2589 | |
| 2590 @override | |
| 2591 R visitPolymerAttributeElement(PolymerAttributeElement element) { | |
| 2592 element.visitChildren(this); | |
| 2593 return null; | |
| 2594 } | |
| 2595 | |
| 2596 @override | |
| 2597 R visitPolymerTagDartElement(PolymerTagDartElement element) { | |
| 2598 element.visitChildren(this); | |
| 2599 return null; | |
| 2600 } | |
| 2601 | |
| 2602 @override | |
| 2603 R visitPolymerTagHtmlElement(PolymerTagHtmlElement element) { | |
| 2604 element.visitChildren(this); | |
| 2605 return null; | |
| 2606 } | |
| 2607 | |
| 2608 @override | |
| 2609 R visitPrefixElement(PrefixElement element) { | |
| 2610 element.visitChildren(this); | |
| 2611 return null; | |
| 2612 } | |
| 2613 | |
| 2614 @override | |
| 2615 R visitPropertyAccessorElement(PropertyAccessorElement element) { | |
| 2616 element.visitChildren(this); | |
| 2617 return null; | |
| 2618 } | |
| 2619 | |
| 2620 @override | |
| 2621 R visitTopLevelVariableElement(TopLevelVariableElement element) { | |
| 2622 element.visitChildren(this); | |
| 2623 return null; | |
| 2624 } | |
| 2625 | |
| 2626 @override | |
| 2627 R visitTypeParameterElement(TypeParameterElement element) { | |
| 2628 element.visitChildren(this); | |
| 2629 return null; | |
| 2630 } | |
| 2631 } | |
| 2632 | |
| 2633 /** | |
| 2634 * Instances of the class `SimpleElementVisitor` implement an element visitor th
at will do | |
| 2635 * nothing when visiting an element. It is intended to be a superclass for class
es that use the | |
| 2636 * visitor pattern primarily as a dispatch mechanism (and hence don't need to re
cursively visit a | |
| 2637 * whole structure) and that only need to visit a small number of element types. | |
| 2638 */ | |
| 2639 class SimpleElementVisitor<R> implements ElementVisitor<R> { | |
| 2640 @override | |
| 2641 R visitAngularComponentElement(AngularComponentElement element) => null; | |
| 2642 | |
| 2643 @override | |
| 2644 R visitAngularControllerElement(AngularControllerElement element) => null; | |
| 2645 | |
| 2646 @override | |
| 2647 R visitAngularDirectiveElement(AngularDecoratorElement element) => null; | |
| 2648 | |
| 2649 @override | |
| 2650 R visitAngularFormatterElement(AngularFormatterElement element) => null; | |
| 2651 | |
| 2652 @override | |
| 2653 R visitAngularPropertyElement(AngularPropertyElement element) => null; | |
| 2654 | |
| 2655 @override | |
| 2656 R visitAngularScopePropertyElement(AngularScopePropertyElement element) => nul
l; | |
| 2657 | |
| 2658 @override | |
| 2659 R visitAngularSelectorElement(AngularSelectorElement element) => null; | |
| 2660 | |
| 2661 @override | |
| 2662 R visitAngularViewElement(AngularViewElement element) => null; | |
| 2663 | |
| 2664 @override | |
| 2665 R visitClassElement(ClassElement element) => null; | |
| 2666 | |
| 2667 @override | |
| 2668 R visitCompilationUnitElement(CompilationUnitElement element) => null; | |
| 2669 | |
| 2670 @override | |
| 2671 R visitConstructorElement(ConstructorElement element) => null; | |
| 2672 | |
| 2673 @override | |
| 2674 R visitEmbeddedHtmlScriptElement(EmbeddedHtmlScriptElement element) => null; | |
| 2675 | |
| 2676 @override | |
| 2677 R visitExportElement(ExportElement element) => null; | |
| 2678 | |
| 2679 @override | |
| 2680 R visitExternalHtmlScriptElement(ExternalHtmlScriptElement element) => null; | |
| 2681 | |
| 2682 @override | |
| 2683 R visitFieldElement(FieldElement element) => null; | |
| 2684 | |
| 2685 @override | |
| 2686 R visitFieldFormalParameterElement(FieldFormalParameterElement element) => nul
l; | |
| 2687 | |
| 2688 @override | |
| 2689 R visitFunctionElement(FunctionElement element) => null; | |
| 2690 | |
| 2691 @override | |
| 2692 R visitFunctionTypeAliasElement(FunctionTypeAliasElement element) => null; | |
| 2693 | |
| 2694 @override | |
| 2695 R visitHtmlElement(HtmlElement element) => null; | |
| 2696 | |
| 2697 @override | |
| 2698 R visitImportElement(ImportElement element) => null; | |
| 2699 | |
| 2700 @override | |
| 2701 R visitLabelElement(LabelElement element) => null; | |
| 2702 | |
| 2703 @override | |
| 2704 R visitLibraryElement(LibraryElement element) => null; | |
| 2705 | |
| 2706 @override | |
| 2707 R visitLocalVariableElement(LocalVariableElement element) => null; | |
| 2708 | |
| 2709 @override | |
| 2710 R visitMethodElement(MethodElement element) => null; | |
| 2711 | |
| 2712 @override | |
| 2713 R visitMultiplyDefinedElement(MultiplyDefinedElement element) => null; | |
| 2714 | |
| 2715 @override | |
| 2716 R visitParameterElement(ParameterElement element) => null; | |
| 2717 | |
| 2718 @override | |
| 2719 R visitPolymerAttributeElement(PolymerAttributeElement element) => null; | |
| 2720 | |
| 2721 @override | |
| 2722 R visitPolymerTagDartElement(PolymerTagDartElement element) => null; | |
| 2723 | |
| 2724 @override | |
| 2725 R visitPolymerTagHtmlElement(PolymerTagHtmlElement element) => null; | |
| 2726 | |
| 2727 @override | |
| 2728 R visitPrefixElement(PrefixElement element) => null; | |
| 2729 | |
| 2730 @override | |
| 2731 R visitPropertyAccessorElement(PropertyAccessorElement element) => null; | |
| 2732 | |
| 2733 @override | |
| 2734 R visitTopLevelVariableElement(TopLevelVariableElement element) => null; | |
| 2735 | |
| 2736 @override | |
| 2737 R visitTypeParameterElement(TypeParameterElement element) => null; | |
| 2738 } | |
| 2739 | |
| 2740 /** | |
| 2741 * For AST nodes that could be in both the getter and setter contexts ([IndexExp
ression]s and | |
| 2742 * [SimpleIdentifier]s), the additional resolved elements are stored in the AST
node, in an | |
| 2743 * [AuxiliaryElements]. Since resolved elements are either statically resolved o
r resolved | |
| 2744 * using propagated type information, this class is a wrapper for a pair of | |
| 2745 * [ExecutableElement]s, not just a single [ExecutableElement]. | |
| 2746 */ | |
| 2747 class AuxiliaryElements { | |
| 2748 /** | |
| 2749 * The element based on propagated type information, or `null` if the AST stru
cture has not | |
| 2750 * been resolved or if this identifier could not be resolved. | |
| 2751 */ | |
| 2752 final ExecutableElement propagatedElement; | |
| 2753 | |
| 2754 /** | |
| 2755 * The element associated with this identifier based on static type informatio
n, or `null` | |
| 2756 * if the AST structure has not been resolved or if this identifier could not
be resolved. | |
| 2757 */ | |
| 2758 final ExecutableElement staticElement; | |
| 2759 | |
| 2760 /** | |
| 2761 * Create the [AuxiliaryElements] with a static and propagated [ExecutableElem
ent]. | |
| 2762 * | |
| 2763 * @param staticElement the static element | |
| 2764 * @param propagatedElement the propagated element | |
| 2765 */ | |
| 2766 AuxiliaryElements(this.staticElement, this.propagatedElement); | |
| 2767 } | |
| 2768 | |
| 2769 /** | |
| 2770 * Instances of the class `ClassElementImpl` implement a `ClassElement`. | |
| 2771 */ | |
| 2772 class ClassElementImpl extends ElementImpl implements ClassElement { | |
| 2773 /** | |
| 2774 * An array containing all of the accessors (getters and setters) contained in
this class. | |
| 2775 */ | |
| 2776 List<PropertyAccessorElement> _accessors = PropertyAccessorElementImpl.EMPTY_A
RRAY; | |
| 2777 | |
| 2778 /** | |
| 2779 * An array containing all of the constructors contained in this class. | |
| 2780 */ | |
| 2781 List<ConstructorElement> _constructors = ConstructorElementImpl.EMPTY_ARRAY; | |
| 2782 | |
| 2783 /** | |
| 2784 * An array containing all of the fields contained in this class. | |
| 2785 */ | |
| 2786 List<FieldElement> _fields = FieldElementImpl.EMPTY_ARRAY; | |
| 2787 | |
| 2788 /** | |
| 2789 * An array containing all of the mixins that are applied to the class being e
xtended in order to | |
| 2790 * derive the superclass of this class. | |
| 2791 */ | |
| 2792 List<InterfaceType> mixins = InterfaceTypeImpl.EMPTY_ARRAY; | |
| 2793 | |
| 2794 /** | |
| 2795 * An array containing all of the interfaces that are implemented by this clas
s. | |
| 2796 */ | |
| 2797 List<InterfaceType> interfaces = InterfaceTypeImpl.EMPTY_ARRAY; | |
| 2798 | |
| 2799 /** | |
| 2800 * An array containing all of the methods contained in this class. | |
| 2801 */ | |
| 2802 List<MethodElement> _methods = MethodElementImpl.EMPTY_ARRAY; | |
| 2803 | |
| 2804 /** | |
| 2805 * The superclass of the class, or `null` if the class does not have an explic
it superclass. | |
| 2806 */ | |
| 2807 InterfaceType supertype; | |
| 2808 | |
| 2809 /** | |
| 2810 * An array containing all of the toolkit objects attached to this class. | |
| 2811 */ | |
| 2812 List<ToolkitObjectElement> _toolkitObjects = ToolkitObjectElement.EMPTY_ARRAY; | |
| 2813 | |
| 2814 /** | |
| 2815 * The type defined by the class. | |
| 2816 */ | |
| 2817 InterfaceType type; | |
| 2818 | |
| 2819 /** | |
| 2820 * An array containing all of the type parameters defined for this class. | |
| 2821 */ | |
| 2822 List<TypeParameterElement> _typeParameters = TypeParameterElementImpl.EMPTY_AR
RAY; | |
| 2823 | |
| 2824 /** | |
| 2825 * An empty array of class elements. | |
| 2826 */ | |
| 2827 static List<ClassElement> EMPTY_ARRAY = new List<ClassElement>(0); | |
| 2828 | |
| 2829 /** | |
| 2830 * Initialize a newly created class element to have the given name. | |
| 2831 * | |
| 2832 * @param name the name of this element | |
| 2833 */ | |
| 2834 ClassElementImpl(Identifier name) : super.forNode(name); | |
| 2835 | |
| 2836 @override | |
| 2837 accept(ElementVisitor visitor) => visitor.visitClassElement(this); | |
| 2838 | |
| 2839 /** | |
| 2840 * Set the toolkit specific information objects attached to this class. | |
| 2841 * | |
| 2842 * @param toolkitObjects the toolkit objects attached to this class | |
| 2843 */ | |
| 2844 void addToolkitObjects(ToolkitObjectElement toolkitObject) { | |
| 2845 (toolkitObject as ToolkitObjectElementImpl).enclosingElement = this; | |
| 2846 _toolkitObjects = ArrayUtils.add(_toolkitObjects, toolkitObject); | |
| 2847 } | |
| 2848 | |
| 2849 @override | |
| 2850 List<PropertyAccessorElement> get accessors => _accessors; | |
| 2851 | |
| 2852 @override | |
| 2853 List<InterfaceType> get allSupertypes { | |
| 2854 List<InterfaceType> list = new List<InterfaceType>(); | |
| 2855 _collectAllSupertypes(list); | |
| 2856 return new List.from(list); | |
| 2857 } | |
| 2858 | |
| 2859 @override | |
| 2860 ElementImpl getChild(String identifier) { | |
| 2861 // | |
| 2862 // The casts in this method are safe because the set methods would have thro
wn a CCE if any of | |
| 2863 // the elements in the arrays were not of the expected types. | |
| 2864 // | |
| 2865 for (PropertyAccessorElement accessor in _accessors) { | |
| 2866 if ((accessor as PropertyAccessorElementImpl).identifier == identifier) { | |
| 2867 return accessor as PropertyAccessorElementImpl; | |
| 2868 } | |
| 2869 } | |
| 2870 for (ConstructorElement constructor in _constructors) { | |
| 2871 if ((constructor as ConstructorElementImpl).identifier == identifier) { | |
| 2872 return constructor as ConstructorElementImpl; | |
| 2873 } | |
| 2874 } | |
| 2875 for (FieldElement field in _fields) { | |
| 2876 if ((field as FieldElementImpl).identifier == identifier) { | |
| 2877 return field as FieldElementImpl; | |
| 2878 } | |
| 2879 } | |
| 2880 for (MethodElement method in _methods) { | |
| 2881 if ((method as MethodElementImpl).identifier == identifier) { | |
| 2882 return method as MethodElementImpl; | |
| 2883 } | |
| 2884 } | |
| 2885 for (TypeParameterElement typeParameter in _typeParameters) { | |
| 2886 if ((typeParameter as TypeParameterElementImpl).identifier == identifier)
{ | |
| 2887 return typeParameter as TypeParameterElementImpl; | |
| 2888 } | |
| 2889 } | |
| 2890 return null; | |
| 2891 } | |
| 2892 | |
| 2893 @override | |
| 2894 List<ConstructorElement> get constructors => _constructors; | |
| 2895 | |
| 2896 @override | |
| 2897 FieldElement getField(String name) { | |
| 2898 for (FieldElement fieldElement in _fields) { | |
| 2899 if (name == fieldElement.name) { | |
| 2900 return fieldElement; | |
| 2901 } | |
| 2902 } | |
| 2903 return null; | |
| 2904 } | |
| 2905 | |
| 2906 @override | |
| 2907 List<FieldElement> get fields => _fields; | |
| 2908 | |
| 2909 @override | |
| 2910 PropertyAccessorElement getGetter(String getterName) { | |
| 2911 for (PropertyAccessorElement accessor in _accessors) { | |
| 2912 if (accessor.isGetter && accessor.name == getterName) { | |
| 2913 return accessor; | |
| 2914 } | |
| 2915 } | |
| 2916 return null; | |
| 2917 } | |
| 2918 | |
| 2919 @override | |
| 2920 ElementKind get kind => ElementKind.CLASS; | |
| 2921 | |
| 2922 @override | |
| 2923 MethodElement getMethod(String methodName) { | |
| 2924 for (MethodElement method in _methods) { | |
| 2925 if (method.name == methodName) { | |
| 2926 return method; | |
| 2927 } | |
| 2928 } | |
| 2929 return null; | |
| 2930 } | |
| 2931 | |
| 2932 @override | |
| 2933 List<MethodElement> get methods => _methods; | |
| 2934 | |
| 2935 @override | |
| 2936 ConstructorElement getNamedConstructor(String name) { | |
| 2937 for (ConstructorElement element in constructors) { | |
| 2938 String elementName = element.name; | |
| 2939 if (elementName != null && elementName == name) { | |
| 2940 return element; | |
| 2941 } | |
| 2942 } | |
| 2943 return null; | |
| 2944 } | |
| 2945 | |
| 2946 @override | |
| 2947 ClassDeclaration get node => getNodeMatching((node) => node is ClassDeclaratio
n); | |
| 2948 | |
| 2949 @override | |
| 2950 PropertyAccessorElement getSetter(String setterName) { | |
| 2951 // TODO (jwren) revisit- should we append '=' here or require clients to inc
lude it? | |
| 2952 // Do we need the check for isSetter below? | |
| 2953 if (!StringUtilities.endsWithChar(setterName, 0x3D)) { | |
| 2954 setterName += '='; | |
| 2955 } | |
| 2956 for (PropertyAccessorElement accessor in _accessors) { | |
| 2957 if (accessor.isSetter && accessor.name == setterName) { | |
| 2958 return accessor; | |
| 2959 } | |
| 2960 } | |
| 2961 return null; | |
| 2962 } | |
| 2963 | |
| 2964 @override | |
| 2965 List<ToolkitObjectElement> get toolkitObjects => _toolkitObjects; | |
| 2966 | |
| 2967 @override | |
| 2968 List<TypeParameterElement> get typeParameters => _typeParameters; | |
| 2969 | |
| 2970 @override | |
| 2971 ConstructorElement get unnamedConstructor { | |
| 2972 for (ConstructorElement element in constructors) { | |
| 2973 String name = element.displayName; | |
| 2974 if (name == null || name.isEmpty) { | |
| 2975 return element; | |
| 2976 } | |
| 2977 } | |
| 2978 return null; | |
| 2979 } | |
| 2980 | |
| 2981 @override | |
| 2982 bool get hasNonFinalField { | |
| 2983 List<ClassElement> classesToVisit = new List<ClassElement>(); | |
| 2984 Set<ClassElement> visitedClasses = new Set<ClassElement>(); | |
| 2985 classesToVisit.add(this); | |
| 2986 while (!classesToVisit.isEmpty) { | |
| 2987 ClassElement currentElement = classesToVisit.removeAt(0); | |
| 2988 if (visitedClasses.add(currentElement)) { | |
| 2989 // check fields | |
| 2990 for (FieldElement field in currentElement.fields) { | |
| 2991 if (!field.isFinal && !field.isConst && !field.isStatic && !field.isSy
nthetic) { | |
| 2992 return true; | |
| 2993 } | |
| 2994 } | |
| 2995 // check mixins | |
| 2996 for (InterfaceType mixinType in currentElement.mixins) { | |
| 2997 ClassElement mixinElement = mixinType.element; | |
| 2998 classesToVisit.add(mixinElement); | |
| 2999 } | |
| 3000 // check super | |
| 3001 InterfaceType supertype = currentElement.supertype; | |
| 3002 if (supertype != null) { | |
| 3003 ClassElement superElement = supertype.element; | |
| 3004 if (superElement != null) { | |
| 3005 classesToVisit.add(superElement); | |
| 3006 } | |
| 3007 } | |
| 3008 } | |
| 3009 } | |
| 3010 // not found | |
| 3011 return false; | |
| 3012 } | |
| 3013 | |
| 3014 @override | |
| 3015 bool get hasReferenceToSuper => hasModifier(Modifier.REFERENCES_SUPER); | |
| 3016 | |
| 3017 @override | |
| 3018 bool get hasStaticMember { | |
| 3019 for (MethodElement method in _methods) { | |
| 3020 if (method.isStatic) { | |
| 3021 return true; | |
| 3022 } | |
| 3023 } | |
| 3024 for (PropertyAccessorElement accessor in _accessors) { | |
| 3025 if (accessor.isStatic) { | |
| 3026 return true; | |
| 3027 } | |
| 3028 } | |
| 3029 return false; | |
| 3030 } | |
| 3031 | |
| 3032 @override | |
| 3033 bool get isAbstract => hasModifier(Modifier.ABSTRACT); | |
| 3034 | |
| 3035 @override | |
| 3036 bool get isOrInheritsProxy => _safeIsOrInheritsProxy(this, new Set<ClassElemen
t>()); | |
| 3037 | |
| 3038 @override | |
| 3039 bool get isProxy { | |
| 3040 for (ElementAnnotation annotation in metadata) { | |
| 3041 if (annotation.isProxy) { | |
| 3042 return true; | |
| 3043 } | |
| 3044 } | |
| 3045 return false; | |
| 3046 } | |
| 3047 | |
| 3048 @override | |
| 3049 bool get isTypedef => hasModifier(Modifier.TYPEDEF); | |
| 3050 | |
| 3051 @override | |
| 3052 bool get isValidMixin => hasModifier(Modifier.MIXIN); | |
| 3053 | |
| 3054 @override | |
| 3055 PropertyAccessorElement lookUpGetter(String getterName, LibraryElement library
) { | |
| 3056 Set<ClassElement> visitedClasses = new Set<ClassElement>(); | |
| 3057 ClassElement currentElement = this; | |
| 3058 while (currentElement != null && !visitedClasses.contains(currentElement)) { | |
| 3059 visitedClasses.add(currentElement); | |
| 3060 PropertyAccessorElement element = currentElement.getGetter(getterName); | |
| 3061 if (element != null && element.isAccessibleIn(library)) { | |
| 3062 return element; | |
| 3063 } | |
| 3064 for (InterfaceType mixin in currentElement.mixins) { | |
| 3065 ClassElement mixinElement = mixin.element; | |
| 3066 if (mixinElement != null) { | |
| 3067 element = mixinElement.getGetter(getterName); | |
| 3068 if (element != null && element.isAccessibleIn(library)) { | |
| 3069 return element; | |
| 3070 } | |
| 3071 } | |
| 3072 } | |
| 3073 InterfaceType supertype = currentElement.supertype; | |
| 3074 if (supertype == null) { | |
| 3075 return null; | |
| 3076 } | |
| 3077 currentElement = supertype.element; | |
| 3078 } | |
| 3079 return null; | |
| 3080 } | |
| 3081 | |
| 3082 @override | |
| 3083 MethodElement lookUpMethod(String methodName, LibraryElement library) { | |
| 3084 Set<ClassElement> visitedClasses = new Set<ClassElement>(); | |
| 3085 ClassElement currentElement = this; | |
| 3086 while (currentElement != null && !visitedClasses.contains(currentElement)) { | |
| 3087 visitedClasses.add(currentElement); | |
| 3088 MethodElement element = currentElement.getMethod(methodName); | |
| 3089 if (element != null && element.isAccessibleIn(library)) { | |
| 3090 return element; | |
| 3091 } | |
| 3092 for (InterfaceType mixin in currentElement.mixins) { | |
| 3093 ClassElement mixinElement = mixin.element; | |
| 3094 if (mixinElement != null) { | |
| 3095 element = mixinElement.getMethod(methodName); | |
| 3096 if (element != null && element.isAccessibleIn(library)) { | |
| 3097 return element; | |
| 3098 } | |
| 3099 } | |
| 3100 } | |
| 3101 InterfaceType supertype = currentElement.supertype; | |
| 3102 if (supertype == null) { | |
| 3103 return null; | |
| 3104 } | |
| 3105 currentElement = supertype.element; | |
| 3106 } | |
| 3107 return null; | |
| 3108 } | |
| 3109 | |
| 3110 @override | |
| 3111 PropertyAccessorElement lookUpSetter(String setterName, LibraryElement library
) { | |
| 3112 Set<ClassElement> visitedClasses = new Set<ClassElement>(); | |
| 3113 ClassElement currentElement = this; | |
| 3114 while (currentElement != null && !visitedClasses.contains(currentElement)) { | |
| 3115 visitedClasses.add(currentElement); | |
| 3116 PropertyAccessorElement element = currentElement.getSetter(setterName); | |
| 3117 if (element != null && element.isAccessibleIn(library)) { | |
| 3118 return element; | |
| 3119 } | |
| 3120 for (InterfaceType mixin in currentElement.mixins) { | |
| 3121 ClassElement mixinElement = mixin.element; | |
| 3122 if (mixinElement != null) { | |
| 3123 element = mixinElement.getSetter(setterName); | |
| 3124 if (element != null && element.isAccessibleIn(library)) { | |
| 3125 return element; | |
| 3126 } | |
| 3127 } | |
| 3128 } | |
| 3129 InterfaceType supertype = currentElement.supertype; | |
| 3130 if (supertype == null) { | |
| 3131 return null; | |
| 3132 } | |
| 3133 currentElement = supertype.element; | |
| 3134 } | |
| 3135 return null; | |
| 3136 } | |
| 3137 | |
| 3138 /** | |
| 3139 * Set whether this class is abstract to correspond to the given value. | |
| 3140 * | |
| 3141 * @param isAbstract `true` if the class is abstract | |
| 3142 */ | |
| 3143 void set abstract(bool isAbstract) { | |
| 3144 setModifier(Modifier.ABSTRACT, isAbstract); | |
| 3145 } | |
| 3146 | |
| 3147 /** | |
| 3148 * Set the accessors contained in this class to the given accessors. | |
| 3149 * | |
| 3150 * @param accessors the accessors contained in this class | |
| 3151 */ | |
| 3152 void set accessors(List<PropertyAccessorElement> accessors) { | |
| 3153 for (PropertyAccessorElement accessor in accessors) { | |
| 3154 (accessor as PropertyAccessorElementImpl).enclosingElement = this; | |
| 3155 } | |
| 3156 this._accessors = accessors; | |
| 3157 } | |
| 3158 | |
| 3159 /** | |
| 3160 * Set the constructors contained in this class to the given constructors. | |
| 3161 * | |
| 3162 * @param constructors the constructors contained in this class | |
| 3163 */ | |
| 3164 void set constructors(List<ConstructorElement> constructors) { | |
| 3165 for (ConstructorElement constructor in constructors) { | |
| 3166 (constructor as ConstructorElementImpl).enclosingElement = this; | |
| 3167 } | |
| 3168 this._constructors = constructors; | |
| 3169 } | |
| 3170 | |
| 3171 /** | |
| 3172 * Set the fields contained in this class to the given fields. | |
| 3173 * | |
| 3174 * @param fields the fields contained in this class | |
| 3175 */ | |
| 3176 void set fields(List<FieldElement> fields) { | |
| 3177 for (FieldElement field in fields) { | |
| 3178 (field as FieldElementImpl).enclosingElement = this; | |
| 3179 } | |
| 3180 this._fields = fields; | |
| 3181 } | |
| 3182 | |
| 3183 /** | |
| 3184 * Set whether this class references 'super' to the given value. | |
| 3185 * | |
| 3186 * @param isReferencedSuper `true` references 'super' | |
| 3187 */ | |
| 3188 void set hasReferenceToSuper(bool isReferencedSuper) { | |
| 3189 setModifier(Modifier.REFERENCES_SUPER, isReferencedSuper); | |
| 3190 } | |
| 3191 | |
| 3192 /** | |
| 3193 * Set the methods contained in this class to the given methods. | |
| 3194 * | |
| 3195 * @param methods the methods contained in this class | |
| 3196 */ | |
| 3197 void set methods(List<MethodElement> methods) { | |
| 3198 for (MethodElement method in methods) { | |
| 3199 (method as MethodElementImpl).enclosingElement = this; | |
| 3200 } | |
| 3201 this._methods = methods; | |
| 3202 } | |
| 3203 | |
| 3204 /** | |
| 3205 * Set whether this class is defined by a typedef construct to correspond to t
he given value. | |
| 3206 * | |
| 3207 * @param isTypedef `true` if the class is defined by a typedef construct | |
| 3208 */ | |
| 3209 void set typedef(bool isTypedef) { | |
| 3210 setModifier(Modifier.TYPEDEF, isTypedef); | |
| 3211 } | |
| 3212 | |
| 3213 /** | |
| 3214 * Set the type parameters defined for this class to the given type parameters
. | |
| 3215 * | |
| 3216 * @param typeParameters the type parameters defined for this class | |
| 3217 */ | |
| 3218 void set typeParameters(List<TypeParameterElement> typeParameters) { | |
| 3219 for (TypeParameterElement typeParameter in typeParameters) { | |
| 3220 (typeParameter as TypeParameterElementImpl).enclosingElement = this; | |
| 3221 } | |
| 3222 this._typeParameters = typeParameters; | |
| 3223 } | |
| 3224 | |
| 3225 /** | |
| 3226 * Set whether this class is a valid mixin to correspond to the given value. | |
| 3227 * | |
| 3228 * @param isValidMixin `true` if this class can be used as a mixin | |
| 3229 */ | |
| 3230 void set validMixin(bool isValidMixin) { | |
| 3231 setModifier(Modifier.MIXIN, isValidMixin); | |
| 3232 } | |
| 3233 | |
| 3234 @override | |
| 3235 void visitChildren(ElementVisitor visitor) { | |
| 3236 super.visitChildren(visitor); | |
| 3237 safelyVisitChildren(_accessors, visitor); | |
| 3238 safelyVisitChildren(_constructors, visitor); | |
| 3239 safelyVisitChildren(_fields, visitor); | |
| 3240 safelyVisitChildren(_methods, visitor); | |
| 3241 safelyVisitChildren(_toolkitObjects, visitor); | |
| 3242 safelyVisitChildren(_typeParameters, visitor); | |
| 3243 } | 5661 } |
| 3244 | 5662 |
| 3245 @override | 5663 @override |
| 3246 void appendTo(JavaStringBuilder builder) { | 5664 void appendTo(JavaStringBuilder builder) { |
| 3247 String name = displayName; | 5665 builder.append("["); |
| 3248 if (name == null) { | 5666 builder.append(name); |
| 3249 builder.append("{unnamed class}"); | 5667 builder.append("]"); |
| 3250 } else { | 5668 } |
| 3251 builder.append(name); | 5669 } |
| 3252 } | 5670 |
| 3253 int variableCount = _typeParameters.length; | 5671 /** |
| 3254 if (variableCount > 0) { | 5672 * The interface `HideElementCombinator` defines the behavior of combinators tha
t cause some |
| 3255 builder.append("<"); | 5673 * of the names in a namespace to be hidden when being imported. |
| 3256 for (int i = 0; i < variableCount; i++) { | 5674 */ |
| 3257 if (i > 0) { | 5675 abstract class HideElementCombinator implements NamespaceCombinator { |
| 3258 builder.append(", "); | 5676 /** |
| 3259 } | 5677 * Return an array containing the names that are not to be made visible in the
importing library |
| 3260 (_typeParameters[i] as TypeParameterElementImpl).appendTo(builder); | 5678 * even if they are defined in the imported library. |
| 3261 } | 5679 * |
| 3262 builder.append(">"); | 5680 * @return the names from the imported library that are hidden from the import
ing library |
| 3263 } | 5681 */ |
| 3264 } | 5682 List<String> get hiddenNames; |
| 3265 | |
| 3266 void _collectAllSupertypes(List<InterfaceType> supertypes) { | |
| 3267 List<InterfaceType> typesToVisit = new List<InterfaceType>(); | |
| 3268 List<ClassElement> visitedClasses = new List<ClassElement>(); | |
| 3269 typesToVisit.add(this.type); | |
| 3270 while (!typesToVisit.isEmpty) { | |
| 3271 InterfaceType currentType = typesToVisit.removeAt(0); | |
| 3272 ClassElement currentElement = currentType.element; | |
| 3273 if (!visitedClasses.contains(currentElement)) { | |
| 3274 visitedClasses.add(currentElement); | |
| 3275 if (!identical(currentType, this.type)) { | |
| 3276 supertypes.add(currentType); | |
| 3277 } | |
| 3278 InterfaceType supertype = currentType.superclass; | |
| 3279 if (supertype != null) { | |
| 3280 typesToVisit.add(supertype); | |
| 3281 } | |
| 3282 for (InterfaceType type in currentElement.interfaces) { | |
| 3283 typesToVisit.add(type); | |
| 3284 } | |
| 3285 for (InterfaceType type in currentElement.mixins) { | |
| 3286 ClassElement element = type.element; | |
| 3287 if (!visitedClasses.contains(element)) { | |
| 3288 supertypes.add(type); | |
| 3289 } | |
| 3290 } | |
| 3291 } | |
| 3292 } | |
| 3293 } | |
| 3294 | |
| 3295 bool _safeIsOrInheritsProxy(ClassElement classElt, Set<ClassElement> visitedCl
assElts) { | |
| 3296 if (visitedClassElts.contains(classElt)) { | |
| 3297 return false; | |
| 3298 } | |
| 3299 visitedClassElts.add(classElt); | |
| 3300 if (classElt.isProxy) { | |
| 3301 return true; | |
| 3302 } else if (classElt.supertype != null && _safeIsOrInheritsProxy(classElt.sup
ertype.element, visitedClassElts)) { | |
| 3303 return true; | |
| 3304 } | |
| 3305 List<InterfaceType> supertypes = classElt.interfaces; | |
| 3306 for (int i = 0; i < supertypes.length; i++) { | |
| 3307 if (_safeIsOrInheritsProxy(supertypes[i].element, visitedClassElts)) { | |
| 3308 return true; | |
| 3309 } | |
| 3310 } | |
| 3311 supertypes = classElt.mixins; | |
| 3312 for (int i = 0; i < supertypes.length; i++) { | |
| 3313 if (_safeIsOrInheritsProxy(supertypes[i].element, visitedClassElts)) { | |
| 3314 return true; | |
| 3315 } | |
| 3316 } | |
| 3317 return false; | |
| 3318 } | |
| 3319 } | |
| 3320 | |
| 3321 /** | |
| 3322 * Instances of the class `CompilationUnitElementImpl` implement a | |
| 3323 * [CompilationUnitElement]. | |
| 3324 */ | |
| 3325 class CompilationUnitElementImpl extends UriReferencedElementImpl implements Com
pilationUnitElement { | |
| 3326 /** | |
| 3327 * An empty array of compilation unit elements. | |
| 3328 */ | |
| 3329 static List<CompilationUnitElement> EMPTY_ARRAY = new List<CompilationUnitElem
ent>(0); | |
| 3330 | |
| 3331 /** | |
| 3332 * The source that corresponds to this compilation unit. | |
| 3333 */ | |
| 3334 Source source; | |
| 3335 | |
| 3336 /** | |
| 3337 * An array containing all of the top-level accessors (getters and setters) co
ntained in this | |
| 3338 * compilation unit. | |
| 3339 */ | |
| 3340 List<PropertyAccessorElement> _accessors = PropertyAccessorElementImpl.EMPTY_A
RRAY; | |
| 3341 | |
| 3342 /** | |
| 3343 * An array containing all of the top-level functions contained in this compil
ation unit. | |
| 3344 */ | |
| 3345 List<FunctionElement> _functions = FunctionElementImpl.EMPTY_ARRAY; | |
| 3346 | |
| 3347 /** | |
| 3348 * A table mapping elements to associated toolkit objects. | |
| 3349 */ | |
| 3350 Map<Element, List<ToolkitObjectElement>> _toolkitObjects = {}; | |
| 3351 | |
| 3352 /** | |
| 3353 * An array containing all of the function type aliases contained in this comp
ilation unit. | |
| 3354 */ | |
| 3355 List<FunctionTypeAliasElement> _typeAliases = FunctionTypeAliasElementImpl.EMP
TY_ARRAY; | |
| 3356 | |
| 3357 /** | |
| 3358 * An array containing all of the types contained in this compilation unit. | |
| 3359 */ | |
| 3360 List<ClassElement> _types = ClassElementImpl.EMPTY_ARRAY; | |
| 3361 | |
| 3362 /** | |
| 3363 * An array containing all of the variables contained in this compilation unit
. | |
| 3364 */ | |
| 3365 List<TopLevelVariableElement> _variables = TopLevelVariableElementImpl.EMPTY_A
RRAY; | |
| 3366 | |
| 3367 /** | |
| 3368 * An array containing all of the Angular views contained in this compilation
unit. | |
| 3369 */ | |
| 3370 List<AngularViewElement> _angularViews = AngularViewElement.EMPTY_ARRAY; | |
| 3371 | |
| 3372 /** | |
| 3373 * Initialize a newly created compilation unit element to have the given name. | |
| 3374 * | |
| 3375 * @param name the name of this element | |
| 3376 */ | |
| 3377 CompilationUnitElementImpl(String name) : super(name, -1); | |
| 3378 | |
| 3379 @override | |
| 3380 accept(ElementVisitor visitor) => visitor.visitCompilationUnitElement(this); | |
| 3381 | |
| 3382 @override | |
| 3383 bool operator ==(Object object) => object != null && runtimeType == object.run
timeType && source == (object as CompilationUnitElementImpl).source; | |
| 3384 | |
| 3385 @override | |
| 3386 List<PropertyAccessorElement> get accessors => _accessors; | |
| 3387 | |
| 3388 @override | |
| 3389 List<AngularViewElement> get angularViews => _angularViews; | |
| 3390 | |
| 3391 @override | |
| 3392 ElementImpl getChild(String identifier) { | |
| 3393 // | |
| 3394 // The casts in this method are safe because the set methods would have thro
wn a CCE if any of | |
| 3395 // the elements in the arrays were not of the expected types. | |
| 3396 // | |
| 3397 for (PropertyAccessorElement accessor in _accessors) { | |
| 3398 if ((accessor as PropertyAccessorElementImpl).identifier == identifier) { | |
| 3399 return accessor as PropertyAccessorElementImpl; | |
| 3400 } | |
| 3401 } | |
| 3402 for (VariableElement variable in _variables) { | |
| 3403 if ((variable as VariableElementImpl).identifier == identifier) { | |
| 3404 return variable as VariableElementImpl; | |
| 3405 } | |
| 3406 } | |
| 3407 for (ExecutableElement function in _functions) { | |
| 3408 if ((function as ExecutableElementImpl).identifier == identifier) { | |
| 3409 return function as ExecutableElementImpl; | |
| 3410 } | |
| 3411 } | |
| 3412 for (FunctionTypeAliasElement typeAlias in _typeAliases) { | |
| 3413 if ((typeAlias as FunctionTypeAliasElementImpl).identifier == identifier)
{ | |
| 3414 return typeAlias as FunctionTypeAliasElementImpl; | |
| 3415 } | |
| 3416 } | |
| 3417 for (ClassElement type in _types) { | |
| 3418 if ((type as ClassElementImpl).identifier == identifier) { | |
| 3419 return type as ClassElementImpl; | |
| 3420 } | |
| 3421 } | |
| 3422 return null; | |
| 3423 } | |
| 3424 | |
| 3425 @override | |
| 3426 LibraryElement get enclosingElement => super.enclosingElement as LibraryElemen
t; | |
| 3427 | |
| 3428 @override | |
| 3429 List<FunctionElement> get functions => _functions; | |
| 3430 | |
| 3431 @override | |
| 3432 List<FunctionTypeAliasElement> get functionTypeAliases => _typeAliases; | |
| 3433 | |
| 3434 @override | |
| 3435 ElementKind get kind => ElementKind.COMPILATION_UNIT; | |
| 3436 | |
| 3437 @override | |
| 3438 CompilationUnit get node => unit; | |
| 3439 | |
| 3440 @override | |
| 3441 List<TopLevelVariableElement> get topLevelVariables => _variables; | |
| 3442 | |
| 3443 @override | |
| 3444 ClassElement getType(String className) { | |
| 3445 for (ClassElement type in _types) { | |
| 3446 if (type.name == className) { | |
| 3447 return type; | |
| 3448 } | |
| 3449 } | |
| 3450 return null; | |
| 3451 } | |
| 3452 | |
| 3453 @override | |
| 3454 List<ClassElement> get types => _types; | |
| 3455 | |
| 3456 @override | |
| 3457 int get hashCode => source.hashCode; | |
| 3458 | |
| 3459 @override | |
| 3460 bool get hasLoadLibraryFunction { | |
| 3461 for (int i = 0; i < _functions.length; i++) { | |
| 3462 if (_functions[i].name == FunctionElement.LOAD_LIBRARY_NAME) { | |
| 3463 return true; | |
| 3464 } | |
| 3465 } | |
| 3466 return false; | |
| 3467 } | |
| 3468 | |
| 3469 /** | |
| 3470 * Set the top-level accessors (getters and setters) contained in this compila
tion unit to the | |
| 3471 * given accessors. | |
| 3472 * | |
| 3473 * @param the top-level accessors (getters and setters) contained in this comp
ilation unit | |
| 3474 */ | |
| 3475 void set accessors(List<PropertyAccessorElement> accessors) { | |
| 3476 for (PropertyAccessorElement accessor in accessors) { | |
| 3477 (accessor as PropertyAccessorElementImpl).enclosingElement = this; | |
| 3478 } | |
| 3479 this._accessors = accessors; | |
| 3480 } | |
| 3481 | |
| 3482 /** | |
| 3483 * Set the Angular views defined in this compilation unit. | |
| 3484 * | |
| 3485 * @param angularViews the Angular views defined in this compilation unit | |
| 3486 */ | |
| 3487 void set angularViews(List<AngularViewElement> angularViews) { | |
| 3488 for (AngularViewElement view in angularViews) { | |
| 3489 (view as AngularViewElementImpl).enclosingElement = this; | |
| 3490 } | |
| 3491 this._angularViews = angularViews; | |
| 3492 } | |
| 3493 | |
| 3494 /** | |
| 3495 * Set the top-level functions contained in this compilation unit to the given
functions. | |
| 3496 * | |
| 3497 * @param functions the top-level functions contained in this compilation unit | |
| 3498 */ | |
| 3499 void set functions(List<FunctionElement> functions) { | |
| 3500 for (FunctionElement function in functions) { | |
| 3501 (function as FunctionElementImpl).enclosingElement = this; | |
| 3502 } | |
| 3503 this._functions = functions; | |
| 3504 } | |
| 3505 | |
| 3506 /** | |
| 3507 * Set the top-level variables contained in this compilation unit to the given
variables. | |
| 3508 * | |
| 3509 * @param variables the top-level variables contained in this compilation unit | |
| 3510 */ | |
| 3511 void set topLevelVariables(List<TopLevelVariableElement> variables) { | |
| 3512 for (TopLevelVariableElement field in variables) { | |
| 3513 (field as TopLevelVariableElementImpl).enclosingElement = this; | |
| 3514 } | |
| 3515 this._variables = variables; | |
| 3516 } | |
| 3517 | |
| 3518 /** | |
| 3519 * Set the function type aliases contained in this compilation unit to the giv
en type aliases. | |
| 3520 * | |
| 3521 * @param typeAliases the function type aliases contained in this compilation
unit | |
| 3522 */ | |
| 3523 void set typeAliases(List<FunctionTypeAliasElement> typeAliases) { | |
| 3524 for (FunctionTypeAliasElement typeAlias in typeAliases) { | |
| 3525 (typeAlias as FunctionTypeAliasElementImpl).enclosingElement = this; | |
| 3526 } | |
| 3527 this._typeAliases = typeAliases; | |
| 3528 } | |
| 3529 | |
| 3530 /** | |
| 3531 * Set the types contained in this compilation unit to the given types. | |
| 3532 * | |
| 3533 * @param types types contained in this compilation unit | |
| 3534 */ | |
| 3535 void set types(List<ClassElement> types) { | |
| 3536 for (ClassElement type in types) { | |
| 3537 (type as ClassElementImpl).enclosingElement = this; | |
| 3538 } | |
| 3539 this._types = types; | |
| 3540 } | |
| 3541 | |
| 3542 @override | |
| 3543 void visitChildren(ElementVisitor visitor) { | |
| 3544 super.visitChildren(visitor); | |
| 3545 safelyVisitChildren(_accessors, visitor); | |
| 3546 safelyVisitChildren(_functions, visitor); | |
| 3547 safelyVisitChildren(_typeAliases, visitor); | |
| 3548 safelyVisitChildren(_types, visitor); | |
| 3549 safelyVisitChildren(_variables, visitor); | |
| 3550 safelyVisitChildren(_angularViews, visitor); | |
| 3551 } | |
| 3552 | |
| 3553 @override | |
| 3554 void appendTo(JavaStringBuilder builder) { | |
| 3555 if (source == null) { | |
| 3556 builder.append("{compilation unit}"); | |
| 3557 } else { | |
| 3558 builder.append(source.fullName); | |
| 3559 } | |
| 3560 } | |
| 3561 | |
| 3562 @override | |
| 3563 String get identifier => source.encoding; | |
| 3564 | |
| 3565 /** | |
| 3566 * Returns the associated toolkit objects. | |
| 3567 * | |
| 3568 * @param element the [Element] to get toolkit objects for | |
| 3569 * @return the associated toolkit objects, may be empty, but not `null` | |
| 3570 */ | |
| 3571 List<ToolkitObjectElement> _getToolkitObjects(Element element) { | |
| 3572 List<ToolkitObjectElement> objects = _toolkitObjects[element]; | |
| 3573 if (objects != null) { | |
| 3574 return objects; | |
| 3575 } | |
| 3576 return ToolkitObjectElement.EMPTY_ARRAY; | |
| 3577 } | |
| 3578 | |
| 3579 /** | |
| 3580 * Sets the toolkit objects that are associated with the given [Element]. | |
| 3581 * | |
| 3582 * @param element the [Element] to associate toolkit objects with | |
| 3583 * @param objects the toolkit objects to associate | |
| 3584 */ | |
| 3585 void _setToolkitObjects(Element element, List<ToolkitObjectElement> objects) { | |
| 3586 _toolkitObjects[element] = objects; | |
| 3587 } | |
| 3588 } | |
| 3589 | |
| 3590 /** | |
| 3591 * Instances of the class `ConstFieldElementImpl` implement a `FieldElement` for
a | |
| 3592 * 'const' field that has an initializer. | |
| 3593 */ | |
| 3594 class ConstFieldElementImpl extends FieldElementImpl { | |
| 3595 /** | |
| 3596 * The result of evaluating this variable's initializer. | |
| 3597 */ | |
| 3598 EvaluationResultImpl _result; | |
| 3599 | |
| 3600 /** | |
| 3601 * Initialize a newly created field element to have the given name. | |
| 3602 * | |
| 3603 * @param name the name of this element | |
| 3604 */ | |
| 3605 ConstFieldElementImpl(Identifier name) : super.con1(name); | |
| 3606 | |
| 3607 @override | |
| 3608 EvaluationResultImpl get evaluationResult => _result; | |
| 3609 | |
| 3610 @override | |
| 3611 void set evaluationResult(EvaluationResultImpl result) { | |
| 3612 this._result = result; | |
| 3613 } | |
| 3614 } | |
| 3615 | |
| 3616 /** | |
| 3617 * Instances of the class `ConstLocalVariableElementImpl` implement a | |
| 3618 * `LocalVariableElement` for a local 'const' variable that has an initializer. | |
| 3619 */ | |
| 3620 class ConstLocalVariableElementImpl extends LocalVariableElementImpl { | |
| 3621 /** | |
| 3622 * The result of evaluating this variable's initializer. | |
| 3623 */ | |
| 3624 EvaluationResultImpl _result; | |
| 3625 | |
| 3626 /** | |
| 3627 * Initialize a newly created local variable element to have the given name. | |
| 3628 * | |
| 3629 * @param name the name of this element | |
| 3630 */ | |
| 3631 ConstLocalVariableElementImpl(Identifier name) : super(name); | |
| 3632 | |
| 3633 @override | |
| 3634 EvaluationResultImpl get evaluationResult => _result; | |
| 3635 | |
| 3636 @override | |
| 3637 void set evaluationResult(EvaluationResultImpl result) { | |
| 3638 this._result = result; | |
| 3639 } | |
| 3640 } | |
| 3641 | |
| 3642 /** | |
| 3643 * Instances of the class `ConstTopLevelVariableElementImpl` implement a | |
| 3644 * `TopLevelVariableElement` for a top-level 'const' variable that has an initia
lizer. | |
| 3645 */ | |
| 3646 class ConstTopLevelVariableElementImpl extends TopLevelVariableElementImpl { | |
| 3647 /** | |
| 3648 * The result of evaluating this variable's initializer. | |
| 3649 */ | |
| 3650 EvaluationResultImpl _result; | |
| 3651 | |
| 3652 /** | |
| 3653 * Initialize a newly created top-level variable element to have the given nam
e. | |
| 3654 * | |
| 3655 * @param name the name of this element | |
| 3656 */ | |
| 3657 ConstTopLevelVariableElementImpl(Identifier name) : super.con1(name); | |
| 3658 | |
| 3659 @override | |
| 3660 EvaluationResultImpl get evaluationResult => _result; | |
| 3661 | |
| 3662 @override | |
| 3663 void set evaluationResult(EvaluationResultImpl result) { | |
| 3664 this._result = result; | |
| 3665 } | |
| 3666 } | |
| 3667 | |
| 3668 /** | |
| 3669 * Instances of the class `ConstructorElementImpl` implement a `ConstructorEleme
nt`. | |
| 3670 */ | |
| 3671 class ConstructorElementImpl extends ExecutableElementImpl implements Constructo
rElement { | |
| 3672 /** | |
| 3673 * An empty array of constructor elements. | |
| 3674 */ | |
| 3675 static List<ConstructorElement> EMPTY_ARRAY = new List<ConstructorElement>(0); | |
| 3676 | |
| 3677 /** | |
| 3678 * The constructor to which this constructor is redirecting. | |
| 3679 */ | |
| 3680 ConstructorElement redirectedConstructor; | |
| 3681 | |
| 3682 /** | |
| 3683 * Initialize a newly created constructor element to have the given name. | |
| 3684 * | |
| 3685 * @param name the name of this element | |
| 3686 */ | |
| 3687 ConstructorElementImpl.forNode(Identifier name) : super.forNode(name); | |
| 3688 | |
| 3689 /** | |
| 3690 * Initialize a newly created constructor element to have the given name. | |
| 3691 * | |
| 3692 * @param name the name of this element | |
| 3693 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 3694 * declaration of this element | |
| 3695 */ | |
| 3696 ConstructorElementImpl(String name, int nameOffset) : super(name, nameOffset); | |
| 3697 | |
| 3698 @override | |
| 3699 accept(ElementVisitor visitor) => visitor.visitConstructorElement(this); | |
| 3700 | |
| 3701 @override | |
| 3702 ClassElement get enclosingElement => super.enclosingElement as ClassElement; | |
| 3703 | |
| 3704 @override | |
| 3705 ElementKind get kind => ElementKind.CONSTRUCTOR; | |
| 3706 | |
| 3707 @override | |
| 3708 ConstructorDeclaration get node => getNodeMatching((node) => node is Construct
orDeclaration); | |
| 3709 | |
| 3710 @override | |
| 3711 bool get isConst => hasModifier(Modifier.CONST); | |
| 3712 | |
| 3713 @override | |
| 3714 bool get isDefaultConstructor { | |
| 3715 // unnamed | |
| 3716 String name = this.name; | |
| 3717 if (name != null && name.length != 0) { | |
| 3718 return false; | |
| 3719 } | |
| 3720 // no required parameters | |
| 3721 for (ParameterElement parameter in parameters) { | |
| 3722 if (parameter.parameterKind == ParameterKind.REQUIRED) { | |
| 3723 return false; | |
| 3724 } | |
| 3725 } | |
| 3726 // OK, can be used as default constructor | |
| 3727 return true; | |
| 3728 } | |
| 3729 | |
| 3730 @override | |
| 3731 bool get isFactory => hasModifier(Modifier.FACTORY); | |
| 3732 | |
| 3733 @override | |
| 3734 bool get isStatic => false; | |
| 3735 | |
| 3736 /** | |
| 3737 * Set whether this constructor represents a 'const' constructor to the given
value. | |
| 3738 * | |
| 3739 * @param isConst `true` if this constructor represents a 'const' constructor | |
| 3740 */ | |
| 3741 void set const2(bool isConst) { | |
| 3742 setModifier(Modifier.CONST, isConst); | |
| 3743 } | |
| 3744 | |
| 3745 /** | |
| 3746 * Set whether this constructor represents a factory method to the given value
. | |
| 3747 * | |
| 3748 * @param isFactory `true` if this constructor represents a factory method | |
| 3749 */ | |
| 3750 void set factory(bool isFactory) { | |
| 3751 setModifier(Modifier.FACTORY, isFactory); | |
| 3752 } | |
| 3753 | |
| 3754 @override | |
| 3755 void appendTo(JavaStringBuilder builder) { | |
| 3756 builder.append(enclosingElement.displayName); | |
| 3757 String name = displayName; | |
| 3758 if (name != null && !name.isEmpty) { | |
| 3759 builder.append("."); | |
| 3760 builder.append(name); | |
| 3761 } | |
| 3762 super.appendTo(builder); | |
| 3763 } | |
| 3764 } | |
| 3765 | |
| 3766 /** | |
| 3767 * Instances of the class `DefaultFieldFormalParameterElementImpl` implement a | |
| 3768 * `FieldFormalParameterElementImpl` for parameters that have an initializer. | |
| 3769 */ | |
| 3770 class DefaultFieldFormalParameterElementImpl extends FieldFormalParameterElement
Impl { | |
| 3771 /** | |
| 3772 * The result of evaluating this variable's initializer. | |
| 3773 */ | |
| 3774 EvaluationResultImpl _result; | |
| 3775 | |
| 3776 /** | |
| 3777 * Initialize a newly created parameter element to have the given name. | |
| 3778 * | |
| 3779 * @param name the name of this element | |
| 3780 */ | |
| 3781 DefaultFieldFormalParameterElementImpl(Identifier name) : super(name); | |
| 3782 | |
| 3783 @override | |
| 3784 EvaluationResultImpl get evaluationResult => _result; | |
| 3785 | |
| 3786 @override | |
| 3787 void set evaluationResult(EvaluationResultImpl result) { | |
| 3788 this._result = result; | |
| 3789 } | |
| 3790 } | |
| 3791 | |
| 3792 /** | |
| 3793 * Instances of the class `DefaultParameterElementImpl` implement a `ParameterEl
ement` | |
| 3794 * for parameters that have an initializer. | |
| 3795 */ | |
| 3796 class DefaultParameterElementImpl extends ParameterElementImpl { | |
| 3797 /** | |
| 3798 * The result of evaluating this variable's initializer. | |
| 3799 */ | |
| 3800 EvaluationResultImpl _result; | |
| 3801 | |
| 3802 /** | |
| 3803 * Initialize a newly created parameter element to have the given name. | |
| 3804 * | |
| 3805 * @param name the name of this element | |
| 3806 */ | |
| 3807 DefaultParameterElementImpl(Identifier name) : super.con1(name); | |
| 3808 | |
| 3809 @override | |
| 3810 EvaluationResultImpl get evaluationResult => _result; | |
| 3811 | |
| 3812 @override | |
| 3813 void set evaluationResult(EvaluationResultImpl result) { | |
| 3814 this._result = result; | |
| 3815 } | |
| 3816 } | |
| 3817 | |
| 3818 /** | |
| 3819 * Instances of the class `DynamicElementImpl` represent the synthetic element r
epresenting | |
| 3820 * the declaration of the type `dynamic`. | |
| 3821 */ | |
| 3822 class DynamicElementImpl extends ElementImpl { | |
| 3823 /** | |
| 3824 * Return the unique instance of this class. | |
| 3825 * | |
| 3826 * @return the unique instance of this class | |
| 3827 */ | |
| 3828 static DynamicElementImpl get instance => DynamicTypeImpl.instance.element as
DynamicElementImpl; | |
| 3829 | |
| 3830 /** | |
| 3831 * The type defined by this element. | |
| 3832 */ | |
| 3833 DynamicTypeImpl type; | |
| 3834 | |
| 3835 /** | |
| 3836 * Initialize a newly created instance of this class. Instances of this class
should <b>not</b> be | |
| 3837 * created except as part of creating the type associated with this element. T
he single instance | |
| 3838 * of this class should be accessed through the method [getInstance]. | |
| 3839 */ | |
| 3840 DynamicElementImpl() : super(Keyword.DYNAMIC.syntax, -1) { | |
| 3841 setModifier(Modifier.SYNTHETIC, true); | |
| 3842 } | |
| 3843 | |
| 3844 @override | |
| 3845 accept(ElementVisitor visitor) => null; | |
| 3846 | |
| 3847 @override | |
| 3848 ElementKind get kind => ElementKind.DYNAMIC; | |
| 3849 } | |
| 3850 | |
| 3851 /** | |
| 3852 * Instances of the class `ElementAnnotationImpl` implement an [ElementAnnotatio
n]. | |
| 3853 */ | |
| 3854 class ElementAnnotationImpl implements ElementAnnotation { | |
| 3855 /** | |
| 3856 * The element representing the field, variable, or constructor being used as
an annotation. | |
| 3857 */ | |
| 3858 final Element element; | |
| 3859 | |
| 3860 /** | |
| 3861 * An empty array of annotations. | |
| 3862 */ | |
| 3863 static List<ElementAnnotationImpl> EMPTY_ARRAY = new List<ElementAnnotationImp
l>(0); | |
| 3864 | |
| 3865 /** | |
| 3866 * The name of the class used to mark an element as being deprecated. | |
| 3867 */ | |
| 3868 static String _DEPRECATED_CLASS_NAME = "Deprecated"; | |
| 3869 | |
| 3870 /** | |
| 3871 * The name of the top-level variable used to mark an element as being depreca
ted. | |
| 3872 */ | |
| 3873 static String _DEPRECATED_VARIABLE_NAME = "deprecated"; | |
| 3874 | |
| 3875 /** | |
| 3876 * The name of the top-level variable used to mark a method as being expected
to override an | |
| 3877 * inherited method. | |
| 3878 */ | |
| 3879 static String _OVERRIDE_VARIABLE_NAME = "override"; | |
| 3880 | |
| 3881 /** | |
| 3882 * The name of the top-level variable used to mark a class as implementing a p
roxy object. | |
| 3883 */ | |
| 3884 static String PROXY_VARIABLE_NAME = "proxy"; | |
| 3885 | |
| 3886 /** | |
| 3887 * Initialize a newly created annotation. | |
| 3888 * | |
| 3889 * @param element the element representing the field, variable, or constructor
being used as an | |
| 3890 * annotation | |
| 3891 */ | |
| 3892 ElementAnnotationImpl(this.element); | |
| 3893 | |
| 3894 @override | |
| 3895 bool get isDeprecated { | |
| 3896 if (element != null) { | |
| 3897 LibraryElement library = element.library; | |
| 3898 if (library != null && library.isDartCore) { | |
| 3899 if (element is ConstructorElement) { | |
| 3900 ConstructorElement constructorElement = element as ConstructorElement; | |
| 3901 if (constructorElement.enclosingElement.name == _DEPRECATED_CLASS_NAME
) { | |
| 3902 return true; | |
| 3903 } | |
| 3904 } else if (element is PropertyAccessorElement && element.name == _DEPREC
ATED_VARIABLE_NAME) { | |
| 3905 return true; | |
| 3906 } | |
| 3907 } | |
| 3908 } | |
| 3909 return false; | |
| 3910 } | |
| 3911 | |
| 3912 @override | |
| 3913 bool get isOverride { | |
| 3914 if (element != null) { | |
| 3915 LibraryElement library = element.library; | |
| 3916 if (library != null && library.isDartCore) { | |
| 3917 if (element is PropertyAccessorElement && element.name == _OVERRIDE_VARI
ABLE_NAME) { | |
| 3918 return true; | |
| 3919 } | |
| 3920 } | |
| 3921 } | |
| 3922 return false; | |
| 3923 } | |
| 3924 | |
| 3925 @override | |
| 3926 bool get isProxy { | |
| 3927 if (element != null) { | |
| 3928 LibraryElement library = element.library; | |
| 3929 if (library != null && library.isDartCore) { | |
| 3930 if (element is PropertyAccessorElement && element.name == PROXY_VARIABLE
_NAME) { | |
| 3931 return true; | |
| 3932 } | |
| 3933 } | |
| 3934 } | |
| 3935 return false; | |
| 3936 } | |
| 3937 | |
| 3938 @override | |
| 3939 String toString() => "@${element.toString()}"; | |
| 3940 } | |
| 3941 | |
| 3942 /** | |
| 3943 * The abstract class `ElementImpl` implements the behavior common to objects th
at implement | |
| 3944 * an [Element]. | |
| 3945 */ | |
| 3946 abstract class ElementImpl implements Element { | |
| 3947 /** | |
| 3948 * The enclosing element of this element, or `null` if this element is at the
root of the | |
| 3949 * element structure. | |
| 3950 */ | |
| 3951 ElementImpl _enclosingElement; | |
| 3952 | |
| 3953 /** | |
| 3954 * The name of this element. | |
| 3955 */ | |
| 3956 String _name; | |
| 3957 | |
| 3958 /** | |
| 3959 * The offset of the name of this element in the file that contains the declar
ation of this | |
| 3960 * element. | |
| 3961 */ | |
| 3962 int nameOffset = 0; | |
| 3963 | |
| 3964 /** | |
| 3965 * A bit-encoded form of the modifiers associated with this element. | |
| 3966 */ | |
| 3967 int _modifiers = 0; | |
| 3968 | |
| 3969 /** | |
| 3970 * An array containing all of the metadata associated with this element. | |
| 3971 */ | |
| 3972 List<ElementAnnotation> metadata = ElementAnnotationImpl.EMPTY_ARRAY; | |
| 3973 | |
| 3974 /** | |
| 3975 * A cached copy of the calculated hashCode for this element. | |
| 3976 */ | |
| 3977 int _cachedHashCode = 0; | |
| 3978 | |
| 3979 /** | |
| 3980 * Initialize a newly created element to have the given name. | |
| 3981 * | |
| 3982 * @param name the name of this element | |
| 3983 */ | |
| 3984 ElementImpl.forNode(Identifier name) : this(name == null ? "" : name.name, nam
e == null ? -1 : name.offset); | |
| 3985 | |
| 3986 /** | |
| 3987 * Initialize a newly created element to have the given name. | |
| 3988 * | |
| 3989 * @param name the name of this element | |
| 3990 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 3991 * declaration of this element | |
| 3992 */ | |
| 3993 ElementImpl(String name, this.nameOffset) { | |
| 3994 this._name = StringUtilities.intern(name); | |
| 3995 } | |
| 3996 | |
| 3997 @override | |
| 3998 String computeDocumentationComment() { | |
| 3999 AnalysisContext context = this.context; | |
| 4000 if (context == null) { | |
| 4001 return null; | |
| 4002 } | |
| 4003 return context.computeDocumentationComment(this); | |
| 4004 } | |
| 4005 | |
| 4006 @override | |
| 4007 bool operator ==(Object object) { | |
| 4008 if (identical(this, object)) { | |
| 4009 return true; | |
| 4010 } | |
| 4011 if (object == null || hashCode != object.hashCode) { | |
| 4012 return false; | |
| 4013 } | |
| 4014 return object.runtimeType == runtimeType && (object as Element).location ==
location; | |
| 4015 } | |
| 4016 | |
| 4017 @override | |
| 4018 Element getAncestor(Predicate<Element> predicate) { | |
| 4019 Element ancestor = _enclosingElement; | |
| 4020 while (ancestor != null && !predicate(ancestor)) { | |
| 4021 ancestor = ancestor.enclosingElement; | |
| 4022 } | |
| 4023 return ancestor; | |
| 4024 } | |
| 4025 | |
| 4026 /** | |
| 4027 * Return the child of this element that is uniquely identified by the given i
dentifier, or | |
| 4028 * `null` if there is no such child. | |
| 4029 * | |
| 4030 * @param identifier the identifier used to select a child | |
| 4031 * @return the child of this element with the given identifier | |
| 4032 */ | |
| 4033 ElementImpl getChild(String identifier) => null; | |
| 4034 | |
| 4035 @override | |
| 4036 AnalysisContext get context { | |
| 4037 if (_enclosingElement == null) { | |
| 4038 return null; | |
| 4039 } | |
| 4040 return _enclosingElement.context; | |
| 4041 } | |
| 4042 | |
| 4043 @override | |
| 4044 String get displayName => _name; | |
| 4045 | |
| 4046 @override | |
| 4047 Element get enclosingElement => _enclosingElement; | |
| 4048 | |
| 4049 @override | |
| 4050 LibraryElement get library => getAncestor((element) => element is LibraryEleme
nt); | |
| 4051 | |
| 4052 @override | |
| 4053 ElementLocation get location => new ElementLocationImpl.con1(this); | |
| 4054 | |
| 4055 @override | |
| 4056 String get name => _name; | |
| 4057 | |
| 4058 @override | |
| 4059 AstNode get node => getNodeMatching((node) => node is AstNode); | |
| 4060 | |
| 4061 @override | |
| 4062 Source get source { | |
| 4063 if (_enclosingElement == null) { | |
| 4064 return null; | |
| 4065 } | |
| 4066 return _enclosingElement.source; | |
| 4067 } | |
| 4068 | |
| 4069 @override | |
| 4070 CompilationUnit get unit => context.resolveCompilationUnit(source, library); | |
| 4071 | |
| 4072 @override | |
| 4073 int get hashCode { | |
| 4074 // TODO: We might want to re-visit this optimization in the future. | |
| 4075 // We cache the hash code value as this is a very frequently called method. | |
| 4076 if (_cachedHashCode == 0) { | |
| 4077 int hashIdentifier = identifier.hashCode; | |
| 4078 Element enclosing = enclosingElement; | |
| 4079 if (enclosing != null) { | |
| 4080 _cachedHashCode = hashIdentifier + enclosing.hashCode; | |
| 4081 } else { | |
| 4082 _cachedHashCode = hashIdentifier; | |
| 4083 } | |
| 4084 } | |
| 4085 return _cachedHashCode; | |
| 4086 } | |
| 4087 | |
| 4088 @override | |
| 4089 bool isAccessibleIn(LibraryElement library) { | |
| 4090 if (Identifier.isPrivateName(_name)) { | |
| 4091 return library == this.library; | |
| 4092 } | |
| 4093 return true; | |
| 4094 } | |
| 4095 | |
| 4096 @override | |
| 4097 bool get isDeprecated { | |
| 4098 for (ElementAnnotation annotation in metadata) { | |
| 4099 if (annotation.isDeprecated) { | |
| 4100 return true; | |
| 4101 } | |
| 4102 } | |
| 4103 return false; | |
| 4104 } | |
| 4105 | |
| 4106 @override | |
| 4107 bool get isOverride { | |
| 4108 for (ElementAnnotation annotation in metadata) { | |
| 4109 if (annotation.isOverride) { | |
| 4110 return true; | |
| 4111 } | |
| 4112 } | |
| 4113 return false; | |
| 4114 } | |
| 4115 | |
| 4116 @override | |
| 4117 bool get isPrivate { | |
| 4118 String name = displayName; | |
| 4119 if (name == null) { | |
| 4120 return true; | |
| 4121 } | |
| 4122 return Identifier.isPrivateName(name); | |
| 4123 } | |
| 4124 | |
| 4125 @override | |
| 4126 bool get isPublic => !isPrivate; | |
| 4127 | |
| 4128 @override | |
| 4129 bool get isSynthetic => hasModifier(Modifier.SYNTHETIC); | |
| 4130 | |
| 4131 /** | |
| 4132 * Set whether this element is synthetic to correspond to the given value. | |
| 4133 * | |
| 4134 * @param isSynthetic `true` if the element is synthetic | |
| 4135 */ | |
| 4136 void set synthetic(bool isSynthetic) { | |
| 4137 setModifier(Modifier.SYNTHETIC, isSynthetic); | |
| 4138 } | |
| 4139 | |
| 4140 @override | |
| 4141 String toString() { | |
| 4142 JavaStringBuilder builder = new JavaStringBuilder(); | |
| 4143 appendTo(builder); | |
| 4144 return builder.toString(); | |
| 4145 } | |
| 4146 | |
| 4147 @override | |
| 4148 void visitChildren(ElementVisitor visitor) { | |
| 4149 } | |
| 4150 | |
| 4151 /** | |
| 4152 * Append a textual representation of this type to the given builder. | |
| 4153 * | |
| 4154 * @param builder the builder to which the text is to be appended | |
| 4155 */ | |
| 4156 void appendTo(JavaStringBuilder builder) { | |
| 4157 if (_name == null) { | |
| 4158 builder.append("<unnamed "); | |
| 4159 builder.append(runtimeType.toString()); | |
| 4160 builder.append(">"); | |
| 4161 } else { | |
| 4162 builder.append(_name); | |
| 4163 } | |
| 4164 } | |
| 4165 | |
| 4166 /** | |
| 4167 * Set this [Element] as an enclosing for given. | |
| 4168 * | |
| 4169 * @param element the element to enclose, must be [ElementImpl] | |
| 4170 */ | |
| 4171 void encloseElement(ElementImpl element) { | |
| 4172 element.enclosingElement = this; | |
| 4173 } | |
| 4174 | |
| 4175 /** | |
| 4176 * Return an identifier that uniquely identifies this element among the childr
en of this element's | |
| 4177 * parent. | |
| 4178 * | |
| 4179 * @return an identifier that uniquely identifies this element relative to its
parent | |
| 4180 */ | |
| 4181 String get identifier => name; | |
| 4182 | |
| 4183 /** | |
| 4184 * Return the resolved [AstNode] of the given type enclosing [getNameOffset]. | |
| 4185 */ | |
| 4186 AstNode getNodeMatching(Predicate<AstNode> predicate) { | |
| 4187 CompilationUnit unit = this.unit; | |
| 4188 if (unit == null) { | |
| 4189 return null; | |
| 4190 } | |
| 4191 int offset = nameOffset; | |
| 4192 AstNode node = new NodeLocator.con1(offset).searchWithin(unit); | |
| 4193 if (node == null) { | |
| 4194 return null; | |
| 4195 } | |
| 4196 return node.getAncestor(predicate); | |
| 4197 } | |
| 4198 | |
| 4199 /** | |
| 4200 * Return `true` if this element has the given modifier associated with it. | |
| 4201 * | |
| 4202 * @param modifier the modifier being tested for | |
| 4203 * @return `true` if this element has the given modifier associated with it | |
| 4204 */ | |
| 4205 bool hasModifier(Modifier modifier) => BooleanArray.getEnum(_modifiers, modifi
er); | |
| 4206 | |
| 4207 /** | |
| 4208 * If the given child is not `null`, use the given visitor to visit it. | |
| 4209 * | |
| 4210 * @param child the child to be visited | |
| 4211 * @param visitor the visitor to be used to visit the child | |
| 4212 */ | |
| 4213 void safelyVisitChild(Element child, ElementVisitor visitor) { | |
| 4214 if (child != null) { | |
| 4215 child.accept(visitor); | |
| 4216 } | |
| 4217 } | |
| 4218 | |
| 4219 /** | |
| 4220 * Use the given visitor to visit all of the children in the given array. | |
| 4221 * | |
| 4222 * @param children the children to be visited | |
| 4223 * @param visitor the visitor being used to visit the children | |
| 4224 */ | |
| 4225 void safelyVisitChildren(List<Element> children, ElementVisitor visitor) { | |
| 4226 if (children != null) { | |
| 4227 for (Element child in children) { | |
| 4228 child.accept(visitor); | |
| 4229 } | |
| 4230 } | |
| 4231 } | |
| 4232 | |
| 4233 /** | |
| 4234 * Set the enclosing element of this element to the given element. | |
| 4235 * | |
| 4236 * @param element the enclosing element of this element | |
| 4237 */ | |
| 4238 void set enclosingElement(Element element) { | |
| 4239 _enclosingElement = element as ElementImpl; | |
| 4240 } | |
| 4241 | |
| 4242 /** | |
| 4243 * Set whether the given modifier is associated with this element to correspon
d to the given | |
| 4244 * value. | |
| 4245 * | |
| 4246 * @param modifier the modifier to be set | |
| 4247 * @param value `true` if the modifier is to be associated with this element | |
| 4248 */ | |
| 4249 void setModifier(Modifier modifier, bool value) { | |
| 4250 _modifiers = BooleanArray.setEnum(_modifiers, modifier, value); | |
| 4251 } | |
| 4252 } | |
| 4253 | |
| 4254 /** | |
| 4255 * Instances of the class `ElementLocationImpl` implement an [ElementLocation]. | |
| 4256 */ | |
| 4257 class ElementLocationImpl implements ElementLocation { | |
| 4258 /** | |
| 4259 * The path to the element whose location is represented by this object. | |
| 4260 */ | |
| 4261 List<String> _components; | |
| 4262 | |
| 4263 /** | |
| 4264 * The character used to separate components in the encoded form. | |
| 4265 */ | |
| 4266 static int _SEPARATOR_CHAR = 0x3B; | |
| 4267 | |
| 4268 /** | |
| 4269 * Initialize a newly created location to represent the given element. | |
| 4270 * | |
| 4271 * @param element the element whose location is being represented | |
| 4272 */ | |
| 4273 ElementLocationImpl.con1(Element element) { | |
| 4274 List<String> components = new List<String>(); | |
| 4275 Element ancestor = element; | |
| 4276 while (ancestor != null) { | |
| 4277 components.insert(0, (ancestor as ElementImpl).identifier); | |
| 4278 ancestor = ancestor.enclosingElement; | |
| 4279 } | |
| 4280 this._components = new List.from(components); | |
| 4281 } | |
| 4282 | |
| 4283 /** | |
| 4284 * Initialize a newly created location from the given encoded form. | |
| 4285 * | |
| 4286 * @param encoding the encoded form of a location | |
| 4287 */ | |
| 4288 ElementLocationImpl.con2(String encoding) { | |
| 4289 this._components = _decode(encoding); | |
| 4290 } | |
| 4291 | |
| 4292 @override | |
| 4293 bool operator ==(Object object) { | |
| 4294 if (identical(this, object)) { | |
| 4295 return true; | |
| 4296 } | |
| 4297 if (object is! ElementLocationImpl) { | |
| 4298 return false; | |
| 4299 } | |
| 4300 ElementLocationImpl location = object as ElementLocationImpl; | |
| 4301 List<String> otherComponents = location._components; | |
| 4302 int length = _components.length; | |
| 4303 if (otherComponents.length != length) { | |
| 4304 return false; | |
| 4305 } | |
| 4306 for (int i = length - 1; i >= 2; i--) { | |
| 4307 if (_components[i] != otherComponents[i]) { | |
| 4308 return false; | |
| 4309 } | |
| 4310 } | |
| 4311 if (length > 1 && !_equalSourceComponents(_components[1], otherComponents[1]
)) { | |
| 4312 return false; | |
| 4313 } | |
| 4314 if (length > 0 && !_equalSourceComponents(_components[0], otherComponents[0]
)) { | |
| 4315 return false; | |
| 4316 } | |
| 4317 return true; | |
| 4318 } | |
| 4319 | |
| 4320 /** | |
| 4321 * Return the path to the element whose location is represented by this object
. | |
| 4322 * | |
| 4323 * @return the path to the element whose location is represented by this objec
t | |
| 4324 */ | |
| 4325 List<String> get components => _components; | |
| 4326 | |
| 4327 @override | |
| 4328 String get encoding { | |
| 4329 JavaStringBuilder builder = new JavaStringBuilder(); | |
| 4330 int length = _components.length; | |
| 4331 for (int i = 0; i < length; i++) { | |
| 4332 if (i > 0) { | |
| 4333 builder.appendChar(_SEPARATOR_CHAR); | |
| 4334 } | |
| 4335 _encode(builder, _components[i]); | |
| 4336 } | |
| 4337 return builder.toString(); | |
| 4338 } | |
| 4339 | |
| 4340 @override | |
| 4341 int get hashCode { | |
| 4342 int result = 1; | |
| 4343 for (int i = 0; i < _components.length; i++) { | |
| 4344 String component = _components[i]; | |
| 4345 int componentHash; | |
| 4346 if (i <= 1) { | |
| 4347 componentHash = _hashSourceComponent(component); | |
| 4348 } else { | |
| 4349 componentHash = component.hashCode; | |
| 4350 } | |
| 4351 result = 31 * result + componentHash; | |
| 4352 } | |
| 4353 return result; | |
| 4354 } | |
| 4355 | |
| 4356 @override | |
| 4357 String toString() => encoding; | |
| 4358 | |
| 4359 /** | |
| 4360 * Decode the encoded form of a location into an array of components. | |
| 4361 * | |
| 4362 * @param encoding the encoded form of a location | |
| 4363 * @return the components that were encoded | |
| 4364 */ | |
| 4365 List<String> _decode(String encoding) { | |
| 4366 List<String> components = new List<String>(); | |
| 4367 JavaStringBuilder builder = new JavaStringBuilder(); | |
| 4368 int index = 0; | |
| 4369 int length = encoding.length; | |
| 4370 while (index < length) { | |
| 4371 int currentChar = encoding.codeUnitAt(index); | |
| 4372 if (currentChar == _SEPARATOR_CHAR) { | |
| 4373 if (index + 1 < length && encoding.codeUnitAt(index + 1) == _SEPARATOR_C
HAR) { | |
| 4374 builder.appendChar(_SEPARATOR_CHAR); | |
| 4375 index += 2; | |
| 4376 } else { | |
| 4377 components.add(builder.toString()); | |
| 4378 builder.length = 0; | |
| 4379 index++; | |
| 4380 } | |
| 4381 } else { | |
| 4382 builder.appendChar(currentChar); | |
| 4383 index++; | |
| 4384 } | |
| 4385 } | |
| 4386 if (builder.length > 0) { | |
| 4387 components.add(builder.toString()); | |
| 4388 } | |
| 4389 return new List.from(components); | |
| 4390 } | |
| 4391 | |
| 4392 /** | |
| 4393 * Append an encoded form of the given component to the given builder. | |
| 4394 * | |
| 4395 * @param builder the builder to which the encoded component is to be appended | |
| 4396 * @param component the component to be appended to the builder | |
| 4397 */ | |
| 4398 void _encode(JavaStringBuilder builder, String component) { | |
| 4399 int length = component.length; | |
| 4400 for (int i = 0; i < length; i++) { | |
| 4401 int currentChar = component.codeUnitAt(i); | |
| 4402 if (currentChar == _SEPARATOR_CHAR) { | |
| 4403 builder.appendChar(_SEPARATOR_CHAR); | |
| 4404 } | |
| 4405 builder.appendChar(currentChar); | |
| 4406 } | |
| 4407 } | |
| 4408 | |
| 4409 /** | |
| 4410 * Return `true` if the given components, when interpreted to be encoded sourc
es with a | |
| 4411 * leading source type indicator, are equal when the source type's are ignored
. | |
| 4412 * | |
| 4413 * @param left the left component being compared | |
| 4414 * @param right the right component being compared | |
| 4415 * @return `true` if the given components are equal when the source type's are
ignored | |
| 4416 */ | |
| 4417 bool _equalSourceComponents(String left, String right) { | |
| 4418 // TODO(brianwilkerson) This method can go away when sources no longer have
a URI kind. | |
| 4419 if (left == null) { | |
| 4420 return right == null; | |
| 4421 } else if (right == null) { | |
| 4422 return false; | |
| 4423 } | |
| 4424 int leftLength = left.length; | |
| 4425 int rightLength = right.length; | |
| 4426 if (leftLength != rightLength) { | |
| 4427 return false; | |
| 4428 } else if (leftLength <= 1 || rightLength <= 1) { | |
| 4429 return left == right; | |
| 4430 } | |
| 4431 return javaStringRegionMatches(left, 1, right, 1, leftLength - 1); | |
| 4432 } | |
| 4433 | |
| 4434 /** | |
| 4435 * Return the hash code of the given encoded source component, ignoring the so
urce type indicator. | |
| 4436 * | |
| 4437 * @param sourceComponent the component to compute a hash code | |
| 4438 * @return the hash code of the given encoded source component | |
| 4439 */ | |
| 4440 int _hashSourceComponent(String sourceComponent) { | |
| 4441 // TODO(brianwilkerson) This method can go away when sources no longer have
a URI kind. | |
| 4442 if (sourceComponent.length <= 1) { | |
| 4443 return sourceComponent.hashCode; | |
| 4444 } | |
| 4445 return sourceComponent.substring(1).hashCode; | |
| 4446 } | |
| 4447 } | |
| 4448 | |
| 4449 /** | |
| 4450 * The class `ElementPair` is a pair of [Element]s. [Object#equals] and | |
| 4451 * [Object#hashCode] so this class can be used in hashed data structures. | |
| 4452 */ | |
| 4453 class ElementPair { | |
| 4454 /** | |
| 4455 * The first [Element] | |
| 4456 */ | |
| 4457 final Element _first; | |
| 4458 | |
| 4459 /** | |
| 4460 * The second [Element] | |
| 4461 */ | |
| 4462 final Element _second; | |
| 4463 | |
| 4464 /** | |
| 4465 * The sole constructor for this class, taking two [Element]s. | |
| 4466 * | |
| 4467 * @param first the first element | |
| 4468 * @param second the second element | |
| 4469 */ | |
| 4470 ElementPair(this._first, this._second); | |
| 4471 | |
| 4472 @override | |
| 4473 bool operator ==(Object object) { | |
| 4474 if (identical(object, this)) { | |
| 4475 return true; | |
| 4476 } | |
| 4477 if (object is ElementPair) { | |
| 4478 ElementPair elementPair = object; | |
| 4479 return (_first == elementPair._first) && (_second == elementPair._second); | |
| 4480 } | |
| 4481 return false; | |
| 4482 } | |
| 4483 | |
| 4484 /** | |
| 4485 * Return the first element. | |
| 4486 * | |
| 4487 * @return the first element | |
| 4488 */ | |
| 4489 Element get firstElt => _first; | |
| 4490 | |
| 4491 /** | |
| 4492 * Return the second element | |
| 4493 * | |
| 4494 * @return the second element | |
| 4495 */ | |
| 4496 Element get secondElt => _second; | |
| 4497 | |
| 4498 @override | |
| 4499 int get hashCode => ObjectUtilities.combineHashCodes(_first.hashCode, _second.
hashCode); | |
| 4500 } | |
| 4501 | |
| 4502 /** | |
| 4503 * Instances of the class `EmbeddedHtmlScriptElementImpl` implement an | |
| 4504 * [EmbeddedHtmlScriptElement]. | |
| 4505 */ | |
| 4506 class EmbeddedHtmlScriptElementImpl extends HtmlScriptElementImpl implements Emb
eddedHtmlScriptElement { | |
| 4507 /** | |
| 4508 * The library defined by the script tag's content. | |
| 4509 */ | |
| 4510 LibraryElement _scriptLibrary; | |
| 4511 | |
| 4512 /** | |
| 4513 * Initialize a newly created script element to have the specified tag name an
d offset. | |
| 4514 * | |
| 4515 * @param node the XML node from which this element is derived (not `null`) | |
| 4516 */ | |
| 4517 EmbeddedHtmlScriptElementImpl(XmlTagNode node) : super(node); | |
| 4518 | |
| 4519 @override | |
| 4520 accept(ElementVisitor visitor) => visitor.visitEmbeddedHtmlScriptElement(this)
; | |
| 4521 | |
| 4522 @override | |
| 4523 ElementKind get kind => ElementKind.EMBEDDED_HTML_SCRIPT; | |
| 4524 | |
| 4525 @override | |
| 4526 LibraryElement get scriptLibrary => _scriptLibrary; | |
| 4527 | |
| 4528 /** | |
| 4529 * Set the script library defined by the script tag's content. | |
| 4530 * | |
| 4531 * @param scriptLibrary the library or `null` if none | |
| 4532 */ | |
| 4533 void set scriptLibrary(LibraryElementImpl scriptLibrary) { | |
| 4534 scriptLibrary.enclosingElement = this; | |
| 4535 this._scriptLibrary = scriptLibrary; | |
| 4536 } | |
| 4537 | |
| 4538 @override | |
| 4539 void visitChildren(ElementVisitor visitor) { | |
| 4540 safelyVisitChild(_scriptLibrary, visitor); | |
| 4541 } | |
| 4542 } | |
| 4543 | |
| 4544 /** | |
| 4545 * The abstract class `ExecutableElementImpl` implements the behavior common to | |
| 4546 * `ExecutableElement`s. | |
| 4547 */ | |
| 4548 abstract class ExecutableElementImpl extends ElementImpl implements ExecutableEl
ement { | |
| 4549 /** | |
| 4550 * An array containing all of the functions defined within this executable ele
ment. | |
| 4551 */ | |
| 4552 List<FunctionElement> _functions = FunctionElementImpl.EMPTY_ARRAY; | |
| 4553 | |
| 4554 /** | |
| 4555 * An array containing all of the labels defined within this executable elemen
t. | |
| 4556 */ | |
| 4557 List<LabelElement> _labels = LabelElementImpl.EMPTY_ARRAY; | |
| 4558 | |
| 4559 /** | |
| 4560 * An array containing all of the local variables defined within this executab
le element. | |
| 4561 */ | |
| 4562 List<LocalVariableElement> _localVariables = LocalVariableElementImpl.EMPTY_AR
RAY; | |
| 4563 | |
| 4564 /** | |
| 4565 * An array containing all of the parameters defined by this executable elemen
t. | |
| 4566 */ | |
| 4567 List<ParameterElement> _parameters = ParameterElementImpl.EMPTY_ARRAY; | |
| 4568 | |
| 4569 /** | |
| 4570 * The return type defined by this executable element. | |
| 4571 */ | |
| 4572 DartType returnType; | |
| 4573 | |
| 4574 /** | |
| 4575 * The type of function defined by this executable element. | |
| 4576 */ | |
| 4577 FunctionType type; | |
| 4578 | |
| 4579 /** | |
| 4580 * An empty array of executable elements. | |
| 4581 */ | |
| 4582 static List<ExecutableElement> EMPTY_ARRAY = new List<ExecutableElement>(0); | |
| 4583 | |
| 4584 /** | |
| 4585 * Initialize a newly created executable element to have the given name. | |
| 4586 * | |
| 4587 * @param name the name of this element | |
| 4588 */ | |
| 4589 ExecutableElementImpl.forNode(Identifier name) : super.forNode(name); | |
| 4590 | |
| 4591 /** | |
| 4592 * Initialize a newly created executable element to have the given name. | |
| 4593 * | |
| 4594 * @param name the name of this element | |
| 4595 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 4596 * declaration of this element | |
| 4597 */ | |
| 4598 ExecutableElementImpl(String name, int nameOffset) : super(name, nameOffset); | |
| 4599 | |
| 4600 @override | |
| 4601 ElementImpl getChild(String identifier) { | |
| 4602 for (ExecutableElement function in _functions) { | |
| 4603 if ((function as ExecutableElementImpl).identifier == identifier) { | |
| 4604 return function as ExecutableElementImpl; | |
| 4605 } | |
| 4606 } | |
| 4607 for (LabelElement label in _labels) { | |
| 4608 if ((label as LabelElementImpl).identifier == identifier) { | |
| 4609 return label as LabelElementImpl; | |
| 4610 } | |
| 4611 } | |
| 4612 for (VariableElement variable in _localVariables) { | |
| 4613 if ((variable as VariableElementImpl).identifier == identifier) { | |
| 4614 return variable as VariableElementImpl; | |
| 4615 } | |
| 4616 } | |
| 4617 for (ParameterElement parameter in _parameters) { | |
| 4618 if ((parameter as ParameterElementImpl).identifier == identifier) { | |
| 4619 return parameter as ParameterElementImpl; | |
| 4620 } | |
| 4621 } | |
| 4622 return null; | |
| 4623 } | |
| 4624 | |
| 4625 @override | |
| 4626 List<FunctionElement> get functions => _functions; | |
| 4627 | |
| 4628 @override | |
| 4629 List<LabelElement> get labels => _labels; | |
| 4630 | |
| 4631 @override | |
| 4632 List<LocalVariableElement> get localVariables => _localVariables; | |
| 4633 | |
| 4634 @override | |
| 4635 List<ParameterElement> get parameters => _parameters; | |
| 4636 | |
| 4637 @override | |
| 4638 bool get isOperator => false; | |
| 4639 | |
| 4640 /** | |
| 4641 * Set the functions defined within this executable element to the given funct
ions. | |
| 4642 * | |
| 4643 * @param functions the functions defined within this executable element | |
| 4644 */ | |
| 4645 void set functions(List<FunctionElement> functions) { | |
| 4646 for (FunctionElement function in functions) { | |
| 4647 (function as FunctionElementImpl).enclosingElement = this; | |
| 4648 } | |
| 4649 this._functions = functions; | |
| 4650 } | |
| 4651 | |
| 4652 /** | |
| 4653 * Set the labels defined within this executable element to the given labels. | |
| 4654 * | |
| 4655 * @param labels the labels defined within this executable element | |
| 4656 */ | |
| 4657 void set labels(List<LabelElement> labels) { | |
| 4658 for (LabelElement label in labels) { | |
| 4659 (label as LabelElementImpl).enclosingElement = this; | |
| 4660 } | |
| 4661 this._labels = labels; | |
| 4662 } | |
| 4663 | |
| 4664 /** | |
| 4665 * Set the local variables defined within this executable element to the given
variables. | |
| 4666 * | |
| 4667 * @param localVariables the local variables defined within this executable el
ement | |
| 4668 */ | |
| 4669 void set localVariables(List<LocalVariableElement> localVariables) { | |
| 4670 for (LocalVariableElement variable in localVariables) { | |
| 4671 (variable as LocalVariableElementImpl).enclosingElement = this; | |
| 4672 } | |
| 4673 this._localVariables = localVariables; | |
| 4674 } | |
| 4675 | |
| 4676 /** | |
| 4677 * Set the parameters defined by this executable element to the given paramete
rs. | |
| 4678 * | |
| 4679 * @param parameters the parameters defined by this executable element | |
| 4680 */ | |
| 4681 void set parameters(List<ParameterElement> parameters) { | |
| 4682 for (ParameterElement parameter in parameters) { | |
| 4683 (parameter as ParameterElementImpl).enclosingElement = this; | |
| 4684 } | |
| 4685 this._parameters = parameters; | |
| 4686 } | |
| 4687 | |
| 4688 @override | |
| 4689 void visitChildren(ElementVisitor visitor) { | |
| 4690 super.visitChildren(visitor); | |
| 4691 safelyVisitChildren(_functions, visitor); | |
| 4692 safelyVisitChildren(_labels, visitor); | |
| 4693 safelyVisitChildren(_localVariables, visitor); | |
| 4694 safelyVisitChildren(_parameters, visitor); | |
| 4695 } | |
| 4696 | |
| 4697 @override | |
| 4698 void appendTo(JavaStringBuilder builder) { | |
| 4699 if (this.kind != ElementKind.GETTER) { | |
| 4700 builder.append("("); | |
| 4701 String closing = null; | |
| 4702 ParameterKind kind = ParameterKind.REQUIRED; | |
| 4703 int parameterCount = _parameters.length; | |
| 4704 for (int i = 0; i < parameterCount; i++) { | |
| 4705 if (i > 0) { | |
| 4706 builder.append(", "); | |
| 4707 } | |
| 4708 ParameterElementImpl parameter = _parameters[i] as ParameterElementImpl; | |
| 4709 ParameterKind parameterKind = parameter.parameterKind; | |
| 4710 if (parameterKind != kind) { | |
| 4711 if (closing != null) { | |
| 4712 builder.append(closing); | |
| 4713 } | |
| 4714 if (parameterKind == ParameterKind.POSITIONAL) { | |
| 4715 builder.append("["); | |
| 4716 closing = "]"; | |
| 4717 } else if (parameterKind == ParameterKind.NAMED) { | |
| 4718 builder.append("{"); | |
| 4719 closing = "}"; | |
| 4720 } else { | |
| 4721 closing = null; | |
| 4722 } | |
| 4723 } | |
| 4724 kind = parameterKind; | |
| 4725 parameter.appendToWithoutDelimiters(builder); | |
| 4726 } | |
| 4727 if (closing != null) { | |
| 4728 builder.append(closing); | |
| 4729 } | |
| 4730 builder.append(")"); | |
| 4731 } | |
| 4732 if (type != null) { | |
| 4733 builder.append(Element.RIGHT_ARROW); | |
| 4734 builder.append(type.returnType); | |
| 4735 } | |
| 4736 } | |
| 4737 } | |
| 4738 | |
| 4739 /** | |
| 4740 * Instances of the class `ExportElementImpl` implement an [ExportElement]. | |
| 4741 */ | |
| 4742 class ExportElementImpl extends UriReferencedElementImpl implements ExportElemen
t { | |
| 4743 /** | |
| 4744 * The library that is exported from this library by this export directive. | |
| 4745 */ | |
| 4746 LibraryElement exportedLibrary; | |
| 4747 | |
| 4748 /** | |
| 4749 * The combinators that were specified as part of the export directive in the
order in which they | |
| 4750 * were specified. | |
| 4751 */ | |
| 4752 List<NamespaceCombinator> combinators = NamespaceCombinator.EMPTY_ARRAY; | |
| 4753 | |
| 4754 /** | |
| 4755 * Initialize a newly created export element. | |
| 4756 */ | |
| 4757 ExportElementImpl() : super(null, -1); | |
| 4758 | |
| 4759 @override | |
| 4760 accept(ElementVisitor visitor) => visitor.visitExportElement(this); | |
| 4761 | |
| 4762 @override | |
| 4763 ElementKind get kind => ElementKind.EXPORT; | |
| 4764 | |
| 4765 @override | |
| 4766 void appendTo(JavaStringBuilder builder) { | |
| 4767 builder.append("export "); | |
| 4768 (exportedLibrary as LibraryElementImpl).appendTo(builder); | |
| 4769 } | |
| 4770 | |
| 4771 @override | |
| 4772 String get identifier => exportedLibrary.name; | |
| 4773 } | |
| 4774 | |
| 4775 /** | |
| 4776 * Instances of the class `ExternalHtmlScriptElementImpl` implement an | |
| 4777 * [ExternalHtmlScriptElement]. | |
| 4778 */ | |
| 4779 class ExternalHtmlScriptElementImpl extends HtmlScriptElementImpl implements Ext
ernalHtmlScriptElement { | |
| 4780 /** | |
| 4781 * The source specified in the `source` attribute or `null` if unspecified. | |
| 4782 */ | |
| 4783 Source scriptSource; | |
| 4784 | |
| 4785 /** | |
| 4786 * Initialize a newly created script element to have the specified tag name an
d offset. | |
| 4787 * | |
| 4788 * @param node the XML node from which this element is derived (not `null`) | |
| 4789 */ | |
| 4790 ExternalHtmlScriptElementImpl(XmlTagNode node) : super(node); | |
| 4791 | |
| 4792 @override | |
| 4793 accept(ElementVisitor visitor) => visitor.visitExternalHtmlScriptElement(this)
; | |
| 4794 | |
| 4795 @override | |
| 4796 ElementKind get kind => ElementKind.EXTERNAL_HTML_SCRIPT; | |
| 4797 } | |
| 4798 | |
| 4799 /** | |
| 4800 * Instances of the class `FieldElementImpl` implement a `FieldElement`. | |
| 4801 */ | |
| 4802 class FieldElementImpl extends PropertyInducingElementImpl implements FieldEleme
nt { | |
| 4803 /** | |
| 4804 * An empty array of field elements. | |
| 4805 */ | |
| 4806 static List<FieldElement> EMPTY_ARRAY = new List<FieldElement>(0); | |
| 4807 | |
| 4808 /** | |
| 4809 * Initialize a newly created field element to have the given name. | |
| 4810 * | |
| 4811 * @param name the name of this element | |
| 4812 */ | |
| 4813 FieldElementImpl.con1(Identifier name) : super.con1(name); | |
| 4814 | |
| 4815 /** | |
| 4816 * Initialize a newly created synthetic field element to have the given name. | |
| 4817 * | |
| 4818 * @param name the name of this element | |
| 4819 */ | |
| 4820 FieldElementImpl.con2(String name) : super.con2(name); | |
| 4821 | |
| 4822 @override | |
| 4823 accept(ElementVisitor visitor) => visitor.visitFieldElement(this); | |
| 4824 | |
| 4825 @override | |
| 4826 ClassElement get enclosingElement => super.enclosingElement as ClassElement; | |
| 4827 | |
| 4828 @override | |
| 4829 ElementKind get kind => ElementKind.FIELD; | |
| 4830 | |
| 4831 @override | |
| 4832 bool get isStatic => hasModifier(Modifier.STATIC); | |
| 4833 | |
| 4834 /** | |
| 4835 * Set whether this field is static to correspond to the given value. | |
| 4836 * | |
| 4837 * @param isStatic `true` if the field is static | |
| 4838 */ | |
| 4839 void set static(bool isStatic) { | |
| 4840 setModifier(Modifier.STATIC, isStatic); | |
| 4841 } | |
| 4842 } | |
| 4843 | |
| 4844 /** | |
| 4845 * Instances of the class `FieldFormalParameterElementImpl` extend | |
| 4846 * [ParameterElementImpl] to provide the additional information of the [FieldEle
ment] | |
| 4847 * associated with the parameter. | |
| 4848 */ | |
| 4849 class FieldFormalParameterElementImpl extends ParameterElementImpl implements Fi
eldFormalParameterElement { | |
| 4850 /** | |
| 4851 * The field associated with this field formal parameter. | |
| 4852 */ | |
| 4853 FieldElement field; | |
| 4854 | |
| 4855 /** | |
| 4856 * Initialize a newly created parameter element to have the given name. | |
| 4857 * | |
| 4858 * @param name the name of this element | |
| 4859 */ | |
| 4860 FieldFormalParameterElementImpl(Identifier name) : super.con1(name); | |
| 4861 | |
| 4862 @override | |
| 4863 accept(ElementVisitor visitor) => visitor.visitFieldFormalParameterElement(thi
s); | |
| 4864 | |
| 4865 @override | |
| 4866 bool get isInitializingFormal => true; | |
| 4867 } | |
| 4868 | |
| 4869 /** | |
| 4870 * Instances of the class `FunctionElementImpl` implement a `FunctionElement`. | |
| 4871 */ | |
| 4872 class FunctionElementImpl extends ExecutableElementImpl implements FunctionEleme
nt { | |
| 4873 /** | |
| 4874 * The offset to the beginning of the visible range for this element. | |
| 4875 */ | |
| 4876 int _visibleRangeOffset = 0; | |
| 4877 | |
| 4878 /** | |
| 4879 * The length of the visible range for this element, or `-1` if this element d
oes not have a | |
| 4880 * visible range. | |
| 4881 */ | |
| 4882 int _visibleRangeLength = -1; | |
| 4883 | |
| 4884 /** | |
| 4885 * An empty array of function elements. | |
| 4886 */ | |
| 4887 static List<FunctionElement> EMPTY_ARRAY = new List<FunctionElement>(0); | |
| 4888 | |
| 4889 /** | |
| 4890 * Initialize a newly created function element to have the given name. | |
| 4891 * | |
| 4892 * @param name the name of this element | |
| 4893 */ | |
| 4894 FunctionElementImpl.forNode(Identifier name) : super.forNode(name); | |
| 4895 | |
| 4896 /** | |
| 4897 * Initialize a newly created function element to have no name and the given o
ffset. This is used | |
| 4898 * for function expressions, which have no name. | |
| 4899 * | |
| 4900 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 4901 * declaration of this element | |
| 4902 */ | |
| 4903 FunctionElementImpl.forOffset(int nameOffset) : super("", nameOffset); | |
| 4904 | |
| 4905 /** | |
| 4906 * Initialize a newly created function element to have the given name and offs
et. | |
| 4907 * | |
| 4908 * @param name the name of this element | |
| 4909 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 4910 * declaration of this element | |
| 4911 */ | |
| 4912 FunctionElementImpl(String name, int nameOffset) : super(name, nameOffset); | |
| 4913 | |
| 4914 @override | |
| 4915 accept(ElementVisitor visitor) => visitor.visitFunctionElement(this); | |
| 4916 | |
| 4917 @override | |
| 4918 ElementKind get kind => ElementKind.FUNCTION; | |
| 4919 | |
| 4920 @override | |
| 4921 FunctionDeclaration get node => getNodeMatching((node) => node is FunctionDecl
aration); | |
| 4922 | |
| 4923 @override | |
| 4924 SourceRange get visibleRange { | |
| 4925 if (_visibleRangeLength < 0) { | |
| 4926 return null; | |
| 4927 } | |
| 4928 return new SourceRange(_visibleRangeOffset, _visibleRangeLength); | |
| 4929 } | |
| 4930 | |
| 4931 @override | |
| 4932 bool get isStatic => enclosingElement is CompilationUnitElement; | |
| 4933 | |
| 4934 /** | |
| 4935 * Set the visible range for this element to the range starting at the given o
ffset with the given | |
| 4936 * length. | |
| 4937 * | |
| 4938 * @param offset the offset to the beginning of the visible range for this ele
ment | |
| 4939 * @param length the length of the visible range for this element, or `-1` if
this element | |
| 4940 * does not have a visible range | |
| 4941 */ | |
| 4942 void setVisibleRange(int offset, int length) { | |
| 4943 _visibleRangeOffset = offset; | |
| 4944 _visibleRangeLength = length; | |
| 4945 } | |
| 4946 | |
| 4947 @override | |
| 4948 void appendTo(JavaStringBuilder builder) { | |
| 4949 String name = displayName; | |
| 4950 if (name != null) { | |
| 4951 builder.append(name); | |
| 4952 } | |
| 4953 super.appendTo(builder); | |
| 4954 } | |
| 4955 | |
| 4956 @override | |
| 4957 String get identifier => "${name}@${nameOffset}"; | |
| 4958 } | |
| 4959 | |
| 4960 /** | |
| 4961 * Instances of the class `FunctionTypeAliasElementImpl` implement a | |
| 4962 * `FunctionTypeAliasElement`. | |
| 4963 */ | |
| 4964 class FunctionTypeAliasElementImpl extends ElementImpl implements FunctionTypeAl
iasElement { | |
| 4965 /** | |
| 4966 * An array containing all of the parameters defined by this type alias. | |
| 4967 */ | |
| 4968 List<ParameterElement> _parameters = ParameterElementImpl.EMPTY_ARRAY; | |
| 4969 | |
| 4970 /** | |
| 4971 * The return type defined by this type alias. | |
| 4972 */ | |
| 4973 DartType returnType; | |
| 4974 | |
| 4975 /** | |
| 4976 * The type of function defined by this type alias. | |
| 4977 */ | |
| 4978 FunctionType type; | |
| 4979 | |
| 4980 /** | |
| 4981 * An array containing all of the type parameters defined for this type. | |
| 4982 */ | |
| 4983 List<TypeParameterElement> _typeParameters = TypeParameterElementImpl.EMPTY_AR
RAY; | |
| 4984 | |
| 4985 /** | |
| 4986 * An empty array of type alias elements. | |
| 4987 */ | |
| 4988 static List<FunctionTypeAliasElement> EMPTY_ARRAY = new List<FunctionTypeAlias
Element>(0); | |
| 4989 | |
| 4990 /** | |
| 4991 * Initialize a newly created type alias element to have the given name. | |
| 4992 * | |
| 4993 * @param name the name of this element | |
| 4994 */ | |
| 4995 FunctionTypeAliasElementImpl(Identifier name) : super.forNode(name); | |
| 4996 | |
| 4997 @override | |
| 4998 accept(ElementVisitor visitor) => visitor.visitFunctionTypeAliasElement(this); | |
| 4999 | |
| 5000 @override | |
| 5001 ElementImpl getChild(String identifier) { | |
| 5002 for (VariableElement parameter in _parameters) { | |
| 5003 if ((parameter as VariableElementImpl).identifier == identifier) { | |
| 5004 return parameter as VariableElementImpl; | |
| 5005 } | |
| 5006 } | |
| 5007 for (TypeParameterElement typeParameter in _typeParameters) { | |
| 5008 if ((typeParameter as TypeParameterElementImpl).identifier == identifier)
{ | |
| 5009 return typeParameter as TypeParameterElementImpl; | |
| 5010 } | |
| 5011 } | |
| 5012 return null; | |
| 5013 } | |
| 5014 | |
| 5015 @override | |
| 5016 CompilationUnitElement get enclosingElement => super.enclosingElement as Compi
lationUnitElement; | |
| 5017 | |
| 5018 @override | |
| 5019 ElementKind get kind => ElementKind.FUNCTION_TYPE_ALIAS; | |
| 5020 | |
| 5021 @override | |
| 5022 FunctionTypeAlias get node => getNodeMatching((node) => node is FunctionTypeAl
ias); | |
| 5023 | |
| 5024 @override | |
| 5025 List<ParameterElement> get parameters => _parameters; | |
| 5026 | |
| 5027 @override | |
| 5028 List<TypeParameterElement> get typeParameters => _typeParameters; | |
| 5029 | |
| 5030 /** | |
| 5031 * Set the parameters defined by this type alias to the given parameters. | |
| 5032 * | |
| 5033 * @param parameters the parameters defined by this type alias | |
| 5034 */ | |
| 5035 void set parameters(List<ParameterElement> parameters) { | |
| 5036 if (parameters != null) { | |
| 5037 for (ParameterElement parameter in parameters) { | |
| 5038 (parameter as ParameterElementImpl).enclosingElement = this; | |
| 5039 } | |
| 5040 } | |
| 5041 this._parameters = parameters; | |
| 5042 } | |
| 5043 | |
| 5044 /** | |
| 5045 * Set the type parameters defined for this type to the given parameters. | |
| 5046 * | |
| 5047 * @param typeParameters the type parameters defined for this type | |
| 5048 */ | |
| 5049 void set typeParameters(List<TypeParameterElement> typeParameters) { | |
| 5050 for (TypeParameterElement typeParameter in typeParameters) { | |
| 5051 (typeParameter as TypeParameterElementImpl).enclosingElement = this; | |
| 5052 } | |
| 5053 this._typeParameters = typeParameters; | |
| 5054 } | |
| 5055 | |
| 5056 /** | |
| 5057 * Set the parameters defined by this type alias to the given parameters witho
ut becoming the | |
| 5058 * parent of the parameters. This should only be used by the [TypeResolverVisi
tor] when | |
| 5059 * creating a synthetic type alias. | |
| 5060 * | |
| 5061 * @param parameters the parameters defined by this type alias | |
| 5062 */ | |
| 5063 void shareParameters(List<ParameterElement> parameters) { | |
| 5064 this._parameters = parameters; | |
| 5065 } | |
| 5066 | |
| 5067 /** | |
| 5068 * Set the type parameters defined for this type to the given parameters witho
ut becoming the | |
| 5069 * parent of the parameters. This should only be used by the [TypeResolverVisi
tor] when | |
| 5070 * creating a synthetic type alias. | |
| 5071 * | |
| 5072 * @param typeParameters the type parameters defined for this type | |
| 5073 */ | |
| 5074 void shareTypeParameters(List<TypeParameterElement> typeParameters) { | |
| 5075 this._typeParameters = typeParameters; | |
| 5076 } | |
| 5077 | |
| 5078 @override | |
| 5079 void visitChildren(ElementVisitor visitor) { | |
| 5080 super.visitChildren(visitor); | |
| 5081 safelyVisitChildren(_parameters, visitor); | |
| 5082 safelyVisitChildren(_typeParameters, visitor); | |
| 5083 } | |
| 5084 | |
| 5085 @override | |
| 5086 void appendTo(JavaStringBuilder builder) { | |
| 5087 builder.append("typedef "); | |
| 5088 builder.append(displayName); | |
| 5089 int typeParameterCount = _typeParameters.length; | |
| 5090 if (typeParameterCount > 0) { | |
| 5091 builder.append("<"); | |
| 5092 for (int i = 0; i < typeParameterCount; i++) { | |
| 5093 if (i > 0) { | |
| 5094 builder.append(", "); | |
| 5095 } | |
| 5096 (_typeParameters[i] as TypeParameterElementImpl).appendTo(builder); | |
| 5097 } | |
| 5098 builder.append(">"); | |
| 5099 } | |
| 5100 builder.append("("); | |
| 5101 int parameterCount = _parameters.length; | |
| 5102 for (int i = 0; i < parameterCount; i++) { | |
| 5103 if (i > 0) { | |
| 5104 builder.append(", "); | |
| 5105 } | |
| 5106 (_parameters[i] as ParameterElementImpl).appendTo(builder); | |
| 5107 } | |
| 5108 builder.append(")"); | |
| 5109 if (type != null) { | |
| 5110 builder.append(Element.RIGHT_ARROW); | |
| 5111 builder.append(type.returnType); | |
| 5112 } | |
| 5113 } | |
| 5114 } | 5683 } |
| 5115 | 5684 |
| 5116 /** | 5685 /** |
| 5117 * Instances of the class `HideElementCombinatorImpl` implement a | 5686 * Instances of the class `HideElementCombinatorImpl` implement a |
| 5118 * [HideElementCombinator]. | 5687 * [HideElementCombinator]. |
| 5119 */ | 5688 */ |
| 5120 class HideElementCombinatorImpl implements HideElementCombinator { | 5689 class HideElementCombinatorImpl implements HideElementCombinator { |
| 5121 /** | 5690 /** |
| 5122 * The names that are not to be made visible in the importing library even if
they are defined in | 5691 * The names that are not to be made visible in the importing library even if
they are defined in |
| 5123 * the imported library. | 5692 * the imported library. |
| 5124 */ | 5693 */ |
| 5125 List<String> hiddenNames = StringUtilities.EMPTY_ARRAY; | 5694 List<String> hiddenNames = StringUtilities.EMPTY_ARRAY; |
| 5126 | 5695 |
| 5127 @override | 5696 @override |
| 5128 String toString() { | 5697 String toString() { |
| 5129 JavaStringBuilder builder = new JavaStringBuilder(); | 5698 JavaStringBuilder builder = new JavaStringBuilder(); |
| 5130 builder.append("show "); | 5699 builder.append("show "); |
| 5131 int count = hiddenNames.length; | 5700 int count = hiddenNames.length; |
| 5132 for (int i = 0; i < count; i++) { | 5701 for (int i = 0; i < count; i++) { |
| 5133 if (i > 0) { | 5702 if (i > 0) { |
| 5134 builder.append(", "); | 5703 builder.append(", "); |
| 5135 } | 5704 } |
| 5136 builder.append(hiddenNames[i]); | 5705 builder.append(hiddenNames[i]); |
| 5137 } | 5706 } |
| 5138 return builder.toString(); | 5707 return builder.toString(); |
| 5139 } | 5708 } |
| 5140 } | 5709 } |
| 5141 | 5710 |
| 5142 /** | 5711 /** |
| 5712 * The interface `HtmlElement` defines the behavior of elements representing an
HTML file. |
| 5713 */ |
| 5714 abstract class HtmlElement implements Element { |
| 5715 /** |
| 5716 * Return the [CompilationUnitElement] associated with this Angular HTML file,
maybe |
| 5717 * `null` if not an Angular file. |
| 5718 */ |
| 5719 CompilationUnitElement get angularCompilationUnit; |
| 5720 |
| 5721 /** |
| 5722 * Return an array containing all of the [PolymerTagHtmlElement]s defined in t
he HTML file. |
| 5723 * |
| 5724 * @return the [PolymerTagHtmlElement]s elements in the HTML file (not `null`, |
| 5725 * contains no `null`s) |
| 5726 */ |
| 5727 List<PolymerTagHtmlElement> get polymerTags; |
| 5728 |
| 5729 /** |
| 5730 * Return an array containing all of the script elements contained in the HTML
file. This includes |
| 5731 * scripts with libraries that are defined by the content of a script tag as w
ell as libraries |
| 5732 * that are referenced in the {@core source} attribute of a script tag. |
| 5733 * |
| 5734 * @return the script elements in the HTML file (not `null`, contains no `null
`s) |
| 5735 */ |
| 5736 List<HtmlScriptElement> get scripts; |
| 5737 } |
| 5738 |
| 5739 /** |
| 5143 * Instances of the class `HtmlElementImpl` implement an [HtmlElement]. | 5740 * Instances of the class `HtmlElementImpl` implement an [HtmlElement]. |
| 5144 */ | 5741 */ |
| 5145 class HtmlElementImpl extends ElementImpl implements HtmlElement { | 5742 class HtmlElementImpl extends ElementImpl implements HtmlElement { |
| 5146 /** | 5743 /** |
| 5147 * An empty array of HTML file elements. | 5744 * An empty array of HTML file elements. |
| 5148 */ | 5745 */ |
| 5149 static List<HtmlElement> EMPTY_ARRAY = new List<HtmlElement>(0); | 5746 static List<HtmlElement> EMPTY_ARRAY = new List<HtmlElement>(0); |
| 5150 | 5747 |
| 5151 /** | 5748 /** |
| 5152 * The analysis context in which this library is defined. | 5749 * The analysis context in which this library is defined. |
| (...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5249 void appendTo(JavaStringBuilder builder) { | 5846 void appendTo(JavaStringBuilder builder) { |
| 5250 if (source == null) { | 5847 if (source == null) { |
| 5251 builder.append("{HTML file}"); | 5848 builder.append("{HTML file}"); |
| 5252 } else { | 5849 } else { |
| 5253 builder.append(source.fullName); | 5850 builder.append(source.fullName); |
| 5254 } | 5851 } |
| 5255 } | 5852 } |
| 5256 } | 5853 } |
| 5257 | 5854 |
| 5258 /** | 5855 /** |
| 5856 * The interface `HtmlScriptElement` defines the behavior of elements representi
ng a script |
| 5857 * tag in an HTML file. |
| 5858 * |
| 5859 * @see EmbeddedHtmlScriptElement |
| 5860 * @see ExternalHtmlScriptElement |
| 5861 */ |
| 5862 abstract class HtmlScriptElement implements Element { |
| 5863 } |
| 5864 |
| 5865 /** |
| 5259 * Instances of the class `HtmlScriptElementImpl` implement an [HtmlScriptElemen
t]. | 5866 * Instances of the class `HtmlScriptElementImpl` implement an [HtmlScriptElemen
t]. |
| 5260 */ | 5867 */ |
| 5261 abstract class HtmlScriptElementImpl extends ElementImpl implements HtmlScriptEl
ement { | 5868 abstract class HtmlScriptElementImpl extends ElementImpl implements HtmlScriptEl
ement { |
| 5262 /** | 5869 /** |
| 5263 * An empty array of HTML script elements. | 5870 * An empty array of HTML script elements. |
| 5264 */ | 5871 */ |
| 5265 static List<HtmlScriptElement> EMPTY_ARRAY = new List<HtmlScriptElement>(0); | 5872 static List<HtmlScriptElement> EMPTY_ARRAY = new List<HtmlScriptElement>(0); |
| 5266 | 5873 |
| 5267 /** | 5874 /** |
| 5268 * Initialize a newly created script element to have the specified tag name an
d offset. | 5875 * Initialize a newly created script element to have the specified tag name an
d offset. |
| 5269 * | 5876 * |
| 5270 * @param node the XML node from which this element is derived (not `null`) | 5877 * @param node the XML node from which this element is derived (not `null`) |
| 5271 */ | 5878 */ |
| 5272 HtmlScriptElementImpl(XmlTagNode node) : super(node.tag, node.tagToken.offset)
; | 5879 HtmlScriptElementImpl(XmlTagNode node) : super(node.tag, node.tagToken.offset)
; |
| 5273 } | 5880 } |
| 5274 | 5881 |
| 5275 /** | 5882 /** |
| 5883 * The interface `ImportElement` defines the behavior of objects representing in
formation |
| 5884 * about a single import directive within a library. |
| 5885 */ |
| 5886 abstract class ImportElement implements Element, UriReferencedElement { |
| 5887 /** |
| 5888 * An empty array of import elements. |
| 5889 */ |
| 5890 static final List<ImportElement> EMPTY_ARRAY = new List<ImportElement>(0); |
| 5891 |
| 5892 /** |
| 5893 * Return an array containing the combinators that were specified as part of t
he import directive |
| 5894 * in the order in which they were specified. |
| 5895 * |
| 5896 * @return the combinators specified in the import directive |
| 5897 */ |
| 5898 List<NamespaceCombinator> get combinators; |
| 5899 |
| 5900 /** |
| 5901 * Return the library that is imported into this library by this import direct
ive. |
| 5902 * |
| 5903 * @return the library that is imported into this library |
| 5904 */ |
| 5905 LibraryElement get importedLibrary; |
| 5906 |
| 5907 /** |
| 5908 * Return the prefix that was specified as part of the import directive, or `n
ull` if there |
| 5909 * was no prefix specified. |
| 5910 * |
| 5911 * @return the prefix that was specified as part of the import directive |
| 5912 */ |
| 5913 PrefixElement get prefix; |
| 5914 |
| 5915 /** |
| 5916 * Return the offset of the prefix of this import in the file that contains th
is import directive, |
| 5917 * or `-1` if this import is synthetic, does not have a prefix, or otherwise d
oes not have |
| 5918 * an offset. |
| 5919 * |
| 5920 * @return the offset of the prefix of this import |
| 5921 */ |
| 5922 int get prefixOffset; |
| 5923 |
| 5924 /** |
| 5925 * Return `true` if this import is for a deferred library. |
| 5926 * |
| 5927 * @return `true` if this import is for a deferred library |
| 5928 */ |
| 5929 bool get isDeferred; |
| 5930 } |
| 5931 |
| 5932 /** |
| 5276 * Instances of the class `ImportElementImpl` implement an [ImportElement]. | 5933 * Instances of the class `ImportElementImpl` implement an [ImportElement]. |
| 5277 */ | 5934 */ |
| 5278 class ImportElementImpl extends UriReferencedElementImpl implements ImportElemen
t { | 5935 class ImportElementImpl extends UriReferencedElementImpl implements ImportElemen
t { |
| 5279 /** | 5936 /** |
| 5280 * The offset of the prefix of this import in the file that contains the this
import directive, or | 5937 * The offset of the prefix of this import in the file that contains the this
import directive, or |
| 5281 * `-1` if this import is synthetic. | 5938 * `-1` if this import is synthetic. |
| 5282 */ | 5939 */ |
| 5283 int prefixOffset = 0; | 5940 int prefixOffset = 0; |
| 5284 | 5941 |
| 5285 /** | 5942 /** |
| (...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5334 void appendTo(JavaStringBuilder builder) { | 5991 void appendTo(JavaStringBuilder builder) { |
| 5335 builder.append("import "); | 5992 builder.append("import "); |
| 5336 (importedLibrary as LibraryElementImpl).appendTo(builder); | 5993 (importedLibrary as LibraryElementImpl).appendTo(builder); |
| 5337 } | 5994 } |
| 5338 | 5995 |
| 5339 @override | 5996 @override |
| 5340 String get identifier => "${(importedLibrary as LibraryElementImpl).identifier
}@${nameOffset}"; | 5997 String get identifier => "${(importedLibrary as LibraryElementImpl).identifier
}@${nameOffset}"; |
| 5341 } | 5998 } |
| 5342 | 5999 |
| 5343 /** | 6000 /** |
| 6001 * The interface `InterfaceType` defines the behavior common to objects represen
ting the type |
| 6002 * introduced by either a class or an interface, or a reference to such a type. |
| 6003 */ |
| 6004 abstract class InterfaceType implements ParameterizedType { |
| 6005 /** |
| 6006 * Return an array containing all of the accessors (getters and setters) decla
red in this type. |
| 6007 * |
| 6008 * @return the accessors declared in this type |
| 6009 */ |
| 6010 List<PropertyAccessorElement> get accessors; |
| 6011 |
| 6012 @override |
| 6013 ClassElement get element; |
| 6014 |
| 6015 /** |
| 6016 * Return the element representing the getter with the given name that is decl
ared in this class, |
| 6017 * or `null` if this class does not declare a getter with the given name. |
| 6018 * |
| 6019 * @param getterName the name of the getter to be returned |
| 6020 * @return the getter declared in this class with the given name |
| 6021 */ |
| 6022 PropertyAccessorElement getGetter(String getterName); |
| 6023 |
| 6024 /** |
| 6025 * Return an array containing all of the interfaces that are implemented by th
is interface. Note |
| 6026 * that this is <b>not</b>, in general, equivalent to getting the interfaces f
rom this type's |
| 6027 * element because the types returned by this method will have had their type
parameters replaced. |
| 6028 * |
| 6029 * @return the interfaces that are implemented by this type |
| 6030 */ |
| 6031 List<InterfaceType> get interfaces; |
| 6032 |
| 6033 /** |
| 6034 * Return the least upper bound of this type and the given type, or `null` if
there is no |
| 6035 * least upper bound. |
| 6036 * |
| 6037 * Given two interfaces <i>I</i> and <i>J</i>, let <i>S<sub>I</sub></i> be the
set of |
| 6038 * superinterfaces of <i>I<i>, let <i>S<sub>J</sub></i> be the set of superint
erfaces of <i>J</i> |
| 6039 * and let <i>S = (I ∪ S<sub>I</sub>) ∩ (J ∪ S<sub>J</sub>)</i>. F
urthermore, we |
| 6040 * define <i>S<sub>n</sub> = {T | T ∈ S ∧ depth(T) = n}</i> for any f
inite <i>n</i>, |
| 6041 * where <i>depth(T)</i> is the number of steps in the longest inheritance pat
h from <i>T</i> to |
| 6042 * <i>Object</i>. Let <i>q</i> be the largest number such that <i>S<sub>q</sub
></i> has |
| 6043 * cardinality one. The least upper bound of <i>I</i> and <i>J</i> is the sole
element of |
| 6044 * <i>S<sub>q</sub></i>. |
| 6045 * |
| 6046 * @param type the other type used to compute the least upper bound |
| 6047 * @return the least upper bound of this type and the given type |
| 6048 */ |
| 6049 @override |
| 6050 DartType getLeastUpperBound(DartType type); |
| 6051 |
| 6052 /** |
| 6053 * Return the element representing the method with the given name that is decl
ared in this class, |
| 6054 * or `null` if this class does not declare a method with the given name. |
| 6055 * |
| 6056 * @param methodName the name of the method to be returned |
| 6057 * @return the method declared in this class with the given name |
| 6058 */ |
| 6059 MethodElement getMethod(String methodName); |
| 6060 |
| 6061 /** |
| 6062 * Return an array containing all of the methods declared in this type. |
| 6063 * |
| 6064 * @return the methods declared in this type |
| 6065 */ |
| 6066 List<MethodElement> get methods; |
| 6067 |
| 6068 /** |
| 6069 * Return an array containing all of the mixins that are applied to the class
being extended in |
| 6070 * order to derive the superclass of this class. Note that this is <b>not</b>,
in general, |
| 6071 * equivalent to getting the mixins from this type's element because the types
returned by this |
| 6072 * method will have had their type parameters replaced. |
| 6073 * |
| 6074 * @return the mixins that are applied to derive the superclass of this class |
| 6075 */ |
| 6076 List<InterfaceType> get mixins; |
| 6077 |
| 6078 /** |
| 6079 * Return the element representing the setter with the given name that is decl
ared in this class, |
| 6080 * or `null` if this class does not declare a setter with the given name. |
| 6081 * |
| 6082 * @param setterName the name of the setter to be returned |
| 6083 * @return the setter declared in this class with the given name |
| 6084 */ |
| 6085 PropertyAccessorElement getSetter(String setterName); |
| 6086 |
| 6087 /** |
| 6088 * Return the type representing the superclass of this type, or null if this t
ype represents the |
| 6089 * class 'Object'. Note that this is <b>not</b>, in general, equivalent to get
ting the superclass |
| 6090 * from this type's element because the type returned by this method will have
had it's type |
| 6091 * parameters replaced. |
| 6092 * |
| 6093 * @return the superclass of this type |
| 6094 */ |
| 6095 InterfaceType get superclass; |
| 6096 |
| 6097 /** |
| 6098 * Return `true` if this type is a direct supertype of the given type. The imp
licit |
| 6099 * interface of class <i>I</i> is a direct supertype of the implicit interface
of class <i>J</i> |
| 6100 * iff: |
| 6101 * * <i>I</i> is Object, and <i>J</i> has no extends clause. |
| 6102 * * <i>I</i> is listed in the extends clause of <i>J</i>. |
| 6103 * * <i>I</i> is listed in the implements clause of <i>J</i>. |
| 6104 * * <i>I</i> is listed in the with clause of <i>J</i>. |
| 6105 * * <i>J</i> is a mixin application of the mixin of <i>I</i>. |
| 6106 * |
| 6107 * @param type the type being compared with this type |
| 6108 * @return `true` if this type is a direct supertype of the given type |
| 6109 */ |
| 6110 bool isDirectSupertypeOf(InterfaceType type); |
| 6111 |
| 6112 /** |
| 6113 * Return `true` if this type is more specific than the given type. An interfa
ce type |
| 6114 * <i>T</i> is more specific than an interface type <i>S</i>, written <i>T &la
quo; S</i>, if one |
| 6115 * of the following conditions is met: |
| 6116 * * Reflexivity: <i>T</i> is <i>S</i>. |
| 6117 * * <i>T</i> is bottom. |
| 6118 * * <i>S</i> is dynamic. |
| 6119 * * Direct supertype: <i>S</i> is a direct supertype of <i>T</i>. |
| 6120 * * <i>T</i> is a type parameter and <i>S</i> is the upper bound of <i>T</i>. |
| 6121 * * Covariance: <i>T</i> is of the form <i>I<T<sub>1</sub>, …, T<su
b>n</sub>></i> |
| 6122 * and S</i> is of the form <i>I<S<sub>1</sub>, …, S<sub>n</sub>>
</i> and |
| 6123 * <i>T<sub>i</sub> « S<sub>i</sub></i>, <i>1 <= i <= n</i>. |
| 6124 * * Transitivity: <i>T « U</i> and <i>U « S</i>. |
| 6125 * |
| 6126 * @param type the type being compared with this type |
| 6127 * @return `true` if this type is more specific than the given type |
| 6128 */ |
| 6129 @override |
| 6130 bool isMoreSpecificThan(DartType type); |
| 6131 |
| 6132 /** |
| 6133 * Return `true` if this type is a subtype of the given type. An interface typ
e <i>T</i> is |
| 6134 * a subtype of an interface type <i>S</i>, written <i>T</i> <: <i>S</i>, iff |
| 6135 * <i>[bottom/dynamic]T</i> « <i>S</i> (<i>T</i> is more specific than <
i>S</i>). If an |
| 6136 * interface type <i>I</i> includes a method named <i>call()</i>, and the type
of <i>call()</i> is |
| 6137 * the function type <i>F</i>, then <i>I</i> is considered to be a subtype of
<i>F</i>. |
| 6138 * |
| 6139 * @param type the type being compared with this type |
| 6140 * @return `true` if this type is a subtype of the given type |
| 6141 */ |
| 6142 @override |
| 6143 bool isSubtypeOf(DartType type); |
| 6144 |
| 6145 /** |
| 6146 * Return the element representing the constructor that results from looking u
p the given |
| 6147 * constructor in this class with respect to the given library, or `null` if t
he look up |
| 6148 * fails. The behavior of this method is defined by the Dart Language Specific
ation in section |
| 6149 * 12.11.1: <blockquote>If <i>e</i> is of the form <b>new</b> <i>T.id()</i> th
en let <i>q<i> be |
| 6150 * the constructor <i>T.id</i>, otherwise let <i>q<i> be the constructor <i>T<
i>. Otherwise, if |
| 6151 * <i>q</i> is not defined or not accessible, a NoSuchMethodException is throw
n. </blockquote> |
| 6152 * |
| 6153 * @param constructorName the name of the constructor being looked up |
| 6154 * @param library the library with respect to which the lookup is being perfor
med |
| 6155 * @return the result of looking up the given constructor in this class with r
espect to the given |
| 6156 * library |
| 6157 */ |
| 6158 ConstructorElement lookUpConstructor(String constructorName, LibraryElement li
brary); |
| 6159 |
| 6160 /** |
| 6161 * Return the element representing the getter that results from looking up the
given getter in |
| 6162 * this class with respect to the given library, or `null` if the look up fail
s. The |
| 6163 * behavior of this method is defined by the Dart Language Specification in se
ction 12.15.1: |
| 6164 * <blockquote>The result of looking up getter (respectively setter) <i>m</i>
in class <i>C</i> |
| 6165 * with respect to library <i>L</i> is: |
| 6166 * * If <i>C</i> declares an instance getter (respectively setter) named <i>m<
/i> that is |
| 6167 * accessible to <i>L</i>, then that getter (respectively setter) is the resul
t of the lookup. |
| 6168 * Otherwise, if <i>C</i> has a superclass <i>S</i>, then the result of the lo
okup is the result |
| 6169 * of looking up getter (respectively setter) <i>m</i> in <i>S</i> with respec
t to <i>L</i>. |
| 6170 * Otherwise, we say that the lookup has failed. |
| 6171 * </blockquote> |
| 6172 * |
| 6173 * @param getterName the name of the getter being looked up |
| 6174 * @param library the library with respect to which the lookup is being perfor
med |
| 6175 * @return the result of looking up the given getter in this class with respec
t to the given |
| 6176 * library |
| 6177 */ |
| 6178 PropertyAccessorElement lookUpGetter(String getterName, LibraryElement library
); |
| 6179 |
| 6180 /** |
| 6181 * Return the element representing the getter that results from looking up the
given getter in the |
| 6182 * superclass of this class with respect to the given library, or `null` if th
e look up |
| 6183 * fails. The behavior of this method is defined by the Dart Language Specific
ation in section |
| 6184 * 12.15.1: <blockquote>The result of looking up getter (respectively setter)
<i>m</i> in class |
| 6185 * <i>C</i> with respect to library <i>L</i> is: |
| 6186 * * If <i>C</i> declares an instance getter (respectively setter) named <i>m<
/i> that is |
| 6187 * accessible to <i>L</i>, then that getter (respectively setter) is the resul
t of the lookup. |
| 6188 * Otherwise, if <i>C</i> has a superclass <i>S</i>, then the result of the lo
okup is the result |
| 6189 * of looking up getter (respectively setter) <i>m</i> in <i>S</i> with respec
t to <i>L</i>. |
| 6190 * Otherwise, we say that the lookup has failed. |
| 6191 * </blockquote> |
| 6192 * |
| 6193 * @param getterName the name of the getter being looked up |
| 6194 * @param library the library with respect to which the lookup is being perfor
med |
| 6195 * @return the result of looking up the given getter in this class with respec
t to the given |
| 6196 * library |
| 6197 */ |
| 6198 PropertyAccessorElement lookUpGetterInSuperclass(String getterName, LibraryEle
ment library); |
| 6199 |
| 6200 /** |
| 6201 * Return the element representing the method that results from looking up the
given method in |
| 6202 * this class with respect to the given library, or `null` if the look up fail
s. The |
| 6203 * behavior of this method is defined by the Dart Language Specification in se
ction 12.15.1: |
| 6204 * <blockquote> The result of looking up method <i>m</i> in class <i>C</i> wit
h respect to library |
| 6205 * <i>L</i> is: |
| 6206 * * If <i>C</i> declares an instance method named <i>m</i> that is accessible
to <i>L</i>, then |
| 6207 * that method is the result of the lookup. Otherwise, if <i>C</i> has a super
class <i>S</i>, then |
| 6208 * the result of the lookup is the result of looking up method <i>m</i> in <i>
S</i> with respect |
| 6209 * to <i>L</i>. Otherwise, we say that the lookup has failed. |
| 6210 * </blockquote> |
| 6211 * |
| 6212 * @param methodName the name of the method being looked up |
| 6213 * @param library the library with respect to which the lookup is being perfor
med |
| 6214 * @return the result of looking up the given method in this class with respec
t to the given |
| 6215 * library |
| 6216 */ |
| 6217 MethodElement lookUpMethod(String methodName, LibraryElement library); |
| 6218 |
| 6219 /** |
| 6220 * Return the element representing the method that results from looking up the
given method in the |
| 6221 * superclass of this class with respect to the given library, or `null` if th
e look up |
| 6222 * fails. The behavior of this method is defined by the Dart Language Specific
ation in section |
| 6223 * 12.15.1: <blockquote> The result of looking up method <i>m</i> in class <i>
C</i> with respect |
| 6224 * to library <i>L</i> is: |
| 6225 * * If <i>C</i> declares an instance method named <i>m</i> that is accessible
to <i>L</i>, then |
| 6226 * that method is the result of the lookup. Otherwise, if <i>C</i> has a super
class <i>S</i>, then |
| 6227 * the result of the lookup is the result of looking up method <i>m</i> in <i>
S</i> with respect |
| 6228 * to <i>L</i>. Otherwise, we say that the lookup has failed. |
| 6229 * </blockquote> |
| 6230 * |
| 6231 * @param methodName the name of the method being looked up |
| 6232 * @param library the library with respect to which the lookup is being perfor
med |
| 6233 * @return the result of looking up the given method in this class with respec
t to the given |
| 6234 * library |
| 6235 */ |
| 6236 MethodElement lookUpMethodInSuperclass(String methodName, LibraryElement libra
ry); |
| 6237 |
| 6238 /** |
| 6239 * Return the element representing the setter that results from looking up the
given setter in |
| 6240 * this class with respect to the given library, or `null` if the look up fail
s. The |
| 6241 * behavior of this method is defined by the Dart Language Specification in se
ction 12.16: |
| 6242 * <blockquote> The result of looking up getter (respectively setter) <i>m</i>
in class <i>C</i> |
| 6243 * with respect to library <i>L</i> is: |
| 6244 * * If <i>C</i> declares an instance getter (respectively setter) named <i>m<
/i> that is |
| 6245 * accessible to <i>L</i>, then that getter (respectively setter) is the resul
t of the lookup. |
| 6246 * Otherwise, if <i>C</i> has a superclass <i>S</i>, then the result of the lo
okup is the result |
| 6247 * of looking up getter (respectively setter) <i>m</i> in <i>S</i> with respec
t to <i>L</i>. |
| 6248 * Otherwise, we say that the lookup has failed. |
| 6249 * </blockquote> |
| 6250 * |
| 6251 * @param setterName the name of the setter being looked up |
| 6252 * @param library the library with respect to which the lookup is being perfor
med |
| 6253 * @return the result of looking up the given setter in this class with respec
t to the given |
| 6254 * library |
| 6255 */ |
| 6256 PropertyAccessorElement lookUpSetter(String setterName, LibraryElement library
); |
| 6257 |
| 6258 /** |
| 6259 * Return the element representing the setter that results from looking up the
given setter in the |
| 6260 * superclass of this class with respect to the given library, or `null` if th
e look up |
| 6261 * fails. The behavior of this method is defined by the Dart Language Specific
ation in section |
| 6262 * 12.16: <blockquote> The result of looking up getter (respectively setter) <
i>m</i> in class |
| 6263 * <i>C</i> with respect to library <i>L</i> is: |
| 6264 * * If <i>C</i> declares an instance getter (respectively setter) named <i>m<
/i> that is |
| 6265 * accessible to <i>L</i>, then that getter (respectively setter) is the resul
t of the lookup. |
| 6266 * Otherwise, if <i>C</i> has a superclass <i>S</i>, then the result of the lo
okup is the result |
| 6267 * of looking up getter (respectively setter) <i>m</i> in <i>S</i> with respec
t to <i>L</i>. |
| 6268 * Otherwise, we say that the lookup has failed. |
| 6269 * </blockquote> |
| 6270 * |
| 6271 * @param setterName the name of the setter being looked up |
| 6272 * @param library the library with respect to which the lookup is being perfor
med |
| 6273 * @return the result of looking up the given setter in this class with respec
t to the given |
| 6274 * library |
| 6275 */ |
| 6276 PropertyAccessorElement lookUpSetterInSuperclass(String setterName, LibraryEle
ment library); |
| 6277 |
| 6278 /** |
| 6279 * Return the type resulting from substituting the given arguments for this ty
pe's parameters. |
| 6280 * This is fully equivalent to `substitute(argumentTypes, getTypeArguments())`
. |
| 6281 * |
| 6282 * @param argumentTypes the actual type arguments being substituted for the ty
pe parameters |
| 6283 * @return the result of performing the substitution |
| 6284 */ |
| 6285 InterfaceType substitute4(List<DartType> argumentTypes); |
| 6286 |
| 6287 @override |
| 6288 InterfaceType substitute2(List<DartType> argumentTypes, List<DartType> paramet
erTypes); |
| 6289 } |
| 6290 |
| 6291 /** |
| 6292 * Instances of the class `InterfaceTypeImpl` defines the behavior common to obj
ects |
| 6293 * representing the type introduced by either a class or an interface, or a refe
rence to such a |
| 6294 * type. |
| 6295 */ |
| 6296 class InterfaceTypeImpl extends TypeImpl implements InterfaceType { |
| 6297 /** |
| 6298 * An empty array of types. |
| 6299 */ |
| 6300 static List<InterfaceType> EMPTY_ARRAY = new List<InterfaceType>(0); |
| 6301 |
| 6302 /** |
| 6303 * This method computes the longest inheritance path from some passed [Type] t
o Object. |
| 6304 * |
| 6305 * @param type the [Type] to compute the longest inheritance path of from the
passed |
| 6306 * [Type] to Object |
| 6307 * @return the computed longest inheritance path to Object |
| 6308 * @see InterfaceType#getLeastUpperBound(Type) |
| 6309 */ |
| 6310 static int computeLongestInheritancePathToObject(InterfaceType type) => _compu
teLongestInheritancePathToObject(type, 0, new Set<ClassElement>()); |
| 6311 |
| 6312 /** |
| 6313 * Returns the set of all superinterfaces of the passed [Type]. |
| 6314 * |
| 6315 * @param type the [Type] to compute the set of superinterfaces of |
| 6316 * @return the [Set] of superinterfaces of the passed [Type] |
| 6317 * @see #getLeastUpperBound(Type) |
| 6318 */ |
| 6319 static Set<InterfaceType> computeSuperinterfaceSet(InterfaceType type) => _com
puteSuperinterfaceSet(type, new Set<InterfaceType>()); |
| 6320 |
| 6321 /** |
| 6322 * This method computes the longest inheritance path from some passed [Type] t
o Object. This |
| 6323 * method calls itself recursively, callers should use the public method |
| 6324 * [computeLongestInheritancePathToObject]. |
| 6325 * |
| 6326 * @param type the [Type] to compute the longest inheritance path of from the
passed |
| 6327 * [Type] to Object |
| 6328 * @param depth a field used recursively |
| 6329 * @param visitedClasses the classes that have already been visited |
| 6330 * @return the computed longest inheritance path to Object |
| 6331 * @see #computeLongestInheritancePathToObject(Type) |
| 6332 * @see #getLeastUpperBound(Type) |
| 6333 */ |
| 6334 static int _computeLongestInheritancePathToObject(InterfaceType type, int dept
h, Set<ClassElement> visitedClasses) { |
| 6335 ClassElement classElement = type.element; |
| 6336 // Object case |
| 6337 if (classElement.supertype == null || visitedClasses.contains(classElement))
{ |
| 6338 return depth; |
| 6339 } |
| 6340 int longestPath = 1; |
| 6341 try { |
| 6342 visitedClasses.add(classElement); |
| 6343 List<InterfaceType> superinterfaces = classElement.interfaces; |
| 6344 int pathLength; |
| 6345 if (superinterfaces.length > 0) { |
| 6346 // loop through each of the superinterfaces recursively calling this met
hod and keeping track |
| 6347 // of the longest path to return |
| 6348 for (InterfaceType superinterface in superinterfaces) { |
| 6349 pathLength = _computeLongestInheritancePathToObject(superinterface, de
pth + 1, visitedClasses); |
| 6350 if (pathLength > longestPath) { |
| 6351 longestPath = pathLength; |
| 6352 } |
| 6353 } |
| 6354 } |
| 6355 // finally, perform this same check on the super type |
| 6356 // TODO(brianwilkerson) Does this also need to add in the number of mixin
classes? |
| 6357 InterfaceType supertype = classElement.supertype; |
| 6358 pathLength = _computeLongestInheritancePathToObject(supertype, depth + 1,
visitedClasses); |
| 6359 if (pathLength > longestPath) { |
| 6360 longestPath = pathLength; |
| 6361 } |
| 6362 } finally { |
| 6363 visitedClasses.remove(classElement); |
| 6364 } |
| 6365 return longestPath; |
| 6366 } |
| 6367 |
| 6368 /** |
| 6369 * Returns the set of all superinterfaces of the passed [Type]. This is a recu
rsive method, |
| 6370 * callers should call the public [computeSuperinterfaceSet]. |
| 6371 * |
| 6372 * @param type the [Type] to compute the set of superinterfaces of |
| 6373 * @param set a [HashSet] used recursively by this method |
| 6374 * @return the [Set] of superinterfaces of the passed [Type] |
| 6375 * @see #computeSuperinterfaceSet(Type) |
| 6376 * @see #getLeastUpperBound(Type) |
| 6377 */ |
| 6378 static Set<InterfaceType> _computeSuperinterfaceSet(InterfaceType type, Set<In
terfaceType> set) { |
| 6379 Element element = type.element; |
| 6380 if (element != null) { |
| 6381 List<InterfaceType> superinterfaces = type.interfaces; |
| 6382 for (InterfaceType superinterface in superinterfaces) { |
| 6383 if (set.add(superinterface)) { |
| 6384 _computeSuperinterfaceSet(superinterface, set); |
| 6385 } |
| 6386 } |
| 6387 InterfaceType supertype = type.superclass; |
| 6388 if (supertype != null) { |
| 6389 if (set.add(supertype)) { |
| 6390 _computeSuperinterfaceSet(supertype, set); |
| 6391 } |
| 6392 } |
| 6393 } |
| 6394 return set; |
| 6395 } |
| 6396 |
| 6397 /** |
| 6398 * Return the intersection of the given sets of types, where intersection is b
ased on the equality |
| 6399 * of the types themselves. |
| 6400 * |
| 6401 * @param first the first set of types to be intersected |
| 6402 * @param second the second set of types to be intersected |
| 6403 * @return the intersection of the given sets of types |
| 6404 */ |
| 6405 static List<InterfaceType> _intersection(Set<InterfaceType> first, Set<Interfa
ceType> second) { |
| 6406 Set<InterfaceType> result = new Set<InterfaceType>.from(first); |
| 6407 result.retainAll(second); |
| 6408 return new List.from(result); |
| 6409 } |
| 6410 |
| 6411 /** |
| 6412 * Return the "least upper bound" of the given types under the assumption that
the types have the |
| 6413 * same element and differ only in terms of the type arguments. The resulting
type is composed by |
| 6414 * comparing the corresponding type arguments, keeping those that are the same
, and using |
| 6415 * 'dynamic' for those that are different. |
| 6416 * |
| 6417 * @param firstType the first type |
| 6418 * @param secondType the second type |
| 6419 * @return the "least upper bound" of the given types |
| 6420 */ |
| 6421 static InterfaceType _leastUpperBound(InterfaceType firstType, InterfaceType s
econdType) { |
| 6422 if (firstType == secondType) { |
| 6423 return firstType; |
| 6424 } |
| 6425 List<DartType> firstArguments = firstType.typeArguments; |
| 6426 List<DartType> secondArguments = secondType.typeArguments; |
| 6427 int argumentCount = firstArguments.length; |
| 6428 if (argumentCount == 0) { |
| 6429 return firstType; |
| 6430 } |
| 6431 List<DartType> lubArguments = new List<DartType>(argumentCount); |
| 6432 for (int i = 0; i < argumentCount; i++) { |
| 6433 // |
| 6434 // Ideally we would take the least upper bound of the two argument types,
but this can cause |
| 6435 // an infinite recursion (such as when finding the least upper bound of St
ring and num). |
| 6436 // |
| 6437 if (firstArguments[i] == secondArguments[i]) { |
| 6438 lubArguments[i] = firstArguments[i]; |
| 6439 } |
| 6440 if (lubArguments[i] == null) { |
| 6441 lubArguments[i] = DynamicTypeImpl.instance; |
| 6442 } |
| 6443 } |
| 6444 InterfaceTypeImpl lub = new InterfaceTypeImpl.con1(firstType.element); |
| 6445 lub.typeArguments = lubArguments; |
| 6446 return lub; |
| 6447 } |
| 6448 |
| 6449 /** |
| 6450 * An array containing the actual types of the type arguments. |
| 6451 */ |
| 6452 List<DartType> typeArguments = TypeImpl.EMPTY_ARRAY; |
| 6453 |
| 6454 /** |
| 6455 * Initialize a newly created type to be declared by the given element. |
| 6456 * |
| 6457 * @param element the element representing the declaration of the type |
| 6458 */ |
| 6459 InterfaceTypeImpl.con1(ClassElement element) : super(element, element.displayN
ame); |
| 6460 |
| 6461 /** |
| 6462 * Initialize a newly created type to have the given name. This constructor sh
ould only be used in |
| 6463 * cases where there is no declaration of the type. |
| 6464 * |
| 6465 * @param name the name of the type |
| 6466 */ |
| 6467 InterfaceTypeImpl.con2(String name) : super(null, name); |
| 6468 |
| 6469 @override |
| 6470 bool operator ==(Object object) => internalEquals(object, new Set<ElementPair>
()); |
| 6471 |
| 6472 @override |
| 6473 List<PropertyAccessorElement> get accessors { |
| 6474 List<PropertyAccessorElement> accessors = element.accessors; |
| 6475 List<PropertyAccessorElement> members = new List<PropertyAccessorElement>(ac
cessors.length); |
| 6476 for (int i = 0; i < accessors.length; i++) { |
| 6477 members[i] = PropertyAccessorMember.from(accessors[i], this); |
| 6478 } |
| 6479 return members; |
| 6480 } |
| 6481 |
| 6482 @override |
| 6483 String get displayName { |
| 6484 String name = this.name; |
| 6485 List<DartType> typeArguments = this.typeArguments; |
| 6486 bool allDynamic = true; |
| 6487 for (DartType type in typeArguments) { |
| 6488 if (type != null && !type.isDynamic) { |
| 6489 allDynamic = false; |
| 6490 break; |
| 6491 } |
| 6492 } |
| 6493 // If there is at least one non-dynamic type, then list them out |
| 6494 if (!allDynamic) { |
| 6495 JavaStringBuilder builder = new JavaStringBuilder(); |
| 6496 builder.append(name); |
| 6497 builder.append("<"); |
| 6498 for (int i = 0; i < typeArguments.length; i++) { |
| 6499 if (i != 0) { |
| 6500 builder.append(", "); |
| 6501 } |
| 6502 DartType typeArg = typeArguments[i]; |
| 6503 builder.append(typeArg.displayName); |
| 6504 } |
| 6505 builder.append(">"); |
| 6506 name = builder.toString(); |
| 6507 } |
| 6508 return name; |
| 6509 } |
| 6510 |
| 6511 @override |
| 6512 ClassElement get element => super.element as ClassElement; |
| 6513 |
| 6514 @override |
| 6515 PropertyAccessorElement getGetter(String getterName) => PropertyAccessorMember
.from((element as ClassElementImpl).getGetter(getterName), this); |
| 6516 |
| 6517 @override |
| 6518 List<InterfaceType> get interfaces { |
| 6519 ClassElement classElement = element; |
| 6520 List<InterfaceType> interfaces = classElement.interfaces; |
| 6521 List<TypeParameterElement> typeParameters = classElement.typeParameters; |
| 6522 List<DartType> parameterTypes = classElement.type.typeArguments; |
| 6523 if (typeParameters.length == 0) { |
| 6524 return interfaces; |
| 6525 } |
| 6526 int count = interfaces.length; |
| 6527 List<InterfaceType> typedInterfaces = new List<InterfaceType>(count); |
| 6528 for (int i = 0; i < count; i++) { |
| 6529 typedInterfaces[i] = interfaces[i].substitute2(typeArguments, parameterTyp
es); |
| 6530 } |
| 6531 return typedInterfaces; |
| 6532 } |
| 6533 |
| 6534 @override |
| 6535 DartType getLeastUpperBound(DartType type) { |
| 6536 // quick check for self |
| 6537 if (identical(type, this)) { |
| 6538 return this; |
| 6539 } |
| 6540 // dynamic |
| 6541 DartType dynamicType = DynamicTypeImpl.instance; |
| 6542 if (identical(this, dynamicType) || identical(type, dynamicType)) { |
| 6543 return dynamicType; |
| 6544 } |
| 6545 // TODO (jwren) opportunity here for a better, faster algorithm if this turn
s out to be a bottle-neck |
| 6546 if (type is! InterfaceType) { |
| 6547 return null; |
| 6548 } |
| 6549 // new names to match up with the spec |
| 6550 InterfaceType i = this; |
| 6551 InterfaceType j = type as InterfaceType; |
| 6552 // compute set of supertypes |
| 6553 Set<InterfaceType> si = computeSuperinterfaceSet(i); |
| 6554 Set<InterfaceType> sj = computeSuperinterfaceSet(j); |
| 6555 // union si with i and sj with j |
| 6556 si.add(i); |
| 6557 sj.add(j); |
| 6558 // compute intersection, reference as set 's' |
| 6559 List<InterfaceType> s = _intersection(si, sj); |
| 6560 // for each element in Set s, compute the largest inheritance path to Object |
| 6561 List<int> depths = new List<int>.filled(s.length, 0); |
| 6562 int maxDepth = 0; |
| 6563 for (int n = 0; n < s.length; n++) { |
| 6564 depths[n] = computeLongestInheritancePathToObject(s[n]); |
| 6565 if (depths[n] > maxDepth) { |
| 6566 maxDepth = depths[n]; |
| 6567 } |
| 6568 } |
| 6569 // ensure that the currently computed maxDepth is unique, |
| 6570 // otherwise, decrement and test for uniqueness again |
| 6571 for (; maxDepth >= 0; maxDepth--) { |
| 6572 int indexOfLeastUpperBound = -1; |
| 6573 int numberOfTypesAtMaxDepth = 0; |
| 6574 for (int m = 0; m < depths.length; m++) { |
| 6575 if (depths[m] == maxDepth) { |
| 6576 numberOfTypesAtMaxDepth++; |
| 6577 indexOfLeastUpperBound = m; |
| 6578 } |
| 6579 } |
| 6580 if (numberOfTypesAtMaxDepth == 1) { |
| 6581 return s[indexOfLeastUpperBound]; |
| 6582 } |
| 6583 } |
| 6584 // illegal state, log and return null- Object at maxDepth == 0 should always
return itself as |
| 6585 // the least upper bound. |
| 6586 // TODO (jwren) log the error state |
| 6587 return null; |
| 6588 } |
| 6589 |
| 6590 @override |
| 6591 MethodElement getMethod(String methodName) => MethodMember.from((element as Cl
assElementImpl).getMethod(methodName), this); |
| 6592 |
| 6593 @override |
| 6594 List<MethodElement> get methods { |
| 6595 List<MethodElement> methods = element.methods; |
| 6596 List<MethodElement> members = new List<MethodElement>(methods.length); |
| 6597 for (int i = 0; i < methods.length; i++) { |
| 6598 members[i] = MethodMember.from(methods[i], this); |
| 6599 } |
| 6600 return members; |
| 6601 } |
| 6602 |
| 6603 @override |
| 6604 List<InterfaceType> get mixins { |
| 6605 ClassElement classElement = element; |
| 6606 List<InterfaceType> mixins = classElement.mixins; |
| 6607 List<TypeParameterElement> typeParameters = classElement.typeParameters; |
| 6608 List<DartType> parameterTypes = classElement.type.typeArguments; |
| 6609 if (typeParameters.length == 0) { |
| 6610 return mixins; |
| 6611 } |
| 6612 int count = mixins.length; |
| 6613 List<InterfaceType> typedMixins = new List<InterfaceType>(count); |
| 6614 for (int i = 0; i < count; i++) { |
| 6615 typedMixins[i] = mixins[i].substitute2(typeArguments, parameterTypes); |
| 6616 } |
| 6617 return typedMixins; |
| 6618 } |
| 6619 |
| 6620 @override |
| 6621 PropertyAccessorElement getSetter(String setterName) => PropertyAccessorMember
.from((element as ClassElementImpl).getSetter(setterName), this); |
| 6622 |
| 6623 @override |
| 6624 InterfaceType get superclass { |
| 6625 ClassElement classElement = element; |
| 6626 InterfaceType supertype = classElement.supertype; |
| 6627 if (supertype == null) { |
| 6628 return null; |
| 6629 } |
| 6630 return supertype.substitute2(typeArguments, classElement.type.typeArguments)
; |
| 6631 } |
| 6632 |
| 6633 @override |
| 6634 List<TypeParameterElement> get typeParameters => element.typeParameters; |
| 6635 |
| 6636 @override |
| 6637 int get hashCode { |
| 6638 ClassElement element = this.element; |
| 6639 if (element == null) { |
| 6640 return 0; |
| 6641 } |
| 6642 return element.hashCode; |
| 6643 } |
| 6644 |
| 6645 @override |
| 6646 bool get isDartCoreFunction { |
| 6647 ClassElement element = this.element; |
| 6648 if (element == null) { |
| 6649 return false; |
| 6650 } |
| 6651 return element.name == "Function" && element.library.isDartCore; |
| 6652 } |
| 6653 |
| 6654 @override |
| 6655 bool isDirectSupertypeOf(InterfaceType type) { |
| 6656 InterfaceType i = this; |
| 6657 InterfaceType j = type; |
| 6658 ClassElement jElement = j.element; |
| 6659 InterfaceType supertype = jElement.supertype; |
| 6660 // |
| 6661 // If J has no direct supertype then it is Object, and Object has no direct
supertypes. |
| 6662 // |
| 6663 if (supertype == null) { |
| 6664 return false; |
| 6665 } |
| 6666 // |
| 6667 // I is listed in the extends clause of J. |
| 6668 // |
| 6669 List<DartType> jArgs = j.typeArguments; |
| 6670 List<DartType> jVars = jElement.type.typeArguments; |
| 6671 supertype = supertype.substitute2(jArgs, jVars); |
| 6672 if (supertype == i) { |
| 6673 return true; |
| 6674 } |
| 6675 // |
| 6676 // I is listed in the implements clause of J. |
| 6677 // |
| 6678 for (InterfaceType interfaceType in jElement.interfaces) { |
| 6679 interfaceType = interfaceType.substitute2(jArgs, jVars); |
| 6680 if (interfaceType == i) { |
| 6681 return true; |
| 6682 } |
| 6683 } |
| 6684 // |
| 6685 // I is listed in the with clause of J. |
| 6686 // |
| 6687 for (InterfaceType mixinType in jElement.mixins) { |
| 6688 mixinType = mixinType.substitute2(jArgs, jVars); |
| 6689 if (mixinType == i) { |
| 6690 return true; |
| 6691 } |
| 6692 } |
| 6693 // |
| 6694 // J is a mixin application of the mixin of I. |
| 6695 // |
| 6696 // TODO(brianwilkerson) Determine whether this needs to be implemented or wh
ether it is covered |
| 6697 // by the case above. |
| 6698 return false; |
| 6699 } |
| 6700 |
| 6701 @override |
| 6702 bool get isObject => element.supertype == null; |
| 6703 |
| 6704 @override |
| 6705 ConstructorElement lookUpConstructor(String constructorName, LibraryElement li
brary) { |
| 6706 // prepare base ConstructorElement |
| 6707 ConstructorElement constructorElement; |
| 6708 if (constructorName == null) { |
| 6709 constructorElement = element.unnamedConstructor; |
| 6710 } else { |
| 6711 constructorElement = element.getNamedConstructor(constructorName); |
| 6712 } |
| 6713 // not found or not accessible |
| 6714 if (constructorElement == null || !constructorElement.isAccessibleIn(library
)) { |
| 6715 return null; |
| 6716 } |
| 6717 // return member |
| 6718 return ConstructorMember.from(constructorElement, this); |
| 6719 } |
| 6720 |
| 6721 @override |
| 6722 PropertyAccessorElement lookUpGetter(String getterName, LibraryElement library
) { |
| 6723 PropertyAccessorElement element = getGetter(getterName); |
| 6724 if (element != null && element.isAccessibleIn(library)) { |
| 6725 return element; |
| 6726 } |
| 6727 return lookUpGetterInSuperclass(getterName, library); |
| 6728 } |
| 6729 |
| 6730 @override |
| 6731 PropertyAccessorElement lookUpGetterInSuperclass(String getterName, LibraryEle
ment library) { |
| 6732 for (InterfaceType mixin in mixins) { |
| 6733 PropertyAccessorElement element = mixin.getGetter(getterName); |
| 6734 if (element != null && element.isAccessibleIn(library)) { |
| 6735 return element; |
| 6736 } |
| 6737 } |
| 6738 Set<ClassElement> visitedClasses = new Set<ClassElement>(); |
| 6739 InterfaceType supertype = superclass; |
| 6740 ClassElement supertypeElement = supertype == null ? null : supertype.element
; |
| 6741 while (supertype != null && !visitedClasses.contains(supertypeElement)) { |
| 6742 visitedClasses.add(supertypeElement); |
| 6743 PropertyAccessorElement element = supertype.getGetter(getterName); |
| 6744 if (element != null && element.isAccessibleIn(library)) { |
| 6745 return element; |
| 6746 } |
| 6747 for (InterfaceType mixin in supertype.mixins) { |
| 6748 element = mixin.getGetter(getterName); |
| 6749 if (element != null && element.isAccessibleIn(library)) { |
| 6750 return element; |
| 6751 } |
| 6752 } |
| 6753 supertype = supertype.superclass; |
| 6754 supertypeElement = supertype == null ? null : supertype.element; |
| 6755 } |
| 6756 return null; |
| 6757 } |
| 6758 |
| 6759 @override |
| 6760 MethodElement lookUpMethod(String methodName, LibraryElement library) { |
| 6761 MethodElement element = getMethod(methodName); |
| 6762 if (element != null && element.isAccessibleIn(library)) { |
| 6763 return element; |
| 6764 } |
| 6765 return lookUpMethodInSuperclass(methodName, library); |
| 6766 } |
| 6767 |
| 6768 @override |
| 6769 MethodElement lookUpMethodInSuperclass(String methodName, LibraryElement libra
ry) { |
| 6770 for (InterfaceType mixin in mixins) { |
| 6771 MethodElement element = mixin.getMethod(methodName); |
| 6772 if (element != null && element.isAccessibleIn(library)) { |
| 6773 return element; |
| 6774 } |
| 6775 } |
| 6776 Set<ClassElement> visitedClasses = new Set<ClassElement>(); |
| 6777 InterfaceType supertype = superclass; |
| 6778 ClassElement supertypeElement = supertype == null ? null : supertype.element
; |
| 6779 while (supertype != null && !visitedClasses.contains(supertypeElement)) { |
| 6780 visitedClasses.add(supertypeElement); |
| 6781 MethodElement element = supertype.getMethod(methodName); |
| 6782 if (element != null && element.isAccessibleIn(library)) { |
| 6783 return element; |
| 6784 } |
| 6785 for (InterfaceType mixin in supertype.mixins) { |
| 6786 element = mixin.getMethod(methodName); |
| 6787 if (element != null && element.isAccessibleIn(library)) { |
| 6788 return element; |
| 6789 } |
| 6790 } |
| 6791 supertype = supertype.superclass; |
| 6792 supertypeElement = supertype == null ? null : supertype.element; |
| 6793 } |
| 6794 return null; |
| 6795 } |
| 6796 |
| 6797 @override |
| 6798 PropertyAccessorElement lookUpSetter(String setterName, LibraryElement library
) { |
| 6799 PropertyAccessorElement element = getSetter(setterName); |
| 6800 if (element != null && element.isAccessibleIn(library)) { |
| 6801 return element; |
| 6802 } |
| 6803 return lookUpSetterInSuperclass(setterName, library); |
| 6804 } |
| 6805 |
| 6806 @override |
| 6807 PropertyAccessorElement lookUpSetterInSuperclass(String setterName, LibraryEle
ment library) { |
| 6808 for (InterfaceType mixin in mixins) { |
| 6809 PropertyAccessorElement element = mixin.getSetter(setterName); |
| 6810 if (element != null && element.isAccessibleIn(library)) { |
| 6811 return element; |
| 6812 } |
| 6813 } |
| 6814 Set<ClassElement> visitedClasses = new Set<ClassElement>(); |
| 6815 InterfaceType supertype = superclass; |
| 6816 ClassElement supertypeElement = supertype == null ? null : supertype.element
; |
| 6817 while (supertype != null && !visitedClasses.contains(supertypeElement)) { |
| 6818 visitedClasses.add(supertypeElement); |
| 6819 PropertyAccessorElement element = supertype.getSetter(setterName); |
| 6820 if (element != null && element.isAccessibleIn(library)) { |
| 6821 return element; |
| 6822 } |
| 6823 for (InterfaceType mixin in supertype.mixins) { |
| 6824 element = mixin.getSetter(setterName); |
| 6825 if (element != null && element.isAccessibleIn(library)) { |
| 6826 return element; |
| 6827 } |
| 6828 } |
| 6829 supertype = supertype.superclass; |
| 6830 supertypeElement = supertype == null ? null : supertype.element; |
| 6831 } |
| 6832 return null; |
| 6833 } |
| 6834 |
| 6835 @override |
| 6836 InterfaceTypeImpl substitute4(List<DartType> argumentTypes) => substitute2(arg
umentTypes, typeArguments); |
| 6837 |
| 6838 @override |
| 6839 InterfaceTypeImpl substitute2(List<DartType> argumentTypes, List<DartType> par
ameterTypes) { |
| 6840 if (argumentTypes.length != parameterTypes.length) { |
| 6841 throw new IllegalArgumentException("argumentTypes.length (${argumentTypes.
length}) != parameterTypes.length (${parameterTypes.length})"); |
| 6842 } |
| 6843 if (argumentTypes.length == 0 || typeArguments.length == 0) { |
| 6844 return this; |
| 6845 } |
| 6846 List<DartType> newTypeArguments = TypeImpl.substitute(typeArguments, argumen
tTypes, parameterTypes); |
| 6847 if (JavaArrays.equals(newTypeArguments, typeArguments)) { |
| 6848 return this; |
| 6849 } |
| 6850 InterfaceTypeImpl newType = new InterfaceTypeImpl.con1(element); |
| 6851 newType.typeArguments = newTypeArguments; |
| 6852 return newType; |
| 6853 } |
| 6854 |
| 6855 @override |
| 6856 void appendTo(JavaStringBuilder builder) { |
| 6857 builder.append(name); |
| 6858 int argumentCount = typeArguments.length; |
| 6859 if (argumentCount > 0) { |
| 6860 builder.append("<"); |
| 6861 for (int i = 0; i < argumentCount; i++) { |
| 6862 if (i > 0) { |
| 6863 builder.append(", "); |
| 6864 } |
| 6865 (typeArguments[i] as TypeImpl).appendTo(builder); |
| 6866 } |
| 6867 builder.append(">"); |
| 6868 } |
| 6869 } |
| 6870 |
| 6871 @override |
| 6872 bool internalEquals(Object object, Set<ElementPair> visitedElementPairs) { |
| 6873 if (object is! InterfaceTypeImpl) { |
| 6874 return false; |
| 6875 } |
| 6876 InterfaceTypeImpl otherType = object as InterfaceTypeImpl; |
| 6877 return (element == otherType.element) && TypeImpl.equalArrays(typeArguments,
otherType.typeArguments, visitedElementPairs); |
| 6878 } |
| 6879 |
| 6880 @override |
| 6881 bool internalIsMoreSpecificThan(DartType type, bool withDynamic, Set<TypeImpl_
TypePair> visitedTypePairs) { |
| 6882 // |
| 6883 // S is dynamic. |
| 6884 // The test to determine whether S is dynamic is done here because dynamic i
s not an instance of |
| 6885 // InterfaceType. |
| 6886 // |
| 6887 if (identical(type, DynamicTypeImpl.instance)) { |
| 6888 return true; |
| 6889 } else if (type is! InterfaceType) { |
| 6890 return false; |
| 6891 } |
| 6892 return _isMoreSpecificThan(type as InterfaceType, new Set<ClassElement>(), w
ithDynamic, visitedTypePairs); |
| 6893 } |
| 6894 |
| 6895 @override |
| 6896 bool internalIsSubtypeOf(DartType type, Set<TypeImpl_TypePair> visitedTypePair
s) { |
| 6897 // |
| 6898 // T is a subtype of S, written T <: S, iff [bottom/dynamic]T << S |
| 6899 // |
| 6900 if (type.isDynamic) { |
| 6901 return true; |
| 6902 } else if (type is TypeParameterType) { |
| 6903 return false; |
| 6904 } else if (type is FunctionType) { |
| 6905 ClassElement element = this.element; |
| 6906 MethodElement callMethod = element.lookUpMethod("call", element.library); |
| 6907 if (callMethod != null) { |
| 6908 return callMethod.type.isSubtypeOf(type); |
| 6909 } |
| 6910 return false; |
| 6911 } else if (type is! InterfaceType) { |
| 6912 return false; |
| 6913 } else if (this == type) { |
| 6914 return true; |
| 6915 } |
| 6916 return _isSubtypeOf(type as InterfaceType, new Set<ClassElement>(), visitedT
ypePairs); |
| 6917 } |
| 6918 |
| 6919 bool _isMoreSpecificThan(InterfaceType s, Set<ClassElement> visitedClasses, bo
ol withDynamic, Set<TypeImpl_TypePair> visitedTypePairs) { |
| 6920 // |
| 6921 // A type T is more specific than a type S, written T << S, if one of the f
ollowing conditions |
| 6922 // is met: |
| 6923 // |
| 6924 // Reflexivity: T is S. |
| 6925 // |
| 6926 if (this == s) { |
| 6927 return true; |
| 6928 } |
| 6929 // |
| 6930 // T is bottom. (This case is handled by the class BottomTypeImpl.) |
| 6931 // |
| 6932 // Direct supertype: S is a direct supertype of T. |
| 6933 // |
| 6934 if (s.isDirectSupertypeOf(this)) { |
| 6935 return true; |
| 6936 } |
| 6937 // |
| 6938 // Covariance: T is of the form I<T1, ..., Tn> and S is of the form I<S1, ..
., Sn> and Ti << Si, 1 <= i <= n. |
| 6939 // |
| 6940 ClassElement tElement = this.element; |
| 6941 ClassElement sElement = s.element; |
| 6942 if (tElement == sElement) { |
| 6943 List<DartType> tArguments = typeArguments; |
| 6944 List<DartType> sArguments = s.typeArguments; |
| 6945 if (tArguments.length != sArguments.length) { |
| 6946 return false; |
| 6947 } |
| 6948 for (int i = 0; i < tArguments.length; i++) { |
| 6949 if (!(tArguments[i] as TypeImpl).isMoreSpecificThan2(sArguments[i], with
Dynamic, visitedTypePairs)) { |
| 6950 return false; |
| 6951 } |
| 6952 } |
| 6953 return true; |
| 6954 } |
| 6955 // |
| 6956 // Transitivity: T << U and U << S. |
| 6957 // |
| 6958 // First check for infinite loops |
| 6959 ClassElement element = this.element; |
| 6960 if (element == null || visitedClasses.contains(element)) { |
| 6961 return false; |
| 6962 } |
| 6963 visitedClasses.add(element); |
| 6964 // Iterate over all of the types U that are more specific than T because the
y are direct |
| 6965 // supertypes of T and return true if any of them are more specific than S. |
| 6966 InterfaceType supertype = superclass; |
| 6967 if (supertype != null && (supertype as InterfaceTypeImpl)._isMoreSpecificTha
n(s, visitedClasses, withDynamic, visitedTypePairs)) { |
| 6968 return true; |
| 6969 } |
| 6970 for (InterfaceType interfaceType in interfaces) { |
| 6971 if ((interfaceType as InterfaceTypeImpl)._isMoreSpecificThan(s, visitedCla
sses, withDynamic, visitedTypePairs)) { |
| 6972 return true; |
| 6973 } |
| 6974 } |
| 6975 for (InterfaceType mixinType in mixins) { |
| 6976 if ((mixinType as InterfaceTypeImpl)._isMoreSpecificThan(s, visitedClasses
, withDynamic, visitedTypePairs)) { |
| 6977 return true; |
| 6978 } |
| 6979 } |
| 6980 return false; |
| 6981 } |
| 6982 |
| 6983 bool _isSubtypeOf(InterfaceType type, Set<ClassElement> visitedClasses, Set<Ty
peImpl_TypePair> visitedTypePairs) { |
| 6984 InterfaceType typeT = this; |
| 6985 InterfaceType typeS = type; |
| 6986 ClassElement elementT = element; |
| 6987 if (elementT == null || visitedClasses.contains(elementT)) { |
| 6988 return false; |
| 6989 } |
| 6990 visitedClasses.add(elementT); |
| 6991 if (typeT == typeS) { |
| 6992 return true; |
| 6993 } else if (elementT == typeS.element) { |
| 6994 // For each of the type arguments return true if all type args from T is a
subtype of all |
| 6995 // types from S. |
| 6996 List<DartType> typeTArgs = typeT.typeArguments; |
| 6997 List<DartType> typeSArgs = typeS.typeArguments; |
| 6998 if (typeTArgs.length != typeSArgs.length) { |
| 6999 // This case covers the case where two objects are being compared that h
ave a different |
| 7000 // number of parameterized types. |
| 7001 return false; |
| 7002 } |
| 7003 for (int i = 0; i < typeTArgs.length; i++) { |
| 7004 // Recursively call isSubtypeOf the type arguments and return false if t
he T argument is not |
| 7005 // a subtype of the S argument. |
| 7006 if (!(typeTArgs[i] as TypeImpl).isSubtypeOf2(typeSArgs[i], visitedTypePa
irs)) { |
| 7007 return false; |
| 7008 } |
| 7009 } |
| 7010 return true; |
| 7011 } else if (typeS.isDartCoreFunction && elementT.getMethod("call") != null) { |
| 7012 return true; |
| 7013 } |
| 7014 InterfaceType supertype = superclass; |
| 7015 // The type is Object, return false. |
| 7016 if (supertype != null && (supertype as InterfaceTypeImpl)._isSubtypeOf(typeS
, visitedClasses, visitedTypePairs)) { |
| 7017 return true; |
| 7018 } |
| 7019 List<InterfaceType> interfaceTypes = interfaces; |
| 7020 for (InterfaceType interfaceType in interfaceTypes) { |
| 7021 if ((interfaceType as InterfaceTypeImpl)._isSubtypeOf(typeS, visitedClasse
s, visitedTypePairs)) { |
| 7022 return true; |
| 7023 } |
| 7024 } |
| 7025 List<InterfaceType> mixinTypes = mixins; |
| 7026 for (InterfaceType mixinType in mixinTypes) { |
| 7027 if ((mixinType as InterfaceTypeImpl)._isSubtypeOf(typeS, visitedClasses, v
isitedTypePairs)) { |
| 7028 return true; |
| 7029 } |
| 7030 } |
| 7031 return false; |
| 7032 } |
| 7033 } |
| 7034 |
| 7035 /** |
| 7036 * Combination of [AngularTagSelectorElementImpl] and [HasAttributeSelectorEleme
ntImpl]. |
| 7037 */ |
| 7038 class IsTagHasAttributeSelectorElementImpl extends AngularSelectorElementImpl { |
| 7039 final String tagName; |
| 7040 |
| 7041 final String attributeName; |
| 7042 |
| 7043 IsTagHasAttributeSelectorElementImpl(this.tagName, this.attributeName) : super
(null, -1); |
| 7044 |
| 7045 @override |
| 7046 bool apply(XmlTagNode node) => node.tag == tagName && node.getAttribute(attrib
uteName) != null; |
| 7047 } |
| 7048 |
| 7049 /** |
| 7050 * The interface `LabelElement` defines the behavior of elements representing a
label |
| 7051 * associated with a statement. |
| 7052 */ |
| 7053 abstract class LabelElement implements Element { |
| 7054 /** |
| 7055 * Return the executable element in which this label is defined. |
| 7056 * |
| 7057 * @return the executable element in which this label is defined |
| 7058 */ |
| 7059 @override |
| 7060 ExecutableElement get enclosingElement; |
| 7061 } |
| 7062 |
| 7063 /** |
| 5344 * Instances of the class `LabelElementImpl` implement a `LabelElement`. | 7064 * Instances of the class `LabelElementImpl` implement a `LabelElement`. |
| 5345 */ | 7065 */ |
| 5346 class LabelElementImpl extends ElementImpl implements LabelElement { | 7066 class LabelElementImpl extends ElementImpl implements LabelElement { |
| 5347 /** | 7067 /** |
| 5348 * A flag indicating whether this label is associated with a `switch` statemen
t. | 7068 * A flag indicating whether this label is associated with a `switch` statemen
t. |
| 5349 */ | 7069 */ |
| 5350 final bool _onSwitchStatement; | 7070 final bool _onSwitchStatement; |
| 5351 | 7071 |
| 5352 /** | 7072 /** |
| 5353 * A flag indicating whether this label is associated with a `switch` member (
`case` | 7073 * A flag indicating whether this label is associated with a `switch` member (
`case` |
| (...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5389 | 7109 |
| 5390 /** | 7110 /** |
| 5391 * Return `true` if this label is associated with a `switch` statement. | 7111 * Return `true` if this label is associated with a `switch` statement. |
| 5392 * | 7112 * |
| 5393 * @return `true` if this label is associated with a `switch` statement | 7113 * @return `true` if this label is associated with a `switch` statement |
| 5394 */ | 7114 */ |
| 5395 bool get isOnSwitchStatement => _onSwitchStatement; | 7115 bool get isOnSwitchStatement => _onSwitchStatement; |
| 5396 } | 7116 } |
| 5397 | 7117 |
| 5398 /** | 7118 /** |
| 7119 * The interface `LibraryElement` defines the behavior of elements representing
a library. |
| 7120 */ |
| 7121 abstract class LibraryElement implements Element { |
| 7122 /** |
| 7123 * Return the compilation unit that defines this library. |
| 7124 * |
| 7125 * @return the compilation unit that defines this library |
| 7126 */ |
| 7127 CompilationUnitElement get definingCompilationUnit; |
| 7128 |
| 7129 /** |
| 7130 * Return the entry point for this library, or `null` if this library does not
have an entry |
| 7131 * point. The entry point is defined to be a zero argument top-level function
whose name is |
| 7132 * `main`. |
| 7133 * |
| 7134 * @return the entry point for this library |
| 7135 */ |
| 7136 FunctionElement get entryPoint; |
| 7137 |
| 7138 /** |
| 7139 * Return an array containing all of the libraries that are exported from this
library. |
| 7140 * |
| 7141 * @return an array containing all of the libraries that are exported from thi
s library |
| 7142 */ |
| 7143 List<LibraryElement> get exportedLibraries; |
| 7144 |
| 7145 /** |
| 7146 * Return an array containing all of the exports defined in this library. |
| 7147 * |
| 7148 * @return the exports defined in this library |
| 7149 */ |
| 7150 List<ExportElement> get exports; |
| 7151 |
| 7152 /** |
| 7153 * Return an array containing all of the libraries that are imported into this
library. This |
| 7154 * includes all of the libraries that are imported using a prefix (also availa
ble through the |
| 7155 * prefixes returned by [getPrefixes]) and those that are imported without a p
refix. |
| 7156 * |
| 7157 * @return an array containing all of the libraries that are imported into thi
s library |
| 7158 */ |
| 7159 List<LibraryElement> get importedLibraries; |
| 7160 |
| 7161 /** |
| 7162 * Return an array containing all of the imports defined in this library. |
| 7163 * |
| 7164 * @return the imports defined in this library |
| 7165 */ |
| 7166 List<ImportElement> get imports; |
| 7167 |
| 7168 /** |
| 7169 * Return an array containing all of the imports that share the given prefix,
or an empty array if |
| 7170 * there are no such imports. |
| 7171 * |
| 7172 * @param prefixElement the prefix element shared by the returned imports |
| 7173 */ |
| 7174 List<ImportElement> getImportsWithPrefix(PrefixElement prefixElement); |
| 7175 |
| 7176 /** |
| 7177 * Return the element representing the synthetic function `loadLibrary` that i
s implicitly |
| 7178 * defined for this library if the library is imported using a deferred import
. |
| 7179 */ |
| 7180 FunctionElement get loadLibraryFunction; |
| 7181 |
| 7182 /** |
| 7183 * Return an array containing all of the compilation units that are included i
n this library using |
| 7184 * a `part` directive. This does not include the defining compilation unit tha
t contains the |
| 7185 * `part` directives. |
| 7186 * |
| 7187 * @return the compilation units that are included in this library |
| 7188 */ |
| 7189 List<CompilationUnitElement> get parts; |
| 7190 |
| 7191 /** |
| 7192 * Return an array containing elements for each of the prefixes used to `impor
t` libraries |
| 7193 * into this library. Each prefix can be used in more than one `import` direct
ive. |
| 7194 * |
| 7195 * @return the prefixes used to `import` libraries into this library |
| 7196 */ |
| 7197 List<PrefixElement> get prefixes; |
| 7198 |
| 7199 /** |
| 7200 * Return the class defined in this library that has the given name, or `null`
if this |
| 7201 * library does not define a class with the given name. |
| 7202 * |
| 7203 * @param className the name of the class to be returned |
| 7204 * @return the class with the given name that is defined in this library |
| 7205 */ |
| 7206 ClassElement getType(String className); |
| 7207 |
| 7208 /** |
| 7209 * Return an array containing all of the compilation units this library consis
ts of. This includes |
| 7210 * the defining compilation unit and units included using the `part` directive
. |
| 7211 * |
| 7212 * @return the compilation units this library consists of |
| 7213 */ |
| 7214 List<CompilationUnitElement> get units; |
| 7215 |
| 7216 /** |
| 7217 * Return an array containing all directly and indirectly imported libraries. |
| 7218 * |
| 7219 * @return all directly and indirectly imported libraries |
| 7220 */ |
| 7221 List<LibraryElement> get visibleLibraries; |
| 7222 |
| 7223 /** |
| 7224 * Return `true` if the defining compilation unit of this library contains at
least one |
| 7225 * import directive whose URI uses the "dart-ext" scheme. |
| 7226 */ |
| 7227 bool get hasExtUri; |
| 7228 |
| 7229 /** |
| 7230 * Return `true` if this library defines a top-level function named `loadLibra
ry`. |
| 7231 * |
| 7232 * @return `true` if this library defines a top-level function named `loadLibr
ary` |
| 7233 */ |
| 7234 bool get hasLoadLibraryFunction; |
| 7235 |
| 7236 /** |
| 7237 * Return `true` if this library is created for Angular analysis. If this libr
ary has not |
| 7238 * yet had toolkit references resolved, then `false` will be returned. |
| 7239 * |
| 7240 * @return `true` if this library is created for Angular analysis |
| 7241 */ |
| 7242 bool get isAngularHtml; |
| 7243 |
| 7244 /** |
| 7245 * Return `true` if this library is an application that can be run in the brow
ser. |
| 7246 * |
| 7247 * @return `true` if this library is an application that can be run in the bro
wser |
| 7248 */ |
| 7249 bool get isBrowserApplication; |
| 7250 |
| 7251 /** |
| 7252 * Return `true` if this library is the dart:core library. |
| 7253 * |
| 7254 * @return `true` if this library is the dart:core library |
| 7255 */ |
| 7256 bool get isDartCore; |
| 7257 |
| 7258 /** |
| 7259 * Return `true` if this library is the dart:core library. |
| 7260 * |
| 7261 * @return `true` if this library is the dart:core library |
| 7262 */ |
| 7263 bool get isInSdk; |
| 7264 |
| 7265 /** |
| 7266 * Return `true` if this library is up to date with respect to the given time
stamp. If any |
| 7267 * transitively referenced Source is newer than the time stamp, this method re
turns false. |
| 7268 * |
| 7269 * @param timeStamp the time stamp to compare against |
| 7270 * @return `true` if this library is up to date with respect to the given time
stamp |
| 7271 */ |
| 7272 bool isUpToDate(int timeStamp); |
| 7273 } |
| 7274 |
| 7275 /** |
| 5399 * Instances of the class `LibraryElementImpl` implement a `LibraryElement`. | 7276 * Instances of the class `LibraryElementImpl` implement a `LibraryElement`. |
| 5400 */ | 7277 */ |
| 5401 class LibraryElementImpl extends ElementImpl implements LibraryElement { | 7278 class LibraryElementImpl extends ElementImpl implements LibraryElement { |
| 5402 /** | 7279 /** |
| 5403 * An empty array of library elements. | 7280 * An empty array of library elements. |
| 5404 */ | 7281 */ |
| 5405 static List<LibraryElement> EMPTY_ARRAY = new List<LibraryElement>(0); | 7282 static List<LibraryElement> EMPTY_ARRAY = new List<LibraryElement>(0); |
| 5406 | 7283 |
| 5407 /** | 7284 /** |
| 5408 * Determine if the given library is up to date with respect to the given time
stamp. | 7285 * Determine if the given library is up to date with respect to the given time
stamp. |
| (...skipping 425 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5834 if (!visited.contains(exportedLibrary)) { | 7711 if (!visited.contains(exportedLibrary)) { |
| 5835 visited.add(exportedLibrary); | 7712 visited.add(exportedLibrary); |
| 5836 } | 7713 } |
| 5837 } | 7714 } |
| 5838 } | 7715 } |
| 5839 return false; | 7716 return false; |
| 5840 } | 7717 } |
| 5841 } | 7718 } |
| 5842 | 7719 |
| 5843 /** | 7720 /** |
| 7721 * The interface `LocalElement` defines the behavior of elements that can be (bu
t are not |
| 7722 * required to be) defined within a method or function (an [ExecutableElement]). |
| 7723 */ |
| 7724 abstract class LocalElement implements Element { |
| 7725 /** |
| 7726 * Return a source range that covers the approximate portion of the source in
which the name of |
| 7727 * this element is visible, or `null` if there is no single range of character
s within which |
| 7728 * the element name is visible. |
| 7729 * * For a local variable, this includes everything from the end of the variab
le's initializer |
| 7730 * to the end of the block that encloses the variable declaration. |
| 7731 * * For a parameter, this includes the body of the method or function that de
clares the |
| 7732 * parameter. |
| 7733 * * For a local function, this includes everything from the beginning of the
function's body to |
| 7734 * the end of the block that encloses the function declaration. |
| 7735 * * For top-level functions, `null` will be returned because they are potenti
ally visible |
| 7736 * in multiple sources. |
| 7737 * |
| 7738 * @return the range of characters in which the name of this element is visibl
e |
| 7739 */ |
| 7740 SourceRange get visibleRange; |
| 7741 } |
| 7742 |
| 7743 /** |
| 7744 * The interface `LocalVariableElement` defines the behavior common to elements
that represent |
| 7745 * a local variable. |
| 7746 */ |
| 7747 abstract class LocalVariableElement implements LocalElement, VariableElement { |
| 7748 /** |
| 7749 * Return an array containing all of the toolkit specific objects attached to
this variable. |
| 7750 * |
| 7751 * @return the toolkit objects attached to this variable |
| 7752 */ |
| 7753 List<ToolkitObjectElement> get toolkitObjects; |
| 7754 } |
| 7755 |
| 7756 /** |
| 5844 * Instances of the class `LocalVariableElementImpl` implement a `LocalVariableE
lement`. | 7757 * Instances of the class `LocalVariableElementImpl` implement a `LocalVariableE
lement`. |
| 5845 */ | 7758 */ |
| 5846 class LocalVariableElementImpl extends VariableElementImpl implements LocalVaria
bleElement { | 7759 class LocalVariableElementImpl extends VariableElementImpl implements LocalVaria
bleElement { |
| 5847 /** | 7760 /** |
| 5848 * Is `true` if this variable is potentially mutated somewhere in its scope. | 7761 * Is `true` if this variable is potentially mutated somewhere in its scope. |
| 5849 */ | 7762 */ |
| 5850 bool _potentiallyMutatedInScope = false; | 7763 bool _potentiallyMutatedInScope = false; |
| 5851 | 7764 |
| 5852 /** | 7765 /** |
| 5853 * Is `true` if this variable is potentially mutated somewhere in closure. | 7766 * Is `true` if this variable is potentially mutated somewhere in closure. |
| (...skipping 86 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 5940 * @param offset the offset to the beginning of the visible range for this ele
ment | 7853 * @param offset the offset to the beginning of the visible range for this ele
ment |
| 5941 * @param length the length of the visible range for this element, or `-1` if
this element | 7854 * @param length the length of the visible range for this element, or `-1` if
this element |
| 5942 * does not have a visible range | 7855 * does not have a visible range |
| 5943 */ | 7856 */ |
| 5944 void setVisibleRange(int offset, int length) { | 7857 void setVisibleRange(int offset, int length) { |
| 5945 _visibleRangeOffset = offset; | 7858 _visibleRangeOffset = offset; |
| 5946 _visibleRangeLength = length; | 7859 _visibleRangeLength = length; |
| 5947 } | 7860 } |
| 5948 | 7861 |
| 5949 @override | 7862 @override |
| 5950 void appendTo(JavaStringBuilder builder) { | |
| 5951 builder.append(type); | |
| 5952 builder.append(" "); | |
| 5953 builder.append(displayName); | |
| 5954 } | |
| 5955 | |
| 5956 @override | |
| 5957 String get identifier => "${super.identifier}@${nameOffset}"; | |
| 5958 } | |
| 5959 | |
| 5960 /** | |
| 5961 * Instances of the class `MethodElementImpl` implement a `MethodElement`. | |
| 5962 */ | |
| 5963 class MethodElementImpl extends ExecutableElementImpl implements MethodElement { | |
| 5964 /** | |
| 5965 * An empty array of method elements. | |
| 5966 */ | |
| 5967 static List<MethodElement> EMPTY_ARRAY = new List<MethodElement>(0); | |
| 5968 | |
| 5969 /** | |
| 5970 * Initialize a newly created method element to have the given name. | |
| 5971 * | |
| 5972 * @param name the name of this element | |
| 5973 */ | |
| 5974 MethodElementImpl.forNode(Identifier name) : super.forNode(name); | |
| 5975 | |
| 5976 /** | |
| 5977 * Initialize a newly created method element to have the given name. | |
| 5978 * | |
| 5979 * @param name the name of this element | |
| 5980 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 5981 * declaration of this element | |
| 5982 */ | |
| 5983 MethodElementImpl(String name, int nameOffset) : super(name, nameOffset); | |
| 5984 | |
| 5985 @override | |
| 5986 accept(ElementVisitor visitor) => visitor.visitMethodElement(this); | |
| 5987 | |
| 5988 @override | |
| 5989 String get displayName { | |
| 5990 String displayName = super.displayName; | |
| 5991 if ("unary-" == displayName) { | |
| 5992 return "-"; | |
| 5993 } | |
| 5994 return displayName; | |
| 5995 } | |
| 5996 | |
| 5997 @override | |
| 5998 ClassElement get enclosingElement => super.enclosingElement as ClassElement; | |
| 5999 | |
| 6000 @override | |
| 6001 ElementKind get kind => ElementKind.METHOD; | |
| 6002 | |
| 6003 @override | |
| 6004 String get name { | |
| 6005 String name = super.name; | |
| 6006 if (isOperator && name == "-") { | |
| 6007 if (parameters.length == 0) { | |
| 6008 return "unary-"; | |
| 6009 } | |
| 6010 } | |
| 6011 return super.name; | |
| 6012 } | |
| 6013 | |
| 6014 @override | |
| 6015 MethodDeclaration get node => getNodeMatching((node) => node is MethodDeclarat
ion); | |
| 6016 | |
| 6017 @override | |
| 6018 bool get isAbstract => hasModifier(Modifier.ABSTRACT); | |
| 6019 | |
| 6020 @override | |
| 6021 bool get isOperator { | |
| 6022 String name = displayName; | |
| 6023 if (name.isEmpty) { | |
| 6024 return false; | |
| 6025 } | |
| 6026 int first = name.codeUnitAt(0); | |
| 6027 return !((0x61 <= first && first <= 0x7A) || (0x41 <= first && first <= 0x5A
) || first == 0x5F || first == 0x24); | |
| 6028 } | |
| 6029 | |
| 6030 @override | |
| 6031 bool get isStatic => hasModifier(Modifier.STATIC); | |
| 6032 | |
| 6033 /** | |
| 6034 * Set whether this method is abstract to correspond to the given value. | |
| 6035 * | |
| 6036 * @param isAbstract `true` if the method is abstract | |
| 6037 */ | |
| 6038 void set abstract(bool isAbstract) { | |
| 6039 setModifier(Modifier.ABSTRACT, isAbstract); | |
| 6040 } | |
| 6041 | |
| 6042 /** | |
| 6043 * Set whether this method is static to correspond to the given value. | |
| 6044 * | |
| 6045 * @param isStatic `true` if the method is static | |
| 6046 */ | |
| 6047 void set static(bool isStatic) { | |
| 6048 setModifier(Modifier.STATIC, isStatic); | |
| 6049 } | |
| 6050 | |
| 6051 @override | |
| 6052 void appendTo(JavaStringBuilder builder) { | |
| 6053 builder.append(enclosingElement.displayName); | |
| 6054 builder.append("."); | |
| 6055 builder.append(displayName); | |
| 6056 super.appendTo(builder); | |
| 6057 } | |
| 6058 } | |
| 6059 | |
| 6060 /** | |
| 6061 * The enumeration `Modifier` defines constants for all of the modifiers defined
by the Dart | |
| 6062 * language and for a few additional flags that are useful. | |
| 6063 */ | |
| 6064 class Modifier extends Enum<Modifier> { | |
| 6065 /** | |
| 6066 * Indicates that the modifier 'abstract' was applied to the element. | |
| 6067 */ | |
| 6068 static const Modifier ABSTRACT = const Modifier('ABSTRACT', 0); | |
| 6069 | |
| 6070 /** | |
| 6071 * Indicates that the modifier 'const' was applied to the element. | |
| 6072 */ | |
| 6073 static const Modifier CONST = const Modifier('CONST', 1); | |
| 6074 | |
| 6075 /** | |
| 6076 * Indicates that the import element represents a deferred library. | |
| 6077 */ | |
| 6078 static const Modifier DEFERRED = const Modifier('DEFERRED', 2); | |
| 6079 | |
| 6080 /** | |
| 6081 * Indicates that the modifier 'factory' was applied to the element. | |
| 6082 */ | |
| 6083 static const Modifier FACTORY = const Modifier('FACTORY', 3); | |
| 6084 | |
| 6085 /** | |
| 6086 * Indicates that the modifier 'final' was applied to the element. | |
| 6087 */ | |
| 6088 static const Modifier FINAL = const Modifier('FINAL', 4); | |
| 6089 | |
| 6090 /** | |
| 6091 * Indicates that the pseudo-modifier 'get' was applied to the element. | |
| 6092 */ | |
| 6093 static const Modifier GETTER = const Modifier('GETTER', 5); | |
| 6094 | |
| 6095 /** | |
| 6096 * A flag used for libraries indicating that the defining compilation unit con
tains at least one | |
| 6097 * import directive whose URI uses the "dart-ext" scheme. | |
| 6098 */ | |
| 6099 static const Modifier HAS_EXT_URI = const Modifier('HAS_EXT_URI', 6); | |
| 6100 | |
| 6101 static const Modifier MIXIN = const Modifier('MIXIN', 7); | |
| 6102 | |
| 6103 static const Modifier REFERENCES_SUPER = const Modifier('REFERENCES_SUPER', 8)
; | |
| 6104 | |
| 6105 /** | |
| 6106 * Indicates that the pseudo-modifier 'set' was applied to the element. | |
| 6107 */ | |
| 6108 static const Modifier SETTER = const Modifier('SETTER', 9); | |
| 6109 | |
| 6110 /** | |
| 6111 * Indicates that the modifier 'static' was applied to the element. | |
| 6112 */ | |
| 6113 static const Modifier STATIC = const Modifier('STATIC', 10); | |
| 6114 | |
| 6115 /** | |
| 6116 * Indicates that the element does not appear in the source code but was impli
citly created. For | |
| 6117 * example, if a class does not define any constructors, an implicit zero-argu
ment constructor | |
| 6118 * will be created and it will be marked as being synthetic. | |
| 6119 */ | |
| 6120 static const Modifier SYNTHETIC = const Modifier('SYNTHETIC', 11); | |
| 6121 | |
| 6122 static const Modifier TYPEDEF = const Modifier('TYPEDEF', 12); | |
| 6123 | |
| 6124 static const List<Modifier> values = const [ | |
| 6125 ABSTRACT, | |
| 6126 CONST, | |
| 6127 DEFERRED, | |
| 6128 FACTORY, | |
| 6129 FINAL, | |
| 6130 GETTER, | |
| 6131 HAS_EXT_URI, | |
| 6132 MIXIN, | |
| 6133 REFERENCES_SUPER, | |
| 6134 SETTER, | |
| 6135 STATIC, | |
| 6136 SYNTHETIC, | |
| 6137 TYPEDEF]; | |
| 6138 | |
| 6139 const Modifier(String name, int ordinal) : super(name, ordinal); | |
| 6140 } | |
| 6141 | |
| 6142 /** | |
| 6143 * Instances of the class `MultiplyDefinedElementImpl` represent a collection of
elements that | |
| 6144 * have the same name within the same scope. | |
| 6145 */ | |
| 6146 class MultiplyDefinedElementImpl implements MultiplyDefinedElement { | |
| 6147 /** | |
| 6148 * Return an element that represents the given conflicting elements. | |
| 6149 * | |
| 6150 * @param context the analysis context in which the multiply defined elements
are defined | |
| 6151 * @param firstElement the first element that conflicts | |
| 6152 * @param secondElement the second element that conflicts | |
| 6153 */ | |
| 6154 static Element fromElements(AnalysisContext context, Element firstElement, Ele
ment secondElement) { | |
| 6155 List<Element> conflictingElements = _computeConflictingElements(firstElement
, secondElement); | |
| 6156 int length = conflictingElements.length; | |
| 6157 if (length == 0) { | |
| 6158 return null; | |
| 6159 } else if (length == 1) { | |
| 6160 return conflictingElements[0]; | |
| 6161 } | |
| 6162 return new MultiplyDefinedElementImpl(context, conflictingElements); | |
| 6163 } | |
| 6164 | |
| 6165 /** | |
| 6166 * Add the given element to the list of elements. If the element is a multiply
-defined element, | |
| 6167 * add all of the conflicting elements that it represents. | |
| 6168 * | |
| 6169 * @param elements the list to which the element(s) are to be added | |
| 6170 * @param element the element(s) to be added | |
| 6171 */ | |
| 6172 static void _add(Set<Element> elements, Element element) { | |
| 6173 if (element is MultiplyDefinedElementImpl) { | |
| 6174 for (Element conflictingElement in element.conflictingElements) { | |
| 6175 elements.add(conflictingElement); | |
| 6176 } | |
| 6177 } else { | |
| 6178 elements.add(element); | |
| 6179 } | |
| 6180 } | |
| 6181 | |
| 6182 /** | |
| 6183 * Use the given elements to construct an array of conflicting elements. If ei
ther of the given | |
| 6184 * elements are multiply-defined elements then the conflicting elements they r
epresent will be | |
| 6185 * included in the array. Otherwise, the element itself will be included. | |
| 6186 * | |
| 6187 * @param firstElement the first element to be included | |
| 6188 * @param secondElement the second element to be included | |
| 6189 * @return an array containing all of the conflicting elements | |
| 6190 */ | |
| 6191 static List<Element> _computeConflictingElements(Element firstElement, Element
secondElement) { | |
| 6192 Set<Element> elements = new Set<Element>(); | |
| 6193 _add(elements, firstElement); | |
| 6194 _add(elements, secondElement); | |
| 6195 return new List.from(elements); | |
| 6196 } | |
| 6197 | |
| 6198 /** | |
| 6199 * The analysis context in which the multiply defined elements are defined. | |
| 6200 */ | |
| 6201 final AnalysisContext context; | |
| 6202 | |
| 6203 /** | |
| 6204 * The name of the conflicting elements. | |
| 6205 */ | |
| 6206 String _name; | |
| 6207 | |
| 6208 /** | |
| 6209 * A list containing all of the elements that conflict. | |
| 6210 */ | |
| 6211 final List<Element> conflictingElements; | |
| 6212 | |
| 6213 /** | |
| 6214 * Initialize a newly created element to represent a list of conflicting eleme
nts. | |
| 6215 * | |
| 6216 * @param context the analysis context in which the multiply defined elements
are defined | |
| 6217 * @param conflictingElements the elements that conflict | |
| 6218 */ | |
| 6219 MultiplyDefinedElementImpl(this.context, this.conflictingElements) { | |
| 6220 _name = conflictingElements[0].name; | |
| 6221 } | |
| 6222 | |
| 6223 @override | |
| 6224 accept(ElementVisitor visitor) => visitor.visitMultiplyDefinedElement(this); | |
| 6225 | |
| 6226 @override | |
| 6227 String computeDocumentationComment() => null; | |
| 6228 | |
| 6229 @override | |
| 6230 Element getAncestor(Predicate<Element> predicate) => null; | |
| 6231 | |
| 6232 @override | |
| 6233 String get displayName => _name; | |
| 6234 | |
| 6235 @override | |
| 6236 Element get enclosingElement => null; | |
| 6237 | |
| 6238 @override | |
| 6239 ElementKind get kind => ElementKind.ERROR; | |
| 6240 | |
| 6241 @override | |
| 6242 LibraryElement get library => null; | |
| 6243 | |
| 6244 @override | |
| 6245 ElementLocation get location => null; | |
| 6246 | |
| 6247 @override | |
| 6248 List<ElementAnnotation> get metadata => ElementAnnotationImpl.EMPTY_ARRAY; | |
| 6249 | |
| 6250 @override | |
| 6251 String get name => _name; | |
| 6252 | |
| 6253 @override | |
| 6254 int get nameOffset => -1; | |
| 6255 | |
| 6256 @override | |
| 6257 AstNode get node => null; | |
| 6258 | |
| 6259 @override | |
| 6260 Source get source => null; | |
| 6261 | |
| 6262 @override | |
| 6263 DartType get type => DynamicTypeImpl.instance; | |
| 6264 | |
| 6265 @override | |
| 6266 CompilationUnit get unit => null; | |
| 6267 | |
| 6268 @override | |
| 6269 bool isAccessibleIn(LibraryElement library) { | |
| 6270 for (Element element in conflictingElements) { | |
| 6271 if (element.isAccessibleIn(library)) { | |
| 6272 return true; | |
| 6273 } | |
| 6274 } | |
| 6275 return false; | |
| 6276 } | |
| 6277 | |
| 6278 @override | |
| 6279 bool get isDeprecated => false; | |
| 6280 | |
| 6281 @override | |
| 6282 bool get isOverride => false; | |
| 6283 | |
| 6284 @override | |
| 6285 bool get isPrivate { | |
| 6286 String name = displayName; | |
| 6287 if (name == null) { | |
| 6288 return false; | |
| 6289 } | |
| 6290 return Identifier.isPrivateName(name); | |
| 6291 } | |
| 6292 | |
| 6293 @override | |
| 6294 bool get isPublic => !isPrivate; | |
| 6295 | |
| 6296 @override | |
| 6297 bool get isSynthetic => true; | |
| 6298 | |
| 6299 @override | |
| 6300 String toString() { | |
| 6301 JavaStringBuilder builder = new JavaStringBuilder(); | |
| 6302 builder.append("["); | |
| 6303 int count = conflictingElements.length; | |
| 6304 for (int i = 0; i < count; i++) { | |
| 6305 if (i > 0) { | |
| 6306 builder.append(", "); | |
| 6307 } | |
| 6308 (conflictingElements[i] as ElementImpl).appendTo(builder); | |
| 6309 } | |
| 6310 builder.append("]"); | |
| 6311 return builder.toString(); | |
| 6312 } | |
| 6313 | |
| 6314 @override | |
| 6315 void visitChildren(ElementVisitor visitor) { | |
| 6316 } | |
| 6317 } | |
| 6318 | |
| 6319 /** | |
| 6320 * The interface [MultiplyInheritedMethodElementImpl] defines all of the behavio
r of an | |
| 6321 * [MethodElementImpl], with the additional information of an array of | |
| 6322 * [ExecutableElement]s from which this element was composed. | |
| 6323 */ | |
| 6324 class MultiplyInheritedMethodElementImpl extends MethodElementImpl implements Mu
ltiplyInheritedExecutableElement { | |
| 6325 /** | |
| 6326 * An array the array of executable elements that were used to compose this el
ement. | |
| 6327 */ | |
| 6328 List<ExecutableElement> _elements = MethodElementImpl.EMPTY_ARRAY; | |
| 6329 | |
| 6330 MultiplyInheritedMethodElementImpl(Identifier name) : super.forNode(name) { | |
| 6331 synthetic = true; | |
| 6332 } | |
| 6333 | |
| 6334 @override | |
| 6335 List<ExecutableElement> get inheritedElements => _elements; | |
| 6336 | |
| 6337 void set inheritedElements(List<ExecutableElement> elements) { | |
| 6338 this._elements = elements; | |
| 6339 } | |
| 6340 } | |
| 6341 | |
| 6342 /** | |
| 6343 * The interface [MultiplyInheritedPropertyAccessorElementImpl] defines all of t
he behavior of | |
| 6344 * an [PropertyAccessorElementImpl], with the additional information of an array
of | |
| 6345 * [ExecutableElement]s from which this element was composed. | |
| 6346 */ | |
| 6347 class MultiplyInheritedPropertyAccessorElementImpl extends PropertyAccessorEleme
ntImpl implements MultiplyInheritedExecutableElement { | |
| 6348 /** | |
| 6349 * An array the array of executable elements that were used to compose this el
ement. | |
| 6350 */ | |
| 6351 List<ExecutableElement> _elements = PropertyAccessorElementImpl.EMPTY_ARRAY; | |
| 6352 | |
| 6353 MultiplyInheritedPropertyAccessorElementImpl(Identifier name) : super.forNode(
name) { | |
| 6354 synthetic = true; | |
| 6355 } | |
| 6356 | |
| 6357 @override | |
| 6358 List<ExecutableElement> get inheritedElements => _elements; | |
| 6359 | |
| 6360 void set inheritedElements(List<ExecutableElement> elements) { | |
| 6361 this._elements = elements; | |
| 6362 } | |
| 6363 } | |
| 6364 | |
| 6365 /** | |
| 6366 * Instances of the class `ParameterElementImpl` implement a `ParameterElement`. | |
| 6367 */ | |
| 6368 class ParameterElementImpl extends VariableElementImpl implements ParameterEleme
nt { | |
| 6369 /** | |
| 6370 * Is `true` if this variable is potentially mutated somewhere in its scope. | |
| 6371 */ | |
| 6372 bool _potentiallyMutatedInScope = false; | |
| 6373 | |
| 6374 /** | |
| 6375 * Is `true` if this variable is potentially mutated somewhere in closure. | |
| 6376 */ | |
| 6377 bool _potentiallyMutatedInClosure = false; | |
| 6378 | |
| 6379 /** | |
| 6380 * An array containing all of the parameters defined by this parameter element
. There will only be | |
| 6381 * parameters if this parameter is a function typed parameter. | |
| 6382 */ | |
| 6383 List<ParameterElement> _parameters = ParameterElementImpl.EMPTY_ARRAY; | |
| 6384 | |
| 6385 /** | |
| 6386 * The kind of this parameter. | |
| 6387 */ | |
| 6388 ParameterKind parameterKind; | |
| 6389 | |
| 6390 /** | |
| 6391 * The offset to the beginning of the default value range for this element. | |
| 6392 */ | |
| 6393 int _defaultValueRangeOffset = 0; | |
| 6394 | |
| 6395 /** | |
| 6396 * The length of the default value range for this element, or `-1` if this ele
ment does not | |
| 6397 * have a default value. | |
| 6398 */ | |
| 6399 int _defaultValueRangeLength = -1; | |
| 6400 | |
| 6401 /** | |
| 6402 * The offset to the beginning of the visible range for this element. | |
| 6403 */ | |
| 6404 int _visibleRangeOffset = 0; | |
| 6405 | |
| 6406 /** | |
| 6407 * The length of the visible range for this element, or `-1` if this element d
oes not have a | |
| 6408 * visible range. | |
| 6409 */ | |
| 6410 int _visibleRangeLength = -1; | |
| 6411 | |
| 6412 /** | |
| 6413 * An empty array of field elements. | |
| 6414 */ | |
| 6415 static List<ParameterElement> EMPTY_ARRAY = new List<ParameterElement>(0); | |
| 6416 | |
| 6417 /** | |
| 6418 * Initialize a newly created parameter element to have the given name. | |
| 6419 * | |
| 6420 * @param name the name of this element | |
| 6421 */ | |
| 6422 ParameterElementImpl.con1(Identifier name) : super.forNode(name); | |
| 6423 | |
| 6424 /** | |
| 6425 * Initialize a newly created parameter element to have the given name. | |
| 6426 * | |
| 6427 * @param name the name of this element | |
| 6428 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 6429 * declaration of this element | |
| 6430 */ | |
| 6431 ParameterElementImpl.con2(String name, int nameOffset) : super(name, nameOffse
t); | |
| 6432 | |
| 6433 @override | |
| 6434 accept(ElementVisitor visitor) => visitor.visitParameterElement(this); | |
| 6435 | |
| 6436 @override | |
| 6437 SourceRange get defaultValueRange { | |
| 6438 if (_defaultValueRangeLength < 0) { | |
| 6439 return null; | |
| 6440 } | |
| 6441 return new SourceRange(_defaultValueRangeOffset, _defaultValueRangeLength); | |
| 6442 } | |
| 6443 | |
| 6444 @override | |
| 6445 ElementKind get kind => ElementKind.PARAMETER; | |
| 6446 | |
| 6447 @override | |
| 6448 List<ParameterElement> get parameters => _parameters; | |
| 6449 | |
| 6450 @override | |
| 6451 SourceRange get visibleRange { | |
| 6452 if (_visibleRangeLength < 0) { | |
| 6453 return null; | |
| 6454 } | |
| 6455 return new SourceRange(_visibleRangeOffset, _visibleRangeLength); | |
| 6456 } | |
| 6457 | |
| 6458 @override | |
| 6459 bool get isInitializingFormal => false; | |
| 6460 | |
| 6461 @override | |
| 6462 bool get isPotentiallyMutatedInClosure => _potentiallyMutatedInClosure; | |
| 6463 | |
| 6464 @override | |
| 6465 bool get isPotentiallyMutatedInScope => _potentiallyMutatedInScope; | |
| 6466 | |
| 6467 /** | |
| 6468 * Specifies that this variable is potentially mutated somewhere in closure. | |
| 6469 */ | |
| 6470 void markPotentiallyMutatedInClosure() { | |
| 6471 _potentiallyMutatedInClosure = true; | |
| 6472 } | |
| 6473 | |
| 6474 /** | |
| 6475 * Specifies that this variable is potentially mutated somewhere in its scope. | |
| 6476 */ | |
| 6477 void markPotentiallyMutatedInScope() { | |
| 6478 _potentiallyMutatedInScope = true; | |
| 6479 } | |
| 6480 | |
| 6481 /** | |
| 6482 * Set the range of the default value for this parameter to the range starting
at the given offset | |
| 6483 * with the given length. | |
| 6484 * | |
| 6485 * @param offset the offset to the beginning of the default value range for th
is element | |
| 6486 * @param length the length of the default value range for this element, or `-
1` if this | |
| 6487 * element does not have a default value | |
| 6488 */ | |
| 6489 void setDefaultValueRange(int offset, int length) { | |
| 6490 _defaultValueRangeOffset = offset; | |
| 6491 _defaultValueRangeLength = length; | |
| 6492 } | |
| 6493 | |
| 6494 /** | |
| 6495 * Set the parameters defined by this executable element to the given paramete
rs. | |
| 6496 * | |
| 6497 * @param parameters the parameters defined by this executable element | |
| 6498 */ | |
| 6499 void set parameters(List<ParameterElement> parameters) { | |
| 6500 for (ParameterElement parameter in parameters) { | |
| 6501 (parameter as ParameterElementImpl).enclosingElement = this; | |
| 6502 } | |
| 6503 this._parameters = parameters; | |
| 6504 } | |
| 6505 | |
| 6506 /** | |
| 6507 * Set the visible range for this element to the range starting at the given o
ffset with the given | |
| 6508 * length. | |
| 6509 * | |
| 6510 * @param offset the offset to the beginning of the visible range for this ele
ment | |
| 6511 * @param length the length of the visible range for this element, or `-1` if
this element | |
| 6512 * does not have a visible range | |
| 6513 */ | |
| 6514 void setVisibleRange(int offset, int length) { | |
| 6515 _visibleRangeOffset = offset; | |
| 6516 _visibleRangeLength = length; | |
| 6517 } | |
| 6518 | |
| 6519 @override | |
| 6520 void visitChildren(ElementVisitor visitor) { | |
| 6521 super.visitChildren(visitor); | |
| 6522 safelyVisitChildren(_parameters, visitor); | |
| 6523 } | |
| 6524 | |
| 6525 @override | |
| 6526 void appendTo(JavaStringBuilder builder) { | |
| 6527 String left = ""; | |
| 6528 String right = ""; | |
| 6529 while (true) { | |
| 6530 if (parameterKind == ParameterKind.NAMED) { | |
| 6531 left = "{"; | |
| 6532 right = "}"; | |
| 6533 } else if (parameterKind == ParameterKind.POSITIONAL) { | |
| 6534 left = "["; | |
| 6535 right = "]"; | |
| 6536 } else if (parameterKind == ParameterKind.REQUIRED) { | |
| 6537 } | |
| 6538 break; | |
| 6539 } | |
| 6540 builder.append(left); | |
| 6541 appendToWithoutDelimiters(builder); | |
| 6542 builder.append(right); | |
| 6543 } | |
| 6544 | |
| 6545 /** | |
| 6546 * Append the type and name of this parameter to the given builder. | |
| 6547 * | |
| 6548 * @param builder the builder to which the type and name are to be appended | |
| 6549 */ | |
| 6550 void appendToWithoutDelimiters(JavaStringBuilder builder) { | |
| 6551 builder.append(type); | |
| 6552 builder.append(" "); | |
| 6553 builder.append(displayName); | |
| 6554 } | |
| 6555 } | |
| 6556 | |
| 6557 /** | |
| 6558 * Instances of the class `PrefixElementImpl` implement a `PrefixElement`. | |
| 6559 */ | |
| 6560 class PrefixElementImpl extends ElementImpl implements PrefixElement { | |
| 6561 /** | |
| 6562 * An array containing all of the libraries that are imported using this prefi
x. | |
| 6563 */ | |
| 6564 List<LibraryElement> _importedLibraries = LibraryElementImpl.EMPTY_ARRAY; | |
| 6565 | |
| 6566 /** | |
| 6567 * An empty array of prefix elements. | |
| 6568 */ | |
| 6569 static List<PrefixElement> EMPTY_ARRAY = new List<PrefixElement>(0); | |
| 6570 | |
| 6571 /** | |
| 6572 * Initialize a newly created prefix element to have the given name. | |
| 6573 * | |
| 6574 * @param name the name of this element | |
| 6575 */ | |
| 6576 PrefixElementImpl(Identifier name) : super.forNode(name); | |
| 6577 | |
| 6578 @override | |
| 6579 accept(ElementVisitor visitor) => visitor.visitPrefixElement(this); | |
| 6580 | |
| 6581 @override | |
| 6582 LibraryElement get enclosingElement => super.enclosingElement as LibraryElemen
t; | |
| 6583 | |
| 6584 @override | |
| 6585 List<LibraryElement> get importedLibraries => _importedLibraries; | |
| 6586 | |
| 6587 @override | |
| 6588 ElementKind get kind => ElementKind.PREFIX; | |
| 6589 | |
| 6590 /** | |
| 6591 * Set the libraries that are imported using this prefix to the given librarie
s. | |
| 6592 * | |
| 6593 * @param importedLibraries the libraries that are imported using this prefix | |
| 6594 */ | |
| 6595 void set importedLibraries(List<LibraryElement> importedLibraries) { | |
| 6596 for (LibraryElement library in importedLibraries) { | |
| 6597 (library as LibraryElementImpl).enclosingElement = this; | |
| 6598 } | |
| 6599 this._importedLibraries = importedLibraries; | |
| 6600 } | |
| 6601 | |
| 6602 @override | |
| 6603 void appendTo(JavaStringBuilder builder) { | |
| 6604 builder.append("as "); | |
| 6605 super.appendTo(builder); | |
| 6606 } | |
| 6607 | |
| 6608 @override | |
| 6609 String get identifier => "_${super.identifier}"; | |
| 6610 } | |
| 6611 | |
| 6612 /** | |
| 6613 * Instances of the class `PropertyAccessorElementImpl` implement a | |
| 6614 * `PropertyAccessorElement`. | |
| 6615 */ | |
| 6616 class PropertyAccessorElementImpl extends ExecutableElementImpl implements Prope
rtyAccessorElement { | |
| 6617 /** | |
| 6618 * The variable associated with this accessor. | |
| 6619 */ | |
| 6620 PropertyInducingElement variable; | |
| 6621 | |
| 6622 /** | |
| 6623 * An empty array of property accessor elements. | |
| 6624 */ | |
| 6625 static List<PropertyAccessorElement> EMPTY_ARRAY = new List<PropertyAccessorEl
ement>(0); | |
| 6626 | |
| 6627 /** | |
| 6628 * Initialize a newly created property accessor element to have the given name
. | |
| 6629 * | |
| 6630 * @param name the name of this element | |
| 6631 */ | |
| 6632 PropertyAccessorElementImpl.forNode(Identifier name) : super.forNode(name); | |
| 6633 | |
| 6634 /** | |
| 6635 * Initialize a newly created synthetic property accessor element to be associ
ated with the given | |
| 6636 * variable. | |
| 6637 * | |
| 6638 * @param variable the variable with which this access is associated | |
| 6639 */ | |
| 6640 PropertyAccessorElementImpl(PropertyInducingElementImpl variable) : super(vari
able.name, variable.nameOffset) { | |
| 6641 this.variable = variable; | |
| 6642 synthetic = true; | |
| 6643 } | |
| 6644 | |
| 6645 @override | |
| 6646 accept(ElementVisitor visitor) => visitor.visitPropertyAccessorElement(this); | |
| 6647 | |
| 6648 @override | |
| 6649 bool operator ==(Object object) => super == object && isGetter == (object as P
ropertyAccessorElement).isGetter; | |
| 6650 | |
| 6651 @override | |
| 6652 PropertyAccessorElement get correspondingGetter { | |
| 6653 if (isGetter || variable == null) { | |
| 6654 return null; | |
| 6655 } | |
| 6656 return variable.getter; | |
| 6657 } | |
| 6658 | |
| 6659 @override | |
| 6660 PropertyAccessorElement get correspondingSetter { | |
| 6661 if (isSetter || variable == null) { | |
| 6662 return null; | |
| 6663 } | |
| 6664 return variable.setter; | |
| 6665 } | |
| 6666 | |
| 6667 @override | |
| 6668 ElementKind get kind { | |
| 6669 if (isGetter) { | |
| 6670 return ElementKind.GETTER; | |
| 6671 } | |
| 6672 return ElementKind.SETTER; | |
| 6673 } | |
| 6674 | |
| 6675 @override | |
| 6676 String get name { | |
| 6677 if (isSetter) { | |
| 6678 return "${super.name}="; | |
| 6679 } | |
| 6680 return super.name; | |
| 6681 } | |
| 6682 | |
| 6683 @override | |
| 6684 AstNode get node { | |
| 6685 if (isSynthetic) { | |
| 6686 return null; | |
| 6687 } | |
| 6688 if (enclosingElement is ClassElement) { | |
| 6689 return getNodeMatching((node) => node is MethodDeclaration); | |
| 6690 } | |
| 6691 if (enclosingElement is CompilationUnitElement) { | |
| 6692 return getNodeMatching((node) => node is FunctionDeclaration); | |
| 6693 } | |
| 6694 return null; | |
| 6695 } | |
| 6696 | |
| 6697 @override | |
| 6698 int get hashCode => ObjectUtilities.combineHashCodes(super.hashCode, isGetter
? 1 : 2); | |
| 6699 | |
| 6700 @override | |
| 6701 bool get isAbstract => hasModifier(Modifier.ABSTRACT); | |
| 6702 | |
| 6703 @override | |
| 6704 bool get isGetter => hasModifier(Modifier.GETTER); | |
| 6705 | |
| 6706 @override | |
| 6707 bool get isSetter => hasModifier(Modifier.SETTER); | |
| 6708 | |
| 6709 @override | |
| 6710 bool get isStatic => hasModifier(Modifier.STATIC); | |
| 6711 | |
| 6712 /** | |
| 6713 * Set whether this accessor is abstract to correspond to the given value. | |
| 6714 * | |
| 6715 * @param isAbstract `true` if the accessor is abstract | |
| 6716 */ | |
| 6717 void set abstract(bool isAbstract) { | |
| 6718 setModifier(Modifier.ABSTRACT, isAbstract); | |
| 6719 } | |
| 6720 | |
| 6721 /** | |
| 6722 * Set whether this accessor is a getter to correspond to the given value. | |
| 6723 * | |
| 6724 * @param isGetter `true` if the accessor is a getter | |
| 6725 */ | |
| 6726 void set getter(bool isGetter) { | |
| 6727 setModifier(Modifier.GETTER, isGetter); | |
| 6728 } | |
| 6729 | |
| 6730 /** | |
| 6731 * Set whether this accessor is a setter to correspond to the given value. | |
| 6732 * | |
| 6733 * @param isSetter `true` if the accessor is a setter | |
| 6734 */ | |
| 6735 void set setter(bool isSetter) { | |
| 6736 setModifier(Modifier.SETTER, isSetter); | |
| 6737 } | |
| 6738 | |
| 6739 /** | |
| 6740 * Set whether this accessor is static to correspond to the given value. | |
| 6741 * | |
| 6742 * @param isStatic `true` if the accessor is static | |
| 6743 */ | |
| 6744 void set static(bool isStatic) { | |
| 6745 setModifier(Modifier.STATIC, isStatic); | |
| 6746 } | |
| 6747 | |
| 6748 @override | |
| 6749 void appendTo(JavaStringBuilder builder) { | |
| 6750 builder.append(isGetter ? "get " : "set "); | |
| 6751 builder.append(variable.displayName); | |
| 6752 super.appendTo(builder); | |
| 6753 } | |
| 6754 } | |
| 6755 | |
| 6756 /** | |
| 6757 * Instances of the class `PropertyInducingElementImpl` implement a | |
| 6758 * `PropertyInducingElement`. | |
| 6759 */ | |
| 6760 abstract class PropertyInducingElementImpl extends VariableElementImpl implement
s PropertyInducingElement { | |
| 6761 /** | |
| 6762 * The getter associated with this element. | |
| 6763 */ | |
| 6764 PropertyAccessorElement getter; | |
| 6765 | |
| 6766 /** | |
| 6767 * The setter associated with this element, or `null` if the element is effect
ively | |
| 6768 * `final` and therefore does not have a setter associated with it. | |
| 6769 */ | |
| 6770 PropertyAccessorElement setter; | |
| 6771 | |
| 6772 /** | |
| 6773 * An empty array of elements. | |
| 6774 */ | |
| 6775 static List<PropertyInducingElement> EMPTY_ARRAY = new List<PropertyInducingEl
ement>(0); | |
| 6776 | |
| 6777 /** | |
| 6778 * Initialize a newly created element to have the given name. | |
| 6779 * | |
| 6780 * @param name the name of this element | |
| 6781 */ | |
| 6782 PropertyInducingElementImpl.con1(Identifier name) : super.forNode(name); | |
| 6783 | |
| 6784 /** | |
| 6785 * Initialize a newly created synthetic element to have the given name. | |
| 6786 * | |
| 6787 * @param name the name of this element | |
| 6788 */ | |
| 6789 PropertyInducingElementImpl.con2(String name) : super(name, -1) { | |
| 6790 synthetic = true; | |
| 6791 } | |
| 6792 } | |
| 6793 | |
| 6794 /** | |
| 6795 * Instances of the class `ShowElementCombinatorImpl` implement a | |
| 6796 * [ShowElementCombinator]. | |
| 6797 */ | |
| 6798 class ShowElementCombinatorImpl implements ShowElementCombinator { | |
| 6799 /** | |
| 6800 * The names that are to be made visible in the importing library if they are
defined in the | |
| 6801 * imported library. | |
| 6802 */ | |
| 6803 List<String> shownNames = StringUtilities.EMPTY_ARRAY; | |
| 6804 | |
| 6805 /** | |
| 6806 * The offset of the character immediately following the last character of thi
s node. | |
| 6807 */ | |
| 6808 int end = -1; | |
| 6809 | |
| 6810 /** | |
| 6811 * The offset of the 'show' keyword of this element. | |
| 6812 */ | |
| 6813 int offset = 0; | |
| 6814 | |
| 6815 @override | |
| 6816 String toString() { | |
| 6817 JavaStringBuilder builder = new JavaStringBuilder(); | |
| 6818 builder.append("show "); | |
| 6819 int count = shownNames.length; | |
| 6820 for (int i = 0; i < count; i++) { | |
| 6821 if (i > 0) { | |
| 6822 builder.append(", "); | |
| 6823 } | |
| 6824 builder.append(shownNames[i]); | |
| 6825 } | |
| 6826 return builder.toString(); | |
| 6827 } | |
| 6828 } | |
| 6829 | |
| 6830 /** | |
| 6831 * Instances of the class `ToolkitObjectElementImpl` implement a `ToolkitObjectE
lement`. | |
| 6832 */ | |
| 6833 abstract class ToolkitObjectElementImpl extends ElementImpl implements ToolkitOb
jectElement { | |
| 6834 /** | |
| 6835 * Initialize a newly created toolkit object element to have the given name. | |
| 6836 * | |
| 6837 * @param name the name of this element | |
| 6838 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 6839 * declaration of this element | |
| 6840 */ | |
| 6841 ToolkitObjectElementImpl(String name, int nameOffset) : super(name, nameOffset
); | |
| 6842 } | |
| 6843 | |
| 6844 /** | |
| 6845 * Instances of the class `TopLevelVariableElementImpl` implement a | |
| 6846 * `TopLevelVariableElement`. | |
| 6847 */ | |
| 6848 class TopLevelVariableElementImpl extends PropertyInducingElementImpl implements
TopLevelVariableElement { | |
| 6849 /** | |
| 6850 * An empty array of top-level variable elements. | |
| 6851 */ | |
| 6852 static List<TopLevelVariableElement> EMPTY_ARRAY = new List<TopLevelVariableEl
ement>(0); | |
| 6853 | |
| 6854 /** | |
| 6855 * Initialize a newly created top-level variable element to have the given nam
e. | |
| 6856 * | |
| 6857 * @param name the name of this element | |
| 6858 */ | |
| 6859 TopLevelVariableElementImpl.con1(Identifier name) : super.con1(name); | |
| 6860 | |
| 6861 /** | |
| 6862 * Initialize a newly created synthetic top-level variable element to have the
given name. | |
| 6863 * | |
| 6864 * @param name the name of this element | |
| 6865 */ | |
| 6866 TopLevelVariableElementImpl.con2(String name) : super.con2(name); | |
| 6867 | |
| 6868 @override | |
| 6869 accept(ElementVisitor visitor) => visitor.visitTopLevelVariableElement(this); | |
| 6870 | |
| 6871 @override | |
| 6872 ElementKind get kind => ElementKind.TOP_LEVEL_VARIABLE; | |
| 6873 | |
| 6874 @override | |
| 6875 bool get isStatic => true; | |
| 6876 } | |
| 6877 | |
| 6878 /** | |
| 6879 * Instances of the class `TypeParameterElementImpl` implement a [TypeParameterE
lement]. | |
| 6880 */ | |
| 6881 class TypeParameterElementImpl extends ElementImpl implements TypeParameterEleme
nt { | |
| 6882 /** | |
| 6883 * The type defined by this type parameter. | |
| 6884 */ | |
| 6885 TypeParameterType type; | |
| 6886 | |
| 6887 /** | |
| 6888 * The type representing the bound associated with this parameter, or `null` i
f this | |
| 6889 * parameter does not have an explicit bound. | |
| 6890 */ | |
| 6891 DartType bound; | |
| 6892 | |
| 6893 /** | |
| 6894 * An empty array of type parameter elements. | |
| 6895 */ | |
| 6896 static List<TypeParameterElement> EMPTY_ARRAY = new List<TypeParameterElement>
(0); | |
| 6897 | |
| 6898 /** | |
| 6899 * Initialize a newly created type parameter element to have the given name. | |
| 6900 * | |
| 6901 * @param name the name of this element | |
| 6902 */ | |
| 6903 TypeParameterElementImpl(Identifier name) : super.forNode(name); | |
| 6904 | |
| 6905 @override | |
| 6906 accept(ElementVisitor visitor) => visitor.visitTypeParameterElement(this); | |
| 6907 | |
| 6908 @override | |
| 6909 ElementKind get kind => ElementKind.TYPE_PARAMETER; | |
| 6910 | |
| 6911 @override | |
| 6912 void appendTo(JavaStringBuilder builder) { | |
| 6913 builder.append(displayName); | |
| 6914 if (bound != null) { | |
| 6915 builder.append(" extends "); | |
| 6916 builder.append(bound); | |
| 6917 } | |
| 6918 } | |
| 6919 } | |
| 6920 | |
| 6921 /** | |
| 6922 * Instances of the class `UriReferencedElementImpl` implement an [UriReferenced
Element] | |
| 6923 * . | |
| 6924 */ | |
| 6925 abstract class UriReferencedElementImpl extends ElementImpl implements UriRefere
ncedElement { | |
| 6926 /** | |
| 6927 * The offset of the URI in the file, may be `-1` if synthetic. | |
| 6928 */ | |
| 6929 int uriOffset = -1; | |
| 6930 | |
| 6931 /** | |
| 6932 * The offset of the character immediately following the last character of thi
s node's URI, may be | |
| 6933 * `-1` if synthetic. | |
| 6934 */ | |
| 6935 int uriEnd = -1; | |
| 6936 | |
| 6937 /** | |
| 6938 * The URI that is specified by this directive. | |
| 6939 */ | |
| 6940 String uri; | |
| 6941 | |
| 6942 /** | |
| 6943 * Initialize a newly created import element. | |
| 6944 * | |
| 6945 * @param name the name of this element | |
| 6946 * @param offset the directive offset, may be `-1` if synthetic. | |
| 6947 */ | |
| 6948 UriReferencedElementImpl(String name, int offset) : super(name, offset); | |
| 6949 } | |
| 6950 | |
| 6951 /** | |
| 6952 * Instances of the class `VariableElementImpl` implement a `VariableElement`. | |
| 6953 */ | |
| 6954 abstract class VariableElementImpl extends ElementImpl implements VariableElemen
t { | |
| 6955 /** | |
| 6956 * The declared type of this variable. | |
| 6957 */ | |
| 6958 DartType type; | |
| 6959 | |
| 6960 /** | |
| 6961 * A synthetic function representing this variable's initializer, or `null` if
this variable | |
| 6962 * does not have an initializer. | |
| 6963 */ | |
| 6964 FunctionElement _initializer; | |
| 6965 | |
| 6966 /** | |
| 6967 * An empty array of variable elements. | |
| 6968 */ | |
| 6969 static List<VariableElement> EMPTY_ARRAY = new List<VariableElement>(0); | |
| 6970 | |
| 6971 /** | |
| 6972 * Initialize a newly created variable element to have the given name. | |
| 6973 * | |
| 6974 * @param name the name of this element | |
| 6975 */ | |
| 6976 VariableElementImpl.forNode(Identifier name) : super.forNode(name); | |
| 6977 | |
| 6978 /** | |
| 6979 * Initialize a newly created variable element to have the given name. | |
| 6980 * | |
| 6981 * @param name the name of this element | |
| 6982 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 6983 * declaration of this element | |
| 6984 */ | |
| 6985 VariableElementImpl(String name, int nameOffset) : super(name, nameOffset); | |
| 6986 | |
| 6987 /** | |
| 6988 * Return the result of evaluating this variable's initializer as a compile-ti
me constant | |
| 6989 * expression, or `null` if this variable is not a 'const' variable, if it doe
s not have an | |
| 6990 * initializer, or if the compilation unit containing the variable has not bee
n resolved. | |
| 6991 * | |
| 6992 * @return the result of evaluating this variable's initializer | |
| 6993 */ | |
| 6994 EvaluationResultImpl get evaluationResult => null; | |
| 6995 | |
| 6996 @override | |
| 6997 FunctionElement get initializer => _initializer; | |
| 6998 | |
| 6999 @override | |
| 7000 VariableDeclaration get node => getNodeMatching((node) => node is VariableDecl
aration); | |
| 7001 | |
| 7002 @override | |
| 7003 bool get isConst => hasModifier(Modifier.CONST); | |
| 7004 | |
| 7005 @override | |
| 7006 bool get isFinal => hasModifier(Modifier.FINAL); | |
| 7007 | |
| 7008 /** | |
| 7009 * Return `true` if this variable is potentially mutated somewhere in a closur
e. This | |
| 7010 * information is only available for local variables (including parameters) an
d only after the | |
| 7011 * compilation unit containing the variable has been resolved. | |
| 7012 * | |
| 7013 * @return `true` if this variable is potentially mutated somewhere in closure | |
| 7014 */ | |
| 7015 bool get isPotentiallyMutatedInClosure => false; | |
| 7016 | |
| 7017 /** | |
| 7018 * Return `true` if this variable is potentially mutated somewhere in its scop
e. This | |
| 7019 * information is only available for local variables (including parameters) an
d only after the | |
| 7020 * compilation unit containing the variable has been resolved. | |
| 7021 * | |
| 7022 * @return `true` if this variable is potentially mutated somewhere in its sco
pe | |
| 7023 */ | |
| 7024 bool get isPotentiallyMutatedInScope => false; | |
| 7025 | |
| 7026 /** | |
| 7027 * Set whether this variable is const to correspond to the given value. | |
| 7028 * | |
| 7029 * @param isConst `true` if the variable is const | |
| 7030 */ | |
| 7031 void set const3(bool isConst) { | |
| 7032 setModifier(Modifier.CONST, isConst); | |
| 7033 } | |
| 7034 | |
| 7035 /** | |
| 7036 * Set the result of evaluating this variable's initializer as a compile-time
constant expression | |
| 7037 * to the given result. | |
| 7038 * | |
| 7039 * @param result the result of evaluating this variable's initializer | |
| 7040 */ | |
| 7041 void set evaluationResult(EvaluationResultImpl result) { | |
| 7042 throw new IllegalStateException("Invalid attempt to set a compile-time const
ant result"); | |
| 7043 } | |
| 7044 | |
| 7045 /** | |
| 7046 * Set whether this variable is final to correspond to the given value. | |
| 7047 * | |
| 7048 * @param isFinal `true` if the variable is final | |
| 7049 */ | |
| 7050 void set final2(bool isFinal) { | |
| 7051 setModifier(Modifier.FINAL, isFinal); | |
| 7052 } | |
| 7053 | |
| 7054 /** | |
| 7055 * Set the function representing this variable's initializer to the given func
tion. | |
| 7056 * | |
| 7057 * @param initializer the function representing this variable's initializer | |
| 7058 */ | |
| 7059 void set initializer(FunctionElement initializer) { | |
| 7060 if (initializer != null) { | |
| 7061 (initializer as FunctionElementImpl).enclosingElement = this; | |
| 7062 } | |
| 7063 this._initializer = initializer; | |
| 7064 } | |
| 7065 | |
| 7066 @override | |
| 7067 void visitChildren(ElementVisitor visitor) { | |
| 7068 super.visitChildren(visitor); | |
| 7069 safelyVisitChild(_initializer, visitor); | |
| 7070 } | |
| 7071 | |
| 7072 @override | |
| 7073 void appendTo(JavaStringBuilder builder) { | 7863 void appendTo(JavaStringBuilder builder) { |
| 7074 builder.append(type); | 7864 builder.append(type); |
| 7075 builder.append(" "); | 7865 builder.append(" "); |
| 7076 builder.append(displayName); | 7866 builder.append(displayName); |
| 7077 } | 7867 } |
| 7078 } | 7868 |
| 7079 | 7869 @override |
| 7080 /** | 7870 String get identifier => "${super.identifier}@${nameOffset}"; |
| 7081 * Information about Angular application. | |
| 7082 */ | |
| 7083 class AngularApplication { | |
| 7084 final Source entryPoint; | |
| 7085 | |
| 7086 final Set<Source> _librarySources; | |
| 7087 | |
| 7088 final List<AngularElement> elements; | |
| 7089 | |
| 7090 final List<Source> elementSources; | |
| 7091 | |
| 7092 AngularApplication(this.entryPoint, this._librarySources, this.elements, this.
elementSources); | |
| 7093 | |
| 7094 /** | |
| 7095 * Checks if this application depends on the library with the given [Source]. | |
| 7096 */ | |
| 7097 bool dependsOn(Source librarySource) => _librarySources.contains(librarySource
); | |
| 7098 } | |
| 7099 | |
| 7100 /** | |
| 7101 * Implementation of `AngularComponentElement`. | |
| 7102 */ | |
| 7103 class AngularComponentElementImpl extends AngularHasSelectorElementImpl implemen
ts AngularComponentElement { | |
| 7104 /** | |
| 7105 * The offset of the defining <code>Component</code> annotation. | |
| 7106 */ | |
| 7107 final int _annotationOffset; | |
| 7108 | |
| 7109 /** | |
| 7110 * The array containing all of the properties declared by this component. | |
| 7111 */ | |
| 7112 List<AngularPropertyElement> _properties = AngularPropertyElement.EMPTY_ARRAY; | |
| 7113 | |
| 7114 /** | |
| 7115 * The array containing all of the scope properties set by this component. | |
| 7116 */ | |
| 7117 List<AngularScopePropertyElement> _scopeProperties = AngularScopePropertyEleme
nt.EMPTY_ARRAY; | |
| 7118 | |
| 7119 /** | |
| 7120 * The the CSS file URI. | |
| 7121 */ | |
| 7122 String styleUri; | |
| 7123 | |
| 7124 /** | |
| 7125 * The offset of the [styleUri] in the [getSource]. | |
| 7126 */ | |
| 7127 int styleUriOffset = 0; | |
| 7128 | |
| 7129 /** | |
| 7130 * The HTML template URI. | |
| 7131 */ | |
| 7132 String templateUri; | |
| 7133 | |
| 7134 /** | |
| 7135 * The HTML template source. | |
| 7136 */ | |
| 7137 Source templateSource; | |
| 7138 | |
| 7139 /** | |
| 7140 * The offset of the [templateUri] in the [getSource]. | |
| 7141 */ | |
| 7142 int templateUriOffset = 0; | |
| 7143 | |
| 7144 /** | |
| 7145 * Initialize a newly created Angular component to have the given name. | |
| 7146 * | |
| 7147 * @param name the name of this element | |
| 7148 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 7149 * declaration of this element | |
| 7150 */ | |
| 7151 AngularComponentElementImpl(String name, int nameOffset, this._annotationOffse
t) : super(name, nameOffset); | |
| 7152 | |
| 7153 @override | |
| 7154 accept(ElementVisitor visitor) => visitor.visitAngularComponentElement(this); | |
| 7155 | |
| 7156 @override | |
| 7157 ElementKind get kind => ElementKind.ANGULAR_COMPONENT; | |
| 7158 | |
| 7159 @override | |
| 7160 List<AngularPropertyElement> get properties => _properties; | |
| 7161 | |
| 7162 @override | |
| 7163 List<AngularScopePropertyElement> get scopeProperties => _scopeProperties; | |
| 7164 | |
| 7165 /** | |
| 7166 * Set an array containing all of the properties declared by this component. | |
| 7167 * | |
| 7168 * @param properties the properties to set | |
| 7169 */ | |
| 7170 void set properties(List<AngularPropertyElement> properties) { | |
| 7171 for (AngularPropertyElement property in properties) { | |
| 7172 encloseElement(property as AngularPropertyElementImpl); | |
| 7173 } | |
| 7174 this._properties = properties; | |
| 7175 } | |
| 7176 | |
| 7177 /** | |
| 7178 * Set an array containing all of the scope properties declared by this compon
ent. | |
| 7179 * | |
| 7180 * @param properties the properties to set | |
| 7181 */ | |
| 7182 void set scopeProperties(List<AngularScopePropertyElement> properties) { | |
| 7183 for (AngularScopePropertyElement property in properties) { | |
| 7184 encloseElement(property as AngularScopePropertyElementImpl); | |
| 7185 } | |
| 7186 this._scopeProperties = properties; | |
| 7187 } | |
| 7188 | |
| 7189 @override | |
| 7190 void visitChildren(ElementVisitor visitor) { | |
| 7191 safelyVisitChildren(_properties, visitor); | |
| 7192 safelyVisitChildren(_scopeProperties, visitor); | |
| 7193 super.visitChildren(visitor); | |
| 7194 } | |
| 7195 | |
| 7196 @override | |
| 7197 String get identifier => "AngularComponent@${_annotationOffset}"; | |
| 7198 } | |
| 7199 | |
| 7200 /** | |
| 7201 * Implementation of `AngularControllerElement`. | |
| 7202 */ | |
| 7203 class AngularControllerElementImpl extends AngularHasSelectorElementImpl impleme
nts AngularControllerElement { | |
| 7204 /** | |
| 7205 * Initialize a newly created Angular controller to have the given name. | |
| 7206 * | |
| 7207 * @param name the name of this element | |
| 7208 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 7209 * declaration of this element | |
| 7210 */ | |
| 7211 AngularControllerElementImpl(String name, int nameOffset) : super(name, nameOf
fset); | |
| 7212 | |
| 7213 @override | |
| 7214 accept(ElementVisitor visitor) => visitor.visitAngularControllerElement(this); | |
| 7215 | |
| 7216 @override | |
| 7217 ElementKind get kind => ElementKind.ANGULAR_CONTROLLER; | |
| 7218 } | |
| 7219 | |
| 7220 /** | |
| 7221 * Implementation of `AngularDirectiveElement`. | |
| 7222 */ | |
| 7223 class AngularDecoratorElementImpl extends AngularHasSelectorElementImpl implemen
ts AngularDecoratorElement { | |
| 7224 /** | |
| 7225 * The offset of the annotation that defines this directive. | |
| 7226 */ | |
| 7227 final int _offset; | |
| 7228 | |
| 7229 /** | |
| 7230 * The array containing all of the properties declared by this directive. | |
| 7231 */ | |
| 7232 List<AngularPropertyElement> _properties = AngularPropertyElement.EMPTY_ARRAY; | |
| 7233 | |
| 7234 /** | |
| 7235 * Initialize a newly created Angular directive to have the given name. | |
| 7236 * | |
| 7237 * @param offset the offset of the annotation that defines this directive | |
| 7238 */ | |
| 7239 AngularDecoratorElementImpl(this._offset) : super(null, -1); | |
| 7240 | |
| 7241 @override | |
| 7242 accept(ElementVisitor visitor) => visitor.visitAngularDirectiveElement(this); | |
| 7243 | |
| 7244 @override | |
| 7245 String get displayName => selector.displayName; | |
| 7246 | |
| 7247 @override | |
| 7248 ElementKind get kind => ElementKind.ANGULAR_DIRECTIVE; | |
| 7249 | |
| 7250 @override | |
| 7251 List<AngularPropertyElement> get properties => _properties; | |
| 7252 | |
| 7253 @override | |
| 7254 bool isClass(String name) { | |
| 7255 Element enclosing = enclosingElement; | |
| 7256 return enclosing is ClassElement && enclosing.name == name; | |
| 7257 } | |
| 7258 | |
| 7259 /** | |
| 7260 * Set an array containing all of the properties declared by this directive. | |
| 7261 * | |
| 7262 * @param properties the properties to set | |
| 7263 */ | |
| 7264 void set properties(List<AngularPropertyElement> properties) { | |
| 7265 for (AngularPropertyElement property in properties) { | |
| 7266 encloseElement(property as AngularPropertyElementImpl); | |
| 7267 } | |
| 7268 this._properties = properties; | |
| 7269 } | |
| 7270 | |
| 7271 @override | |
| 7272 void visitChildren(ElementVisitor visitor) { | |
| 7273 safelyVisitChildren(_properties, visitor); | |
| 7274 super.visitChildren(visitor); | |
| 7275 } | |
| 7276 | |
| 7277 @override | |
| 7278 String get identifier => "Decorator@${_offset}"; | |
| 7279 } | |
| 7280 | |
| 7281 /** | |
| 7282 * Implementation of `AngularElement`. | |
| 7283 */ | |
| 7284 abstract class AngularElementImpl extends ToolkitObjectElementImpl implements An
gularElement { | |
| 7285 /** | |
| 7286 * The [AngularApplication] this element is used in. | |
| 7287 */ | |
| 7288 AngularApplication _application; | |
| 7289 | |
| 7290 /** | |
| 7291 * Initialize a newly created Angular element to have the given name. | |
| 7292 * | |
| 7293 * @param name the name of this element | |
| 7294 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 7295 * declaration of this element | |
| 7296 */ | |
| 7297 AngularElementImpl(String name, int nameOffset) : super(name, nameOffset); | |
| 7298 | |
| 7299 @override | |
| 7300 AngularApplication get application => _application; | |
| 7301 | |
| 7302 /** | |
| 7303 * Set the [AngularApplication] this element is used in. | |
| 7304 */ | |
| 7305 void set application(AngularApplication application) { | |
| 7306 this._application = application; | |
| 7307 } | |
| 7308 } | |
| 7309 | |
| 7310 /** | |
| 7311 * Implementation of `AngularFormatterElement`. | |
| 7312 */ | |
| 7313 class AngularFormatterElementImpl extends AngularElementImpl implements AngularF
ormatterElement { | |
| 7314 /** | |
| 7315 * Initialize a newly created Angular formatter to have the given name. | |
| 7316 * | |
| 7317 * @param name the name of this element | |
| 7318 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 7319 * declaration of this element | |
| 7320 */ | |
| 7321 AngularFormatterElementImpl(String name, int nameOffset) : super(name, nameOff
set); | |
| 7322 | |
| 7323 @override | |
| 7324 accept(ElementVisitor visitor) => visitor.visitAngularFormatterElement(this); | |
| 7325 | |
| 7326 @override | |
| 7327 ElementKind get kind => ElementKind.ANGULAR_FORMATTER; | |
| 7328 } | |
| 7329 | |
| 7330 /** | |
| 7331 * Implementation of [AngularSelectorElement] based on presence of a class. | |
| 7332 */ | |
| 7333 class AngularHasClassSelectorElementImpl extends AngularSelectorElementImpl impl
ements AngularHasClassSelectorElement { | |
| 7334 AngularHasClassSelectorElementImpl(String name, int offset) : super(name, offs
et); | |
| 7335 | |
| 7336 @override | |
| 7337 bool apply(XmlTagNode node) { | |
| 7338 XmlAttributeNode attribute = node.getAttribute("class"); | |
| 7339 if (attribute != null) { | |
| 7340 String text = attribute.text; | |
| 7341 if (text != null) { | |
| 7342 String name = this.name; | |
| 7343 for (String className in StringUtils.split(text)) { | |
| 7344 if (className == name) { | |
| 7345 return true; | |
| 7346 } | |
| 7347 } | |
| 7348 } | |
| 7349 } | |
| 7350 return false; | |
| 7351 } | |
| 7352 | |
| 7353 @override | |
| 7354 void appendTo(JavaStringBuilder builder) { | |
| 7355 builder.append("."); | |
| 7356 builder.append(name); | |
| 7357 } | |
| 7358 } | |
| 7359 | |
| 7360 /** | |
| 7361 * Implementation of `AngularSelectorElement`. | |
| 7362 */ | |
| 7363 abstract class AngularHasSelectorElementImpl extends AngularElementImpl implemen
ts AngularHasSelectorElement { | |
| 7364 /** | |
| 7365 * The selector of this element. | |
| 7366 */ | |
| 7367 AngularSelectorElement _selector; | |
| 7368 | |
| 7369 /** | |
| 7370 * Initialize a newly created Angular element to have the given name. | |
| 7371 * | |
| 7372 * @param name the name of this element | |
| 7373 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 7374 * declaration of this element | |
| 7375 */ | |
| 7376 AngularHasSelectorElementImpl(String name, int nameOffset) : super(name, nameO
ffset); | |
| 7377 | |
| 7378 @override | |
| 7379 AngularSelectorElement get selector => _selector; | |
| 7380 | |
| 7381 /** | |
| 7382 * Set the selector of this selector-based element. | |
| 7383 * | |
| 7384 * @param selector the selector to set | |
| 7385 */ | |
| 7386 void set selector(AngularSelectorElement selector) { | |
| 7387 encloseElement(selector as AngularSelectorElementImpl); | |
| 7388 this._selector = selector; | |
| 7389 } | |
| 7390 | |
| 7391 @override | |
| 7392 void visitChildren(ElementVisitor visitor) { | |
| 7393 safelyVisitChild(_selector, visitor); | |
| 7394 super.visitChildren(visitor); | |
| 7395 } | |
| 7396 } | |
| 7397 | |
| 7398 /** | |
| 7399 * Implementation of `AngularPropertyElement`. | |
| 7400 */ | |
| 7401 class AngularPropertyElementImpl extends AngularElementImpl implements AngularPr
opertyElement { | |
| 7402 /** | |
| 7403 * The [FieldElement] to which this property is bound. | |
| 7404 */ | |
| 7405 FieldElement field; | |
| 7406 | |
| 7407 /** | |
| 7408 * The offset of the field name in the property map. | |
| 7409 */ | |
| 7410 int fieldNameOffset = -1; | |
| 7411 | |
| 7412 AngularPropertyKind propertyKind; | |
| 7413 | |
| 7414 /** | |
| 7415 * Initialize a newly created Angular property to have the given name. | |
| 7416 * | |
| 7417 * @param name the name of this element | |
| 7418 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 7419 * declaration of this element | |
| 7420 */ | |
| 7421 AngularPropertyElementImpl(String name, int nameOffset) : super(name, nameOffs
et); | |
| 7422 | |
| 7423 @override | |
| 7424 accept(ElementVisitor visitor) => visitor.visitAngularPropertyElement(this); | |
| 7425 | |
| 7426 @override | |
| 7427 ElementKind get kind => ElementKind.ANGULAR_PROPERTY; | |
| 7428 } | |
| 7429 | |
| 7430 /** | |
| 7431 * Implementation of `AngularScopePropertyElement`. | |
| 7432 */ | |
| 7433 class AngularScopePropertyElementImpl extends AngularElementImpl implements Angu
larScopePropertyElement { | |
| 7434 /** | |
| 7435 * The type of the property | |
| 7436 */ | |
| 7437 final DartType type; | |
| 7438 | |
| 7439 /** | |
| 7440 * Initialize a newly created Angular scope property to have the given name. | |
| 7441 * | |
| 7442 * @param name the name of this element | |
| 7443 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 7444 * declaration of this element | |
| 7445 */ | |
| 7446 AngularScopePropertyElementImpl(String name, int nameOffset, this.type) : supe
r(name, nameOffset); | |
| 7447 | |
| 7448 @override | |
| 7449 accept(ElementVisitor visitor) => visitor.visitAngularScopePropertyElement(thi
s); | |
| 7450 | |
| 7451 @override | |
| 7452 ElementKind get kind => ElementKind.ANGULAR_SCOPE_PROPERTY; | |
| 7453 } | |
| 7454 | |
| 7455 /** | |
| 7456 * Implementation of `AngularFormatterElement`. | |
| 7457 */ | |
| 7458 abstract class AngularSelectorElementImpl extends AngularElementImpl implements
AngularSelectorElement { | |
| 7459 /** | |
| 7460 * Initialize a newly created Angular selector to have the given name. | |
| 7461 * | |
| 7462 * @param name the name of this element | |
| 7463 * @param nameOffset the offset of the name of this element in the file that c
ontains the | |
| 7464 * declaration of this element | |
| 7465 */ | |
| 7466 AngularSelectorElementImpl(String name, int nameOffset) : super(name, nameOffs
et); | |
| 7467 | |
| 7468 @override | |
| 7469 accept(ElementVisitor visitor) => visitor.visitAngularSelectorElement(this); | |
| 7470 | |
| 7471 @override | |
| 7472 ElementKind get kind => ElementKind.ANGULAR_SELECTOR; | |
| 7473 } | |
| 7474 | |
| 7475 /** | |
| 7476 * Implementation of [AngularSelectorElement] based on tag name. | |
| 7477 */ | |
| 7478 class AngularTagSelectorElementImpl extends AngularSelectorElementImpl implement
s AngularTagSelectorElement { | |
| 7479 AngularTagSelectorElementImpl(String name, int offset) : super(name, offset); | |
| 7480 | |
| 7481 @override | |
| 7482 bool apply(XmlTagNode node) { | |
| 7483 String tagName = name; | |
| 7484 return node.tag == tagName; | |
| 7485 } | |
| 7486 | |
| 7487 @override | |
| 7488 AngularApplication get application => (enclosingElement as AngularElementImpl)
.application; | |
| 7489 } | |
| 7490 | |
| 7491 /** | |
| 7492 * Implementation of `AngularViewElement`. | |
| 7493 */ | |
| 7494 class AngularViewElementImpl extends AngularElementImpl implements AngularViewEl
ement { | |
| 7495 /** | |
| 7496 * The HTML template URI. | |
| 7497 */ | |
| 7498 final String templateUri; | |
| 7499 | |
| 7500 /** | |
| 7501 * The offset of the [templateUri] in the [getSource]. | |
| 7502 */ | |
| 7503 final int templateUriOffset; | |
| 7504 | |
| 7505 /** | |
| 7506 * The HTML template source. | |
| 7507 */ | |
| 7508 Source templateSource; | |
| 7509 | |
| 7510 /** | |
| 7511 * Initialize a newly created Angular view. | |
| 7512 */ | |
| 7513 AngularViewElementImpl(this.templateUri, this.templateUriOffset) : super(null,
-1); | |
| 7514 | |
| 7515 @override | |
| 7516 accept(ElementVisitor visitor) => visitor.visitAngularViewElement(this); | |
| 7517 | |
| 7518 @override | |
| 7519 ElementKind get kind => ElementKind.ANGULAR_VIEW; | |
| 7520 | |
| 7521 @override | |
| 7522 String get identifier => "AngularView@${templateUriOffset}"; | |
| 7523 } | |
| 7524 | |
| 7525 /** | |
| 7526 * Implementation of [AngularSelectorElement] based on presence of attribute. | |
| 7527 */ | |
| 7528 class HasAttributeSelectorElementImpl extends AngularSelectorElementImpl impleme
nts AngularHasAttributeSelectorElement { | |
| 7529 HasAttributeSelectorElementImpl(String attributeName, int offset) : super(attr
ibuteName, offset); | |
| 7530 | |
| 7531 @override | |
| 7532 bool apply(XmlTagNode node) { | |
| 7533 String attributeName = name; | |
| 7534 return node.getAttribute(attributeName) != null; | |
| 7535 } | |
| 7536 | |
| 7537 @override | |
| 7538 void appendTo(JavaStringBuilder builder) { | |
| 7539 builder.append("["); | |
| 7540 builder.append(name); | |
| 7541 builder.append("]"); | |
| 7542 } | |
| 7543 } | |
| 7544 | |
| 7545 /** | |
| 7546 * Combination of [AngularTagSelectorElementImpl] and [HasAttributeSelectorEleme
ntImpl]. | |
| 7547 */ | |
| 7548 class IsTagHasAttributeSelectorElementImpl extends AngularSelectorElementImpl { | |
| 7549 final String tagName; | |
| 7550 | |
| 7551 final String attributeName; | |
| 7552 | |
| 7553 IsTagHasAttributeSelectorElementImpl(this.tagName, this.attributeName) : super
(null, -1); | |
| 7554 | |
| 7555 @override | |
| 7556 bool apply(XmlTagNode node) => node.tag == tagName && node.getAttribute(attrib
uteName) != null; | |
| 7557 } | |
| 7558 | |
| 7559 /** | |
| 7560 * Instances of the class `ConstructorMember` represent a constructor element de
fined in a | |
| 7561 * parameterized type where the values of the type parameters are known. | |
| 7562 */ | |
| 7563 class ConstructorMember extends ExecutableMember implements ConstructorElement { | |
| 7564 /** | |
| 7565 * If the given constructor's type is different when any type parameters from
the defining type's | |
| 7566 * declaration are replaced with the actual type arguments from the defining t
ype, create a | |
| 7567 * constructor member representing the given constructor. Return the member th
at was created, or | |
| 7568 * the base constructor if no member was created. | |
| 7569 * | |
| 7570 * @param baseConstructor the base constructor for which a member might be cre
ated | |
| 7571 * @param definingType the type defining the parameters and arguments to be us
ed in the | |
| 7572 * substitution | |
| 7573 * @return the constructor element that will return the correctly substituted
types | |
| 7574 */ | |
| 7575 static ConstructorElement from(ConstructorElement baseConstructor, InterfaceTy
pe definingType) { | |
| 7576 if (baseConstructor == null || definingType.typeArguments.length == 0) { | |
| 7577 return baseConstructor; | |
| 7578 } | |
| 7579 FunctionType baseType = baseConstructor.type; | |
| 7580 if (baseType == null) { | |
| 7581 // TODO(brianwilkerson) We need to understand when this can happen. | |
| 7582 return baseConstructor; | |
| 7583 } | |
| 7584 List<DartType> argumentTypes = definingType.typeArguments; | |
| 7585 List<DartType> parameterTypes = definingType.element.type.typeArguments; | |
| 7586 FunctionType substitutedType = baseType.substitute2(argumentTypes, parameter
Types); | |
| 7587 if (baseType == substitutedType) { | |
| 7588 return baseConstructor; | |
| 7589 } | |
| 7590 // TODO(brianwilkerson) Consider caching the substituted type in the instanc
e. It would use more | |
| 7591 // memory but speed up some operations. We need to see how often the type is
being re-computed. | |
| 7592 return new ConstructorMember(baseConstructor, definingType); | |
| 7593 } | |
| 7594 | |
| 7595 /** | |
| 7596 * Initialize a newly created element to represent a constructor of the given
parameterized type. | |
| 7597 * | |
| 7598 * @param baseElement the element on which the parameterized element was creat
ed | |
| 7599 * @param definingType the type in which the element is defined | |
| 7600 */ | |
| 7601 ConstructorMember(ConstructorElement baseElement, InterfaceType definingType)
: super(baseElement, definingType); | |
| 7602 | |
| 7603 @override | |
| 7604 accept(ElementVisitor visitor) => visitor.visitConstructorElement(this); | |
| 7605 | |
| 7606 @override | |
| 7607 ConstructorElement get baseElement => super.baseElement as ConstructorElement; | |
| 7608 | |
| 7609 @override | |
| 7610 ClassElement get enclosingElement => baseElement.enclosingElement; | |
| 7611 | |
| 7612 @override | |
| 7613 ConstructorDeclaration get node => baseElement.node; | |
| 7614 | |
| 7615 @override | |
| 7616 ConstructorElement get redirectedConstructor => from(baseElement.redirectedCon
structor, definingType); | |
| 7617 | |
| 7618 @override | |
| 7619 bool get isConst => baseElement.isConst; | |
| 7620 | |
| 7621 @override | |
| 7622 bool get isDefaultConstructor => baseElement.isDefaultConstructor; | |
| 7623 | |
| 7624 @override | |
| 7625 bool get isFactory => baseElement.isFactory; | |
| 7626 | |
| 7627 @override | |
| 7628 String toString() { | |
| 7629 ConstructorElement baseElement = this.baseElement; | |
| 7630 List<ParameterElement> parameters = this.parameters; | |
| 7631 FunctionType type = this.type; | |
| 7632 JavaStringBuilder builder = new JavaStringBuilder(); | |
| 7633 builder.append(baseElement.enclosingElement.displayName); | |
| 7634 String name = displayName; | |
| 7635 if (name != null && !name.isEmpty) { | |
| 7636 builder.append("."); | |
| 7637 builder.append(name); | |
| 7638 } | |
| 7639 builder.append("("); | |
| 7640 int parameterCount = parameters.length; | |
| 7641 for (int i = 0; i < parameterCount; i++) { | |
| 7642 if (i > 0) { | |
| 7643 builder.append(", "); | |
| 7644 } | |
| 7645 builder.append(parameters[i]).toString(); | |
| 7646 } | |
| 7647 builder.append(")"); | |
| 7648 if (type != null) { | |
| 7649 builder.append(Element.RIGHT_ARROW); | |
| 7650 builder.append(type.returnType); | |
| 7651 } | |
| 7652 return builder.toString(); | |
| 7653 } | |
| 7654 | |
| 7655 @override | |
| 7656 InterfaceType get definingType => super.definingType as InterfaceType; | |
| 7657 } | |
| 7658 | |
| 7659 /** | |
| 7660 * The abstract class `ExecutableMember` defines the behavior common to members
that represent | |
| 7661 * an executable element defined in a parameterized type where the values of the
type parameters are | |
| 7662 * known. | |
| 7663 */ | |
| 7664 abstract class ExecutableMember extends Member implements ExecutableElement { | |
| 7665 /** | |
| 7666 * Initialize a newly created element to represent an executable element of th
e given | |
| 7667 * parameterized type. | |
| 7668 * | |
| 7669 * @param baseElement the element on which the parameterized element was creat
ed | |
| 7670 * @param definingType the type in which the element is defined | |
| 7671 */ | |
| 7672 ExecutableMember(ExecutableElement baseElement, InterfaceType definingType) :
super(baseElement, definingType); | |
| 7673 | |
| 7674 @override | |
| 7675 ExecutableElement get baseElement => super.baseElement as ExecutableElement; | |
| 7676 | |
| 7677 @override | |
| 7678 List<FunctionElement> get functions { | |
| 7679 // | |
| 7680 // Elements within this element should have type parameters substituted, jus
t like this element. | |
| 7681 // | |
| 7682 throw new UnsupportedOperationException(); | |
| 7683 } | |
| 7684 | |
| 7685 @override | |
| 7686 List<LabelElement> get labels => baseElement.labels; | |
| 7687 | |
| 7688 @override | |
| 7689 List<LocalVariableElement> get localVariables { | |
| 7690 // | |
| 7691 // Elements within this element should have type parameters substituted, jus
t like this element. | |
| 7692 // | |
| 7693 throw new UnsupportedOperationException(); | |
| 7694 } | |
| 7695 | |
| 7696 @override | |
| 7697 List<ParameterElement> get parameters { | |
| 7698 List<ParameterElement> baseParameters = baseElement.parameters; | |
| 7699 int parameterCount = baseParameters.length; | |
| 7700 if (parameterCount == 0) { | |
| 7701 return baseParameters; | |
| 7702 } | |
| 7703 List<ParameterElement> parameterizedParameters = new List<ParameterElement>(
parameterCount); | |
| 7704 for (int i = 0; i < parameterCount; i++) { | |
| 7705 parameterizedParameters[i] = ParameterMember.from(baseParameters[i], defin
ingType); | |
| 7706 } | |
| 7707 return parameterizedParameters; | |
| 7708 } | |
| 7709 | |
| 7710 @override | |
| 7711 DartType get returnType => substituteFor(baseElement.returnType); | |
| 7712 | |
| 7713 @override | |
| 7714 FunctionType get type => substituteFor(baseElement.type); | |
| 7715 | |
| 7716 @override | |
| 7717 bool get isOperator => baseElement.isOperator; | |
| 7718 | |
| 7719 @override | |
| 7720 bool get isStatic => baseElement.isStatic; | |
| 7721 | |
| 7722 @override | |
| 7723 void visitChildren(ElementVisitor visitor) { | |
| 7724 // TODO(brianwilkerson) We need to finish implementing the accessors used be
low so that we can | |
| 7725 // safely invoke them. | |
| 7726 super.visitChildren(visitor); | |
| 7727 safelyVisitChildren(baseElement.functions, visitor); | |
| 7728 safelyVisitChildren(labels, visitor); | |
| 7729 safelyVisitChildren(baseElement.localVariables, visitor); | |
| 7730 safelyVisitChildren(parameters, visitor); | |
| 7731 } | |
| 7732 } | |
| 7733 | |
| 7734 /** | |
| 7735 * Instances of the class `FieldFormalParameterMember` represent a parameter ele
ment defined | |
| 7736 * in a parameterized type where the values of the type parameters are known. | |
| 7737 */ | |
| 7738 class FieldFormalParameterMember extends ParameterMember implements FieldFormalP
arameterElement { | |
| 7739 /** | |
| 7740 * Initialize a newly created element to represent a parameter of the given pa
rameterized type. | |
| 7741 * | |
| 7742 * @param baseElement the element on which the parameterized element was creat
ed | |
| 7743 * @param definingType the type in which the element is defined | |
| 7744 */ | |
| 7745 FieldFormalParameterMember(FieldFormalParameterElement baseElement, Parameteri
zedType definingType) : super(baseElement, definingType); | |
| 7746 | |
| 7747 @override | |
| 7748 accept(ElementVisitor visitor) => visitor.visitFieldFormalParameterElement(thi
s); | |
| 7749 | |
| 7750 @override | |
| 7751 FieldElement get field => (baseElement as FieldFormalParameterElement).field; | |
| 7752 } | |
| 7753 | |
| 7754 /** | |
| 7755 * Instances of the class `FieldMember` represent a field element defined in a p
arameterized | |
| 7756 * type where the values of the type parameters are known. | |
| 7757 */ | |
| 7758 class FieldMember extends VariableMember implements FieldElement { | |
| 7759 /** | |
| 7760 * If the given field's type is different when any type parameters from the de
fining type's | |
| 7761 * declaration are replaced with the actual type arguments from the defining t
ype, create a field | |
| 7762 * member representing the given field. Return the member that was created, or
the base field if | |
| 7763 * no member was created. | |
| 7764 * | |
| 7765 * @param baseField the base field for which a member might be created | |
| 7766 * @param definingType the type defining the parameters and arguments to be us
ed in the | |
| 7767 * substitution | |
| 7768 * @return the field element that will return the correctly substituted types | |
| 7769 */ | |
| 7770 static FieldElement from(FieldElement baseField, InterfaceType definingType) { | |
| 7771 if (baseField == null || definingType.typeArguments.length == 0) { | |
| 7772 return baseField; | |
| 7773 } | |
| 7774 DartType baseType = baseField.type; | |
| 7775 if (baseType == null) { | |
| 7776 return baseField; | |
| 7777 } | |
| 7778 List<DartType> argumentTypes = definingType.typeArguments; | |
| 7779 List<DartType> parameterTypes = definingType.element.type.typeArguments; | |
| 7780 DartType substitutedType = baseType.substitute2(argumentTypes, parameterType
s); | |
| 7781 if (baseType == substitutedType) { | |
| 7782 return baseField; | |
| 7783 } | |
| 7784 // TODO(brianwilkerson) Consider caching the substituted type in the instanc
e. It would use more | |
| 7785 // memory but speed up some operations. We need to see how often the type is
being re-computed. | |
| 7786 return new FieldMember(baseField, definingType); | |
| 7787 } | |
| 7788 | |
| 7789 /** | |
| 7790 * Initialize a newly created element to represent a field of the given parame
terized type. | |
| 7791 * | |
| 7792 * @param baseElement the element on which the parameterized element was creat
ed | |
| 7793 * @param definingType the type in which the element is defined | |
| 7794 */ | |
| 7795 FieldMember(FieldElement baseElement, InterfaceType definingType) : super(base
Element, definingType); | |
| 7796 | |
| 7797 @override | |
| 7798 accept(ElementVisitor visitor) => visitor.visitFieldElement(this); | |
| 7799 | |
| 7800 @override | |
| 7801 FieldElement get baseElement => super.baseElement as FieldElement; | |
| 7802 | |
| 7803 @override | |
| 7804 ClassElement get enclosingElement => baseElement.enclosingElement; | |
| 7805 | |
| 7806 @override | |
| 7807 PropertyAccessorElement get getter => PropertyAccessorMember.from(baseElement.
getter, definingType); | |
| 7808 | |
| 7809 @override | |
| 7810 PropertyAccessorElement get setter => PropertyAccessorMember.from(baseElement.
setter, definingType); | |
| 7811 | |
| 7812 @override | |
| 7813 bool get isStatic => baseElement.isStatic; | |
| 7814 | |
| 7815 @override | |
| 7816 InterfaceType get definingType => super.definingType as InterfaceType; | |
| 7817 } | 7871 } |
| 7818 | 7872 |
| 7819 /** | 7873 /** |
| 7820 * The abstract class `Member` defines the behavior common to elements that repr
esent members | 7874 * The abstract class `Member` defines the behavior common to elements that repr
esent members |
| 7821 * of parameterized types. | 7875 * of parameterized types. |
| 7822 */ | 7876 */ |
| 7823 abstract class Member implements Element { | 7877 abstract class Member implements Element { |
| 7824 /** | 7878 /** |
| 7825 * The element on which the parameterized element was created. | 7879 * The element on which the parameterized element was created. |
| 7826 */ | 7880 */ |
| (...skipping 137 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 7964 int count = types.length; | 8018 int count = types.length; |
| 7965 List<InterfaceType> substitutedTypes = new List<InterfaceType>(count); | 8019 List<InterfaceType> substitutedTypes = new List<InterfaceType>(count); |
| 7966 for (int i = 0; i < count; i++) { | 8020 for (int i = 0; i < count; i++) { |
| 7967 substitutedTypes[i] = substituteFor(types[i]); | 8021 substitutedTypes[i] = substituteFor(types[i]); |
| 7968 } | 8022 } |
| 7969 return substitutedTypes; | 8023 return substitutedTypes; |
| 7970 } | 8024 } |
| 7971 } | 8025 } |
| 7972 | 8026 |
| 7973 /** | 8027 /** |
| 8028 * The interface `MethodElement` defines the behavior of elements that represent
a method |
| 8029 * defined within a type. |
| 8030 */ |
| 8031 abstract class MethodElement implements ClassMemberElement, ExecutableElement { |
| 8032 /** |
| 8033 * Return the resolved [MethodDeclaration] node that declares this [MethodElem
ent]. |
| 8034 * |
| 8035 * This method is expensive, because resolved AST might be evicted from cache,
so parsing and |
| 8036 * resolving will be performed. |
| 8037 * |
| 8038 * @return the resolved [MethodDeclaration], not `null`. |
| 8039 */ |
| 8040 @override |
| 8041 MethodDeclaration get node; |
| 8042 |
| 8043 /** |
| 8044 * Return `true` if this method is abstract. Methods are abstract if they are
not external |
| 8045 * and have no body. |
| 8046 * |
| 8047 * @return `true` if this method is abstract |
| 8048 */ |
| 8049 bool get isAbstract; |
| 8050 } |
| 8051 |
| 8052 /** |
| 8053 * Instances of the class `MethodElementImpl` implement a `MethodElement`. |
| 8054 */ |
| 8055 class MethodElementImpl extends ExecutableElementImpl implements MethodElement { |
| 8056 /** |
| 8057 * An empty array of method elements. |
| 8058 */ |
| 8059 static List<MethodElement> EMPTY_ARRAY = new List<MethodElement>(0); |
| 8060 |
| 8061 /** |
| 8062 * Initialize a newly created method element to have the given name. |
| 8063 * |
| 8064 * @param name the name of this element |
| 8065 */ |
| 8066 MethodElementImpl.forNode(Identifier name) : super.forNode(name); |
| 8067 |
| 8068 /** |
| 8069 * Initialize a newly created method element to have the given name. |
| 8070 * |
| 8071 * @param name the name of this element |
| 8072 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 8073 * declaration of this element |
| 8074 */ |
| 8075 MethodElementImpl(String name, int nameOffset) : super(name, nameOffset); |
| 8076 |
| 8077 @override |
| 8078 accept(ElementVisitor visitor) => visitor.visitMethodElement(this); |
| 8079 |
| 8080 @override |
| 8081 String get displayName { |
| 8082 String displayName = super.displayName; |
| 8083 if ("unary-" == displayName) { |
| 8084 return "-"; |
| 8085 } |
| 8086 return displayName; |
| 8087 } |
| 8088 |
| 8089 @override |
| 8090 ClassElement get enclosingElement => super.enclosingElement as ClassElement; |
| 8091 |
| 8092 @override |
| 8093 ElementKind get kind => ElementKind.METHOD; |
| 8094 |
| 8095 @override |
| 8096 String get name { |
| 8097 String name = super.name; |
| 8098 if (isOperator && name == "-") { |
| 8099 if (parameters.length == 0) { |
| 8100 return "unary-"; |
| 8101 } |
| 8102 } |
| 8103 return super.name; |
| 8104 } |
| 8105 |
| 8106 @override |
| 8107 MethodDeclaration get node => getNodeMatching((node) => node is MethodDeclarat
ion); |
| 8108 |
| 8109 @override |
| 8110 bool get isAbstract => hasModifier(Modifier.ABSTRACT); |
| 8111 |
| 8112 @override |
| 8113 bool get isOperator { |
| 8114 String name = displayName; |
| 8115 if (name.isEmpty) { |
| 8116 return false; |
| 8117 } |
| 8118 int first = name.codeUnitAt(0); |
| 8119 return !((0x61 <= first && first <= 0x7A) || (0x41 <= first && first <= 0x5A
) || first == 0x5F || first == 0x24); |
| 8120 } |
| 8121 |
| 8122 @override |
| 8123 bool get isStatic => hasModifier(Modifier.STATIC); |
| 8124 |
| 8125 /** |
| 8126 * Set whether this method is abstract to correspond to the given value. |
| 8127 * |
| 8128 * @param isAbstract `true` if the method is abstract |
| 8129 */ |
| 8130 void set abstract(bool isAbstract) { |
| 8131 setModifier(Modifier.ABSTRACT, isAbstract); |
| 8132 } |
| 8133 |
| 8134 /** |
| 8135 * Set whether this method is static to correspond to the given value. |
| 8136 * |
| 8137 * @param isStatic `true` if the method is static |
| 8138 */ |
| 8139 void set static(bool isStatic) { |
| 8140 setModifier(Modifier.STATIC, isStatic); |
| 8141 } |
| 8142 |
| 8143 @override |
| 8144 void appendTo(JavaStringBuilder builder) { |
| 8145 builder.append(enclosingElement.displayName); |
| 8146 builder.append("."); |
| 8147 builder.append(displayName); |
| 8148 super.appendTo(builder); |
| 8149 } |
| 8150 } |
| 8151 |
| 8152 /** |
| 7974 * Instances of the class `MethodMember` represent a method element defined in a
parameterized | 8153 * Instances of the class `MethodMember` represent a method element defined in a
parameterized |
| 7975 * type where the values of the type parameters are known. | 8154 * type where the values of the type parameters are known. |
| 7976 */ | 8155 */ |
| 7977 class MethodMember extends ExecutableMember implements MethodElement { | 8156 class MethodMember extends ExecutableMember implements MethodElement { |
| 7978 /** | 8157 /** |
| 7979 * If the given method's type is different when any type parameters from the d
efining type's | 8158 * If the given method's type is different when any type parameters from the d
efining type's |
| 7980 * declaration are replaced with the actual type arguments from the defining t
ype, create a method | 8159 * declaration are replaced with the actual type arguments from the defining t
ype, create a method |
| 7981 * member representing the given method. Return the member that was created, o
r the base method if | 8160 * member representing the given method. Return the member that was created, o
r the base method if |
| 7982 * no member was created. | 8161 * no member was created. |
| 7983 * | 8162 * |
| (...skipping 60 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 8044 } | 8223 } |
| 8045 builder.append(")"); | 8224 builder.append(")"); |
| 8046 if (type != null) { | 8225 if (type != null) { |
| 8047 builder.append(Element.RIGHT_ARROW); | 8226 builder.append(Element.RIGHT_ARROW); |
| 8048 builder.append(type.returnType); | 8227 builder.append(type.returnType); |
| 8049 } | 8228 } |
| 8050 return builder.toString(); | 8229 return builder.toString(); |
| 8051 } | 8230 } |
| 8052 } | 8231 } |
| 8053 | 8232 |
| 8233 /** |
| 8234 * The enumeration `Modifier` defines constants for all of the modifiers defined
by the Dart |
| 8235 * language and for a few additional flags that are useful. |
| 8236 */ |
| 8237 class Modifier extends Enum<Modifier> { |
| 8238 /** |
| 8239 * Indicates that the modifier 'abstract' was applied to the element. |
| 8240 */ |
| 8241 static const Modifier ABSTRACT = const Modifier('ABSTRACT', 0); |
| 8242 |
| 8243 /** |
| 8244 * Indicates that the modifier 'const' was applied to the element. |
| 8245 */ |
| 8246 static const Modifier CONST = const Modifier('CONST', 1); |
| 8247 |
| 8248 /** |
| 8249 * Indicates that the import element represents a deferred library. |
| 8250 */ |
| 8251 static const Modifier DEFERRED = const Modifier('DEFERRED', 2); |
| 8252 |
| 8253 /** |
| 8254 * Indicates that the modifier 'factory' was applied to the element. |
| 8255 */ |
| 8256 static const Modifier FACTORY = const Modifier('FACTORY', 3); |
| 8257 |
| 8258 /** |
| 8259 * Indicates that the modifier 'final' was applied to the element. |
| 8260 */ |
| 8261 static const Modifier FINAL = const Modifier('FINAL', 4); |
| 8262 |
| 8263 /** |
| 8264 * Indicates that the pseudo-modifier 'get' was applied to the element. |
| 8265 */ |
| 8266 static const Modifier GETTER = const Modifier('GETTER', 5); |
| 8267 |
| 8268 /** |
| 8269 * A flag used for libraries indicating that the defining compilation unit con
tains at least one |
| 8270 * import directive whose URI uses the "dart-ext" scheme. |
| 8271 */ |
| 8272 static const Modifier HAS_EXT_URI = const Modifier('HAS_EXT_URI', 6); |
| 8273 |
| 8274 static const Modifier MIXIN = const Modifier('MIXIN', 7); |
| 8275 |
| 8276 static const Modifier REFERENCES_SUPER = const Modifier('REFERENCES_SUPER', 8)
; |
| 8277 |
| 8278 /** |
| 8279 * Indicates that the pseudo-modifier 'set' was applied to the element. |
| 8280 */ |
| 8281 static const Modifier SETTER = const Modifier('SETTER', 9); |
| 8282 |
| 8283 /** |
| 8284 * Indicates that the modifier 'static' was applied to the element. |
| 8285 */ |
| 8286 static const Modifier STATIC = const Modifier('STATIC', 10); |
| 8287 |
| 8288 /** |
| 8289 * Indicates that the element does not appear in the source code but was impli
citly created. For |
| 8290 * example, if a class does not define any constructors, an implicit zero-argu
ment constructor |
| 8291 * will be created and it will be marked as being synthetic. |
| 8292 */ |
| 8293 static const Modifier SYNTHETIC = const Modifier('SYNTHETIC', 11); |
| 8294 |
| 8295 static const Modifier TYPEDEF = const Modifier('TYPEDEF', 12); |
| 8296 |
| 8297 static const List<Modifier> values = const [ |
| 8298 ABSTRACT, |
| 8299 CONST, |
| 8300 DEFERRED, |
| 8301 FACTORY, |
| 8302 FINAL, |
| 8303 GETTER, |
| 8304 HAS_EXT_URI, |
| 8305 MIXIN, |
| 8306 REFERENCES_SUPER, |
| 8307 SETTER, |
| 8308 STATIC, |
| 8309 SYNTHETIC, |
| 8310 TYPEDEF]; |
| 8311 |
| 8312 const Modifier(String name, int ordinal) : super(name, ordinal); |
| 8313 } |
| 8314 |
| 8315 /** |
| 8316 * The interface `MultiplyDefinedElement` defines the behavior of pseudo-element
s that |
| 8317 * represent multiple elements defined within a single scope that have the same
name. This situation |
| 8318 * is not allowed by the language, so objects implementing this interface always
represent an error. |
| 8319 * As a result, most of the normal operations on elements do not make sense and
will return useless |
| 8320 * results. |
| 8321 */ |
| 8322 abstract class MultiplyDefinedElement implements Element { |
| 8323 /** |
| 8324 * Return an array containing all of the elements that were defined within the
scope to have the |
| 8325 * same name. |
| 8326 * |
| 8327 * @return the elements that were defined with the same name |
| 8328 */ |
| 8329 List<Element> get conflictingElements; |
| 8330 |
| 8331 /** |
| 8332 * Return the type of this element as the dynamic type. |
| 8333 * |
| 8334 * @return the type of this element as the dynamic type |
| 8335 */ |
| 8336 DartType get type; |
| 8337 } |
| 8338 |
| 8339 /** |
| 8340 * Instances of the class `MultiplyDefinedElementImpl` represent a collection of
elements that |
| 8341 * have the same name within the same scope. |
| 8342 */ |
| 8343 class MultiplyDefinedElementImpl implements MultiplyDefinedElement { |
| 8344 /** |
| 8345 * Return an element that represents the given conflicting elements. |
| 8346 * |
| 8347 * @param context the analysis context in which the multiply defined elements
are defined |
| 8348 * @param firstElement the first element that conflicts |
| 8349 * @param secondElement the second element that conflicts |
| 8350 */ |
| 8351 static Element fromElements(AnalysisContext context, Element firstElement, Ele
ment secondElement) { |
| 8352 List<Element> conflictingElements = _computeConflictingElements(firstElement
, secondElement); |
| 8353 int length = conflictingElements.length; |
| 8354 if (length == 0) { |
| 8355 return null; |
| 8356 } else if (length == 1) { |
| 8357 return conflictingElements[0]; |
| 8358 } |
| 8359 return new MultiplyDefinedElementImpl(context, conflictingElements); |
| 8360 } |
| 8361 |
| 8362 /** |
| 8363 * Add the given element to the list of elements. If the element is a multiply
-defined element, |
| 8364 * add all of the conflicting elements that it represents. |
| 8365 * |
| 8366 * @param elements the list to which the element(s) are to be added |
| 8367 * @param element the element(s) to be added |
| 8368 */ |
| 8369 static void _add(Set<Element> elements, Element element) { |
| 8370 if (element is MultiplyDefinedElementImpl) { |
| 8371 for (Element conflictingElement in element.conflictingElements) { |
| 8372 elements.add(conflictingElement); |
| 8373 } |
| 8374 } else { |
| 8375 elements.add(element); |
| 8376 } |
| 8377 } |
| 8378 |
| 8379 /** |
| 8380 * Use the given elements to construct an array of conflicting elements. If ei
ther of the given |
| 8381 * elements are multiply-defined elements then the conflicting elements they r
epresent will be |
| 8382 * included in the array. Otherwise, the element itself will be included. |
| 8383 * |
| 8384 * @param firstElement the first element to be included |
| 8385 * @param secondElement the second element to be included |
| 8386 * @return an array containing all of the conflicting elements |
| 8387 */ |
| 8388 static List<Element> _computeConflictingElements(Element firstElement, Element
secondElement) { |
| 8389 Set<Element> elements = new Set<Element>(); |
| 8390 _add(elements, firstElement); |
| 8391 _add(elements, secondElement); |
| 8392 return new List.from(elements); |
| 8393 } |
| 8394 |
| 8395 /** |
| 8396 * The analysis context in which the multiply defined elements are defined. |
| 8397 */ |
| 8398 final AnalysisContext context; |
| 8399 |
| 8400 /** |
| 8401 * The name of the conflicting elements. |
| 8402 */ |
| 8403 String _name; |
| 8404 |
| 8405 /** |
| 8406 * A list containing all of the elements that conflict. |
| 8407 */ |
| 8408 final List<Element> conflictingElements; |
| 8409 |
| 8410 /** |
| 8411 * Initialize a newly created element to represent a list of conflicting eleme
nts. |
| 8412 * |
| 8413 * @param context the analysis context in which the multiply defined elements
are defined |
| 8414 * @param conflictingElements the elements that conflict |
| 8415 */ |
| 8416 MultiplyDefinedElementImpl(this.context, this.conflictingElements) { |
| 8417 _name = conflictingElements[0].name; |
| 8418 } |
| 8419 |
| 8420 @override |
| 8421 accept(ElementVisitor visitor) => visitor.visitMultiplyDefinedElement(this); |
| 8422 |
| 8423 @override |
| 8424 String computeDocumentationComment() => null; |
| 8425 |
| 8426 @override |
| 8427 Element getAncestor(Predicate<Element> predicate) => null; |
| 8428 |
| 8429 @override |
| 8430 String get displayName => _name; |
| 8431 |
| 8432 @override |
| 8433 Element get enclosingElement => null; |
| 8434 |
| 8435 @override |
| 8436 ElementKind get kind => ElementKind.ERROR; |
| 8437 |
| 8438 @override |
| 8439 LibraryElement get library => null; |
| 8440 |
| 8441 @override |
| 8442 ElementLocation get location => null; |
| 8443 |
| 8444 @override |
| 8445 List<ElementAnnotation> get metadata => ElementAnnotationImpl.EMPTY_ARRAY; |
| 8446 |
| 8447 @override |
| 8448 String get name => _name; |
| 8449 |
| 8450 @override |
| 8451 int get nameOffset => -1; |
| 8452 |
| 8453 @override |
| 8454 AstNode get node => null; |
| 8455 |
| 8456 @override |
| 8457 Source get source => null; |
| 8458 |
| 8459 @override |
| 8460 DartType get type => DynamicTypeImpl.instance; |
| 8461 |
| 8462 @override |
| 8463 CompilationUnit get unit => null; |
| 8464 |
| 8465 @override |
| 8466 bool isAccessibleIn(LibraryElement library) { |
| 8467 for (Element element in conflictingElements) { |
| 8468 if (element.isAccessibleIn(library)) { |
| 8469 return true; |
| 8470 } |
| 8471 } |
| 8472 return false; |
| 8473 } |
| 8474 |
| 8475 @override |
| 8476 bool get isDeprecated => false; |
| 8477 |
| 8478 @override |
| 8479 bool get isOverride => false; |
| 8480 |
| 8481 @override |
| 8482 bool get isPrivate { |
| 8483 String name = displayName; |
| 8484 if (name == null) { |
| 8485 return false; |
| 8486 } |
| 8487 return Identifier.isPrivateName(name); |
| 8488 } |
| 8489 |
| 8490 @override |
| 8491 bool get isPublic => !isPrivate; |
| 8492 |
| 8493 @override |
| 8494 bool get isSynthetic => true; |
| 8495 |
| 8496 @override |
| 8497 String toString() { |
| 8498 JavaStringBuilder builder = new JavaStringBuilder(); |
| 8499 builder.append("["); |
| 8500 int count = conflictingElements.length; |
| 8501 for (int i = 0; i < count; i++) { |
| 8502 if (i > 0) { |
| 8503 builder.append(", "); |
| 8504 } |
| 8505 (conflictingElements[i] as ElementImpl).appendTo(builder); |
| 8506 } |
| 8507 builder.append("]"); |
| 8508 return builder.toString(); |
| 8509 } |
| 8510 |
| 8511 @override |
| 8512 void visitChildren(ElementVisitor visitor) { |
| 8513 } |
| 8514 } |
| 8515 |
| 8516 /** |
| 8517 * The interface [MultiplyInheritedExecutableElement] defines all of the behavio
r of an |
| 8518 * [ExecutableElement], with the additional information of an array of |
| 8519 * [ExecutableElement]s from which this element was composed. |
| 8520 */ |
| 8521 abstract class MultiplyInheritedExecutableElement implements ExecutableElement { |
| 8522 /** |
| 8523 * Return an array containing all of the executable elements defined within th
is executable |
| 8524 * element. |
| 8525 * |
| 8526 * @return the elements defined within this executable element |
| 8527 */ |
| 8528 List<ExecutableElement> get inheritedElements; |
| 8529 } |
| 8530 |
| 8531 /** |
| 8532 * The interface [MultiplyInheritedMethodElementImpl] defines all of the behavio
r of an |
| 8533 * [MethodElementImpl], with the additional information of an array of |
| 8534 * [ExecutableElement]s from which this element was composed. |
| 8535 */ |
| 8536 class MultiplyInheritedMethodElementImpl extends MethodElementImpl implements Mu
ltiplyInheritedExecutableElement { |
| 8537 /** |
| 8538 * An array the array of executable elements that were used to compose this el
ement. |
| 8539 */ |
| 8540 List<ExecutableElement> _elements = MethodElementImpl.EMPTY_ARRAY; |
| 8541 |
| 8542 MultiplyInheritedMethodElementImpl(Identifier name) : super.forNode(name) { |
| 8543 synthetic = true; |
| 8544 } |
| 8545 |
| 8546 @override |
| 8547 List<ExecutableElement> get inheritedElements => _elements; |
| 8548 |
| 8549 void set inheritedElements(List<ExecutableElement> elements) { |
| 8550 this._elements = elements; |
| 8551 } |
| 8552 } |
| 8553 |
| 8554 /** |
| 8555 * The interface [MultiplyInheritedPropertyAccessorElementImpl] defines all of t
he behavior of |
| 8556 * an [PropertyAccessorElementImpl], with the additional information of an array
of |
| 8557 * [ExecutableElement]s from which this element was composed. |
| 8558 */ |
| 8559 class MultiplyInheritedPropertyAccessorElementImpl extends PropertyAccessorEleme
ntImpl implements MultiplyInheritedExecutableElement { |
| 8560 /** |
| 8561 * An array the array of executable elements that were used to compose this el
ement. |
| 8562 */ |
| 8563 List<ExecutableElement> _elements = PropertyAccessorElementImpl.EMPTY_ARRAY; |
| 8564 |
| 8565 MultiplyInheritedPropertyAccessorElementImpl(Identifier name) : super.forNode(
name) { |
| 8566 synthetic = true; |
| 8567 } |
| 8568 |
| 8569 @override |
| 8570 List<ExecutableElement> get inheritedElements => _elements; |
| 8571 |
| 8572 void set inheritedElements(List<ExecutableElement> elements) { |
| 8573 this._elements = elements; |
| 8574 } |
| 8575 } |
| 8576 |
| 8577 /** |
| 8578 * The interface `NamespaceCombinator` defines the behavior common to objects th
at control how |
| 8579 * namespaces are combined. |
| 8580 */ |
| 8581 abstract class NamespaceCombinator { |
| 8582 /** |
| 8583 * An empty array of namespace combinators. |
| 8584 */ |
| 8585 static final List<NamespaceCombinator> EMPTY_ARRAY = new List<NamespaceCombina
tor>(0); |
| 8586 } |
| 8587 |
| 8588 /** |
| 8589 * The interface `ParameterElement` defines the behavior of elements representin
g a parameter |
| 8590 * defined within an executable element. |
| 8591 */ |
| 8592 abstract class ParameterElement implements LocalElement, VariableElement { |
| 8593 /** |
| 8594 * Return a source range that covers the portion of the source in which the de
fault value for this |
| 8595 * parameter is specified, or `null` if there is no default value. |
| 8596 * |
| 8597 * @return the range of characters in which the default value of this paramete
r is specified |
| 8598 */ |
| 8599 SourceRange get defaultValueRange; |
| 8600 |
| 8601 /** |
| 8602 * Return the kind of this parameter. |
| 8603 * |
| 8604 * @return the kind of this parameter |
| 8605 */ |
| 8606 ParameterKind get parameterKind; |
| 8607 |
| 8608 /** |
| 8609 * Return an array containing all of the parameters defined by this parameter.
A parameter will |
| 8610 * only define other parameters if it is a function typed parameter. |
| 8611 * |
| 8612 * @return the parameters defined by this parameter element |
| 8613 */ |
| 8614 List<ParameterElement> get parameters; |
| 8615 |
| 8616 /** |
| 8617 * Return `true` if this parameter is an initializing formal parameter. |
| 8618 * |
| 8619 * @return `true` if this parameter is an initializing formal parameter |
| 8620 */ |
| 8621 bool get isInitializingFormal; |
| 8622 } |
| 8623 |
| 8624 /** |
| 8625 * Instances of the class `ParameterElementImpl` implement a `ParameterElement`. |
| 8626 */ |
| 8627 class ParameterElementImpl extends VariableElementImpl implements ParameterEleme
nt { |
| 8628 /** |
| 8629 * Is `true` if this variable is potentially mutated somewhere in its scope. |
| 8630 */ |
| 8631 bool _potentiallyMutatedInScope = false; |
| 8632 |
| 8633 /** |
| 8634 * Is `true` if this variable is potentially mutated somewhere in closure. |
| 8635 */ |
| 8636 bool _potentiallyMutatedInClosure = false; |
| 8637 |
| 8638 /** |
| 8639 * An array containing all of the parameters defined by this parameter element
. There will only be |
| 8640 * parameters if this parameter is a function typed parameter. |
| 8641 */ |
| 8642 List<ParameterElement> _parameters = ParameterElementImpl.EMPTY_ARRAY; |
| 8643 |
| 8644 /** |
| 8645 * The kind of this parameter. |
| 8646 */ |
| 8647 ParameterKind parameterKind; |
| 8648 |
| 8649 /** |
| 8650 * The offset to the beginning of the default value range for this element. |
| 8651 */ |
| 8652 int _defaultValueRangeOffset = 0; |
| 8653 |
| 8654 /** |
| 8655 * The length of the default value range for this element, or `-1` if this ele
ment does not |
| 8656 * have a default value. |
| 8657 */ |
| 8658 int _defaultValueRangeLength = -1; |
| 8659 |
| 8660 /** |
| 8661 * The offset to the beginning of the visible range for this element. |
| 8662 */ |
| 8663 int _visibleRangeOffset = 0; |
| 8664 |
| 8665 /** |
| 8666 * The length of the visible range for this element, or `-1` if this element d
oes not have a |
| 8667 * visible range. |
| 8668 */ |
| 8669 int _visibleRangeLength = -1; |
| 8670 |
| 8671 /** |
| 8672 * An empty array of field elements. |
| 8673 */ |
| 8674 static List<ParameterElement> EMPTY_ARRAY = new List<ParameterElement>(0); |
| 8675 |
| 8676 /** |
| 8677 * Initialize a newly created parameter element to have the given name. |
| 8678 * |
| 8679 * @param name the name of this element |
| 8680 */ |
| 8681 ParameterElementImpl.con1(Identifier name) : super.forNode(name); |
| 8682 |
| 8683 /** |
| 8684 * Initialize a newly created parameter element to have the given name. |
| 8685 * |
| 8686 * @param name the name of this element |
| 8687 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 8688 * declaration of this element |
| 8689 */ |
| 8690 ParameterElementImpl.con2(String name, int nameOffset) : super(name, nameOffse
t); |
| 8691 |
| 8692 @override |
| 8693 accept(ElementVisitor visitor) => visitor.visitParameterElement(this); |
| 8694 |
| 8695 @override |
| 8696 SourceRange get defaultValueRange { |
| 8697 if (_defaultValueRangeLength < 0) { |
| 8698 return null; |
| 8699 } |
| 8700 return new SourceRange(_defaultValueRangeOffset, _defaultValueRangeLength); |
| 8701 } |
| 8702 |
| 8703 @override |
| 8704 ElementKind get kind => ElementKind.PARAMETER; |
| 8705 |
| 8706 @override |
| 8707 List<ParameterElement> get parameters => _parameters; |
| 8708 |
| 8709 @override |
| 8710 SourceRange get visibleRange { |
| 8711 if (_visibleRangeLength < 0) { |
| 8712 return null; |
| 8713 } |
| 8714 return new SourceRange(_visibleRangeOffset, _visibleRangeLength); |
| 8715 } |
| 8716 |
| 8717 @override |
| 8718 bool get isInitializingFormal => false; |
| 8719 |
| 8720 @override |
| 8721 bool get isPotentiallyMutatedInClosure => _potentiallyMutatedInClosure; |
| 8722 |
| 8723 @override |
| 8724 bool get isPotentiallyMutatedInScope => _potentiallyMutatedInScope; |
| 8725 |
| 8726 /** |
| 8727 * Specifies that this variable is potentially mutated somewhere in closure. |
| 8728 */ |
| 8729 void markPotentiallyMutatedInClosure() { |
| 8730 _potentiallyMutatedInClosure = true; |
| 8731 } |
| 8732 |
| 8733 /** |
| 8734 * Specifies that this variable is potentially mutated somewhere in its scope. |
| 8735 */ |
| 8736 void markPotentiallyMutatedInScope() { |
| 8737 _potentiallyMutatedInScope = true; |
| 8738 } |
| 8739 |
| 8740 /** |
| 8741 * Set the range of the default value for this parameter to the range starting
at the given offset |
| 8742 * with the given length. |
| 8743 * |
| 8744 * @param offset the offset to the beginning of the default value range for th
is element |
| 8745 * @param length the length of the default value range for this element, or `-
1` if this |
| 8746 * element does not have a default value |
| 8747 */ |
| 8748 void setDefaultValueRange(int offset, int length) { |
| 8749 _defaultValueRangeOffset = offset; |
| 8750 _defaultValueRangeLength = length; |
| 8751 } |
| 8752 |
| 8753 /** |
| 8754 * Set the parameters defined by this executable element to the given paramete
rs. |
| 8755 * |
| 8756 * @param parameters the parameters defined by this executable element |
| 8757 */ |
| 8758 void set parameters(List<ParameterElement> parameters) { |
| 8759 for (ParameterElement parameter in parameters) { |
| 8760 (parameter as ParameterElementImpl).enclosingElement = this; |
| 8761 } |
| 8762 this._parameters = parameters; |
| 8763 } |
| 8764 |
| 8765 /** |
| 8766 * Set the visible range for this element to the range starting at the given o
ffset with the given |
| 8767 * length. |
| 8768 * |
| 8769 * @param offset the offset to the beginning of the visible range for this ele
ment |
| 8770 * @param length the length of the visible range for this element, or `-1` if
this element |
| 8771 * does not have a visible range |
| 8772 */ |
| 8773 void setVisibleRange(int offset, int length) { |
| 8774 _visibleRangeOffset = offset; |
| 8775 _visibleRangeLength = length; |
| 8776 } |
| 8777 |
| 8778 @override |
| 8779 void visitChildren(ElementVisitor visitor) { |
| 8780 super.visitChildren(visitor); |
| 8781 safelyVisitChildren(_parameters, visitor); |
| 8782 } |
| 8783 |
| 8784 @override |
| 8785 void appendTo(JavaStringBuilder builder) { |
| 8786 String left = ""; |
| 8787 String right = ""; |
| 8788 while (true) { |
| 8789 if (parameterKind == ParameterKind.NAMED) { |
| 8790 left = "{"; |
| 8791 right = "}"; |
| 8792 } else if (parameterKind == ParameterKind.POSITIONAL) { |
| 8793 left = "["; |
| 8794 right = "]"; |
| 8795 } else if (parameterKind == ParameterKind.REQUIRED) { |
| 8796 } |
| 8797 break; |
| 8798 } |
| 8799 builder.append(left); |
| 8800 appendToWithoutDelimiters(builder); |
| 8801 builder.append(right); |
| 8802 } |
| 8803 |
| 8804 /** |
| 8805 * Append the type and name of this parameter to the given builder. |
| 8806 * |
| 8807 * @param builder the builder to which the type and name are to be appended |
| 8808 */ |
| 8809 void appendToWithoutDelimiters(JavaStringBuilder builder) { |
| 8810 builder.append(type); |
| 8811 builder.append(" "); |
| 8812 builder.append(displayName); |
| 8813 } |
| 8814 } |
| 8815 |
| 8054 /** | 8816 /** |
| 8055 * Instances of the class `ParameterMember` represent a parameter element define
d in a | 8817 * Instances of the class `ParameterMember` represent a parameter element define
d in a |
| 8056 * parameterized type where the values of the type parameters are known. | 8818 * parameterized type where the values of the type parameters are known. |
| 8057 */ | 8819 */ |
| 8058 class ParameterMember extends VariableMember implements ParameterElement { | 8820 class ParameterMember extends VariableMember implements ParameterElement { |
| 8059 /** | 8821 /** |
| 8060 * If the given parameter's type is different when any type parameters from th
e defining type's | 8822 * If the given parameter's type is different when any type parameters from th
e defining type's |
| 8061 * declaration are replaced with the actual type arguments from the defining t
ype, create a | 8823 * declaration are replaced with the actual type arguments from the defining t
ype, create a |
| 8062 * parameter member representing the given parameter. Return the member that w
as created, or the | 8824 * parameter member representing the given parameter. Return the member that w
as created, or the |
| 8063 * base parameter if no member was created. | 8825 * base parameter if no member was created. |
| (...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 8177 } | 8939 } |
| 8178 | 8940 |
| 8179 @override | 8941 @override |
| 8180 void visitChildren(ElementVisitor visitor) { | 8942 void visitChildren(ElementVisitor visitor) { |
| 8181 super.visitChildren(visitor); | 8943 super.visitChildren(visitor); |
| 8182 safelyVisitChildren(parameters, visitor); | 8944 safelyVisitChildren(parameters, visitor); |
| 8183 } | 8945 } |
| 8184 } | 8946 } |
| 8185 | 8947 |
| 8186 /** | 8948 /** |
| 8187 * Instances of the class `PropertyAccessorMember` represent a property accessor
element | 8949 * The interface `ParameterizedType` defines the behavior common to objects repr
esenting a |
| 8188 * defined in a parameterized type where the values of the type parameters are k
nown. | 8950 * type with type parameters, such as a class or function type alias. |
| 8189 */ | 8951 */ |
| 8190 class PropertyAccessorMember extends ExecutableMember implements PropertyAccesso
rElement { | 8952 abstract class ParameterizedType implements DartType { |
| 8191 /** | 8953 /** |
| 8192 * If the given property accessor's type is different when any type parameters
from the defining | 8954 * Return an array containing the actual types of the type arguments. If this
type's element does |
| 8193 * type's declaration are replaced with the actual type arguments from the def
ining type, create a | 8955 * not have type parameters, then the array should be empty (although it is po
ssible for type |
| 8194 * property accessor member representing the given property accessor. Return t
he member that was | 8956 * arguments to be erroneously declared). If the element has type parameters a
nd the actual type |
| 8195 * created, or the base accessor if no member was created. | 8957 * does not explicitly include argument values, then the type "dynamic" will b
e automatically |
| 8958 * provided. |
| 8196 * | 8959 * |
| 8197 * @param baseAccessor the base property accessor for which a member might be
created | 8960 * @return the actual types of the type arguments |
| 8198 * @param definingType the type defining the parameters and arguments to be us
ed in the | |
| 8199 * substitution | |
| 8200 * @return the property accessor element that will return the correctly substi
tuted types | |
| 8201 */ | 8961 */ |
| 8202 static PropertyAccessorElement from(PropertyAccessorElement baseAccessor, Inte
rfaceType definingType) { | 8962 List<DartType> get typeArguments; |
| 8203 if (baseAccessor == null || definingType.typeArguments.length == 0) { | |
| 8204 return baseAccessor; | |
| 8205 } | |
| 8206 FunctionType baseType = baseAccessor.type; | |
| 8207 List<DartType> argumentTypes = definingType.typeArguments; | |
| 8208 List<DartType> parameterTypes = definingType.element.type.typeArguments; | |
| 8209 FunctionType substitutedType = baseType.substitute2(argumentTypes, parameter
Types); | |
| 8210 if (baseType == substitutedType) { | |
| 8211 return baseAccessor; | |
| 8212 } | |
| 8213 // TODO(brianwilkerson) Consider caching the substituted type in the instanc
e. It would use more | |
| 8214 // memory but speed up some operations. We need to see how often the type is
being re-computed. | |
| 8215 return new PropertyAccessorMember(baseAccessor, definingType); | |
| 8216 } | |
| 8217 | 8963 |
| 8218 /** | 8964 /** |
| 8219 * Initialize a newly created element to represent a property accessor of the
given parameterized | 8965 * Return an array containing all of the type parameters declared for this typ
e. |
| 8220 * type. | |
| 8221 * | 8966 * |
| 8222 * @param baseElement the element on which the parameterized element was creat
ed | 8967 * @return the type parameters declared for this type |
| 8223 * @param definingType the type in which the element is defined | |
| 8224 */ | 8968 */ |
| 8225 PropertyAccessorMember(PropertyAccessorElement baseElement, InterfaceType defi
ningType) : super(baseElement, definingType); | 8969 List<TypeParameterElement> get typeParameters; |
| 8226 | |
| 8227 @override | |
| 8228 accept(ElementVisitor visitor) => visitor.visitPropertyAccessorElement(this); | |
| 8229 | |
| 8230 @override | |
| 8231 PropertyAccessorElement get baseElement => super.baseElement as PropertyAccess
orElement; | |
| 8232 | |
| 8233 @override | |
| 8234 PropertyAccessorElement get correspondingGetter => from(baseElement.correspond
ingGetter, definingType); | |
| 8235 | |
| 8236 @override | |
| 8237 PropertyAccessorElement get correspondingSetter => from(baseElement.correspond
ingSetter, definingType); | |
| 8238 | |
| 8239 @override | |
| 8240 Element get enclosingElement => baseElement.enclosingElement; | |
| 8241 | |
| 8242 @override | |
| 8243 PropertyInducingElement get variable { | |
| 8244 PropertyInducingElement variable = baseElement.variable; | |
| 8245 if (variable is FieldElement) { | |
| 8246 return FieldMember.from(variable, definingType); | |
| 8247 } | |
| 8248 return variable; | |
| 8249 } | |
| 8250 | |
| 8251 @override | |
| 8252 bool get isAbstract => baseElement.isAbstract; | |
| 8253 | |
| 8254 @override | |
| 8255 bool get isGetter => baseElement.isGetter; | |
| 8256 | |
| 8257 @override | |
| 8258 bool get isSetter => baseElement.isSetter; | |
| 8259 | |
| 8260 @override | |
| 8261 String toString() { | |
| 8262 PropertyAccessorElement baseElement = this.baseElement; | |
| 8263 List<ParameterElement> parameters = this.parameters; | |
| 8264 FunctionType type = this.type; | |
| 8265 JavaStringBuilder builder = new JavaStringBuilder(); | |
| 8266 if (isGetter) { | |
| 8267 builder.append("get "); | |
| 8268 } else { | |
| 8269 builder.append("set "); | |
| 8270 } | |
| 8271 builder.append(baseElement.enclosingElement.displayName); | |
| 8272 builder.append("."); | |
| 8273 builder.append(baseElement.displayName); | |
| 8274 builder.append("("); | |
| 8275 int parameterCount = parameters.length; | |
| 8276 for (int i = 0; i < parameterCount; i++) { | |
| 8277 if (i > 0) { | |
| 8278 builder.append(", "); | |
| 8279 } | |
| 8280 builder.append(parameters[i]).toString(); | |
| 8281 } | |
| 8282 builder.append(")"); | |
| 8283 if (type != null) { | |
| 8284 builder.append(Element.RIGHT_ARROW); | |
| 8285 builder.append(type.returnType); | |
| 8286 } | |
| 8287 return builder.toString(); | |
| 8288 } | |
| 8289 | |
| 8290 @override | |
| 8291 InterfaceType get definingType => super.definingType as InterfaceType; | |
| 8292 } | 8970 } |
| 8293 | 8971 |
| 8294 /** | 8972 /** |
| 8295 * The abstract class `VariableMember` defines the behavior common to members th
at represent a | 8973 * The interface `PolymerAttributeElement` defines an attribute in |
| 8296 * variable element defined in a parameterized type where the values of the type
parameters are | 8974 * [PolymerTagHtmlElement]. |
| 8297 * known. | 8975 * |
| 8976 * <pre> |
| 8977 * <polymer-element name="my-example" attributes='attrA attrB'> |
| 8978 * </polymer-element> |
| 8979 * </pre> |
| 8298 */ | 8980 */ |
| 8299 abstract class VariableMember extends Member implements VariableElement { | 8981 abstract class PolymerAttributeElement implements PolymerElement { |
| 8300 /** | 8982 /** |
| 8301 * Initialize a newly created element to represent an executable element of th
e given | 8983 * An empty array of Polymer custom tag attributes. |
| 8302 * parameterized type. | |
| 8303 * | |
| 8304 * @param baseElement the element on which the parameterized element was creat
ed | |
| 8305 * @param definingType the type in which the element is defined | |
| 8306 */ | 8984 */ |
| 8307 VariableMember(VariableElement baseElement, ParameterizedType definingType) :
super(baseElement, definingType); | 8985 static final List<PolymerAttributeElement> EMPTY_ARRAY = new List<PolymerAttri
buteElement>(0); |
| 8308 | 8986 |
| 8309 @override | 8987 /** |
| 8310 VariableElement get baseElement => super.baseElement as VariableElement; | 8988 * Return the [FieldElement] associated with this attribute. Maybe `null` if |
| 8311 | 8989 * [PolymerTagDartElement] does not have a field associated with it. |
| 8312 @override | 8990 */ |
| 8313 FunctionElement get initializer { | 8991 FieldElement get field; |
| 8314 // | |
| 8315 // Elements within this element should have type parameters substituted, jus
t like this element. | |
| 8316 // | |
| 8317 throw new UnsupportedOperationException(); | |
| 8318 } | |
| 8319 | |
| 8320 @override | |
| 8321 VariableDeclaration get node => baseElement.node; | |
| 8322 | |
| 8323 @override | |
| 8324 DartType get type => substituteFor(baseElement.type); | |
| 8325 | |
| 8326 @override | |
| 8327 bool get isConst => baseElement.isConst; | |
| 8328 | |
| 8329 @override | |
| 8330 bool get isFinal => baseElement.isFinal; | |
| 8331 | |
| 8332 @override | |
| 8333 void visitChildren(ElementVisitor visitor) { | |
| 8334 // TODO(brianwilkerson) We need to finish implementing the accessors used be
low so that we can | |
| 8335 // safely invoke them. | |
| 8336 super.visitChildren(visitor); | |
| 8337 safelyVisitChild(baseElement.initializer, visitor); | |
| 8338 } | |
| 8339 } | 8992 } |
| 8340 | 8993 |
| 8341 /** | 8994 /** |
| 8342 * Implementation of `PolymerAttributeElement`. | 8995 * Implementation of `PolymerAttributeElement`. |
| 8343 */ | 8996 */ |
| 8344 class PolymerAttributeElementImpl extends PolymerElementImpl implements PolymerA
ttributeElement { | 8997 class PolymerAttributeElementImpl extends PolymerElementImpl implements PolymerA
ttributeElement { |
| 8345 /** | 8998 /** |
| 8346 * The [FieldElement] associated with this attribute. | 8999 * The [FieldElement] associated with this attribute. |
| 8347 */ | 9000 */ |
| 8348 FieldElement field; | 9001 FieldElement field; |
| 8349 | 9002 |
| 8350 /** | 9003 /** |
| 8351 * Initialize a newly created Polymer attribute to have the given name. | 9004 * Initialize a newly created Polymer attribute to have the given name. |
| 8352 * | 9005 * |
| 8353 * @param name the name of this element | 9006 * @param name the name of this element |
| 8354 * @param nameOffset the offset of the name of this element in the file that c
ontains the | 9007 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 8355 * declaration of this element | 9008 * declaration of this element |
| 8356 */ | 9009 */ |
| 8357 PolymerAttributeElementImpl(String name, int nameOffset) : super(name, nameOff
set); | 9010 PolymerAttributeElementImpl(String name, int nameOffset) : super(name, nameOff
set); |
| 8358 | 9011 |
| 8359 @override | 9012 @override |
| 8360 accept(ElementVisitor visitor) => visitor.visitPolymerAttributeElement(this); | 9013 accept(ElementVisitor visitor) => visitor.visitPolymerAttributeElement(this); |
| 8361 | 9014 |
| 8362 @override | 9015 @override |
| 8363 ElementKind get kind => ElementKind.POLYMER_ATTRIBUTE; | 9016 ElementKind get kind => ElementKind.POLYMER_ATTRIBUTE; |
| 8364 } | 9017 } |
| 8365 | 9018 |
| 8366 /** | 9019 /** |
| 9020 * The interface `PolymerElement` defines the behavior of objects representing i
nformation |
| 9021 * about a Polymer specific element. |
| 9022 */ |
| 9023 abstract class PolymerElement implements ToolkitObjectElement { |
| 9024 /** |
| 9025 * An empty array of Polymer elements. |
| 9026 */ |
| 9027 static final List<PolymerElement> EMPTY_ARRAY = new List<PolymerElement>(0); |
| 9028 } |
| 9029 |
| 9030 /** |
| 8367 * Implementation of `PolymerElement`. | 9031 * Implementation of `PolymerElement`. |
| 8368 */ | 9032 */ |
| 8369 abstract class PolymerElementImpl extends ToolkitObjectElementImpl implements Po
lymerElement { | 9033 abstract class PolymerElementImpl extends ToolkitObjectElementImpl implements Po
lymerElement { |
| 8370 /** | 9034 /** |
| 8371 * Initialize a newly created Polymer element to have the given name. | 9035 * Initialize a newly created Polymer element to have the given name. |
| 8372 * | 9036 * |
| 8373 * @param name the name of this element | 9037 * @param name the name of this element |
| 8374 * @param nameOffset the offset of the name of this element in the file that c
ontains the | 9038 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 8375 * declaration of this element | 9039 * declaration of this element |
| 8376 */ | 9040 */ |
| 8377 PolymerElementImpl(String name, int nameOffset) : super(name, nameOffset); | 9041 PolymerElementImpl(String name, int nameOffset) : super(name, nameOffset); |
| 8378 } | 9042 } |
| 8379 | 9043 |
| 8380 /** | 9044 /** |
| 9045 * The interface `PolymerTagDartElement` defines a Polymer custom tag in Dart. |
| 9046 * |
| 9047 * <pre> |
| 9048 * @CustomTag('my-example') |
| 9049 * </pre> |
| 9050 */ |
| 9051 abstract class PolymerTagDartElement implements PolymerElement { |
| 9052 /** |
| 9053 * Return the [ClassElement] that is associated with this Polymer custom tag.
Not |
| 9054 * `null`, because [PolymerTagDartElement]s are created for [ClassElement]s |
| 9055 * marked with the `@CustomTag` annotation. |
| 9056 */ |
| 9057 ClassElement get classElement; |
| 9058 |
| 9059 /** |
| 9060 * Return the [PolymerTagHtmlElement] part of this Polymer custom tag. Maybe `
null` if |
| 9061 * it has not been resolved yet or there are no corresponding Dart part define
d. |
| 9062 */ |
| 9063 PolymerTagHtmlElement get htmlElement; |
| 9064 } |
| 9065 |
| 9066 /** |
| 8381 * Implementation of `PolymerTagDartElement`. | 9067 * Implementation of `PolymerTagDartElement`. |
| 8382 */ | 9068 */ |
| 8383 class PolymerTagDartElementImpl extends PolymerElementImpl implements PolymerTag
DartElement { | 9069 class PolymerTagDartElementImpl extends PolymerElementImpl implements PolymerTag
DartElement { |
| 8384 /** | 9070 /** |
| 8385 * The [ClassElement] that is associated with this Polymer custom tag. | 9071 * The [ClassElement] that is associated with this Polymer custom tag. |
| 8386 */ | 9072 */ |
| 8387 final ClassElement classElement; | 9073 final ClassElement classElement; |
| 8388 | 9074 |
| 8389 /** | 9075 /** |
| 8390 * The [PolymerTagHtmlElement] part of this Polymer custom tag. Maybe `null` i
f it has | 9076 * The [PolymerTagHtmlElement] part of this Polymer custom tag. Maybe `null` i
f it has |
| (...skipping 11 matching lines...) Expand all Loading... |
| 8402 PolymerTagDartElementImpl(String name, int nameOffset, this.classElement) : su
per(name, nameOffset); | 9088 PolymerTagDartElementImpl(String name, int nameOffset, this.classElement) : su
per(name, nameOffset); |
| 8403 | 9089 |
| 8404 @override | 9090 @override |
| 8405 accept(ElementVisitor visitor) => visitor.visitPolymerTagDartElement(this); | 9091 accept(ElementVisitor visitor) => visitor.visitPolymerTagDartElement(this); |
| 8406 | 9092 |
| 8407 @override | 9093 @override |
| 8408 ElementKind get kind => ElementKind.POLYMER_TAG_DART; | 9094 ElementKind get kind => ElementKind.POLYMER_TAG_DART; |
| 8409 } | 9095 } |
| 8410 | 9096 |
| 8411 /** | 9097 /** |
| 9098 * The interface `PolymerTagHtmlElement` defines a Polymer custom tag in HTML. |
| 9099 * |
| 9100 * <pre> |
| 9101 * <polymer-element name="my-example" attributes='attrA attrB'> |
| 9102 * </polymer-element> |
| 9103 * </pre> |
| 9104 */ |
| 9105 abstract class PolymerTagHtmlElement implements PolymerElement { |
| 9106 /** |
| 9107 * An empty array of [PolymerTagHtmlElement]s. |
| 9108 */ |
| 9109 static final List<PolymerTagHtmlElement> EMPTY_ARRAY = new List<PolymerTagHtml
Element>(0); |
| 9110 |
| 9111 /** |
| 9112 * Return an array containing all of the attributes declared by this tag. |
| 9113 */ |
| 9114 List<PolymerAttributeElement> get attributes; |
| 9115 |
| 9116 /** |
| 9117 * Return the [PolymerTagDartElement] part on this Polymer custom tag. Maybe `
null` if |
| 9118 * it has not been resolved yet or there are no corresponding Dart part define
d. |
| 9119 */ |
| 9120 PolymerTagDartElement get dartElement; |
| 9121 } |
| 9122 |
| 9123 /** |
| 8412 * Implementation of `PolymerTagHtmlElement`. | 9124 * Implementation of `PolymerTagHtmlElement`. |
| 8413 */ | 9125 */ |
| 8414 class PolymerTagHtmlElementImpl extends PolymerElementImpl implements PolymerTag
HtmlElement { | 9126 class PolymerTagHtmlElementImpl extends PolymerElementImpl implements PolymerTag
HtmlElement { |
| 8415 /** | 9127 /** |
| 8416 * The [PolymerTagDartElement] part of this Polymer custom tag. Maybe `null` i
f it has | 9128 * The [PolymerTagDartElement] part of this Polymer custom tag. Maybe `null` i
f it has |
| 8417 * not been resolved yet or there are no corresponding Dart part defined. | 9129 * not been resolved yet or there are no corresponding Dart part defined. |
| 8418 */ | 9130 */ |
| 8419 PolymerTagDartElement dartElement; | 9131 PolymerTagDartElement dartElement; |
| 8420 | 9132 |
| 8421 /** | 9133 /** |
| (...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 8454 } | 9166 } |
| 8455 | 9167 |
| 8456 @override | 9168 @override |
| 8457 void visitChildren(ElementVisitor visitor) { | 9169 void visitChildren(ElementVisitor visitor) { |
| 8458 safelyVisitChildren(_attributes, visitor); | 9170 safelyVisitChildren(_attributes, visitor); |
| 8459 super.visitChildren(visitor); | 9171 super.visitChildren(visitor); |
| 8460 } | 9172 } |
| 8461 } | 9173 } |
| 8462 | 9174 |
| 8463 /** | 9175 /** |
| 8464 * The unique instance of the class `BottomTypeImpl` implements the type `bottom
`. | 9176 * The interface `PrefixElement` defines the behavior common to elements that re
present a |
| 8465 */ | 9177 * prefix used to import one or more libraries into another library. |
| 8466 class BottomTypeImpl extends TypeImpl { | 9178 */ |
| 8467 /** | 9179 abstract class PrefixElement implements Element { |
| 8468 * The unique instance of this class. | 9180 /** |
| 8469 */ | 9181 * Return the library into which other libraries are imported using this prefi
x. |
| 8470 static BottomTypeImpl _INSTANCE = new BottomTypeImpl(); | 9182 * |
| 8471 | 9183 * @return the library into which other libraries are imported using this pref
ix |
| 8472 /** | 9184 */ |
| 8473 * Return the unique instance of this class. | 9185 @override |
| 8474 * | 9186 LibraryElement get enclosingElement; |
| 8475 * @return the unique instance of this class | 9187 |
| 8476 */ | 9188 /** |
| 8477 static BottomTypeImpl get instance => _INSTANCE; | 9189 * Return an array containing all of the libraries that are imported using thi
s prefix. |
| 8478 | 9190 * |
| 8479 /** | 9191 * @return the libraries that are imported using this prefix |
| 8480 * Prevent the creation of instances of this class. | 9192 */ |
| 8481 */ | 9193 List<LibraryElement> get importedLibraries; |
| 8482 BottomTypeImpl() : super(null, "<bottom>"); | 9194 } |
| 8483 | 9195 |
| 8484 @override | 9196 /** |
| 8485 bool operator ==(Object object) => identical(object, this); | 9197 * Instances of the class `PrefixElementImpl` implement a `PrefixElement`. |
| 8486 | 9198 */ |
| 8487 @override | 9199 class PrefixElementImpl extends ElementImpl implements PrefixElement { |
| 8488 int get hashCode => 0; | 9200 /** |
| 8489 | 9201 * An array containing all of the libraries that are imported using this prefi
x. |
| 8490 @override | 9202 */ |
| 8491 bool get isBottom => true; | 9203 List<LibraryElement> _importedLibraries = LibraryElementImpl.EMPTY_ARRAY; |
| 8492 | 9204 |
| 8493 @override | 9205 /** |
| 8494 bool isSupertypeOf(DartType type) => false; | 9206 * An empty array of prefix elements. |
| 8495 | 9207 */ |
| 8496 @override | 9208 static List<PrefixElement> EMPTY_ARRAY = new List<PrefixElement>(0); |
| 8497 BottomTypeImpl substitute2(List<DartType> argumentTypes, List<DartType> parame
terTypes) => this; | 9209 |
| 8498 | 9210 /** |
| 8499 @override | 9211 * Initialize a newly created prefix element to have the given name. |
| 8500 bool internalEquals(Object object, Set<ElementPair> visitedElementPairs) => id
entical(object, this); | 9212 * |
| 8501 | 9213 * @param name the name of this element |
| 8502 @override | 9214 */ |
| 8503 bool internalIsMoreSpecificThan(DartType type, bool withDynamic, Set<TypeImpl_
TypePair> visitedTypePairs) => true; | 9215 PrefixElementImpl(Identifier name) : super.forNode(name); |
| 8504 | 9216 |
| 8505 @override | 9217 @override |
| 8506 bool internalIsSubtypeOf(DartType type, Set<TypeImpl_TypePair> visitedTypePair
s) => true; | 9218 accept(ElementVisitor visitor) => visitor.visitPrefixElement(this); |
| 8507 } | 9219 |
| 8508 | 9220 @override |
| 8509 /** | 9221 LibraryElement get enclosingElement => super.enclosingElement as LibraryElemen
t; |
| 8510 * The unique instance of the class `DynamicTypeImpl` implements the type `dynam
ic`. | 9222 |
| 8511 */ | 9223 @override |
| 8512 class DynamicTypeImpl extends TypeImpl { | 9224 List<LibraryElement> get importedLibraries => _importedLibraries; |
| 8513 /** | 9225 |
| 8514 * The unique instance of this class. | 9226 @override |
| 8515 */ | 9227 ElementKind get kind => ElementKind.PREFIX; |
| 8516 static DynamicTypeImpl _INSTANCE = new DynamicTypeImpl(); | 9228 |
| 8517 | 9229 /** |
| 8518 /** | 9230 * Set the libraries that are imported using this prefix to the given librarie
s. |
| 8519 * Return the unique instance of this class. | 9231 * |
| 8520 * | 9232 * @param importedLibraries the libraries that are imported using this prefix |
| 8521 * @return the unique instance of this class | 9233 */ |
| 8522 */ | 9234 void set importedLibraries(List<LibraryElement> importedLibraries) { |
| 8523 static DynamicTypeImpl get instance => _INSTANCE; | 9235 for (LibraryElement library in importedLibraries) { |
| 8524 | 9236 (library as LibraryElementImpl).enclosingElement = this; |
| 8525 /** | 9237 } |
| 8526 * Prevent the creation of instances of this class. | 9238 this._importedLibraries = importedLibraries; |
| 8527 */ | 9239 } |
| 8528 DynamicTypeImpl() : super(new DynamicElementImpl(), Keyword.DYNAMIC.syntax) { | 9240 |
| 8529 (element as DynamicElementImpl).type = this; | 9241 @override |
| 8530 } | 9242 void appendTo(JavaStringBuilder builder) { |
| 8531 | 9243 builder.append("as "); |
| 8532 @override | 9244 super.appendTo(builder); |
| 8533 bool operator ==(Object object) => identical(object, this); | 9245 } |
| 8534 | 9246 |
| 8535 @override | 9247 @override |
| 8536 int get hashCode => 1; | 9248 String get identifier => "_${super.identifier}"; |
| 8537 | 9249 } |
| 8538 @override | 9250 |
| 8539 bool get isDynamic => true; | 9251 /** |
| 8540 | 9252 * The interface `PropertyAccessorElement` defines the behavior of elements repr
esenting a |
| 8541 @override | 9253 * getter or a setter. Note that explicitly defined property accessors implicitl
y define a synthetic |
| 8542 bool isSupertypeOf(DartType type) => true; | 9254 * field. Symmetrically, synthetic accessors are implicitly created for explicit
ly defined fields. |
| 8543 | 9255 * The following rules apply: |
| 8544 @override | 9256 * * Every explicit field is represented by a non-synthetic [FieldElement]. |
| 8545 DartType substitute2(List<DartType> argumentTypes, List<DartType> parameterTyp
es) { | 9257 * * Every explicit field induces a getter and possibly a setter, both of which
are represented by |
| 8546 int length = parameterTypes.length; | 9258 * synthetic [PropertyAccessorElement]s. |
| 8547 for (int i = 0; i < length; i++) { | 9259 * * Every explicit getter or setter is represented by a non-synthetic |
| 8548 if (parameterTypes[i] == this) { | 9260 * [PropertyAccessorElement]. |
| 8549 return argumentTypes[i]; | 9261 * * Every explicit getter or setter (or pair thereof if they have the same name
) induces a field |
| 9262 * that is represented by a synthetic [FieldElement]. |
| 9263 */ |
| 9264 abstract class PropertyAccessorElement implements ExecutableElement { |
| 9265 /** |
| 9266 * Return the accessor representing the getter that corresponds to (has the sa
me name as) this |
| 9267 * setter, or `null` if this accessor is not a setter or if there is no corres
ponding |
| 9268 * getter. |
| 9269 * |
| 9270 * @return the getter that corresponds to this setter |
| 9271 */ |
| 9272 PropertyAccessorElement get correspondingGetter; |
| 9273 |
| 9274 /** |
| 9275 * Return the accessor representing the setter that corresponds to (has the sa
me name as) this |
| 9276 * getter, or `null` if this accessor is not a getter or if there is no corres
ponding |
| 9277 * setter. |
| 9278 * |
| 9279 * @return the setter that corresponds to this getter |
| 9280 */ |
| 9281 PropertyAccessorElement get correspondingSetter; |
| 9282 |
| 9283 /** |
| 9284 * Return the field or top-level variable associated with this accessor. If th
is accessor was |
| 9285 * explicitly defined (is not synthetic) then the variable associated with it
will be synthetic. |
| 9286 * |
| 9287 * @return the variable associated with this accessor |
| 9288 */ |
| 9289 PropertyInducingElement get variable; |
| 9290 |
| 9291 /** |
| 9292 * Return `true` if this accessor is abstract. Accessors are abstract if they
are not |
| 9293 * external and have no body. |
| 9294 * |
| 9295 * @return `true` if this accessor is abstract |
| 9296 */ |
| 9297 bool get isAbstract; |
| 9298 |
| 9299 /** |
| 9300 * Return `true` if this accessor represents a getter. |
| 9301 * |
| 9302 * @return `true` if this accessor represents a getter |
| 9303 */ |
| 9304 bool get isGetter; |
| 9305 |
| 9306 /** |
| 9307 * Return `true` if this accessor represents a setter. |
| 9308 * |
| 9309 * @return `true` if this accessor represents a setter |
| 9310 */ |
| 9311 bool get isSetter; |
| 9312 } |
| 9313 |
| 9314 /** |
| 9315 * Instances of the class `PropertyAccessorElementImpl` implement a |
| 9316 * `PropertyAccessorElement`. |
| 9317 */ |
| 9318 class PropertyAccessorElementImpl extends ExecutableElementImpl implements Prope
rtyAccessorElement { |
| 9319 /** |
| 9320 * The variable associated with this accessor. |
| 9321 */ |
| 9322 PropertyInducingElement variable; |
| 9323 |
| 9324 /** |
| 9325 * An empty array of property accessor elements. |
| 9326 */ |
| 9327 static List<PropertyAccessorElement> EMPTY_ARRAY = new List<PropertyAccessorEl
ement>(0); |
| 9328 |
| 9329 /** |
| 9330 * Initialize a newly created property accessor element to have the given name
. |
| 9331 * |
| 9332 * @param name the name of this element |
| 9333 */ |
| 9334 PropertyAccessorElementImpl.forNode(Identifier name) : super.forNode(name); |
| 9335 |
| 9336 /** |
| 9337 * Initialize a newly created synthetic property accessor element to be associ
ated with the given |
| 9338 * variable. |
| 9339 * |
| 9340 * @param variable the variable with which this access is associated |
| 9341 */ |
| 9342 PropertyAccessorElementImpl(PropertyInducingElementImpl variable) : super(vari
able.name, variable.nameOffset) { |
| 9343 this.variable = variable; |
| 9344 synthetic = true; |
| 9345 } |
| 9346 |
| 9347 @override |
| 9348 accept(ElementVisitor visitor) => visitor.visitPropertyAccessorElement(this); |
| 9349 |
| 9350 @override |
| 9351 bool operator ==(Object object) => super == object && isGetter == (object as P
ropertyAccessorElement).isGetter; |
| 9352 |
| 9353 @override |
| 9354 PropertyAccessorElement get correspondingGetter { |
| 9355 if (isGetter || variable == null) { |
| 9356 return null; |
| 9357 } |
| 9358 return variable.getter; |
| 9359 } |
| 9360 |
| 9361 @override |
| 9362 PropertyAccessorElement get correspondingSetter { |
| 9363 if (isSetter || variable == null) { |
| 9364 return null; |
| 9365 } |
| 9366 return variable.setter; |
| 9367 } |
| 9368 |
| 9369 @override |
| 9370 ElementKind get kind { |
| 9371 if (isGetter) { |
| 9372 return ElementKind.GETTER; |
| 9373 } |
| 9374 return ElementKind.SETTER; |
| 9375 } |
| 9376 |
| 9377 @override |
| 9378 String get name { |
| 9379 if (isSetter) { |
| 9380 return "${super.name}="; |
| 9381 } |
| 9382 return super.name; |
| 9383 } |
| 9384 |
| 9385 @override |
| 9386 AstNode get node { |
| 9387 if (isSynthetic) { |
| 9388 return null; |
| 9389 } |
| 9390 if (enclosingElement is ClassElement) { |
| 9391 return getNodeMatching((node) => node is MethodDeclaration); |
| 9392 } |
| 9393 if (enclosingElement is CompilationUnitElement) { |
| 9394 return getNodeMatching((node) => node is FunctionDeclaration); |
| 9395 } |
| 9396 return null; |
| 9397 } |
| 9398 |
| 9399 @override |
| 9400 int get hashCode => ObjectUtilities.combineHashCodes(super.hashCode, isGetter
? 1 : 2); |
| 9401 |
| 9402 @override |
| 9403 bool get isAbstract => hasModifier(Modifier.ABSTRACT); |
| 9404 |
| 9405 @override |
| 9406 bool get isGetter => hasModifier(Modifier.GETTER); |
| 9407 |
| 9408 @override |
| 9409 bool get isSetter => hasModifier(Modifier.SETTER); |
| 9410 |
| 9411 @override |
| 9412 bool get isStatic => hasModifier(Modifier.STATIC); |
| 9413 |
| 9414 /** |
| 9415 * Set whether this accessor is abstract to correspond to the given value. |
| 9416 * |
| 9417 * @param isAbstract `true` if the accessor is abstract |
| 9418 */ |
| 9419 void set abstract(bool isAbstract) { |
| 9420 setModifier(Modifier.ABSTRACT, isAbstract); |
| 9421 } |
| 9422 |
| 9423 /** |
| 9424 * Set whether this accessor is a getter to correspond to the given value. |
| 9425 * |
| 9426 * @param isGetter `true` if the accessor is a getter |
| 9427 */ |
| 9428 void set getter(bool isGetter) { |
| 9429 setModifier(Modifier.GETTER, isGetter); |
| 9430 } |
| 9431 |
| 9432 /** |
| 9433 * Set whether this accessor is a setter to correspond to the given value. |
| 9434 * |
| 9435 * @param isSetter `true` if the accessor is a setter |
| 9436 */ |
| 9437 void set setter(bool isSetter) { |
| 9438 setModifier(Modifier.SETTER, isSetter); |
| 9439 } |
| 9440 |
| 9441 /** |
| 9442 * Set whether this accessor is static to correspond to the given value. |
| 9443 * |
| 9444 * @param isStatic `true` if the accessor is static |
| 9445 */ |
| 9446 void set static(bool isStatic) { |
| 9447 setModifier(Modifier.STATIC, isStatic); |
| 9448 } |
| 9449 |
| 9450 @override |
| 9451 void appendTo(JavaStringBuilder builder) { |
| 9452 builder.append(isGetter ? "get " : "set "); |
| 9453 builder.append(variable.displayName); |
| 9454 super.appendTo(builder); |
| 9455 } |
| 9456 } |
| 9457 |
| 9458 /** |
| 9459 * Instances of the class `PropertyAccessorMember` represent a property accessor
element |
| 9460 * defined in a parameterized type where the values of the type parameters are k
nown. |
| 9461 */ |
| 9462 class PropertyAccessorMember extends ExecutableMember implements PropertyAccesso
rElement { |
| 9463 /** |
| 9464 * If the given property accessor's type is different when any type parameters
from the defining |
| 9465 * type's declaration are replaced with the actual type arguments from the def
ining type, create a |
| 9466 * property accessor member representing the given property accessor. Return t
he member that was |
| 9467 * created, or the base accessor if no member was created. |
| 9468 * |
| 9469 * @param baseAccessor the base property accessor for which a member might be
created |
| 9470 * @param definingType the type defining the parameters and arguments to be us
ed in the |
| 9471 * substitution |
| 9472 * @return the property accessor element that will return the correctly substi
tuted types |
| 9473 */ |
| 9474 static PropertyAccessorElement from(PropertyAccessorElement baseAccessor, Inte
rfaceType definingType) { |
| 9475 if (baseAccessor == null || definingType.typeArguments.length == 0) { |
| 9476 return baseAccessor; |
| 9477 } |
| 9478 FunctionType baseType = baseAccessor.type; |
| 9479 List<DartType> argumentTypes = definingType.typeArguments; |
| 9480 List<DartType> parameterTypes = definingType.element.type.typeArguments; |
| 9481 FunctionType substitutedType = baseType.substitute2(argumentTypes, parameter
Types); |
| 9482 if (baseType == substitutedType) { |
| 9483 return baseAccessor; |
| 9484 } |
| 9485 // TODO(brianwilkerson) Consider caching the substituted type in the instanc
e. It would use more |
| 9486 // memory but speed up some operations. We need to see how often the type is
being re-computed. |
| 9487 return new PropertyAccessorMember(baseAccessor, definingType); |
| 9488 } |
| 9489 |
| 9490 /** |
| 9491 * Initialize a newly created element to represent a property accessor of the
given parameterized |
| 9492 * type. |
| 9493 * |
| 9494 * @param baseElement the element on which the parameterized element was creat
ed |
| 9495 * @param definingType the type in which the element is defined |
| 9496 */ |
| 9497 PropertyAccessorMember(PropertyAccessorElement baseElement, InterfaceType defi
ningType) : super(baseElement, definingType); |
| 9498 |
| 9499 @override |
| 9500 accept(ElementVisitor visitor) => visitor.visitPropertyAccessorElement(this); |
| 9501 |
| 9502 @override |
| 9503 PropertyAccessorElement get baseElement => super.baseElement as PropertyAccess
orElement; |
| 9504 |
| 9505 @override |
| 9506 PropertyAccessorElement get correspondingGetter => from(baseElement.correspond
ingGetter, definingType); |
| 9507 |
| 9508 @override |
| 9509 PropertyAccessorElement get correspondingSetter => from(baseElement.correspond
ingSetter, definingType); |
| 9510 |
| 9511 @override |
| 9512 Element get enclosingElement => baseElement.enclosingElement; |
| 9513 |
| 9514 @override |
| 9515 PropertyInducingElement get variable { |
| 9516 PropertyInducingElement variable = baseElement.variable; |
| 9517 if (variable is FieldElement) { |
| 9518 return FieldMember.from(variable, definingType); |
| 9519 } |
| 9520 return variable; |
| 9521 } |
| 9522 |
| 9523 @override |
| 9524 bool get isAbstract => baseElement.isAbstract; |
| 9525 |
| 9526 @override |
| 9527 bool get isGetter => baseElement.isGetter; |
| 9528 |
| 9529 @override |
| 9530 bool get isSetter => baseElement.isSetter; |
| 9531 |
| 9532 @override |
| 9533 String toString() { |
| 9534 PropertyAccessorElement baseElement = this.baseElement; |
| 9535 List<ParameterElement> parameters = this.parameters; |
| 9536 FunctionType type = this.type; |
| 9537 JavaStringBuilder builder = new JavaStringBuilder(); |
| 9538 if (isGetter) { |
| 9539 builder.append("get "); |
| 9540 } else { |
| 9541 builder.append("set "); |
| 9542 } |
| 9543 builder.append(baseElement.enclosingElement.displayName); |
| 9544 builder.append("."); |
| 9545 builder.append(baseElement.displayName); |
| 9546 builder.append("("); |
| 9547 int parameterCount = parameters.length; |
| 9548 for (int i = 0; i < parameterCount; i++) { |
| 9549 if (i > 0) { |
| 9550 builder.append(", "); |
| 8550 } | 9551 } |
| 8551 } | 9552 builder.append(parameters[i]).toString(); |
| 8552 return this; | 9553 } |
| 8553 } | 9554 builder.append(")"); |
| 8554 | 9555 if (type != null) { |
| 8555 @override | 9556 builder.append(Element.RIGHT_ARROW); |
| 8556 bool internalEquals(Object object, Set<ElementPair> visitedElementPairs) => id
entical(object, this); | 9557 builder.append(type.returnType); |
| 8557 | 9558 } |
| 8558 @override | 9559 return builder.toString(); |
| 8559 bool internalIsMoreSpecificThan(DartType type, bool withDynamic, Set<TypeImpl_
TypePair> visitedTypePairs) { | 9560 } |
| 8560 // T is S | 9561 |
| 8561 if (identical(this, type)) { | 9562 @override |
| 8562 return true; | 9563 InterfaceType get definingType => super.definingType as InterfaceType; |
| 8563 } | 9564 } |
| 8564 // else | 9565 |
| 8565 return withDynamic; | 9566 /** |
| 8566 } | 9567 * The interface `PropertyInducingElement` defines the behavior of elements repr
esenting a |
| 8567 | 9568 * variable that has an associated getter and possibly a setter. Note that expli
citly defined |
| 8568 @override | 9569 * variables implicitly define a synthetic getter and that non-`final` explicitl
y defined |
| 8569 bool internalIsSubtypeOf(DartType type, Set<TypeImpl_TypePair> visitedTypePair
s) => true; | 9570 * variables implicitly define a synthetic setter. Symmetrically, synthetic fiel
ds are implicitly |
| 8570 } | 9571 * created for explicitly defined getters and setters. The following rules apply
: |
| 8571 | 9572 * * Every explicit variable is represented by a non-synthetic [PropertyInducing
Element]. |
| 8572 /** | 9573 * * Every explicit variable induces a getter and possibly a setter, both of whi
ch are represented |
| 8573 * Instances of the class `FunctionTypeImpl` defines the behavior common to obje
cts | 9574 * by synthetic [PropertyAccessorElement]s. |
| 8574 * representing the type of a function, method, constructor, getter, or setter. | 9575 * * Every explicit getter or setter is represented by a non-synthetic |
| 8575 */ | 9576 * [PropertyAccessorElement]. |
| 8576 class FunctionTypeImpl extends TypeImpl implements FunctionType { | 9577 * * Every explicit getter or setter (or pair thereof if they have the same name
) induces a |
| 8577 /** | 9578 * variable that is represented by a synthetic [PropertyInducingElement]. |
| 8578 * Return `true` if all of the name/type pairs in the first map are equal to t
he | 9579 */ |
| 8579 * corresponding name/type pairs in the second map. The maps are expected to i
terate over their | 9580 abstract class PropertyInducingElement implements VariableElement { |
| 8580 * entries in the same order in which those entries were added to the map. | 9581 /** |
| 8581 * | 9582 * Return the getter associated with this variable. If this variable was expli
citly defined (is |
| 8582 * @param firstTypes the first map of name/type pairs being compared | 9583 * not synthetic) then the getter associated with it will be synthetic. |
| 8583 * @param secondTypes the second map of name/type pairs being compared | 9584 * |
| 8584 * @param visitedElementPairs a set of visited element pairs | 9585 * @return the getter associated with this variable |
| 8585 * @return `true` if all of the name/type pairs in the first map are equal to
the | 9586 */ |
| 8586 * corresponding name/type pairs in the second map | 9587 PropertyAccessorElement get getter; |
| 8587 */ | 9588 |
| 8588 static bool _equals(Map<String, DartType> firstTypes, Map<String, DartType> se
condTypes, Set<ElementPair> visitedElementPairs) { | 9589 /** |
| 8589 if (secondTypes.length != firstTypes.length) { | 9590 * Return the setter associated with this variable, or `null` if the variable
is effectively |
| 8590 return false; | 9591 * `final` and therefore does not have a setter associated with it. (This can
happen either |
| 8591 } | 9592 * because the variable is explicitly defined as being `final` or because the
variable is |
| 8592 JavaIterator<MapEntry<String, DartType>> firstIterator = new JavaIterator(ge
tMapEntrySet(firstTypes)); | 9593 * induced by an explicit getter that does not have a corresponding setter.) I
f this variable was |
| 8593 JavaIterator<MapEntry<String, DartType>> secondIterator = new JavaIterator(g
etMapEntrySet(secondTypes)); | 9594 * explicitly defined (is not synthetic) then the setter associated with it wi
ll be synthetic. |
| 8594 while (firstIterator.hasNext) { | 9595 * |
| 8595 MapEntry<String, DartType> firstEntry = firstIterator.next(); | 9596 * @return the setter associated with this variable |
| 8596 MapEntry<String, DartType> secondEntry = secondIterator.next(); | 9597 */ |
| 8597 if (firstEntry.getKey() != secondEntry.getKey() || !(firstEntry.getValue()
as TypeImpl).internalEquals(secondEntry.getValue(), visitedElementPairs)) { | 9598 PropertyAccessorElement get setter; |
| 8598 return false; | 9599 |
| 9600 /** |
| 9601 * Return `true` if this element is a static element. A static element is an e
lement that is |
| 9602 * not associated with a particular instance, but rather with an entire librar
y or class. |
| 9603 * |
| 9604 * @return `true` if this executable element is a static element |
| 9605 */ |
| 9606 bool get isStatic; |
| 9607 } |
| 9608 |
| 9609 /** |
| 9610 * Instances of the class `PropertyInducingElementImpl` implement a |
| 9611 * `PropertyInducingElement`. |
| 9612 */ |
| 9613 abstract class PropertyInducingElementImpl extends VariableElementImpl implement
s PropertyInducingElement { |
| 9614 /** |
| 9615 * The getter associated with this element. |
| 9616 */ |
| 9617 PropertyAccessorElement getter; |
| 9618 |
| 9619 /** |
| 9620 * The setter associated with this element, or `null` if the element is effect
ively |
| 9621 * `final` and therefore does not have a setter associated with it. |
| 9622 */ |
| 9623 PropertyAccessorElement setter; |
| 9624 |
| 9625 /** |
| 9626 * An empty array of elements. |
| 9627 */ |
| 9628 static List<PropertyInducingElement> EMPTY_ARRAY = new List<PropertyInducingEl
ement>(0); |
| 9629 |
| 9630 /** |
| 9631 * Initialize a newly created element to have the given name. |
| 9632 * |
| 9633 * @param name the name of this element |
| 9634 */ |
| 9635 PropertyInducingElementImpl.con1(Identifier name) : super.forNode(name); |
| 9636 |
| 9637 /** |
| 9638 * Initialize a newly created synthetic element to have the given name. |
| 9639 * |
| 9640 * @param name the name of this element |
| 9641 */ |
| 9642 PropertyInducingElementImpl.con2(String name) : super(name, -1) { |
| 9643 synthetic = true; |
| 9644 } |
| 9645 } |
| 9646 |
| 9647 /** |
| 9648 * Instances of the class `RecursiveElementVisitor` implement an element visitor
that will |
| 9649 * recursively visit all of the element in an element model. For example, using
an instance of this |
| 9650 * class to visit a [CompilationUnitElement] will also cause all of the types in
the |
| 9651 * compilation unit to be visited. |
| 9652 * |
| 9653 * Subclasses that override a visit method must either invoke the overridden vis
it method or must |
| 9654 * explicitly ask the visited element to visit its children. Failure to do so wi
ll cause the |
| 9655 * children of the visited element to not be visited. |
| 9656 */ |
| 9657 class RecursiveElementVisitor<R> implements ElementVisitor<R> { |
| 9658 @override |
| 9659 R visitAngularComponentElement(AngularComponentElement element) { |
| 9660 element.visitChildren(this); |
| 9661 return null; |
| 9662 } |
| 9663 |
| 9664 @override |
| 9665 R visitAngularControllerElement(AngularControllerElement element) { |
| 9666 element.visitChildren(this); |
| 9667 return null; |
| 9668 } |
| 9669 |
| 9670 @override |
| 9671 R visitAngularDirectiveElement(AngularDecoratorElement element) { |
| 9672 element.visitChildren(this); |
| 9673 return null; |
| 9674 } |
| 9675 |
| 9676 @override |
| 9677 R visitAngularFormatterElement(AngularFormatterElement element) { |
| 9678 element.visitChildren(this); |
| 9679 return null; |
| 9680 } |
| 9681 |
| 9682 @override |
| 9683 R visitAngularPropertyElement(AngularPropertyElement element) { |
| 9684 element.visitChildren(this); |
| 9685 return null; |
| 9686 } |
| 9687 |
| 9688 @override |
| 9689 R visitAngularScopePropertyElement(AngularScopePropertyElement element) { |
| 9690 element.visitChildren(this); |
| 9691 return null; |
| 9692 } |
| 9693 |
| 9694 @override |
| 9695 R visitAngularSelectorElement(AngularSelectorElement element) { |
| 9696 element.visitChildren(this); |
| 9697 return null; |
| 9698 } |
| 9699 |
| 9700 @override |
| 9701 R visitAngularViewElement(AngularViewElement element) { |
| 9702 element.visitChildren(this); |
| 9703 return null; |
| 9704 } |
| 9705 |
| 9706 @override |
| 9707 R visitClassElement(ClassElement element) { |
| 9708 element.visitChildren(this); |
| 9709 return null; |
| 9710 } |
| 9711 |
| 9712 @override |
| 9713 R visitCompilationUnitElement(CompilationUnitElement element) { |
| 9714 element.visitChildren(this); |
| 9715 return null; |
| 9716 } |
| 9717 |
| 9718 @override |
| 9719 R visitConstructorElement(ConstructorElement element) { |
| 9720 element.visitChildren(this); |
| 9721 return null; |
| 9722 } |
| 9723 |
| 9724 @override |
| 9725 R visitEmbeddedHtmlScriptElement(EmbeddedHtmlScriptElement element) { |
| 9726 element.visitChildren(this); |
| 9727 return null; |
| 9728 } |
| 9729 |
| 9730 @override |
| 9731 R visitExportElement(ExportElement element) { |
| 9732 element.visitChildren(this); |
| 9733 return null; |
| 9734 } |
| 9735 |
| 9736 @override |
| 9737 R visitExternalHtmlScriptElement(ExternalHtmlScriptElement element) { |
| 9738 element.visitChildren(this); |
| 9739 return null; |
| 9740 } |
| 9741 |
| 9742 @override |
| 9743 R visitFieldElement(FieldElement element) { |
| 9744 element.visitChildren(this); |
| 9745 return null; |
| 9746 } |
| 9747 |
| 9748 @override |
| 9749 R visitFieldFormalParameterElement(FieldFormalParameterElement element) { |
| 9750 element.visitChildren(this); |
| 9751 return null; |
| 9752 } |
| 9753 |
| 9754 @override |
| 9755 R visitFunctionElement(FunctionElement element) { |
| 9756 element.visitChildren(this); |
| 9757 return null; |
| 9758 } |
| 9759 |
| 9760 @override |
| 9761 R visitFunctionTypeAliasElement(FunctionTypeAliasElement element) { |
| 9762 element.visitChildren(this); |
| 9763 return null; |
| 9764 } |
| 9765 |
| 9766 @override |
| 9767 R visitHtmlElement(HtmlElement element) { |
| 9768 element.visitChildren(this); |
| 9769 return null; |
| 9770 } |
| 9771 |
| 9772 @override |
| 9773 R visitImportElement(ImportElement element) { |
| 9774 element.visitChildren(this); |
| 9775 return null; |
| 9776 } |
| 9777 |
| 9778 @override |
| 9779 R visitLabelElement(LabelElement element) { |
| 9780 element.visitChildren(this); |
| 9781 return null; |
| 9782 } |
| 9783 |
| 9784 @override |
| 9785 R visitLibraryElement(LibraryElement element) { |
| 9786 element.visitChildren(this); |
| 9787 return null; |
| 9788 } |
| 9789 |
| 9790 @override |
| 9791 R visitLocalVariableElement(LocalVariableElement element) { |
| 9792 element.visitChildren(this); |
| 9793 return null; |
| 9794 } |
| 9795 |
| 9796 @override |
| 9797 R visitMethodElement(MethodElement element) { |
| 9798 element.visitChildren(this); |
| 9799 return null; |
| 9800 } |
| 9801 |
| 9802 @override |
| 9803 R visitMultiplyDefinedElement(MultiplyDefinedElement element) { |
| 9804 element.visitChildren(this); |
| 9805 return null; |
| 9806 } |
| 9807 |
| 9808 @override |
| 9809 R visitParameterElement(ParameterElement element) { |
| 9810 element.visitChildren(this); |
| 9811 return null; |
| 9812 } |
| 9813 |
| 9814 @override |
| 9815 R visitPolymerAttributeElement(PolymerAttributeElement element) { |
| 9816 element.visitChildren(this); |
| 9817 return null; |
| 9818 } |
| 9819 |
| 9820 @override |
| 9821 R visitPolymerTagDartElement(PolymerTagDartElement element) { |
| 9822 element.visitChildren(this); |
| 9823 return null; |
| 9824 } |
| 9825 |
| 9826 @override |
| 9827 R visitPolymerTagHtmlElement(PolymerTagHtmlElement element) { |
| 9828 element.visitChildren(this); |
| 9829 return null; |
| 9830 } |
| 9831 |
| 9832 @override |
| 9833 R visitPrefixElement(PrefixElement element) { |
| 9834 element.visitChildren(this); |
| 9835 return null; |
| 9836 } |
| 9837 |
| 9838 @override |
| 9839 R visitPropertyAccessorElement(PropertyAccessorElement element) { |
| 9840 element.visitChildren(this); |
| 9841 return null; |
| 9842 } |
| 9843 |
| 9844 @override |
| 9845 R visitTopLevelVariableElement(TopLevelVariableElement element) { |
| 9846 element.visitChildren(this); |
| 9847 return null; |
| 9848 } |
| 9849 |
| 9850 @override |
| 9851 R visitTypeParameterElement(TypeParameterElement element) { |
| 9852 element.visitChildren(this); |
| 9853 return null; |
| 9854 } |
| 9855 } |
| 9856 |
| 9857 /** |
| 9858 * The interface `ShowElementCombinator` defines the behavior of combinators tha
t cause some |
| 9859 * of the names in a namespace to be visible (and the rest hidden) when being im
ported. |
| 9860 */ |
| 9861 abstract class ShowElementCombinator implements NamespaceCombinator { |
| 9862 /** |
| 9863 * Return the offset of the character immediately following the last character
of this node. |
| 9864 * |
| 9865 * @return the offset of the character just past this node |
| 9866 */ |
| 9867 int get end; |
| 9868 |
| 9869 /** |
| 9870 * Return the offset of the 'show' keyword of this element. |
| 9871 * |
| 9872 * @return the offset of the 'show' keyword of this element |
| 9873 */ |
| 9874 int get offset; |
| 9875 |
| 9876 /** |
| 9877 * Return an array containing the names that are to be made visible in the imp
orting library if |
| 9878 * they are defined in the imported library. |
| 9879 * |
| 9880 * @return the names from the imported library that are visible in the importi
ng library |
| 9881 */ |
| 9882 List<String> get shownNames; |
| 9883 } |
| 9884 |
| 9885 /** |
| 9886 * Instances of the class `ShowElementCombinatorImpl` implement a |
| 9887 * [ShowElementCombinator]. |
| 9888 */ |
| 9889 class ShowElementCombinatorImpl implements ShowElementCombinator { |
| 9890 /** |
| 9891 * The names that are to be made visible in the importing library if they are
defined in the |
| 9892 * imported library. |
| 9893 */ |
| 9894 List<String> shownNames = StringUtilities.EMPTY_ARRAY; |
| 9895 |
| 9896 /** |
| 9897 * The offset of the character immediately following the last character of thi
s node. |
| 9898 */ |
| 9899 int end = -1; |
| 9900 |
| 9901 /** |
| 9902 * The offset of the 'show' keyword of this element. |
| 9903 */ |
| 9904 int offset = 0; |
| 9905 |
| 9906 @override |
| 9907 String toString() { |
| 9908 JavaStringBuilder builder = new JavaStringBuilder(); |
| 9909 builder.append("show "); |
| 9910 int count = shownNames.length; |
| 9911 for (int i = 0; i < count; i++) { |
| 9912 if (i > 0) { |
| 9913 builder.append(", "); |
| 8599 } | 9914 } |
| 8600 } | 9915 builder.append(shownNames[i]); |
| 8601 return true; | 9916 } |
| 8602 } | 9917 return builder.toString(); |
| 8603 | 9918 } |
| 8604 /** | 9919 } |
| 8605 * An array containing the actual types of the type arguments. | 9920 |
| 8606 */ | 9921 /** |
| 8607 List<DartType> typeArguments = TypeImpl.EMPTY_ARRAY; | 9922 * Instances of the class `SimpleElementVisitor` implement an element visitor th
at will do |
| 8608 | 9923 * nothing when visiting an element. It is intended to be a superclass for class
es that use the |
| 8609 /** | 9924 * visitor pattern primarily as a dispatch mechanism (and hence don't need to re
cursively visit a |
| 8610 * Initialize a newly created function type to be declared by the given elemen
t and to have the | 9925 * whole structure) and that only need to visit a small number of element types. |
| 8611 * given name. | 9926 */ |
| 8612 * | 9927 class SimpleElementVisitor<R> implements ElementVisitor<R> { |
| 8613 * @param element the element representing the declaration of the function typ
e | 9928 @override |
| 8614 */ | 9929 R visitAngularComponentElement(AngularComponentElement element) => null; |
| 8615 FunctionTypeImpl.con1(ExecutableElement element) : super(element, element == n
ull ? null : element.name); | 9930 |
| 8616 | 9931 @override |
| 8617 /** | 9932 R visitAngularControllerElement(AngularControllerElement element) => null; |
| 8618 * Initialize a newly created function type to be declared by the given elemen
t and to have the | 9933 |
| 8619 * given name. | 9934 @override |
| 8620 * | 9935 R visitAngularDirectiveElement(AngularDecoratorElement element) => null; |
| 8621 * @param element the element representing the declaration of the function typ
e | 9936 |
| 8622 */ | 9937 @override |
| 8623 FunctionTypeImpl.con2(FunctionTypeAliasElement element) : super(element, eleme
nt == null ? null : element.name); | 9938 R visitAngularFormatterElement(AngularFormatterElement element) => null; |
| 8624 | 9939 |
| 8625 @override | 9940 @override |
| 8626 bool operator ==(Object object) => internalEquals(object, new Set<ElementPair>
()); | 9941 R visitAngularPropertyElement(AngularPropertyElement element) => null; |
| 8627 | 9942 |
| 8628 @override | 9943 @override |
| 8629 String get displayName { | 9944 R visitAngularScopePropertyElement(AngularScopePropertyElement element) => nul
l; |
| 8630 String name = this.name; | 9945 |
| 8631 if (name == null || name.length == 0) { | 9946 @override |
| 8632 // TODO(brianwilkerson) Determine whether function types should ever have
an empty name. | 9947 R visitAngularSelectorElement(AngularSelectorElement element) => null; |
| 8633 List<DartType> normalParameterTypes = this.normalParameterTypes; | 9948 |
| 8634 List<DartType> optionalParameterTypes = this.optionalParameterTypes; | 9949 @override |
| 8635 Map<String, DartType> namedParameterTypes = this.namedParameterTypes; | 9950 R visitAngularViewElement(AngularViewElement element) => null; |
| 8636 DartType returnType = this.returnType; | 9951 |
| 8637 JavaStringBuilder builder = new JavaStringBuilder(); | 9952 @override |
| 8638 builder.append("("); | 9953 R visitClassElement(ClassElement element) => null; |
| 8639 bool needsComma = false; | 9954 |
| 8640 if (normalParameterTypes.length > 0) { | 9955 @override |
| 8641 for (DartType type in normalParameterTypes) { | 9956 R visitCompilationUnitElement(CompilationUnitElement element) => null; |
| 8642 if (needsComma) { | 9957 |
| 8643 builder.append(", "); | 9958 @override |
| 8644 } else { | 9959 R visitConstructorElement(ConstructorElement element) => null; |
| 8645 needsComma = true; | 9960 |
| 8646 } | 9961 @override |
| 8647 builder.append(type.displayName); | 9962 R visitEmbeddedHtmlScriptElement(EmbeddedHtmlScriptElement element) => null; |
| 8648 } | 9963 |
| 8649 } | 9964 @override |
| 8650 if (optionalParameterTypes.length > 0) { | 9965 R visitExportElement(ExportElement element) => null; |
| 8651 if (needsComma) { | 9966 |
| 8652 builder.append(", "); | 9967 @override |
| 8653 needsComma = false; | 9968 R visitExternalHtmlScriptElement(ExternalHtmlScriptElement element) => null; |
| 8654 } | 9969 |
| 8655 builder.append("["); | 9970 @override |
| 8656 for (DartType type in optionalParameterTypes) { | 9971 R visitFieldElement(FieldElement element) => null; |
| 8657 if (needsComma) { | 9972 |
| 8658 builder.append(", "); | 9973 @override |
| 8659 } else { | 9974 R visitFieldFormalParameterElement(FieldFormalParameterElement element) => nul
l; |
| 8660 needsComma = true; | 9975 |
| 8661 } | 9976 @override |
| 8662 builder.append(type.displayName); | 9977 R visitFunctionElement(FunctionElement element) => null; |
| 8663 } | 9978 |
| 8664 builder.append("]"); | 9979 @override |
| 8665 needsComma = true; | 9980 R visitFunctionTypeAliasElement(FunctionTypeAliasElement element) => null; |
| 8666 } | 9981 |
| 8667 if (namedParameterTypes.length > 0) { | 9982 @override |
| 8668 if (needsComma) { | 9983 R visitHtmlElement(HtmlElement element) => null; |
| 8669 builder.append(", "); | 9984 |
| 8670 needsComma = false; | 9985 @override |
| 8671 } | 9986 R visitImportElement(ImportElement element) => null; |
| 8672 builder.append("{"); | 9987 |
| 8673 for (MapEntry<String, DartType> entry in getMapEntrySet(namedParameterTy
pes)) { | 9988 @override |
| 8674 if (needsComma) { | 9989 R visitLabelElement(LabelElement element) => null; |
| 8675 builder.append(", "); | 9990 |
| 8676 } else { | 9991 @override |
| 8677 needsComma = true; | 9992 R visitLibraryElement(LibraryElement element) => null; |
| 8678 } | 9993 |
| 8679 builder.append(entry.getKey()); | 9994 @override |
| 8680 builder.append(": "); | 9995 R visitLocalVariableElement(LocalVariableElement element) => null; |
| 8681 builder.append(entry.getValue().displayName); | 9996 |
| 8682 } | 9997 @override |
| 8683 builder.append("}"); | 9998 R visitMethodElement(MethodElement element) => null; |
| 8684 needsComma = true; | 9999 |
| 8685 } | 10000 @override |
| 8686 builder.append(")"); | 10001 R visitMultiplyDefinedElement(MultiplyDefinedElement element) => null; |
| 8687 builder.append(Element.RIGHT_ARROW); | 10002 |
| 8688 if (returnType == null) { | 10003 @override |
| 8689 builder.append("null"); | 10004 R visitParameterElement(ParameterElement element) => null; |
| 8690 } else { | 10005 |
| 8691 builder.append(returnType.displayName); | 10006 @override |
| 8692 } | 10007 R visitPolymerAttributeElement(PolymerAttributeElement element) => null; |
| 8693 name = builder.toString(); | 10008 |
| 8694 } | 10009 @override |
| 8695 return name; | 10010 R visitPolymerTagDartElement(PolymerTagDartElement element) => null; |
| 8696 } | 10011 |
| 8697 | 10012 @override |
| 8698 @override | 10013 R visitPolymerTagHtmlElement(PolymerTagHtmlElement element) => null; |
| 8699 Map<String, DartType> get namedParameterTypes { | 10014 |
| 8700 LinkedHashMap<String, DartType> namedParameterTypes = new LinkedHashMap<Stri
ng, DartType>(); | 10015 @override |
| 8701 List<ParameterElement> parameters = baseParameters; | 10016 R visitPrefixElement(PrefixElement element) => null; |
| 8702 if (parameters.length == 0) { | 10017 |
| 8703 return namedParameterTypes; | 10018 @override |
| 8704 } | 10019 R visitPropertyAccessorElement(PropertyAccessorElement element) => null; |
| 8705 List<DartType> typeParameters = TypeParameterTypeImpl.getTypes(this.typePara
meters); | 10020 |
| 8706 for (ParameterElement parameter in parameters) { | 10021 @override |
| 8707 if (parameter.parameterKind == ParameterKind.NAMED) { | 10022 R visitTopLevelVariableElement(TopLevelVariableElement element) => null; |
| 8708 namedParameterTypes[parameter.name] = parameter.type.substitute2(typeArg
uments, typeParameters); | 10023 |
| 8709 } | 10024 @override |
| 8710 } | 10025 R visitTypeParameterElement(TypeParameterElement element) => null; |
| 8711 return namedParameterTypes; | 10026 } |
| 8712 } | 10027 |
| 8713 | 10028 /** |
| 8714 @override | 10029 * The interface `ToolkitObjectElement` defines the behavior of elements that re
present a |
| 8715 List<DartType> get normalParameterTypes { | 10030 * toolkit specific object, such as Angular controller or component. These eleme
nts are not based on |
| 8716 List<ParameterElement> parameters = baseParameters; | 10031 * the Dart syntax, but on some semantic agreement, such as a special annotation
. |
| 8717 if (parameters.length == 0) { | 10032 */ |
| 8718 return TypeImpl.EMPTY_ARRAY; | 10033 abstract class ToolkitObjectElement implements Element { |
| 8719 } | 10034 /** |
| 8720 List<DartType> typeParameters = TypeParameterTypeImpl.getTypes(this.typePara
meters); | 10035 * An empty array of toolkit object elements. |
| 8721 List<DartType> types = new List<DartType>(); | 10036 */ |
| 8722 for (ParameterElement parameter in parameters) { | 10037 static final List<ToolkitObjectElement> EMPTY_ARRAY = new List<ToolkitObjectEl
ement>(0); |
| 8723 if (parameter.parameterKind == ParameterKind.REQUIRED) { | 10038 } |
| 8724 types.add(parameter.type.substitute2(typeArguments, typeParameters)); | 10039 |
| 8725 } | 10040 /** |
| 8726 } | 10041 * Instances of the class `ToolkitObjectElementImpl` implement a `ToolkitObjectE
lement`. |
| 8727 return new List.from(types); | 10042 */ |
| 8728 } | 10043 abstract class ToolkitObjectElementImpl extends ElementImpl implements ToolkitOb
jectElement { |
| 8729 | 10044 /** |
| 8730 @override | 10045 * Initialize a newly created toolkit object element to have the given name. |
| 8731 List<DartType> get optionalParameterTypes { | 10046 * |
| 8732 List<ParameterElement> parameters = baseParameters; | 10047 * @param name the name of this element |
| 8733 if (parameters.length == 0) { | 10048 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 8734 return TypeImpl.EMPTY_ARRAY; | 10049 * declaration of this element |
| 8735 } | 10050 */ |
| 8736 List<DartType> typeParameters = TypeParameterTypeImpl.getTypes(this.typePara
meters); | 10051 ToolkitObjectElementImpl(String name, int nameOffset) : super(name, nameOffset
); |
| 8737 List<DartType> types = new List<DartType>(); | 10052 } |
| 8738 for (ParameterElement parameter in parameters) { | 10053 |
| 8739 if (parameter.parameterKind == ParameterKind.POSITIONAL) { | 10054 /** |
| 8740 types.add(parameter.type.substitute2(typeArguments, typeParameters)); | 10055 * The interface `TopLevelVariableElement` defines the behavior of elements repr
esenting a |
| 8741 } | 10056 * top-level variable. |
| 8742 } | 10057 */ |
| 8743 return new List.from(types); | 10058 abstract class TopLevelVariableElement implements PropertyInducingElement { |
| 8744 } | 10059 } |
| 8745 | 10060 |
| 8746 @override | 10061 /** |
| 8747 List<ParameterElement> get parameters { | 10062 * Instances of the class `TopLevelVariableElementImpl` implement a |
| 8748 List<ParameterElement> baseParameters = this.baseParameters; | 10063 * `TopLevelVariableElement`. |
| 8749 // no parameters, quick return | 10064 */ |
| 8750 int parameterCount = baseParameters.length; | 10065 class TopLevelVariableElementImpl extends PropertyInducingElementImpl implements
TopLevelVariableElement { |
| 8751 if (parameterCount == 0) { | 10066 /** |
| 8752 return baseParameters; | 10067 * An empty array of top-level variable elements. |
| 8753 } | 10068 */ |
| 8754 // create specialized parameters | 10069 static List<TopLevelVariableElement> EMPTY_ARRAY = new List<TopLevelVariableEl
ement>(0); |
| 8755 List<ParameterElement> specializedParameters = new List<ParameterElement>(pa
rameterCount); | 10070 |
| 8756 for (int i = 0; i < parameterCount; i++) { | 10071 /** |
| 8757 specializedParameters[i] = ParameterMember.from(baseParameters[i], this); | 10072 * Initialize a newly created top-level variable element to have the given nam
e. |
| 8758 } | 10073 * |
| 8759 return specializedParameters; | 10074 * @param name the name of this element |
| 8760 } | 10075 */ |
| 8761 | 10076 TopLevelVariableElementImpl.con1(Identifier name) : super.con1(name); |
| 8762 @override | 10077 |
| 8763 DartType get returnType { | 10078 /** |
| 8764 DartType baseReturnType = this.baseReturnType; | 10079 * Initialize a newly created synthetic top-level variable element to have the
given name. |
| 8765 if (baseReturnType == null) { | 10080 * |
| 8766 // TODO(brianwilkerson) This is a patch. The return type should never be n
ull and we need to | 10081 * @param name the name of this element |
| 8767 // understand why it is and fix it. | 10082 */ |
| 8768 return DynamicTypeImpl.instance; | 10083 TopLevelVariableElementImpl.con2(String name) : super.con2(name); |
| 8769 } | 10084 |
| 8770 return baseReturnType.substitute2(typeArguments, TypeParameterTypeImpl.getTy
pes(typeParameters)); | 10085 @override |
| 8771 } | 10086 accept(ElementVisitor visitor) => visitor.visitTopLevelVariableElement(this); |
| 8772 | 10087 |
| 8773 @override | 10088 @override |
| 8774 List<TypeParameterElement> get typeParameters { | 10089 ElementKind get kind => ElementKind.TOP_LEVEL_VARIABLE; |
| 8775 Element element = this.element; | 10090 |
| 8776 if (element is FunctionTypeAliasElement) { | 10091 @override |
| 8777 return element.typeParameters; | 10092 bool get isStatic => true; |
| 8778 } | 10093 } |
| 8779 ClassElement definingClass = element.getAncestor((element) => element is Cla
ssElement); | 10094 |
| 8780 if (definingClass != null) { | 10095 /** |
| 8781 return definingClass.typeParameters; | |
| 8782 } | |
| 8783 return TypeParameterElementImpl.EMPTY_ARRAY; | |
| 8784 } | |
| 8785 | |
| 8786 @override | |
| 8787 int get hashCode { | |
| 8788 if (element == null) { | |
| 8789 return 0; | |
| 8790 } | |
| 8791 // Reference the arrays of parameters | |
| 8792 List<DartType> normalParameterTypes = this.normalParameterTypes; | |
| 8793 List<DartType> optionalParameterTypes = this.optionalParameterTypes; | |
| 8794 Iterable<DartType> namedParameterTypes = this.namedParameterTypes.values; | |
| 8795 // Generate the hashCode | |
| 8796 int hashCode = returnType.hashCode; | |
| 8797 for (int i = 0; i < normalParameterTypes.length; i++) { | |
| 8798 hashCode = (hashCode << 1) + normalParameterTypes[i].hashCode; | |
| 8799 } | |
| 8800 for (int i = 0; i < optionalParameterTypes.length; i++) { | |
| 8801 hashCode = (hashCode << 1) + optionalParameterTypes[i].hashCode; | |
| 8802 } | |
| 8803 for (DartType type in namedParameterTypes) { | |
| 8804 hashCode = (hashCode << 1) + type.hashCode; | |
| 8805 } | |
| 8806 return hashCode; | |
| 8807 } | |
| 8808 | |
| 8809 @override | |
| 8810 bool internalIsMoreSpecificThan(DartType type, bool withDynamic, Set<TypeImpl_
TypePair> visitedTypePairs) { | |
| 8811 // trivial base cases | |
| 8812 if (type == null) { | |
| 8813 return false; | |
| 8814 } else if (identical(this, type) || type.isDynamic || type.isDartCoreFunctio
n || type.isObject) { | |
| 8815 return true; | |
| 8816 } else if (type is! FunctionType) { | |
| 8817 return false; | |
| 8818 } else if (this == type) { | |
| 8819 return true; | |
| 8820 } | |
| 8821 FunctionType t = this; | |
| 8822 FunctionType s = type as FunctionType; | |
| 8823 List<DartType> tTypes = t.normalParameterTypes; | |
| 8824 List<DartType> tOpTypes = t.optionalParameterTypes; | |
| 8825 List<DartType> sTypes = s.normalParameterTypes; | |
| 8826 List<DartType> sOpTypes = s.optionalParameterTypes; | |
| 8827 // If one function has positional and the other has named parameters, return
false. | |
| 8828 if ((sOpTypes.length > 0 && t.namedParameterTypes.length > 0) || (tOpTypes.l
ength > 0 && s.namedParameterTypes.length > 0)) { | |
| 8829 return false; | |
| 8830 } | |
| 8831 // named parameters case | |
| 8832 if (t.namedParameterTypes.length > 0) { | |
| 8833 // check that the number of required parameters are equal, and check that
every t_i is | |
| 8834 // more specific than every s_i | |
| 8835 if (t.normalParameterTypes.length != s.normalParameterTypes.length) { | |
| 8836 return false; | |
| 8837 } else if (t.normalParameterTypes.length > 0) { | |
| 8838 for (int i = 0; i < tTypes.length; i++) { | |
| 8839 if (!(tTypes[i] as TypeImpl).isMoreSpecificThan2(sTypes[i], withDynami
c, visitedTypePairs)) { | |
| 8840 return false; | |
| 8841 } | |
| 8842 } | |
| 8843 } | |
| 8844 Map<String, DartType> namedTypesT = t.namedParameterTypes; | |
| 8845 Map<String, DartType> namedTypesS = s.namedParameterTypes; | |
| 8846 // if k >= m is false, return false: the passed function type has more nam
ed parameter types than this | |
| 8847 if (namedTypesT.length < namedTypesS.length) { | |
| 8848 return false; | |
| 8849 } | |
| 8850 // Loop through each element in S verifying that T has a matching paramete
r name and that the | |
| 8851 // corresponding type is more specific then the type in S. | |
| 8852 JavaIterator<MapEntry<String, DartType>> iteratorS = new JavaIterator(getM
apEntrySet(namedTypesS)); | |
| 8853 while (iteratorS.hasNext) { | |
| 8854 MapEntry<String, DartType> entryS = iteratorS.next(); | |
| 8855 DartType typeT = namedTypesT[entryS.getKey()]; | |
| 8856 if (typeT == null) { | |
| 8857 return false; | |
| 8858 } | |
| 8859 if (!(typeT as TypeImpl).isMoreSpecificThan2(entryS.getValue(), withDyna
mic, visitedTypePairs)) { | |
| 8860 return false; | |
| 8861 } | |
| 8862 } | |
| 8863 } else if (s.namedParameterTypes.length > 0) { | |
| 8864 return false; | |
| 8865 } else { | |
| 8866 // positional parameter case | |
| 8867 int tArgLength = tTypes.length + tOpTypes.length; | |
| 8868 int sArgLength = sTypes.length + sOpTypes.length; | |
| 8869 // Check that the total number of parameters in t is greater than or equal
to the number of | |
| 8870 // parameters in s and that the number of required parameters in s is grea
ter than or equal to | |
| 8871 // the number of required parameters in t. | |
| 8872 if (tArgLength < sArgLength || sTypes.length < tTypes.length) { | |
| 8873 return false; | |
| 8874 } | |
| 8875 if (tOpTypes.length == 0 && sOpTypes.length == 0) { | |
| 8876 // No positional arguments, don't copy contents to new array | |
| 8877 for (int i = 0; i < sTypes.length; i++) { | |
| 8878 if (!(tTypes[i] as TypeImpl).isMoreSpecificThan2(sTypes[i], withDynami
c, visitedTypePairs)) { | |
| 8879 return false; | |
| 8880 } | |
| 8881 } | |
| 8882 } else { | |
| 8883 // Else, we do have positional parameters, copy required and positional
parameter types into | |
| 8884 // arrays to do the compare (for loop below). | |
| 8885 List<DartType> tAllTypes = new List<DartType>(sArgLength); | |
| 8886 for (int i = 0; i < tTypes.length; i++) { | |
| 8887 tAllTypes[i] = tTypes[i]; | |
| 8888 } | |
| 8889 for (int i = tTypes.length, j = 0; i < sArgLength; i++, j++) { | |
| 8890 tAllTypes[i] = tOpTypes[j]; | |
| 8891 } | |
| 8892 List<DartType> sAllTypes = new List<DartType>(sArgLength); | |
| 8893 for (int i = 0; i < sTypes.length; i++) { | |
| 8894 sAllTypes[i] = sTypes[i]; | |
| 8895 } | |
| 8896 for (int i = sTypes.length, j = 0; i < sArgLength; i++, j++) { | |
| 8897 sAllTypes[i] = sOpTypes[j]; | |
| 8898 } | |
| 8899 for (int i = 0; i < sAllTypes.length; i++) { | |
| 8900 if (!(tAllTypes[i] as TypeImpl).isMoreSpecificThan2(sAllTypes[i], with
Dynamic, visitedTypePairs)) { | |
| 8901 return false; | |
| 8902 } | |
| 8903 } | |
| 8904 } | |
| 8905 } | |
| 8906 DartType tRetType = t.returnType; | |
| 8907 DartType sRetType = s.returnType; | |
| 8908 return sRetType.isVoid || (tRetType as TypeImpl).isMoreSpecificThan2(sRetTyp
e, withDynamic, visitedTypePairs); | |
| 8909 } | |
| 8910 | |
| 8911 @override | |
| 8912 bool isAssignableTo(DartType type) => isSubtypeOf2(type, new Set<TypeImpl_Type
Pair>()); | |
| 8913 | |
| 8914 @override | |
| 8915 FunctionTypeImpl substitute3(List<DartType> argumentTypes) => substitute2(argu
mentTypes, typeArguments); | |
| 8916 | |
| 8917 @override | |
| 8918 FunctionTypeImpl substitute2(List<DartType> argumentTypes, List<DartType> para
meterTypes) { | |
| 8919 if (argumentTypes.length != parameterTypes.length) { | |
| 8920 throw new IllegalArgumentException("argumentTypes.length (${argumentTypes.
length}) != parameterTypes.length (${parameterTypes.length})"); | |
| 8921 } | |
| 8922 if (argumentTypes.length == 0) { | |
| 8923 return this; | |
| 8924 } | |
| 8925 Element element = this.element; | |
| 8926 FunctionTypeImpl newType = (element is ExecutableElement) ? new FunctionType
Impl.con1(element) : new FunctionTypeImpl.con2(element as FunctionTypeAliasEleme
nt); | |
| 8927 newType.typeArguments = TypeImpl.substitute(typeArguments, argumentTypes, pa
rameterTypes); | |
| 8928 return newType; | |
| 8929 } | |
| 8930 | |
| 8931 @override | |
| 8932 void appendTo(JavaStringBuilder builder) { | |
| 8933 List<DartType> normalParameterTypes = this.normalParameterTypes; | |
| 8934 List<DartType> optionalParameterTypes = this.optionalParameterTypes; | |
| 8935 Map<String, DartType> namedParameterTypes = this.namedParameterTypes; | |
| 8936 DartType returnType = this.returnType; | |
| 8937 builder.append("("); | |
| 8938 bool needsComma = false; | |
| 8939 if (normalParameterTypes.length > 0) { | |
| 8940 for (DartType type in normalParameterTypes) { | |
| 8941 if (needsComma) { | |
| 8942 builder.append(", "); | |
| 8943 } else { | |
| 8944 needsComma = true; | |
| 8945 } | |
| 8946 (type as TypeImpl).appendTo(builder); | |
| 8947 } | |
| 8948 } | |
| 8949 if (optionalParameterTypes.length > 0) { | |
| 8950 if (needsComma) { | |
| 8951 builder.append(", "); | |
| 8952 needsComma = false; | |
| 8953 } | |
| 8954 builder.append("["); | |
| 8955 for (DartType type in optionalParameterTypes) { | |
| 8956 if (needsComma) { | |
| 8957 builder.append(", "); | |
| 8958 } else { | |
| 8959 needsComma = true; | |
| 8960 } | |
| 8961 (type as TypeImpl).appendTo(builder); | |
| 8962 } | |
| 8963 builder.append("]"); | |
| 8964 needsComma = true; | |
| 8965 } | |
| 8966 if (namedParameterTypes.length > 0) { | |
| 8967 if (needsComma) { | |
| 8968 builder.append(", "); | |
| 8969 needsComma = false; | |
| 8970 } | |
| 8971 builder.append("{"); | |
| 8972 for (MapEntry<String, DartType> entry in getMapEntrySet(namedParameterType
s)) { | |
| 8973 if (needsComma) { | |
| 8974 builder.append(", "); | |
| 8975 } else { | |
| 8976 needsComma = true; | |
| 8977 } | |
| 8978 builder.append(entry.getKey()); | |
| 8979 builder.append(": "); | |
| 8980 (entry.getValue() as TypeImpl).appendTo(builder); | |
| 8981 } | |
| 8982 builder.append("}"); | |
| 8983 needsComma = true; | |
| 8984 } | |
| 8985 builder.append(")"); | |
| 8986 builder.append(Element.RIGHT_ARROW); | |
| 8987 if (returnType == null) { | |
| 8988 builder.append("null"); | |
| 8989 } else { | |
| 8990 (returnType as TypeImpl).appendTo(builder); | |
| 8991 } | |
| 8992 } | |
| 8993 | |
| 8994 /** | |
| 8995 * @return the base parameter elements of this function element, not `null`. | |
| 8996 */ | |
| 8997 List<ParameterElement> get baseParameters { | |
| 8998 Element element = this.element; | |
| 8999 if (element is ExecutableElement) { | |
| 9000 return element.parameters; | |
| 9001 } else { | |
| 9002 return (element as FunctionTypeAliasElement).parameters; | |
| 9003 } | |
| 9004 } | |
| 9005 | |
| 9006 @override | |
| 9007 bool internalEquals(Object object, Set<ElementPair> visitedElementPairs) { | |
| 9008 if (object is! FunctionTypeImpl) { | |
| 9009 return false; | |
| 9010 } | |
| 9011 FunctionTypeImpl otherType = object as FunctionTypeImpl; | |
| 9012 // If the visitedTypePairs already has the pair (this, type), use the elemen
ts to determine equality | |
| 9013 ElementPair elementPair = new ElementPair(element, otherType.element); | |
| 9014 if (!visitedElementPairs.add(elementPair)) { | |
| 9015 return elementPair.firstElt == elementPair.secondElt; | |
| 9016 } | |
| 9017 // Compute the result | |
| 9018 bool result = TypeImpl.equalArrays(normalParameterTypes, otherType.normalPar
ameterTypes, visitedElementPairs) && TypeImpl.equalArrays(optionalParameterTypes
, otherType.optionalParameterTypes, visitedElementPairs) && _equals(namedParamet
erTypes, otherType.namedParameterTypes, visitedElementPairs) && (returnType as T
ypeImpl).internalEquals(otherType.returnType, visitedElementPairs); | |
| 9019 // Remove the pair from our visited pairs list | |
| 9020 visitedElementPairs.remove(elementPair); | |
| 9021 // Return the result | |
| 9022 return result; | |
| 9023 } | |
| 9024 | |
| 9025 @override | |
| 9026 bool internalIsSubtypeOf(DartType type, Set<TypeImpl_TypePair> visitedTypePair
s) { | |
| 9027 // trivial base cases | |
| 9028 if (type == null) { | |
| 9029 return false; | |
| 9030 } else if (identical(this, type) || type.isDynamic || type.isDartCoreFunctio
n || type.isObject) { | |
| 9031 return true; | |
| 9032 } else if (type is! FunctionType) { | |
| 9033 return false; | |
| 9034 } else if (this == type) { | |
| 9035 return true; | |
| 9036 } | |
| 9037 FunctionType t = this; | |
| 9038 FunctionType s = type as FunctionType; | |
| 9039 List<DartType> tTypes = t.normalParameterTypes; | |
| 9040 List<DartType> tOpTypes = t.optionalParameterTypes; | |
| 9041 List<DartType> sTypes = s.normalParameterTypes; | |
| 9042 List<DartType> sOpTypes = s.optionalParameterTypes; | |
| 9043 // If one function has positional and the other has named parameters, return
false. | |
| 9044 if ((sOpTypes.length > 0 && t.namedParameterTypes.length > 0) || (tOpTypes.l
ength > 0 && s.namedParameterTypes.length > 0)) { | |
| 9045 return false; | |
| 9046 } | |
| 9047 // named parameters case | |
| 9048 if (t.namedParameterTypes.length > 0) { | |
| 9049 // check that the number of required parameters are equal, and check that
every t_i is | |
| 9050 // assignable to every s_i | |
| 9051 if (t.normalParameterTypes.length != s.normalParameterTypes.length) { | |
| 9052 return false; | |
| 9053 } else if (t.normalParameterTypes.length > 0) { | |
| 9054 for (int i = 0; i < tTypes.length; i++) { | |
| 9055 if (!(tTypes[i] as TypeImpl).isAssignableTo2(sTypes[i], visitedTypePai
rs)) { | |
| 9056 return false; | |
| 9057 } | |
| 9058 } | |
| 9059 } | |
| 9060 Map<String, DartType> namedTypesT = t.namedParameterTypes; | |
| 9061 Map<String, DartType> namedTypesS = s.namedParameterTypes; | |
| 9062 // if k >= m is false, return false: the passed function type has more nam
ed parameter types than this | |
| 9063 if (namedTypesT.length < namedTypesS.length) { | |
| 9064 return false; | |
| 9065 } | |
| 9066 // Loop through each element in S verifying that T has a matching paramete
r name and that the | |
| 9067 // corresponding type is assignable to the type in S. | |
| 9068 JavaIterator<MapEntry<String, DartType>> iteratorS = new JavaIterator(getM
apEntrySet(namedTypesS)); | |
| 9069 while (iteratorS.hasNext) { | |
| 9070 MapEntry<String, DartType> entryS = iteratorS.next(); | |
| 9071 DartType typeT = namedTypesT[entryS.getKey()]; | |
| 9072 if (typeT == null) { | |
| 9073 return false; | |
| 9074 } | |
| 9075 if (!(typeT as TypeImpl).isAssignableTo2(entryS.getValue(), visitedTypeP
airs)) { | |
| 9076 return false; | |
| 9077 } | |
| 9078 } | |
| 9079 } else if (s.namedParameterTypes.length > 0) { | |
| 9080 return false; | |
| 9081 } else { | |
| 9082 // positional parameter case | |
| 9083 int tArgLength = tTypes.length + tOpTypes.length; | |
| 9084 int sArgLength = sTypes.length + sOpTypes.length; | |
| 9085 // Check that the total number of parameters in t is greater than or equal
to the number of | |
| 9086 // parameters in s and that the number of required parameters in s is grea
ter than or equal to | |
| 9087 // the number of required parameters in t. | |
| 9088 if (tArgLength < sArgLength || sTypes.length < tTypes.length) { | |
| 9089 return false; | |
| 9090 } | |
| 9091 if (tOpTypes.length == 0 && sOpTypes.length == 0) { | |
| 9092 // No positional arguments, don't copy contents to new array | |
| 9093 for (int i = 0; i < sTypes.length; i++) { | |
| 9094 if (!(tTypes[i] as TypeImpl).isAssignableTo2(sTypes[i], visitedTypePai
rs)) { | |
| 9095 return false; | |
| 9096 } | |
| 9097 } | |
| 9098 } else { | |
| 9099 // Else, we do have positional parameters, copy required and positional
parameter types into | |
| 9100 // arrays to do the compare (for loop below). | |
| 9101 List<DartType> tAllTypes = new List<DartType>(sArgLength); | |
| 9102 for (int i = 0; i < tTypes.length; i++) { | |
| 9103 tAllTypes[i] = tTypes[i]; | |
| 9104 } | |
| 9105 for (int i = tTypes.length, j = 0; i < sArgLength; i++, j++) { | |
| 9106 tAllTypes[i] = tOpTypes[j]; | |
| 9107 } | |
| 9108 List<DartType> sAllTypes = new List<DartType>(sArgLength); | |
| 9109 for (int i = 0; i < sTypes.length; i++) { | |
| 9110 sAllTypes[i] = sTypes[i]; | |
| 9111 } | |
| 9112 for (int i = sTypes.length, j = 0; i < sArgLength; i++, j++) { | |
| 9113 sAllTypes[i] = sOpTypes[j]; | |
| 9114 } | |
| 9115 for (int i = 0; i < sAllTypes.length; i++) { | |
| 9116 if (!(tAllTypes[i] as TypeImpl).isAssignableTo2(sAllTypes[i], visitedT
ypePairs)) { | |
| 9117 return false; | |
| 9118 } | |
| 9119 } | |
| 9120 } | |
| 9121 } | |
| 9122 DartType tRetType = t.returnType; | |
| 9123 DartType sRetType = s.returnType; | |
| 9124 return sRetType.isVoid || (tRetType as TypeImpl).isAssignableTo2(sRetType, v
isitedTypePairs); | |
| 9125 } | |
| 9126 | |
| 9127 /** | |
| 9128 * Return the return type defined by this function's element. | |
| 9129 * | |
| 9130 * @return the return type defined by this function's element | |
| 9131 */ | |
| 9132 DartType get baseReturnType { | |
| 9133 Element element = this.element; | |
| 9134 if (element is ExecutableElement) { | |
| 9135 return element.returnType; | |
| 9136 } else { | |
| 9137 return (element as FunctionTypeAliasElement).returnType; | |
| 9138 } | |
| 9139 } | |
| 9140 } | |
| 9141 | |
| 9142 /** | |
| 9143 * Instances of the class `InterfaceTypeImpl` defines the behavior common to obj
ects | |
| 9144 * representing the type introduced by either a class or an interface, or a refe
rence to such a | |
| 9145 * type. | |
| 9146 */ | |
| 9147 class InterfaceTypeImpl extends TypeImpl implements InterfaceType { | |
| 9148 /** | |
| 9149 * An empty array of types. | |
| 9150 */ | |
| 9151 static List<InterfaceType> EMPTY_ARRAY = new List<InterfaceType>(0); | |
| 9152 | |
| 9153 /** | |
| 9154 * This method computes the longest inheritance path from some passed [Type] t
o Object. | |
| 9155 * | |
| 9156 * @param type the [Type] to compute the longest inheritance path of from the
passed | |
| 9157 * [Type] to Object | |
| 9158 * @return the computed longest inheritance path to Object | |
| 9159 * @see InterfaceType#getLeastUpperBound(Type) | |
| 9160 */ | |
| 9161 static int computeLongestInheritancePathToObject(InterfaceType type) => _compu
teLongestInheritancePathToObject(type, 0, new Set<ClassElement>()); | |
| 9162 | |
| 9163 /** | |
| 9164 * Returns the set of all superinterfaces of the passed [Type]. | |
| 9165 * | |
| 9166 * @param type the [Type] to compute the set of superinterfaces of | |
| 9167 * @return the [Set] of superinterfaces of the passed [Type] | |
| 9168 * @see #getLeastUpperBound(Type) | |
| 9169 */ | |
| 9170 static Set<InterfaceType> computeSuperinterfaceSet(InterfaceType type) => _com
puteSuperinterfaceSet(type, new Set<InterfaceType>()); | |
| 9171 | |
| 9172 /** | |
| 9173 * This method computes the longest inheritance path from some passed [Type] t
o Object. This | |
| 9174 * method calls itself recursively, callers should use the public method | |
| 9175 * [computeLongestInheritancePathToObject]. | |
| 9176 * | |
| 9177 * @param type the [Type] to compute the longest inheritance path of from the
passed | |
| 9178 * [Type] to Object | |
| 9179 * @param depth a field used recursively | |
| 9180 * @param visitedClasses the classes that have already been visited | |
| 9181 * @return the computed longest inheritance path to Object | |
| 9182 * @see #computeLongestInheritancePathToObject(Type) | |
| 9183 * @see #getLeastUpperBound(Type) | |
| 9184 */ | |
| 9185 static int _computeLongestInheritancePathToObject(InterfaceType type, int dept
h, Set<ClassElement> visitedClasses) { | |
| 9186 ClassElement classElement = type.element; | |
| 9187 // Object case | |
| 9188 if (classElement.supertype == null || visitedClasses.contains(classElement))
{ | |
| 9189 return depth; | |
| 9190 } | |
| 9191 int longestPath = 1; | |
| 9192 try { | |
| 9193 visitedClasses.add(classElement); | |
| 9194 List<InterfaceType> superinterfaces = classElement.interfaces; | |
| 9195 int pathLength; | |
| 9196 if (superinterfaces.length > 0) { | |
| 9197 // loop through each of the superinterfaces recursively calling this met
hod and keeping track | |
| 9198 // of the longest path to return | |
| 9199 for (InterfaceType superinterface in superinterfaces) { | |
| 9200 pathLength = _computeLongestInheritancePathToObject(superinterface, de
pth + 1, visitedClasses); | |
| 9201 if (pathLength > longestPath) { | |
| 9202 longestPath = pathLength; | |
| 9203 } | |
| 9204 } | |
| 9205 } | |
| 9206 // finally, perform this same check on the super type | |
| 9207 // TODO(brianwilkerson) Does this also need to add in the number of mixin
classes? | |
| 9208 InterfaceType supertype = classElement.supertype; | |
| 9209 pathLength = _computeLongestInheritancePathToObject(supertype, depth + 1,
visitedClasses); | |
| 9210 if (pathLength > longestPath) { | |
| 9211 longestPath = pathLength; | |
| 9212 } | |
| 9213 } finally { | |
| 9214 visitedClasses.remove(classElement); | |
| 9215 } | |
| 9216 return longestPath; | |
| 9217 } | |
| 9218 | |
| 9219 /** | |
| 9220 * Returns the set of all superinterfaces of the passed [Type]. This is a recu
rsive method, | |
| 9221 * callers should call the public [computeSuperinterfaceSet]. | |
| 9222 * | |
| 9223 * @param type the [Type] to compute the set of superinterfaces of | |
| 9224 * @param set a [HashSet] used recursively by this method | |
| 9225 * @return the [Set] of superinterfaces of the passed [Type] | |
| 9226 * @see #computeSuperinterfaceSet(Type) | |
| 9227 * @see #getLeastUpperBound(Type) | |
| 9228 */ | |
| 9229 static Set<InterfaceType> _computeSuperinterfaceSet(InterfaceType type, Set<In
terfaceType> set) { | |
| 9230 Element element = type.element; | |
| 9231 if (element != null) { | |
| 9232 List<InterfaceType> superinterfaces = type.interfaces; | |
| 9233 for (InterfaceType superinterface in superinterfaces) { | |
| 9234 if (set.add(superinterface)) { | |
| 9235 _computeSuperinterfaceSet(superinterface, set); | |
| 9236 } | |
| 9237 } | |
| 9238 InterfaceType supertype = type.superclass; | |
| 9239 if (supertype != null) { | |
| 9240 if (set.add(supertype)) { | |
| 9241 _computeSuperinterfaceSet(supertype, set); | |
| 9242 } | |
| 9243 } | |
| 9244 } | |
| 9245 return set; | |
| 9246 } | |
| 9247 | |
| 9248 /** | |
| 9249 * Return the intersection of the given sets of types, where intersection is b
ased on the equality | |
| 9250 * of the types themselves. | |
| 9251 * | |
| 9252 * @param first the first set of types to be intersected | |
| 9253 * @param second the second set of types to be intersected | |
| 9254 * @return the intersection of the given sets of types | |
| 9255 */ | |
| 9256 static List<InterfaceType> _intersection(Set<InterfaceType> first, Set<Interfa
ceType> second) { | |
| 9257 Set<InterfaceType> result = new Set<InterfaceType>.from(first); | |
| 9258 result.retainAll(second); | |
| 9259 return new List.from(result); | |
| 9260 } | |
| 9261 | |
| 9262 /** | |
| 9263 * Return the "least upper bound" of the given types under the assumption that
the types have the | |
| 9264 * same element and differ only in terms of the type arguments. The resulting
type is composed by | |
| 9265 * comparing the corresponding type arguments, keeping those that are the same
, and using | |
| 9266 * 'dynamic' for those that are different. | |
| 9267 * | |
| 9268 * @param firstType the first type | |
| 9269 * @param secondType the second type | |
| 9270 * @return the "least upper bound" of the given types | |
| 9271 */ | |
| 9272 static InterfaceType _leastUpperBound(InterfaceType firstType, InterfaceType s
econdType) { | |
| 9273 if (firstType == secondType) { | |
| 9274 return firstType; | |
| 9275 } | |
| 9276 List<DartType> firstArguments = firstType.typeArguments; | |
| 9277 List<DartType> secondArguments = secondType.typeArguments; | |
| 9278 int argumentCount = firstArguments.length; | |
| 9279 if (argumentCount == 0) { | |
| 9280 return firstType; | |
| 9281 } | |
| 9282 List<DartType> lubArguments = new List<DartType>(argumentCount); | |
| 9283 for (int i = 0; i < argumentCount; i++) { | |
| 9284 // | |
| 9285 // Ideally we would take the least upper bound of the two argument types,
but this can cause | |
| 9286 // an infinite recursion (such as when finding the least upper bound of St
ring and num). | |
| 9287 // | |
| 9288 if (firstArguments[i] == secondArguments[i]) { | |
| 9289 lubArguments[i] = firstArguments[i]; | |
| 9290 } | |
| 9291 if (lubArguments[i] == null) { | |
| 9292 lubArguments[i] = DynamicTypeImpl.instance; | |
| 9293 } | |
| 9294 } | |
| 9295 InterfaceTypeImpl lub = new InterfaceTypeImpl.con1(firstType.element); | |
| 9296 lub.typeArguments = lubArguments; | |
| 9297 return lub; | |
| 9298 } | |
| 9299 | |
| 9300 /** | |
| 9301 * An array containing the actual types of the type arguments. | |
| 9302 */ | |
| 9303 List<DartType> typeArguments = TypeImpl.EMPTY_ARRAY; | |
| 9304 | |
| 9305 /** | |
| 9306 * Initialize a newly created type to be declared by the given element. | |
| 9307 * | |
| 9308 * @param element the element representing the declaration of the type | |
| 9309 */ | |
| 9310 InterfaceTypeImpl.con1(ClassElement element) : super(element, element.displayN
ame); | |
| 9311 | |
| 9312 /** | |
| 9313 * Initialize a newly created type to have the given name. This constructor sh
ould only be used in | |
| 9314 * cases where there is no declaration of the type. | |
| 9315 * | |
| 9316 * @param name the name of the type | |
| 9317 */ | |
| 9318 InterfaceTypeImpl.con2(String name) : super(null, name); | |
| 9319 | |
| 9320 @override | |
| 9321 bool operator ==(Object object) => internalEquals(object, new Set<ElementPair>
()); | |
| 9322 | |
| 9323 @override | |
| 9324 List<PropertyAccessorElement> get accessors { | |
| 9325 List<PropertyAccessorElement> accessors = element.accessors; | |
| 9326 List<PropertyAccessorElement> members = new List<PropertyAccessorElement>(ac
cessors.length); | |
| 9327 for (int i = 0; i < accessors.length; i++) { | |
| 9328 members[i] = PropertyAccessorMember.from(accessors[i], this); | |
| 9329 } | |
| 9330 return members; | |
| 9331 } | |
| 9332 | |
| 9333 @override | |
| 9334 String get displayName { | |
| 9335 String name = this.name; | |
| 9336 List<DartType> typeArguments = this.typeArguments; | |
| 9337 bool allDynamic = true; | |
| 9338 for (DartType type in typeArguments) { | |
| 9339 if (type != null && !type.isDynamic) { | |
| 9340 allDynamic = false; | |
| 9341 break; | |
| 9342 } | |
| 9343 } | |
| 9344 // If there is at least one non-dynamic type, then list them out | |
| 9345 if (!allDynamic) { | |
| 9346 JavaStringBuilder builder = new JavaStringBuilder(); | |
| 9347 builder.append(name); | |
| 9348 builder.append("<"); | |
| 9349 for (int i = 0; i < typeArguments.length; i++) { | |
| 9350 if (i != 0) { | |
| 9351 builder.append(", "); | |
| 9352 } | |
| 9353 DartType typeArg = typeArguments[i]; | |
| 9354 builder.append(typeArg.displayName); | |
| 9355 } | |
| 9356 builder.append(">"); | |
| 9357 name = builder.toString(); | |
| 9358 } | |
| 9359 return name; | |
| 9360 } | |
| 9361 | |
| 9362 @override | |
| 9363 ClassElement get element => super.element as ClassElement; | |
| 9364 | |
| 9365 @override | |
| 9366 PropertyAccessorElement getGetter(String getterName) => PropertyAccessorMember
.from((element as ClassElementImpl).getGetter(getterName), this); | |
| 9367 | |
| 9368 @override | |
| 9369 List<InterfaceType> get interfaces { | |
| 9370 ClassElement classElement = element; | |
| 9371 List<InterfaceType> interfaces = classElement.interfaces; | |
| 9372 List<TypeParameterElement> typeParameters = classElement.typeParameters; | |
| 9373 List<DartType> parameterTypes = classElement.type.typeArguments; | |
| 9374 if (typeParameters.length == 0) { | |
| 9375 return interfaces; | |
| 9376 } | |
| 9377 int count = interfaces.length; | |
| 9378 List<InterfaceType> typedInterfaces = new List<InterfaceType>(count); | |
| 9379 for (int i = 0; i < count; i++) { | |
| 9380 typedInterfaces[i] = interfaces[i].substitute2(typeArguments, parameterTyp
es); | |
| 9381 } | |
| 9382 return typedInterfaces; | |
| 9383 } | |
| 9384 | |
| 9385 @override | |
| 9386 DartType getLeastUpperBound(DartType type) { | |
| 9387 // quick check for self | |
| 9388 if (identical(type, this)) { | |
| 9389 return this; | |
| 9390 } | |
| 9391 // dynamic | |
| 9392 DartType dynamicType = DynamicTypeImpl.instance; | |
| 9393 if (identical(this, dynamicType) || identical(type, dynamicType)) { | |
| 9394 return dynamicType; | |
| 9395 } | |
| 9396 // TODO (jwren) opportunity here for a better, faster algorithm if this turn
s out to be a bottle-neck | |
| 9397 if (type is! InterfaceType) { | |
| 9398 return null; | |
| 9399 } | |
| 9400 // new names to match up with the spec | |
| 9401 InterfaceType i = this; | |
| 9402 InterfaceType j = type as InterfaceType; | |
| 9403 // compute set of supertypes | |
| 9404 Set<InterfaceType> si = computeSuperinterfaceSet(i); | |
| 9405 Set<InterfaceType> sj = computeSuperinterfaceSet(j); | |
| 9406 // union si with i and sj with j | |
| 9407 si.add(i); | |
| 9408 sj.add(j); | |
| 9409 // compute intersection, reference as set 's' | |
| 9410 List<InterfaceType> s = _intersection(si, sj); | |
| 9411 // for each element in Set s, compute the largest inheritance path to Object | |
| 9412 List<int> depths = new List<int>.filled(s.length, 0); | |
| 9413 int maxDepth = 0; | |
| 9414 for (int n = 0; n < s.length; n++) { | |
| 9415 depths[n] = computeLongestInheritancePathToObject(s[n]); | |
| 9416 if (depths[n] > maxDepth) { | |
| 9417 maxDepth = depths[n]; | |
| 9418 } | |
| 9419 } | |
| 9420 // ensure that the currently computed maxDepth is unique, | |
| 9421 // otherwise, decrement and test for uniqueness again | |
| 9422 for (; maxDepth >= 0; maxDepth--) { | |
| 9423 int indexOfLeastUpperBound = -1; | |
| 9424 int numberOfTypesAtMaxDepth = 0; | |
| 9425 for (int m = 0; m < depths.length; m++) { | |
| 9426 if (depths[m] == maxDepth) { | |
| 9427 numberOfTypesAtMaxDepth++; | |
| 9428 indexOfLeastUpperBound = m; | |
| 9429 } | |
| 9430 } | |
| 9431 if (numberOfTypesAtMaxDepth == 1) { | |
| 9432 return s[indexOfLeastUpperBound]; | |
| 9433 } | |
| 9434 } | |
| 9435 // illegal state, log and return null- Object at maxDepth == 0 should always
return itself as | |
| 9436 // the least upper bound. | |
| 9437 // TODO (jwren) log the error state | |
| 9438 return null; | |
| 9439 } | |
| 9440 | |
| 9441 @override | |
| 9442 MethodElement getMethod(String methodName) => MethodMember.from((element as Cl
assElementImpl).getMethod(methodName), this); | |
| 9443 | |
| 9444 @override | |
| 9445 List<MethodElement> get methods { | |
| 9446 List<MethodElement> methods = element.methods; | |
| 9447 List<MethodElement> members = new List<MethodElement>(methods.length); | |
| 9448 for (int i = 0; i < methods.length; i++) { | |
| 9449 members[i] = MethodMember.from(methods[i], this); | |
| 9450 } | |
| 9451 return members; | |
| 9452 } | |
| 9453 | |
| 9454 @override | |
| 9455 List<InterfaceType> get mixins { | |
| 9456 ClassElement classElement = element; | |
| 9457 List<InterfaceType> mixins = classElement.mixins; | |
| 9458 List<TypeParameterElement> typeParameters = classElement.typeParameters; | |
| 9459 List<DartType> parameterTypes = classElement.type.typeArguments; | |
| 9460 if (typeParameters.length == 0) { | |
| 9461 return mixins; | |
| 9462 } | |
| 9463 int count = mixins.length; | |
| 9464 List<InterfaceType> typedMixins = new List<InterfaceType>(count); | |
| 9465 for (int i = 0; i < count; i++) { | |
| 9466 typedMixins[i] = mixins[i].substitute2(typeArguments, parameterTypes); | |
| 9467 } | |
| 9468 return typedMixins; | |
| 9469 } | |
| 9470 | |
| 9471 @override | |
| 9472 PropertyAccessorElement getSetter(String setterName) => PropertyAccessorMember
.from((element as ClassElementImpl).getSetter(setterName), this); | |
| 9473 | |
| 9474 @override | |
| 9475 InterfaceType get superclass { | |
| 9476 ClassElement classElement = element; | |
| 9477 InterfaceType supertype = classElement.supertype; | |
| 9478 if (supertype == null) { | |
| 9479 return null; | |
| 9480 } | |
| 9481 return supertype.substitute2(typeArguments, classElement.type.typeArguments)
; | |
| 9482 } | |
| 9483 | |
| 9484 @override | |
| 9485 List<TypeParameterElement> get typeParameters => element.typeParameters; | |
| 9486 | |
| 9487 @override | |
| 9488 int get hashCode { | |
| 9489 ClassElement element = this.element; | |
| 9490 if (element == null) { | |
| 9491 return 0; | |
| 9492 } | |
| 9493 return element.hashCode; | |
| 9494 } | |
| 9495 | |
| 9496 @override | |
| 9497 bool get isDartCoreFunction { | |
| 9498 ClassElement element = this.element; | |
| 9499 if (element == null) { | |
| 9500 return false; | |
| 9501 } | |
| 9502 return element.name == "Function" && element.library.isDartCore; | |
| 9503 } | |
| 9504 | |
| 9505 @override | |
| 9506 bool isDirectSupertypeOf(InterfaceType type) { | |
| 9507 InterfaceType i = this; | |
| 9508 InterfaceType j = type; | |
| 9509 ClassElement jElement = j.element; | |
| 9510 InterfaceType supertype = jElement.supertype; | |
| 9511 // | |
| 9512 // If J has no direct supertype then it is Object, and Object has no direct
supertypes. | |
| 9513 // | |
| 9514 if (supertype == null) { | |
| 9515 return false; | |
| 9516 } | |
| 9517 // | |
| 9518 // I is listed in the extends clause of J. | |
| 9519 // | |
| 9520 List<DartType> jArgs = j.typeArguments; | |
| 9521 List<DartType> jVars = jElement.type.typeArguments; | |
| 9522 supertype = supertype.substitute2(jArgs, jVars); | |
| 9523 if (supertype == i) { | |
| 9524 return true; | |
| 9525 } | |
| 9526 // | |
| 9527 // I is listed in the implements clause of J. | |
| 9528 // | |
| 9529 for (InterfaceType interfaceType in jElement.interfaces) { | |
| 9530 interfaceType = interfaceType.substitute2(jArgs, jVars); | |
| 9531 if (interfaceType == i) { | |
| 9532 return true; | |
| 9533 } | |
| 9534 } | |
| 9535 // | |
| 9536 // I is listed in the with clause of J. | |
| 9537 // | |
| 9538 for (InterfaceType mixinType in jElement.mixins) { | |
| 9539 mixinType = mixinType.substitute2(jArgs, jVars); | |
| 9540 if (mixinType == i) { | |
| 9541 return true; | |
| 9542 } | |
| 9543 } | |
| 9544 // | |
| 9545 // J is a mixin application of the mixin of I. | |
| 9546 // | |
| 9547 // TODO(brianwilkerson) Determine whether this needs to be implemented or wh
ether it is covered | |
| 9548 // by the case above. | |
| 9549 return false; | |
| 9550 } | |
| 9551 | |
| 9552 @override | |
| 9553 bool get isObject => element.supertype == null; | |
| 9554 | |
| 9555 @override | |
| 9556 ConstructorElement lookUpConstructor(String constructorName, LibraryElement li
brary) { | |
| 9557 // prepare base ConstructorElement | |
| 9558 ConstructorElement constructorElement; | |
| 9559 if (constructorName == null) { | |
| 9560 constructorElement = element.unnamedConstructor; | |
| 9561 } else { | |
| 9562 constructorElement = element.getNamedConstructor(constructorName); | |
| 9563 } | |
| 9564 // not found or not accessible | |
| 9565 if (constructorElement == null || !constructorElement.isAccessibleIn(library
)) { | |
| 9566 return null; | |
| 9567 } | |
| 9568 // return member | |
| 9569 return ConstructorMember.from(constructorElement, this); | |
| 9570 } | |
| 9571 | |
| 9572 @override | |
| 9573 PropertyAccessorElement lookUpGetter(String getterName, LibraryElement library
) { | |
| 9574 PropertyAccessorElement element = getGetter(getterName); | |
| 9575 if (element != null && element.isAccessibleIn(library)) { | |
| 9576 return element; | |
| 9577 } | |
| 9578 return lookUpGetterInSuperclass(getterName, library); | |
| 9579 } | |
| 9580 | |
| 9581 @override | |
| 9582 PropertyAccessorElement lookUpGetterInSuperclass(String getterName, LibraryEle
ment library) { | |
| 9583 for (InterfaceType mixin in mixins) { | |
| 9584 PropertyAccessorElement element = mixin.getGetter(getterName); | |
| 9585 if (element != null && element.isAccessibleIn(library)) { | |
| 9586 return element; | |
| 9587 } | |
| 9588 } | |
| 9589 Set<ClassElement> visitedClasses = new Set<ClassElement>(); | |
| 9590 InterfaceType supertype = superclass; | |
| 9591 ClassElement supertypeElement = supertype == null ? null : supertype.element
; | |
| 9592 while (supertype != null && !visitedClasses.contains(supertypeElement)) { | |
| 9593 visitedClasses.add(supertypeElement); | |
| 9594 PropertyAccessorElement element = supertype.getGetter(getterName); | |
| 9595 if (element != null && element.isAccessibleIn(library)) { | |
| 9596 return element; | |
| 9597 } | |
| 9598 for (InterfaceType mixin in supertype.mixins) { | |
| 9599 element = mixin.getGetter(getterName); | |
| 9600 if (element != null && element.isAccessibleIn(library)) { | |
| 9601 return element; | |
| 9602 } | |
| 9603 } | |
| 9604 supertype = supertype.superclass; | |
| 9605 supertypeElement = supertype == null ? null : supertype.element; | |
| 9606 } | |
| 9607 return null; | |
| 9608 } | |
| 9609 | |
| 9610 @override | |
| 9611 MethodElement lookUpMethod(String methodName, LibraryElement library) { | |
| 9612 MethodElement element = getMethod(methodName); | |
| 9613 if (element != null && element.isAccessibleIn(library)) { | |
| 9614 return element; | |
| 9615 } | |
| 9616 return lookUpMethodInSuperclass(methodName, library); | |
| 9617 } | |
| 9618 | |
| 9619 @override | |
| 9620 MethodElement lookUpMethodInSuperclass(String methodName, LibraryElement libra
ry) { | |
| 9621 for (InterfaceType mixin in mixins) { | |
| 9622 MethodElement element = mixin.getMethod(methodName); | |
| 9623 if (element != null && element.isAccessibleIn(library)) { | |
| 9624 return element; | |
| 9625 } | |
| 9626 } | |
| 9627 Set<ClassElement> visitedClasses = new Set<ClassElement>(); | |
| 9628 InterfaceType supertype = superclass; | |
| 9629 ClassElement supertypeElement = supertype == null ? null : supertype.element
; | |
| 9630 while (supertype != null && !visitedClasses.contains(supertypeElement)) { | |
| 9631 visitedClasses.add(supertypeElement); | |
| 9632 MethodElement element = supertype.getMethod(methodName); | |
| 9633 if (element != null && element.isAccessibleIn(library)) { | |
| 9634 return element; | |
| 9635 } | |
| 9636 for (InterfaceType mixin in supertype.mixins) { | |
| 9637 element = mixin.getMethod(methodName); | |
| 9638 if (element != null && element.isAccessibleIn(library)) { | |
| 9639 return element; | |
| 9640 } | |
| 9641 } | |
| 9642 supertype = supertype.superclass; | |
| 9643 supertypeElement = supertype == null ? null : supertype.element; | |
| 9644 } | |
| 9645 return null; | |
| 9646 } | |
| 9647 | |
| 9648 @override | |
| 9649 PropertyAccessorElement lookUpSetter(String setterName, LibraryElement library
) { | |
| 9650 PropertyAccessorElement element = getSetter(setterName); | |
| 9651 if (element != null && element.isAccessibleIn(library)) { | |
| 9652 return element; | |
| 9653 } | |
| 9654 return lookUpSetterInSuperclass(setterName, library); | |
| 9655 } | |
| 9656 | |
| 9657 @override | |
| 9658 PropertyAccessorElement lookUpSetterInSuperclass(String setterName, LibraryEle
ment library) { | |
| 9659 for (InterfaceType mixin in mixins) { | |
| 9660 PropertyAccessorElement element = mixin.getSetter(setterName); | |
| 9661 if (element != null && element.isAccessibleIn(library)) { | |
| 9662 return element; | |
| 9663 } | |
| 9664 } | |
| 9665 Set<ClassElement> visitedClasses = new Set<ClassElement>(); | |
| 9666 InterfaceType supertype = superclass; | |
| 9667 ClassElement supertypeElement = supertype == null ? null : supertype.element
; | |
| 9668 while (supertype != null && !visitedClasses.contains(supertypeElement)) { | |
| 9669 visitedClasses.add(supertypeElement); | |
| 9670 PropertyAccessorElement element = supertype.getSetter(setterName); | |
| 9671 if (element != null && element.isAccessibleIn(library)) { | |
| 9672 return element; | |
| 9673 } | |
| 9674 for (InterfaceType mixin in supertype.mixins) { | |
| 9675 element = mixin.getSetter(setterName); | |
| 9676 if (element != null && element.isAccessibleIn(library)) { | |
| 9677 return element; | |
| 9678 } | |
| 9679 } | |
| 9680 supertype = supertype.superclass; | |
| 9681 supertypeElement = supertype == null ? null : supertype.element; | |
| 9682 } | |
| 9683 return null; | |
| 9684 } | |
| 9685 | |
| 9686 @override | |
| 9687 InterfaceTypeImpl substitute4(List<DartType> argumentTypes) => substitute2(arg
umentTypes, typeArguments); | |
| 9688 | |
| 9689 @override | |
| 9690 InterfaceTypeImpl substitute2(List<DartType> argumentTypes, List<DartType> par
ameterTypes) { | |
| 9691 if (argumentTypes.length != parameterTypes.length) { | |
| 9692 throw new IllegalArgumentException("argumentTypes.length (${argumentTypes.
length}) != parameterTypes.length (${parameterTypes.length})"); | |
| 9693 } | |
| 9694 if (argumentTypes.length == 0 || typeArguments.length == 0) { | |
| 9695 return this; | |
| 9696 } | |
| 9697 List<DartType> newTypeArguments = TypeImpl.substitute(typeArguments, argumen
tTypes, parameterTypes); | |
| 9698 if (JavaArrays.equals(newTypeArguments, typeArguments)) { | |
| 9699 return this; | |
| 9700 } | |
| 9701 InterfaceTypeImpl newType = new InterfaceTypeImpl.con1(element); | |
| 9702 newType.typeArguments = newTypeArguments; | |
| 9703 return newType; | |
| 9704 } | |
| 9705 | |
| 9706 @override | |
| 9707 void appendTo(JavaStringBuilder builder) { | |
| 9708 builder.append(name); | |
| 9709 int argumentCount = typeArguments.length; | |
| 9710 if (argumentCount > 0) { | |
| 9711 builder.append("<"); | |
| 9712 for (int i = 0; i < argumentCount; i++) { | |
| 9713 if (i > 0) { | |
| 9714 builder.append(", "); | |
| 9715 } | |
| 9716 (typeArguments[i] as TypeImpl).appendTo(builder); | |
| 9717 } | |
| 9718 builder.append(">"); | |
| 9719 } | |
| 9720 } | |
| 9721 | |
| 9722 @override | |
| 9723 bool internalEquals(Object object, Set<ElementPair> visitedElementPairs) { | |
| 9724 if (object is! InterfaceTypeImpl) { | |
| 9725 return false; | |
| 9726 } | |
| 9727 InterfaceTypeImpl otherType = object as InterfaceTypeImpl; | |
| 9728 return (element == otherType.element) && TypeImpl.equalArrays(typeArguments,
otherType.typeArguments, visitedElementPairs); | |
| 9729 } | |
| 9730 | |
| 9731 @override | |
| 9732 bool internalIsMoreSpecificThan(DartType type, bool withDynamic, Set<TypeImpl_
TypePair> visitedTypePairs) { | |
| 9733 // | |
| 9734 // S is dynamic. | |
| 9735 // The test to determine whether S is dynamic is done here because dynamic i
s not an instance of | |
| 9736 // InterfaceType. | |
| 9737 // | |
| 9738 if (identical(type, DynamicTypeImpl.instance)) { | |
| 9739 return true; | |
| 9740 } else if (type is! InterfaceType) { | |
| 9741 return false; | |
| 9742 } | |
| 9743 return _isMoreSpecificThan(type as InterfaceType, new Set<ClassElement>(), w
ithDynamic, visitedTypePairs); | |
| 9744 } | |
| 9745 | |
| 9746 @override | |
| 9747 bool internalIsSubtypeOf(DartType type, Set<TypeImpl_TypePair> visitedTypePair
s) { | |
| 9748 // | |
| 9749 // T is a subtype of S, written T <: S, iff [bottom/dynamic]T << S | |
| 9750 // | |
| 9751 if (type.isDynamic) { | |
| 9752 return true; | |
| 9753 } else if (type is TypeParameterType) { | |
| 9754 return false; | |
| 9755 } else if (type is FunctionType) { | |
| 9756 ClassElement element = this.element; | |
| 9757 MethodElement callMethod = element.lookUpMethod("call", element.library); | |
| 9758 if (callMethod != null) { | |
| 9759 return callMethod.type.isSubtypeOf(type); | |
| 9760 } | |
| 9761 return false; | |
| 9762 } else if (type is! InterfaceType) { | |
| 9763 return false; | |
| 9764 } else if (this == type) { | |
| 9765 return true; | |
| 9766 } | |
| 9767 return _isSubtypeOf(type as InterfaceType, new Set<ClassElement>(), visitedT
ypePairs); | |
| 9768 } | |
| 9769 | |
| 9770 bool _isMoreSpecificThan(InterfaceType s, Set<ClassElement> visitedClasses, bo
ol withDynamic, Set<TypeImpl_TypePair> visitedTypePairs) { | |
| 9771 // | |
| 9772 // A type T is more specific than a type S, written T << S, if one of the f
ollowing conditions | |
| 9773 // is met: | |
| 9774 // | |
| 9775 // Reflexivity: T is S. | |
| 9776 // | |
| 9777 if (this == s) { | |
| 9778 return true; | |
| 9779 } | |
| 9780 // | |
| 9781 // T is bottom. (This case is handled by the class BottomTypeImpl.) | |
| 9782 // | |
| 9783 // Direct supertype: S is a direct supertype of T. | |
| 9784 // | |
| 9785 if (s.isDirectSupertypeOf(this)) { | |
| 9786 return true; | |
| 9787 } | |
| 9788 // | |
| 9789 // Covariance: T is of the form I<T1, ..., Tn> and S is of the form I<S1, ..
., Sn> and Ti << Si, 1 <= i <= n. | |
| 9790 // | |
| 9791 ClassElement tElement = this.element; | |
| 9792 ClassElement sElement = s.element; | |
| 9793 if (tElement == sElement) { | |
| 9794 List<DartType> tArguments = typeArguments; | |
| 9795 List<DartType> sArguments = s.typeArguments; | |
| 9796 if (tArguments.length != sArguments.length) { | |
| 9797 return false; | |
| 9798 } | |
| 9799 for (int i = 0; i < tArguments.length; i++) { | |
| 9800 if (!(tArguments[i] as TypeImpl).isMoreSpecificThan2(sArguments[i], with
Dynamic, visitedTypePairs)) { | |
| 9801 return false; | |
| 9802 } | |
| 9803 } | |
| 9804 return true; | |
| 9805 } | |
| 9806 // | |
| 9807 // Transitivity: T << U and U << S. | |
| 9808 // | |
| 9809 // First check for infinite loops | |
| 9810 ClassElement element = this.element; | |
| 9811 if (element == null || visitedClasses.contains(element)) { | |
| 9812 return false; | |
| 9813 } | |
| 9814 visitedClasses.add(element); | |
| 9815 // Iterate over all of the types U that are more specific than T because the
y are direct | |
| 9816 // supertypes of T and return true if any of them are more specific than S. | |
| 9817 InterfaceType supertype = superclass; | |
| 9818 if (supertype != null && (supertype as InterfaceTypeImpl)._isMoreSpecificTha
n(s, visitedClasses, withDynamic, visitedTypePairs)) { | |
| 9819 return true; | |
| 9820 } | |
| 9821 for (InterfaceType interfaceType in interfaces) { | |
| 9822 if ((interfaceType as InterfaceTypeImpl)._isMoreSpecificThan(s, visitedCla
sses, withDynamic, visitedTypePairs)) { | |
| 9823 return true; | |
| 9824 } | |
| 9825 } | |
| 9826 for (InterfaceType mixinType in mixins) { | |
| 9827 if ((mixinType as InterfaceTypeImpl)._isMoreSpecificThan(s, visitedClasses
, withDynamic, visitedTypePairs)) { | |
| 9828 return true; | |
| 9829 } | |
| 9830 } | |
| 9831 return false; | |
| 9832 } | |
| 9833 | |
| 9834 bool _isSubtypeOf(InterfaceType type, Set<ClassElement> visitedClasses, Set<Ty
peImpl_TypePair> visitedTypePairs) { | |
| 9835 InterfaceType typeT = this; | |
| 9836 InterfaceType typeS = type; | |
| 9837 ClassElement elementT = element; | |
| 9838 if (elementT == null || visitedClasses.contains(elementT)) { | |
| 9839 return false; | |
| 9840 } | |
| 9841 visitedClasses.add(elementT); | |
| 9842 if (typeT == typeS) { | |
| 9843 return true; | |
| 9844 } else if (elementT == typeS.element) { | |
| 9845 // For each of the type arguments return true if all type args from T is a
subtype of all | |
| 9846 // types from S. | |
| 9847 List<DartType> typeTArgs = typeT.typeArguments; | |
| 9848 List<DartType> typeSArgs = typeS.typeArguments; | |
| 9849 if (typeTArgs.length != typeSArgs.length) { | |
| 9850 // This case covers the case where two objects are being compared that h
ave a different | |
| 9851 // number of parameterized types. | |
| 9852 return false; | |
| 9853 } | |
| 9854 for (int i = 0; i < typeTArgs.length; i++) { | |
| 9855 // Recursively call isSubtypeOf the type arguments and return false if t
he T argument is not | |
| 9856 // a subtype of the S argument. | |
| 9857 if (!(typeTArgs[i] as TypeImpl).isSubtypeOf2(typeSArgs[i], visitedTypePa
irs)) { | |
| 9858 return false; | |
| 9859 } | |
| 9860 } | |
| 9861 return true; | |
| 9862 } else if (typeS.isDartCoreFunction && elementT.getMethod("call") != null) { | |
| 9863 return true; | |
| 9864 } | |
| 9865 InterfaceType supertype = superclass; | |
| 9866 // The type is Object, return false. | |
| 9867 if (supertype != null && (supertype as InterfaceTypeImpl)._isSubtypeOf(typeS
, visitedClasses, visitedTypePairs)) { | |
| 9868 return true; | |
| 9869 } | |
| 9870 List<InterfaceType> interfaceTypes = interfaces; | |
| 9871 for (InterfaceType interfaceType in interfaceTypes) { | |
| 9872 if ((interfaceType as InterfaceTypeImpl)._isSubtypeOf(typeS, visitedClasse
s, visitedTypePairs)) { | |
| 9873 return true; | |
| 9874 } | |
| 9875 } | |
| 9876 List<InterfaceType> mixinTypes = mixins; | |
| 9877 for (InterfaceType mixinType in mixinTypes) { | |
| 9878 if ((mixinType as InterfaceTypeImpl)._isSubtypeOf(typeS, visitedClasses, v
isitedTypePairs)) { | |
| 9879 return true; | |
| 9880 } | |
| 9881 } | |
| 9882 return false; | |
| 9883 } | |
| 9884 } | |
| 9885 | |
| 9886 /** | |
| 9887 * The abstract class `TypeImpl` implements the behavior common to objects repre
senting the | 10096 * The abstract class `TypeImpl` implements the behavior common to objects repre
senting the |
| 9888 * declared type of elements in the element model. | 10097 * declared type of elements in the element model. |
| 9889 */ | 10098 */ |
| 9890 abstract class TypeImpl implements DartType { | 10099 abstract class TypeImpl implements DartType { |
| 9891 static bool equalArrays(List<DartType> typeArgs1, List<DartType> typeArgs2, Se
t<ElementPair> visitedElementPairs) { | 10100 static bool equalArrays(List<DartType> typeArgs1, List<DartType> typeArgs2, Se
t<ElementPair> visitedElementPairs) { |
| 9892 if (typeArgs1.length != typeArgs2.length) { | 10101 if (typeArgs1.length != typeArgs2.length) { |
| 9893 return false; | 10102 return false; |
| 9894 } | 10103 } |
| 9895 for (int i = 0; i < typeArgs1.length; i++) { | 10104 for (int i = 0; i < typeArgs1.length; i++) { |
| 9896 if (!(typeArgs1[i] as TypeImpl).internalEquals(typeArgs2[i], visitedElemen
tPairs)) { | 10105 if (!(typeArgs1[i] as TypeImpl).internalEquals(typeArgs2[i], visitedElemen
tPairs)) { |
| (...skipping 205 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 10102 Element secondElement = _secondType.element; | 10311 Element secondElement = _secondType.element; |
| 10103 secondHashCode = secondElement == null ? 0 : secondElement.hashCode; | 10312 secondHashCode = secondElement == null ? 0 : secondElement.hashCode; |
| 10104 } | 10313 } |
| 10105 _cachedHashCode = firstHashCode + secondHashCode; | 10314 _cachedHashCode = firstHashCode + secondHashCode; |
| 10106 } | 10315 } |
| 10107 return _cachedHashCode; | 10316 return _cachedHashCode; |
| 10108 } | 10317 } |
| 10109 } | 10318 } |
| 10110 | 10319 |
| 10111 /** | 10320 /** |
| 10321 * The interface `TypeParameterElement` defines the behavior of elements represe
nting a type |
| 10322 * parameter. |
| 10323 */ |
| 10324 abstract class TypeParameterElement implements Element { |
| 10325 /** |
| 10326 * Return the type representing the bound associated with this parameter, or `
null` if this |
| 10327 * parameter does not have an explicit bound. |
| 10328 * |
| 10329 * @return the type representing the bound associated with this parameter |
| 10330 */ |
| 10331 DartType get bound; |
| 10332 |
| 10333 /** |
| 10334 * Return the type defined by this type parameter. |
| 10335 * |
| 10336 * @return the type defined by this type parameter |
| 10337 */ |
| 10338 TypeParameterType get type; |
| 10339 } |
| 10340 |
| 10341 /** |
| 10342 * Instances of the class `TypeParameterElementImpl` implement a [TypeParameterE
lement]. |
| 10343 */ |
| 10344 class TypeParameterElementImpl extends ElementImpl implements TypeParameterEleme
nt { |
| 10345 /** |
| 10346 * The type defined by this type parameter. |
| 10347 */ |
| 10348 TypeParameterType type; |
| 10349 |
| 10350 /** |
| 10351 * The type representing the bound associated with this parameter, or `null` i
f this |
| 10352 * parameter does not have an explicit bound. |
| 10353 */ |
| 10354 DartType bound; |
| 10355 |
| 10356 /** |
| 10357 * An empty array of type parameter elements. |
| 10358 */ |
| 10359 static List<TypeParameterElement> EMPTY_ARRAY = new List<TypeParameterElement>
(0); |
| 10360 |
| 10361 /** |
| 10362 * Initialize a newly created type parameter element to have the given name. |
| 10363 * |
| 10364 * @param name the name of this element |
| 10365 */ |
| 10366 TypeParameterElementImpl(Identifier name) : super.forNode(name); |
| 10367 |
| 10368 @override |
| 10369 accept(ElementVisitor visitor) => visitor.visitTypeParameterElement(this); |
| 10370 |
| 10371 @override |
| 10372 ElementKind get kind => ElementKind.TYPE_PARAMETER; |
| 10373 |
| 10374 @override |
| 10375 void appendTo(JavaStringBuilder builder) { |
| 10376 builder.append(displayName); |
| 10377 if (bound != null) { |
| 10378 builder.append(" extends "); |
| 10379 builder.append(bound); |
| 10380 } |
| 10381 } |
| 10382 } |
| 10383 |
| 10384 /** |
| 10385 * The interface `TypeParameterType` defines the behavior of objects representin
g the type |
| 10386 * introduced by a type parameter. |
| 10387 */ |
| 10388 abstract class TypeParameterType implements DartType { |
| 10389 @override |
| 10390 TypeParameterElement get element; |
| 10391 } |
| 10392 |
| 10393 /** |
| 10112 * Instances of the class `TypeParameterTypeImpl` defines the behavior of object
s representing | 10394 * Instances of the class `TypeParameterTypeImpl` defines the behavior of object
s representing |
| 10113 * the type introduced by a type parameter. | 10395 * the type introduced by a type parameter. |
| 10114 */ | 10396 */ |
| 10115 class TypeParameterTypeImpl extends TypeImpl implements TypeParameterType { | 10397 class TypeParameterTypeImpl extends TypeImpl implements TypeParameterType { |
| 10116 /** | 10398 /** |
| 10117 * An empty array of type parameter types. | 10399 * An empty array of type parameter types. |
| 10118 */ | 10400 */ |
| 10119 static List<TypeParameterType> EMPTY_ARRAY = new List<TypeParameterType>(0); | 10401 static List<TypeParameterType> EMPTY_ARRAY = new List<TypeParameterType>(0); |
| 10120 | 10402 |
| 10121 /** | 10403 /** |
| (...skipping 102 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 10224 visitedTypes.add(bound); | 10506 visitedTypes.add(bound); |
| 10225 // Then check upper bound. | 10507 // Then check upper bound. |
| 10226 return boundTypeParameter._isMoreSpecificThan(s, visitedTypes, withDynamic
, visitedTypePairs); | 10508 return boundTypeParameter._isMoreSpecificThan(s, visitedTypes, withDynamic
, visitedTypePairs); |
| 10227 } | 10509 } |
| 10228 // Check interface type. | 10510 // Check interface type. |
| 10229 return (bound as TypeImpl).isMoreSpecificThan2(s, withDynamic, visitedTypePa
irs); | 10511 return (bound as TypeImpl).isMoreSpecificThan2(s, withDynamic, visitedTypePa
irs); |
| 10230 } | 10512 } |
| 10231 } | 10513 } |
| 10232 | 10514 |
| 10233 /** | 10515 /** |
| 10234 * The unique instance of the class `VoidTypeImpl` implements the type `void`. | 10516 * The interface `UndefinedElement` defines the behavior of pseudo-elements that
represent |
| 10235 */ | 10517 * names that are undefined. This situation is not allowed by the language, so o
bjects implementing |
| 10236 class VoidTypeImpl extends TypeImpl implements VoidType { | 10518 * this interface always represent an error. As a result, most of the normal ope
rations on elements |
| 10237 /** | 10519 * do not make sense and will return useless results. |
| 10238 * The unique instance of this class. | 10520 */ |
| 10239 */ | 10521 abstract class UndefinedElement implements Element { |
| 10240 static VoidTypeImpl _INSTANCE = new VoidTypeImpl(); | 10522 } |
| 10241 | 10523 |
| 10242 /** | 10524 /** |
| 10243 * Return the unique instance of this class. | 10525 * The interface `UriReferencedElement` defines the behavior of objects included
into a |
| 10244 * | 10526 * library using some URI. |
| 10245 * @return the unique instance of this class | 10527 */ |
| 10246 */ | 10528 abstract class UriReferencedElement implements Element { |
| 10247 static VoidTypeImpl get instance => _INSTANCE; | 10529 /** |
| 10248 | 10530 * Return the offset of the character immediately following the last character
of this node's URI, |
| 10249 /** | 10531 * or `-1` for synthetic import. |
| 10250 * Prevent the creation of instances of this class. | 10532 * |
| 10251 */ | 10533 * @return the offset of the character just past the node's URI |
| 10252 VoidTypeImpl() : super(null, Keyword.VOID.syntax); | 10534 */ |
| 10253 | 10535 int get uriEnd; |
| 10254 @override | 10536 |
| 10255 bool operator ==(Object object) => identical(object, this); | 10537 /** |
| 10256 | 10538 * Return the offset of the URI in the file, or `-1` if this element is synthe
tic. |
| 10257 @override | 10539 * |
| 10258 int get hashCode => 2; | 10540 * @return the offset of the URI |
| 10259 | 10541 */ |
| 10260 @override | 10542 int get uriOffset; |
| 10261 bool get isVoid => true; | 10543 |
| 10262 | 10544 /** |
| 10263 @override | 10545 * Return the URI that is used to include this element into the enclosing libr
ary, or `null` |
| 10264 VoidTypeImpl substitute2(List<DartType> argumentTypes, List<DartType> paramete
rTypes) => this; | 10546 * if this is the defining compilation unit of a library. |
| 10265 | 10547 * |
| 10266 @override | 10548 * @return the URI that is used to include this element into the enclosing lib
rary |
| 10267 bool internalEquals(Object object, Set<ElementPair> visitedElementPairs) => id
entical(object, this); | 10549 */ |
| 10268 | 10550 String get uri; |
| 10269 @override | 10551 } |
| 10270 bool internalIsMoreSpecificThan(DartType type, bool withDynamic, Set<TypeImpl_
TypePair> visitedTypePairs) => isSubtypeOf(type); | 10552 |
| 10271 | 10553 /** |
| 10272 @override | 10554 * Instances of the class `UriReferencedElementImpl` implement an [UriReferenced
Element] |
| 10273 bool internalIsSubtypeOf(DartType type, Set<TypeImpl_TypePair> visitedTypePair
s) => identical(type, this) || identical(type, DynamicTypeImpl.instance); | 10555 * . |
| 10274 } | 10556 */ |
| 10275 | 10557 abstract class UriReferencedElementImpl extends ElementImpl implements UriRefere
ncedElement { |
| 10276 /** | 10558 /** |
| 10277 * The interface `FunctionType` defines the behavior common to objects represent
ing the type | 10559 * The offset of the URI in the file, may be `-1` if synthetic. |
| 10278 * of a function, method, constructor, getter, or setter. Function types come in
three variations: | 10560 */ |
| 10279 * <ol> | 10561 int uriOffset = -1; |
| 10280 * * The types of functions that only have required parameters. These have the g
eneral form | 10562 |
| 10281 * <i>(T<sub>1</sub>, …, T<sub>n</sub>) → T</i>. | 10563 /** |
| 10282 * * The types of functions with optional positional parameters. These have the
general form | 10564 * The offset of the character immediately following the last character of thi
s node's URI, may be |
| 10283 * <i>(T<sub>1</sub>, …, T<sub>n</sub>, [T<sub>n+1</sub>, …, T<sub
>n+k</sub>]) → | 10565 * `-1` if synthetic. |
| 10284 * T</i>. | 10566 */ |
| 10285 * * The types of functions with named parameters. These have the general form <
i>(T<sub>1</sub>, | 10567 int uriEnd = -1; |
| 10286 * …, T<sub>n</sub>, {T<sub>x1</sub> x1, …, T<sub>xk</sub> xk}) &r
arr; T</i>. | 10568 |
| 10287 * </ol> | 10569 /** |
| 10288 */ | 10570 * The URI that is specified by this directive. |
| 10289 abstract class FunctionType implements ParameterizedType { | 10571 */ |
| 10290 /** | 10572 String uri; |
| 10291 * Return a map from the names of named parameters to the types of the named p
arameters of this | 10573 |
| 10292 * type of function. The entries in the map will be iterated in the same order
as the order in | 10574 /** |
| 10293 * which the named parameters were defined. If there were no named parameters
declared then the | 10575 * Initialize a newly created import element. |
| 10294 * map will be empty. | 10576 * |
| 10295 * | 10577 * @param name the name of this element |
| 10296 * @return a map from the name to the types of the named parameters of this ty
pe of function | 10578 * @param offset the directive offset, may be `-1` if synthetic. |
| 10297 */ | 10579 */ |
| 10298 Map<String, DartType> get namedParameterTypes; | 10580 UriReferencedElementImpl(String name, int offset) : super(name, offset); |
| 10299 | 10581 } |
| 10300 /** | 10582 |
| 10301 * Return an array containing the types of the normal parameters of this type
of function. The | 10583 /** |
| 10302 * parameter types are in the same order as they appear in the declaration of
the function. | 10584 * The interface `VariableElement` defines the behavior common to elements that
represent a |
| 10303 * | 10585 * variable. |
| 10304 * @return the types of the normal parameters of this type of function | 10586 */ |
| 10305 */ | 10587 abstract class VariableElement implements Element { |
| 10306 List<DartType> get normalParameterTypes; | 10588 /** |
| 10307 | 10589 * Return a synthetic function representing this variable's initializer, or `n
ull` if this |
| 10308 /** | 10590 * variable does not have an initializer. The function will have no parameters
. The return type of |
| 10309 * Return a map from the names of optional (positional) parameters to the type
s of the optional | 10591 * the function will be the compile-time type of the initialization expression
. |
| 10310 * parameters of this type of function. The entries in the map will be iterate
d in the same order | 10592 * |
| 10311 * as the order in which the optional parameters were defined. If there were n
o optional | 10593 * @return a synthetic function representing this variable's initializer |
| 10312 * parameters declared then the map will be empty. | 10594 */ |
| 10313 * | 10595 FunctionElement get initializer; |
| 10314 * @return a map from the name to the types of the optional parameters of this
type of function | 10596 |
| 10315 */ | 10597 /** |
| 10316 List<DartType> get optionalParameterTypes; | 10598 * Return the resolved [VariableDeclaration] node that declares this [Variable
Element] |
| 10317 | 10599 * . |
| 10318 /** | 10600 * |
| 10319 * Return an array containing the parameters elements of this type of function
. The parameter | 10601 * This method is expensive, because resolved AST might be evicted from cache,
so parsing and |
| 10320 * types are in the same order as they appear in the declaration of the functi
on. | 10602 * resolving will be performed. |
| 10321 * | 10603 * |
| 10322 * @return the parameters elements of this type of function | 10604 * @return the resolved [VariableDeclaration], not `null`. |
| 10323 */ | 10605 */ |
| 10324 List<ParameterElement> get parameters; | 10606 @override |
| 10325 | 10607 VariableDeclaration get node; |
| 10326 /** | 10608 |
| 10327 * Return the type of object returned by this type of function. | 10609 /** |
| 10328 * | 10610 * Return the declared type of this variable, or `null` if the variable did no
t have a |
| 10329 * @return the type of object returned by this type of function | 10611 * declared type (such as if it was declared using the keyword 'var'). |
| 10330 */ | 10612 * |
| 10331 DartType get returnType; | 10613 * @return the declared type of this variable |
| 10332 | 10614 */ |
| 10333 /** | 10615 DartType get type; |
| 10334 * Return `true` if this type is a subtype of the given type. | 10616 |
| 10335 * | 10617 /** |
| 10336 * A function type <i>(T<sub>1</sub>, …, T<sub>n</sub>) → T</i> is
a subtype of the | 10618 * Return `true` if this variable was declared with the 'const' modifier. |
| 10337 * function type <i>(S<sub>1</sub>, …, S<sub>n</sub>) → S</i>, if
all of the following | 10619 * |
| 10338 * conditions are met: | 10620 * @return `true` if this variable was declared with the 'const' modifier |
| 10339 * * Either | 10621 */ |
| 10340 * * <i>S</i> is void, or | 10622 bool get isConst; |
| 10341 * * <i>T ⇔ S</i>. | 10623 |
| 10342 * | 10624 /** |
| 10343 * * For all <i>i</i>, 1 <= <i>i</i> <= <i>n</i>, <i>T<sub>i</sub> ⇔ S<su
b>i</sub></i>. | 10625 * Return `true` if this variable was declared with the 'final' modifier. Vari
ables that are |
| 10344 * A function type <i>(T<sub>1</sub>, …, T<sub>n</sub>, [T<sub>n+1</sub
>, …, | 10626 * declared with the 'const' modifier will return `false` even though they are
implicitly |
| 10345 * T<sub>n+k</sub>]) → T</i> is a subtype of the function type <i>(S<sub>
1</sub>, …, | 10627 * final. |
| 10346 * S<sub>n</sub>, [S<sub>n+1</sub>, …, S<sub>n+m</sub>]) → S</i>,
if all of the | 10628 * |
| 10347 * following conditions are met: | 10629 * @return `true` if this variable was declared with the 'final' modifier |
| 10348 * * Either | 10630 */ |
| 10349 * * <i>S</i> is void, or | 10631 bool get isFinal; |
| 10350 * * <i>T ⇔ S</i>. | 10632 } |
| 10351 * | 10633 |
| 10352 * * <i>k</i> >= <i>m</i> and for all <i>i</i>, 1 <= <i>i</i> <= <i>n+m</i>, <
i>T<sub>i</sub> | 10634 /** |
| 10353 * ⇔ S<sub>i</sub></i>. | 10635 * Instances of the class `VariableElementImpl` implement a `VariableElement`. |
| 10354 * A function type <i>(T<sub>1</sub>, …, T<sub>n</sub>, {T<sub>x1</sub>
x1, …, | 10636 */ |
| 10355 * T<sub>xk</sub> xk}) → T</i> is a subtype of the function type <i>(S<su
b>1</sub>, …, | 10637 abstract class VariableElementImpl extends ElementImpl implements VariableElemen
t { |
| 10356 * S<sub>n</sub>, {S<sub>y1</sub> y1, …, S<sub>ym</sub> ym}) → S</
i>, if all of the | 10638 /** |
| 10357 * following conditions are met: | 10639 * The declared type of this variable. |
| 10358 * * Either | 10640 */ |
| 10359 * * <i>S</i> is void, | 10641 DartType type; |
| 10360 * * or <i>T ⇔ S</i>. | 10642 |
| 10361 * | 10643 /** |
| 10362 * * For all <i>i</i>, 1 <= <i>i</i> <= <i>n</i>, <i>T<sub>i</sub> ⇔ S<su
b>i</sub></i>. | 10644 * A synthetic function representing this variable's initializer, or `null` if
this variable |
| 10363 * * <i>k</i> >= <i>m</i> and <i>y<sub>i</sub></i> in <i>{x<sub>1</sub>, &hell
ip;, | 10645 * does not have an initializer. |
| 10364 * x<sub>k</sub>}</i>, 1 <= <i>i</i> <= <i>m</i>. | 10646 */ |
| 10365 * * For all <i>y<sub>i</sub></i> in <i>{y<sub>1</sub>, …, y<sub>m</sub
>}</i>, | 10647 FunctionElement _initializer; |
| 10366 * <i>y<sub>i</sub> = x<sub>j</sub> => Tj ⇔ Si</i>. | 10648 |
| 10367 * In addition, the following subtype rules apply: | 10649 /** |
| 10368 * | 10650 * An empty array of variable elements. |
| 10369 * <i>(T<sub>1</sub>, …, T<sub>n</sub>, []) → T <: (T<sub>1</sub>,
…, | 10651 */ |
| 10370 * T<sub>n</sub>) → T.</i><br> | 10652 static List<VariableElement> EMPTY_ARRAY = new List<VariableElement>(0); |
| 10371 * <i>(T<sub>1</sub>, …, T<sub>n</sub>) → T <: (T<sub>1</sub>, &he
llip;, | 10653 |
| 10372 * T<sub>n</sub>, {}) → T.</i><br> | 10654 /** |
| 10373 * <i>(T<sub>1</sub>, …, T<sub>n</sub>, {}) → T <: (T<sub>1</sub>,
…, | 10655 * Initialize a newly created variable element to have the given name. |
| 10374 * T<sub>n</sub>) → T.</i><br> | 10656 * |
| 10375 * <i>(T<sub>1</sub>, …, T<sub>n</sub>) → T <: (T<sub>1</sub>, &he
llip;, | 10657 * @param name the name of this element |
| 10376 * T<sub>n</sub>, []) → T.</i> | 10658 */ |
| 10377 * | 10659 VariableElementImpl.forNode(Identifier name) : super.forNode(name); |
| 10378 * All functions implement the class `Function`. However not all function type
s are a | 10660 |
| 10379 * subtype of `Function`. If an interface type <i>I</i> includes a method name
d | 10661 /** |
| 10380 * `call()`, and the type of `call()` is the function type <i>F</i>, then <i>I
</i> is | 10662 * Initialize a newly created variable element to have the given name. |
| 10381 * considered to be a subtype of <i>F</i>. | 10663 * |
| 10382 * | 10664 * @param name the name of this element |
| 10383 * @param type the type being compared with this type | 10665 * @param nameOffset the offset of the name of this element in the file that c
ontains the |
| 10384 * @return `true` if this type is a subtype of the given type | 10666 * declaration of this element |
| 10385 */ | 10667 */ |
| 10386 @override | 10668 VariableElementImpl(String name, int nameOffset) : super(name, nameOffset); |
| 10387 bool isSubtypeOf(DartType type); | 10669 |
| 10388 | 10670 /** |
| 10389 /** | 10671 * Return the result of evaluating this variable's initializer as a compile-ti
me constant |
| 10390 * Return the type resulting from substituting the given arguments for this ty
pe's parameters. | 10672 * expression, or `null` if this variable is not a 'const' variable, if it doe
s not have an |
| 10391 * This is fully equivalent to `substitute(argumentTypes, getTypeArguments())`
. | 10673 * initializer, or if the compilation unit containing the variable has not bee
n resolved. |
| 10392 * | 10674 * |
| 10393 * @param argumentTypes the actual type arguments being substituted for the ty
pe parameters | 10675 * @return the result of evaluating this variable's initializer |
| 10394 * @return the result of performing the substitution | 10676 */ |
| 10395 */ | 10677 EvaluationResultImpl get evaluationResult => null; |
| 10396 FunctionType substitute3(List<DartType> argumentTypes); | 10678 |
| 10397 | 10679 @override |
| 10398 @override | 10680 FunctionElement get initializer => _initializer; |
| 10399 FunctionType substitute2(List<DartType> argumentTypes, List<DartType> paramete
rTypes); | 10681 |
| 10400 } | 10682 @override |
| 10401 | 10683 VariableDeclaration get node => getNodeMatching((node) => node is VariableDecl
aration); |
| 10402 /** | 10684 |
| 10403 * The interface `InterfaceType` defines the behavior common to objects represen
ting the type | 10685 @override |
| 10404 * introduced by either a class or an interface, or a reference to such a type. | 10686 bool get isConst => hasModifier(Modifier.CONST); |
| 10405 */ | 10687 |
| 10406 abstract class InterfaceType implements ParameterizedType { | 10688 @override |
| 10407 /** | 10689 bool get isFinal => hasModifier(Modifier.FINAL); |
| 10408 * Return an array containing all of the accessors (getters and setters) decla
red in this type. | 10690 |
| 10409 * | 10691 /** |
| 10410 * @return the accessors declared in this type | 10692 * Return `true` if this variable is potentially mutated somewhere in a closur
e. This |
| 10411 */ | 10693 * information is only available for local variables (including parameters) an
d only after the |
| 10412 List<PropertyAccessorElement> get accessors; | 10694 * compilation unit containing the variable has been resolved. |
| 10413 | 10695 * |
| 10414 @override | 10696 * @return `true` if this variable is potentially mutated somewhere in closure |
| 10415 ClassElement get element; | 10697 */ |
| 10416 | 10698 bool get isPotentiallyMutatedInClosure => false; |
| 10417 /** | 10699 |
| 10418 * Return the element representing the getter with the given name that is decl
ared in this class, | 10700 /** |
| 10419 * or `null` if this class does not declare a getter with the given name. | 10701 * Return `true` if this variable is potentially mutated somewhere in its scop
e. This |
| 10420 * | 10702 * information is only available for local variables (including parameters) an
d only after the |
| 10421 * @param getterName the name of the getter to be returned | 10703 * compilation unit containing the variable has been resolved. |
| 10422 * @return the getter declared in this class with the given name | 10704 * |
| 10423 */ | 10705 * @return `true` if this variable is potentially mutated somewhere in its sco
pe |
| 10424 PropertyAccessorElement getGetter(String getterName); | 10706 */ |
| 10425 | 10707 bool get isPotentiallyMutatedInScope => false; |
| 10426 /** | 10708 |
| 10427 * Return an array containing all of the interfaces that are implemented by th
is interface. Note | 10709 /** |
| 10428 * that this is <b>not</b>, in general, equivalent to getting the interfaces f
rom this type's | 10710 * Set whether this variable is const to correspond to the given value. |
| 10429 * element because the types returned by this method will have had their type
parameters replaced. | 10711 * |
| 10430 * | 10712 * @param isConst `true` if the variable is const |
| 10431 * @return the interfaces that are implemented by this type | 10713 */ |
| 10432 */ | 10714 void set const3(bool isConst) { |
| 10433 List<InterfaceType> get interfaces; | 10715 setModifier(Modifier.CONST, isConst); |
| 10434 | 10716 } |
| 10435 /** | 10717 |
| 10436 * Return the least upper bound of this type and the given type, or `null` if
there is no | 10718 /** |
| 10437 * least upper bound. | 10719 * Set the result of evaluating this variable's initializer as a compile-time
constant expression |
| 10438 * | 10720 * to the given result. |
| 10439 * Given two interfaces <i>I</i> and <i>J</i>, let <i>S<sub>I</sub></i> be the
set of | 10721 * |
| 10440 * superinterfaces of <i>I<i>, let <i>S<sub>J</sub></i> be the set of superint
erfaces of <i>J</i> | 10722 * @param result the result of evaluating this variable's initializer |
| 10441 * and let <i>S = (I ∪ S<sub>I</sub>) ∩ (J ∪ S<sub>J</sub>)</i>. F
urthermore, we | 10723 */ |
| 10442 * define <i>S<sub>n</sub> = {T | T ∈ S ∧ depth(T) = n}</i> for any f
inite <i>n</i>, | 10724 void set evaluationResult(EvaluationResultImpl result) { |
| 10443 * where <i>depth(T)</i> is the number of steps in the longest inheritance pat
h from <i>T</i> to | 10725 throw new IllegalStateException("Invalid attempt to set a compile-time const
ant result"); |
| 10444 * <i>Object</i>. Let <i>q</i> be the largest number such that <i>S<sub>q</sub
></i> has | 10726 } |
| 10445 * cardinality one. The least upper bound of <i>I</i> and <i>J</i> is the sole
element of | 10727 |
| 10446 * <i>S<sub>q</sub></i>. | 10728 /** |
| 10447 * | 10729 * Set whether this variable is final to correspond to the given value. |
| 10448 * @param type the other type used to compute the least upper bound | 10730 * |
| 10449 * @return the least upper bound of this type and the given type | 10731 * @param isFinal `true` if the variable is final |
| 10450 */ | 10732 */ |
| 10451 @override | 10733 void set final2(bool isFinal) { |
| 10452 DartType getLeastUpperBound(DartType type); | 10734 setModifier(Modifier.FINAL, isFinal); |
| 10453 | 10735 } |
| 10454 /** | 10736 |
| 10455 * Return the element representing the method with the given name that is decl
ared in this class, | 10737 /** |
| 10456 * or `null` if this class does not declare a method with the given name. | 10738 * Set the function representing this variable's initializer to the given func
tion. |
| 10457 * | 10739 * |
| 10458 * @param methodName the name of the method to be returned | 10740 * @param initializer the function representing this variable's initializer |
| 10459 * @return the method declared in this class with the given name | 10741 */ |
| 10460 */ | 10742 void set initializer(FunctionElement initializer) { |
| 10461 MethodElement getMethod(String methodName); | 10743 if (initializer != null) { |
| 10462 | 10744 (initializer as FunctionElementImpl).enclosingElement = this; |
| 10463 /** | 10745 } |
| 10464 * Return an array containing all of the methods declared in this type. | 10746 this._initializer = initializer; |
| 10465 * | 10747 } |
| 10466 * @return the methods declared in this type | 10748 |
| 10467 */ | 10749 @override |
| 10468 List<MethodElement> get methods; | 10750 void visitChildren(ElementVisitor visitor) { |
| 10469 | 10751 super.visitChildren(visitor); |
| 10470 /** | 10752 safelyVisitChild(_initializer, visitor); |
| 10471 * Return an array containing all of the mixins that are applied to the class
being extended in | 10753 } |
| 10472 * order to derive the superclass of this class. Note that this is <b>not</b>,
in general, | 10754 |
| 10473 * equivalent to getting the mixins from this type's element because the types
returned by this | 10755 @override |
| 10474 * method will have had their type parameters replaced. | 10756 void appendTo(JavaStringBuilder builder) { |
| 10475 * | 10757 builder.append(type); |
| 10476 * @return the mixins that are applied to derive the superclass of this class | 10758 builder.append(" "); |
| 10477 */ | 10759 builder.append(displayName); |
| 10478 List<InterfaceType> get mixins; | 10760 } |
| 10479 | 10761 } |
| 10480 /** | 10762 |
| 10481 * Return the element representing the setter with the given name that is decl
ared in this class, | 10763 /** |
| 10482 * or `null` if this class does not declare a setter with the given name. | 10764 * The abstract class `VariableMember` defines the behavior common to members th
at represent a |
| 10483 * | 10765 * variable element defined in a parameterized type where the values of the type
parameters are |
| 10484 * @param setterName the name of the setter to be returned | 10766 * known. |
| 10485 * @return the setter declared in this class with the given name | 10767 */ |
| 10486 */ | 10768 abstract class VariableMember extends Member implements VariableElement { |
| 10487 PropertyAccessorElement getSetter(String setterName); | 10769 /** |
| 10488 | 10770 * Initialize a newly created element to represent an executable element of th
e given |
| 10489 /** | 10771 * parameterized type. |
| 10490 * Return the type representing the superclass of this type, or null if this t
ype represents the | 10772 * |
| 10491 * class 'Object'. Note that this is <b>not</b>, in general, equivalent to get
ting the superclass | 10773 * @param baseElement the element on which the parameterized element was creat
ed |
| 10492 * from this type's element because the type returned by this method will have
had it's type | 10774 * @param definingType the type in which the element is defined |
| 10493 * parameters replaced. | 10775 */ |
| 10494 * | 10776 VariableMember(VariableElement baseElement, ParameterizedType definingType) :
super(baseElement, definingType); |
| 10495 * @return the superclass of this type | 10777 |
| 10496 */ | 10778 @override |
| 10497 InterfaceType get superclass; | 10779 VariableElement get baseElement => super.baseElement as VariableElement; |
| 10498 | 10780 |
| 10499 /** | 10781 @override |
| 10500 * Return `true` if this type is a direct supertype of the given type. The imp
licit | 10782 FunctionElement get initializer { |
| 10501 * interface of class <i>I</i> is a direct supertype of the implicit interface
of class <i>J</i> | 10783 // |
| 10502 * iff: | 10784 // Elements within this element should have type parameters substituted, jus
t like this element. |
| 10503 * * <i>I</i> is Object, and <i>J</i> has no extends clause. | 10785 // |
| 10504 * * <i>I</i> is listed in the extends clause of <i>J</i>. | 10786 throw new UnsupportedOperationException(); |
| 10505 * * <i>I</i> is listed in the implements clause of <i>J</i>. | 10787 } |
| 10506 * * <i>I</i> is listed in the with clause of <i>J</i>. | 10788 |
| 10507 * * <i>J</i> is a mixin application of the mixin of <i>I</i>. | 10789 @override |
| 10508 * | 10790 VariableDeclaration get node => baseElement.node; |
| 10509 * @param type the type being compared with this type | 10791 |
| 10510 * @return `true` if this type is a direct supertype of the given type | 10792 @override |
| 10511 */ | 10793 DartType get type => substituteFor(baseElement.type); |
| 10512 bool isDirectSupertypeOf(InterfaceType type); | 10794 |
| 10513 | 10795 @override |
| 10514 /** | 10796 bool get isConst => baseElement.isConst; |
| 10515 * Return `true` if this type is more specific than the given type. An interfa
ce type | 10797 |
| 10516 * <i>T</i> is more specific than an interface type <i>S</i>, written <i>T &la
quo; S</i>, if one | 10798 @override |
| 10517 * of the following conditions is met: | 10799 bool get isFinal => baseElement.isFinal; |
| 10518 * * Reflexivity: <i>T</i> is <i>S</i>. | 10800 |
| 10519 * * <i>T</i> is bottom. | 10801 @override |
| 10520 * * <i>S</i> is dynamic. | 10802 void visitChildren(ElementVisitor visitor) { |
| 10521 * * Direct supertype: <i>S</i> is a direct supertype of <i>T</i>. | 10803 // TODO(brianwilkerson) We need to finish implementing the accessors used be
low so that we can |
| 10522 * * <i>T</i> is a type parameter and <i>S</i> is the upper bound of <i>T</i>. | 10804 // safely invoke them. |
| 10523 * * Covariance: <i>T</i> is of the form <i>I<T<sub>1</sub>, …, T<su
b>n</sub>></i> | 10805 super.visitChildren(visitor); |
| 10524 * and S</i> is of the form <i>I<S<sub>1</sub>, …, S<sub>n</sub>>
</i> and | 10806 safelyVisitChild(baseElement.initializer, visitor); |
| 10525 * <i>T<sub>i</sub> « S<sub>i</sub></i>, <i>1 <= i <= n</i>. | 10807 } |
| 10526 * * Transitivity: <i>T « U</i> and <i>U « S</i>. | 10808 } |
| 10527 * | 10809 |
| 10528 * @param type the type being compared with this type | 10810 /** |
| 10529 * @return `true` if this type is more specific than the given type | |
| 10530 */ | |
| 10531 @override | |
| 10532 bool isMoreSpecificThan(DartType type); | |
| 10533 | |
| 10534 /** | |
| 10535 * Return `true` if this type is a subtype of the given type. An interface typ
e <i>T</i> is | |
| 10536 * a subtype of an interface type <i>S</i>, written <i>T</i> <: <i>S</i>, iff | |
| 10537 * <i>[bottom/dynamic]T</i> « <i>S</i> (<i>T</i> is more specific than <
i>S</i>). If an | |
| 10538 * interface type <i>I</i> includes a method named <i>call()</i>, and the type
of <i>call()</i> is | |
| 10539 * the function type <i>F</i>, then <i>I</i> is considered to be a subtype of
<i>F</i>. | |
| 10540 * | |
| 10541 * @param type the type being compared with this type | |
| 10542 * @return `true` if this type is a subtype of the given type | |
| 10543 */ | |
| 10544 @override | |
| 10545 bool isSubtypeOf(DartType type); | |
| 10546 | |
| 10547 /** | |
| 10548 * Return the element representing the constructor that results from looking u
p the given | |
| 10549 * constructor in this class with respect to the given library, or `null` if t
he look up | |
| 10550 * fails. The behavior of this method is defined by the Dart Language Specific
ation in section | |
| 10551 * 12.11.1: <blockquote>If <i>e</i> is of the form <b>new</b> <i>T.id()</i> th
en let <i>q<i> be | |
| 10552 * the constructor <i>T.id</i>, otherwise let <i>q<i> be the constructor <i>T<
i>. Otherwise, if | |
| 10553 * <i>q</i> is not defined or not accessible, a NoSuchMethodException is throw
n. </blockquote> | |
| 10554 * | |
| 10555 * @param constructorName the name of the constructor being looked up | |
| 10556 * @param library the library with respect to which the lookup is being perfor
med | |
| 10557 * @return the result of looking up the given constructor in this class with r
espect to the given | |
| 10558 * library | |
| 10559 */ | |
| 10560 ConstructorElement lookUpConstructor(String constructorName, LibraryElement li
brary); | |
| 10561 | |
| 10562 /** | |
| 10563 * Return the element representing the getter that results from looking up the
given getter in | |
| 10564 * this class with respect to the given library, or `null` if the look up fail
s. The | |
| 10565 * behavior of this method is defined by the Dart Language Specification in se
ction 12.15.1: | |
| 10566 * <blockquote>The result of looking up getter (respectively setter) <i>m</i>
in class <i>C</i> | |
| 10567 * with respect to library <i>L</i> is: | |
| 10568 * * If <i>C</i> declares an instance getter (respectively setter) named <i>m<
/i> that is | |
| 10569 * accessible to <i>L</i>, then that getter (respectively setter) is the resul
t of the lookup. | |
| 10570 * Otherwise, if <i>C</i> has a superclass <i>S</i>, then the result of the lo
okup is the result | |
| 10571 * of looking up getter (respectively setter) <i>m</i> in <i>S</i> with respec
t to <i>L</i>. | |
| 10572 * Otherwise, we say that the lookup has failed. | |
| 10573 * </blockquote> | |
| 10574 * | |
| 10575 * @param getterName the name of the getter being looked up | |
| 10576 * @param library the library with respect to which the lookup is being perfor
med | |
| 10577 * @return the result of looking up the given getter in this class with respec
t to the given | |
| 10578 * library | |
| 10579 */ | |
| 10580 PropertyAccessorElement lookUpGetter(String getterName, LibraryElement library
); | |
| 10581 | |
| 10582 /** | |
| 10583 * Return the element representing the getter that results from looking up the
given getter in the | |
| 10584 * superclass of this class with respect to the given library, or `null` if th
e look up | |
| 10585 * fails. The behavior of this method is defined by the Dart Language Specific
ation in section | |
| 10586 * 12.15.1: <blockquote>The result of looking up getter (respectively setter)
<i>m</i> in class | |
| 10587 * <i>C</i> with respect to library <i>L</i> is: | |
| 10588 * * If <i>C</i> declares an instance getter (respectively setter) named <i>m<
/i> that is | |
| 10589 * accessible to <i>L</i>, then that getter (respectively setter) is the resul
t of the lookup. | |
| 10590 * Otherwise, if <i>C</i> has a superclass <i>S</i>, then the result of the lo
okup is the result | |
| 10591 * of looking up getter (respectively setter) <i>m</i> in <i>S</i> with respec
t to <i>L</i>. | |
| 10592 * Otherwise, we say that the lookup has failed. | |
| 10593 * </blockquote> | |
| 10594 * | |
| 10595 * @param getterName the name of the getter being looked up | |
| 10596 * @param library the library with respect to which the lookup is being perfor
med | |
| 10597 * @return the result of looking up the given getter in this class with respec
t to the given | |
| 10598 * library | |
| 10599 */ | |
| 10600 PropertyAccessorElement lookUpGetterInSuperclass(String getterName, LibraryEle
ment library); | |
| 10601 | |
| 10602 /** | |
| 10603 * Return the element representing the method that results from looking up the
given method in | |
| 10604 * this class with respect to the given library, or `null` if the look up fail
s. The | |
| 10605 * behavior of this method is defined by the Dart Language Specification in se
ction 12.15.1: | |
| 10606 * <blockquote> The result of looking up method <i>m</i> in class <i>C</i> wit
h respect to library | |
| 10607 * <i>L</i> is: | |
| 10608 * * If <i>C</i> declares an instance method named <i>m</i> that is accessible
to <i>L</i>, then | |
| 10609 * that method is the result of the lookup. Otherwise, if <i>C</i> has a super
class <i>S</i>, then | |
| 10610 * the result of the lookup is the result of looking up method <i>m</i> in <i>
S</i> with respect | |
| 10611 * to <i>L</i>. Otherwise, we say that the lookup has failed. | |
| 10612 * </blockquote> | |
| 10613 * | |
| 10614 * @param methodName the name of the method being looked up | |
| 10615 * @param library the library with respect to which the lookup is being perfor
med | |
| 10616 * @return the result of looking up the given method in this class with respec
t to the given | |
| 10617 * library | |
| 10618 */ | |
| 10619 MethodElement lookUpMethod(String methodName, LibraryElement library); | |
| 10620 | |
| 10621 /** | |
| 10622 * Return the element representing the method that results from looking up the
given method in the | |
| 10623 * superclass of this class with respect to the given library, or `null` if th
e look up | |
| 10624 * fails. The behavior of this method is defined by the Dart Language Specific
ation in section | |
| 10625 * 12.15.1: <blockquote> The result of looking up method <i>m</i> in class <i>
C</i> with respect | |
| 10626 * to library <i>L</i> is: | |
| 10627 * * If <i>C</i> declares an instance method named <i>m</i> that is accessible
to <i>L</i>, then | |
| 10628 * that method is the result of the lookup. Otherwise, if <i>C</i> has a super
class <i>S</i>, then | |
| 10629 * the result of the lookup is the result of looking up method <i>m</i> in <i>
S</i> with respect | |
| 10630 * to <i>L</i>. Otherwise, we say that the lookup has failed. | |
| 10631 * </blockquote> | |
| 10632 * | |
| 10633 * @param methodName the name of the method being looked up | |
| 10634 * @param library the library with respect to which the lookup is being perfor
med | |
| 10635 * @return the result of looking up the given method in this class with respec
t to the given | |
| 10636 * library | |
| 10637 */ | |
| 10638 MethodElement lookUpMethodInSuperclass(String methodName, LibraryElement libra
ry); | |
| 10639 | |
| 10640 /** | |
| 10641 * Return the element representing the setter that results from looking up the
given setter in | |
| 10642 * this class with respect to the given library, or `null` if the look up fail
s. The | |
| 10643 * behavior of this method is defined by the Dart Language Specification in se
ction 12.16: | |
| 10644 * <blockquote> The result of looking up getter (respectively setter) <i>m</i>
in class <i>C</i> | |
| 10645 * with respect to library <i>L</i> is: | |
| 10646 * * If <i>C</i> declares an instance getter (respectively setter) named <i>m<
/i> that is | |
| 10647 * accessible to <i>L</i>, then that getter (respectively setter) is the resul
t of the lookup. | |
| 10648 * Otherwise, if <i>C</i> has a superclass <i>S</i>, then the result of the lo
okup is the result | |
| 10649 * of looking up getter (respectively setter) <i>m</i> in <i>S</i> with respec
t to <i>L</i>. | |
| 10650 * Otherwise, we say that the lookup has failed. | |
| 10651 * </blockquote> | |
| 10652 * | |
| 10653 * @param setterName the name of the setter being looked up | |
| 10654 * @param library the library with respect to which the lookup is being perfor
med | |
| 10655 * @return the result of looking up the given setter in this class with respec
t to the given | |
| 10656 * library | |
| 10657 */ | |
| 10658 PropertyAccessorElement lookUpSetter(String setterName, LibraryElement library
); | |
| 10659 | |
| 10660 /** | |
| 10661 * Return the element representing the setter that results from looking up the
given setter in the | |
| 10662 * superclass of this class with respect to the given library, or `null` if th
e look up | |
| 10663 * fails. The behavior of this method is defined by the Dart Language Specific
ation in section | |
| 10664 * 12.16: <blockquote> The result of looking up getter (respectively setter) <
i>m</i> in class | |
| 10665 * <i>C</i> with respect to library <i>L</i> is: | |
| 10666 * * If <i>C</i> declares an instance getter (respectively setter) named <i>m<
/i> that is | |
| 10667 * accessible to <i>L</i>, then that getter (respectively setter) is the resul
t of the lookup. | |
| 10668 * Otherwise, if <i>C</i> has a superclass <i>S</i>, then the result of the lo
okup is the result | |
| 10669 * of looking up getter (respectively setter) <i>m</i> in <i>S</i> with respec
t to <i>L</i>. | |
| 10670 * Otherwise, we say that the lookup has failed. | |
| 10671 * </blockquote> | |
| 10672 * | |
| 10673 * @param setterName the name of the setter being looked up | |
| 10674 * @param library the library with respect to which the lookup is being perfor
med | |
| 10675 * @return the result of looking up the given setter in this class with respec
t to the given | |
| 10676 * library | |
| 10677 */ | |
| 10678 PropertyAccessorElement lookUpSetterInSuperclass(String setterName, LibraryEle
ment library); | |
| 10679 | |
| 10680 /** | |
| 10681 * Return the type resulting from substituting the given arguments for this ty
pe's parameters. | |
| 10682 * This is fully equivalent to `substitute(argumentTypes, getTypeArguments())`
. | |
| 10683 * | |
| 10684 * @param argumentTypes the actual type arguments being substituted for the ty
pe parameters | |
| 10685 * @return the result of performing the substitution | |
| 10686 */ | |
| 10687 InterfaceType substitute4(List<DartType> argumentTypes); | |
| 10688 | |
| 10689 @override | |
| 10690 InterfaceType substitute2(List<DartType> argumentTypes, List<DartType> paramet
erTypes); | |
| 10691 } | |
| 10692 | |
| 10693 /** | |
| 10694 * The interface `ParameterizedType` defines the behavior common to objects repr
esenting a | |
| 10695 * type with type parameters, such as a class or function type alias. | |
| 10696 */ | |
| 10697 abstract class ParameterizedType implements DartType { | |
| 10698 /** | |
| 10699 * Return an array containing the actual types of the type arguments. If this
type's element does | |
| 10700 * not have type parameters, then the array should be empty (although it is po
ssible for type | |
| 10701 * arguments to be erroneously declared). If the element has type parameters a
nd the actual type | |
| 10702 * does not explicitly include argument values, then the type "dynamic" will b
e automatically | |
| 10703 * provided. | |
| 10704 * | |
| 10705 * @return the actual types of the type arguments | |
| 10706 */ | |
| 10707 List<DartType> get typeArguments; | |
| 10708 | |
| 10709 /** | |
| 10710 * Return an array containing all of the type parameters declared for this typ
e. | |
| 10711 * | |
| 10712 * @return the type parameters declared for this type | |
| 10713 */ | |
| 10714 List<TypeParameterElement> get typeParameters; | |
| 10715 } | |
| 10716 | |
| 10717 /** | |
| 10718 * The interface `Type` defines the behavior of objects representing the declare
d type of | |
| 10719 * elements in the element model. | |
| 10720 */ | |
| 10721 abstract class DartType { | |
| 10722 /** | |
| 10723 * Return the name of this type as it should appear when presented to users in
contexts such as | |
| 10724 * error messages. | |
| 10725 * | |
| 10726 * @return the name of this type | |
| 10727 */ | |
| 10728 String get displayName; | |
| 10729 | |
| 10730 /** | |
| 10731 * Return the element representing the declaration of this type, or `null` if
the type has | |
| 10732 * not, or cannot, be associated with an element. The former case will occur i
f the element model | |
| 10733 * is not yet complete; the latter case will occur if this object represents a
n undefined type. | |
| 10734 * | |
| 10735 * @return the element representing the declaration of this type | |
| 10736 */ | |
| 10737 Element get element; | |
| 10738 | |
| 10739 /** | |
| 10740 * Return the least upper bound of this type and the given type, or `null` if
there is no | |
| 10741 * least upper bound. | |
| 10742 * | |
| 10743 * @param type the other type used to compute the least upper bound | |
| 10744 * @return the least upper bound of this type and the given type | |
| 10745 */ | |
| 10746 DartType getLeastUpperBound(DartType type); | |
| 10747 | |
| 10748 /** | |
| 10749 * Return the name of this type, or `null` if the type does not have a name, s
uch as when | |
| 10750 * the type represents the type of an unnamed function. | |
| 10751 * | |
| 10752 * @return the name of this type | |
| 10753 */ | |
| 10754 String get name; | |
| 10755 | |
| 10756 /** | |
| 10757 * Return `true` if this type is assignable to the given type. A type <i>T</i>
may be | |
| 10758 * assigned to a type <i>S</i>, written <i>T</i> ⇔ <i>S</i>, iff either <
i>T</i> <: <i>S</i> | |
| 10759 * or <i>S</i> <: <i>T</i>. | |
| 10760 * | |
| 10761 * @param type the type being compared with this type | |
| 10762 * @return `true` if this type is assignable to the given type | |
| 10763 */ | |
| 10764 bool isAssignableTo(DartType type); | |
| 10765 | |
| 10766 /** | |
| 10767 * Return `true` if this type represents the bottom type. | |
| 10768 * | |
| 10769 * @return `true` if this type represents the bottom type | |
| 10770 */ | |
| 10771 bool get isBottom; | |
| 10772 | |
| 10773 /** | |
| 10774 * Return `true` if this type represents the type 'Function' defined in the da
rt:core | |
| 10775 * library. | |
| 10776 * | |
| 10777 * @return `true` if this type represents the type 'Function' defined in the d
art:core | |
| 10778 * library | |
| 10779 */ | |
| 10780 bool get isDartCoreFunction; | |
| 10781 | |
| 10782 /** | |
| 10783 * Return `true` if this type represents the type 'dynamic'. | |
| 10784 * | |
| 10785 * @return `true` if this type represents the type 'dynamic' | |
| 10786 */ | |
| 10787 bool get isDynamic; | |
| 10788 | |
| 10789 /** | |
| 10790 * Return `true` if this type is more specific than the given type. | |
| 10791 * | |
| 10792 * @param type the type being compared with this type | |
| 10793 * @return `true` if this type is more specific than the given type | |
| 10794 */ | |
| 10795 bool isMoreSpecificThan(DartType type); | |
| 10796 | |
| 10797 /** | |
| 10798 * Return `true` if this type represents the type 'Object'. | |
| 10799 * | |
| 10800 * @return `true` if this type represents the type 'Object' | |
| 10801 */ | |
| 10802 bool get isObject; | |
| 10803 | |
| 10804 /** | |
| 10805 * Return `true` if this type is a subtype of the given type. | |
| 10806 * | |
| 10807 * @param type the type being compared with this type | |
| 10808 * @return `true` if this type is a subtype of the given type | |
| 10809 */ | |
| 10810 bool isSubtypeOf(DartType type); | |
| 10811 | |
| 10812 /** | |
| 10813 * Return `true` if this type is a supertype of the given type. A type <i>S</i
> is a | |
| 10814 * supertype of <i>T</i>, written <i>S</i> :> <i>T</i>, iff <i>T</i> is a subt
ype of <i>S</i>. | |
| 10815 * | |
| 10816 * @param type the type being compared with this type | |
| 10817 * @return `true` if this type is a supertype of the given type | |
| 10818 */ | |
| 10819 bool isSupertypeOf(DartType type); | |
| 10820 | |
| 10821 /** | |
| 10822 * Return `true` if this type represents the type 'void'. | |
| 10823 * | |
| 10824 * @return `true` if this type represents the type 'void' | |
| 10825 */ | |
| 10826 bool get isVoid; | |
| 10827 | |
| 10828 /** | |
| 10829 * Return the type resulting from substituting the given arguments for the giv
en parameters in | |
| 10830 * this type. The specification defines this operation in section 2: <blockquo
te> The notation | |
| 10831 * <i>[x<sub>1</sub>, ..., x<sub>n</sub>/y<sub>1</sub>, ..., y<sub>n</sub>]E</
i> denotes a copy of | |
| 10832 * <i>E</i> in which all occurrences of <i>y<sub>i</sub>, 1 <= i <= n</i> have
been replaced with | |
| 10833 * <i>x<sub>i</sub></i>.</blockquote> Note that, contrary to the specification
, this method will | |
| 10834 * not create a copy of this type if no substitutions were required, but will
return this type | |
| 10835 * directly. | |
| 10836 * | |
| 10837 * @param argumentTypes the actual type arguments being substituted for the pa
rameters | |
| 10838 * @param parameterTypes the parameters to be replaced | |
| 10839 * @return the result of performing the substitution | |
| 10840 */ | |
| 10841 DartType substitute2(List<DartType> argumentTypes, List<DartType> parameterTyp
es); | |
| 10842 } | |
| 10843 | |
| 10844 /** | |
| 10845 * The interface `TypeParameterType` defines the behavior of objects representin
g the type | |
| 10846 * introduced by a type parameter. | |
| 10847 */ | |
| 10848 abstract class TypeParameterType implements DartType { | |
| 10849 @override | |
| 10850 TypeParameterElement get element; | |
| 10851 } | |
| 10852 | |
| 10853 /** | |
| 10854 * The interface `VoidType` defines the behavior of the unique object representi
ng the type | 10811 * The interface `VoidType` defines the behavior of the unique object representi
ng the type |
| 10855 * `void`. | 10812 * `void`. |
| 10856 */ | 10813 */ |
| 10857 abstract class VoidType implements DartType { | 10814 abstract class VoidType implements DartType { |
| 10858 @override | 10815 @override |
| 10859 VoidType substitute2(List<DartType> argumentTypes, List<DartType> parameterTyp
es); | 10816 VoidType substitute2(List<DartType> argumentTypes, List<DartType> parameterTyp
es); |
| 10817 } |
| 10818 |
| 10819 /** |
| 10820 * The unique instance of the class `VoidTypeImpl` implements the type `void`. |
| 10821 */ |
| 10822 class VoidTypeImpl extends TypeImpl implements VoidType { |
| 10823 /** |
| 10824 * The unique instance of this class. |
| 10825 */ |
| 10826 static VoidTypeImpl _INSTANCE = new VoidTypeImpl(); |
| 10827 |
| 10828 /** |
| 10829 * Return the unique instance of this class. |
| 10830 * |
| 10831 * @return the unique instance of this class |
| 10832 */ |
| 10833 static VoidTypeImpl get instance => _INSTANCE; |
| 10834 |
| 10835 /** |
| 10836 * Prevent the creation of instances of this class. |
| 10837 */ |
| 10838 VoidTypeImpl() : super(null, Keyword.VOID.syntax); |
| 10839 |
| 10840 @override |
| 10841 bool operator ==(Object object) => identical(object, this); |
| 10842 |
| 10843 @override |
| 10844 int get hashCode => 2; |
| 10845 |
| 10846 @override |
| 10847 bool get isVoid => true; |
| 10848 |
| 10849 @override |
| 10850 VoidTypeImpl substitute2(List<DartType> argumentTypes, List<DartType> paramete
rTypes) => this; |
| 10851 |
| 10852 @override |
| 10853 bool internalEquals(Object object, Set<ElementPair> visitedElementPairs) => id
entical(object, this); |
| 10854 |
| 10855 @override |
| 10856 bool internalIsMoreSpecificThan(DartType type, bool withDynamic, Set<TypeImpl_
TypePair> visitedTypePairs) => isSubtypeOf(type); |
| 10857 |
| 10858 @override |
| 10859 bool internalIsSubtypeOf(DartType type, Set<TypeImpl_TypePair> visitedTypePair
s) => identical(type, this) || identical(type, DynamicTypeImpl.instance); |
| 10860 } | 10860 } |
| OLD | NEW |