4

我必须在主线程的上下文中执行一些代码。我正在使用 Lazarus + FPC。我从 DLL 中的线程(如果在 linux 上是共享库)中接收到一个事件,并且我的回调函数被调用。请注意,此函数不是任何类的成员,而是附加了“cdecl”指令的独立传统函数。

我必须为收到的每条此类消息触发一个对应的属性事件处理程序。这些事件必须在主线程的上下文中传递。我知道两种这样的解决方案:

  1. 留言
  2. Application.QueueAsyncCall

第一个没问题,但它需要一个窗口句柄。由于这是一个库代码,因此没有可用的句柄。AllocateHWND 不是一个选项,因为它不是跨平台的。我知道我可以创建一个虚拟表单,但这是一个非常糟糕的解决方案

第二个工作正常,但我有一个问题,例如,在我将鼠标移动到应用程序中之前,不会处理调用。也许我做错了什么我不知道。我就像我的电话只有在消息处理开始时才被处理。但这显然是一个漫长的等待。

所以我想知道这里最好的解决方案是什么(可能是 QueueAsyncCall)以及如何确保我的消息(调用)将在可接受的时间范围内得到处理?

4

1 回答 1

1

你不能 100% 确定,就像你不能在任何非实时系统中一样。如果主线程挂起,它不会检查主循环中的消息或其他事件。这很正常。

你唯一能做的就是避免在主线程中做一些可能需要很长时间的事情。准确判断什么是必要的,什么不是。一些面向实时的人将所有文件系统访问移至线程,并将 GUI 严格保留为 UI,只是因为如果用户为此或其他配置网络共享上的路径,共享问题很容易导致长时间的超时等待,甚至几分钟。

如果我查看 application.queueasynccall,我没有看到线程安全处理(没有锁定或锁定队列),所以它已经出局了。

我知道 Lazarus 在一定程度上在非 Windows 上模拟了 postmessage,我检查了实现并且它确实有锁,所以我认为它是多线程安全的。

于 2010-08-27T09:50:12.747 回答