对于WPF应用程序,内部是GetMessage/DispatchMessage
内部的经典消息循环(在Windows' Application.Run
意义上)?是否可以捕获从另一个带有PostThreadMessage的Win32应用程序发布到WPF UI线程(没有HWND句柄的消息)的消息。谢谢。
答案 0 :(得分:3)
我使用.NET Reflector跟踪Applicaton.Run
实现到Dispatcher.PushFrameImpl
。也可以从.NET Framework reference sources获得相同的信息。确实有一个经典的消息循环:
private void PushFrameImpl(DispatcherFrame frame)
{
SynchronizationContext syncContext = null;
SynchronizationContext current = null;
MSG msg = new MSG();
this._frameDepth++;
try
{
current = SynchronizationContext.Current;
syncContext = new DispatcherSynchronizationContext(this);
SynchronizationContext.SetSynchronizationContext(syncContext);
try
{
while (frame.Continue)
{
if (!this.GetMessage(ref msg, IntPtr.Zero, 0, 0))
{
break;
}
this.TranslateAndDispatchMessage(ref msg);
}
if ((this._frameDepth == 1) && this._hasShutdownStarted)
{
this.ShutdownImpl();
}
}
finally
{
SynchronizationContext.SetSynchronizationContext(current);
}
}
finally
{
this._frameDepth--;
if (this._frameDepth == 0)
{
this._exitAllFrames = false;
}
}
}
此外,这里是TranslateAndDispatchMessage
的实现,它确实会在RaiseThreadMessage
内执行ComponentDispatcher.ThreadFilterMessage事件。
private void TranslateAndDispatchMessage(ref MSG msg)
{
if (!ComponentDispatcher.RaiseThreadMessage(ref msg))
{
UnsafeNativeMethods.TranslateMessage(ref msg);
UnsafeNativeMethods.DispatchMessage(ref msg);
}
}
显然,它适用于任何已发布的消息,而不仅仅是键盘消息。您应该可以订阅ComponentDispatcher.ThreadFilterMessage
并留意您感兴趣的消息。