Използвах събитие KeyDown и някакъв прост код като if (e.KeyCode == Keys.F1)
за улавяне на F1 е натиснат във формуляр, НО ако има някои текстови полета във формуляра или ако има някои електронни таблици с Dock Fill във формуляра, тогава кодът по-горе става безполезен и не прави нищо. Но искам да направя нещо, когато потребителят натисне F1 на този формуляр. така че как да заснемем конкретно събитие на натискане на клавиш като F1 в целия формуляр...и аз не искам да отида до маршрута, който улавя KeyDown на всички други контроли във формуляра и ги предава на формуляра за обработка. има ли някакъв по-чист начин да направите това?
Как да уловя Keys.F1 независимо от фокусираната контрола във формуляр?
Отговори (4)
Да, наистина има. Правилният начин формулярът да обработва ключови събития, независимо от контролата, която в момента има входен фокус, е да замени ProcessCmdKey
метод на вашия клас формуляр:
protected override bool ProcessCmdKey(ref Message msg, Keys keyData)
{
if (keyData == Keys.F1)
{
MessageBox.Show("You pressed the F1 key");
return true; // indicate that you handled this keystroke
}
// Call the base class
return base.ProcessCmdKey(ref msg, keyData);
}
Връщате true
, за да посочите, че сте обработили натискането на клавиша и не искате то да бъде предадено на други контроли. Ако наистина искате то да бъде предадено на манипулаторите на събития за други контроли, просто върнете false
.
И най-добре е да игнорирате свойството KeyPreview
. Това е анахронизъм от 6-те дни на VB и всъщност не е предпочитаният начин да се направи това в света на .NET. Допълнителна информация: Недостатък на настройката на Form.KeyPreview = true?
KeyPreview
използва ориентираната към събитията архитектура на .NET, докато вие просто отменяте WndProc
, предпочитания Win3.1 (да, точно така, технология от 1992 г.) начин за това.
- person Blindy; 10.05.2011
WndProc
(въпреки че и това работи). Рамката извиква този метод в подходящия момент специално за обработка на тези събития. Освен това правенето на нещата по този начин ви позволява да решите дали искате събитието да бъде предадено на други контроли или не.
- person Cody Gray; 10.05.2011
WndProc
, когато uMsg=WM_KEYDOWN
. И точно както при проверката на кодовете на виртуалните ключове в API на Win32, вие не знаете дали потребителят е въвел действителния ключ или неговата изместена версия (наред с други неща). Всеки сам, но бих бил по-внимателен кой API наричам по-лош.
- person Blindy; 10.05.2011
KeyPreview
е по-добра алтернатива.
- person Cody Gray; 10.05.2011
Задайте KeyPreview
на формуляра на true. Това ще гарантира, че формулярът първо получава съобщенията за натискане на клавиши и ако се справите с него, можете да зададете e.Handled = true
, така че да не се предава надолу към контролите.
Включете KeyPreview
и всяко натискане на клавиш във формуляра първо ще бъде пренасочено през неговите манипулатори на ключови събития.
Друг начин е да замените функцията ProcessCmdKey http://msdn.microsoft.com/en-us/library/system.windows.forms.control.processcmdkey(v=VS.100).aspx