0

我目前正在尝试编写自己的 Visual Studio 扩展(自定义编辑器)。我尝试编写一些类似于MS在SDK中提供的示例的代码,但它不起作用。

发生的情况是,在运行 VS 的第二个实验性实例并构建所有必要的类(编辑器工厂、编辑器窗格和编辑器控件本身)之后,VS 通知“操作无法完成”并且没有其他任何事情发生。

确实连接了调试器,但它不会因任何错误而停止。除了在我的源代码中明确放置的两条痕迹之外,没有关于扩展的痕迹:

Entering constructor for: Spooksoft.Spk.SpkPackage
Entering Initialize() of: Spooksoft.Spk.SpkPackage
'devenv.exe' (Managed (v4.0.30319)): Loaded 'C:\Windows\Microsoft.Net\assembly\GAC_MSIL\Microsoft.VisualStudio.Data.Tools.Delta.UI\v4.0_11.1.0.0__b03f5f7f11d50a3a\Microsoft.VisualStudio.Data.Tools.Delta.UI.dll', Skipped loading symbols. Module is optimized and the debugger option 'Just My Code' is enabled.
'devenv.exe' (Managed (v4.0.30319)): Loaded 'C:\Windows\Microsoft.Net\assembly\GAC_MSIL\Microsoft.TeamFoundation.Controls\v4.0_11.0.0.0__b03f5f7f11d50a3a\Microsoft.TeamFoundation.Controls.dll', Skipped loading symbols. Module is optimized and the debugger option 'Just My Code' is enabled.
'devenv.exe' (Managed (v4.0.30319)): Loaded 'C:\Windows\assembly\GAC_MSIL\Microsoft.TeamFoundation.Client\11.0.0.0__b03f5f7f11d50a3a\Microsoft.TeamFoundation.Client.dll', Skipped loading symbols. Module is optimized and the debugger option 'Just My Code' is enabled.

(...)

'devenv.exe' (Managed (v4.0.30319)): Loaded 'C:\Windows\Microsoft.Net\assembly\GAC_MSIL\Microsoft.VisualStudio.Web.HTML.Razor.Shims\v4.0_11.0.0.0__b03f5f7f11d50a3a\Microsoft.VisualStudio.Web.HTML.Razor.Shims.dll', Skipped loading symbols. Module is optimized and the debugger option 'Just My Code' is enabled.
'devenv.exe' (Managed (v4.0.30319)): Loaded 'C:\Windows\Microsoft.Net\assembly\GAC_MSIL\Microsoft.VisualStudio.Web.HTML.Razor.Implementation.Shims.2_0\v4.0_11.0.0.0__b03f5f7f11d50a3a\Microsoft.VisualStudio.Web.HTML.Razor.Implementation.Shims.2_0.dll'
The thread 'StatusBar' (0x760) has exited with code 0 (0x0).
The thread '<No Name>' (0xffc) has exited with code 0 (0x0).
The program '[4200] devenv.exe: Managed (v4.0.30319)' has exited with code 0 (0x0).

我该如何确定,出了什么问题?我在哪里可以搜索任何错误消息?

源代码(如果有人关心的话)。

4

1 回答 1

0

这可能没有解决我的问题,但肯定会提供更多选择。在 MS 员工(在 MS 论坛上)的帮助下,我设法确定了哪些接口有望在 VS 中实现。

您必须实现 ICustomQueryInterface。它的实现可能如下所示:

public CustomQueryInterfaceResult GetInterface(ref Guid iid, out IntPtr ppv) 
{
    Debug.WriteLine(String.Format("Attempt to cast to interface with iid {0}", iid));

    ppv = IntPtr.Zero;
    return CustomQueryInterfaceResult.NotHandled;
}

您将得到以下结果:

