问题标签 [wrl]

For questions regarding programming in ECMAScript (JavaScript/JS) and its various dialects/implementations (excluding ActionScript). Note JavaScript is NOT the same as Java! Please include all relevant tags on your question; e.g., [node.js], [jquery], [json], [reactjs], [angular], [ember.js], [vue.js], [typescript], [svelte], etc.

0 投票
0 回答
1182 浏览

com - 如何等待 IAsyncOperation 完成使用 C++ WRL?

我正在编写代码以WinRT使用 C++ WRL(即不使用 C++/CX 或 C++/CLI)在 Windows 10 上使用 API。我正在使用Package 类中的GetAppListEntriesAsync()来获取安装在系统上的 UWP 应用程序的名称。GetAppListEntriesAsync()异步调用回调方法。我想等到所有这些异步方法都完成。不像没有任何关键字来等待异步任务。C++/CX WRLawait

细节

以下代码用于获取列表。

package3 是指向类型的指针ABI::Windows::ApplicationModel::IPackage3:-

我如下调用异步操作。

Where保存对异步调用cb的回调函数的引用。GetAppListEntriesAsync()(见更新2)

有几个这样的异步操作被调用。我想运行一段代码,该代码只有在所有此类异步回调完成后才能运行。C++/CXawait关键字用于等待异步任务。我应该如何使用WRL C++?我尝试使用WaitForSingleObject()但它似乎不起作用。

一种非常粗暴的方法是在 while 循环中不断检查每个异步操作的状态。

我不确定这是否可以保证工作,或者是否会导致性能损失。我的代码的 COM 单元类型是APTTYPE_STA(注意确定这条信息是否与问题相关;我想设置为RO_INIT_MULTITHREADEDRoInitialize()失败,但是 WRL 代码似乎工作正常)。

更新 2:

以下是 cb(回调)的实现方式。

试图实施IAgileObject

为了使我的回调实现IAgileObject,我将不得不使用Implements<>WRL 模板类。所以回调会是这样auto cb = Callback<Implements<IAgileObject,...>>的,但问题是IAsyncOperationCompletedHandler<ABI::Windows::Foundation::Collections::__FIVectorView_1_Windows__CApplicationModel__CCore__CAppListEntry_t *>它不是派生自IInspectable,因此在其上使用实施:-

Callback<Implements<ABI::Windows::Foundation::IAsyncOperationCompletedHandler<ABI::Windows::Foundation::Collections::__FIVectorView_1_Windows__CApplicationModel__CCore__CAppListEntry_t *>,IAgileObject>>给出以下错误(Visual Studio 2017)。

Error C2338 'I' has to derive from 'IWeakReference', 'IWeakReferenceSource' or 'IInspectable' AsyncTask c:\sw\tools\sdk\winsdk\win10\include\winrt\wrl\implements.h 413

0 投票
1 回答
338 浏览

c++ - 在 midl 中使用 Windows::Foundation 命名空间接口

我想在我的 midl 文件中使用 Windows::Foundation 中定义的接口。为此,我编写了以下示例代码,但它给出了编译错误:错误 MIDL2011 未解析的类型声明:IStringable [过程'MyCustomMethod2'的参数'param2'(接口'mytestmidl.MyTestInterface')] mytestmidl.idl 12

如何从我的 midl 文件中引用 IStringable 或其他接口?

0 投票
1 回答
180 浏览

arrays - 通过 WRL idl 检索数组

我也在这里问过同样的问题。

我在制作返回对象数组的 API 时遇到了麻烦。
这是我到目前为止所尝试的。我编写了将数组作为参数返回的方法

这给了我以下错误: Error MIDL4048 [msg]Unsupported array pattern detected. [context]myobj

另外,我尝试将数组添加到自定义对象中,即

在这种情况下,我收到以下错误: Error MIDL4000 [msg]A structure field cannot be a type of pointer. [context]: someParams1 [ Field 'someParams1' of Struct 'MyName.Space.MyCustomObject' ]

谁能告诉我这里有什么问题?或提供工作示例以通过 WRL idl 检索对象数组

0 投票
0 回答
803 浏览

c++ - 在 UWP 应用中使用 ATL/COM 对象

我公司有很多用 vb6 编写的旧项目。我们有一些用 ATL/C++ 编写的可重用软件组件。我们现在正在考虑用 UWP 重写我们的应用程序,但似乎 UWP 应用程序不支持旧的 COM 技术。我正在研究是否有办法实现也支持 UWP 的 COM 对象。我知道将我们的旧组件移植到 UWP 组件肯定会奏效。但是我们不想维护两个版本的通用组件,因为我们已经发布了很多旧软件,我们仍然提供软件支持。其中一些软件已被我们的客户使用超过 10 年。不可能升级我们发布的所有软件。

