C# 或 .NET 刷新键盘缓冲区
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/978091/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
C# or .NET Flushing Keyboard Buffer
提问by Amar Patel
How do I flush the keyboard buffer in C# using Windows Forms?
如何使用 Windows 窗体在 C# 中刷新键盘缓冲区?
I have a barcode scanner which acts like a keyboard. If a really long barcode is scanned and the cancel button is hit on the form, I need the keyboard buffer to be cleared. So I need to flush and ignore all pending input. I need the buffer cleared because if the barcode contains spaces, the spaces are processed as button clicks which is unecessary.
我有一个像键盘一样的条形码扫描仪。如果扫描了一个非常长的条形码并点击了表单上的取消按钮,我需要清除键盘缓冲区。所以我需要刷新并忽略所有挂起的输入。我需要清除缓冲区,因为如果条形码包含空格,则空格将作为不必要的按钮点击进行处理。
采纳答案by rein
I'm not sure you can do this. The keystrokes go into the event queue for the main event loop. Any action you take to cancel these keystrokes will be placed in the queue after the keystrokes.
我不确定你能做到这一点。击键进入主事件循环的事件队列。您为取消这些击键而采取的任何操作都将在击键后放入队列中。
The event loop will only get to your cancel action after the keystrokes have been processed. You can only cancel the keystrokes based on some event that happens in the middle of the keystroke sequence.
事件循环只会在处理完击键后才能执行您的取消操作。您只能根据在击键序列中间发生的某些事件来取消击键。
回答by SLaks
Set KeyPreview
on the Form to true
, then catch the KeyPress
event and set e.Handled
to true
if cancel was clicked.
KeyPreview
在 Form 上设置为true
,然后捕获KeyPress
事件并设置e.Handled
为true
如果单击取消。
EDIT: Catch the Form'sKeyPress event
编辑:捕获表单的KeyPress 事件
回答by VVS
You coulddo BIOS level flushing (http://support.microsoft.com/?scid=kb%3Ben-us%3B43993&x=22&y=10) but I would advise against this low level approach since Windows also does keyboard buffering on a higher level.
您可以执行 BIOS 级别刷新(http://support.microsoft.com/?scid=kb%3Ben-us%3B43993&x=22&y=10)但我建议不要使用这种低级别方法,因为 Windows 也会在更高级别上进行键盘缓冲等级。
The best way seems to be to eat any arriving char while a specific flag is set. As SLaks suggests I would set KeyPreview
to true and set e.Handled
to true either in KeyPress
or in KeyDown
.. should make no difference.
最好的方法似乎是在设置特定标志时吃掉任何到达的字符。正如 SLaks 建议的那样,我将设置KeyPreview
为 true 并设置e.Handled
为 trueKeyPress
或 in KeyDown
.. 应该没有区别。
回答by Chris
while (Console.KeyAvailable) { Console.ReadKey(true); }
while (Console.KeyAvailable) { Console.ReadKey(true); }
回答by jp2code
@Chris:
@克里斯:
Console.KeyAvailable
threw an exception on me because the Console did not have focus.
Console.KeyAvailable
向我抛出异常,因为控制台没有焦点。
The exception message was helpful, though. It suggested using Console.In.Peek()
to read in that instance.
不过,异常消息很有帮助。它建议Console.In.Peek()
在那种情况下使用阅读。
I thought it would be worth noting here as an alternate solution and for posterity.
我认为作为替代解决方案和后代,这里值得一提。
if (-1 < Console.In.Peek()) {
Console.In.ReadToEnd();
}
回答by midspace
Disable the form, and force all processing to occur with DoEvents whilst it's disabled. The Controls should reject any keystokes because they are disabled. Then re-enable the form.
禁用表单,并在禁用时强制所有处理与 DoEvents 一起发生。控件应拒绝任何按键操作,因为它们已被禁用。然后重新启用表单。
this.Enabled = false;
Application.DoEvents();
this.Enabled = true;
回答by BlinkSun
It's a old question but I got the same issue and I found a good way to do it...
When Application.DoEvent()is called, the keystoke buffer call the KeyPress event but _keypress is set to false, so it'll skip all them, after that _keypress return to true to be ready for another keypress event !
这是一个老问题,但我遇到了同样的问题,我找到了一个很好的方法来做到这一点......
当Application.DoEvent()被调用时,keystoke 缓冲区调用 KeyPress 事件但 _keypress 设置为 false,所以它会跳过所有这些,在那之后 _keypress 返回 true 为另一个按键事件做好准备!
Public _keypress As Boolean
Private Sub Form1_KeyPress(sender As Object, e As KeyPressEventArgs) Handles Form1.KeyPress
If Not _keypress Then
_keypress = True
//instructions
End If
Application.DoEvents()
_keypress = False
End Sub