| Index: pkg/analysis_server/lib/src/services/correction/util.dart
|
| diff --git a/pkg/analysis_server/lib/src/services/correction/util.dart b/pkg/analysis_server/lib/src/services/correction/util.dart
|
| index 445aab2ca47b0aaa79c5bd49aa8ede83a7ab34f1..8a357d696ba12a1b04d5334ba2f7bda3418cd9f6 100644
|
| --- a/pkg/analysis_server/lib/src/services/correction/util.dart
|
| +++ b/pkg/analysis_server/lib/src/services/correction/util.dart
|
| @@ -663,6 +663,17 @@ Expression stepUpNamedExpression(Expression expression) {
|
| return expression;
|
| }
|
|
|
| +/**
|
| + * Describes the location for a newly created [ClassMember].
|
| + */
|
| +class ClassMemberLocation {
|
| + final String prefix;
|
| + final int offset;
|
| + final String suffix;
|
| +
|
| + ClassMemberLocation(this.prefix, this.offset, this.suffix);
|
| +}
|
| +
|
| class CorrectionUtils {
|
| final CompilationUnit unit;
|
|
|
| @@ -1214,6 +1225,15 @@ class CorrectionUtils {
|
| _invertCondition0(expression)._source;
|
|
|
| /**
|
| + * Return `true` if the given [classDeclaration] has open '{' and close '}'
|
| + * at the same line, e.g. `class X {}`.
|
| + */
|
| + bool isClassWithEmptyBody(ClassDeclaration classDeclaration) {
|
| + return getLineThis(classDeclaration.leftBracket.offset) ==
|
| + getLineThis(classDeclaration.rightBracket.offset);
|
| + }
|
| +
|
| + /**
|
| * @return <code>true</code> if selection range contains only whitespace or comments
|
| */
|
| bool isJustWhitespaceOrComment(SourceRange range) {
|
| @@ -1226,6 +1246,57 @@ class CorrectionUtils {
|
| return TokenUtils.getTokens(trimmedText).isEmpty;
|
| }
|
|
|
| + ClassMemberLocation prepareNewClassMemberLocation(
|
| + ClassDeclaration classDeclaration,
|
| + bool shouldSkip(ClassMember existingMember)) {
|
| + String indent = getIndent(1);
|
| + // Find the last target member.
|
| + ClassMember targetMember = null;
|
| + List<ClassMember> members = classDeclaration.members;
|
| + for (ClassMember member in members) {
|
| + if (shouldSkip(member)) {
|
| + targetMember = member;
|
| + } else {
|
| + break;
|
| + }
|
| + }
|
| + // After the last target member.
|
| + if (targetMember != null) {
|
| + return new ClassMemberLocation(
|
| + endOfLine + endOfLine + indent, targetMember.end, '');
|
| + }
|
| + // At the beginning of the class.
|
| + String suffix = members.isNotEmpty || isClassWithEmptyBody(classDeclaration)
|
| + ? endOfLine
|
| + : '';
|
| + return new ClassMemberLocation(
|
| + endOfLine + indent, classDeclaration.leftBracket.end, suffix);
|
| + }
|
| +
|
| + ClassMemberLocation prepareNewConstructorLocation(
|
| + ClassDeclaration classDeclaration) {
|
| + return prepareNewClassMemberLocation(
|
| + classDeclaration,
|
| + (member) =>
|
| + member is FieldDeclaration || member is ConstructorDeclaration);
|
| + }
|
| +
|
| + ClassMemberLocation prepareNewFieldLocation(
|
| + ClassDeclaration classDeclaration) {
|
| + return prepareNewClassMemberLocation(
|
| + classDeclaration, (member) => member is FieldDeclaration);
|
| + }
|
| +
|
| + ClassMemberLocation prepareNewGetterLocation(
|
| + ClassDeclaration classDeclaration) {
|
| + return prepareNewClassMemberLocation(
|
| + classDeclaration,
|
| + (member) =>
|
| + member is FieldDeclaration ||
|
| + member is ConstructorDeclaration ||
|
| + member is MethodDeclaration && member.isGetter);
|
| + }
|
| +
|
| /**
|
| * Returns the source with indentation changed from [oldIndent] to
|
| * [newIndent], keeping indentation of lines relative to each other.
|
|
|