delphi文件监视主单元文件


本文整理自网络,侵删。

 //--------------------------------------------------------------------------
//delphi文件监视主单元文件
//作者:hnxyy QQ:19026695
//修改自 ccrun(老妖) 的 C++Builder 单元代码
//-------------------------------------------------------------------------
{利用未公开函数实现Shell操作监视 作者 : TechnoFantasy
在Windows下有一个未公开函数SHChangeNotifyRegister可以吧你的窗口添加到系统的
系统消息监视链中,该函数在Delphi中的定义如下:
Function SHChangeNotifyRegister(hWnd,uFlags,dwEventID,uMSG,cItems:LongWord;
lpps:PIDLSTRUCT):integer;stdcall;external 'Shell32.dll' index 2;
其中参数hWnd定义了监视系统操作的窗口得句柄,参数uFlags dwEventID定义监视操作
参数,参数uMsg定义操作消息,参数cItems定义附加参数,参数lpps指定一个PIDLSTRUCT
结构,该结构指定监视的目录。
当函数调用成功之后,函数会返回一个监视操作句柄,同时系统就会将hWnd指定的窗
口加入到操作监视链中,当有文件操作发生时,系统会向hWnd发送uMsg指定的消息,我
们只要在程序中加入该消息的处理函数就可以实现对系统操作的监视了。
如果要退出程序监视,就要调用另外一个未公开得函数SHChangeNotifyDeregister来取
消程序监视。}
unit Unit1;
interface
uses
Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
Dialogs, StdCtrls, ExtCtrls, shlobj, Activex;
//通知消息
const
WM_SHNOTIFY = $401;
type
TForm1 = class(TForm)
Panel1: TPanel;
Panel2: TPanel;
MM: TMemo;
Button1: TButton;
Button2: TButton;
Button3: TButton;
procedure FormCreate(Sender: TObject);
procedure FormClose(Sender: TObject; var Action: TCloseAction);
procedure Button1Click(Sender: TObject);
procedure Button2Click(Sender: TObject);
procedure Button3Click(Sender: TObject);
private
{ Private declarations }
procedure WMShellReg(var Message:TMessage);message WM_SHNOTIFY;
public
{ Public declarations }
end;
type PIDLSTRUCT = ^IDLSTRUCT;
_IDLSTRUCT = record
pidl : PItemIDList;
bWatchSubFolders : Integer;
end;
IDLSTRUCT =_IDLSTRUCT;
type PSHNOTIFYSTRUCT=^SHNOTIFYSTRUCT;
SHNOTIFYSTRUCT = record
dwItem1 : PItemIDList;
dwItem2 : PItemIDList;
end;
//注册通知消息
function RegSHNotify(hWnd :Integer):Bool;
//解除通知注册
function UnregSHNotify:Bool;
//获取消息具体内容
function NotifyReceipt(wParam :WPARAM;lParam :LPARAM):string;
//定义未公开API函数
Function SHChangeNotifyDeregister(hNotify:integer):integer;stdcall;
external 'Shell32.dll' index 4;
Function SHChangeNotifyRegister(hWnd,uFlags,dwEventID,uMSG,cItems:LongWord;
lpps:PIDLSTRUCT):integer;stdcall;external 'Shell32.dll' index 2;
var
Form1: TForm1;
g_HSHNotify :integer;
g_pidlDesktop :PItemIDList;
implementation
{$R *.dfm}
//获取消息具体内容
function NotifyReceipt(wParam :WPARAM;lParam :LPARAM):string;
var
strEvent :String;
strPath1,strPath2 :String;
szBuf :array[0..MAX_PATH] of char;
pidlItem :PSHNOTIFYSTRUCT;
begin
pidlItem :=PSHNOTIFYSTRUCT(wParam);
//获得系统消息相关的路径
SHGetPathFromIDList(pidlItem.dwItem1,szBuf);
strPath1:=szBuf;
SHGetPathFromIDList(pidlItem.dwItem2,szBuf);
strPath2:=szBuf;
//根据参数设置提示消息
case lParam of
SHCNE_RENAMEITEM: strEvent := '重命名文件: ' + strPath1 + ' 为 '+ strpath2;
SHCNE_CREATE: strEvent := '建立文件, 文件名: ' + strPath1;
SHCNE_DELETE: strEvent := '删除文件, 文件名:' + strPath1;
SHCNE_MKDIR: strEvent := '新建目录, 目录名:' + strPath1;
SHCNE_RMDIR: strEvent := '删除目录, 目录名:' + strPath1;
SHCNE_ATTRIBUTES: strEvent := '改变文件目录属性, 文件名:' + strPath1;
SHCNE_MEDIAINSERTED: strEvent := strPath1 + ' 中插入可移动存储介质';
SHCNE_MEDIAREMOVED: strEvent := strPath1 + ' 中移去可移动存储介质';
SHCNE_DRIVEREMOVED: strEvent := '移去驱动器: '+ strPath1;
SHCNE_DRIVEADD: strEvent := '添加驱动器: ' + strPath1;
SHCNE_NETSHARE: strEvent := '改变目录 ' + strPath1 + ' 的共享属性';
SHCNE_UPDATEDIR: strEvent := '更新目录: ' + strPath1;
SHCNE_UPDATEITEM: strEvent := '更新文件, 文件名: ' + strPath1;
SHCNE_SERVERDISCONNECT: strEvent := '断开与服务器的连接: ' + strPath1 + ' ' + strpath2;
SHCNE_UPDATEIMAGE: strEvent :='更新图标: ' + strPath1 + ' ' + strpath2;
SHCNE_DRIVEADDGUI: strEvent := '添加并显示驱动器: ' + strPath1;
SHCNE_RENAMEFOLDER: strEvent := '重命名文件夹: ' + strPath1 + ' 为 ' + strpath2;
SHCNE_FREESPACE: strEvent := '磁盘空间大小改变: ' + strPath1 + ' ' + strpath2;
SHCNE_ASSOCCHANGED: strEvent := '改变文件关联' + strPath1 + ' ' + strpath2;
else
strEvent:='其他操作'+IntToStr(lParam);
end;
Result:=strEvent;
end;
//注册通知消息
function RegSHNotify(hWnd :Integer):Bool;
var
ps:PIDLSTRUCT;
begin
Result:=False;
If g_HSHNotify = 0 then
begin
//取得桌面的IDL
SHGetSpecialFolderLocation(0, CSIDL_DESKTOP{CSIDL_DRIVES}, g_pidlDesktop);
//if SHGetSpecialFolderLocation(0, CSIDL_DESKTOP,g_pidlDesktop)<> NOERROR then
// Form1.close;
if Boolean(g_pidlDesktop) then
begin
getmem(ps,sizeof(IDLSTRUCT));
ps.bWatchSubFolders := 1;
ps.pidl := g_pidlDesktop;
//注册Windows监视
g_HSHNotify := SHChangeNotifyRegister(hWnd, (SHCNF_TYPE Or SHCNF_IDLIST),
(SHCNE_ALLEVENTS Or SHCNE_INTERRUPT),WM_SHNOTIFY, 1, ps);
Result := Boolean(g_HSHNotify);
end else
//如果出现错误就使用 CoTaskMemFree函数来释放句柄
CoTaskMemFree(g_pidlDesktop);
end;
end;
//解除通知注册
function UnregSHNotify:Bool;
begin
Result:=False;
if Boolean(g_HSHNotify) Then
begin
//取消系统消息监视,同时释放桌面的IDL
if Boolean(SHChangeNotifyDeregister(g_HSHNotify)) Then
begin
g_HSHNotify := 1;
CoTaskMemFree(g_pidlDesktop);
//Boolean(g_pidlDesktop) :=0;
Result := True;
end;
end;
end;
procedure TForm1.FormCreate(Sender: TObject);
begin
Caption :=Application.Title;
end;
procedure TForm1.WMShellReg(var Message: TMessage);
begin
MM.Lines.Add(NotifyReceipt(Message.WParam,Message.lParam));//+chr(13)+chr(10));
end;
procedure TForm1.FormClose(Sender: TObject; var Action: TCloseAction);
begin
//在程序退出的同时删除监视
if Boolean(g_pidlDesktop) then
UnregSHNotify;
end;
procedure TForm1.Button1Click(Sender: TObject);
begin
g_HSHNotify :=0;
MM.Lines.Clear;
if RegSHNotify(Handle) then
begin
MM.Lines.Add('开始监视程序-->成功!');
Button1.Enabled :=False;
end else
MM.Lines.Add('开始监视程序-->失败!');
end;
procedure TForm1.Button2Click(Sender: TObject);
begin
if Boolean(g_pidlDesktop) then
begin
if UnregSHNotify then
begin
MM.Lines.Add('停止监视程序-->成功!');
Button1.Enabled :=True;
end else
MM.Lines.Add('停止监视程序-->失败!');
end;
end;
procedure TForm1.Button3Click(Sender: TObject);
begin
MessageBox(0, '文件监视功能演示' + #13#10 +
'Coded By: hnxyy' + #13#10 +
'Homepage: http://www.wrsky.com' + #13#10 +
'Contact: QQ:19026695', '火狐出品', 0);
end;
end.

相关阅读 >>

Delphi 调用批处理

Delphi reset 以只读方式打开文件

Delphi中的record怎么动态分配内存?

Delphi字符串旋转任意角度

Delphi列表控件tlistview定位到某一行

Delphi 查找字符串并删除该字符串

Delphi xe7中的运行时设置android应用程序屏幕方向

Delphi savetextfiledialog 用法

Delphi 快速获取文件大小(使用_lopen和fileseek,此函数可以快速获取文件大小,即使文件已经被其它程序锁定)

Delphi 位运算

更多相关阅读请进入《Delphi》频道 >>



打赏

取消

感谢您的支持,我会继续努力的!

扫码支持
扫码打赏,您说多少就多少

打开支付宝扫一扫,即可进行扫码打赏哦

分享从这里开始,精彩与您同在

评论

管理员已关闭评论功能...