Konvertieren eines Platform::String in ein char*

Unter WinRT (z.B. für die Plattform Windows 10) ist es nicht länger möglich eine Managed C++ Bibliothek (C++/clr) zu erstellen, die Zugriff auf eine Managed .NET Assembly von der C++ Seite aus hat. Das liegt daran, dass WinRT komplett in C++ entwickelt wurde und im Gegensatz zur Verwendung im Zusammenspiel mit der .NET CLR auf dem Desktop (bis jetzt) keine gemischte Assembly unterstützt wird.

Der Zugriff von einer .NET Assembly auf eine C++ Bibliothek wird unter WinRT ermöglicht, indem die API der Bibliothek durch Metadaten beschrieben wird, mit deren Hilfe die .NET CLR (Common Language Runtime) auf die C++ Bibliothek zugreifen kann. Dabei kommt des der .NET CLR sehr entgegen, dass die Metadaten in dem Format ECMA 335 vorliegen, welche unter anderem auch von dem CLI (Common Language Infrastructure) in der CLR selbst verwendet wird. Der umgekehrte Weg, von einem WinRT C++ Projekt eine .NET CLR Assembly zu verwenden ist (bisher) mit diesem Mapper nicht möglich.

Konvertieren eines Platform::String in ein const char* unter WinRT

Da es unter WinRT keine Möglichkeit gibt, auf die .NET BCL (Base Class Library) und die msCoreLib zu zugreifen, kann in diesem Fall der Type System::String nicht länger verwendet werden, anstelle dessen kommt der Type Platform::String von WinRT zum Einsatz. Dieser enthält intern eine Zeichenkette von wide characters (was dem Type wchar_t * entspricht, der unter Windows aus UTF-16 Unicode Zeichen besteht). Ferner können auch die marshalling-Funktionen des .NET Frameworks nicht länger verwendet werden, da sich keine .NET CLR Assemblys in einem Windows RT Projekt einbinden lassen. (WinRT does not support #using of a managed assembly - WinRT unterstützt nicht #using von einer verwalteten Assembly) Aus diesem Grund kommen an dieser Stelle die Standard C++ Konvertierungsfunktionen für Zeichenketten zum Einsatz. Mit Hilfe der folgenden kleinen Hilfsfunktionen lässt sich ein Platform::String in mehreren Schritten in einen const char * sowie umgekehrt einen const char * in ein Platform::String konvertieren (eng.: marshalling).

std::wstring stows(std::string s)
{
    std::wstring ws;
    ws.assign(s.begin(), s.end());
    return ws;
}

std::string wstos(std::wstring ws)
{
    std::string s;
    s.assign(ws.begin(), ws.end());
    return s;
}

Platform::String ^stops(std::string s)
{
    return ref new Platform::String(stows(s).c_str());
}

std::string pstos(Platform::String^ ps)
{
    return wstos(std::wstring(ps->Data()));
}


Platform::String ^txtops(const char *text)
{    
    return stops(std::string(text));
}

const char *text pstotx(Platform::String^ ps)
{
    return wstos(std::wstring(ps->Data())).c_str();
}