如何在 .NET Compact Framework 中抑制输入事件





5.00/5 (4投票s)
在加载时抑制按键和鼠标事件
简介 我最近在开发 Windows Mobile 6.5 应用程序时,在使用 .NET Compact CE 处理输入事件时遇到一个问题。 由于很难在互联网上找到解决方案,我认为分享我的经验是个好主意,以便其他遇到相同问题开发人员可以减少这方面的麻烦。 情况 我的问题如下。 我的窗体应用程序调用 Web 服务来检查用户输入的凭据并加载一些数据以显示。 在执行过程中,我显示等待光标。
Cursor.Current = Cursors.WaitCursor
我认为这足以让最终用户知道他必须等待一段时间,直到有结果。 但麻烦在我发现一位急于测试我的应用程序的同事后开始了。 问题 虽然执行过程(检查凭据、加载数据)可能需要超过 5 秒,我的急于求成的同事在约 2 秒后开始产生鼠标点击。 这导致在 Web 服务执行完成后显示的屏幕上产生点击事件。 当然,这不是我想要的! 毕竟,设置等待光标只是设置等待光标,不多也不少。 因此,我尝试禁用窗体、显示加载屏幕等,但这些都不足以抑制鼠标和按键事件。 实际上发生的情况是,操作系统会缓冲用户输入,并在新窗体激活后**触发**这些输入。 因此,我们必须在这个地方处理问题。 解决方案 我创建了一个名为 InputEvents
的密封类,可以在窗体的激活事件中调用,以抑制在窗体实际激活之前发生的所有未处理输入事件。public sealed class InputEvents
{
internal struct MSG
{
public IntPtr hwnd;
public int Msg;
public IntPtr wParam;
public IntPtr lParam;
public int time;
public int pt_x;
public int pt_y;
}
[DllImport("coredll.dll", EntryPoint = "PeekMessage", SetLastError = true)]
private static extern bool PeekMessage(out MSG lpMsg, IntPtr hWnd, uint wMsgFilterMin, uint wMsgFilterMax, uint wRemoveMsg);
[DllImport("coredll.dll", EntryPoint = "GetMessageW", SetLastError = true)]
private static extern bool GetMessage(out MSG lpMsg, IntPtr hWnd, uint wMsgFilterMin, uint wMsgFilterMax);
[DllImport("coredll.dll", EntryPoint = "TranslateMessage", SetLastError = true)]
private static extern bool TranslateMessage(out MSG lpMsg);
[DllImport("coredll.dll", EntryPoint = "DispatchMessage", SetLastError = true)]
private static extern bool DispatchMessage(ref MSG lpMsg);
private const int WM_KEYFIRST = 256;
private const int WM_KEYLAST = 264;
private const int WM_MOUSEFIRST = 512;
private const int WM_MOUSELAST = 521;
private const int PM_NOREMOVE = 0;
private const int PM_REMOVE = 1;
public static bool SuppressKeyMouseEvents()
{
MSG lpMsg;
// check for messages
while (PeekMessage(out lpMsg, IntPtr.Zero, 0, 0, PM_NOREMOVE))
{
// there is, so get the top one
if (GetMessage(out lpMsg, IntPtr.Zero, 0, 0))
{
if (!((WM_MOUSEFIRST <= lpMsg.Msg && lpMsg.Msg <= WM_MOUSELAST) || (WM_KEYFIRST <= lpMsg.Msg && lpMsg.Msg <= WM_KEYLAST)))
{
TranslateMessage(out lpMsg);
DispatchMessage(ref lpMsg);
}
}
}
return true;
}
}
更多信息请参见 http://msdn.microsoft.com/en-us/library/ms907610.aspx[^].