全國最多中醫師線上諮詢網站-台灣中醫網
發文 回覆 瀏覽次數:4346
推到 Plurk!
推到 Facebook!

如何获取自己在程序中运行的外部EXE的Handle?

缺席
bundur
一般會員


發表:16
回覆:44
積分:22
註冊:2002-11-30

發送簡訊給我
#1 引用回覆 回覆 發表時間:2003-08-01 10:12:06 IP:218.104.xxx.xxx 未訂閱
请问用什么方法可以运行一个外部的EXE并返回它的Handle? WinExec 返回不是该EXE的Handle ShellExecute, ShellExecuteEx 也不是 CreateProcess 返回的是 Process Handle 到底要如何才可以返回和 GetWindow 所返回的一样的 Handle? ==================== 交流是进步的良师 批评是成长的益友
sos_admin
版主


發表:121
回覆:697
積分:768
註冊:2003-07-23

發送簡訊給我
#2 引用回覆 回覆 發表時間:2003-08-01 11:31:52 IP:61.155.xxx.xxx 未訂閱
可以用FindWindow()函数,它能够解决这个问题,它有两个参数:lpClassName:程序的类名;lpWindowName:程序窗体的标题。 例如: procedure TForm1.Button1Click(Sender: TObject); begin ShellExecute(handle,'open','notepad.exe',nil,nil,SW_ShowNormal); end; procedure TForm1.Button2Click(Sender: TObject); var ExeHandle:Thandle; Begin //获得句柄 ExeHandle:=FindWindow('notepad',nil);//'');//返回句柄 //关闭程序 if ExeHandle<>0 then SendMessage(ExeHandle,WM_Close,0,0) Else Application.MessageBox('没有打开"记事本"程序!','提示', MB_IconInformation MB_OK); end;
bundur
一般會員


發表:16
回覆:44
積分:22
註冊:2002-11-30

發送簡訊給我
#3 引用回覆 回覆 發表時間:2003-08-01 11:51:22 IP:218.104.xxx.xxx 未訂閱
谢谢sos_admin, FindWindow() 方法不是我想要的,因为这里的lpWindowName 具有不确定性,没有办法准确地找到。 我希望能在执行这支外部程序里就可以得到它的 Handle. 比如有没有办法,通过Process Handle得到它有 Application Handle 以及 MainForm Handle ==================== 交流是进步的良师 批评是成长的益友
sos_admin
版主


發表:121
回覆:697
積分:768
註冊:2003-07-23

發送簡訊給我
#4 引用回覆 回覆 發表時間:2003-08-01 12:02:22 IP:61.155.xxx.xxx 未訂閱
您可以通过lpClassName:程序的类名来准确地找到。 ExeHandle:=FindWindow('notepad',nil);//返回句柄
bundur
一般會員


發表:16
回覆:44
積分:22
註冊:2002-11-30

發送簡訊給我
#5 引用回覆 回覆 發表時間:2003-08-01 12:45:56 IP:218.104.xxx.xxx 未訂閱
引言: 您可以通过lpClassName:程序的类名来准确地找到。 ExeHandle:=FindWindow('notepad',nil);//返回句柄
这个外部程序是不确定的,也不一定是自己写的,所以无法确定类名. ==================== 交流是进步的良师 批评是成长的益友
sos_admin
版主


發表:121
回覆:697
積分:768
註冊:2003-07-23

