这是我能获取到的内容,我认为它与您所需的内容非常相似。如果您有问题,我将通过更新更多详细信息来解决。
![VS 2010图标修饰](https://istack.dev59.com/glDmI.webp)
我是从VS 2010 SDK网站的这个示例开始的。它已经非常接近您所需的内容,但需要进行几个步骤。
下载C#版本,解压到一个文件夹中,编译。要运行它并测试,您需要转到项目>属性>调试
您需要选择 "启动外部程序 "选项,并设置路径到您的 VS 2010 应用程序,例如:C:\Program Files (x86)\Microsoft Visual Studio 10.0\Common7\IDE\devenv.exe
在命令行参数中设置:/rootsuffix Exp
现在,您应该能够运行它,在打开的 VS 中创建一些示例项目,如果您在任何地方键入六位数字,如00AA00
,它将显示为具有相应颜色的矩形。关闭调试的 VS 实例。
现在让我们编辑一些代码。在 ColorAdornmentTagger.cs
中注释掉定义 #define HIDING_TEXT
。这将显示修饰品在文本旁边而不是替换它。
在同一文件中,您需要找到初始化SnapshotSpan adornmentSpan
的位置,并将该行更改为:
SnapshotSpan adornmentSpan = new SnapshotSpan(colorTagSpans[0].End, 0);
这将在文本范围之后放置修饰,而不是之前。
在ColorTagger.cs
中。更改构造函数中的正则表达式,使构造函数现在如下所示
internal ColorTagger(ITextBuffer buffer)
: base(
buffer,
new[] { new Regex(@"/// <summary>.*", RegexOptions.Compiled | RegexOptions.CultureInvariant | RegexOptions.IgnoreCase) }
)
{
}
这将设置正则表达式以识别方法注释行。
在这个类中的其它方法我们不会用到,你可以将它们注释掉或者返回一些随机颜色。
在 'ColorAdornment.cs' 中。这是 WPF 控件本身的修饰。首先将基类从 Button
更改为 ContentControl
。更改类的构造函数为
internal ColorAdornment(ColorTag colorTag)
{
BitmapImage image = new BitmapImage();
using (FileStream stream = File.OpenRead("c:\\temp\\sologo.png"))
{
image.BeginInit();
image.StreamSource = stream;
image.CacheOption = BitmapCacheOption.OnLoad;
image.EndInit();
}
this.Content = new Image() { Margin = new Thickness(20,0,0,0), Width = 100, Height = 30, Source = image };
}
您可以更改图像路径为您所需的图像路径。我只是从维基百科下载了SO标志并将其放入我的临时文件夹中。
编译并运行。您应该能够在调试VS实例的注释旁边看到SO标志。
一些额外的说明。
首先,通过这种方式,您只需获得一个可工作的原型,然后应根据您的需求重命名类并清理代码。
其次,在我调试它时,我的调试VS不时会冻结。我认为这可能与IntraTextAdornmentTagger.cs
中的锁有关。
如果您也遇到了冻结,请尝试以以下方式更新此方法:
protected void InvalidateSpans(IList<SnapshotSpan> spans)
{
if (spans.Count == 0)
return;
bool wasEmpty = false;
lock (this.invalidatedSpans)
{
wasEmpty = this.invalidatedSpans.Count == 0;
this.invalidatedSpans.AddRange(spans);
}
if (wasEmpty)
this.view.VisualElement.Dispatcher.BeginInvoke(new Action(AsyncUpdate));
}
并且可以通过以下方式进行AsyncUpdate:
private void AsyncUpdate()
{
if (this.snapshot != this.view.TextBuffer.CurrentSnapshot)
{
this.snapshot = this.view.TextBuffer.CurrentSnapshot;
Dictionary<SnapshotSpan, TAdornment> translatedAdornmentCache = new Dictionary<SnapshotSpan, TAdornment>();
foreach (var keyValuePair in this.adornmentCache)
translatedAdornmentCache.Add(keyValuePair.Key.TranslateTo(this.snapshot, SpanTrackingMode.EdgeExclusive), keyValuePair.Value);
this.adornmentCache = translatedAdornmentCache;
}
List<SnapshotSpan> spansCopy;
lock (this.invalidatedSpans)
{
spansCopy = this.invalidatedSpans.ToList();
this.invalidatedSpans.Clear();
}
List<SnapshotSpan> translatedSpans = spansCopy.Select(s => s.TranslateTo(this.snapshot, SpanTrackingMode.EdgeInclusive)).ToList();
if (translatedSpans.Count == 0)
return;
var start = translatedSpans.Select(span => span.Start).Min();
var end = translatedSpans.Select(span => span.End).Max();
RaiseTagsChanged(new SnapshotSpan(start, end));
}