Introduction
Welcome to CSingleInstance
, a freeware MFC class to make your app into a single instance. Limiting your app to single instance is more tricky in Win32 with the removal of the hPrevInstance
parameter from WinMain
and the introduction of separate address spaces.
There are numerous examples already out there of making your app single instance, but some such as the one I found on http://www.codeguru.com/ require knowledge of undocumented or heavy duty MFC.
Other methods such as using FindWindow
or FindWindowEx
are not 100% bullet proof due to the preemptive Win32 environment.
This class internally uses a memory mapped file (MMF) into which the handle of the main window of your application is stuffed. When a second instance of your app is run, it detects that the memory mapped file exists, gets the window handle of the first instance from the MMF and reactivates the old window.
The source zip file contains the CSingleInstance
source code and a simple MFC app (without Doc/View) which demonstrates all the functionality of the class. For further details on how to use the class, have a look at the BOOL CMyApp::InitInstance()
function and the included documentation.
Features
- Very simple API, only 2 functions exposed.
- Does not require any messing around with window styles and your mainfrm source code.
- Much more robust implementation than other methods as already mentioned.
- The classes are fully Unicode compliant and include Unicode built options in the workspace file.
Usage
To use the class in your code, simply include sinstance.cpp in your project and #include sinstance.h
in your app's source file. Create your mainfrm window as normal but before you show it, simply include the following code:
CMyApp::InitInstance()
{
CInstanceChecker instanceChecker;
if (instanceChecker.PreviousInstanceRunning())
{
AfxMessageBox(_T("Previous version detected, will now restore it"),
MB_OK);
instanceChecker.ActivatePreviousInstance();
return FALSE;
}
....
CMainFrame* pMainFrame = new CMainFrame;
m_pMainWnd = pMainFrame;
if (!pMainFrame->LoadFrame(IDR_MAINFRAME))
return FALSE;
if (!instanceChecker.PreviousInstanceRunning())
instanceChecker.TrackFirstInstanceRunning();
.....
}
That's all there is to it. Your application should now be single instance. For those interested in the nitty gritty of the code, have a look at sinstance.cpp.
History
- V1.0 (29th July 1998)
- V1.01 (27th March 2000)
- Now ships with a VC 5 workspace.
- Fixed a potential handle leak where the file handle
m_hPrevInstance
was not being closed under certain circumstances.
- The remaining changes were made by Neville Franks. Contact nevf@getsoft.com, http://www.getsoft.com/.
- Changed
#pragma
error in instance header file to #pragma
message. Former wouldn't compile under VC6
- Replaced above
#pragma
with #include
.
- Added
TrackFirstInstanceRunning()
, MakeMMFFilename()
- Split
PreviousInstanceRunning()
up into separate functions so we can call it without needing the MainFrame window.
- Changed
ActivatePreviousInstance()
to return hWnd
.
- V1.02 (28th March 2000)
- Minor update to the documentation.
API Reference
The API consists of the the two public member functions of the class CSingleInstance
:
- CSingleInstance::PreviousInstanceRunninging
-
BOOL CSingleInstance::PreviousInstanceRunning()
Return Value:
TRUE
if a previous instance of this application is running, otherwise FALSE
.
Remarks:
In response to TRUE
being sent back the program, should call ActivatePreviousInstance()
and abort prematurely from the current instance of the app.
- CSingleInstance::ActivatePreviousInstance
-
BOOL CSingleInstance::ActivatePreviousInstance()
Remarks:
Activates the previous instance of the app as detected in a call to PreviousInstanceRunning()
.
Contacting the Author
PJ Naughter
Email: mailto:pjn@indigo..ie
Web: http://www.naughter.com/
29th July 1998