From b980a3893bac45aaba4d2bb47a85d6f147e880a3 Mon Sep 17 00:00:00 2001 From: Heejae Chang Date: Tue, 26 Mar 2019 23:07:53 -0700 Subject: [PATCH] first work to remove IEditorClassificationService (#31734) * removed IEditorClassificationService that is marked obsolete since 2017 and bunch of other code that only existed for the IEditorClassificationService. according to vso, only F# still has dependency so I talked to them to move to new API (IClassificationService) - https://devdiv.visualstudio.com/DevDiv/_git/DotNet-Source-Build-Tarball?path=%2Fsrc%2Ffsharp%2Fvsintegration%2Fsrc%2FFSharp.Editor%2FClassification%2FColorizationService.fs&version=GBmaster and a bunch of clean up and move code that has no dependency to the editor to lower layers so that I can consume in razor scenario. * added shim project for FSharp that has internal visible to FSharp editor * merged https://github.com/dotnet/roslyn/pull/31941 * addressing PR feedback * moved some type (such as DocumentSpan, ClassifiedSpan and etc) back to where fsharp has IVT to. can't move those since partner team is using them and they don't have IVT to workspace layer for some reasons. also, have put the IEditorClassificationService back and add a proxy in FSharp External Access so that it can still work until they remove all IVT. --- ...stractFindUsagesService.ProgressAdapter.cs | 1 + .../IDefinitionsAndReferencesFactory.cs | 1 + .../IEditorClassificationService.cs | 55 ------------- ...assificationBufferTaggerProvider.Tagger.cs | 18 +---- .../SemanticClassificationUtilities.cs | 27 +++---- ...emanticClassificationViewTaggerProvider.cs | 19 +---- ...lassificationTaggerProvider.TagComputer.cs | 55 ++++++------- .../QuickInfo/IntellisenseQuickInfoBuilder.cs | 2 +- ...crosoft.CodeAnalysis.EditorFeatures.csproj | 3 +- ...{ContentTypeNames.cs => TypeForwarders.cs} | 0 .../Classification/ClassificationTests.vb | 13 ++- .../ClassifiedSpansAndHighlightSpan.cs | 3 +- .../ClassifiedSpansAndHighlightSpanFactory.cs | 7 +- .../VS.ExternalAPIs.Roslyn.Package.csproj | 79 ++++++++++--------- .../FSharpClassificationService.cs | 66 ++++++++++++++++ ....CodeAnalysis.ExternalAccess.FSharp.csproj | 4 +- ...bstractTableDataSourceFindUsagesContext.cs | 1 + ...ntainedDocument.DocumentServiceProvider.cs | 4 +- .../Setup/source.extension.vsixmanifest | 1 + .../Classification/ClassifierHelper.cs} | 51 +++--------- .../Microsoft.CodeAnalysis.Workspaces.csproj | 1 + 21 files changed, 179 insertions(+), 232 deletions(-) rename src/EditorFeatures/Core/{ContentTypeNames.cs => TypeForwarders.cs} (100%) rename src/Features/Core/Portable/{FindUsages => }/ClassifiedSpansAndHighlightSpan.cs (89%) rename src/{EditorFeatures/Core/FindUsages => Features/Core/Portable}/ClassifiedSpansAndHighlightSpanFactory.cs (94%) create mode 100644 src/Tools/ExternalAccess/FSharp/Classification/FSharpClassificationService.cs rename src/{EditorFeatures/Core/Implementation/Classification/EditorClassifier.cs => Workspaces/Core/Portable/Classification/ClassifierHelper.cs} (81%) diff --git a/src/EditorFeatures/Core/FindUsages/AbstractFindUsagesService.ProgressAdapter.cs b/src/EditorFeatures/Core/FindUsages/AbstractFindUsagesService.ProgressAdapter.cs index 431ca26dca7..ce4f54f501f 100644 --- a/src/EditorFeatures/Core/FindUsages/AbstractFindUsagesService.ProgressAdapter.cs +++ b/src/EditorFeatures/Core/FindUsages/AbstractFindUsagesService.ProgressAdapter.cs @@ -3,6 +3,7 @@ using System.Collections.Generic; using System.Threading; using System.Threading.Tasks; +using Microsoft.CodeAnalysis.Classification; using Microsoft.CodeAnalysis.Editor.Shared.Utilities; using Microsoft.CodeAnalysis.FindSymbols; using Microsoft.CodeAnalysis.FindUsages; diff --git a/src/EditorFeatures/Core/FindUsages/IDefinitionsAndReferencesFactory.cs b/src/EditorFeatures/Core/FindUsages/IDefinitionsAndReferencesFactory.cs index 9452803356e..b7f5ec3f6cb 100644 --- a/src/EditorFeatures/Core/FindUsages/IDefinitionsAndReferencesFactory.cs +++ b/src/EditorFeatures/Core/FindUsages/IDefinitionsAndReferencesFactory.cs @@ -5,6 +5,7 @@ using System.Diagnostics; using System.Threading; using System.Threading.Tasks; +using Microsoft.CodeAnalysis.Classification; using Microsoft.CodeAnalysis.Completion; using Microsoft.CodeAnalysis.Features.RQName; using Microsoft.CodeAnalysis.FindSymbols; diff --git a/src/EditorFeatures/Core/Implementation/Classification/IEditorClassificationService.cs b/src/EditorFeatures/Core/Implementation/Classification/IEditorClassificationService.cs index b799f80c02e..ce600bbecb2 100644 --- a/src/EditorFeatures/Core/Implementation/Classification/IEditorClassificationService.cs +++ b/src/EditorFeatures/Core/Implementation/Classification/IEditorClassificationService.cs @@ -53,59 +53,4 @@ internal interface IEditorClassificationService : ILanguageService /// ClassifiedSpan AdjustStaleClassification(SourceText text, ClassifiedSpan classifiedSpan); } - - /// - /// Exists to bridge between and - /// - internal interface IClassificationDelegationService - { - void AddLexicalClassifications(TClassificationService service, SourceText text, TextSpan textSpan, List result, CancellationToken cancellationToken); - Task AddSyntacticClassificationsAsync(TClassificationService service, Document document, TextSpan textSpan, List result, CancellationToken cancellationToken); - Task AddSemanticClassificationsAsync(TClassificationService service, Document document, TextSpan textSpan, List result, CancellationToken cancellationToken); - ClassifiedSpan AdjustStaleClassification(TClassificationService service, SourceText text, ClassifiedSpan classifiedSpan); - } - - internal class WorkspaceClassificationDelegationService : IClassificationDelegationService - { - public static readonly IClassificationDelegationService Instance = new WorkspaceClassificationDelegationService(); - - private WorkspaceClassificationDelegationService() - { - } - - public void AddLexicalClassifications(IClassificationService service, SourceText text, TextSpan textSpan, List result, CancellationToken cancellationToken) - => service.AddLexicalClassifications(text, textSpan, result, cancellationToken); - - public Task AddSyntacticClassificationsAsync(IClassificationService service, Document document, TextSpan textSpan, List result, CancellationToken cancellationToken) - => service.AddSyntacticClassificationsAsync(document, textSpan, result, cancellationToken); - - public Task AddSemanticClassificationsAsync(IClassificationService service, Document document, TextSpan textSpan, List result, CancellationToken cancellationToken) - => service.AddSemanticClassificationsAsync(document, textSpan, result, cancellationToken); - - public ClassifiedSpan AdjustStaleClassification(IClassificationService service, SourceText text, ClassifiedSpan classifiedSpan) - => service.AdjustStaleClassification(text, classifiedSpan); - } - -#pragma warning disable CS0618 // Type or member is obsolete - internal class EditorClassificationDelegationService : IClassificationDelegationService - { - public static readonly IClassificationDelegationService Instance = new EditorClassificationDelegationService(); - - private EditorClassificationDelegationService() - { - } - - public void AddLexicalClassifications(IEditorClassificationService service, SourceText text, TextSpan textSpan, List result, CancellationToken cancellationToken) - => service.AddLexicalClassifications(text, textSpan, result, cancellationToken); - - public Task AddSyntacticClassificationsAsync(IEditorClassificationService service, Document document, TextSpan textSpan, List result, CancellationToken cancellationToken) - => service.AddSyntacticClassificationsAsync(document, textSpan, result, cancellationToken); - - public Task AddSemanticClassificationsAsync(IEditorClassificationService service, Document document, TextSpan textSpan, List result, CancellationToken cancellationToken) - => service.AddSemanticClassificationsAsync(document, textSpan, result, cancellationToken); - - public ClassifiedSpan AdjustStaleClassification(IEditorClassificationService service, SourceText text, ClassifiedSpan classifiedSpan) - => service.AdjustStaleClassification(text, classifiedSpan); - } -#pragma warning restore CS0612 // Type or member is obsolete } diff --git a/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationBufferTaggerProvider.Tagger.cs b/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationBufferTaggerProvider.Tagger.cs index 6bf2f57e7ae..4f01940235d 100644 --- a/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationBufferTaggerProvider.Tagger.cs +++ b/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationBufferTaggerProvider.Tagger.cs @@ -6,10 +6,10 @@ using System.Linq; using System.Threading; using System.Threading.Tasks; +using Microsoft.CodeAnalysis.Classification; using Microsoft.CodeAnalysis.Editor.Shared.Tagging; using Microsoft.CodeAnalysis.Editor.Shared.Utilities; using Microsoft.CodeAnalysis.Editor.Tagging; -using Microsoft.CodeAnalysis.Host; using Microsoft.CodeAnalysis.Shared.Extensions; using Microsoft.CodeAnalysis.Text; using Microsoft.CodeAnalysis.Text.Shared.Extensions; @@ -167,25 +167,13 @@ public IEnumerable> GetAllTags(NormalizedSnapshotSp } private Task ProduceTagsAsync(TaggerContext context, DocumentSnapshotSpan documentSpan, ClassificationTypeMap typeMap) - { - return Task.WhenAll( - ProduceTagsAsync(context, documentSpan, typeMap, WorkspaceClassificationDelegationService.Instance), - ProduceTagsAsync(context, documentSpan, typeMap, EditorClassificationDelegationService.Instance)); - } - - private Task ProduceTagsAsync( - TaggerContext context, - DocumentSnapshotSpan documentSpan, - ClassificationTypeMap typeMap, - IClassificationDelegationService delegationService) where TClassificationService : class, ILanguageService { var document = documentSpan.Document; - var classificationService = document.GetLanguageService(); + var classificationService = document.GetLanguageService(); if (classificationService != null) { - return SemanticClassificationUtilities.ProduceTagsAsync( - context, documentSpan, delegationService, classificationService, typeMap); + return SemanticClassificationUtilities.ProduceTagsAsync(context, documentSpan, classificationService, typeMap); } return Task.CompletedTask; diff --git a/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationUtilities.cs b/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationUtilities.cs index 88e4e58825d..eda269cb1b9 100644 --- a/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationUtilities.cs +++ b/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationUtilities.cs @@ -2,11 +2,11 @@ using System; using System.Threading.Tasks; +using Microsoft.CodeAnalysis.Classification; using Microsoft.CodeAnalysis.Editor.Shared.Extensions; using Microsoft.CodeAnalysis.Editor.Shared.Utilities; using Microsoft.CodeAnalysis.Editor.Tagging; using Microsoft.CodeAnalysis.ErrorReporting; -using Microsoft.CodeAnalysis.Host; using Microsoft.CodeAnalysis.Internal.Log; using Microsoft.CodeAnalysis.LanguageServices; using Microsoft.CodeAnalysis.Shared.Extensions; @@ -20,11 +20,10 @@ namespace Microsoft.CodeAnalysis.Editor.Implementation.Classification { internal static class SemanticClassificationUtilities { - public static async Task ProduceTagsAsync( + public static async Task ProduceTagsAsync( TaggerContext context, DocumentSnapshotSpan spanToTag, - IClassificationDelegationService delegationService, - TClassificationService classificationService, + IClassificationService classificationService, ClassificationTypeMap typeMap) { var document = spanToTag.Document; @@ -34,7 +33,7 @@ internal static class SemanticClassificationUtilities } var classified = await TryClassifyContainingMemberSpan( - context, spanToTag, delegationService, classificationService, typeMap).ConfigureAwait(false); + context, spanToTag, classificationService, typeMap).ConfigureAwait(false); if (classified) { return; @@ -43,14 +42,13 @@ internal static class SemanticClassificationUtilities // We weren't able to use our specialized codepaths for semantic classifying. // Fall back to classifying the full span that was asked for. await ClassifySpansAsync( - context, spanToTag, delegationService, classificationService, typeMap).ConfigureAwait(false); + context, spanToTag, classificationService, typeMap).ConfigureAwait(false); } - private static async Task TryClassifyContainingMemberSpan( + private static async Task TryClassifyContainingMemberSpan( TaggerContext context, DocumentSnapshotSpan spanToTag, - IClassificationDelegationService delegationService, - TClassificationService classificationService, + IClassificationService classificationService, ClassificationTypeMap typeMap) { var range = context.TextChangeRange; @@ -110,15 +108,14 @@ internal static class SemanticClassificationUtilities // re-classify only the member we're inside. await ClassifySpansAsync( - context, subSpanToTag, delegationService, classificationService, typeMap).ConfigureAwait(false); + context, subSpanToTag, classificationService, typeMap).ConfigureAwait(false); return true; } - private static async Task ClassifySpansAsync( + private static async Task ClassifySpansAsync( TaggerContext context, DocumentSnapshotSpan spanToTag, - IClassificationDelegationService delegationService, - TClassificationService classificationService, + IClassificationService classificationService, ClassificationTypeMap typeMap) { try @@ -132,8 +129,8 @@ internal static class SemanticClassificationUtilities { var classifiedSpans = ClassificationUtilities.GetOrCreateClassifiedSpanList(); - await delegationService.AddSemanticClassificationsAsync( - classificationService, document, snapshotSpan.Span.ToTextSpan(), classifiedSpans, cancellationToken: cancellationToken).ConfigureAwait(false); + await classificationService.AddSemanticClassificationsAsync( + document, snapshotSpan.Span.ToTextSpan(), classifiedSpans, cancellationToken: cancellationToken).ConfigureAwait(false); ClassificationUtilities.Convert(typeMap, snapshotSpan.Snapshot, classifiedSpans, context.AddTag); ClassificationUtilities.ReturnClassifiedSpanList(classifiedSpans); diff --git a/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationViewTaggerProvider.cs b/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationViewTaggerProvider.cs index 093490e572a..a1b1a2cef19 100644 --- a/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationViewTaggerProvider.cs +++ b/src/EditorFeatures/Core/Implementation/Classification/SemanticClassificationViewTaggerProvider.cs @@ -5,12 +5,12 @@ using System.Diagnostics; using System.Linq; using System.Threading.Tasks; +using Microsoft.CodeAnalysis.Classification; using Microsoft.CodeAnalysis.Editor.Shared.Extensions; using Microsoft.CodeAnalysis.Editor.Shared.Options; using Microsoft.CodeAnalysis.Editor.Shared.Tagging; using Microsoft.CodeAnalysis.Editor.Shared.Utilities; using Microsoft.CodeAnalysis.Editor.Tagging; -using Microsoft.CodeAnalysis.Host; using Microsoft.CodeAnalysis.Notification; using Microsoft.CodeAnalysis.Options; using Microsoft.CodeAnalysis.Shared.Extensions; @@ -92,31 +92,18 @@ protected override Task ProduceTagsAsync(TaggerContext conte var spanToTag = context.SpansToTag.Single(); - var task1 = ProduceTagsAsync(context, spanToTag, WorkspaceClassificationDelegationService.Instance); - var task2 = ProduceTagsAsync(context, spanToTag, EditorClassificationDelegationService.Instance); - - return Task.WhenAll(task1, task2); - } - - private Task ProduceTagsAsync( - TaggerContext context, - DocumentSnapshotSpan spanToTag, - IClassificationDelegationService delegationService) - where TClassificationService : class, ILanguageService - { var document = spanToTag.Document; // Attempt to get a classification service which will actually produce the results. // If we can't (because we have no Document, or because the language doesn't support // this service), then bail out immediately. - var classificationService = document?.GetLanguageService(); + var classificationService = document?.GetLanguageService(); if (classificationService == null) { return Task.CompletedTask; } - return SemanticClassificationUtilities.ProduceTagsAsync( - context, spanToTag, delegationService, classificationService, _typeMap); + return SemanticClassificationUtilities.ProduceTagsAsync(context, spanToTag, classificationService, _typeMap); } } } diff --git a/src/EditorFeatures/Core/Implementation/Classification/SyntacticClassificationTaggerProvider.TagComputer.cs b/src/EditorFeatures/Core/Implementation/Classification/SyntacticClassificationTaggerProvider.TagComputer.cs index 847566be4a6..2d35ea0fefe 100644 --- a/src/EditorFeatures/Core/Implementation/Classification/SyntacticClassificationTaggerProvider.TagComputer.cs +++ b/src/EditorFeatures/Core/Implementation/Classification/SyntacticClassificationTaggerProvider.TagComputer.cs @@ -246,8 +246,7 @@ public IEnumerable> GetTags(NormalizedSnapshotSpanC var languageServices = _workspace.Services.GetLanguageServices(firstSpan.Snapshot.ContentType); if (languageServices != null) { - var result = GetTags(spans, languageServices, WorkspaceClassificationDelegationService.Instance) ?? - GetTags(spans, languageServices, EditorClassificationDelegationService.Instance); + var result = GetTags(spans, languageServices); if (result != null) { return result; @@ -259,13 +258,10 @@ public IEnumerable> GetTags(NormalizedSnapshotSpanC } } - private IEnumerable> GetTags( - NormalizedSnapshotSpanCollection spans, - HostLanguageServices languageServices, - IClassificationDelegationService delegationService) where TClassificationService : class, ILanguageService + private IEnumerable> GetTags( + NormalizedSnapshotSpanCollection spans, HostLanguageServices languageServices) { - var classificationService = languageServices.GetService(); - + var classificationService = languageServices.GetService(); if (classificationService == null) { return null; @@ -275,16 +271,15 @@ public IEnumerable> GetTags(NormalizedSnapshotSpanC foreach (var span in spans) { - AddClassifiedSpans(delegationService, classificationService, span, classifiedSpans); + AddClassifiedSpans(classificationService, span, classifiedSpans); } return ClassificationUtilities.ConvertAndReturnList( _typeMap, spans[0].Snapshot, classifiedSpans); } - private void AddClassifiedSpans( - IClassificationDelegationService delegationService, - TClassificationService classificationService, + private void AddClassifiedSpans( + IClassificationService classificationService, SnapshotSpan span, List classifiedSpans) { @@ -302,7 +297,7 @@ public IEnumerable> GetTags(NormalizedSnapshotSpanC if (lastDocument == null) { // We don't have a syntax tree yet. Just do a lexical classification of the document. - AddClassifiedSpansForTokens(delegationService, classificationService, span, classifiedSpans); + AddClassifiedSpansForTokens(classificationService, span, classifiedSpans); return; } @@ -313,20 +308,19 @@ public IEnumerable> GetTags(NormalizedSnapshotSpanC if (lastSnapshot.Version.ReiteratedVersionNumber == span.Snapshot.Version.ReiteratedVersionNumber) { AddClassifiedSpansForCurrentTree( - delegationService, classificationService, span, lastDocument, classifiedSpans); + classificationService, span, lastDocument, classifiedSpans); } else { // Slightly more complicated. We have a parse tree, it's just not for the snapshot // we're being asked for. AddClassifiedSpansForPreviousTree( - delegationService, classificationService, span, lastSnapshot, lastDocument, classifiedSpans); + classificationService, span, lastSnapshot, lastDocument, classifiedSpans); } } - private void AddClassifiedSpansForCurrentTree( - IClassificationDelegationService delegationService, - TClassificationService classificationService, + private void AddClassifiedSpansForCurrentTree( + IClassificationService classificationService, SnapshotSpan span, Document document, List classifiedSpans) @@ -335,8 +329,8 @@ public IEnumerable> GetTags(NormalizedSnapshotSpanC { tempList = ClassificationUtilities.GetOrCreateClassifiedSpanList(); - delegationService.AddSyntacticClassificationsAsync( - classificationService, document, span.Span.ToTextSpan(), tempList, CancellationToken.None).Wait(CancellationToken.None); + classificationService.AddSyntacticClassificationsAsync( + document, span.Span.ToTextSpan(), tempList, CancellationToken.None).Wait(CancellationToken.None); _lastLineCache.Update(span, tempList); } @@ -347,9 +341,8 @@ public IEnumerable> GetTags(NormalizedSnapshotSpanC classifiedSpans.AddRange(tempList); } - private void AddClassifiedSpansForPreviousTree( - IClassificationDelegationService delegationService, - TClassificationService classificationService, + private void AddClassifiedSpansForPreviousTree( + IClassificationService classificationService, SnapshotSpan span, ITextSnapshot lastSnapshot, Document lastDocument, @@ -389,13 +382,13 @@ public IEnumerable> GetTags(NormalizedSnapshotSpanC { // well, there is no information we can get from previous tree, use lexer to // classify given span. soon we will re-classify the region. - AddClassifiedSpansForTokens(delegationService, classificationService, span, classifiedSpans); + AddClassifiedSpansForTokens(classificationService, span, classifiedSpans); return; } var tempList = ClassificationUtilities.GetOrCreateClassifiedSpanList(); AddClassifiedSpansForCurrentTree( - delegationService, classificationService, translatedSpan, lastDocument, tempList); + classificationService, translatedSpan, lastDocument, tempList); var currentSnapshot = span.Snapshot; var currentText = currentSnapshot.AsText(); @@ -411,8 +404,7 @@ public IEnumerable> GetTags(NormalizedSnapshotSpanC // 3) The classifications may be incorrect due to changes in the text. For example, // if "clss" becomes "class", then we want to changes the classification from // 'identifier' to 'keyword'. - currentClassifiedSpan = delegationService.AdjustStaleClassification( - classificationService, currentText, currentClassifiedSpan); + currentClassifiedSpan = classificationService.AdjustStaleClassification(currentText, currentClassifiedSpan); classifiedSpans.Add(currentClassifiedSpan); } @@ -420,14 +412,13 @@ public IEnumerable> GetTags(NormalizedSnapshotSpanC ClassificationUtilities.ReturnClassifiedSpanList(tempList); } - private void AddClassifiedSpansForTokens( - IClassificationDelegationService delegationService, - TClassificationService classificationService, + private void AddClassifiedSpansForTokens( + IClassificationService classificationService, SnapshotSpan span, List classifiedSpans) { - delegationService.AddLexicalClassifications( - classificationService, span.Snapshot.AsText(), span.Span.ToTextSpan(), classifiedSpans, CancellationToken.None); + classificationService.AddLexicalClassifications( + span.Snapshot.AsText(), span.Span.ToTextSpan(), classifiedSpans, CancellationToken.None); } private void OnDocumentActiveContextChanged(object sender, DocumentActiveContextChangedEventArgs args) diff --git a/src/EditorFeatures/Core/Implementation/IntelliSense/QuickInfo/IntellisenseQuickInfoBuilder.cs b/src/EditorFeatures/Core/Implementation/IntelliSense/QuickInfo/IntellisenseQuickInfoBuilder.cs index 485e4267405..6b581eb44c3 100644 --- a/src/EditorFeatures/Core/Implementation/IntelliSense/QuickInfo/IntellisenseQuickInfoBuilder.cs +++ b/src/EditorFeatures/Core/Implementation/IntelliSense/QuickInfo/IntellisenseQuickInfoBuilder.cs @@ -100,7 +100,7 @@ internal static class IntellisenseQuickInfoBuilder var classifiedSpanList = new List(); foreach (var span in quickInfoItem.RelatedSpans) { - var classifiedSpans = await EditorClassifier.GetClassifiedSpansAsync(document, span, cancellationToken).ConfigureAwait(false); + var classifiedSpans = await ClassifierHelper.GetClassifiedSpansAsync(document, span, cancellationToken).ConfigureAwait(false); classifiedSpanList.AddRange(classifiedSpans); } diff --git a/src/EditorFeatures/Core/Microsoft.CodeAnalysis.EditorFeatures.csproj b/src/EditorFeatures/Core/Microsoft.CodeAnalysis.EditorFeatures.csproj index f0d8990333a..78c60c5e885 100644 --- a/src/EditorFeatures/Core/Microsoft.CodeAnalysis.EditorFeatures.csproj +++ b/src/EditorFeatures/Core/Microsoft.CodeAnalysis.EditorFeatures.csproj @@ -13,7 +13,7 @@ Microsoft.CodeAnalysis.EditorFeatures.Common true - .NET Compiler Platform ("Roslyn") support for editor features inside the Visual Studio editor. + .NET Compiler Platform ("Roslyn") support for editor features inside the Visual Studio editor. @@ -53,6 +53,7 @@ + - <_File Include="%(_File.RootDir)%(_File.Directory)%(_File.FileName).xml" TargetDir="%(_File.TargetDir)" Condition="Exists('%(_File.RootDir)%(_File.Directory)%(_File.FileName).xml')"/> + <_File Include="%(_File.RootDir)%(_File.Directory)%(_File.FileName).xml" TargetDir="%(_File.TargetDir)" Condition="Exists('%(_File.RootDir)%(_File.Directory)%(_File.FileName).xml')" /> diff --git a/src/Tools/ExternalAccess/FSharp/Classification/FSharpClassificationService.cs b/src/Tools/ExternalAccess/FSharp/Classification/FSharpClassificationService.cs new file mode 100644 index 00000000000..4ac8d71e4c9 --- /dev/null +++ b/src/Tools/ExternalAccess/FSharp/Classification/FSharpClassificationService.cs @@ -0,0 +1,66 @@ +// 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.Collections.Generic; +using System.Composition; +using System.Threading; +using System.Threading.Tasks; +using Microsoft.CodeAnalysis.Classification; +using Microsoft.CodeAnalysis.Host.Mef; +using Microsoft.CodeAnalysis.Text; +using Microsoft.CodeAnalysis.Editor; +using Microsoft.CodeAnalysis.Host; + +namespace Microsoft.CodeAnalysis.ExternalAccess.Classification +{ + [ExportLanguageServiceFactory(typeof(IClassificationService), LanguageNames.FSharp), Shared] + internal class FSharpClassificationServiceFactory : ILanguageServiceFactory + { +#pragma warning disable CS0618 // Type or member is obsolete + public ILanguageService CreateLanguageService(HostLanguageServices languageServices) + { + return new ProxyService(languageServices.GetService()); + } + + private class ProxyService : IClassificationService + { + private readonly IEditorClassificationService _delegatee; + + public ProxyService(IEditorClassificationService classificationService) + { + // connect to existing FSharp classification service that uses old obsolete service and + // export as new classification service. + // this is a temporary until fsharp team get our new bits + _delegatee = classificationService ?? new NullService(); + } + + public void AddLexicalClassifications(SourceText text, TextSpan textSpan, List result, CancellationToken cancellationToken) + { + _delegatee.AddLexicalClassifications(text, textSpan, result, cancellationToken); + } + + public Task AddSemanticClassificationsAsync(Document document, TextSpan textSpan, List result, CancellationToken cancellationToken) + { + return _delegatee.AddSemanticClassificationsAsync(document, textSpan, result, cancellationToken); + } + + public Task AddSyntacticClassificationsAsync(Document document, TextSpan textSpan, List result, CancellationToken cancellationToken) + { + return _delegatee.AddSyntacticClassificationsAsync(document, textSpan, result, cancellationToken); + } + + public ClassifiedSpan AdjustStaleClassification(SourceText text, ClassifiedSpan classifiedSpan) + { + return _delegatee.AdjustStaleClassification(text, classifiedSpan); + } + + private class NullService : IEditorClassificationService + { + public void AddLexicalClassifications(SourceText text, TextSpan textSpan, List result, CancellationToken cancellationToken) { } + public Task AddSemanticClassificationsAsync(Document document, TextSpan textSpan, List result, CancellationToken cancellationToken) => Task.CompletedTask; + public Task AddSyntacticClassificationsAsync(Document document, TextSpan textSpan, List result, CancellationToken cancellationToken) => Task.CompletedTask; + public ClassifiedSpan AdjustStaleClassification(SourceText text, ClassifiedSpan classifiedSpan) => classifiedSpan; + } + } +#pragma warning restore CS0618 // Type or member is obsolete + } +} diff --git a/src/Tools/ExternalAccess/FSharp/Microsoft.CodeAnalysis.ExternalAccess.FSharp.csproj b/src/Tools/ExternalAccess/FSharp/Microsoft.CodeAnalysis.ExternalAccess.FSharp.csproj index 7df36240c35..b5b6d8f3539 100644 --- a/src/Tools/ExternalAccess/FSharp/Microsoft.CodeAnalysis.ExternalAccess.FSharp.csproj +++ b/src/Tools/ExternalAccess/FSharp/Microsoft.CodeAnalysis.ExternalAccess.FSharp.csproj @@ -14,7 +14,7 @@ https://github.com/Microsoft/visualfsharp - +