问题描述
当我使用microsoft docs to migrate to winrt from cx中的helper函数时,会发生此错误。我看到类似的问题here,但是提到的解决方案似乎对我不起作用。此处提到的解决方案在具有此错误的文件中的任何其他winrt标头之前添加#include
template <typename T>
T from_cx(Platform::Object ^ from) {
T to{nullptr};
winrt::check_hresult(reinterpret_cast<::IUnkNown*>(from)->QueryInterface(
winrt::guid_of<T>(),reinterpret_cast<void**>(winrt::put_abi(to))));
return to;
}
这是整个文件:
#pragma once
#include <Unknwn.h>
#include <winrt/Windows.Foundation.h>
namespace x {
namespace y {
template <typename T>
T from_cx(Platform::Object ^ from) {
T to{nullptr};
winrt::check_hresult(reinterpret_cast<::IUnkNown*>(from)->QueryInterface(
winrt::guid_of<T>(),reinterpret_cast<void**>(winrt::put_abi(to))));
return to;
}
template <typename T>
T ^
to_cx(winrt::Windows::Foundation::IUnkNown const& from) {
return safe_cast<T ^>(reinterpret_cast<Platform::Object ^>(winrt::get_abi(from)));
}
}
}
解决方法
winrt::guid_of()
返回一个winrt::guid
。根据{{3}}:
- 重大变化。 GUID现在投影为
winrt::guid
。对于实现的API,必须对GUID参数使用winrt::guid
。否则,winrt::guid
会转换为GUID,只要您包含unknwn.h,然后再包含任何C ++ / WinRT标头。参见What's new in C++/WinRT。
每Interoperating with the ABI's GUID struct:
GUID
投影为winrt::guid
。对于您实现的API,必须对winrt::guid
参数使用GUID
。否则,只要您包含winrt::guid
(由和许多其他头文件隐含),在包含任何内容的 GUID
和unknwn.h
之间会自动进行转换。 C ++ / WinRT标头。如果您不这样做,则可以在它们之间进行强行
reinterpret_cast
。
因此,请确保在WinRT标头之前包含unknwn.h
,或者可以显式reinterpret_cast
,例如:
template <typename T>
T from_cx(Platform::Object ^ from) {
T to{nullptr};
winrt::guid iid = winrt::guid_of<T>();
winrt::check_hresult(
reinterpret_cast<::IUnknown*>(from)->QueryInterface(
reinterpret_cast<GUID&>(iid),reinterpret_cast<void**>(winrt::put_abi(to)))
);
return to;
}
,
IInspectable的评论也对我有用:
如果您#include
,请确保在添加之前确实包含它 任何winrt标头。使用预编译头文件时,您可以在其中 还必须包括Unknwn.h。 ...至关重要的是,您的编译单元必须包含Unknwn.h 在任何其他winrt头文件之前。编译单元通常有一个 .cpp,.cc或.cxx的文件扩展名。
我认为标头必须包含在定义这些辅助函数的文件中。