【问题标题】:Constructing PropertyChangedEventArgs throws winrt::hresult_wrong_thread构造 PropertyChangedEventArgs 抛出 winrt::hresult_wrong_thread
【发布时间】:2019-08-28 19:18:19
【问题描述】:

我正在创建 C++/WinRT 控制台应用程序,在创建 PropertyChangedEventArgs 时遇到错误,而其他类型已正确激活。代码如下:

#include "pch.h"

#include <winrt/Windows.UI.Xaml.Data.h>

int main()
{
    winrt::init_apartment();

    winrt::Windows::UI::Xaml::Data::PropertyChangedEventArgs args(L"Title");
}

例外是:

Unhandled exception at 0x00007FFCDE9BA839 in ConsoleApplication1.exe: Microsoft C++ exception: winrt::hresult_wrong_thread at memory location 0x0000002CF310EF48. occurred

这是使用 Microsoft.Windows.CppWinRT 的 v2.0.190730.2 并针对在 10.0.18362.295 上运行的 Windows 10.0.18362.0。

【问题讨论】:

    标签: c++-winrt


    【解决方案1】:

    这似乎是一个线程问题。对 winrt::init_apartment 的调用在 Windows 运行时初始化线程,默认情况下,在多线程单元中。所以当你想使用 UI 的内容时,你需要像下面这样返回 UI 线程。

    IAsyncAction MyMethod() 
    {
        winrt::apartment_context ui_thread;
        co_await ui_thread;
        winrt::Windows::UI::Xaml::Data::PropertyChangedEventArgs args{ L"Title" };
    }
    
    int main()
    {
        winrt::init_apartment();
        MyMethod();
    }
    

    【讨论】:

    • 这并不能解决问题。您正在捕获调用线程的上下文,然后立即在该线程上恢复执行。 MyMethod 的前两行本质上是空操作。您需要转到 UI 线程。您可以使用resume_foreground,例如,传入适当的Dispatcher
    • 从这个document,我们可以使用 apartment_context 切换回调用上下文。另外,我尝试在app中添加resume_foreground,但是失败了。
    • 我明白这一点。但是您正在立即切换回调用上下文。如果原始代码失败,那么它也会失败,因为它不会改变任何东西。正如我之前指出的,MyMethod 的前两行是无操作的。无论这两行是否存在,行为都是相同的。
    • 更一般地说:winrt::apartment_context ctx; 后跟 co_await ctx; 不做任何事情,除非中间有协程暂停点。
    • 谢谢,我明白了,但我不能在应用程序中使用 add resume_foreground。
    猜你喜欢
    • 2011-06-02
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-04-07
    • 2014-08-10
    • 2011-11-04
    • 1970-01-01
    相关资源
    最近更新 更多