Attempt to cast to interface with iid f22a0ad5-8f51-4f66-a644-ea64770cf8b7
Attempt to cast to interface with iid 9d71890d-090c-4b67-80c3-4cb55c600b60
Attempt to cast to interface with iid d5d49c61-1c0b-4ea1-9adb-a79fb1dbc7b5
Attempt to cast to interface with iid 9d71890d-090c-4b67-80c3-4cb55c600b60
Attempt to cast to interface with iid d5d49c61-1c0b-4ea1-9adb-a79fb1dbc7b5
Attempt to cast to interface with iid d5d49c61-1c0b-4ea1-9adb-a79fb1dbc7b5
Attempt to cast to interface with iid 9d71890d-090c-4b67-80c3-4cb55c600b60
Attempt to cast to interface with iid d5d49c61-1c0b-4ea1-9adb-a79fb1dbc7b5
Attempt to cast to interface with iid d5d49c61-1c0b-4ea1-9adb-a79fb1dbc7b5
Attempt to cast to interface with iid 00020400-0000-0000-c000-000000000046
Attempt to cast to interface with iid d5d49c61-1c0b-4ea1-9adb-a79fb1dbc7b5
Attempt to cast to interface with iid d5d49c61-1c0b-4ea1-9adb-a79fb1dbc7b5
Attempt to cast to interface with iid 8560cecd-dfac-4f7b-9d2a-e6d9810f3443
Attempt to cast to interface with iid 8560cecd-dfac-4f7b-9d2a-e6d9810f3443

这为我们提供了接口的 GUID,VS 尝试将我们的类转换为该 GUID。现在我们可以使用以下类从 GUID 中检索实际类型。

正如七号所说,粗鲁,但有效。

public static class Util 
{

    private static Dictionary<string, Type> guidMap;

    static Util()
    {
        guidMap = new Dictionary<string, Type>();

        AppDomain.CurrentDomain.AssemblyLoad += (s, e) =>
        {
            try 
            {
                _ScanAssembly(e.LoadedAssembly);
            } 
            catch 
            {

            }
        };

        foreach (Assembly a in AppDomain.CurrentDomain.GetAssemblies())
        {
            try 
            {
                _ScanAssembly(a);
            } 
            catch 
            {

            }
        }
    }

    private static void _ScanAssembly(Assembly a)
    {
        foreach (Type t in a.GetTypes())
        {
            var attrs = t.GetCustomAttributes<GuidAttribute>(false);
            foreach (var item in attrs) {

                if (!guidMap.ContainsKey(item.Value.ToLower()))
                    guidMap.Add(item.Value.ToLower(), t);
            }
        }
    }

    public static Dictionary<string, Type> GuidMap 
    {
        get 
        {
            return guidMap;
        }
    }
}

现在我们可以用稍微不同的方式实现 ICustomQueryInterface:

    public CustomQueryInterfaceResult GetInterface(ref Guid iid, out IntPtr ppv) 
    {
        if (Util.GuidMap.ContainsKey(iid.ToString().ToLower())) 
        {
            Type t = Util.GuidMap[iid.ToString()];
            Debug.WriteLine(String.Format("Attempt to cast to interface {0}", t.ToString()));
        }
        else
            Debug.WriteLine(String.Format("Attempt to cast to interface with iid {0}", iid));

        ppv = IntPtr.Zero;
        return CustomQueryInterfaceResult.NotHandled;
    }

结果更有帮助:

Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsDeferredDocView
Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsPersistDocData2
Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsPersistDocData
Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsPersistDocData2
Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsPersistDocData
Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsPersistDocData
Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsPersistDocData2
Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsPersistDocData
Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsPersistDocData
Attempt to cast to interface System.Runtime.InteropServices.NativeMethods+IDispatch
Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsPersistDocData
Attempt to cast to interface Microsoft.VisualStudio.Shell.Interop.IVsPersistDocData
Attempt to cast to interface Microsoft.VisualStudio.TextManager.Interop.SVsCodeWindow
Attempt to cast to interface Microsoft.VisualStudio.TextManager.Interop.SVsCodeWindow

现在我将尝试确定哪些接口是必需的,哪些是可选的。

于 2013-10-03T06:39:31.677 回答