⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sinstance.cpp

📁 远程网络监视程序的源码
💻 CPP
字号:
/*
Module : SINSTANCE.CPP
Purpose: Defines the implementation for an MFC wrapper classe
         to do instance checking
Created: PJN / 29-07-1998
History: None

Copyright (c) 1998 by PJ Naughter.  
All rights reserved.

*/


/////////////////////////////////  Includes  //////////////////////////////////
#include "stdafx.h"
#include "sinstance.h"


#ifdef _DEBUG
#undef THIS_FILE
static char BASED_CODE THIS_FILE[] = __FILE__;
#define new DEBUG_NEW
#endif


///////////////////////////////// Implementation //////////////////////////////

//struct which is put into shared memory
struct WININSTANCE_S
{
	HWND hMainWnd;
};

//Class which be used as a static to ensure that we
//only close the file mapping at the very last chance
class CMmfManager
{
public:
	CMmfManager();
	~CMmfManager();

protected:
	HANDLE m_hMMFCreated;
	friend class CInstanceChecker;
};

CMmfManager::CMmfManager()
{
	m_hMMFCreated = NULL;
}

CMmfManager::~CMmfManager()
{
	if (m_hMMFCreated != NULL)
	{
		::CloseHandle(m_hMMFCreated);
		m_hMMFCreated = NULL;
	}
}

static CMmfManager g_obMmfManager;

//////////////////////////////////////////////////////////////////
//  Instance checker class implement
//
CInstanceChecker::CInstanceChecker(LPCTSTR szAppName) :
	m_mutexInstance(FALSE, szAppName)
{
	// Only one object of type CInstanceChecker should be created
	VERIFY(g_obMmfManager.m_hMMFCreated == NULL);

	m_hPrevMMF = NULL;
	m_sMMF = _T("InstanceChecker_MMF_");
	m_sMMF += szAppName;

	// lock during the checking period
	m_mutexInstance.Lock(5000);
}

BOOL CInstanceChecker::InstanceIsRunning()
{
	//Try to open the MMF first to see if we are the second instance
	m_hPrevMMF = ::OpenFileMapping( FILE_MAP_ALL_ACCESS, FALSE, m_sMMF);

	return (m_hPrevMMF != NULL); 
}

void CInstanceChecker::ActivatePrevInstance()
{
	VERIFY(m_hPrevMMF != NULL); //Whats happened to my handle !

	//Open up the MMF
	int nMMFSize = sizeof(WININSTANCE_S);
	WININSTANCE_S *pInstanceData = (WININSTANCE_S *) ::MapViewOfFile(m_hPrevMMF, FILE_MAP_READ | FILE_MAP_WRITE, 0, 0, nMMFSize);
	VERIFY(pInstanceData != NULL); //Opening the MMF should work

	//activate the old window
	HWND hWindow = pInstanceData->hMainWnd;
	CWnd wndPrev; 
	wndPrev.Attach(hWindow);
	if( ::IsWindow(wndPrev.m_hWnd) )
	{
		CWnd *pWndChild = wndPrev.GetLastActivePopup();

		if (wndPrev.IsIconic())
			wndPrev.ShowWindow(SW_RESTORE); 
		pWndChild->SetForegroundWindow();
	}

	//Detach the CWnd we were using
	wndPrev.Detach();

	//Unmap the MMF we were using
	VERIFY(::UnmapViewOfFile(pInstanceData));

	//Close the MMF
	VERIFY(::CloseHandle(m_hPrevMMF));
	m_hPrevMMF = NULL;
}

void CInstanceChecker::SaveHwnd(HWND hWnd)
{
	//If this is the first instance then copy our info into the shared memory
	if (m_hPrevMMF != NULL)
	{
		return;
	}

	//Create the MMF
	int nMMFSize = sizeof(WININSTANCE_S);
	g_obMmfManager.m_hMMFCreated = ::CreateFileMapping(INVALID_HANDLE_VALUE, NULL, PAGE_READWRITE, 0, nMMFSize, m_sMMF);
	VERIFY(g_obMmfManager.m_hMMFCreated != NULL); //Creating the MMF should work

	//Open the MMF
   	WININSTANCE_S *pInstanceData = (WININSTANCE_S *) ::MapViewOfFile(g_obMmfManager.m_hMMFCreated, FILE_MAP_READ | FILE_MAP_WRITE, 0, 0, nMMFSize);
	VERIFY(pInstanceData != NULL);   //Opening the MMF should work

	ASSERT(hWnd != NULL);
	pInstanceData->hMainWnd = hWnd;

	VERIFY(::UnmapViewOfFile(pInstanceData));
}

CInstanceChecker::~CInstanceChecker()
{
	if( m_hPrevMMF != NULL )
	{
		VERIFY(::CloseHandle(m_hPrevMMF));
	}

	m_mutexInstance.Unlock();
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -