diff --git a/src/EditorFeatures/CSharp/Formatting/CSharpEditorFormattingService.cs b/src/EditorFeatures/CSharp/Formatting/CSharpEditorFormattingService.cs index 1887ee71c238b3750db244d09ecb87c285cdae8b..3cbcb7753ff71647325b4d0ac926ee7198f13ad0 100644 --- a/src/EditorFeatures/CSharp/Formatting/CSharpEditorFormattingService.cs +++ b/src/EditorFeatures/CSharp/Formatting/CSharpEditorFormattingService.cs @@ -131,7 +131,7 @@ private IEnumerable GetFormattingRules(Document document public async Task> GetFormattingChangesOnReturnAsync(Document document, int caretPosition, CancellationToken cancellationToken) { var options = await document.GetOptionsAsync(cancellationToken).ConfigureAwait(false); - if (!options.GetOption(FeatureOnOffOptions.AutoFormattingOnReturn)) + if (!options.GetOption(FormattingOptions.AutoFormattingOnReturn)) { return null; } diff --git a/src/EditorFeatures/CSharp/Formatting/Indentation/SmartTokenFormatterCommandHandler.cs b/src/EditorFeatures/CSharp/Formatting/Indentation/SmartTokenFormatterCommandHandler.cs index c975c06356144ba74226225bd319a12d619e9c69..2190453da05b9a0cd5d35cbda3c720c0411d89a4 100644 --- a/src/EditorFeatures/CSharp/Formatting/Indentation/SmartTokenFormatterCommandHandler.cs +++ b/src/EditorFeatures/CSharp/Formatting/Indentation/SmartTokenFormatterCommandHandler.cs @@ -5,6 +5,7 @@ using System.Linq; using System.Threading; using Microsoft.CodeAnalysis.CSharp; +using Microsoft.CodeAnalysis.CSharp.Indentation; using Microsoft.CodeAnalysis.CSharp.Syntax; using Microsoft.CodeAnalysis.Editor.Implementation.Formatting.Indentation; using Microsoft.CodeAnalysis.Formatting; diff --git a/src/EditorFeatures/CSharp/Formatting/Indentation/WhitespaceExtensions.cs b/src/EditorFeatures/CSharp/Formatting/Indentation/WhitespaceExtensions.cs deleted file mode 100644 index bf7ffc4dc0e3f2dc55fde61efed3d35290f61470..0000000000000000000000000000000000000000 --- a/src/EditorFeatures/CSharp/Formatting/Indentation/WhitespaceExtensions.cs +++ /dev/null @@ -1,15 +0,0 @@ -// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. - - -namespace Microsoft.CodeAnalysis.Editor.CSharp.Formatting.Indentation -{ - internal static class WhitespaceExtensions - { -#if false - public static bool IsFirstTokenOnLine(this SyntaxToken token, ITextSnapshot snapshot) - { - return token.IsFirstTokenOnLine(snapshot); - } -#endif - } -} diff --git a/src/EditorFeatures/CSharp/SplitStringLiteral/SplitStringLiteralCommandHandler.StringSplitter.cs b/src/EditorFeatures/CSharp/SplitStringLiteral/SplitStringLiteralCommandHandler.StringSplitter.cs index 2c69c027a2659afefe2d2addf052aa7965dd8510..a537b55afc02a69886a3ce425289f4b0097bac61 100644 --- a/src/EditorFeatures/CSharp/SplitStringLiteral/SplitStringLiteralCommandHandler.StringSplitter.cs +++ b/src/EditorFeatures/CSharp/SplitStringLiteral/SplitStringLiteralCommandHandler.StringSplitter.cs @@ -1,5 +1,4 @@ -using System; -using System.Linq; +using System.Linq; using System.Threading; using Microsoft.CodeAnalysis.CSharp; using Microsoft.CodeAnalysis.CSharp.Syntax; @@ -150,7 +149,7 @@ private string GetIndentString(SyntaxNode newRoot) { var newDocument = Document.WithSyntaxRoot(newRoot); - var indentationService = (IBlankLineIndentationService)newDocument.GetLanguageService(); + var indentationService = newDocument.GetLanguageService(); var originalLineNumber = SourceText.Lines.GetLineFromPosition(CursorPosition).LineNumber; var desiredIndentation = indentationService.GetBlankLineIndentation( diff --git a/src/EditorFeatures/CSharp/Wrapping/BinaryExpression/CSharpBinaryExpressionWrapper.cs b/src/EditorFeatures/CSharp/Wrapping/BinaryExpression/CSharpBinaryExpressionWrapper.cs index 79ea92f7410c5072c0543f3e6d209173d82dc930..fa7207af4a4058741e7ff510a3da0781be505da3 100644 --- a/src/EditorFeatures/CSharp/Wrapping/BinaryExpression/CSharpBinaryExpressionWrapper.cs +++ b/src/EditorFeatures/CSharp/Wrapping/BinaryExpression/CSharpBinaryExpressionWrapper.cs @@ -2,7 +2,7 @@ using Microsoft.CodeAnalysis.CSharp; using Microsoft.CodeAnalysis.CSharp.Syntax; -using Microsoft.CodeAnalysis.Editor.CSharp.Formatting.Indentation; +using Microsoft.CodeAnalysis.CSharp.Indentation; using Microsoft.CodeAnalysis.Editor.Wrapping.BinaryExpression; namespace Microsoft.CodeAnalysis.Editor.CSharp.Wrapping.BinaryExpression diff --git a/src/EditorFeatures/CSharp/Wrapping/SeparatedSyntaxList/AbstractCSharpSeparatedSyntaxListWrapper.cs b/src/EditorFeatures/CSharp/Wrapping/SeparatedSyntaxList/AbstractCSharpSeparatedSyntaxListWrapper.cs index e824e4cbb7d34aa2c8c1a0516804af8ee5559cf1..acaaaaf8e60a7e99125c435917e6d90ffa3e989d 100644 --- a/src/EditorFeatures/CSharp/Wrapping/SeparatedSyntaxList/AbstractCSharpSeparatedSyntaxListWrapper.cs +++ b/src/EditorFeatures/CSharp/Wrapping/SeparatedSyntaxList/AbstractCSharpSeparatedSyntaxListWrapper.cs @@ -1,7 +1,6 @@ // Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. -using Microsoft.CodeAnalysis.Editor; -using Microsoft.CodeAnalysis.Editor.CSharp.Formatting.Indentation; +using Microsoft.CodeAnalysis.CSharp.Indentation; using Microsoft.CodeAnalysis.Editor.Wrapping.SeparatedSyntaxList; namespace Microsoft.CodeAnalysis.CSharp.Editor.Wrapping.SeparatedSyntaxList diff --git a/src/EditorFeatures/CSharpTest/Formatting/Indentation/SmartIndenterEnterOnTokenTests.cs b/src/EditorFeatures/CSharpTest/Formatting/Indentation/SmartIndenterEnterOnTokenTests.cs index ebca590cbcfe73fbd8f4980237e3f666ae753e03..2ff3e51c083c336cf437cf7f39812f8fe1aed7f5 100644 --- a/src/EditorFeatures/CSharpTest/Formatting/Indentation/SmartIndenterEnterOnTokenTests.cs +++ b/src/EditorFeatures/CSharpTest/Formatting/Indentation/SmartIndenterEnterOnTokenTests.cs @@ -3,8 +3,8 @@ using System.Linq; using System.Threading; using System.Threading.Tasks; +using Microsoft.CodeAnalysis.CSharp.Indentation; using Microsoft.CodeAnalysis.CSharp.Syntax; -using Microsoft.CodeAnalysis.Editor.CSharp.Formatting.Indentation; using Microsoft.CodeAnalysis.Editor.UnitTests.Workspaces; using Microsoft.CodeAnalysis.Formatting; using Microsoft.CodeAnalysis.Test.Utilities; diff --git a/src/EditorFeatures/Core/Implementation/Formatting/Indentation/AbstractSmartTokenFormatterCommandHandler.cs b/src/EditorFeatures/Core/Implementation/Formatting/Indentation/AbstractSmartTokenFormatterCommandHandler.cs index 4b2570d4eb0fc98273182180c07c111d774dda2b..78a6f5f2c3430234bf9911dbd3744795cbe5a1be 100644 --- a/src/EditorFeatures/Core/Implementation/Formatting/Indentation/AbstractSmartTokenFormatterCommandHandler.cs +++ b/src/EditorFeatures/Core/Implementation/Formatting/Indentation/AbstractSmartTokenFormatterCommandHandler.cs @@ -8,6 +8,7 @@ using Microsoft.CodeAnalysis.Editor.Shared.Utilities; using Microsoft.CodeAnalysis.Formatting; using Microsoft.CodeAnalysis.Formatting.Rules; +using Microsoft.CodeAnalysis.Indentation; using Microsoft.CodeAnalysis.Options; using Microsoft.CodeAnalysis.Shared.Extensions; using Microsoft.CodeAnalysis.Text; @@ -139,7 +140,7 @@ internal void ExecuteCommandWorker(ReturnKeyCommandArgs args, CancellationToken return; } - var indentationService = document.GetLanguageService(); + var indentationService = document.GetLanguageService(); var indentation = indentationService.GetDesiredIndentation(document, currentPosition.GetContainingLine().LineNumber, cancellationToken); diff --git a/src/EditorFeatures/Core/Implementation/SmartIndent/IBlankLineIndentationService.cs b/src/EditorFeatures/Core/Implementation/SmartIndent/IBlankLineIndentationService.cs deleted file mode 100644 index 1d4c36a6f319313cc56818d524c880817178d9fb..0000000000000000000000000000000000000000 --- a/src/EditorFeatures/Core/Implementation/SmartIndent/IBlankLineIndentationService.cs +++ /dev/null @@ -1,23 +0,0 @@ -// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. - -using System.Threading; -using Microsoft.CodeAnalysis.Formatting; - -namespace Microsoft.CodeAnalysis.Editor -{ - internal interface IBlankLineIndentationService - { - /// - /// Determines indentation for a blank line (i.e. after hitting enter at the end of a line, - /// or after moving to a blank line). - /// - /// Specifically, this function operates as if the line specified by - /// is blank. The actual contents of the line do not matter. All indentation information is - /// determined from the previous lines in the document. - /// - /// This function will always succeed. - /// - IndentationResult GetBlankLineIndentation( - Document document, int lineNumber, FormattingOptions.IndentStyle indentStyle, CancellationToken cancellationToken); - } -} diff --git a/src/EditorFeatures/Core/Implementation/SmartIndent/IIndentationService.cs b/src/EditorFeatures/Core/Implementation/SmartIndent/IIndentationService.cs index 92ff2e89b03c14d3a96a97b0ab544037a59d02dc..4997c593a575d33827ea025dc361d830764280fb 100644 --- a/src/EditorFeatures/Core/Implementation/SmartIndent/IIndentationService.cs +++ b/src/EditorFeatures/Core/Implementation/SmartIndent/IIndentationService.cs @@ -1,5 +1,6 @@ // Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. +using System; using System.Threading; using System.Threading.Tasks; using Microsoft.CodeAnalysis.Host; @@ -18,6 +19,7 @@ namespace Microsoft.CodeAnalysis.Editor /// current line. With this tuple, both forms can be expressed, and the implementor does not /// have to convert from one to the other. /// + [Obsolete("Use Microsoft.CodeAnalysis.Indentation.IndentationResult instead.")] internal struct IndentationResult { /// @@ -36,13 +38,18 @@ public IndentationResult(int basePosition, int offset) : this() this.BasePosition = basePosition; this.Offset = offset; } + + public static implicit operator Indentation.IndentationResult(IndentationResult result) + => new Indentation.IndentationResult(result.BasePosition, result.Offset); } + [Obsolete("Use Microsoft.CodeAnalysis.Indentation.IIndentationService instead.")] internal interface IIndentationService : ILanguageService { Task GetDesiredIndentation(Document document, int lineNumber, CancellationToken cancellationToken); } + [Obsolete("Use Microsoft.CodeAnalysis.Indentation.IIndentationService instead.")] internal interface ISynchronousIndentationService : ILanguageService { /// diff --git a/src/EditorFeatures/Core/Implementation/SmartIndent/SmartIndent.cs b/src/EditorFeatures/Core/Implementation/SmartIndent/SmartIndent.cs index 72f0c9cc59b16546a329d1e5a205df4c9ae4114e..bb44edc20585f317eca09d2191094cb9f85f59a7 100644 --- a/src/EditorFeatures/Core/Implementation/SmartIndent/SmartIndent.cs +++ b/src/EditorFeatures/Core/Implementation/SmartIndent/SmartIndent.cs @@ -2,7 +2,7 @@ using System; using System.Threading; -using Microsoft.CodeAnalysis.Editor.Shared.Extensions; +using Microsoft.CodeAnalysis.Indentation; using Microsoft.CodeAnalysis.Internal.Log; using Microsoft.CodeAnalysis.Shared.Extensions; using Microsoft.CodeAnalysis.Text; @@ -10,6 +10,10 @@ using Microsoft.VisualStudio.Text.Editor; using Roslyn.Utilities; +using NewIndentationService = Microsoft.CodeAnalysis.Indentation.IIndentationService; +using OldIndentationService = Microsoft.CodeAnalysis.Editor.IIndentationService; +using OldSynchronousIndentationService = Microsoft.CodeAnalysis.Editor.ISynchronousIndentationService; + namespace Microsoft.CodeAnalysis.Editor.Implementation.SmartIndent { internal partial class SmartIndent : ISmartIndent @@ -40,21 +44,39 @@ public void Dispose() using (Logger.LogBlock(FunctionId.SmartIndentation_Start, cancellationToken)) { var document = lineToBeIndented.Snapshot.GetOpenDocumentInCurrentContextWithChanges(); - var syncService = document?.GetLanguageService(); + if (document == null) + { + return null; + } - if (syncService != null) + // First, try to go through the normal feature-layer indentation service. + var newService = document.GetLanguageService(); + if (newService != null) { - var result = syncService.GetDesiredIndentation(document, lineToBeIndented.LineNumber, cancellationToken); + var result = newService.GetDesiredIndentation(document, lineToBeIndented.LineNumber, cancellationToken); return result?.GetIndentation(_textView, lineToBeIndented); } - var asyncService = document?.GetLanguageService(); - if (asyncService != null) + // If we don't have a feature-layer service, try to fall back to the legacy + // editor-feature-layer interfaces. + +#pragma warning disable CS0618 // Type or member is obsolete + var oldSyncService = document.GetLanguageService(); + if (oldSyncService != null) { - var result = asyncService.GetDesiredIndentation(document, lineToBeIndented.LineNumber, cancellationToken).WaitAndGetResult(cancellationToken); + var result = (Indentation.IndentationResult?)oldSyncService.GetDesiredIndentation(document, lineToBeIndented.LineNumber, cancellationToken); return result?.GetIndentation(_textView, lineToBeIndented); } + var oldAsyncService = document.GetLanguageService(); + if (oldAsyncService != null) + { + var result = (Indentation.IndentationResult?)oldAsyncService.GetDesiredIndentation(document, lineToBeIndented.LineNumber, cancellationToken).WaitAndGetResult(cancellationToken); + return result?.GetIndentation(_textView, lineToBeIndented); + } +#pragma warning restore CS0618 // Type or member is obsolete + + return null; } } diff --git a/src/EditorFeatures/Core/Shared/Extensions/SmartIndentExtensions.cs b/src/EditorFeatures/Core/Shared/Extensions/SmartIndentExtensions.cs index 4a94941bffae1989ef02637b960309806a74d112..390c8f101bd20c2f50ce591a99c20c87c143ff68 100644 --- a/src/EditorFeatures/Core/Shared/Extensions/SmartIndentExtensions.cs +++ b/src/EditorFeatures/Core/Shared/Extensions/SmartIndentExtensions.cs @@ -4,7 +4,7 @@ using Microsoft.VisualStudio.Text; using Microsoft.VisualStudio.Text.Editor; -namespace Microsoft.CodeAnalysis.Editor.Shared.Extensions +namespace Microsoft.CodeAnalysis.Indentation { internal static class SmartIndentExtensions { diff --git a/src/EditorFeatures/Core/Shared/Options/FeatureOnOffOptions.cs b/src/EditorFeatures/Core/Shared/Options/FeatureOnOffOptions.cs index ebe63805e47f9a9100c45d3d31ebdccf43cae516..796966c6c71eb250ec5e81672eb0f5b513c57f60 100644 --- a/src/EditorFeatures/Core/Shared/Options/FeatureOnOffOptions.cs +++ b/src/EditorFeatures/Core/Shared/Options/FeatureOnOffOptions.cs @@ -44,10 +44,6 @@ internal static class FeatureOnOffOptions nameof(FeatureOnOffOptions), nameof(AutoFormattingOnTyping), defaultValue: true, storageLocations: new RoamingProfileStorageLocation("TextEditor.%LANGUAGE%.Specific.Auto Formatting On Typing")); - public static readonly PerLanguageOption AutoFormattingOnReturn = new PerLanguageOption( - nameof(FeatureOnOffOptions), nameof(AutoFormattingOnReturn), defaultValue: true, - storageLocations: new RoamingProfileStorageLocation("TextEditor.%LANGUAGE%.Specific.Auto Formatting On Return")); - public static readonly PerLanguageOption AutoFormattingOnCloseBrace = new PerLanguageOption( nameof(FeatureOnOffOptions), nameof(AutoFormattingOnCloseBrace), defaultValue: true, storageLocations: new RoamingProfileStorageLocation("TextEditor.%LANGUAGE%.Specific.Auto Formatting On Close Brace")); @@ -107,7 +103,6 @@ internal class FeatureOnOffOptionsProvider : IOptionProvider FeatureOnOffOptions.AutoInsertBlockCommentStartString, FeatureOnOffOptions.PrettyListing, FeatureOnOffOptions.AutoFormattingOnTyping, - FeatureOnOffOptions.AutoFormattingOnReturn, FeatureOnOffOptions.AutoFormattingOnCloseBrace, FeatureOnOffOptions.AutoFormattingOnSemicolon, FeatureOnOffOptions.RenameTrackingPreview, diff --git a/src/EditorFeatures/Core/Wrapping/AbstractWrapper.cs b/src/EditorFeatures/Core/Wrapping/AbstractWrapper.cs index d464f3b15688fadd400e9cff3f6e4a524bbab8e0..e4f4aa2f79d0d6ce315f8c15e07e71b088e78cc3 100644 --- a/src/EditorFeatures/Core/Wrapping/AbstractWrapper.cs +++ b/src/EditorFeatures/Core/Wrapping/AbstractWrapper.cs @@ -21,9 +21,9 @@ namespace Microsoft.CodeAnalysis.Editor.Wrapping /// internal abstract partial class AbstractSyntaxWrapper : ISyntaxWrapper { - protected IBlankLineIndentationService IndentationService { get; } + protected Indentation.IIndentationService IndentationService { get; } - protected AbstractSyntaxWrapper(IBlankLineIndentationService indentationService) + protected AbstractSyntaxWrapper(Indentation.IIndentationService indentationService) { this.IndentationService = indentationService; } diff --git a/src/EditorFeatures/Core/Wrapping/BinaryExpression/AbstractBinaryExpressionWrapper.cs b/src/EditorFeatures/Core/Wrapping/BinaryExpression/AbstractBinaryExpressionWrapper.cs index 8fb66c6d5a17eaaad6ec1fd8b9dda3cf2e65e0d2..d17ee495c5e9b1cb4b3a2eb95d0998cd0a097df9 100644 --- a/src/EditorFeatures/Core/Wrapping/BinaryExpression/AbstractBinaryExpressionWrapper.cs +++ b/src/EditorFeatures/Core/Wrapping/BinaryExpression/AbstractBinaryExpressionWrapper.cs @@ -6,7 +6,6 @@ using System.Threading.Tasks; using Microsoft.CodeAnalysis.LanguageServices; using Microsoft.CodeAnalysis.PooledObjects; -using Microsoft.CodeAnalysis.Shared.Extensions; namespace Microsoft.CodeAnalysis.Editor.Wrapping.BinaryExpression { @@ -17,7 +16,7 @@ internal abstract partial class AbstractBinaryExpressionWrapper(); + var blankLineIndenter = document.GetLanguageService(); var indentStyle = workspace.Options.GetOption(FormattingOptions.SmartIndent, GetLanguageName()); var blankLineIndentResult = blankLineIndenter.GetBlankLineIndentation( document, indentationLine, indentStyle, CancellationToken.None); diff --git a/src/EditorFeatures/TestUtilities/TestExportProvider.cs b/src/EditorFeatures/TestUtilities/TestExportProvider.cs index 5c845a5af3c60e2ac549cc3f7fbf9ad7fe7dc8f6..53b000f086da9fb622b8f740cd1efeb39eb7598e 100644 --- a/src/EditorFeatures/TestUtilities/TestExportProvider.cs +++ b/src/EditorFeatures/TestUtilities/TestExportProvider.cs @@ -57,8 +57,8 @@ private static Type[] GetNeutralAndCSharpAndVisualBasicTypes() typeof(CodeAnalysis.VisualBasic.IntroduceVariable.VisualBasicIntroduceVariableService), // Ensures that BasicFeatures is included in the composition typeof(CSharp.ContentType.ContentTypeDefinitions), // CSharp Content Type typeof(VisualBasic.ContentType.ContentTypeDefinitions), // VB Content Type - typeof(VisualBasic.Formatting.Indentation.VisualBasicIndentationService), - typeof(CSharp.Formatting.Indentation.CSharpIndentationService), + typeof(CodeAnalysis.VisualBasic.Indentation.VisualBasicIndentationService), + typeof(CodeAnalysis.CSharp.Indentation.CSharpIndentationService), typeof(CodeAnalysis.CSharp.CSharpCompilationFactoryService), typeof(CodeAnalysis.VisualBasic.VisualBasicCompilationFactoryService), typeof(CodeAnalysis.CSharp.CSharpSyntaxTreeFactoryServiceFactory), // CSharpServicesCore diff --git a/src/EditorFeatures/VisualBasic/Formatting/Indentation/SmartTokenFormatterCommandHandler.vb b/src/EditorFeatures/VisualBasic/Formatting/Indentation/SmartTokenFormatterCommandHandler.vb index 06f4d3f4ac7da7cf27ffc07d4c91d4f3ae7d3129..8de480da9e827cf6701beb970f6c2cd8a9566ce6 100644 --- a/src/EditorFeatures/VisualBasic/Formatting/Indentation/SmartTokenFormatterCommandHandler.vb +++ b/src/EditorFeatures/VisualBasic/Formatting/Indentation/SmartTokenFormatterCommandHandler.vb @@ -7,6 +7,7 @@ Imports Microsoft.CodeAnalysis.Formatting Imports Microsoft.CodeAnalysis.Formatting.Rules Imports Microsoft.CodeAnalysis.Options Imports Microsoft.CodeAnalysis.Text +Imports Microsoft.CodeAnalysis.VisualBasic.Indentation Imports Microsoft.CodeAnalysis.VisualBasic.Syntax Imports Microsoft.VisualStudio.Text.Operations Imports Microsoft.VisualStudio.Utilities @@ -20,8 +21,6 @@ Namespace Microsoft.CodeAnalysis.Editor.VisualBasic.Formatting.Indentation Friend Class SmartTokenFormatterCommandHandler Inherits AbstractSmartTokenFormatterCommandHandler - Private ReadOnly _formattingRules As IEnumerable(Of AbstractFormattingRule) - Public Sub New(undoHistoryRegistry As ITextUndoHistoryRegistry, editorOperationsFactoryService As IEditorOperationsFactoryService) diff --git a/src/EditorFeatures/VisualBasic/Wrapping/BinaryExpression/VisualBasicBinaryExpressionWrapper.vb b/src/EditorFeatures/VisualBasic/Wrapping/BinaryExpression/VisualBasicBinaryExpressionWrapper.vb index 8e46ef06f72dc4e6f8853038abd20c2f63be5f97..139c7b523ecc2879142038a693aa82632d37f130 100644 --- a/src/EditorFeatures/VisualBasic/Wrapping/BinaryExpression/VisualBasicBinaryExpressionWrapper.vb +++ b/src/EditorFeatures/VisualBasic/Wrapping/BinaryExpression/VisualBasicBinaryExpressionWrapper.vb @@ -1,7 +1,7 @@ ' Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. -Imports Microsoft.CodeAnalysis.Editor.VisualBasic.Formatting.Indentation Imports Microsoft.CodeAnalysis.Editor.Wrapping.BinaryExpression +Imports Microsoft.CodeAnalysis.VisualBasic.Indentation Imports Microsoft.CodeAnalysis.VisualBasic.Syntax Namespace Microsoft.CodeAnalysis.Editor.VisualBasic.Wrapping.BinaryExpression diff --git a/src/EditorFeatures/VisualBasic/Wrapping/SeparatedSyntaxList/AbstractVisualBasicSeparatedSyntaxListWrapper.vb b/src/EditorFeatures/VisualBasic/Wrapping/SeparatedSyntaxList/AbstractVisualBasicSeparatedSyntaxListWrapper.vb index a74cb0c02101c41cbd01f537a2c13cd316c0192c..2e74317421e5b61c248eac15794b709d0a449a20 100644 --- a/src/EditorFeatures/VisualBasic/Wrapping/SeparatedSyntaxList/AbstractVisualBasicSeparatedSyntaxListWrapper.vb +++ b/src/EditorFeatures/VisualBasic/Wrapping/SeparatedSyntaxList/AbstractVisualBasicSeparatedSyntaxListWrapper.vb @@ -1,7 +1,7 @@ ' Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. -Imports Microsoft.CodeAnalysis.Editor.VisualBasic.Formatting.Indentation Imports Microsoft.CodeAnalysis.Editor.Wrapping.SeparatedSyntaxList +Imports Microsoft.CodeAnalysis.VisualBasic.Indentation Namespace Microsoft.CodeAnalysis.Editor.VisualBasic.Wrapping.SeparatedSyntaxList Partial Friend MustInherit Class AbstractVisualBasicSeparatedSyntaxListWrapper( diff --git a/src/EditorFeatures/VisualBasicTest/Formatting/Indentation/SmartTokenFormatter_FormatTokenTests.vb b/src/EditorFeatures/VisualBasicTest/Formatting/Indentation/SmartTokenFormatter_FormatTokenTests.vb index 79e3fc25f4fdbebe169cf27cbc6a020b6dfe4fe8..be675cc95136041fa83fa7ba7b1ad6a2c4c7e761 100644 --- a/src/EditorFeatures/VisualBasicTest/Formatting/Indentation/SmartTokenFormatter_FormatTokenTests.vb +++ b/src/EditorFeatures/VisualBasicTest/Formatting/Indentation/SmartTokenFormatter_FormatTokenTests.vb @@ -7,6 +7,7 @@ Imports Microsoft.CodeAnalysis.Editor.VisualBasic.Formatting.Indentation Imports Microsoft.CodeAnalysis.Formatting Imports Microsoft.CodeAnalysis.Text Imports Microsoft.CodeAnalysis.Text.Shared.Extensions +Imports Microsoft.CodeAnalysis.VisualBasic.Indentation Imports Microsoft.CodeAnalysis.VisualBasic.Syntax Imports Microsoft.VisualStudio.Text.Editor Imports Moq diff --git a/src/EditorFeatures/CSharp/Formatting/Indentation/CSharpIndentationService.Indenter.cs b/src/Features/CSharp/Portable/Indentation/CSharpIndentationService.Indenter.cs similarity index 98% rename from src/EditorFeatures/CSharp/Formatting/Indentation/CSharpIndentationService.Indenter.cs rename to src/Features/CSharp/Portable/Indentation/CSharpIndentationService.Indenter.cs index 7336f917f43a66feae1bb4ad92f08bccfcc30f2c..e1aa2f1b11b0a9cf6ca463aa401b6709b5bc44a7 100644 --- a/src/EditorFeatures/CSharp/Formatting/Indentation/CSharpIndentationService.Indenter.cs +++ b/src/Features/CSharp/Portable/Indentation/CSharpIndentationService.Indenter.cs @@ -4,21 +4,19 @@ using System.Diagnostics; using System.Linq; using System.Threading; -using Microsoft.CodeAnalysis.CSharp; using Microsoft.CodeAnalysis.CSharp.Extensions; using Microsoft.CodeAnalysis.CSharp.Formatting; using Microsoft.CodeAnalysis.CSharp.Syntax; -using Microsoft.CodeAnalysis.Editor.Implementation.Formatting.Indentation; using Microsoft.CodeAnalysis.Formatting; using Microsoft.CodeAnalysis.Formatting.Rules; +using Microsoft.CodeAnalysis.Indentation; using Microsoft.CodeAnalysis.LanguageServices; using Microsoft.CodeAnalysis.Options; using Microsoft.CodeAnalysis.Shared.Extensions; using Microsoft.CodeAnalysis.Text; -using Microsoft.CodeAnalysis.Text.Shared.Extensions; using Roslyn.Utilities; -namespace Microsoft.CodeAnalysis.Editor.CSharp.Formatting.Indentation +namespace Microsoft.CodeAnalysis.CSharp.Indentation { internal partial class CSharpIndentationService { diff --git a/src/EditorFeatures/CSharp/Formatting/Indentation/CSharpIndentationService.cs b/src/Features/CSharp/Portable/Indentation/CSharpIndentationService.cs similarity index 94% rename from src/EditorFeatures/CSharp/Formatting/Indentation/CSharpIndentationService.cs rename to src/Features/CSharp/Portable/Indentation/CSharpIndentationService.cs index 58755397ba091c52c5885fa2de5325de71187447..4f8e93490790853bf7ea5e669317a3c04c8497b1 100644 --- a/src/EditorFeatures/CSharp/Formatting/Indentation/CSharpIndentationService.cs +++ b/src/Features/CSharp/Portable/Indentation/CSharpIndentationService.cs @@ -4,25 +4,21 @@ using System.Composition; using System.Diagnostics; using System.Threading; -using Microsoft.CodeAnalysis.CSharp; using Microsoft.CodeAnalysis.CSharp.Extensions; using Microsoft.CodeAnalysis.CSharp.Syntax; -using Microsoft.CodeAnalysis.Editor.Implementation.Formatting.Indentation; -using Microsoft.CodeAnalysis.Editor.Implementation.SmartIndent; -using Microsoft.CodeAnalysis.Editor.Shared.Options; using Microsoft.CodeAnalysis.Formatting; using Microsoft.CodeAnalysis.Formatting.Rules; using Microsoft.CodeAnalysis.Host.Mef; +using Microsoft.CodeAnalysis.Indentation; using Microsoft.CodeAnalysis.LanguageServices; using Microsoft.CodeAnalysis.Options; using Microsoft.CodeAnalysis.Shared.Extensions; using Microsoft.CodeAnalysis.Text; -using Microsoft.CodeAnalysis.Text.Shared.Extensions; using Roslyn.Utilities; -namespace Microsoft.CodeAnalysis.Editor.CSharp.Formatting.Indentation +namespace Microsoft.CodeAnalysis.CSharp.Indentation { - [ExportLanguageService(typeof(ISynchronousIndentationService), LanguageNames.CSharp), Shared] + [ExportLanguageService(typeof(IIndentationService), LanguageNames.CSharp), Shared] internal sealed partial class CSharpIndentationService : AbstractIndentationService { public static readonly CSharpIndentationService Instance = new CSharpIndentationService(); @@ -52,7 +48,7 @@ protected override AbstractFormattingRule GetSpecializedIndentationFormattingRul Contract.ThrowIfNull(formattingRules); Contract.ThrowIfNull(root); - if (!optionSet.GetOption(FeatureOnOffOptions.AutoFormattingOnReturn, LanguageNames.CSharp)) + if (!optionSet.GetOption(FormattingOptions.AutoFormattingOnReturn, LanguageNames.CSharp)) { return false; } diff --git a/src/EditorFeatures/Core/Implementation/SmartIndent/AbstractIndentationService.AbstractIndenter.cs b/src/Features/Core/Portable/Indentation/AbstractIndentationService.AbstractIndenter.cs similarity index 98% rename from src/EditorFeatures/Core/Implementation/SmartIndent/AbstractIndentationService.AbstractIndenter.cs rename to src/Features/Core/Portable/Indentation/AbstractIndentationService.AbstractIndenter.cs index 69aaf6808067a0309e4b84bbff941c6f6d86f0e5..20fb4f57396572e418dd21a183512b28e35a1938 100644 --- a/src/EditorFeatures/Core/Implementation/SmartIndent/AbstractIndentationService.AbstractIndenter.cs +++ b/src/Features/Core/Portable/Indentation/AbstractIndentationService.AbstractIndenter.cs @@ -11,9 +11,8 @@ using Microsoft.CodeAnalysis.Options; using Microsoft.CodeAnalysis.Shared.Extensions; using Microsoft.CodeAnalysis.Text; -using Microsoft.CodeAnalysis.Text.Shared.Extensions; -namespace Microsoft.CodeAnalysis.Editor.Implementation.SmartIndent +namespace Microsoft.CodeAnalysis.Indentation { internal abstract partial class AbstractIndentationService { diff --git a/src/EditorFeatures/Core/Implementation/SmartIndent/AbstractIndentationService.cs b/src/Features/Core/Portable/Indentation/AbstractIndentationService.cs similarity index 96% rename from src/EditorFeatures/Core/Implementation/SmartIndent/AbstractIndentationService.cs rename to src/Features/Core/Portable/Indentation/AbstractIndentationService.cs index 44b9109fe79db8b3e2512f36e7ac312253f9899b..768a620b96a6c2aeb6bdda6fcd5fe5d1d2188521 100644 --- a/src/EditorFeatures/Core/Implementation/SmartIndent/AbstractIndentationService.cs +++ b/src/Features/Core/Portable/Indentation/AbstractIndentationService.cs @@ -1,6 +1,5 @@ // Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. -using System; using System.Collections.Generic; using System.Linq; using System.Threading; @@ -12,10 +11,9 @@ using Microsoft.CodeAnalysis.Text; using Roslyn.Utilities; -namespace Microsoft.CodeAnalysis.Editor.Implementation.SmartIndent +namespace Microsoft.CodeAnalysis.Indentation { - internal abstract partial class AbstractIndentationService - : ISynchronousIndentationService, IBlankLineIndentationService + internal abstract partial class AbstractIndentationService : IIndentationService where TSyntaxRoot : SyntaxNode, ICompilationUnitSyntax { protected abstract AbstractFormattingRule GetSpecializedIndentationFormattingRule(); diff --git a/src/Features/Core/Portable/Indentation/IIndentationService.cs b/src/Features/Core/Portable/Indentation/IIndentationService.cs new file mode 100644 index 0000000000000000000000000000000000000000..ea63fc2a819042cebb13c46580fd86e791c1a163 --- /dev/null +++ b/src/Features/Core/Portable/Indentation/IIndentationService.cs @@ -0,0 +1,70 @@ +// Copyright (c) Microsoft. All Rights Reserved. Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information. + +using System.Threading; +using System.Threading.Tasks; +using Microsoft.CodeAnalysis.Formatting; +using Microsoft.CodeAnalysis.Host; + +namespace Microsoft.CodeAnalysis.Indentation +{ + /// + /// An indentation result represents where the indent should be placed. It conveys this through + /// a pair of values. A position in the existing document where the indent should be relative, + /// and the number of columns after that the indent should be placed at. + /// + /// This pairing provides flexibility to the implementor to compute the indentation results in + /// a variety of ways. For example, one implementation may wish to express indentation of a + /// newline as being four columns past the start of the first token on a previous line. Another + /// may wish to simply express the indentation as an absolute amount from the start of the + /// current line. With this tuple, both forms can be expressed, and the implementor does not + /// have to convert from one to the other. + /// + internal struct IndentationResult + { + /// + /// The base position in the document that the indent should be relative to. This position + /// can occur on any line (including the current line, or a previous line). + /// + public int BasePosition { get; } + + /// + /// The number of columns the indent should be at relative to the BasePosition's column. + /// + public int Offset { get; } + + public IndentationResult(int basePosition, int offset) : this() + { + this.BasePosition = basePosition; + this.Offset = offset; + } + } + + internal interface IIndentationService : ILanguageService + { + /// + /// Determines the desired indentation of a given line. May return if the + /// does not want any sort of automatic indentation. May also return + /// if the line in question is not blank and thus indentation should + /// be deferred to the formatting command handler to handle. + /// + IndentationResult? GetDesiredIndentation(Document document, int lineNumber, CancellationToken cancellationToken); + + /// + /// Determines indentation for a blank line (i.e. after hitting enter at the end of a line, + /// or after moving to a blank line). + /// + /// Specifically, this function operates as if the line specified by + /// is blank. The actual contents of the line do not matter. All indentation information is + /// determined from the previous lines in the document. + /// + /// This is often useful for features which want to insert new code at a certain + /// location, indented to the appropriate amount. This allows those features to + /// figure out that position, without having to care about what might already be + /// at that line (or further on in the document). + /// + /// This function will always succeed. + /// + IndentationResult GetBlankLineIndentation( + Document document, int lineNumber, FormattingOptions.IndentStyle indentStyle, CancellationToken cancellationToken); + } +} diff --git a/src/EditorFeatures/VisualBasic/Formatting/Indentation/SpecialFormattingOperation.vb b/src/Features/VisualBasic/Portable/Indentation/SpecialFormattingOperation.vb similarity index 99% rename from src/EditorFeatures/VisualBasic/Formatting/Indentation/SpecialFormattingOperation.vb rename to src/Features/VisualBasic/Portable/Indentation/SpecialFormattingOperation.vb index be6a2c92fd81775d9591a31b80ec673c51e7cf85..4af9bf4307691bdcfe468a84025e79373ecf207c 100644 --- a/src/EditorFeatures/VisualBasic/Formatting/Indentation/SpecialFormattingOperation.vb +++ b/src/Features/VisualBasic/Portable/Indentation/SpecialFormattingOperation.vb @@ -7,8 +7,7 @@ Imports Microsoft.CodeAnalysis.Options Imports Microsoft.CodeAnalysis.Text Imports Microsoft.CodeAnalysis.VisualBasic.Syntax -Namespace Microsoft.CodeAnalysis.Editor.VisualBasic.Formatting.Indentation - +Namespace Microsoft.CodeAnalysis.VisualBasic.Indentation Friend Class SpecialFormattingRule Inherits CompatAbstractFormattingRule diff --git a/src/EditorFeatures/VisualBasic/Formatting/Indentation/VisualBasicIndentationService.Indenter.vb b/src/Features/VisualBasic/Portable/Indentation/VisualBasicIndentationService.Indenter.vb similarity index 99% rename from src/EditorFeatures/VisualBasic/Formatting/Indentation/VisualBasicIndentationService.Indenter.vb rename to src/Features/VisualBasic/Portable/Indentation/VisualBasicIndentationService.Indenter.vb index 1d9e0a3403e2478b4d5cf5dbb5242e41c7b6a0ea..ddc6bdc70cb4b27110a14445b70335bb3b2f8cb1 100644 --- a/src/EditorFeatures/VisualBasic/Formatting/Indentation/VisualBasicIndentationService.Indenter.vb +++ b/src/Features/VisualBasic/Portable/Indentation/VisualBasicIndentationService.Indenter.vb @@ -3,14 +3,14 @@ Imports System.Threading Imports Microsoft.CodeAnalysis.Formatting Imports Microsoft.CodeAnalysis.Formatting.Rules +Imports Microsoft.CodeAnalysis.Indentation Imports Microsoft.CodeAnalysis.LanguageServices Imports Microsoft.CodeAnalysis.Options Imports Microsoft.CodeAnalysis.Text -Imports Microsoft.CodeAnalysis.Text.Shared.Extensions Imports Microsoft.CodeAnalysis.VisualBasic.Formatting Imports Microsoft.CodeAnalysis.VisualBasic.Syntax -Namespace Microsoft.CodeAnalysis.Editor.VisualBasic.Formatting.Indentation +Namespace Microsoft.CodeAnalysis.VisualBasic.Indentation Partial Friend Class VisualBasicIndentationService Private Class Indenter Inherits AbstractIndenter diff --git a/src/EditorFeatures/VisualBasic/Formatting/Indentation/VisualBasicIndentationService.vb b/src/Features/VisualBasic/Portable/Indentation/VisualBasicIndentationService.vb similarity index 94% rename from src/EditorFeatures/VisualBasic/Formatting/Indentation/VisualBasicIndentationService.vb rename to src/Features/VisualBasic/Portable/Indentation/VisualBasicIndentationService.vb index 5344e028d967faaf52421a9ea451c0d83c27322a..00eb191d00df0d7102e68d7b1f5d5816a954b8fa 100644 --- a/src/EditorFeatures/VisualBasic/Formatting/Indentation/VisualBasicIndentationService.vb +++ b/src/Features/VisualBasic/Portable/Indentation/VisualBasicIndentationService.vb @@ -2,17 +2,16 @@ Imports System.Composition Imports System.Threading -Imports Microsoft.CodeAnalysis.Editor.Implementation.SmartIndent Imports Microsoft.CodeAnalysis.Formatting.Rules Imports Microsoft.CodeAnalysis.Host.Mef +Imports Microsoft.CodeAnalysis.Indentation Imports Microsoft.CodeAnalysis.LanguageServices Imports Microsoft.CodeAnalysis.Options Imports Microsoft.CodeAnalysis.Text -Imports Microsoft.CodeAnalysis.Text.Shared.Extensions Imports Microsoft.CodeAnalysis.VisualBasic.Syntax -Namespace Microsoft.CodeAnalysis.Editor.VisualBasic.Formatting.Indentation - +Namespace Microsoft.CodeAnalysis.VisualBasic.Indentation + Partial Friend NotInheritable Class VisualBasicIndentationService Inherits AbstractIndentationService(Of CompilationUnitSyntax) diff --git a/src/Workspaces/Core/Portable/Formatting/FormattingOptions.cs b/src/Workspaces/Core/Portable/Formatting/FormattingOptions.cs index 69548e1b239e208bb8993839366efeab5522c523..ced6ef0c9c6f9a65e029b367f909ed5c92bf6e95 100644 --- a/src/Workspaces/Core/Portable/Formatting/FormattingOptions.cs +++ b/src/Workspaces/Core/Portable/Formatting/FormattingOptions.cs @@ -99,6 +99,9 @@ private static string GetEndOfLineEditorConfigString(string option) internal static Option AllowDisjointSpanMerging { get; } = CreateOption(OptionGroup.Default, nameof(AllowDisjointSpanMerging), defaultValue: false); + internal static readonly PerLanguageOption AutoFormattingOnReturn = CreatePerLanguageOption(OptionGroup.Default, nameof(AutoFormattingOnReturn), defaultValue: true, + storageLocations: new RoamingProfileStorageLocation("TextEditor.%LANGUAGE%.Specific.Auto Formatting On Return")); + static FormattingOptions() { // Note that the static constructor executes after all the static field initializers for the options have executed,