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

在已執行程式中開啟的方法?

答題得分者是:carstyc
cjqupru
一般會員


發表:5
回覆:11
積分:3
註冊:2007-06-14

發送簡訊給我
#1 引用回覆 回覆 發表時間:2009-06-30 20:36:57 IP:118.161.xxx.xxx 訂閱
我要作一個類似 Ultraedit 的 Text Reader,
首先我已經做好分頁開啟的功能,我把他包在一個Function : void OpenFile(AnsiString Path)
也在網路上找到了禁止程式重複開啟的方法。
而透過檔案關聯開啟的功能也有了(就是在要開的檔案上點兩下的方式)。
但是,問題來了。

因為禁止程式重複開啟的關係,
雖然第一次開啟沒有問題,但第二次開啟時,因為程式已經在執行,
所以會把第二次開啟的程式關閉,這樣造成第二次要開啟的檔案無法開啟。

後來在網路上找到一個在不同程式間傳遞訊息的方法 ... wm_copydata
第二次開啟檔案的路徑也傳給了已經開啟的程式,並且傳入了void OpenFile(AnsiString Path)
(而且確實有進去Function內,我用ShowMessage確認的。)
但是卻沒有反應。

請問各位先進,我進行的方向是對的嗎?
亦或者是另有他法呢?

最後簡單描述一下我要的功能:
在要執行的文件上點兩下左鍵,若程式未開啟,則執行程式並且在Memo中打開文件。
若是程式已經在執行,則以分頁方式在已執行程式中開啟。
carstyc
資深會員


發表:16
回覆:254
積分:329
註冊:2003-07-18

發送簡訊給我
#2 引用回覆 回覆 發表時間:2009-06-30 23:05:37 IP:219.84.xxx.xxx 訂閱
cjqupru 大大您描述的很清楚了,可是我的問題是,即然重覆開啟時,你原來開啟的程式已經能接收到訊息了,您自己都用Showmessage確認過有收到訊息了。那接下來也是你自己開發的程式,為啥沒反應,不是應該很容易就能Debug出來。

還是你要把code 貼出來大家來幫忙看看。

不然Showmessage能顯示出來,但程式沒反應,這個問題還蠻難回覆的。




===================引 用 cjqupru 文 章===================
我要作一個類似 Ultraedit 的 Text Reader,
首先我已經做好分頁開啟的功能,我把他包在一個Function : void OpenFile(AnsiString Path)
也在網路上找到了禁止程式重複開啟的方法。
而透過檔案關聯開啟的功能也有了(就是在要開的檔案上點兩下的方式)。
但是,問題來了。

因為禁止程式重複開啟的關係,
雖然第一次開啟沒有問題,但第二次開啟時,因為程式已經在執行,
所以會把第二次開啟的程式關閉,這樣造成第二次要開啟的檔案無法開啟。

後來在網路上找到一個在不同程式間傳遞訊息的方法 ... wm_copydata
第二次開啟檔案的路徑也傳給了已經開啟的程式,並且傳入了void OpenFile(AnsiString Path)
(而且確實有進去Function內,我用ShowMessage確認的。)
但是卻沒有反應。

請問各位先進,我進行的方向是對的嗎?
亦或者是另有他法呢?

最後簡單描述一下我要的功能:
在要執行的文件上點兩下左鍵,若程式未開啟,則執行程式並且在Memo中打開文件。
若是程式已經在執行,則以分頁方式在已執行程式中開啟。
cjqupru
一般會員


發表:5
回覆:11
積分:3
註冊:2007-06-14

發送簡訊給我
#3 引用回覆 回覆 發表時間:2009-07-01 21:07:38 IP:118.161.xxx.xxx 訂閱
感謝carstyc 大大的回應,我的問題已經找到了,
因為我懷疑接收到訊息的程式是否正確,
所以今天我在程式中加上了可以把Handle Show出來的功能,
發現接收到的程式根本就是錯誤的。原來在搜尋已執行程式時所找到的Handle是發送端自己的= =a

後來有想到解決的辦法,就是把第一次開啟的程式名稱改過,
然後第二次開時,搜尋改過的名稱就不會找到自己了。
只是這樣子不夠Smart,不知道大大有沒有更好的辦法。

