2
我正在开发一个项目,在该项目中我们已将C#代码分解为函数,并将这些函数存储在IElisonBuffers之内。我有智能感知勾搭上了,并且缓冲器细其它扩展交互,如下图所示:向IElisonBuffer添加语法高亮
但是,我不能让语法高亮这些编辑器内工作。
我通过以下步骤嵌入这些编辑:
- 创建该文件的
IVsInvisibleEditor
。 - 获取
IVsTextLines
这IVsInvisibleEditor
- 创建
IVsCodeWindow
并设置缓冲区此IVsCodeWindow
是从IVsInvisibleEditor
- 的
IVsTextLines
获得从该代码窗口中IWpfTextViewHost
。这使我回到了“WPF Land”,我可以在这里与传统跨度进行交互。 - 创建
IWpfTextViewHost
的文本视图的SnapshotSpan。此SnapshotSpan包含一个功能。 - 创建一个包含SnapshotSpan的
IElisionBuffer
。 - 通过
IVsEditorAdaptersFactoryService.CreateVsTextBufferAdapterForSecondaryBuffer()
通过IElisionBuffer
创建IVsTextBuffer
。 - 现在我将
IVsTextBuffer
改为IVsTextLines
,并调用SetLanguageServiceID()
传入C#GUID:694DD9B6-B865-4C5B-AD85-86356E9C88DC。 - 我仔细检查它是否通过
GetLanguageServiceID()
正确设置,一切看起来都不错。 - 我创建了一个
IVsTextView
并使用新的IVsTextBuffer
进行初始化。 - 然后我得到这个
IVsTextView
的IWpfTextViewHost
。
在为IElisionBuffer设置语言服务ID时是否需要注意任何特殊步骤?
为了完整本的缘故是我使用的代码:
public CustomEditorViewModel CreateEditor(string filePath, int start, int end) {
IVsInvisibleEditor invisibleEditor;
ErrorHandler.ThrowOnFailure(this._InvisibleEditorManager.RegisterInvisibleEditor(
filePath
, pProject: null
, dwFlags: (uint)_EDITORREGFLAGS.RIEF_ENABLECACHING
, pFactory: null
, ppEditor: out invisibleEditor));
var docDataPointer = IntPtr.Zero;
Guid guidIVsTextLines = typeof(IVsTextLines).GUID;
ErrorHandler.ThrowOnFailure(
invisibleEditor.GetDocData(
fEnsureWritable: 1
, riid: ref guidIVsTextLines
, ppDocData: out docDataPointer));
IVsTextLines docData = (IVsTextLines)Marshal.GetObjectForIUnknown(docDataPointer);
//Createa a code window adapter
var codeWindow = _EditorAdapterFactory.CreateVsCodeWindowAdapter(VisualStudioServices.OLEServiceProvider);
//Associate our IVsTextLines with our new code window
ErrorHandler.ThrowOnFailure(codeWindow.SetBuffer(docData));
//Get our text view for our editor which we will use to get the WPF control that hosts that editor.
IVsTextView textView;
ErrorHandler.ThrowOnFailure(codeWindow.GetPrimaryView(out textView));
//This is our TextViewHost
//It transports us back into the land of WPF
IWpfTextViewHost textViewHost = _EditorAdapterFactory.GetWpfTextViewHost(textView);
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
//Now we need to subset TextBuffer somehow...
//~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
int length = end - start;
SnapshotSpan subsetSnapshot = new SnapshotSpan(textViewHost.TextView.TextSnapshot, start, length);
var CSharpType = _contentTypeRegistry.GetContentType("CSharp");
var projBuffer = _ProjectionBufferFactory.CreateElisionBuffer(
null
, new NormalizedSnapshotSpanCollection(subsetSnapshot)
, ElisionBufferOptions.None
,CSharpType);
IVsTextBuffer bufferAdapter = _EditorAdapterFactory.CreateVsTextBufferAdapterForSecondaryBuffer(VisualStudioServices.OLEServiceProvider, projBuffer);
//My attempt at getting syntax coloring to work:
Guid CSharpLanguageServiceId = new Guid("694DD9B6-B865-4C5B-AD85-86356E9C88DC");
IVsTextLines buffer = (IVsTextLines)bufferAdapter;
buffer.SetLanguageServiceID(ref CSharpLanguageServiceId);
IVsTextView projTextView = _EditorAdapterFactory.CreateVsTextViewAdapter(VisualStudioServices.OLEServiceProvider);
projTextView.Initialize(
(IVsTextLines)bufferAdapter
, IntPtr.Zero
, (uint)TextViewInitFlags.VIF_HSCROLL | (uint)TextViewInitFlags.VIF_VSCROLL | (uint)TextViewInitFlags3.VIF_NO_HWND_SUPPORT,
new[] { new INITVIEW { fSelectionMargin = 0, fWidgetMargin = 0, fVirtualSpace = 0, fDragDropMove = 0 } }
);
return _EditorAdapterFactory.GetWpfTextViewHost(projTextView);
}
如果我使用ProjectionContentType创建Elision Buffer,我会获得语法高亮显示,但在编辑器中会失去Intellisense和VsVim(插件不会像他们应该那样连接它)。 有没有手动设置语法高亮的选项?我担心手动设置智能感知会更困难。 – JoshVarty
感谢您的帮助。我的错误部分是由于内容类型不正确,部分原因是由于为单个文件创建了多个IVsInvisibleEditors。 – JoshVarty
我正在做类似的事情。但我正在使用不属于解决方案的临时文件路径。它有一些解析错误。那些解析错误出现在错误列表中,有没有告诉visual studio在错误列表窗口中不显示解析错误? – ravyoli