简体   繁体   English

来自C ++ COM的C#字符串

[英]String for C# from C++ COM

I have a C++ DLL and some functions return Unicode null-terminated strings: 我有一个C ++ DLL,一些函数返回Unicode以null结尾的字符串:

void SomeFunc(wchar_t* StrBuf)

The caller must allocate StrBuf - string can be up to 256 characters. 调用者必须分配StrBuf - 字符串最多可以包含256个字符。 This DLL also exposes a COM object to use this DLL from C# via COM. 此DLL还公开COM对象以通过COM从C#使用此DLL。 Definition in IDL: IDL中的定义:

[id(1), helpstring("bla")]
HRESULT SomeFunc([in,out] BSTR* TextStr, [out,retval] LONG* RetValue);

Currently the C# code looks like this: 目前C#代码如下所示:

string val = new string('\0', 256); // Allocate memory
MyComObj.SomeFunc(ref val); // Get string
val = val.Substring(0, val.IndexOf('\0')); // Convert from null-terminated string

Is there a way to define such a COM function so it can be used from C# easier? 有没有办法定义这样的COM函数,以便从C#中使用它更容易? Right now it looks ugly and takes three lines to call the function or five lines if a function has two string parameters. 现在它看起来很丑,如果函数有两个字符串参数,则需要三行来调用函数或五行。

If the memory for the string in the client allocates and fills it to the COM server, you must use a StringBuilder: 如果客户端中字符串的内存分配并将其填充到COM服务器,则必须使用StringBuilder:

// IDL code
HRESULT GetStr(/*[out]*/ LPSTR pStr);

// Interop
void GetStr(/*[out]*/ [MarshalAs(UnmanagedType.LPStr)] StringBuilder pStr);

// C# code
var str = new StringBuilder(256);
MyComObj.GetStr(a);

Then the StringBuilder will be empty or filled with characters. 然后StringBuilder将为空或填充字符。

Solved. 解决了。 In C++ I use this code in the COM wrapper: 在C ++中,我在COM包装器中使用此代码:

STDMETHODIMP MyClassClass::SomeFunc(BSTR* OptionValue, LONG* RetValue)
{
    *RetValue = 0;
    UNICODECHAR txt[MAXSTATSTRLEN];

    //... Copy text to txt variable
    *OptionValue = W2BSTR(txt);
    return S_OK;
}

IDL: IDL:

[id(1), helpstring("")] HRESULT SomeFunc([out] BSTR* OptionValue, [out,retval] LONG* RetValue);

In C# it can now be called easily: 在C#中,现在可以轻松调用它:

string val;
MyComObj.SomeFunc(out val);

If you have this exposed as a COM object, just use visual studio to add a reference to your object. 如果将此公开为COM对象,只需使用visual studio添加对象的引用即可。 It will automatically generate an assembly for you (I believe they call this a COM callable wrapper). 它会自动为你生成一个程序集(我相信它们称之为COM可调用包装器)。

This will expose your COM objects methods to .NET and works unless you start trying to pass across some custom structures. 除非您开始尝试传递某些自定义结构,否则这会将您的COM对象方法暴露给.NET并起作用。

Here are some resources for you: 以下是一些资源:

COM Callable Wrapper COM Callable Wrapper

COM Interop Part 1: C# Client Tutorial COM Interop第1部分:C#客户端教程

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM