我目前正在研究 C# 和 COM 接口。C# 中的 COM 文档很少,因为 C# 出现在 COM 之后(也许我们 SO 可以修复)。我发现C# 编译器可以提供信息丰富的错误消息。可以从错误消息中读取方法签名的 C# 语法版本,然后添加到您的类中。这适用于 IAdviseSink,但不适用于 IBindCtx。
我收到最后一种方法RevokeObjectParam(string a)
的错误,C++ 中的语法是HRESULT RevokeObjectParam( [in] LPOLESTR pszKey );
并且LPOLESTR
是一个空终止的基于 2 字节的字符串,因此使用[MarshalAs(UnmanagedType.LPWStr)]
应该可以工作。但它没有,我收到错误消息
* Class1.cs(25,14,25,40): error CS0539: 'IBindCtx.RevokeObjectParam' in explicit interface declaration is not a member of interface
* Class1.cs(6,18,6,24): error CS0535: 'ComInterfacesInCSharp.Class1' does not implement interface member 'System.Runtime.InteropServices.ComTypes.IBindCtx.RevokeObjectParam(string)'
那么我该如何修改这个方法签名来修复呢?下面是可复制到 Visual Studio 中的完整代码(创建一个类库项目)。
using System.Runtime.InteropServices.ComTypes;
using System.Runtime.InteropServices;
namespace ComInterfacesInCSharp
{
public class Class1 : System.Runtime.InteropServices.ComTypes.IBindCtx
{
void IBindCtx.RegisterObjectBound(object obj) { }
void IBindCtx.RevokeObjectBound(object obj) { }
void IBindCtx.ReleaseBoundObjects() { }
void IBindCtx.SetBindOptions(ref System.Runtime.InteropServices.ComTypes.BIND_OPTS opts) { }
void IBindCtx.GetBindOptions(ref System.Runtime.InteropServices.ComTypes.BIND_OPTS opts) { }
void IBindCtx.GetRunningObjectTable(out System.Runtime.InteropServices.ComTypes.IRunningObjectTable tab) { }
void IBindCtx.RegisterObjectParam(string s, object obj) { }
void IBindCtx.GetObjectParam(string s, out object obj) { }
void IBindCtx.EnumObjectParam(out System.Runtime.InteropServices.ComTypes.IEnumString enumString) { }
/* Problem here https://msdn.microsoft.com/en-us/library/windows/desktop/ms693771(v=vs.85).aspx
* C++ Syntax is
* HRESULT RevokeObjectParam( [in] LPOLESTR pszKey );
* LPOLESTR is a null terminated 2 byte based string so UnmanagedType.LPWStr ought to work
*
*/
//void IBindCtx.RevokeObjectParam(string a) { }
void IBindCtx.RevokeObjectParam([MarshalAs(UnmanagedType.LPWStr)] string a) { }
/*
* Compile errors are
* Class1.cs(25,14,25,40): error CS0539: 'IBindCtx.RevokeObjectParam' in explicit interface declaration is not a member of interface
* Class1.cs(6,18,6,24): error CS0535: 'ComInterfacesInCSharp.Class1' does not implement interface member 'System.Runtime.InteropServices.ComTypes.IBindCtx.RevokeObjectParam(string)'
*/
}
}
顺便说一句,如果您有一个详细介绍这些 C# 接口的 Web 资源,那将是非常棒的!