P.S.
因為程式放在公司(趁休息時間寫的XD),所以無法po出來(因為記不得了Orz)。
明天到公司有空在把問題寫詳細一點~
編輯記錄
cjqupru 重新編輯於 2009-07-01 21:08:13, 註解 無‧
carstyc
資深會員


發表:16
回覆:254
積分:329
註冊:2003-07-18

發送簡訊給我
#4 引用回覆 回覆 發表時間:2009-07-01 22:11:08 IP:219.84.xxx.xxx 訂閱
這個誤會應該大了吧。

你檢查的機制是放在那裡檢查的啊....為啥還能在FindWindow 的時候找到自己本身的Handle。那不就表示你的Main Form已經執行起來了。

你應該是在 Main Form 還沒被Create出來前去做檢查及 SendMessage吧。

這樣的話就不太可能找到自己的 Handle 才對吧。


begin
if GotoPreviousInstance32(Extractfilename(Application.ExeName)) then
begin
Application.MessageBox('本程式已經啟動過!', '系統重覆執行', MB_ICONSTOP);

FindWindow & SendMessage process

Application.Terminate;
end;

Application.Initialize;
Application.CreateForm(TFormMain, FormMain);

Application.Run;
end.




===================引 用 cjqupru 文 章===================
感謝carstyc 大大的回應,我的問題已經找到了,
因為我懷疑接收到訊息的程式是否正確,
所以今天我在程式中加上了可以把Handle Show出來的功能,
發現接收到的程式根本就是錯誤的。原來在搜尋已執行程式時所找到的Handle是發送端自己的= =a

後來有想到解決的辦法,就是把第一次開啟的程式名稱改過,
然後第二次開時,搜尋改過的名稱就不會找到自己了。
只是這樣子不夠Smart,不知道大大有沒有更好的辦法。

P.S.
因為程式放在公司(趁休息時間寫的XD),所以無法po出來(因為記不得了Orz)。
明天到公司有空在把問題寫詳細一點~
cjqupru
一般會員


發表:5
回覆:11
積分:3
註冊:2007-06-14

發送簡訊給我
#5 引用回覆 回覆 發表時間:2009-07-02 07:51:26 IP:118.161.xxx.xxx 訂閱
er...我是參考那個"BCB心得分享"的例子,
放在FormCreate 的Event 裡面...

請問您貼的那一段Code,是放在BCB哪裡?

===================引 用 carstyc 文 章===================
這個誤會應該大了吧。

你檢查的機制是放在那裡檢查的啊....為啥還能在FindWindow 的時候找到自己本身的Handle。那不就表示你的Main Form已經執行起來了。

你應該是在 Main Form 還沒被Create出來前去做檢查及 SendMessage吧。

這樣的話就不太可能找到自己的 Handle 才對吧。


begin
if GotoPreviousInstance32(Extractfilename(Application.ExeName)) then
begin
Application.MessageBox('本程式已經啟動過!', '系統重覆執行', MB_ICONSTOP);

FindWindow & SendMessage process

Application.Terminate;
end;

Application.Initialize;
Application.CreateForm(TFormMain, FormMain);

Application.Run;
end.
carstyc
資深會員


發表:16
回覆:254
積分:329
註冊:2003-07-18

發送簡訊給我
#6 引用回覆 回覆 發表時間:2009-07-02 09:02:00 IP:203.79.xxx.xxx 訂閱
 
我這是 Delphi 的語法

BCB 的應該在上方的主選單中 Priject -> View Source

WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int)
{
try
{
Application->Initialize();
Application->CreateForm(__classid(TForm1), &Form1);
Application->Run();
}
catch (Exception &exception)
{
Application->ShowException(&exception);
}
return 0;
}


===================引 用 cjqupru 文 章===================
er...我是參考那個"BCB心得分享"的例子,
放在FormCreate 的Event 裡面...

請問您貼的那一段Code,是放在BCB哪裡?

===================引 用 carstyc 文 章===================
這個誤會應該大了吧。

你檢查的機制是放在那裡檢查的啊....為啥還能在FindWindow 的時候找到自己本身的Handle。那不就表示你的Main Form已經執行起來了。

你應該是在 Main Form 還沒被Create出來前去做檢查及 SendMessage吧。

這樣的話就不太可能找到自己的 Handle 才對吧。


begin
if GotoPreviousInstance32(Extractfilename(Application.ExeName)) then
begin
Application.MessageBox('本程式已經啟動過!', '系統重覆執行', MB_ICONSTOP);

