提交 b8e35af4 编写于 作者: D David Poeschl

Merge pull request #891 from dpoeschl/HierarchicalFindRefs

Hierarchical Find References
// 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;
namespace Microsoft.VisualStudio.LanguageServices.Implementation.Library.FindResults
{
internal abstract class AbstractListItem
{
public ushort GlyphIndex { get; private set; }
public string DisplayText { get; private set; }
public ushort DisplaySelectionStart { get; private set; }
public ushort DisplaySelectionLength { get; private set; }
protected AbstractListItem(ushort glyphIndex)
{
this.GlyphIndex = glyphIndex;
}
protected void SetDisplayProperties(string filePath, int mappedLineNumber, int mappedOffset, int lineNumber, int offset, string lineText, int spanLength)
{
// TODO: Old C# code base has a helper, GetLineTextWithUnicodeDirectionMarkersIfNeeded, which we will need at some point.
var sourceSnippet = lineText.Replace('\t', ' ').TrimStart(' ');
var displayText = GetDisplayText(filePath, mappedLineNumber + 1, mappedOffset + 1, sourceSnippet);
var selectionStart = offset + displayText.Length - lineText.Length;
displayText = displayText.TrimEnd();
if (displayText.Length > ushort.MaxValue)
{
displayText = displayText.Substring(0, ushort.MaxValue);
}
this.DisplayText = displayText;
this.DisplaySelectionStart = checked((ushort)Math.Min(ushort.MaxValue, selectionStart));
this.DisplaySelectionLength = checked((ushort)Math.Min(spanLength, DisplayText.Length - DisplaySelectionStart));
}
private static string GetDisplayText(string fileName, int lineNumber, int offset, string sourceText)
{
if (string.IsNullOrWhiteSpace(fileName))
{
return string.Format("({0}, {1}) : {2}", lineNumber, offset, sourceText);
}
else
{
return string.Format("{0} - ({1}, {2}) : {3}", fileName, lineNumber, offset, sourceText);
}
}
public abstract int GoToSource();
}
}
......@@ -4,7 +4,6 @@
using System.Linq;
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.FindSymbols;
using Microsoft.CodeAnalysis.Host;
using Microsoft.CodeAnalysis.Navigation;
using Microsoft.CodeAnalysis.Shared.Extensions;
using Microsoft.CodeAnalysis.Text;
......@@ -35,12 +34,14 @@ public void PresentReferencedSymbols(string title, Solution solution, IEnumerabl
PresentObjectList(title, new ObjectList(CreateFindReferencesItems(solution, items), this));
}
private IList<AbstractListItem> CreateFindReferencesItems(Solution solution, IEnumerable<ReferencedSymbol> referencedSymbols)
private IList<AbstractTreeItem> CreateFindReferencesItems(Solution solution, IEnumerable<ReferencedSymbol> referencedSymbols)
{
var list = new List<AbstractListItem>();
HashSet<ValueTuple<Document, TextSpan>> uniqueLocations = null;
var definitions = new List<AbstractTreeItem>();
var uniqueLocations = new HashSet<ValueTuple<Document, TextSpan>>();
var symbolNavigationService = solution.Workspace.Services.GetService<ISymbolNavigationService>();
referencedSymbols = referencedSymbols.FilterUnreferencedSyntheticDefinitions().ToList();
foreach (var referencedSymbol in referencedSymbols)
{
if (!IncludeDefinition(referencedSymbol))
......@@ -50,30 +51,60 @@ private IList<AbstractListItem> CreateFindReferencesItems(Solution solution, IEn
var definition = referencedSymbol.Definition;
var locations = definition.Locations;
uniqueLocations = AddLocations(solution, list, uniqueLocations, locations, definition.GetGlyph());
uniqueLocations = AddLocations(solution, list, uniqueLocations, referencedSymbol.Locations.Select(loc => loc.Location), Glyph.Reference);
string filePath;
int lineNumber, charOffset;
var symbolNavigationService = solution.Workspace.Services.GetService<ISymbolNavigationService>();
foreach (var definitionLocation in definition.Locations)
{
var definitionItem = ConvertToDefinitionItem(solution, referencedSymbol, uniqueLocations, definitionLocation, definition.GetGlyph());
if (definitionItem != null)
{
definitions.Add(definitionItem);
var referenceItems = CreateReferenceItems(solution, uniqueLocations, referencedSymbol.Locations.Select(loc => loc.Location), Glyph.Reference);
definitionItem.Children.AddRange(referenceItems);
(definitionItem as ITreeItemWithReferenceCount)?.SetReferenceCount(referenceItems.Count);
}
}
// Add on any definition locations from third party language services
string filePath;
int lineNumber, charOffset;
if (symbolNavigationService.WouldNavigateToSymbol(definition, solution, out filePath, out lineNumber, out charOffset))
{
list.Add(new ExternalListItem(filePath, lineNumber, charOffset, definition.Name, definition.GetGlyph().GetGlyphIndex(), this.ServiceProvider));
definitions.Add(new ExternalLanguageDefinitionTreeItem(filePath, lineNumber, charOffset, definition.Name, definition.GetGlyph().GetGlyphIndex(), this.ServiceProvider));
}
}
return list;
return definitions;
}
private HashSet<ValueTuple<Document, TextSpan>> AddLocations(
private AbstractTreeItem ConvertToDefinitionItem(
Solution solution,
List<AbstractListItem> list,
ReferencedSymbol referencedSymbol,
HashSet<ValueTuple<Document, TextSpan>> uniqueLocations,
IEnumerable<Location> locations,
Location location,
Glyph glyph)
{
if (!location.IsInSource)
{
return referencedSymbol.Locations.Any()
? new MetadataDefinitionTreeItem(referencedSymbol.Definition, glyph.GetGlyphIndex())
: null;
}
var document = solution.GetDocument(location.SourceTree);
var sourceSpan = location.SourceSpan;
if (!IsValidSourceLocation(document, sourceSpan) ||
!uniqueLocations.Add(new ValueTuple<Document, TextSpan>(document, sourceSpan)))
{
return null;
}
return new SourceDefinitionTreeItem(document, sourceSpan, referencedSymbol.Definition, glyph.GetGlyphIndex());
}
private IList<SourceReferenceTreeItem> CreateReferenceItems(Solution solution, HashSet<ValueTuple<Document, TextSpan>> uniqueLocations, IEnumerable<Location> locations, Glyph glyph)
{
var referenceItems = new List<SourceReferenceTreeItem>();
foreach (var location in locations)
{
if (!location.IsInSource)
......@@ -88,15 +119,20 @@ private IList<AbstractListItem> CreateFindReferencesItems(Solution solution, IEn
continue;
}
uniqueLocations = uniqueLocations ?? new HashSet<ValueTuple<Document, TextSpan>>();
if (uniqueLocations.Add(new ValueTuple<Document, TextSpan>(document, sourceSpan)))
{
list.Add(new SourceListItem(document, sourceSpan, glyph.GetGlyphIndex()));
referenceItems.Add(new SourceReferenceTreeItem(document, sourceSpan, glyph.GetGlyphIndex()));
}
}
return uniqueLocations;
var linkedReferences = referenceItems.GroupBy(r => r.DisplayText.ToLowerInvariant()).Where(g => g.Count() > 1).SelectMany(g => g);
foreach (var linkedReference in linkedReferences)
{
linkedReference.AddProjectNameDisambiguator();
}
referenceItems.Sort();
return referenceItems;
}
}
}
......@@ -11,12 +11,12 @@ namespace Microsoft.VisualStudio.LanguageServices.Implementation.Library.FindRes
{
internal partial class LibraryManager
{
private IList<AbstractListItem> CreateGoToDefinitionItems(IEnumerable<INavigableItem> items)
private IList<AbstractTreeItem> CreateGoToDefinitionItems(IEnumerable<INavigableItem> items)
{
var sourceListItems =
from item in items
where IsValidSourceLocation(item.Document, item.SourceSpan)
select (AbstractListItem)new SourceListItem(item.Document, item.SourceSpan, item.Glyph.GetGlyphIndex());
select (AbstractTreeItem)new SourceReferenceTreeItem(item.Document, item.SourceSpan, item.Glyph.GetGlyphIndex());
return sourceListItems.ToList();
}
......
......@@ -4,14 +4,15 @@
using Microsoft.CodeAnalysis;
using Microsoft.VisualStudio.LanguageServices.Implementation.Utilities;
using Microsoft.VisualStudio.Shell.Interop;
using System.Linq;
namespace Microsoft.VisualStudio.LanguageServices.Implementation.Library.FindResults
{
internal class ObjectList : AbstractObjectList<LibraryManager>
{
private readonly IList<AbstractListItem> _items;
private readonly IList<AbstractTreeItem> _items;
public ObjectList(IList<AbstractListItem> items, LibraryManager manager)
public ObjectList(IList<AbstractTreeItem> items, LibraryManager manager)
: base(manager)
{
_items = items;
......@@ -27,10 +28,10 @@ protected override bool CanGoToSource(uint index, VSOBJGOTOSRCTYPE srcType)
return true;
case VSOBJGOTOSRCTYPE.GS_DEFINITION:
return item.GlyphIndex != Glyph.Reference.GetGlyphIndex();
return item.GlyphIndex != Glyph.Reference.GetGlyphIndex() && item.CanGoToSource;
case VSOBJGOTOSRCTYPE.GS_REFERENCE:
return item.GlyphIndex == Glyph.Reference.GetGlyphIndex();
return item.GlyphIndex == Glyph.Reference.GetGlyphIndex() && item.CanGoToSource;
}
return false;
......@@ -56,13 +57,20 @@ protected override void GetDisplayData(uint index, ref VSTREEDISPLAYDATA data)
data.Image = item.GlyphIndex;
data.SelectedImage = item.GlyphIndex;
data.State |= (uint)_VSTREEDISPLAYSTATE.TDS_FORCESELECT;
if (item.UseGrayText)
{
data.State |= (uint)_VSTREEDISPLAYSTATE.TDS_GRAYTEXT;
}
data.ForceSelectStart = item.DisplaySelectionStart;
data.ForceSelectLength = item.DisplaySelectionLength;
}
protected override bool GetExpandable(uint index, uint listTypeExcluded)
{
return false;
var item = _items[(int)index];
return (item?.Children?.Any() == true);
}
protected override uint GetItemCount()
......@@ -72,7 +80,8 @@ protected override uint GetItemCount()
protected override IVsSimpleObjectList2 GetList(uint index, uint listType, uint flags, VSOBSEARCHCRITERIA2[] pobSrch)
{
return null;
var item = _items[(int)index];
return (item?.Children?.Any() == true) ? new ObjectList(item.Children, LibraryManager) : null;
}
protected override string GetText(uint index, VSTREETEXTOPTIONS tto)
......
......@@ -2,7 +2,6 @@
using System.Threading;
using Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.Host;
using Microsoft.CodeAnalysis.Navigation;
using Microsoft.CodeAnalysis.Text;
using Microsoft.VisualStudio.LanguageServices.Implementation.Extensions;
......@@ -11,32 +10,35 @@
namespace Microsoft.VisualStudio.LanguageServices.Implementation.Library.FindResults
{
internal class SourceListItem : AbstractListItem
internal abstract class AbstractSourceTreeItem : AbstractTreeItem
{
private readonly Workspace _workspace;
private readonly DocumentId _documentId;
private readonly int _lineNumber;
private readonly int _offset;
protected readonly Workspace _workspace;
protected readonly DocumentId _documentId;
protected readonly string _projectName;
protected readonly string _filePath;
protected readonly TextSpan _sourceSpan;
protected readonly string _textLineString;
protected readonly int _lineNumber;
protected readonly int _offset;
protected readonly int _mappedLineNumber;
protected readonly int _mappedOffset;
public SourceListItem(Location location, Solution solution, ushort glyphIndex)
: this(solution.GetDocument(location.SourceTree), location.SourceSpan, glyphIndex)
public AbstractSourceTreeItem(Document document, TextSpan sourceSpan, ushort glyphIndex)
: base (glyphIndex)
{
}
public SourceListItem(Document document, TextSpan sourceSpan, ushort glyphIndex)
: base(glyphIndex)
{
_workspace = document.Project.Solution.Workspace;
// We store the document ID, line and offset for navigation so that we
// still provide reasonable navigation if the user makes changes elsewhere
// in the document other than inserting or removing lines.
_documentId = document.Id;
var filePath = document.FilePath;
_workspace = document.Project.Solution.Workspace;
_documentId = document.Id;
_projectName = document.Project.Name;
_filePath = document.FilePath;
_sourceSpan = sourceSpan;
var text = document.GetTextAsync(CancellationToken.None).WaitAndGetResult(CancellationToken.None);
var textLine = text.Lines.GetLineFromPosition(sourceSpan.Start);
var textLine = text.Lines.GetLineFromPosition(_sourceSpan.Start);
_textLineString = textLine.ToString();
_lineNumber = textLine.LineNumber;
_offset = sourceSpan.Start - textLine.Start;
......@@ -44,12 +46,11 @@ public SourceListItem(Document document, TextSpan sourceSpan, ushort glyphIndex)
var spanInSecondaryBuffer = text.GetVsTextSpanForLineOffset(_lineNumber, _offset);
VsTextSpan spanInPrimaryBuffer;
var succeeded = spanInSecondaryBuffer.TryMapSpanFromSecondaryBufferToPrimaryBuffer(_workspace, document.Id, out spanInPrimaryBuffer);
var succeeded = spanInSecondaryBuffer.TryMapSpanFromSecondaryBufferToPrimaryBuffer(_workspace, _documentId, out spanInPrimaryBuffer);
var mappedLineNumber = succeeded ? spanInPrimaryBuffer.iStartLine : _lineNumber;
var mappedOffset = succeeded ? spanInPrimaryBuffer.iStartIndex : _offset;
_mappedLineNumber = succeeded ? spanInPrimaryBuffer.iStartLine : _lineNumber;
_mappedOffset = succeeded ? spanInPrimaryBuffer.iStartIndex : _offset;
SetDisplayProperties(filePath, mappedLineNumber, mappedOffset, _lineNumber, _offset, textLine.ToString(), sourceSpan.Length);
}
public override int GoToSource()
......
// 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 Microsoft.CodeAnalysis;
namespace Microsoft.VisualStudio.LanguageServices.Implementation.Library.FindResults
{
internal abstract class AbstractTreeItem
{
public IList<AbstractTreeItem> Children { get; protected set; }
public ushort GlyphIndex { get; protected set; }
// TODO: Old C# code base has a helper, GetLineTextWithUnicodeDirectionMarkersIfNeeded, which we will need at some point.
public string DisplayText { get; protected set; }
public ushort DisplaySelectionStart { get; protected set; }
public ushort DisplaySelectionLength { get; protected set; }
public virtual bool UseGrayText
{
get
{
return false;
}
}
public virtual bool CanGoToSource
{
get
{
return true;
}
}
protected static readonly SymbolDisplayFormat definitionDisplayFormat =
new SymbolDisplayFormat(
typeQualificationStyle: SymbolDisplayTypeQualificationStyle.NameAndContainingTypesAndNamespaces,
genericsOptions: SymbolDisplayGenericsOptions.IncludeTypeParameters,
parameterOptions: SymbolDisplayParameterOptions.IncludeType,
propertyStyle: SymbolDisplayPropertyStyle.ShowReadWriteDescriptor,
delegateStyle: SymbolDisplayDelegateStyle.NameAndSignature,
kindOptions: SymbolDisplayKindOptions.IncludeMemberKeyword | SymbolDisplayKindOptions.IncludeNamespaceKeyword | SymbolDisplayKindOptions.IncludeTypeKeyword,
localOptions: SymbolDisplayLocalOptions.IncludeType,
memberOptions:
SymbolDisplayMemberOptions.IncludeAccessibility |
SymbolDisplayMemberOptions.IncludeContainingType |
SymbolDisplayMemberOptions.IncludeExplicitInterface |
SymbolDisplayMemberOptions.IncludeModifiers |
SymbolDisplayMemberOptions.IncludeParameters |
SymbolDisplayMemberOptions.IncludeType,
miscellaneousOptions:
SymbolDisplayMiscellaneousOptions.EscapeKeywordIdentifiers |
SymbolDisplayMiscellaneousOptions.UseSpecialTypes);
protected AbstractTreeItem(ushort glyphIndex)
{
this.Children = new List<AbstractTreeItem>();
this.GlyphIndex = glyphIndex;
}
public abstract int GoToSource();
protected void SetDisplayProperties(string filePath, int mappedLineNumber, int mappedOffset, int offset, string lineText, int spanLength, string projectNameDisambiguator)
{
var sourceSnippet = lineText.Replace('\t', ' ').TrimStart(' ');
var displayText = GetDisplayText(filePath, projectNameDisambiguator, mappedLineNumber + 1, mappedOffset + 1, sourceSnippet);
var selectionStart = offset + displayText.Length - lineText.Length;
displayText = displayText.TrimEnd();
if (displayText.Length > ushort.MaxValue)
{
displayText = displayText.Substring(0, ushort.MaxValue);
}
this.DisplayText = displayText;
this.DisplaySelectionStart = checked((ushort)Math.Min(ushort.MaxValue, selectionStart));
this.DisplaySelectionLength = checked((ushort)Math.Min(spanLength, DisplayText.Length - DisplaySelectionStart));
}
private static string GetDisplayText(string fileName, string projectNameDisambiguator, int lineNumber, int offset, string sourceText)
{
var fileLocationDescription = GetFileLocationsText(fileName, projectNameDisambiguator);
return string.IsNullOrWhiteSpace(fileLocationDescription)
? $"({lineNumber}, {offset}) : {sourceText}"
: $"{fileLocationDescription} - ({lineNumber}, {offset}) : {sourceText}";
}
private static string GetFileLocationsText(string fileName, string projectNameDisambiguator)
{
if (!string.IsNullOrWhiteSpace(fileName) && !string.IsNullOrWhiteSpace(projectNameDisambiguator))
{
return $"{fileName} [{projectNameDisambiguator}]";
}
if (!string.IsNullOrWhiteSpace(fileName))
{
return fileName;
}
if (!string.IsNullOrWhiteSpace(projectNameDisambiguator))
{
return $"[{projectNameDisambiguator}]";
}
return string.Empty;
}
}
}
......@@ -9,14 +9,17 @@
namespace Microsoft.VisualStudio.LanguageServices.Implementation.Library.FindResults
{
internal class ExternalListItem : AbstractListItem
internal class ExternalLanguageDefinitionTreeItem : AbstractTreeItem
{
private readonly IServiceProvider _serviceProvider;
private readonly string _filePath;
private readonly int _lineNumber;
private readonly int _charOffset;
public ExternalListItem(string filePath, int lineNumber, int offset, string symbolName, ushort glyphIndex, IServiceProvider serviceProvider)
/// <summary>
/// A definition from an external language service (e.g. xaml).
/// </summary>
public ExternalLanguageDefinitionTreeItem(string filePath, int lineNumber, int offset, string symbolName, ushort glyphIndex, IServiceProvider serviceProvider)
: base(glyphIndex)
{
_filePath = filePath;
......@@ -24,7 +27,14 @@ public ExternalListItem(string filePath, int lineNumber, int offset, string symb
_charOffset = offset;
_serviceProvider = serviceProvider;
SetDisplayProperties(filePath, lineNumber, offset, lineNumber, offset, GetSourceLine(filePath, lineNumber, serviceProvider), symbolName.Length);
SetDisplayProperties(
filePath,
lineNumber,
offset,
offset,
GetSourceLine(filePath, lineNumber, serviceProvider),
symbolName.Length,
projectNameDisambiguator: string.Empty);
}
private static string GetSourceLine(string filePath, int lineNumber, IServiceProvider serviceProvider)
......
// 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.VisualStudio.LanguageServices.Implementation.Library.FindResults
{
internal interface ITreeItemWithReferenceCount
{
void SetReferenceCount(int referenceCount);
}
}
// 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 Microsoft.CodeAnalysis;
namespace Microsoft.VisualStudio.LanguageServices.Implementation.Library.FindResults
{
internal class MetadataDefinitionTreeItem : AbstractTreeItem, ITreeItemWithReferenceCount
{
private readonly string _assemblyName;
private readonly string _symbolDefinition;
public override bool CanGoToSource
{
get
{
return false;
}
}
public override bool UseGrayText
{
get
{
return true;
}
}
public MetadataDefinitionTreeItem(ISymbol definition, ushort glyphIndex)
: base(glyphIndex)
{
_assemblyName = definition.ContainingAssembly.ToDisplayString(SymbolDisplayFormat.MinimallyQualifiedFormat);
_symbolDefinition = definition.ToDisplayString(definitionDisplayFormat);
this.DisplayText = $"[{_assemblyName}] {_symbolDefinition}";
}
public override int GoToSource()
{
return VSConstants.E_NOTIMPL;
}
public void SetReferenceCount(int referenceCount)
{
if (referenceCount > 0)
{
var referenceCountDisplay = referenceCount == 1
? string.Format(ServicesVSResources.ReferenceCountSingular, referenceCount)
: string.Format(ServicesVSResources.ReferenceCountPlural, referenceCount);
this.DisplayText = $"[{_assemblyName}] {_symbolDefinition} ({referenceCountDisplay})";
}
}
}
}
// 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 Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.Text;
namespace Microsoft.VisualStudio.LanguageServices.Implementation.Library.FindResults
{
internal class SourceDefinitionTreeItem : AbstractSourceTreeItem, ITreeItemWithReferenceCount
{
private readonly string _symbolDisplay;
public SourceDefinitionTreeItem(Document document, TextSpan sourceSpan, ISymbol symbol, ushort glyphIndex)
: base(document, sourceSpan, glyphIndex)
{
_symbolDisplay = symbol.ToDisplayString(definitionDisplayFormat);
this.DisplayText = $"[{document.Project.Name}] {_symbolDisplay}";
}
public void SetReferenceCount(int referenceCount)
{
if (referenceCount > 0)
{
var referenceCountDisplay = referenceCount == 1
? string.Format(ServicesVSResources.ReferenceCountSingular, referenceCount)
: string.Format(ServicesVSResources.ReferenceCountPlural, referenceCount);
this.DisplayText = $"[{_projectName}] {_symbolDisplay} ({referenceCountDisplay})";
}
}
}
}
// 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 Microsoft.CodeAnalysis;
using Microsoft.CodeAnalysis.Text;
namespace Microsoft.VisualStudio.LanguageServices.Implementation.Library.FindResults
{
internal class SourceReferenceTreeItem : AbstractSourceTreeItem, IComparable<SourceReferenceTreeItem>
{
public SourceReferenceTreeItem(Location location, Solution solution, ushort glyphIndex)
: this(solution.GetDocument(location.SourceTree), location.SourceSpan, glyphIndex)
{
}
public SourceReferenceTreeItem(Document document, TextSpan sourceSpan, ushort glyphIndex)
: this (document, sourceSpan, glyphIndex, includeProjectNameDisambiguator: false)
{
}
public SourceReferenceTreeItem(Document document, TextSpan sourceSpan, ushort glyphIndex, bool includeProjectNameDisambiguator)
: base(document, sourceSpan, glyphIndex)
{
SetDisplayProperties(
_filePath,
_mappedLineNumber,
_mappedOffset,
_offset,
_textLineString,
sourceSpan.Length,
projectNameDisambiguator: string.Empty);
}
public void AddProjectNameDisambiguator()
{
SetDisplayProperties(
_filePath,
_mappedLineNumber,
_mappedOffset,
_offset,
_textLineString,
_sourceSpan.Length,
projectNameDisambiguator: _projectName);
}
int IComparable<SourceReferenceTreeItem>.CompareTo(SourceReferenceTreeItem other)
{
if (other == null)
{
return 1;
}
int compare = _filePath.CompareTo(other._filePath);
compare = compare != 0 ? compare : _lineNumber.CompareTo(other._lineNumber);
compare = compare != 0 ? compare : _offset.CompareTo(other._offset);
compare = compare != 0 ? compare : _projectName.CompareTo(other._projectName);
return compare;
}
}
}
......@@ -840,6 +840,24 @@ internal class ServicesVSResources {
}
}
/// <summary>
/// Looks up a localized string similar to {0} references.
/// </summary>
internal static string ReferenceCountPlural {
get {
return ResourceManager.GetString("ReferenceCountPlural", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to {0} reference.
/// </summary>
internal static string ReferenceCountSingular {
get {
return ResourceManager.GetString("ReferenceCountSingular", resourceCulture);
}
}
/// <summary>
/// Looks up a localized string similar to The following references were not found. {0}Please locate and add them manually..
/// </summary>
......
......@@ -447,4 +447,10 @@ Use the dropdown to view and switch to other projects this file may belong to.</
<data name="WRN_AnalyzerDependencyConflictMessage" xml:space="preserve">
<value>Assembly '{0}' used by analyzer '{1}' and assembly '{2}' used by analyzer '{3}' have the same identity but different contents. These analyzers may not run correctly.</value>
</data>
<data name="ReferenceCountPlural" xml:space="preserve">
<value>{0} references</value>
</data>
<data name="ReferenceCountSingular" xml:space="preserve">
<value>{0} reference</value>
</data>
</root>
\ No newline at end of file
......@@ -23,6 +23,10 @@
<Compile Include="Implementation\AnalyzerDependencyConflict.cs" />
<Compile Include="Implementation\CompilationErrorTelemetry\CompilationErrorTelemetryIncrementalAnalyzer.cs" />
<Compile Include="Implementation\Diagnostics\VisualStudioVenusSpanMappingService.cs" />
<Compile Include="Implementation\Library\FindResults\TreeItems\AbstractSourceTreeItem.cs" />
<Compile Include="Implementation\Library\FindResults\TreeItems\ITreeItemWithReferenceCount.cs" />
<Compile Include="Implementation\Library\FindResults\TreeItems\MetadataDefinitionTreeItem.cs" />
<Compile Include="Implementation\Library\FindResults\TreeItems\SourceDefinitionTreeItem.cs" />
<Compile Include="Implementation\Preview\ReferenceChange.MetadataReferenceChange.cs" />
<Compile Include="Implementation\Preview\ReferenceChange.AnalyzerReferenceChange.cs" />
<Compile Include="Implementation\Preview\ReferenceChange.ProjectReferenceChange.cs" />
......@@ -418,14 +422,14 @@
<Compile Include="Implementation\Library\AbstractLibraryManager_IVsLibraryMgr.cs" />
<Compile Include="Implementation\Library\AbstractLibraryManager_IVsSimpleLibrary2.cs" />
<Compile Include="Implementation\Library\AbstractObjectList.cs" />
<Compile Include="Implementation\Library\FindResults\AbstractListItem.cs" />
<Compile Include="Implementation\Library\FindResults\ExternalListItem.cs" />
<Compile Include="Implementation\Library\FindResults\TreeItems\AbstractTreeItem.cs" />
<Compile Include="Implementation\Library\FindResults\TreeItems\ExternalLanguageDefinitionTreeItem.cs" />
<Compile Include="Implementation\Library\FindResults\LibraryManager.cs" />
<Compile Include="Implementation\Library\FindResults\LibraryManager_FindReferences.cs" />
<Compile Include="Implementation\Library\FindResults\LibraryManager_GoToDefinition.cs" />
<Compile Include="Implementation\Library\FindResults\NavInfo.cs" />
<Compile Include="Implementation\Library\FindResults\ObjectList.cs" />
<Compile Include="Implementation\Library\FindResults\SourceListItem.cs" />
<Compile Include="Implementation\Library\FindResults\TreeItems\SourceReferenceTreeItem.cs" />
<Compile Include="Implementation\Library\ObjectBrowser\AbstractDescriptionBuilder.cs" />
<Compile Include="Implementation\Library\ObjectBrowser\AbstractDescriptionBuilder.LinkFlags.cs" />
<Compile Include="Implementation\Library\ObjectBrowser\AbstractObjectBrowserLibraryManager.cs" />
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册