KeyDown : 识别多个键
Posted
技术标签:
【中文标题】KeyDown : 识别多个键【英文标题】:KeyDown : recognizing multiple keys 【发布时间】:2010-11-18 22:25:41 【问题描述】:我如何确定在KeyDown
中按下了 CtrlUp。
private void listView1_KeyDown(object sender, KeyEventArgs e)
if (e.KeyCode == Keys.Control && e.KeyCode == Keys.Up)
//do stuff
不能工作,因为从来没有在同一秒内同时按下两个键。你总是先按 Ctrl 然后另一个...
【问题讨论】:
【参考方案1】:您可以像这样检查 KeyEventArgs 的修饰符:
private void listView1_KeyDown(object sender, KeyEventArgs e)
if (e.KeyCode == Keys.Up && e.Modifiers == Keys.Control)
//do stuff
MSDN reference
【讨论】:
这在我的键盘上从来都不是真的——例如,如果我按下 LShiftKey 和 Keys.Up,它 e.Shift 永远不会是真的,并且 e.Modifiers 将永远保持为 None。知道为什么吗? 似乎箭头键在某些方面很特别。这个问题提供了一些见解:***.com/questions/1646998/… 我只发现有e.Key,没有e.KeyCode。也没有 e.Modifier。 @KMC 令人困惑的是,有两个不同的KeyEventArgs
。我假设您正在使用来自Windows.UI.Core
的那个,来自CoreWindow
事件。这个答案是关于一个不同的事件。【参考方案2】:
来自MSDN page on KeyEventArgs:
if (e.KeyCode == Keys.F1 && (e.Alt || e.Control || e.Shift))
//Do stuff...
【讨论】:
【参考方案3】:您可以尝试使用Keyboard
对象来检测IsKeyDown
属性。此外,如果您不希望浏览器快捷方式被覆盖,您可以将Handled
属性设置为 true。但是在覆盖浏览器快捷方式时要小心,因为它可能会导致混淆。
private void Page_KeyDown(object sender, KeyEventArgs e)
// If leftCtrl + T is pressed autofill username
if (Keyboard.IsKeyDown(Key.T) && Keyboard.IsKeyDown(Key.LeftCtrl))
txtUser.Text = "My AutoFilled UserName";
e.Handled = true;
【讨论】:
注意:这是 WPF。 @TaW - 我们正在运行 XBAP 应用程序(在 Internet Explorer 中运行的 WPF)。因此,在这种情况下,您仍然需要将击键设置为Handled
,否则 IE 会选择它。 XBAP 不是一个使用非常广泛的框架,但我想我会让你知道我为什么要讨论处理浏览器:) - 谢谢。【参考方案4】:
KeyEventArgs
中有属性 Ctrl、Alt 和 Shift 显示这些按钮是否被按下。
【讨论】:
谢谢这工作完美!if(e.Control && e.KeyCode == Keys.A)
【参考方案5】:
private void listView1_KeyDown(object sender, KeyEventArgs e)
if (e.Key == Key.Up && Keyboard.IsKeyDown(Key.LeftCtrl))
//do stuff
此代码仅在您先按 LeftCtrl,然后按“UP”时才有效。 如果顺序不重要,我推荐一个:
if ((Keyboard.IsKeyDown(Key.LeftCtrl) || Keyboard.IsKeyDown(Key.RightCtrl))&& Keyboard.IsKeyDown(Key.Z))
//do stuff
在这种情况下,两个 Ctrl 都被考虑在内,并且顺序无关紧要。
【讨论】:
【参考方案6】:您可以使用 ModifierKeys 属性:
if (e.KeyCode == Keys.Up && (ModifierKeys & Keys.Control) == Keys.Control)
// CTRL + UP was pressed
请注意,ModifierKeys 值可以是值的组合,因此如果您想检测是否按下了 CTRL,而不管 SHIFT 或 的状态如何ALT 键,您将需要按照我上面的示例执行按位比较。如果你想确保没有按下其他修饰符,你应该检查是否相等:
if (e.KeyCode == Keys.Up && ModifierKeys == Keys.Control)
// CTRL + UP was pressed
【讨论】:
在HERE,您说数据在KeyData字段中。这里没有人提到KeyData。这些答案不正确吗? 不错@jp2code!ModifierKeys
是Control
上的一个属性(例如windows 窗体),它将为您提供有关当前 被按下的修饰键的信息。键事件附带的KeyData
包含有关与导致事件的键一起按下的修饰键的信息。回想起来,我会说ModifierKeys
与按钮单击或类似事件一起更有趣,在关键事件中使用KeyData
会更准确。【参考方案7】:
这肯定会奏效。小心处理KeyUp
事件而不是keyDown
。
private void mainForm_KeyUp(object sender, KeyEventArgs e)
if (e.Modifiers == Keys.Control && e.KeyCode == Keys.A)
//insert here
对我来说,keyDown
不起作用,keyU
p 对相同的代码起作用。
我不知道为什么,但似乎是因为keyDown
事件在你按下任意键后直接发生,即使那是 ctrl 键,所以如果你按下 ctrl kbd>+Up 您将在 UP 键之前按 ctrl 键,因此事件将在您按下另一个之前发生,同时按下第二个键将再次触发事件。
虽然使用KeyUp
不会触发事件,直到你松开按键,所以你可以按ctrl,再按第二个键,会触发一个事件。
【讨论】:
【参考方案8】:我测试了下面的代码。它有效...
private void listView1_KeyDown(object sender, KeyEventArgs e)
if ((int) e.KeyData == (int) Keys.Control + (int) Keys.Up)
MessageBox.Show("Ctrl + Up pressed...");
【讨论】:
【参考方案9】:在尝试检测 [Alt][Right] 时,我花了一段时间才找到最终需要的提示。我在这里找到了它:https://social.msdn.microsoft.com/Forums/vstudio/en-US/4355ab9a-9214-4fe1-87ea-b32dfc22946c/issue-with-alt-key-and-key-down-event?forum=wpf
在我使用的 Shortcut
助手类中归结为类似这样的内容:
public Shortcut(KeyEventArgs e) : this(e.Key == System.Windows.Input.Key.System ? e.SystemKey : e.Key, Keyboard.Modifiers, false)
public Shortcut(Key key, ModifierKeys modifiers, bool createDisplayString)
...
在“重新映射”原始值之后(注意e.Key == System.Windows.Input.Key.System ? e.SystemKey : e.Key
部分),可以照常进行进一步处理。
【讨论】:
【参考方案10】:if (e.Control && e.Shift && e.KeyCode == Keys.A)
【讨论】:
在回答旧帖子时,如果您可以为您的回答提供一些上下文而不仅仅是代码,这将很有帮助,因为它可能对其他人更有用。【参考方案11】:KeyDown 事件将只保存最近按下的键的信息。我已经成功构建了一个字符串,其中包含所有最新的按键连接在一起。
如果按下“Control”键,或者字符串长度超过 10 个字符,我会清除字符串。
每次检查字符串,然后在执行任务后执行任务,可以很好地使用应用程序中的秘密热键功能。
private void ConfigurationManager_KeyDown(object sender, KeyEventArgs e)
string currentKey = e.KeyCode.ToString().ToLower();
if ((currentKey == "controlkey") || (hotKeyList.Length > 10))
hotKeyList = "";
else
hotKeyList += currentKey;
if ((hotKeyList == "int") && (!adminLogin))
hotKeyList = "";
adminLogin = true;
AdminLoginEvn();
对于上面的函数,我的热键将是“Control(清除字符串)+ i + n + t”来触发我的 AdminLoginEvn 方法。 adminLogin 布尔值被合并,所以我只在应用程序打开时运行一次 AdminLoginEvn。
【讨论】:
【参考方案12】:你可以试试我的工作代码:
private void listView1_KeyDown(object sender, KeyEventArgs e)
if (e.KeyCode == Keys.Up)
if(e.Alt==true)
//do your stuff
我使用此代码是因为我不知道为什么使用时:
(e.Keycode == Keys>up && e.Alt==true)
没用。
【讨论】:
【参考方案13】:您必须记住按下的键(即在布尔数组中)。并在按下 (keydown) 时将位置设置为 1,在向上时将位置设置为 0。
这样您可以跟踪多个键。我建议只为特殊键做一个数组
所以你可以这样做:
if (e.KeyCode == Keys.Control)
keys[0] = true;
// could do the same with alt/shift/... - or just rename keys[0] to ctrlPressed
if (keys[0] == true && e.KeyCode == Keys.Up)
doyourstuff
【讨论】:
以上是关于KeyDown : 识别多个键的主要内容,如果未能解决你的问题,请参考以下文章