2009-07-07 55 views
27

我正在編寫一個自定義工具,並且我目前正在按照我想要的功能進行操作。如果出現問題,我希望能夠寫入Visual Studio。 (格式不正確的代碼或其他)。如何在我的自定義工具中寫入Visual Studio輸出窗口?

是否有這方面的任何標準?現在我基本上可以強制該工具失敗,並且Visual Studio會提示它已經這樣做了。我希望Output窗口中有一個類別以及我想發送的任何結果消息。我也可以在錯誤列表窗口中使用更具描述性的任務/警告。

+0

爲什麼不寫到標準輸出爲你工作? – avakar 2009-07-07 19:43:18

+0

向Console.Write寫入消息不會在輸出窗口中給我任何東西。 – 2009-07-07 20:11:23

回答

44

輸出窗口

要寫入「常規」輸出窗口在Visual Studio中,你需要做到以下幾點:

IVsOutputWindow outWindow = Package.GetGlobalService(typeof(SVsOutputWindow)) as IVsOutputWindow; 

Guid generalPaneGuid = VSConstants.GUID_OutWindowGeneralPane; // P.S. There's also the GUID_OutWindowDebugPane available. 
IVsOutputWindowPane generalPane; 
outWindow.GetPane(ref generalPaneGuid , out generalPane); 

generalPane.OutputString("Hello World!"); 
generalPane.Activate(); // Brings this pane into view 

但是,如果你想寫一個自定義窗口,這是你需要做的:在IVsOutputWindowIVsOutputWindowPane

IVsOutputWindow outWindow = Package.GetGlobalService(typeof(SVsOutputWindow)) as IVsOutputWindow; 

// Use e.g. Tools -> Create GUID to make a stable, but unique GUID for your pane. 
// Also, in a real project, this should probably be a static constant, and not a local variable 
Guid customGuid = new Guid("0F44E2D1-F5FA-4d2d-AB30-22BE8ECD9789"); 
string customTitle = "Custom Window Title"; 
outWindow.CreatePane(ref customGuid, customTitle, 1, 1); 

IVsOutputWindowPane customPane; 
outWindow.GetPane(ref customGuid, out customPane); 

customPane.OutputString("Hello, Custom World!"); 
customPane.Activate(); // Brings this pane into view 

詳細信息可以在MSDN上找到。

錯誤列表

對於將項目添加到錯誤列表,所述IVsSingleFileGenerator有一個方法調用void Generate(...)其具有類型IVsGeneratorProgress的參數。該界面有一個方法void GeneratorError(),它允許您向Visual Studio錯誤列表報告錯誤和警告。

public class MyCodeGenerator : IVsSingleFileGenerator 
{ 
    ... 
    public void Generate(string inputFilePath, string inputFileContents, string defaultNamespace, out IntPtr outputFileContents, out int output, IVsGeneratorProgress generateProgress) 
    { 
     ... 
     generateProgress.GeneratorError(false, 0, "An error occured", 2, 4); 
     ... 
    } 
    ... 
} 

GeneratorError()的詳細信息可以在MSDN上找到。

4

如果你想要的東西出現在輸出窗口,它必須來自標準輸出。爲此,您的應用需要作爲「控制檯」應用進行鏈接。在項目的屬性頁中設置/ SUBSYSTEM:CONSOLE標誌,在鏈接器/系統下將SubSystem屬性設置爲CONSOLE。

一旦你在窗口中的輸出,如果包括文本「錯誤:」它會出現一個錯誤,或者如果你設置「警告:」這將顯示爲警告。如果您的錯誤文本以路徑/文件名開頭,然後是括號中的行號,則IDE會將其識別爲「可點擊」錯誤,並自動導航到錯誤行。

+0

我在C#中這樣做,項目屬性中沒有/子系統的東西,我需要做一個控制檯應用程序來做到這一點?它現在作爲DLL工作,但顯然我沒有得到輸出。 – 2009-07-08 14:55:02

+0

這是一個DLL?它是如何被調用的?通常情況下,輸出窗口捕獲MSBuild構建的工具鏈中執行的工具,但據我所知,這些工具都是獨立的可執行文件,MSBuild只是捕獲所有stdout以便在窗口中顯示。 剛纔我發現您的自定義工具可能與建築物無關。 「輸出」窗口保留用於構建過程。如果你正在尋找運行時信息,你應該使用調試窗口(使用OutputDebugString()或Debug.Print()或其他)。 – 2009-07-08 16:51:00

-2

使用System.Diagnostics.Debugger.Message

7

有使用Marshal.GetActiveObject抓住當前DTE2實例的另一種方式。

首先參考EnvDTE和envdte80。目前這個工作在VisualStudio 2012中,我還沒有嘗試過其他的。

using System; 
using System.Runtime.InteropServices; 
using EnvDTE; 
using EnvDTE80; 

internal class VsOutputLogger 
{ 
    private static Lazy<Action<string>> _Logger = new Lazy<Action<string>>(() => GetWindow().OutputString); 

    private static Action<string> Logger 
    { 
     get { return _Logger.Value; } 
    } 

    public static void SetLogger(Action<string> logger) 
    { 
     _Logger = new Lazy<Action<string>>(() => logger); 
    } 

    public static void Write(string format, params object[] args) 
    { 
     var message = string.Format(format, args); 
     Write(message); 
    } 

    public static void Write(string message) 
    { 
     Logger(message + Environment.NewLine); 
    } 

    private static OutputWindowPane GetWindow() 
    { 
     var dte = (DTE2) Marshal.GetActiveObject("VisualStudio.DTE"); 
     return dte.ToolWindows.OutputWindow.ActivePane; 
    } 
} 
相關問題