【问题标题】:ActiveX component changes back to UI threadActiveX 组件变回 UI 线程
【发布时间】:2013-01-14 19:57:48
【问题描述】:

在 .NET 应用程序中,我使用第三方 ActiveX 控件连接到设备。该组件没有 UI,因此我可以从 Windows 应用程序、控制台应用程序或 Windows 服务中使用。问题在于它的行为因应用程序类型而异。

从控制台应用程序(或 Windows 服务)使用它:

  1. 我使用 ThreadPool 调用组件方法,也就是说,在主线程之外的线程中。
  2. 该方法在同一个线程中执行。 (如预期)
  3. 方法回调在同一个线程中运行。 (如预期)

但是,当从 Windows 应用程序中使用它时:

  1. 调用一个使用线程池的组件方法,也就是说,在一个线程而不是 UI 线程中。 --> 此时ActiveX控件似乎变成了UI线程。
  2. 该方法在 UI 线程中执行(我看到 UI 阻塞了!)
  3. 方法回调正在 UI 线程中运行。

有没有办法隔离组件,以便调用在 UI 以外的线程中执行?

谢谢!

【问题讨论】:

  • 它可能将 ActiveX 控件视为 UI 控件。只有一个评论。该控件是否有任何 UI 组件?
  • 它没有(几乎可以肯定)。我正在阅读我应该在 STA 模式下创建一个线程,但不确定如何在其中实例化组件。

标签: .net activex threadpool


【解决方案1】:

经过长时间的搜索和阅读,我能够使它工作。这是我使用的代码,带有一些 cmets。要了解更多信息,请在 Google 中搜索“.net Com thread sta”或类似内容。

// COM objects will always execute in the same thread where they were created, 
// so it's better to create them in another thread (that must be alive as long as the object
// exists) to avoid blocking the UI thread.
var thread = new Thread(CreateComponent);
thread.SetApartmentState(ApartmentState.STA);
threads.Add(thread);

thread.Start("optional parameters");


private void CreateComponent(object obj)
{
    var parameters = obj as string;

    // Create the COM object here
    var component = new CreateYourCOMComponent(parameters);

    // You might want to catch all unhandled exceptions too
    Application.ThreadException += Application_ThreadException;

    // Once the object is created, the thread must be alive during 
    // the whole time the COM object remains alive. The Application.Run 
    // will pump the messages required for COM and prevent the thread for exiting.
    Application.Run();
}

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-03-08
    • 1970-01-01
    • 1970-01-01
    • 2021-11-08
    • 2014-12-11
    • 1970-01-01
    相关资源
    最近更新 更多