線上訂房服務-台灣趴趴狗聯合訂房中心
發文 回覆 瀏覽次數:1904
推到 Plurk!
推到 Facebook!

請問setforcus 在某個資料夾的問題

尚未結案
anaconda1813
一般會員


發表:29
回覆:29
積分:11
註冊:2004-10-12

發送簡訊給我
#1 引用回覆 回覆 發表時間:2005-08-29 02:33:13 IP:140.123.xxx.xxx 未訂閱
想要複製依個資料夾..,打算用模擬ctrl c ctrl v的方法去複製 filepath 已經是那個資料夾的路徑 可是卻不知道要怎麼去選取它 想請問要怎麼setfocus在路徑上的資料夾呢?? 還是需要用到其他的元件才可以達到??
RedSnow
版主


發表:79
回覆:1322
積分:845
註冊:2003-12-15

發送簡訊給我
#2 引用回覆 回覆 發表時間:2005-09-10 23:32:29 IP:61.230.xxx.xxx 未訂閱
anaconda1813 您好:    您既然都已經知道資料夾的路徑了,那麼我實在看不出來您所謂的 "不知道要怎樣去選取它" 指的是什麼樣的問題? 可否請您將相關的背景資料提供得詳實一點?例如:您所要寫的是何種類型的程式、打算提供何種操作方式及操作介面所謂的 SetFocus 是指用在何種元件或是模式上....等等。 7 天天敲鍵盤 v 時時按滑鼠 8
anaconda1813
一般會員


發表:29
回覆:29
積分:11
註冊:2004-10-12

發送簡訊給我
#3 引用回覆 回覆 發表時間:2005-09-11 21:22:05 IP:140.123.xxx.xxx 未訂閱
引言: anaconda1813 您好: 您既然都已經知道資料夾的路徑了,那麼我實在看不出來您所謂的 "不知道要怎樣去選取它" 指的是什麼樣的問題? 可否請您將相關的背景資料提供得詳實一點?例如:您所要寫的是何種類型的程式、打算提供何種操作方式及操作介面所謂的 SetFocus 是指用在何種元件或是模式上....等等。 7 天天敲鍵盤 v 時時按滑鼠 8
恩~主要是因為我想要像是在一班windows環境下那樣,複製依個資料夾 譬如要複製C:\Downloads這個資料夾,不是都會先點一下這個資料夾 然後按下ctrl c這樣~ 我只是想要用依個bottom按下後的事件去模擬以上動作而已 而沒有用到其他的元件~
RedSnow
版主


發表:79
回覆:1322
積分:845
註冊:2003-12-15