發送簡訊給我
#6 引用回覆 回覆 發表時間:2003-08-01 13:35:11 IP:61.155.xxx.xxx 未訂閱
function ExecuteFile(const FileName, Params, DefaultDir: String; ShowCmd: Integer): THandle; var zFileName, zParams, zDir: array[0..79] of Char; begin Result := ShellExecute(Application.MainForm.Handle, nil, StrPCopy(zFileName, FileName), StrPCopy(zParams, Params), StrPCopy(zDir, DefaultDir), ShowCmd); end; procedure TForm1.Button3Click(Sender: TObject); var hwd:thandle; begin hwd:=ExecuteFile('notepad.exe','','',SW_ShowNormal); if hwd<>0 then showmessage('哈哈~~' #13 '我取到handle了,是>>>' inttostr(hwd)); end;
bundur
一般會員


發表:16
回覆:44
積分:22
註冊:2002-11-30

發送簡訊給我
#7 引用回覆 回覆 發表時間:2003-08-01 14:42:34 IP:218.104.xxx.xxx 未訂閱
谢谢您的热心帮助, 但ShellExecute得到的并不是Handle 用FindWindow得到的才是真正的Handle 你可以试一下. 最简单的方法就是向你得到的Handle发一个WM_QUIT消息,看它是否会被关闭. 如: SendMessage(AHandle, WM_QUIT, 0, 0); ==================== 交流是进步的良师 批评是成长的益友
sos_admin
版主


發表:121
回覆:697
積分:768
註冊:2003-07-23

發送簡訊給我
#8 引用回覆 回覆 發表時間:2003-08-01 21:12:46 IP:218.2.xxx.xxx 未訂閱
我看了很多delphi的资料,好像只有FindWindow()函数是 可以实现的,至于是否还有其它的方法,我 不太清楚!
bundur
一般會員


發表:16
回覆:44
積分:22
註冊:2002-11-30

發送簡訊給我
#9 引用回覆 回覆 發表時間:2003-08-05 09:11:50 IP:218.104.xxx.xxx 未訂閱
引言: 我看了很多delphi的资料,好像只有FindWindow()函数是 可以实现的,至于是否还有其它的方法,我 不太清楚! < face="Verdana, Arial, Helvetica"> 我已从大富翁论坛上得到了满意的结论了,在这和大家分享一下: (大富翁论坛: http://www.delphibbs.com/) type PEnumInfo = ^TEnumInfo; TEnumInfo = record ProcessID : DWORD; HWND : THandle; end; function EnumWindowsProc(Wnd: DWORD; var EI: TEnumInfo): Bool; stdcall; var PID : DWORD; begin GetWindowThreadProcessID(Wnd, @PID); Result := (PID <> EI.ProcessID) or (not IsWindowVisible(WND)) or (not IsWindowEnabled(WND)); if not result then EI.HWND := WND; end; function FindMainWindow(PID: DWORD): DWORD; var EI : TEnumInfo; begin EI.ProcessID := PID; EI.HWND := 0; EnumWindows(@EnumWindowsProc, Integer(@EI)); Result := EI.HWND; end; procedure TForm1.Button1Click(Sender: TObject); var SI : TStartupInfo; PI : TProcessInformation; H : THandle; S : String; begin ZeroMemory(@SI, SizeOf(SI)); ZeroMemory(@PI, SizeOf(PI)); SI.cb := SizeOf(SI); if CreateProcess(nil,'CALC.EXE', nil, nil, FALSE, 0 ,nil,nil, SI, PI) then begin //注意! WaitForInputIdle(PI.hProcess, INFINITE); H := FindMainWindow(PI.dwProcessID); if H > 0 then begin SetLength(S, 255); GetWindowText(H, PChar(S), 255); SetLength(S, StrLen(PChar(S))); ShowMessage(S); end; CloseHandle(PI.hProcess); CloseHandle(PI.hThread); end; end; end. ==================== 交流是进步的良师 批评是成长的益友
bruce0211
版主


發表:157
回覆:668
積分:279
註冊:2002-06-13

發送簡訊給我
#10 引用回覆 回覆 發表時間:2003-10-13 15:12:17 IP:211.21.xxx.xxx 未訂閱
長官 上面的程式碼好像不能用 問題出在 EnumWindows(@EnumWindowsProc, Integer(@EI));
pceyes
尊榮會員


發表:70
回覆:657
積分:1140
註冊:2003-03-13

發送簡訊給我
#11 引用回覆 回覆 發表時間:2008-07-14 21:48:19 IP:220.141.xxx.xxx 訂閱
除了沒排整齊,試過是可用的。
環境:win2000 delphi 7
例子在這裏
http://delphi.ktop.com.tw/board.php?cid=30&fid=1498&tid=94449
Delphi 新手問題 / 作業研討 » FindWindow的問題
------
努力會更接近成功
編輯記錄
pceyes 重新編輯於 2008-07-14 21:49:22, 註解 無‧
pceyes 重新編輯於 2008-07-14 22:01:35, 註解 無‧
系統時間:2024-03-29 16:36:19
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!