Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright (c) 2017, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2017, 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 /** | 5 /** |
| 6 * A collection of utility methods used by completion contributors. | 6 * A collection of utility methods used by completion contributors. |
| 7 */ | 7 */ |
| 8 import 'package:analysis_server/plugin/protocol/protocol.dart' as protocol | 8 import 'package:analysis_server/plugin/protocol/protocol.dart' as protocol |
| 9 show Element, ElementKind; | 9 show Element, ElementKind; |
| 10 import 'package:analysis_server/src/ide_options.dart'; | |
| 10 import 'package:analysis_server/src/protocol_server.dart' | 11 import 'package:analysis_server/src/protocol_server.dart' |
| 11 show CompletionSuggestion, CompletionSuggestionKind, Location; | 12 show CompletionSuggestion, CompletionSuggestionKind, Location; |
| 12 import 'package:analysis_server/src/provisional/completion/dart/completion_dart. dart'; | 13 import 'package:analysis_server/src/provisional/completion/dart/completion_dart. dart'; |
| 14 import 'package:analysis_server/src/services/correction/flutter_util.dart'; | |
| 13 import 'package:analyzer/dart/ast/ast.dart'; | 15 import 'package:analyzer/dart/ast/ast.dart'; |
| 14 import 'package:analyzer/dart/ast/standard_ast_factory.dart'; | 16 import 'package:analyzer/dart/ast/standard_ast_factory.dart'; |
| 15 import 'package:analyzer/dart/ast/token.dart'; | 17 import 'package:analyzer/dart/ast/token.dart'; |
| 16 import 'package:analyzer/dart/element/element.dart'; | 18 import 'package:analyzer/dart/element/element.dart'; |
| 19 import 'package:analyzer/dart/element/type.dart'; | |
| 17 import 'package:analyzer/src/dart/ast/token.dart'; | 20 import 'package:analyzer/src/dart/ast/token.dart'; |
| 18 import 'package:analyzer/src/generated/source.dart'; | 21 import 'package:analyzer/src/generated/source.dart'; |
| 19 | 22 |
| 20 /** | 23 /** |
| 21 * The name of the type `dynamic`; | 24 * The name of the type `dynamic`; |
| 22 */ | 25 */ |
| 23 const DYNAMIC = 'dynamic'; | 26 const DYNAMIC = 'dynamic'; |
| 24 | 27 |
| 25 /** | 28 /** |
| 26 * A marker used in place of `null` when a function has no return type. | 29 * A marker used in place of `null` when a function has no return type. |
| 27 */ | 30 */ |
| 28 final TypeName NO_RETURN_TYPE = astFactory.typeName( | 31 final TypeName NO_RETURN_TYPE = astFactory.typeName( |
| 29 astFactory.simpleIdentifier(new StringToken(TokenType.IDENTIFIER, '', 0)), | 32 astFactory.simpleIdentifier(new StringToken(TokenType.IDENTIFIER, '', 0)), |
| 30 null); | 33 null); |
| 31 | 34 |
| 32 /** | 35 /** |
| 33 * Add default argument list text and ranges based on the given [requiredParams] | 36 * Add default argument list text and ranges based on the given [requiredParams] |
| 34 * and [namedParams]. | 37 * and [namedParams]. |
| 35 */ | 38 */ |
| 36 void addDefaultArgDetails( | 39 void addDefaultArgDetails( |
| 37 CompletionSuggestion suggestion, | 40 CompletionSuggestion suggestion, |
| 41 Element element, | |
| 38 Iterable<ParameterElement> requiredParams, | 42 Iterable<ParameterElement> requiredParams, |
| 39 Iterable<ParameterElement> namedParams) { | 43 Iterable<ParameterElement> namedParams, |
| 44 IdeOptions options) { | |
| 40 StringBuffer sb = new StringBuffer(); | 45 StringBuffer sb = new StringBuffer(); |
| 41 List<int> ranges = <int>[]; | 46 List<int> ranges = <int>[]; |
| 42 | 47 |
| 43 int offset; | 48 int offset; |
| 44 | 49 |
| 45 for (ParameterElement param in requiredParams) { | 50 for (ParameterElement param in requiredParams) { |
| 46 if (sb.isNotEmpty) { | 51 if (sb.isNotEmpty) { |
| 47 sb.write(', '); | 52 sb.write(', '); |
| 48 } | 53 } |
| 49 offset = sb.length; | 54 offset = sb.length; |
| 50 String name = param.name; | 55 String name = param.name; |
| 51 sb.write(name); | 56 sb.write(name); |
| 52 ranges.addAll([offset, name.length]); | 57 ranges.addAll([offset, name.length]); |
| 53 } | 58 } |
| 54 | 59 |
| 55 for (ParameterElement param in namedParams) { | 60 for (ParameterElement param in namedParams) { |
| 56 if (param.isRequired) { | 61 if (param.isRequired) { |
| 57 if (sb.isNotEmpty) { | 62 if (sb.isNotEmpty) { |
| 58 sb.write(', '); | 63 sb.write(', '); |
| 59 } | 64 } |
| 60 String name = param.name; | 65 String name = param.name; |
| 61 sb.write('$name: '); | 66 sb.write('$name: '); |
| 62 offset = sb.length; | 67 offset = sb.length; |
| 63 String defaultValue = _getDefaultValue(param); | 68 String defaultValue = _getDefaultValue(param); |
| 64 sb.write(defaultValue); | 69 sb.write(defaultValue); |
| 65 ranges.addAll([offset, defaultValue.length]); | 70 ranges.addAll([offset, defaultValue.length]); |
| 66 } | 71 } |
| 67 } | 72 } |
| 68 | 73 |
| 74 //TODO(pq): generalize and unify with _getDefaultValue | |
| 75 if (options?.generateFlutterWidgetChildrenBoilerPlate == true) { | |
|
Brian Wilkerson
2017/03/22 22:05:46
I think I'd just make it mandatory to pass in a no
| |
| 76 if (element is ConstructorElement) { | |
| 77 ConstructorElement constructorElement = element; | |
| 78 ClassElement classElement = constructorElement.enclosingElement; | |
| 79 if (isFlutterWidget(classElement)) { | |
| 80 for (ParameterElement param in constructorElement.parameters) { | |
| 81 if (param.name == 'children') { | |
| 82 DartType type = param.type; | |
| 83 if (type is InterfaceType && _isDartList(type)) { | |
| 84 InterfaceType interfaceType = type; | |
| 85 List<DartType> typeArguments = interfaceType.typeArguments; | |
| 86 if (typeArguments.length == 1) { | |
| 87 if (sb.isNotEmpty) { | |
| 88 sb.write(', '); | |
| 89 } | |
| 90 offset = sb.length; | |
| 91 sb.write('children: <${typeArguments.first.name}>[]'); | |
| 92 } | |
| 93 } | |
| 94 } | |
| 95 } | |
| 96 } | |
| 97 } | |
| 98 } | |
| 99 | |
| 69 suggestion.defaultArgumentListString = sb.isNotEmpty ? sb.toString() : null; | 100 suggestion.defaultArgumentListString = sb.isNotEmpty ? sb.toString() : null; |
| 70 suggestion.defaultArgumentListTextRanges = ranges.isNotEmpty ? ranges : null; | 101 suggestion.defaultArgumentListTextRanges = ranges.isNotEmpty ? ranges : null; |
| 71 } | 102 } |
| 72 | 103 |
| 73 /** | 104 /** |
| 74 * Create a new protocol Element for inclusion in a completion suggestion. | 105 * Create a new protocol Element for inclusion in a completion suggestion. |
| 75 */ | 106 */ |
| 76 protocol.Element createLocalElement( | 107 protocol.Element createLocalElement( |
| 77 Source source, protocol.ElementKind kind, SimpleIdentifier id, | 108 Source source, protocol.ElementKind kind, SimpleIdentifier id, |
| 78 {String parameters, | 109 {String parameters, |
| (...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 192 //TODO (danrubel) include type arguments | 223 //TODO (danrubel) include type arguments |
| 193 } | 224 } |
| 194 return name; | 225 return name; |
| 195 } else if (type is GenericFunctionType) { | 226 } else if (type is GenericFunctionType) { |
| 196 // TODO(brianwilkerson) Implement this. | 227 // TODO(brianwilkerson) Implement this. |
| 197 } | 228 } |
| 198 return DYNAMIC; | 229 return DYNAMIC; |
| 199 } | 230 } |
| 200 | 231 |
| 201 String _getDefaultValue(ParameterElement param) => 'null'; | 232 String _getDefaultValue(ParameterElement param) => 'null'; |
| 233 | |
| 234 bool _isDartList(DartType type) { | |
| 235 ClassElement element = type.element; | |
| 236 if (element != null) { | |
| 237 return element.name == "List" && element.library.isDartCore; | |
| 238 } | |
| 239 return false; | |
| 240 } | |
| OLD | NEW |