我想出了几个可能的解决方案:

桌面桥

我发现了一个名为“Packaged COM”的短语,UWP 应用程序可以通过桌面桥使用它。这篇文章,桌面桥的 COM 服务器和 OLE 文档支持,提供了一个从 UWP 应用程序调用 exe COM 服务器的示例。如果它也支持 InProcessServer,这似乎是一个很好的解决方案。我确实发现了一些可疑的东西,InProcessServer,但事实证明它是针对 WinRT 组件的。

我还尝试将 COM 引用添加到 UWP 项目。代码可以成功引用 COM 对象。但是,它在运行时不起作用。UWP 应用有自己的注册表配置单元,因此不会加载已注册到系统注册表的 COM 对象。我在想,如果我将注册信息添加到 UWP 应用程序的私有配置单元并将 COM dll 与应用程序一起打包,这可能会起作用。只是找不到任何例子。

ATL/COM

因为我们已经在 COM 对象中实现了我们的业务逻辑。最可行的解决方案是升级我们的 COM 对象以支持 UWP 应用程序。WinRT 组件仍然使用 COM 技术但实现了新的接口IInspectable,我假设旧的基于 ATL 的 COM 对象如果实现IInspectable接口可以修改以支持 UWP 的调用约定。我只是没有任何线索来做这件事。

WRL

我找到了一篇 MSDN 文章How to: Create a Classic COM Component Using WRL,讨论了使用 WRL 项目模板来实现可在 Win32 应用程序和 UWP 应用程序中使用的类 COM 对象。

它说:

除了将其用于通用 Windows 平台 (UWP) 应用程序之外,您还可以使用 Windows 运行时 C++ 模板库 (WRL) 创建用于桌面应用程序的基本经典 COM 组件

但我很快意识到微软不再支持 WRL 项目模板。我在网上找到的项目模板的所有下载链接都不再可用。

C++/WinRT

这项技术似乎是 WRL 的继任者。它看起来很有希望,但不幸的是尚未发布。


为了澄清@Peter Torr的几件事:

(1) 您是否希望您的应用程序/COM 对象是“纯”UWP(在所有设备上运行)或者您是否可以使用仅限桌面的 fullTrust UWP(又名桌面桥)?(2) COM 对象是否仅用于发布它们的应用程序,或者它们应该被其他应用程序使用?

  1. 我公司使用Windows平台提供基于PC的工业自动化服务(硬件和软件)。所以答案是肯定的,我们对 fullTrust UWP 很满意。我们的产品只能在桌面上运行。我们只想拥抱新技术并利用 UWP 的出色 UI 框架。

  2. COM 对象适用于新应用程序 (UWP) 和旧软件(有些基于 vb6)。我们很高兴将 COM 对象与 UWP 应用程序打包在一起,并将系统注册的 COM 用于旧软件,只要这些 COM 对象是相同的(从相同的代码库构建)。

0 投票
0 回答
273 浏览

c++ - 'Microsoft::WRL::FtmBase' 类具有虚函数,但析构函数不是虚函数

我收到这个编译错误

C:\Program Files (x86)\Windows Kits\10\include\10.0.17134.0\winrt\wrl\implements.h(1453): 警告 C4265: 'Microsoft::WRL::FtmBase': 类有虚函数,但是析构函数不是虚拟的

在我的程序中添加“#include < wrl.h>”之后。我正在使用 /W4 标志。有什么我在这里想念的吗?某种需要定义的宏?好奇是否有办法在不抑制它的情况下修复该警告。

另外,如果有帮助,我将使用最新的 VS 2017 和 c++17。

0 投票
3 回答
7499 浏览

c++ - 更新 Visual Studio 2017,现在出现编译错误 C7510:“回调”:使用依赖模板名称必须以“模板”为前缀

在更新(15.8.0)之后,我尝试像往常一样编译我的项目。我将 showincludes 设置为 yes 以找出错误的来源,但它都是系统代码。从 stdafx.cpp 开始,它会遍历所有包含和错误:

有没有人见过这个?我在谷歌上下搜索以找到无济于事的答案。缺少修改windows sdk,不知道该怎么做。

编辑:在我安装的 Windows SDK 中,错误出现在文件中 -

C:\Program Files (x86)\Windows Kits\10\Include\10.0.17134.0\winrt\wrl\event.h

