分享

复制任意文件或文件夹到剪贴板

 aaie_ 2012-10-12

复制任意文件或文件夹到剪贴板

华软源码

uses

  ShlObj, ClipBrd;

procedure CopyFilesToClipboard(FileList: string);

var

  DropFiles: PDropFiles;

  hGlobal: THandle;

  iLen: Integer;

begin

  iLen := Length(FileList) + 2;

  FileList := FileList + #0#0;

  hGlobal := GlobalAlloc(GMEM_SHARE or GMEM_MOVEABLE or GMEM_ZEROINIT,

    SizeOf(TDropFiles) + iLen);

  if (hGlobal = 0) then raise Exception.Create('Could not allocate memory.');

  begin

    DropFiles := GlobalLock(hGlobal);

    DropFiles^.pFiles := SizeOf(TDropFiles);

    Move(FileList[1], (PChar(DropFiles) + SizeOf(TDropFiles))^, iLen);

    GlobalUnlock(hGlobal);

    Clipboard.SetAsHandle(CF_HDROP, hGlobal);

  end;

end;

// Example:

procedure TForm1.Button1Click(Sender: TObject);

begin

  CopyFilesToClipboard('C:\Bootlog.Txt'#0'C:\AutoExec.Bat');

end;

{

  Separate the files with a #0.

}

********************************

沈前卫的回答 :

unit Unit1;

interface

uses

 Windows, Messages, SysUtils, Classes, Graphics, Controls, Forms, Dialogs,

 StdCtrls,ShlObj;

type

 TForm1 = class(TForm)

   Button1: TButton;

   procedure Button1Click(Sender: TObject);

 private

   { Private declarations }

 public

   { Public declarations }

 end;

var

 Form1: TForm1;

implementation

{$R *.DFM}

procedure TForm1.Button1Click(Sender: TObject);

const  FileName:string='c:\netlog.txt';

var

 DataHandle: THandle;

 DataPointer: PDROPFILES;

begin

 DataHandle := GlobalAlloc(GMEM_DDESHARE or GMEM_MOVEABLE,SizeOf(DROPFILES)+2+Length(FileName));

 DataPointer := PDROPFILES(GlobalLock(DataHandle));

 FillChar(DataPointer^,SizeOf(DROPFILES)+2+Length(FileName),0);

 DataPointer.pFiles:=SizeOf(DROPFILES);

 DataPointer.pt:=Point(0,0);

 DataPointer.fNC:=False;

 DataPointer.fWide:=False;

 Move(FileName[1],Pointer(Integer(DataPointer)+SizeOf(DROPFILES))^,Length(FileName));

 GlobalUnlock(DataHandle);

 OpenClipboard(Form1.Handle);

 EmptyClipboard;

 SetClipboardData(CF_HDROP, DataHandle);

 CloseClipboard;

end;

end.

***************************

在 Windows 的资源管理器中 ,选中一个或多个文件 ,在文件上单击鼠标右键 ,在弹出菜单中选复制。再切换到另外的目录 ,单击鼠标右键 ,点粘贴。就这样执行了一次文件的拷贝操作 ,那么 Windows 在拷贝过程中执行了什么操作 ,是否将整个文件拷贝到剪贴板上了呢?当然没有。实际上 ,Windows 只是将一个文件结构拷贝到了剪贴版 ,这个结构如下 :

    tDropFile+ 文件 1 文件名 +vbNullChar+ 文件 2 文件名 +vbNullChar …… + 文件 N 文件名 +vbNullChar,其中 tDropFile 是一个 DROPFILES 结构 ,这个结构在 Windows API 中有定义。在粘贴文件时 ,利用 API 函数  DragQueryFile  就可以获得拷贝到剪贴板的文件全路径名 ,然后就可以根据获得的文件名执行文件拷贝函数 ,实现对文件的粘贴操作。

那么如何从剪切板或取复制的文件内容呢?请参看下面的例子 :

/// Author:Peter Below

uses

  clipbrd, shellapi;

{$R *.dfm}

procedure TForm1.Button1Click(Sender: TObject);

var

  f: THandle;

  buffer: array [0..MAX_PATH] of Char;

  i, numFiles: Integer;

begin

  if not Clipboard.HasFormat(CF_HDROP) then Exit;

  Clipboard.Open;

  try

    f := Clipboard.GetAsHandle(CF_HDROP);

    if f <> 0 then

    begin

      numFiles := DragQueryFile(f, $FFFFFFFF, nil, 0);

      memo1.Clear;

      for i := 0 to numfiles - 1 do

      begin

        buffer[0] := #0;

        DragQueryFile(f, i, buffer, SizeOf(buffer));

        memo1.Lines.Add(buffer);

      end;

    end;

  finally

    Clipboard.Close;

  end;

end;

    本站是提供个人知识管理的网络存储空间,所有内容均由用户发布,不代表本站观点。请注意甄别内容中的联系方式、诱导购买等信息,谨防诈骗。如发现有害或侵权内容,请点击一键举报。
    转藏 分享 献花(0

    0条评论

    发表

    请遵守用户 评论公约

    类似文章 更多