protected override async TPL.Task ProduceTagsAsync( TaggerContext <IClassificationTag> taggerContext, DocumentSnapshotSpan snapshotSpan) { // We should check this at the call site. // This a safety check to make sure we do this when // we introduce a new call site. Debug.Assert(snapshotSpan.Document != null); var document = snapshotSpan.Document; var cancellationToken = taggerContext.CancellationToken; var classificationService = document.Project.LanguageServices.GetService <IClassificationService>() as IRemoteClassificationService; if (classificationService == null) { return; } var classifiedSpans = ClassificationUtilities.GetOrCreateClassifiedSpanList(); var tagSpan = TextSpan.FromBounds(snapshotSpan.SnapshotSpan.Start, snapshotSpan.SnapshotSpan.End); await classificationService.AddRemoteSyntacticClassificationsAsync(document, tagSpan, classifiedSpans, cancellationToken).ConfigureAwait(false); ClassificationUtilities.Convert(_typeMap, snapshotSpan.SnapshotSpan.Snapshot, classifiedSpans, taggerContext.AddTag); ClassificationUtilities.ReturnClassifiedSpanList(classifiedSpans); }
private async Task EnqueueProcessSnapshotWorkerAsync(DocumentId documentId, CancellationToken cancellationToken) { var workspace = this._workspace; if (workspace == null) { return; } // This is an essentially arbitrary version of the document - we basically just want the path. var document = workspace.CurrentSolution.GetDocument(documentId); if (document == null) { return; } // Changes after this point might not be incorporated into the server response, so // allow scheduling of additional requests. int wasRequestPending = Interlocked.Exchange(ref this._isRequestPending, 0); Debug.Assert(wasRequestPending == 1); var classificationService = document.Project.LanguageServices.GetService <IClassificationService>() as IRemoteClassificationService; if (classificationService == null) { return; } var tree = await document.GetSyntaxTreeAsync(cancellationToken).ConfigureAwait(false); var text = await tree.GetTextAsync(cancellationToken).ConfigureAwait(false); var snapshot = text.FindCorrespondingEditorTextSnapshot(); if (snapshot == null) { return; } var classifiedSpans = ClassificationUtilities.GetOrCreateClassifiedSpanList(); await classificationService.AddRemoteSyntacticClassificationsAsync(document, TextSpan.FromBounds(0, tree.Length), classifiedSpans, cancellationToken).ConfigureAwait(false); using var tagSpans = SharedPools.Default <List <ITagSpan <IClassificationTag> > >().GetPooledObject(); ClassificationUtilities.Convert(_typeMap, snapshot, classifiedSpans, tagSpans.Object.Add); ClassificationUtilities.ReturnClassifiedSpanList(classifiedSpans); var tagList = new TagSpanList <IClassificationTag>(tagSpans.Object); Interlocked.Exchange(ref this._lastProcessedTagList, tagList); this.TagsChanged?.Invoke(this, new SnapshotSpanEventArgs(snapshot.GetFullSpan())); }