更改第 316 行:返回 DelegateHelper::Traits::Callback(Details::Forward(callback));

to: return DelegateHelper::Traits::template Callback(Details::Forward(callback));

和第 324 行:返回 DelegateHelper::Traits::Callback(

返回 DelegateHelper::Traits::template Callback(Details::Forward(callback));

由于修改 sdk 并不是真正的解决方案,Peng Du 在配置窗口中选择 nonconformance 的解决方案是可行的方法。

0 投票
1 回答
40 浏览

windows - 如何在 win32 应用程序中实现 Facebook 的操作系统共享?

我有一个用于图像编辑的 win32 应用程序。我必须通过操作系统为图像实现 Facebook 共享。

我已经在 UWP 应用程序中进行了调查。这可以使用 dataTransferManager ( https://docs.microsoft.com/en-us/uwp/api/windows.applicationmodel.datatransfer.datatransfermanager ) 来完成。它显示了一个共享面板,其中包含所有可以接受图像的应用程序。Facebook 应用程序也显示在共享面板中。选择 Facebook 后,Facebook 会打开,共享对话框会在 Facebook 内打开,其中包含图像。

我找到了可用于使用 WRL 共享的代码(https://github.com/arunjeetsingh/Build2015/tree/master/Win32ShareSourceSamples/Win32_Share_Desktop),但他们没有在 dataTransferManager 中添加图像,因此没有显示像 Facebook 这样的应用程序在共享面板中。我对如何使用 WRL 在 dataTransferManager 中添加图像没有清楚的了解。

我有两个问题:

  1. 是否可以使用共享面板和 dataTransferManager 在 win32 应用程序(经典)中完成图像共享?
  2. 我可以获得一些有用的文章或任何实际完成的 Github 存储库吗?
0 投票
1 回答
788 浏览

c++ - 使用 winrt::com_ptr使用 D3D11CreateDevice()?

我一直在研究DirectXTK 示例项目中的代码,并尝试在一个新项目中实现它。不过,微软似乎建议在新项目中使用 WinRT,所以我决定尝试切换 to 的WRL::ComPtr实例winrt::com_ptr。不过,我被困住了,试图ID3D11Device1在项目的类GameID3DDevice.D3D11CreateDevice()

这是示例代码,为了简单起见,稍微抽象了一点:

这是我使用 WinRT 的近似值:

但是,每次运行它时,都会出现以下错误:

我已经阅读了这里的文档、WRL::ComPtr.As() 这里的文档以及winrt::com_ptr.as() 这里的“转换”示例我现在可以忍受的次数已经差不多了。我错过了什么?

0 投票
1 回答
211 浏览

c++ - 从工厂方法返回的 ComPtr 的引用计数增加了两次

我声明了一个COM接口,并且我有两个接口的实现(类),具体取决于输入配置。我还有一个工厂方法,可以检查输入配置并在类上适当地调用 NEW。在我的课堂上,我AddRef()按照Release()规范COM实施。我声明一个ComPtr并调用工厂方法来访问上面的接口。我可以通过两种方式做到这一点,

1) 从 Factory 方法返回 ComPtr

从上述调用返回后,Ref 计数captureSource为 '2'。我期待它是1。

但是使用以下代码,参考计数为 1

2)ComPtr将地址作为参数传递给工厂方法

captureSource参考计数现在为 1。

请指导我为什么上述两种方法的引用计数存在差异,以及为什么返回一个对象是增加引用计数(2),而将对象指针设置为*ppv (引用计数 1)。

正如所料,方法 (1) 会导致 memleak,因为 ref 计数不会变为 0。

0 投票
1 回答
460 浏览

winapi - 实现 ABI::Windows::Foundation::Collections::IVector 给出 - 错误 C2338 此接口实例尚未由 MIDL 专门化

我正在尝试在 win32 应用程序中实现 IVector。编译器总是给我这个我无法摆脱的 MIDL 断言错误。这是示例类 -

编译它会产生错误-

错误 C2338 此接口实例尚未由 MIDL 专门化。这可能是由于忘记了接口类型上的“*”指针、在 idl 文件中省略了必要的“declare”子句、忘记包含必要的 MIDL 生成的标头之一。IVector c:\program files (x86)\windows kits\10\include\10.0.17763.0\winrt\windows.foundation.collections.h 201

似乎 collections.h 有not_yet_specialized_placeholder总是将值设置为“假”。如果我在文件中定义下面的代码片段,那么错误就会消失,但是对于 IVector 没有 uuid,我会得到不同的错误。这使我相信这是不正确的解决方案。

至于我错过了什么,这让我发疯。