Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(156)

Side by Side Diff: pkg/analysis_server/lib/src/services/completion/statement/statement_completion.dart

Issue 2869083002: Convert server to use RangeFactory (Closed)
Patch Set: Created 3 years, 7 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
OLDNEW
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 library services.src.completion.statement; 5 library services.src.completion.statement;
6 6
7 import 'dart:async'; 7 import 'dart:async';
8 8
9 import 'package:analysis_server/protocol/protocol_generated.dart'; 9 import 'package:analysis_server/protocol/protocol_generated.dart';
10 import 'package:analysis_server/src/protocol_server.dart' hide Element; 10 import 'package:analysis_server/src/protocol_server.dart' hide Element;
11 import 'package:analysis_server/src/services/correction/source_buffer.dart'; 11 import 'package:analysis_server/src/services/correction/source_buffer.dart';
12 import 'package:analysis_server/src/services/correction/source_range.dart';
13 import 'package:analysis_server/src/services/correction/util.dart'; 12 import 'package:analysis_server/src/services/correction/util.dart';
14 import 'package:analyzer/dart/ast/ast.dart'; 13 import 'package:analyzer/dart/ast/ast.dart';
15 import 'package:analyzer/dart/ast/token.dart'; 14 import 'package:analyzer/dart/ast/token.dart';
16 import 'package:analyzer/dart/element/element.dart'; 15 import 'package:analyzer/dart/element/element.dart';
17 import 'package:analyzer/error/error.dart'; 16 import 'package:analyzer/error/error.dart';
18 import 'package:analyzer/error/error.dart' as engine; 17 import 'package:analyzer/error/error.dart' as engine;
19 import 'package:analyzer/src/dart/ast/utilities.dart'; 18 import 'package:analyzer/src/dart/ast/utilities.dart';
20 import 'package:analyzer/src/dart/error/hint_codes.dart'; 19 import 'package:analyzer/src/dart/error/hint_codes.dart';
21 import 'package:analyzer/src/dart/error/syntactic_errors.dart'; 20 import 'package:analyzer/src/dart/error/syntactic_errors.dart';
22 import 'package:analyzer/src/generated/engine.dart'; 21 import 'package:analyzer/src/generated/engine.dart';
23 import 'package:analyzer/src/generated/java_core.dart'; 22 import 'package:analyzer/src/generated/java_core.dart';
24 import 'package:analyzer/src/generated/source.dart'; 23 import 'package:analyzer/src/generated/source.dart';
24 import 'package:analyzer_plugin/utilities/range_factory.dart';
25 25
26 /** 26 /**
27 * An enumeration of possible statement completion kinds. 27 * An enumeration of possible statement completion kinds.
28 */ 28 */
29 class DartStatementCompletion { 29 class DartStatementCompletion {
30 static const NO_COMPLETION = 30 static const NO_COMPLETION =
31 const StatementCompletionKind('No_COMPLETION', 'No completion available'); 31 const StatementCompletionKind('No_COMPLETION', 'No completion available');
32 static const SIMPLE_ENTER = const StatementCompletionKind( 32 static const SIMPLE_ENTER = const StatementCompletionKind(
33 'SIMPLE_ENTER', "Insert a newline at the end of the current line"); 33 'SIMPLE_ENTER', "Insert a newline at the end of the current line");
34 static const SIMPLE_SEMICOLON = const StatementCompletionKind( 34 static const SIMPLE_SEMICOLON = const StatementCompletionKind(
(...skipping 325 matching lines...) Expand 10 before | Expand all | Expand 10 after
360 } 360 }
361 DoStatement statement = node; 361 DoStatement statement = node;
362 SourceBuilder sb = _sourceBuilderAfterKeyword(statement.doKeyword); 362 SourceBuilder sb = _sourceBuilderAfterKeyword(statement.doKeyword);
363 bool hasWhileKeyword = statement.whileKeyword.lexeme == "while"; 363 bool hasWhileKeyword = statement.whileKeyword.lexeme == "while";
364 int exitDelta = 0; 364 int exitDelta = 0;
365 if (!_statementHasValidBody(statement.doKeyword, statement.body)) { 365 if (!_statementHasValidBody(statement.doKeyword, statement.body)) {
366 String text = utils.getNodeText(statement.body); 366 String text = utils.getNodeText(statement.body);
367 int delta = 0; 367 int delta = 0;
368 if (text.startsWith(';')) { 368 if (text.startsWith(';')) {
369 delta = 1; 369 delta = 1;
370 _addReplaceEdit(rangeStartLength(statement.body.offset, delta), ''); 370 _addReplaceEdit(range.startLength(statement.body, delta), '');
371 if (hasWhileKeyword) { 371 if (hasWhileKeyword) {
372 text = utils.getNodeText(statement); 372 text = utils.getNodeText(statement);
373 if (text.indexOf(new RegExp(r'do\s*;\s*while')) == 0) { 373 if (text.indexOf(new RegExp(r'do\s*;\s*while')) == 0) {
374 int end = text.indexOf('while'); 374 int end = text.indexOf('while');
375 int start = text.indexOf(';') + 1; 375 int start = text.indexOf(';') + 1;
376 delta += end - start - 1; 376 delta += end - start - 1;
377 _addReplaceEdit( 377 _addReplaceEdit(
378 rangeStartLength(start + statement.offset, end - start), ' '); 378 new SourceRange(start + statement.offset, end - start), ' ');
379 } 379 }
380 } 380 }
381 sb = new SourceBuilder(file, sb.offset + delta); 381 sb = new SourceBuilder(file, sb.offset + delta);
382 sb.append(' '); 382 sb.append(' ');
383 } 383 }
384 _appendEmptyBraces(sb, 384 _appendEmptyBraces(sb,
385 !(hasWhileKeyword && _isSyntheticExpression(statement.condition))); 385 !(hasWhileKeyword && _isSyntheticExpression(statement.condition)));
386 if (delta != 0) { 386 if (delta != 0) {
387 exitDelta = sb.length - delta; 387 exitDelta = sb.length - delta;
388 } 388 }
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after
444 SourceBuilder sb = 444 SourceBuilder sb =
445 new SourceBuilder(file, forNode.rightParenthesis.offset + 1); 445 new SourceBuilder(file, forNode.rightParenthesis.offset + 1);
446 AstNode name = forNode.identifier; 446 AstNode name = forNode.identifier;
447 name ??= forNode.loopVariable; 447 name ??= forNode.loopVariable;
448 String src = utils.getNodeText(forNode); 448 String src = utils.getNodeText(forNode);
449 if (name == null) { 449 if (name == null) {
450 exitPosition = new Position(file, forNode.leftParenthesis.offset + 1); 450 exitPosition = new Position(file, forNode.leftParenthesis.offset + 1);
451 src = src.substring(forNode.leftParenthesis.offset - forNode.offset); 451 src = src.substring(forNode.leftParenthesis.offset - forNode.offset);
452 if (src.startsWith(new RegExp(r'\(\s*in\s*\)'))) { 452 if (src.startsWith(new RegExp(r'\(\s*in\s*\)'))) {
453 _addReplaceEdit( 453 _addReplaceEdit(
454 rangeStartEnd(forNode.leftParenthesis.offset + 1, 454 range.offsetEndIndex(forNode.leftParenthesis.offset + 1,
455 forNode.rightParenthesis.offset), 455 forNode.rightParenthesis.offset),
456 ' in '); 456 ' in ');
457 } else if (src.startsWith(new RegExp(r'\(\s*in'))) { 457 } else if (src.startsWith(new RegExp(r'\(\s*in'))) {
458 _addReplaceEdit( 458 _addReplaceEdit(
459 rangeStartEnd( 459 range.offsetEndIndex(
460 forNode.leftParenthesis.offset + 1, forNode.inKeyword.offset), 460 forNode.leftParenthesis.offset + 1, forNode.inKeyword.offset),
461 ' '); 461 ' ');
462 } 462 }
463 } else if (_isSyntheticExpression(forNode.iterable)) { 463 } else if (_isSyntheticExpression(forNode.iterable)) {
464 exitPosition = new Position(file, forNode.rightParenthesis.offset + 1); 464 exitPosition = new Position(file, forNode.rightParenthesis.offset + 1);
465 src = src.substring(forNode.inKeyword.offset - forNode.offset); 465 src = src.substring(forNode.inKeyword.offset - forNode.offset);
466 if (src.startsWith(new RegExp(r'in\s*\)'))) { 466 if (src.startsWith(new RegExp(r'in\s*\)'))) {
467 _addReplaceEdit( 467 _addReplaceEdit(
468 rangeStartEnd(forNode.inKeyword.offset + forNode.inKeyword.length, 468 range.offsetEndIndex(
469 forNode.inKeyword.offset + forNode.inKeyword.length,
469 forNode.rightParenthesis.offset), 470 forNode.rightParenthesis.offset),
470 ' '); 471 ' ');
471 } 472 }
472 } 473 }
473 if (!_statementHasValidBody(forNode.forKeyword, forNode.body)) { 474 if (!_statementHasValidBody(forNode.forKeyword, forNode.body)) {
474 sb.append(' '); 475 sb.append(' ');
475 _appendEmptyBraces(sb, exitPosition == null); 476 _appendEmptyBraces(sb, exitPosition == null);
476 } 477 }
477 _insertBuilder(sb); 478 _insertBuilder(sb);
478 _setCompletion(DartStatementCompletion.COMPLETE_FOR_EACH_STMT); 479 _setCompletion(DartStatementCompletion.COMPLETE_FOR_EACH_STMT);
(...skipping 24 matching lines...) Expand all
503 } else if (!forNode.leftSeparator.isSynthetic) { 504 } else if (!forNode.leftSeparator.isSynthetic) {
504 if (_isSyntheticExpression(forNode.condition)) { 505 if (_isSyntheticExpression(forNode.condition)) {
505 exitPosition = _newPosition(forNode.leftSeparator.offset + 1); 506 exitPosition = _newPosition(forNode.leftSeparator.offset + 1);
506 String text = utils 507 String text = utils
507 .getNodeText(forNode) 508 .getNodeText(forNode)
508 .substring(forNode.leftSeparator.offset - forNode.offset); 509 .substring(forNode.leftSeparator.offset - forNode.offset);
509 if (text.startsWith(new RegExp(r';\s*\)'))) { 510 if (text.startsWith(new RegExp(r';\s*\)'))) {
510 // emptyCondition 511 // emptyCondition
511 int end = text.indexOf(')'); 512 int end = text.indexOf(')');
512 sb = new SourceBuilder(file, forNode.leftSeparator.offset); 513 sb = new SourceBuilder(file, forNode.leftSeparator.offset);
513 _addReplaceEdit(rangeStartLength(sb.offset, end), '; ; '); 514 _addReplaceEdit(new SourceRange(sb.offset, end), '; ; ');
514 delta = end - '; '.length; 515 delta = end - '; '.length;
515 } else { 516 } else {
516 // emptyInitializersEmptyCondition 517 // emptyInitializersEmptyCondition
517 exitPosition = _newPosition(forNode.rightParenthesis.offset); 518 exitPosition = _newPosition(forNode.rightParenthesis.offset);
518 sb = new SourceBuilder(file, forNode.rightParenthesis.offset); 519 sb = new SourceBuilder(file, forNode.rightParenthesis.offset);
519 } 520 }
520 } else { 521 } else {
521 // emptyUpdaters 522 // emptyUpdaters
522 exitPosition = _newPosition(forNode.rightSeparator.offset); 523 exitPosition = _newPosition(forNode.rightSeparator.offset);
523 sb = new SourceBuilder(file, forNode.rightSeparator.offset); 524 sb = new SourceBuilder(file, forNode.rightSeparator.offset);
524 _addReplaceEdit(rangeStartLength(sb.offset, 0), '; '); 525 _addReplaceEdit(new SourceRange(sb.offset, 0), '; ');
525 delta = -'; '.length; 526 delta = -'; '.length;
526 } 527 }
527 } else if (_isSyntheticExpression(forNode.initialization)) { 528 } else if (_isSyntheticExpression(forNode.initialization)) {
528 // emptyInitializers 529 // emptyInitializers
529 exitPosition = _newPosition(forNode.rightParenthesis.offset); 530 exitPosition = _newPosition(forNode.rightParenthesis.offset);
530 sb = new SourceBuilder(file, forNode.rightParenthesis.offset); 531 sb = new SourceBuilder(file, forNode.rightParenthesis.offset);
531 } else { 532 } else {
532 int start = forNode.condition.offset + forNode.condition.length; 533 int start = forNode.condition.offset + forNode.condition.length;
533 String text = 534 String text =
534 utils.getNodeText(forNode).substring(start - forNode.offset); 535 utils.getNodeText(forNode).substring(start - forNode.offset);
535 if (text.startsWith(new RegExp(r'\s*\)'))) { 536 if (text.startsWith(new RegExp(r'\s*\)'))) {
536 // missingLeftSeparator 537 // missingLeftSeparator
537 int end = text.indexOf(')'); 538 int end = text.indexOf(')');
538 sb = new SourceBuilder(file, start); 539 sb = new SourceBuilder(file, start);
539 _addReplaceEdit(rangeStartLength(start, end), '; '); 540 _addReplaceEdit(new SourceRange(start, end), '; ');
540 delta = end - '; '.length; 541 delta = end - '; '.length;
541 exitPosition = new Position(file, start); 542 exitPosition = new Position(file, start);
542 } else { 543 } else {
543 // Not possible; any comment following init is attached to init. 544 // Not possible; any comment following init is attached to init.
544 exitPosition = _newPosition(forNode.rightParenthesis.offset); 545 exitPosition = _newPosition(forNode.rightParenthesis.offset);
545 sb = new SourceBuilder(file, forNode.rightParenthesis.offset); 546 sb = new SourceBuilder(file, forNode.rightParenthesis.offset);
546 } 547 }
547 } 548 }
548 } 549 }
549 if (!_statementHasValidBody(forNode.forKeyword, forNode.body)) { 550 if (!_statementHasValidBody(forNode.forKeyword, forNode.body)) {
(...skipping 365 matching lines...) Expand 10 before | Expand all | Expand 10 after
915 LinkedEditGroup group = linkedPositionGroups[groupId]; 916 LinkedEditGroup group = linkedPositionGroups[groupId];
916 if (group == null) { 917 if (group == null) {
917 group = new LinkedEditGroup.empty(); 918 group = new LinkedEditGroup.empty();
918 linkedPositionGroups[groupId] = group; 919 linkedPositionGroups[groupId] = group;
919 } 920 }
920 return group; 921 return group;
921 } 922 }
922 923
923 void _insertBuilder(SourceBuilder builder, [int length = 0]) { 924 void _insertBuilder(SourceBuilder builder, [int length = 0]) {
924 { 925 {
925 SourceRange range = rangeStartLength(builder.offset, length); 926 SourceRange range = new SourceRange(builder.offset, length);
926 String text = builder.toString(); 927 String text = builder.toString();
927 _addReplaceEdit(range, text); 928 _addReplaceEdit(range, text);
928 } 929 }
929 // add linked positions 930 // add linked positions
930 builder.linkedPositionGroups.forEach((String id, LinkedEditGroup group) { 931 builder.linkedPositionGroups.forEach((String id, LinkedEditGroup group) {
931 LinkedEditGroup fixGroup = _getLinkedPosition(id); 932 LinkedEditGroup fixGroup = _getLinkedPosition(id);
932 group.positions.forEach((Position position) { 933 group.positions.forEach((Position position) {
933 fixGroup.addPosition(position, group.length); 934 fixGroup.addPosition(position, group.length);
934 }); 935 });
935 group.suggestions.forEach((LinkedEditSuggestion suggestion) { 936 group.suggestions.forEach((LinkedEditSuggestion suggestion) {
(...skipping 88 matching lines...) Expand 10 before | Expand all | Expand 10 after
1024 final Token keyword; 1025 final Token keyword;
1025 final Token leftParenthesis, rightParenthesis; 1026 final Token leftParenthesis, rightParenthesis;
1026 final Expression condition; 1027 final Expression condition;
1027 final Statement block; 1028 final Statement block;
1028 1029
1029 _KeywordConditionBlockStructure(this.keyword, this.leftParenthesis, 1030 _KeywordConditionBlockStructure(this.keyword, this.leftParenthesis,
1030 this.condition, this.rightParenthesis, this.block); 1031 this.condition, this.rightParenthesis, this.block);
1031 1032
1032 int get offset => keyword.offset; 1033 int get offset => keyword.offset;
1033 } 1034 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698