簡體   English   中英

如何在工作線程(非UI線程)中創建模態對話框?

[英]How do I create Modal dialog in worker thread(Non-UI thread)?

我編寫了一個示例MFC應用程序,其中有兩個線程: - 主線程(UI線程) - 工作線程(非UI線程)

我有一個特定的要求,在非UI(工作線程)中創建一個Modal對話框。 當我創建CDialog對象並在同一個上調用DoModal時,它可以正常工作。 該對話框已創建並充當應用程序的模態。 (Win XP SP2機器)但這在Windows 2003服務器機器上不起作用。 2003服務器中的行為是,模態對話框落后於應用程序主窗口,只有當我單擊主窗口時,對話框才會顯示在前面。 它不是我的應用程序的模態對話框。

可能是什么問題 - 任何想法?

如果在非UI線程中創建UI控件是問題,那么是否有任何Win32 API允許我將我的工作線程鏈接到主UI線程,以便DoModal發生在主線程中。 我嘗試了AttachThreadInput,但它無法正常工作。

沒有可靠的方法在多個線程之間傳播GUI模態。 每個窗口都由一個HWND引用的對象表示,而該HWND又具有線程關聯性。 這是Windows的16位天的遺留問題,沒有多線程。 因此, HWND不受並發訪問保護。 Old New Thing有一個關於“用戶界面對象的線程親和性”的優秀系列(第1部分2 3 附錄 )。

通過首先啟用對話框窗口然后禁用其父窗口來實現模態。 第一步是安全的,而第二步是嘗試從不是窗口擁有線程的線程禁用窗口。 由於啟用/禁用窗口修改通過HWND引用的對象,因此它表示競爭條件。

建議的解決方案是將GUI限制在單個線程中,並從工作線程與GUI線程進行通信,以使其代表工作線程執行用戶交互。 完成此操作的最簡單方法是從工作線程調用SendMessage來阻止,直到GUI線程的消息處理程序返回。 如果在顯示對話框時工作線程應繼續運行,則可以使用PostMessage,並使用PostThreadMessage與工作線程進行通信,或發信號通知事件對象等同步對象。

首先,我想同意其他海報,在主UI線程上顯示對話框可能更好。

但是,如果必須,可以使用以下步驟在另一個線程模式上進行對話:

  1. 創建對話框時,將活動窗口作為所有者傳遞。
  2. 顯示對話框時,迭代其他窗口並執行EnableWindow(FALSE) 對話框隱藏時,反過來。 您可能必須記住Windows啟用狀態並恢復原始狀態,而不僅僅是EnableWindow(TRUE)
  3. 確保在顯示對話框時忽略加速器和其他全局命令。

注意,(2)不應該是必要的,只要你做(1),但你提到了MFC,我不記得它的確切行為。 它有自己的模態對話框實現,可能與Win32不完全匹配。 如果你很幸運,(1)和(3)就足夠了。

雖然我不知道Server 2003上對話框處理的細節,但是獲得主線程的最簡單的解決方法是使用自定義窗口消息do ::SendMessage()並在消息處理程序中顯示對話框。

我建議你不要做主題建議的問題,並將所有UI限制在一個線程中。 如果您需要其他線程與用戶通信,請創建一些消息傳遞機制,要求UI線程執行此操作,然后將結果傳回。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM