阻止按键重复 (C#)
在此应用程序中,我需要能够停止按住的键的响应,以防止不必要的数据进入输出。我遇到的问题是,使用下面代码中的方法确实可以防止按键重复,但它也会阻止它们足够的响应 - 因为用户敲击按键的速度非常快。
我不确定这是我的硬件、API 限制还是我的代码问题,但我下面的例程并不仅仅能够快速运行而不会使程序无法使用。一种识别按键是否被主动按下(以及持续多长时间)的方法也将有助于该程序的另一个功能并解决当前的问题。
有什么想法吗?
private void Form1_KeyDown(object sender, KeyEventArgs e)
{
e.SuppressKeyPress = isKeyDown;
isKeyDown = true;
}
private void Form1_KeyUp(object sender, KeyEventArgs e)
{
isKeyDown = false;
}
private void Form1_KeyPress(object sender, KeyPressEventArgs e)
{
if (!isStreamPlaying) return;
if (e.KeyChar.Equals('d') || e.KeyChar.Equals('j'))
{
//red hit
SoundPlayer hitSounds = new SoundPlayer(taikoLiveMapper.Properties.Resources.normal_hitnormal);
hitSounds.Play();
outputlist.Add(string.Format("320,240,{0},1,{1}", ms, 0));
lastms = ms;
}
else if (e.KeyChar.Equals('s') || e.KeyChar.Equals('k'))
{
//blue hit
SoundPlayer hitSounds = new SoundPlayer(taikoLiveMapper.Properties.Resources.normal_hitclap);
hitSounds.Play();
outputlist.Add(string.Format("320,240,{0},1,{1}", ms, 8));
lastms = ms;
}
}
In this application, I need to be able to stop the response from a key which is held down in order to prevent unnessecary data from entering the output. The problem I'm having is, using the methods in my code below does prevent the keys from repeating, but it also stops them from being responsive enough - as the users are hitting the keys very quickly.
I'm not sure if it's my hardware, api restriction or a problem with my code, but the routines I have below do not simply come round fast enough to work without making the program impossible to use. A way of identifying if a key is being actively held down (and for how long) would also help another feature for the program and solve this current issue.
Any ideas?
private void Form1_KeyDown(object sender, KeyEventArgs e)
{
e.SuppressKeyPress = isKeyDown;
isKeyDown = true;
}
private void Form1_KeyUp(object sender, KeyEventArgs e)
{
isKeyDown = false;
}
private void Form1_KeyPress(object sender, KeyPressEventArgs e)
{
if (!isStreamPlaying) return;
if (e.KeyChar.Equals('d') || e.KeyChar.Equals('j'))
{
//red hit
SoundPlayer hitSounds = new SoundPlayer(taikoLiveMapper.Properties.Resources.normal_hitnormal);
hitSounds.Play();
outputlist.Add(string.Format("320,240,{0},1,{1}", ms, 0));
lastms = ms;
}
else if (e.KeyChar.Equals('s') || e.KeyChar.Equals('k'))
{
//blue hit
SoundPlayer hitSounds = new SoundPlayer(taikoLiveMapper.Properties.Resources.normal_hitclap);
hitSounds.Play();
outputlist.Add(string.Format("320,240,{0},1,{1}", ms, 8));
lastms = ms;
}
}
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
您可以使用 GetKeyState 来查明某个键是否被按下,并用它来跟踪这些键:
此示例在每次按下某个键时对
i
进行计数,并显示按下的时间。它使用 GetKeyState 而不是跟踪 KeyDown/KeyUp,因为如果其他内容具有焦点,您可能会错过这些消息。You can use GetKeyState to find out if a key is down and use that to track the keys:
This example counts
i
up every time a key is pressed, and shows for how long it has been pressed. It uses GetKeyState instead of tracking KeyDown/KeyUp since you might miss those messages if something else has focus.根据文档< /a>, “如果按住该键,则每次重复该键时都会发生 [d]uplicate KeyDown 事件,但当用户释放该键时仅生成一个 KeyUp 事件。”
因此,最简单的解决方案是忽略重复的 KeyDown 事件,除非已看到其相应的 KeyUp 事件。
刚刚为我工作。
According to the documentation, "[d]uplicate KeyDown events occur each time the key repeats, if the key is held down, but only one KeyUp event is generated when the user releases the key."
So the simplest solution is to ignore a repeated KeyDown event unless its corresponding KeyUp event has been seen.
Just worked for me.
使用计时器代替:初始化计时器,每个“操作”一个(例如按 d/j 或 s/k)在计时器内移动红色命中/蓝色命中代码,而不是当前代码,使用以下代码:
在计时器中 Elpased代码执行后,事件还将其 Enabled 设置为
false
。Use Timers instead: initialize timers, one for each "action" (e.g. pressing d/j or s/k) move the red hit/blue hit code inside the timer and instead of your current code, have this:
And in the timers Elpased event also set their Enabled to
false
after the code is executed.