为啥不显示消息框?
Posted
技术标签:
【中文标题】为啥不显示消息框?【英文标题】:Why would a message box be not displaying?为什么不显示消息框? 【发布时间】:2016-12-12 17:34:59 【问题描述】:我的 MFC 项目有一个非常奇怪的窗口模式设置。我认为这种设置搞砸了自有消息框的显示方式。
在按下 ALT 键之前,消息框是不可见的。
我仍在尝试围绕他们正在使用的窗口设置进行思考,但也许有人可以给我一个线索,让我知道要寻找什么?
我写了一个解决方法,我将所有者窗口和消息框的标题传递给一个类,该类生成一个线程,该线程遍历所有窗口并找到一个由指定所有者拥有的消息框对话框,该对话框具有指定的标题.但是,我必须搜索和替换 1000 多个实例才能使其在系统范围内工作。
更好的选择是找到根本原因。但是这其中的复杂性是相当令人生畏的。任何我应该寻找的可能导致这种行为的线索将不胜感激。
【问题讨论】:
这可能是绘画/重绘问题。 @1201ProgramAlarm,因为这是一个普通的windows MessageBox,不知道会怎么样。 您是否使用多显示器设置?消息框可以在您已断开连接的显示器上吗? 你是如何显示消息框的?您是否将对话框窗口句柄传递给它? Win32 MessageBox doesn't appear 表现出相同的故障模式。在该问答中,owner 窗口的WM_PAINT
-handler 缺少 BeginPaint
/EndPaint
调用。有了手头的信息,我建议查看(或注释掉)所有者窗口的PreTranslateMessage
实现。按 [Alt] 进入模式循环,即系统提供的消息循环,绕过应用程序提供的消息循环(这可能是错误的)。
【参考方案1】:
这是由MFC CDialog DoModal can't show window if parent window message queue is 'busy'“功能”引起的,如果消息队列包含任何消息,它将不会显示系统消息框。 (请对该错误进行投票或评论。这种行为非常出乎意料。)
我通过尝试使用以下方法抓取队列中的所有消息来追踪这一点:
MSG msg = 0 ;
while (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
TRACE(_T(R"--(,"% *.*s",PEEK,0x%08x,"%s",0x%08x,0x%08x,0x%08x)--" "\n"),
0, 0, _T(""), msg.hwnd, "Window HAS msg",
msg.message, msg.wParam, msg.lParam);
TranslateMessage(&msg);
DispatchMessage(&msg);
这将输出队列中的所有消息,并向我显示哪个窗口和哪个消息(在本例中为WM_PAINT
)是违规者。
然后,我追踪了该窗口附加到的类对象,并查看了它的 OnPaint()
处理程序。
原来,以前的程序员在构造 CPaintDC
对象之前先放置了 if
x 然后 return
条件。它的构造函数调用BeginPaint()
,进而验证无效区域。在不验证无效区域的情况下,系统会继续生成WM_PAINT
消息,直到无效区域为空。这将导致消息队列永远不会为空。
不确定这是否重要,但有问题的窗口和对话框之间的关系是它们在同一个线程中,不在根应用程序窗口之外。有两种显示模式,具有以下设置:
-ROOT -ROOT
+-CHILD +-MESSAGE BOX
+-MESSAGE BOX +-CHILD
+-CHILD +-CHILD
+-CHILD +-CHILD < Offender
+-CHILD < Offender +-CHILD
+-CHILD
【讨论】:
如果您简短地描述有问题的窗口和不会显示的对话框之间的关系,这可能对未来的访问者有用。以上是关于为啥不显示消息框?的主要内容,如果未能解决你的问题,请参考以下文章