FindWindow & SendMessage process

Application.Terminate;
end;

Application.Initialize;
Application.CreateForm(TFormMain, FormMain);

Application.Run;
end.

carstyc
資深會員


發表:16
回覆:254
積分:329
註冊:2003-07-18

發送簡訊給我
#7 引用回覆 回覆 發表時間:2009-07-02 09:02:43 IP:203.79.xxx.xxx 訂閱
編輯記錄
carstyc 重新編輯於 2009-07-02 09:04:29, 註解 無‧
cjqupru
一般會員


發表:5
回覆:11
積分:3
註冊:2007-06-14

發送簡訊給我
#8 引用回覆 回覆 發表時間:2009-07-02 18:40:31 IP:219.87.xxx.xxx 訂閱
請教一下大大,
我在 Application->Initlalize() 前加上判斷,
但是我都找不到已開啟的Handle,
請大大幫我看一下是不是我寫錯了?


[code cpp]
HWND Handle = FindWindow("TApplication", Application->Title.c_str());
if (
Handle != 0){
//SendMessage
return 0;
}

[/code]


===================引 用 carstyc 文 章===================

我這是 Delphi 的語法

BCB 的應該在上方的主選單中 Priject -> View Source

WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int)
{
try
{
Application->Initialize();
Application->CreateForm(__classid(TForm1), &Form1);
Application->Run();
}
catch (Exception &exception)
{
Application->ShowException(&exception);
}
return 0;
}
carstyc
資深會員


發表:16
回覆:254
積分:329
註冊:2003-07-18

發送簡訊給我
#9 引用回覆 回覆 發表時間:2009-07-02 22:08:36 IP:219.84.xxx.xxx 訂閱
兩個問題點
1. 這個問題點可能不是問題,但一般我用 FindWindow ,第一個參數都是用 nil ,不特別指定是那種 Class Name。

2. 這個問題才是大問題,你的 Application 還沒Create Main Form,你用Application->Title.c_str() 去找,找不到應該很正常吧。
你試試看用直接的字串去找看看吧(記得字串要一字不差)




===================引 用 cjqupru 文 章===================
請教一下大大,
我在 Application->Initlalize() 前加上判斷,
但是我都找不到已開啟的Handle,
請大大幫我看一下是不是我寫錯了?


[code cpp]
HWND Handle = FindWindow("TApplication", Application->Title.c_str());
if (
Handle != 0){
//SendMessage
return 0;
}

[/code]


===================引 用 carstyc 文 章===================

我這是 Delphi 的語法

BCB 的應該在上方的主選單中 Priject -> View Source

WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int)
{
try
{
Application->Initialize();
Application->CreateForm(__classid(TForm1), &Form1);
Application->Run();
}
catch (Exception &exception)
{
Application->ShowException(&exception);
}
return 0;
}
cjqupru
一般會員


發表:5
回覆:11
積分:3
註冊:2007-06-14

發送簡訊給我
#10 引用回覆 回覆 發表時間:2009-07-03 18:45:32 IP:219.87.xxx.xxx 訂閱
OK了,不過現在有個缺點,因為我的 BEGIN_MESSAGE_MAP 是放在class TForm1 : public TForm,
因此我必須將Message傳給TForm的Handle。而TForm的Caption我打算開文字檔時,
學Ultraedit把文件的路徑Display 在上面。但是這樣一來我就沒辦法事先寫好TForm的名字。
只好放棄這個功能了。

感謝 carstyc 大大的幫忙。

===================引 用 carstyc 文 章===================
兩個問題點
1. 這個問題點可能不是問題,但一般我用 FindWindow ,第一個參數都是用 nil ,不特別指定是那種 Class Name。

2. 這個問題才是大問題,你的 Application 還沒Create Main Form,你用Application->Title.c_str() 去找,找不到應該很正常吧。
你試試看用直接的字串去找看看吧(記得字串要一字不差)
系統時間:2024-11-23 5:36:35
聯絡我們 | Delphi K.Top討論版
本站聲明
1. 本論壇為無營利行為之開放平台,所有文章都是由網友自行張貼,如牽涉到法律糾紛一切與本站無關。
2. 假如網友發表之內容涉及侵權,而損及您的利益,請立即通知版主刪除。
3. 請勿批評中華民國元首及政府或批評各政黨,是藍是綠本站無權干涉,但這裡不是政治性論壇!