禁止程序重复运行并将已运行程序窗体弹出的问题。(老妖快来,你给的代码有问题哦)
以下是老妖给的代码:
//---------------------------------------------------------------------------
#include <vcl.h>
#pragma hdrstop
//---------------------------------------------------------------------------
USEFORM("Unit1.cpp", Form1);
//---------------------------------------------------------------------------
WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int)
{
// 创建互斥
HANDLE hMutex = ::CreateMutex(NULL, TRUE, "MyProjectRunFlag");
if(GetLastError() == ERROR_ALREADY_EXISTS)
{
// 如果实例已经运行
HWND hWin = FindWindow("TForm1", "Form1");
if(hWin)
{
if(!IsWindowVisible(hWin))
{
// 如果最小化状态就将窗体恢复
PostMessage(hWin, WM_SYSCOMMAND, SC_RESTORE, 0);
}
// 窗体置前
SetForegroundWindow(hWin);
BringWindowToTop(hWin);
}
if(hMutex)
CloseHandle(hMutex);
return 0;
}
//
try
{
Application->Initialize();
Application->CreateForm(__classid(TForm1), &Form1);
Application->Run();
}
catch (Exception &exception)
{
Application->ShowException(&exception);
}
catch (...)
{
try
{
throw Exception("");
}
catch (Exception &exception)
{
Application->ShowException(&exception);
}
}
return 0;
}
//---------------------------------------------------------------------------
问题出来了,如果有另一个程序的窗体也叫Form1的话,就很可能把别的程序的窗体起动起来哦,有没有更好的办法呢?(要方便哦不要太麻烦哦,呵呵)
//---------------------------------------------------------------------------
#include <vcl.h>
#pragma hdrstop
//---------------------------------------------------------------------------
USEFORM("Unit1.cpp", Form1);
//---------------------------------------------------------------------------
WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int)
{
// 创建互斥
HANDLE hMutex = ::CreateMutex(NULL, TRUE, "MyProjectRunFlag");
if(GetLastError() == ERROR_ALREADY_EXISTS)
{
// 如果实例已经运行
HWND hWin = FindWindow("TForm1", "Form1");
if(hWin)
{
if(!IsWindowVisible(hWin))
{
// 如果最小化状态就将窗体恢复
PostMessage(hWin, WM_SYSCOMMAND, SC_RESTORE, 0);
}
// 窗体置前
SetForegroundWindow(hWin);
BringWindowToTop(hWin);
}
if(hMutex)
CloseHandle(hMutex);
return 0;
}
//
try
{
Application->Initialize();
Application->CreateForm(__classid(TForm1), &Form1);
Application->Run();
}
catch (Exception &exception)
{
Application->ShowException(&exception);
}
catch (...)
{
try
{
throw Exception("");
}
catch (Exception &exception)
{
Application->ShowException(&exception);
}
}
return 0;
}
//---------------------------------------------------------------------------
问题出来了,如果有另一个程序的窗体也叫Form1的话,就很可能把别的程序的窗体起动起来哦,有没有更好的办法呢?(要方便哦不要太麻烦哦,呵呵)
...全文
请发表友善的回复…
发表回复
Maconel 2005-12-14
- 打赏
- 举报
还有一个方法,就是用普通的查找与自己窗体一样名字的窗体,然后发一个自定义消息给它,如果它是自己写的程序,则回复一个消息,如果不是自己写的,那当然是没反应了。
这个方法没试过,感觉挺麻烦,而且这个窗体必须是创建好以后才能响应消息。
这个方法没试过,感觉挺麻烦,而且这个窗体必须是创建好以后才能响应消息。
Maconel 2005-12-14
- 打赏
- 举报
我的方法和季老大的一样,在共享内存里写上自己的窗体句柄,如果发现已经有了,就读出他的句柄并显示他,如果没有,就写入自己的句柄。
我试了,这种方法如果在进程管理器中结束自己,不会影响下次运行。
我试了,这种方法如果在进程管理器中结束自己,不会影响下次运行。
penu 2005-12-14
- 打赏
- 举报
回复人: penu(懒猫·子在川上之再上征程·杀人无心之寓怒于静) ( ) 信誉:99 2005-12-13 09:46:00 得分: 0
一个是用进程互斥的方法,这是所谓的标准方法啦!老妖说过了。
还有其它的方法是很多的,比如你可以在程序开始时扫描内存中的进程,发现和本程序一样的(可以是判断进程名称、或者窗口标题等等),就给其发一个restore消息,同时结束本程序。不过这些方法都不太好,为什么?自己想想啦!
——NND,那个贴子偶都提了,本想接下去说来着,你们倒跑这边新开一贴,还把偶的话都说完了:(
一个是用进程互斥的方法,这是所谓的标准方法啦!老妖说过了。
还有其它的方法是很多的,比如你可以在程序开始时扫描内存中的进程,发现和本程序一样的(可以是判断进程名称、或者窗口标题等等),就给其发一个restore消息,同时结束本程序。不过这些方法都不太好,为什么?自己想想啦!
——NND,那个贴子偶都提了,本想接下去说来着,你们倒跑这边新开一贴,还把偶的话都说完了:(
constantine 2005-12-14
- 打赏
- 举报
季老大的方法好
AddAtom...这些麻烦在也有一个句柄的问题
AddAtom...这些麻烦在也有一个句柄的问题
alloutoflove 2005-12-14
- 打赏
- 举报
我是用Maconel所说的自定义消息的方法来的...
窗口标题可以用一些别的程序一般不会用的的字符来区分..当然TFrom1这样的名称太那个...........
窗口标题可以用一些别的程序一般不会用的的字符来区分..当然TFrom1这样的名称太那个...........
friendbcb 2005-12-14
- 打赏
- 举报
好多星星,看的头都晕了。支持季老大的方法
ccrun.com 2005-12-14
- 打赏
- 举报
来晚了。就用季老大的方法好了。
cczlp 2005-12-14
- 打赏
- 举报
凑热闹.
jishiping的方法最好.
其它方法还有,用 AddAtom FindAtom DeleteAtom 也可以实现
jishiping的方法最好.
其它方法还有,用 AddAtom FindAtom DeleteAtom 也可以实现
Maconel 2005-12-14
- 打赏
- 举报
老季的这个方法,我曾写过一个类,发给你参考一下。
weill 2005-12-14
- 打赏
- 举报
"不要用FindWindow,可以使用文件映射方式的共享内存,将主窗口句柄写在共享内存中。程序运行时,先检查共享存在是否存在,如果已经存在,从共享内存中读出上次的主窗口句柄。"
季老大……呵呵,代码何在……
给个代码来看看撒,偶不会咯,虽然混了个星星,但偶还是小菜鸟吖……
季老大……呵呵,代码何在……
给个代码来看看撒,偶不会咯,虽然混了个星星,但偶还是小菜鸟吖……
jishiping 2005-12-13
- 打赏
- 举报
还可以使用一个办法,就是主窗口设定一个特殊名字的属性(用API函数SetProp),这种情况也不会有前面的问题。
jishiping 2005-12-13
- 打赏
- 举报
使用 Mutex 有一个缺点,如果你的程序死了(比如任务管理器中强制结束),那么Mutex不会释放,那么程序就不能再运行啦。
jishiping 2005-12-13
- 打赏
- 举报
不要用FindWindow,可以使用文件映射方式的共享内存,将主窗口句柄写在共享内存中。程序运行时,先检查共享存在是否存在,如果已经存在,从共享内存中读出上次的主窗口句柄。
CACACACACA 2005-12-13
- 打赏
- 举报
ReleaseMutex(hMutex); 怎么不见了...:-)
勉励前行 2005-12-13
- 打赏
- 举报
使用dll的公用變量,這樣就不用FindWindow了。
dll給出一個類似的接口:bool RunMeOneTime(HANDLE );
不過那樣你的程序要帶一個dll。
dll給出一個類似的接口:bool RunMeOneTime(HANDLE );
不過那樣你的程序要帶一個dll。
TR@SOE 2005-12-13
- 打赏
- 举报
好像还有一个办法是在Global Heap里放置一些程序专用的字符串。。。呼唤达人
TR@SOE 2005-12-13
- 打赏
- 举报
这个,,,没有完全的可避免的方法的。这个方法是很标准的了。
一般来说,别人的程序,如果是已经release的程序,主窗口的名字不会不改一下的吧?
一般来说,别人的程序,如果是已经release的程序,主窗口的名字不会不改一下的吧?