Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Delphi: Общие вопросы > Определение нажатия клавиши


Автор: Piton 22.9.2003, 09:47
Есть проблема! Надо отловить все нажатия клавиш пользователя и определить, какая именно клавиша нажата.
Под Windows все работает, но с DOS есть неувязки!
Я использую комманду GetAsyncKeyState, может есть другой путь решения?

Автор: oleg1973 22.9.2003, 13:16
ну так GetAsyncKeyState это из виндосовского АПИ так что под досом не заработает 100%
используй какуюнить стандартную функцию как к примеру getchar() в Си
в паскале не знаю просто как

Автор: neutrino 22.9.2003, 15:45
Однозначно тебе нужно использовать Хук. Перехват всех событий в Windows (в том числе и событий от клавиатуры) выполняется с помощью вызова функции SetWindowsHook[Ex](). Данная функция регистрирует в системе Windows ловушку (hook) для определенного типа событий/сообщений. Ловушка - это пользовательская процедура, которая будет обрабатывать указанное событие.

Цитата

Var CountChars:Integer; //Количество выловленных символов
       Str:String; //Накопитель выловленых символов
       HookHandle: hHook; //Хранит значение предыдущего обработчика клавы, который был по умолчанию

//Объявление функции обработки нажатии клавиатуры
Function KeyboardProc(Code: integer; WParam: WParam; LParam: LParam): LResult; stdcall; //Обработчик событий от клавиатуры
  Type TWParamTranslation=Record
                           Byte12:Word;
                           Byte3:Byte;
                           Byte4:Byte;
                          End;

Begin
  If TWParamTranslation(LParam).Byte4 and 128<>0 Then //Отлавливается сообщение, в котором
                                                      //содержится символ
  Begin
   Inc(CountChars);
   Str:=Str+Chr(WParam);
  End;
  If Length(Str)>20 Then SendMessage(fMain.Handle,WM_Received,0,0); //Останавливаем перехват
                       //клавиатуры в случае, когда выловлено необходимое количество символов
End;


Procedure StartHook; //Начинает перехват событий от клавиатуры
Begin
   CountChars:=0;
   Str:='';
   HookHandle := SetWindowsHookEx(WH_KEYBOARD, @KeyboardProc, Hinstance, 0);
End;

Procedure StopHook; //Прекращает перехват событий от клавиатуры
Begin
  UnhookWindowsHookEx(HookHandle);
End;


Автор: neutrino 22.9.2003, 15:52
Небольшое дополнение: можно вызвать прежний обработчик клавиатуры, вызвав функцию CallNextHookEx()

И еще, все объявления находятся тут: WinTypes, WinProcs;

Автор: oleg1973 22.9.2003, 16:23
neutrino не будет оно в дос сессии ловить кнопочки
покрайне мере я делал не получилось
в виндосе все ловит прекрасно
просто вопрос так поставлен что его можно по разному понять еслиб Piton
уточнил что он имеет в виду под словом DOS (чистый дос, дос сессию (эмуляцию) в виндосе)
тогдаб можно было и по конкретней обьяснить

Автор: neutrino 22.9.2003, 16:32
Угу, в эмуляции запустить :etWindowsHook будет крайне тяжело.
smile.gif
А мой способ с Дос окном должен работать...

Автор: dm9 22.9.2003, 17:16
Если надо под чистым ДОСом, могу написать программу. (Ну, типа клавиатурный шпион). А под винду - хуки. Это уже написали.

Автор: cot 23.9.2003, 06:28
Ловит нажатие любой клавиши в DOC, но это правдв чистый Паскаль
function ReadKeyWord:word;
var Regs:Registers;
begin
with Regs do begin
AH:=0;
intr($16,Regs);
ReadKeyWord:=AX
end
end;
Вообще ничего такого, чтобы не работало в Delphi здесь нет.

Автор: Akella 23.9.2003, 08:41
Сколько хуков я не перепробовал...
нормально работают только хуки в самой программе, т.е. в самом хуке, а отлавливать в во всей системе тяжело, это надо быть очень умным, у меня есть три или четыре примера и ни один нормально не работает.

Автор: dm9 23.9.2003, 10:50
cot, боюсь что это не все клавиши.
С Shift-Ctrl-Alt, с xxxxLock, с PrintScreen, c Pause/Break работать не будет.

Автор: oleg1973 23.9.2003, 12:48
dsergey
ну не знаю недавно написал кейлогер
все ловит окромя доссесии
обычный глобальный хук на клаву использовал

Автор: Akella 23.9.2003, 21:08
давай я пришлю свои, а ты посмотришь чего я на партачил, отпиши адрес, если ты не против.
А то я уже совсем замучился с этими хуками.

Автор: dm9 23.9.2003, 22:06
dsergey, прочитай статью и посмотри прилагаемые к ней исходники.

http://www.delphimaster.ru/articles/hooks/index.html

Это уже классика жанра smile.gif

Автор: cot 24.9.2003, 06:09
cot, боюсь что это не все клавиши.
Насчет клавиш не знаю по идее должно перехватывать все. Дело в другом в Делфи нет Паскалевого модуля Dos или WinDos , которые содержат запись Register

Автор: dm9 24.9.2003, 13:33
cot, да не в этом дело. Это можно сделать на асме. Твоя функция:

Код
function ReadKeyWord : Word;
var R : Word;
begin
  asm
     mov ah,0
     int 16h
     mov R,AX
  end;
  Result := R;
end


Только это не даст тебе возможности ловить клавиши всех процессов. Не путай ДОС с многозадачной системой.

Автор: Piton 29.9.2003, 11:06
Здравствуйте, извините, что долго не отвечал - болел и на работу не ходил!

Хочется чуть пояснить - нужна программа, отлавливающая в системе нажатия клавиш с буквами и цифрами, но проблема в том, что пользователь частенько сидит в редакторе под Norton Commander (в DOS сессии), и вот здесь я уже не могу что-либо отловить. Хуки тоже не срабатывают!

Цитата

Однозначно тебе нужно использовать Хук. Перехват всех событий в Windows (в том числе и событий от клавиатуры) выполняется с помощью вызова функции SetWindowsHook[Ex](). Данная функция регистрирует в системе Windows ловушку (hook) для определенного типа событий/сообщений. Ловушка - это пользовательская процедура, которая будет обрабатывать указанное событие.


Кстати, neutrino, как можно передать дальнейшую обработку системе событий, поступающих с клавы, т.к. после установки данного хука, клава "замолкает", а файлик растет!

Автор: oleg1973 29.9.2003, 20:01
ну ты его ставиш с SetWindowsHookEx
а потом после получения кнопочки передаеш дальше с CallNextHookEx

Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)