發送簡訊給我
#4 引用回覆 回覆 發表時間:2005-09-13 00:25:54 IP:59.115.xxx.xxx 未訂閱
anaconda1813 您好:    以下方式可以呼叫出檔案總管 (Windows Explorer),並 Focus 到指定的目錄去:
AnsiString dir = getenv("SystemRoot");  // 取得系統目錄名稱
AnsiString target = dir "\\explorer.exe";  // 指定執行對象為檔案總管
AnsiString param = "/e, \"C:\\downloads\"";  // 設定啟動參數與欲指向的目錄
ShellExecute(NULL, "Open", target.c_str(), param.c_str(), NULL, SW_SHOWNORMAL);
請注意,以紅色標示的地方是雙引號,在字串中使用雙引號 (") 或反斜線 (\) 等特定字元時,需要在前方加上一個反斜線。 7 天天敲鍵盤 v 時時按滑鼠 8
anaconda1813
一般會員


發表:29
回覆:29
積分:11
註冊:2004-10-12

發送簡訊給我
#5 引用回覆 回覆 發表時間:2005-09-14 03:31:14 IP:140.123.xxx.xxx 未訂閱
引言: anaconda1813 您好: 以下方式可以呼叫出檔案總管 (Windows Explorer),並 Focus 到指定的目錄去:
AnsiString dir = getenv("SystemRoot");  // 取得系統目錄名稱
AnsiString target = dir "\\explorer.exe";  // 指定執行對象為檔案總管
AnsiString param = "/e, \"C:\\downloads\"";  // 設定啟動參數與欲指向的目錄
ShellExecute(NULL, "Open", target.c_str(), param.c_str(), NULL, SW_SHOWNORMAL);
請注意,以紅色標示的地方是雙引號,在字串中使用雙引號 (") 或反斜線 (\) 等特定字元時,需要在前方加上一個反斜線。 7 天天敲鍵盤 v 時時按滑鼠 8
謝謝您~~ 想請問那個參數/e是代表什麼意思呢?? 再請問 因為如果直接加上ctrl c ctrl v會變成沒有效果(因為還在開啟路徑表中), 我是用sleep去等待.. 想再請問能否有辦法得知是否已經開完路徑了呢?(避免使用sleep)
RedSnow
版主


發表:79
回覆:1322
積分:845
註冊:2003-12-15

發送簡訊給我
#6 引用回覆 回覆 發表時間:2005-09-14 18:31:13 IP:59.115.xxx.xxx 未訂閱
anaconda1813 您好:    有關檔案總管的啟動參數及其相關解說請參考下列微軟的網頁: 如何自訂 Windows XP 中的 Windows 檔案總管檢視 http://support.microsoft.com/?scid=kb%3Bzh-tw%3B307856&x=10&y=12 另外關於等待檔案總管載入完畢的動作可以使用 FindWindow() 配合迴圈來處理,我將前一個範例加上等待動作修改如下:
AnsiString sysdir = getenv("SystemRoot");  // 取得系統目錄名稱
AnsiString prog = sysdir+"\\explorer.exe";  // 指定執行對象為檔案總管
AnsiString target = "C:\\Downloads";  // 設定要指向的目錄名稱
AnsiString param = "/e, \""+target+"\"";  // 設定啟動參數與欲指向的目錄
ShellExecute(NULL, "Open", prog.c_str(), param.c_str(), NULL, SW_SHOWNORMAL);
while (FindWindow(NULL, target.c_str()) == NULL) {  // 直到檔案總管啟動完畢為止
    Application->ProcessMessages();  // 避免迴圈咬住程式而影響其它動作
    if (Application->Terminated) {  // 設定在程式結束時跳出迴圈
        break;
    }
}
.... 接著做其它的動作 (例如您提到的複製動作) ....
7 天天敲鍵盤 v 時時按滑鼠 8
anaconda1813
一般會員


發表:29
回覆:29
積分:11
註冊:2004-10-12

發送簡訊給我
#7 引用回覆 回覆 發表時間:2005-09-14 21:02:12 IP:140.123.xxx.xxx 未訂閱
引言: anaconda1813 您好: 有關檔案總管的啟動參數及其相關解說請參考下列微軟的網頁: 如何自訂 Windows XP 中的 Windows 檔案總管檢視 http://support.microsoft.com/?scid=kb%3Bzh-tw%3B307856&x=10&y=12 另外關於等待檔案總管載入完畢的動作可以使用 FindWindow() 配合迴圈來處理,我將前一個範例加上等待動作修改如下:
AnsiString sysdir = getenv("SystemRoot");  // 取得系統目錄名稱
AnsiString prog = sysdir+"\\explorer.exe";  // 指定執行對象為檔案總管
AnsiString target = "C:\\Downloads";  // 設定要指向的目錄名稱
AnsiString param = "/e, \""+target+"\"";  // 設定啟動參數與欲指向的目錄
ShellExecute(NULL, "Open", prog.c_str(), param.c_str(), NULL, SW_SHOWNORMAL);
while (FindWindow(NULL, target.c_str()) == NULL) {  // 直到檔案總管啟動完畢為止
    Application->ProcessMessages();  // 避免迴圈咬住程式而影響其它動作
    if (Application->Terminated) {  // 設定在程式結束時跳出迴圈
        break;
    }
}
.... 接著做其它的動作 (例如您提到的複製動作) ....
7 天天敲鍵盤 v 時時按滑鼠 8
不過我在
if (Application->Terminated) {  // 設定在程式結束時跳出迴圈
       ShowMessage("123"); break;
    }
或是在while的最外面ShowMessage("123") 結果都不會有效果,請問這是為什麼呢?不是在他結束後因該會顯示出來ShowMessage才對阿??
RedSnow
版主


發表:79
回覆:1322
積分:845
註冊:2003-12-15

發送簡訊給我
#8 引用回覆 回覆 發表時間:2005-09-14 23:04:59 IP:59.115.xxx.xxx 未訂閱
anaconda1813 您好:
引言:不過我在 if (Application->Terminated) { // 設定在程式結束時跳出迴圈 ShowMessage("123"); break; } 或是在while的最外面ShowMessage("123") 結果都不會有效果,請問這是為什麼呢?不是在他結束後因該會顯示出來ShowMessage才對阿??
請您看仔細一點,我在那ㄧ行後邊加上註解寫的是 "設定在程式結束時跳出迴圈",判斷式寫的也是 if (Application->Terminated) {,亦即該判斷式是在程式本身結束掉時跳出迴圈使用的 (因應程式還在執行該迴圈,卻突然被結束掉使用的),如果您對該判斷式有疑問的話,請將那三行刪除掉好了,影響不大的。 關於第二個問題,會不會是 ShowMessage() 其實是有秀出來,只是被呼叫出來的檔案總管遮住了?我貼上來的程式碼在我的環境中 (Windows 2000 BCB4) 是能正確執行的,如果在您的環境中有問題的話,請檢查一下您設定的 target 名稱與呼叫出來後的檔案總管 Caption 是否相同?如果找不出問題的話,請將您現在實際測試的程式碼貼上來,比便於討論。 7 天天敲鍵盤 v 時時按滑鼠 8 發表人 - RedSnow 於 2005/09/14 23:48:35
malanlk
尊榮會員


發表:20
回覆:694
積分:577
註冊:2004-04-19

發送簡訊給我
#9 引用回覆 回覆 發表時間:2005-09-15 07:17:11 IP:203.69.xxx.xxx 未訂閱
procedure TForm1.Button1Click(Sender: TObject);
begin
  Application.Terminate;
  ShowMessage('I am Free');
  MessageBox(Application.Handle,'I am Free','Free! I Need to be Free!',MB_OK);
end;
ShowMessage 是由 TCustomFrom 繼承下來, 當 Application 結束, ShowMessage 無法指定 Owner 或 Parent, 所以應該是沒反應的. 如果要有反應可以考慮用 Window API... MessageBox.
RedSnow
版主


發表:79
回覆:1322
積分:845
註冊:2003-12-15

發送簡訊給我
#10 引用回覆 回覆 發表時間:2005-09-15 12:18:25 IP:61.230.xxx.xxx 未訂閱
malanlk 您好:    您的說明有點令人摸不著頭腦....,可否請您說明一下您的發言是針對我與 anaconda1813 之間的那一段討論而來的?      7 天天敲鍵盤 v 時時按滑鼠 8
malanlk
尊榮會員


發表:20
回覆:694
積分:577
註冊:2004-04-19

發送簡訊給我
#11 引用回覆 回覆 發表時間:2005-09-15 12:54:03 IP:203.69.xxx.xxx 未訂閱
引言: 不過我在 if (Application->Terminated) { // 設定在程式結束時跳出迴圈 ShowMessage("123"); break; } 或是在while的最外面ShowMessage("123") 結果都不會有效果,請問這是為什麼呢?不是在他結束後因該會顯示出來ShowMessage才對阿??
針對這段.... 我ㄧ直認為要解決這個問題就要 模擬 Explorer 被按下 Ctrl-C 時將檔案或目錄寫入 Clipboard 的動作. 我有找了 Anders Melander 的 Drag and Drop 元件來研究 http://codecentral.borland.com/Item.aspx?id=14069 看看能不能將 TDropSource 在拖拉開始時對 Clipboard 做的動作, 把它改成單純地模擬Ctrl-C 的動作... RedSnow 大大可以ㄧ起玩玩看...
RedSnow
版主


發表:79
回覆:1322
積分:845
註冊:2003-12-15

發送簡訊給我
#12 引用回覆 回覆 發表時間:2005-09-15 14:28:02 IP:59.115.xxx.xxx 未訂閱
malanlk 您好:    您所引用 anaconda1813 的那一段程式碼,大概是 anaconda1813 為了要做測試才會加上 ShowMessage 那個敘述的,他可能是誤會了那個迴圈的跳出時機 (FindWindow 那行敘述才是呼叫檔案總管後,要等待程式載入的判斷動作,那個 if 判斷式是在前述條件未滿足時,突然結束掉呼叫檔案總管那支程式本身時跳出迴圈之用的),所以才會將 ShowMessage 敘述放在那個 if 判斷式之內。 我已經試過將檔案總管呼叫出來並指向特定目錄,然後以 keybd_event() 送出按鍵信號的方式來模擬複製的動作了 (貼上的動作尚未透過程式來測試,但是已透過手動方式確認目錄資料確實有複製到剪貼板內了),這些動作均經測試成功並無問題,但是我並不清楚 anaconda1813 打算使用何種方式去進行他自己描述的複製動作,因此我在自己的範例中予以略過。 您不妨也試試看使用 keybd_event() 來模擬按下 Ctrl-C 的動作,看看是否能達到您預期的效果? 7 天天敲鍵盤 v 時時按滑鼠 8
malanlk
尊榮會員


發表:20
回覆:694
積分:577
註冊:2004-04-19

發送簡訊給我
#13 引用回覆 回覆 發表時間:2005-09-15 14:37:47 IP:203.69.xxx.xxx 未訂閱
unit Unit1;    interface    uses
  Windows, Messages, SysUtils, Variants, Classes, Graphics, Controls, Forms,
  Dialogs, ActiveX, Clipbrd, ShlObj, StdCtrls;    type      TForm1 = class(TForm)
    Button1: TButton;
    procedure Button1Click(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;    var
  Form1: TForm1;
  CF_FILEGROUPDESCRIPTOR, CF_FILECONTENTS, CF_FILENAMEMAP, CF_FILENAMEMAPW,
  CF_IDLIST: UINT; //, CF_PREFERREDDROPEFFECT, CF_URL: UINT; //see initialization.
  ShellMalloc: IMalloc;    implementation    {$R *.dfm}    // -----------------------------------------------------------------------------
//                        Miscellaneous functions.
// -----------------------------------------------------------------------------    function GetSizeOfPidl(pidl: pItemIDList): integer;
var
  i: integer;
begin
  result := SizeOf(Word);
  repeat
    i := pSHItemID(pidl)^.cb;
    inc(result,i);
    inc(longint(pidl),i);
  until i = 0;
end;
// -----------------------------------------------------------------------------
function GetShellFolderOfPath(FolderPath: TFileName): IShellFolder;
var
  DeskTopFolder: IShellFolder;
  PathPidl: pItemIDList;
  OlePath: array[0..MAX_PATH] of WideChar;
  dummy,pdwAttributes: ULONG;
begin
  result := nil;
  StringToWideChar( FolderPath, OlePath, MAX_PATH );
  pdwAttributes := SFGAO_FOLDER;
  try
    if not (SHGetDesktopFolder(DeskTopFolder) = NOERROR) then exit;
    if (DesktopFolder.ParseDisplayName(0,
          nil,OlePath,dummy,PathPidl,pdwAttributes) = NOERROR) and
          (pdwAttributes and SFGAO_FOLDER <> 0) then
      DesktopFolder.BindToObject(PathPidl,nil,IID_IShellFolder,pointer(result));
    ShellMalloc.Free(PathPidl);
  except
  end;
end;
// -----------------------------------------------------------------------------
function GetFullPIDLFromPath(Path: TFileName): pItemIDList;
var
   DeskTopFolder: IShellFolder;
   OlePath: array[0..MAX_PATH] of WideChar;
   dummy1,dummy2: ULONG;
begin
  result := nil;
  StringToWideChar( Path, OlePath, MAX_PATH );
  try
    if (SHGetDesktopFolder(DeskTopFolder) = NOERROR) then
      DesktopFolder.ParseDisplayName(0,nil,OlePath,dummy1,result,dummy2);
  except
  end;
end;
// -----------------------------------------------------------------------------
function GetSubPidl(Folder: IShellFolder; Sub: TFilename): pItemIDList;
var
  dummy1,dummy2: ULONG;
  OleFile: array[0..MAX_PATH] of WideChar;
begin
  result := nil;
  try
    StringToWideChar( Sub, OleFile, MAX_PATH );
    Folder.ParseDisplayName(0,nil,OleFile,dummy1,result,dummy2);
  except
  end;
end;
// -----------------------------------------------------------------------------    //See "Clipboard Formats for Shell Data Transfers" in Ole.hlp...
//(Needed to drag links (shortcuts).)    type
  POffsets = ^TOffsets;
  TOffsets = array[0..$FFFF] of UINT;    function ConvertFilesToShellIDList(path: string; files: TStrings): HGlobal;
var
  shf: IShellFolder;
  PathPidl, pidl: pItemIDList;
  Ida: PIDA;
  pOffset: POffsets;
  ptrByte: ^Byte;
  i, PathPidlSize, IdaSize, PreviousPidlSize: integer;
begin
  result := 0;
  shf := GetShellFolderOfPath(path);
  if shf = nil then exit;
  //Calculate size of IDA structure ...
  // cidl: UINT ; Directory pidl offset: UINT ; all file pidl offsets
  IdaSize := (files.count   2) * sizeof(UINT);      PathPidl := GetFullPIDLFromPath(path);
  if PathPidl = nil then exit;
  PathPidlSize := GetSizeOfPidl(PathPidl);      //Add to IdaSize space for ALL pidls...
  IdaSize := IdaSize   PathPidlSize;
  for i := 0 to files.count-1 do
  begin
    pidl := GetSubPidl(shf,files[i]);
    IdaSize := IdaSize   GetSizeOfPidl(Pidl);
    ShellMalloc.Free(pidl);
  end;      //Allocate memory...
  Result := GlobalAlloc(GMEM_SHARE or GMEM_ZEROINIT, IdaSize);
  if (Result = 0) then
  begin
    ShellMalloc.Free(PathPidl);
    Exit;
  end;      Ida := GlobalLock(Result);
  try
    FillChar(Ida^,IdaSize,0);        //Fill in offset and pidl data...
    Ida^.cidl := files.count; //cidl = file count
    pOffset := @(Ida^.aoffset);
    pOffset^[0] := (files.count 2) * sizeof(UINT); //offset of Path pidl        ptrByte := pointer(Ida);
    inc(ptrByte,pOffset^[0]); //ptrByte now points to Path pidl
    move(PathPidl^, ptrByte^, PathPidlSize); //copy path pidl
    ShellMalloc.Free(PathPidl);        PreviousPidlSize := PathPidlSize;
    for i := 1 to files.count do
    begin
      pidl := GetSubPidl(shf,files[i-1]);
      pOffset^[i] := pOffset^[i-1]   UINT(PreviousPidlSize); //offset of pidl
      PreviousPidlSize := GetSizeOfPidl(Pidl);          ptrByte := pointer(Ida);
      inc(ptrByte,pOffset^[i]); //ptrByte now points to current file pidl
      move(Pidl^, ptrByte^, PreviousPidlSize); //copy file pidl
                            //PreviousPidlSize = current pidl size here
      ShellMalloc.Free(pidl);
    end;
  finally
    GlobalUnLock(Result);
  end;
end;    function DoGetData(const FormatEtcIn: TFormatEtc;
         out Medium: TStgMedium; fFiles,fMappedNames: TStringList):HRESULT;
var
  i: Integer;
  dropfiles: pDropFiles;
  pFile: PChar;
  pFileW: PWideChar;
  DropEffect: ^DWORD;
  strlength: Integer;
  tmpFilenames: TStringList;
begin
  Medium.tymed := 0;
  Medium.UnkForRelease := NIL;
  Medium.hGlobal := 0;      if fFiles.count = 0 then result := E_UNEXPECTED
  //--------------------------------------------------------------------------
  else if (FormatEtcIn.cfFormat = CF_HDROP) and
    (FormatEtcIn.dwAspect = DVASPECT_CONTENT) and
    (FormatEtcIn.tymed and TYMED_HGLOBAL <> 0) then
  begin
    strlength := 0;
    for i := 0 to fFiles.Count-1 do
      Inc(strlength, Length(fFiles[i]) 1);
    Medium.hGlobal :=
      GlobalAlloc(GMEM_SHARE or GMEM_ZEROINIT, SizeOf(TDropFiles) strlength 1);
    if (Medium.hGlobal = 0) then
      result:=E_OUTOFMEMORY
    else
    begin
      Medium.tymed := TYMED_HGLOBAL;
      dropfiles := GlobalLock(Medium.hGlobal);
      try
        dropfiles^.pfiles := SizeOf(TDropFiles);
        dropfiles^.fwide := False;
        longint(pFile) := longint(dropfiles) SizeOf(TDropFiles);
        for i := 0 to fFiles.Count-1 do
        begin
          StrPCopy(pFile,fFiles[i]);
          Inc(pFile, Length(fFiles[i]) 1);
        end;
        pFile^ := #0;
      finally
        GlobalUnlock(Medium.hGlobal);
      end;
      result := S_OK;
    end;
  end
  //--------------------------------------------------------------------------
  else if (FormatEtcIn.cfFormat = CF_FILENAMEMAP) and
    (FormatEtcIn.dwAspect = DVASPECT_CONTENT) and
    (FormatEtcIn.tymed and TYMED_HGLOBAL <> 0) and
    //make sure there is a Mapped Name for each filename...
    (fMappedNames.Count = fFiles.Count) then
  begin
    strlength := 0;
    for i := 0 to fMappedNames.Count-1 do
      Inc(strlength, Length(fMappedNames[i]) 1);        Medium.hGlobal :=
      GlobalAlloc(GMEM_SHARE or GMEM_ZEROINIT, strlength 1);
    if (Medium.hGlobal = 0) then
      result:=E_OUTOFMEMORY
    else
    begin
      Medium.tymed := TYMED_HGLOBAL;
      pFile := GlobalLock(Medium.hGlobal);
      try
        for i := 0 to fMappedNames.Count-1 do
        begin
          StrPCopy(pFile,fMappedNames[i]);
          Inc(pFile, Length(fMappedNames[i]) 1);
        end;
        pFile^ := #0;
      finally
        GlobalUnlock(Medium.hGlobal);
      end;
      result := S_OK;
    end;
  end
  //--------------------------------------------------------------------------
  else if (FormatEtcIn.cfFormat = CF_FILENAMEMAPW) and
    (FormatEtcIn.dwAspect = DVASPECT_CONTENT) and
    (FormatEtcIn.tymed and TYMED_HGLOBAL <> 0) and
    //make sure there is a Mapped Name for each filename...
    (fMappedNames.Count = fFiles.Count) then
  begin
    strlength := 2;
    for i := 0 to fMappedNames.Count-1 do
      Inc(strlength, (Length(fMappedNames[i]) 1)*2);        Medium.hGlobal := GlobalAlloc(GMEM_SHARE or GMEM_ZEROINIT, strlength);
    if (Medium.hGlobal = 0) then
      result:=E_OUTOFMEMORY
    else
    begin
      Medium.tymed := TYMED_HGLOBAL;
      pFileW := GlobalLock(Medium.hGlobal);
      try
        for i := 0 to fMappedNames.Count-1 do
        begin
          StringToWideChar(fMappedNames[i], pFileW,
            (length(fMappedNames[i]) 1)*2);
          Inc(pFileW, Length(fMappedNames[i]) 1);
        end;
        pFileW^ := #0;
      finally
        GlobalUnlock(Medium.hGlobal);
      end;
      result := S_OK;
    end;
  end
  //--------------------------------------------------------------------------
  else if (FormatEtcIn.cfFormat = CF_IDLIST) and
    (FormatEtcIn.dwAspect = DVASPECT_CONTENT) and
    (FormatEtcIn.tymed and TYMED_HGLOBAL <> 0) then
  begin
    tmpFilenames := TStringList.create;
    try
      Medium.tymed := TYMED_HGLOBAL;
      for i := 0 to fFiles.count-1 do
        tmpFilenames.add(extractfilename(fFiles[i]));
      Medium.hGlobal :=
          ConvertFilesToShellIDList(extractfilepath(fFiles[0]),tmpFilenames);
      if Medium.hGlobal = 0 then
        result:=E_outOFMEMORY else
        result := S_OK;
    finally
      tmpFilenames.free;
    end;
  end
  //--------------------------------------------------------------------------      ////This next format does not work for Win95 but should for Win98, WinNT ...
  ////It stops the shell from prompting (with a popup menu) for the choice of
  ////Copy/Move/Shortcut when performing a file 'Shortcut' onto Desktop or Explorer.
  //else if (FormatEtcIn.cfFormat = CF_PREFERREDDROPEFFECT) and
  //  (FormatEtcIn.dwAspect = DVASPECT_CONTENT) and
  //  (FormatEtcIn.tymed and TYMED_HGLOBAL <> 0) then
  //begin
  //  Medium.tymed := TYMED_HGLOBAL;
  //  Medium.hGlobal := GlobalAlloc(GMEM_SHARE or GMEM_ZEROINIT, SizeOf(DWORD));
  //  if Medium.hGlobal = 0 then
  //    result:=E_outOFMEMORY
  //  else
  //  begin
  //    DropEffect := GlobalLock(Medium.hGlobal);
  //    try
  //      DropEffect^ := DWORD(FeedbackEffect);
  //    finally
  //      GlobalUnLock(Medium.hGlobal);
  //    end;
  //    result := S_OK;
  //  end;
  //end
  else
    result := DV_E_FORMATETC;
end;    function CutOrCopyToClipboard_Files: boolean;
var
  FormatEtcIn: TFormatEtc;
  Medium: TStgMedium;
  fFiles,fMappedNames: TStringList;
begin
  fFiles := TStringList.Create;
  fMappedNames := TStringList.Create;      try
    fFiles.Add('C:\icons');
    FormatEtcIn.cfFormat := CF_HDROP;
    FormatEtcIn.dwAspect := DVASPECT_CONTENT;
    FormatEtcIn.tymed := TYMED_HGLOBAL;
    if (fFiles.count = 0) then result := false
    else if DoGetData(formatetcIn,Medium,fFiles,fMappedNames) = S_OK then
    begin
      Clipboard.SetAsHandle(CF_HDROP,Medium.hGlobal);
      result := true;
    end else result := false;
  finally
    fFiles.Free;
    fMappedNames.Free;
  end;
end;    function CutOrCopyToClipboard_Link: boolean;
var
  FormatEtcIn: TFormatEtc;
  Medium: TStgMedium;
  fFiles,fMappedNames: TStringList;
begin
  fFiles := TStringList.Create;
  fMappedNames := TStringList.Create;      try
    fFiles.Add('C:\icons');
    FormatEtcIn.cfFormat := CF_IDLIST;
    FormatEtcIn.dwAspect := DVASPECT_CONTENT;
    FormatEtcIn.tymed := TYMED_HGLOBAL;
    if (fFiles.count = 0) then result := false
    else if DoGetData(formatetcIn,Medium,fFiles,fMappedNames) = S_OK then
    begin
      Clipboard.SetAsHandle(CF_IDLIST,Medium.hGlobal);
      result := true;
    end else result := false;
  finally
    fFiles.Free;
    fMappedNames.Free;
  end;
end;    procedure TForm1.Button1Click(Sender: TObject);
begin
  CutOrCopyToClipboard_Files;
  //CutOrCopyToClipboard_Link;
end;    initialization
  OleInitialize(NIL);      CF_FILECONTENTS := RegisterClipboardFormat(CFSTR_FILECONTENTS);
  CF_FILEGROUPDESCRIPTOR := RegisterClipboardFormat(CFSTR_FILEDESCRIPTOR);
  CF_IDLIST := RegisterClipboardFormat(CFSTR_SHELLIDLIST);
  //CF_PREFERREDDROPEFFECT := RegisterClipboardFormat('Preferred DropEffect');
  //CF_URL := RegisterClipboardFormat('UniformResourceLocator');
  CF_FILENAMEMAP := RegisterClipboardFormat(CFSTR_FILENAMEMAPA);
  CF_FILENAMEMAPW := RegisterClipboardFormat(CFSTR_FILENAMEMAPW);      ShGetMalloc(ShellMalloc);
finalization
  OleUninitialize;
end.
本範例只是依問題需求將 CF_HDROP, CF_IDLIST 做出來, 有興趣的人可以再進ㄧ步研究 Anders Melander 的 Drag and Drop 元件 這個範例在 Button1 按下之後 會將 'C:\icons' 這個目錄放到 Clipboard 內, 之後可以在檔案總管選一個目錄 將其 "貼上"
anaconda1813
一般會員


發表:29
回覆:29
積分:11
註冊:2004-10-12

發送簡訊給我
#14 引用回覆 回覆 發表時間:2005-09-15 23:12:06 IP:140.123.xxx.xxx 未訂閱
引言: anaconda1813 您好:
引言:不過我在 if (Application->Terminated) { // 設定在程式結束時跳出迴圈 ShowMessage("123"); break; } 或是在while的最外面ShowMessage("123") 結果都不會有效果,請問這是為什麼呢?不是在他結束後因該會顯示出來ShowMessage才對阿??
請您看仔細一點,我在那ㄧ行後邊加上註解寫的是 "設定在程式結束時跳出迴圈",判斷式寫的也是 if (Application->Terminated) {,亦即該判斷式是在程式本身結束掉時跳出迴圈使用的 (因應程式還在執行該迴圈,卻突然被結束掉使用的),如果您對該判斷式有疑問的話,請將那三行刪除掉好了,影響不大的。 關於第二個問題,會不會是 ShowMessage() 其實是有秀出來,只是被呼叫出來的檔案總管遮住了?我貼上來的程式碼在我的環境中 (Windows 2000 BCB4) 是能正確執行的,如果在您的環境中有問題的話,請檢查一下您設定的 target 名稱與呼叫出來後的檔案總管 Caption 是否相同?如果找不出問題的話,請將您現在實際測試的程式碼貼上來,比便於討論。 7 天天敲鍵盤 v 時時按滑鼠 8 發表人 - RedSnow 於 2005/09/14 23:48:35
AnsiString sysdir = getenv("SystemRoot");  // 取得系統目錄名稱
AnsiString prog = sysdir "\\explorer.exe";  // 指定執行對象為檔案總管
AnsiString target = "C:\\Downloads";  // 設定要指向的目錄名稱
AnsiString param = "/e, \"" target "\"";  // 設定啟動參數與欲指向的目錄
ShellExecute(NULL, "Open", prog.c_str(), param.c_str(), NULL, SW_SHOWNORMAL);
while (FindWindow(NULL, target.c_str()) == NULL) {  // 直到檔案總管啟動完畢為止
    Application->ProcessMessages();  // 避免迴圈咬住程式而影響其它動作
    if (Application->Terminated) {  // 設定在程式結束時跳出迴圈
        break;
    }
}     keybd_event(VK_CONTROL, 0, 0, 0); // 按下 Ctrl
    keybd_event(67, 0, 0, 0); // 按下 C
    keybd_event(67, 0, KEYEVENTF_KEYUP, 0); // 放開 C
    keybd_event(VK_CONTROL, 0, KEYEVENTF_KEYUP, 0); // 放開 Ctrl
....
像這樣,這樣不是代表已經檔案總管已經結束才執行ctrl c的動作嗎?? 結果就是沒有效果一般~ 還是我又誤會了呢??
RedSnow
版主


發表:79
回覆:1322
積分:845
註冊:2003-12-15

發送簡訊給我
#15 引用回覆 回覆 發表時間:2005-09-16 00:13:53 IP:61.230.xxx.xxx 未訂閱
anaconda1813 您好:    我在三測試後,仍然是可以正確複製目錄資料,我不知道您為何會有無法正確執行的現象?請您檢查下列事項: 1. 請在執行該動作之前,確認沒有任何已啟動的檔案總管有開啟相同目錄 (C:\Downloads),否則 FindWindow() 傳回的訊息會無法正確的配合程式動作。 2. 該動作執行完畢後,請在檔案總管另選擇一個適當的目錄,然後案滑鼠右鍵,接著點選 "貼上",看看是否能將 C:\Downloads 目錄內的檔案複製過去? 3. 請先不要使用除錯模式進行測試,否則 Focus 可能會不正確,而無法讓模擬按鍵的動作達到預期效果。 7 天天敲鍵盤 v 時時按滑鼠 8 發表人 - RedSnow 於 2005/09/16 00:22:07
anaconda1813
一般會員


發表:29
回覆:29
積分:11
註冊:2004-10-12

發送簡訊給我
#16 引用回覆 回覆 發表時間:2005-09-16 13:39:48 IP:140.123.xxx.xxx 未訂閱
引言: anaconda1813 您好: 我在三測試後,仍然是可以正確複製目錄資料,我不知道您為何會有無法正確執行的現象?請您檢查下列事項: 1. 請在執行該動作之前,確認沒有任何已啟動的檔案總管有開啟相同目錄 (C:\Downloads),否則 FindWindow() 傳回的訊息會無法正確的配合程式動作。 2. 該動作執行完畢後,請在檔案總管另選擇一個適當的目錄,然後案滑鼠右鍵,接著點選 "貼上",看看是否能將 C:\Downloads 目錄內的檔案複製過去? 3. 請先不要使用除錯模式進行測試,否則 Focus 可能會不正確,而無法讓模擬按鍵的動作達到預期效果。 7 天天敲鍵盤 v 時時按滑鼠 8 發表人 - RedSnow 於 2005/09/16 00:22:07
謝謝您熱心的回答~,不過我不曉得為什麼會不行 我在別的地方滑鼠右鍵複製的那個選項是不可點選的~ 也很好奇是不是只有在我的電腦上會這樣 已經檔案上傳到求助區~麻煩請您看一下,
RedSnow
版主


發表:79
回覆:1322
積分:845
註冊:2003-12-15

發送簡訊給我
#17 引用回覆 回覆 發表時間:2005-09-16 22:15:26 IP:59.115.xxx.xxx 未訂閱
anaconda1813 您好:    我直接在我的電腦上執行您已經編譯好的 exe 程式,結果是 OK 的,我可以在點選按鈕後呼叫出檔案總管,同時在檔案總管顯示出來之後,在檔案總管按下滑鼠右鍵叫出的關聯式選單選擇 "貼上" 項目,並且執行複製 C:\downloads 目錄的動作。    如果您已經確實按照我在前一篇回覆所提示的狀態下執行,而結果仍無法複製的話,那麼我已經沒輒了~      7 天天敲鍵盤 v 時時按滑鼠 8
anaconda1813
一般會員


發表:29
回覆:29
積分:11
註冊:2004-10-12

發送簡訊給我
#18 引用回覆 回覆 發表時間:2005-09-16 23:39:06 IP:140.123.xxx.xxx 未訂閱
引言: anaconda1813 您好: 我直接在我的電腦上執行您已經編譯好的 exe 程式,結果是 OK 的,我可以在點選按鈕後呼叫出檔案總管,同時在檔案總管顯示出來之後,在檔案總管按下滑鼠右鍵叫出的關聯式選單選擇 "貼上" 項目,並且執行複製 C:\downloads 目錄的動作。 如果您已經確實按照我在前一篇回覆所提示的狀態下執行,而結果仍無法複製的話,那麼我已經沒輒了~ 7 天天敲鍵盤 v 時時按滑鼠 8
看樣子真的是電腦的問題= = thx~
系統時間:2024-06-24 21:02:57
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!