首页 / 软件开发 / Delphi / 第七章-剪贴板和动态数据交换(一)(4)
第七章-剪贴板和动态数据交换(一)(4)2007-05-07为解决这些问题,我开发了下面的程序。程序启动时,以极小化方式运行。此时只要剪贴板中存入位图,则自动弹出一个对话框请求用户保存。如果用户希望查看确认,则可以双击运行程序图标,选择相应按钮,剪贴板中的位图就会显示在屏幕上。部件关键属性设计如下: ClipSaveForm:Caption=‘Save Bitmap in Clipboard "Panel1:Align = " Top "Image1:Align = " Client "SaveDialog1:FileEditStyle = fsEditFileName = "*.bmp"Filter = "Bitmap Files(*.bmp)|*.bmp|Any Files(*.*)|*.*"InitialDir = "c:mp"Title = "Save Bitmap" 程序主窗口是TForm派生类TClipSaveForm的实例。TClipSaveForm通过定义一些私有数据成员和过程,使响应和处理Windows的相应消息成为可能。下面是TClipSaveForm的类定义: typeTClipSaveForm = class(TForm)SaveDialog1: TSaveDialog;Image1: TImage;Panel1: TPanel;Button1: TButton;SpeedButton1: TSpeedButton;SpeedButton2: TSpeedButton;Button2: TButton;procedure FormCreate(Sender: TObject);procedure FormDestroy(Sender: TObject);procedure Button1Click(Sender: TObject);procedure Button2Click(Sender: TObject);procedure SpeedButton1Click(Sender: TObject);procedure SpeedButton2Click(Sender: TObject);private{ Private declarations }MyBitmap: TBitmap; { 保存截获的位图 }View: Boolean; { 判断是否显示 }NextViewerHandle: HWND; { 下一剪贴板观察器的句柄 }procedure WMDrawClipboard(var Msg:TWMDrawClipboard);message WM_DRAWCLIPBOARD;procedure WMChangeCBChain(var Msg:TWMChangeCBChain);message WM_CHANGECBCHAIN; { 响应Windows的剪贴板消息 }public{ Public declarations }end;窗口创建时,把该窗口登录为剪贴板观察器,添加到剪贴板观察器链中,同时进行变量、部件和剪贴板的初始化。 procedure TClipSaveForm.FormCreate(Sender: TObject);beginView := False;SpeedButton2.Down := True;MyBitmap := TBitmap.create;tryMyBitmap.Width := 0;MyBitmap.Height := 0 ;exceptApplication.terminate;end;Clipboard.Clear;NextViewerHandle := SetClipboardViewer(Handle);end; 窗口关闭时,退出剪贴板观察器链,并释放内存: procedure TClipSaveForm.FormDestroy(Sender: TObject);beginChangeClipboardChain(Handle,NextViewerHandle);MyBitmap.Free;end; 在以上两段程序中用到的两个Windows API函数SetClipboardViewer和ChangeClipboardChain分别用于登录和退出剪贴板观察器链。程序保存位图的功能是在消息响应过程WMDrawClipboard中实现的。该过程在剪贴板内容有变化时被调用。 procedure TClipSaveForm.WMDrawClipboard(var Msg: TWMDrawClipboard);varFileName: String;beginIf NextViewerHandle <> 0 thenSendMessage(NextViewerHandle,msg.Msg,0,0);If ClipBoard.HasFormat(CF_BITMAP) thenbeginMyBitmap.Assign(Clipboard);If SaveDialog1.Execute thenbeginFileName := SaveDialog1.FileName;MyBitmap.SaveToFile(FileName);end;If View thenbeginWindowState := wsNormal;Image1.Picture.Bitmap := MyBitmap;end;end;Msg.Result := 0;end; 程序首先判断在剪贴板观察器链中是否还存在下一个观察器。如果有,则把消息传递下去,这是剪贴板观察器程序的义务。而后判断剪贴板上内容的格式是否为位图。如是,则首先把剪贴板上内容保存到数据成员MyBitmap中,并激活一个文件保存对话框把位图保存到文件中。如果View=True,则把窗口状态(WindowState)设置为wsNormal,并把MyBitmap赋给Image部件的相应值,使用户可以对剪贴板上的位图进行观察。