티스토리 뷰

프로그램을 하나만 실행하기
Apr 08 2003 11:06 Written by mrsroses (codenuri.com members)


프로그램을 하나만 실행하기

제가 만든 프로그램을 항상 하나만 실행하도록 하는 방법에 대해 알아봅시다.
두 번째 실행시에는 먼저 실행되어 있던 프로그램을 앞으로 띄웁니다.

여러가지 방법이 있겠지만 파일맵핑 객체를 이용하도록 하겠습니다.
처음 뜨는 프로그램이 정해진 이름의 파일 맵핑 객체를 만들어 놓으면(여기서는 MyTestMap)
나중에 뜨는 프로그램들이 이 이름의 파일 맵핑 객체가 있는지 살펴보고 있으면 실행을 중지하는 방법입니다.
이 것이 가능한 이유는 파일 맵핑 객체는 시스템 전역 객체이기 때문입니다.
먼저 항상 하나만 떠 있 게 하는 방법을 알아보고 다음으로
기존의 프로그램을 앞으로 띄우는 코드를 알아보도록 하겠습니다.



항상 하나만 떠 있게 하는 방법

(윈도우의 캡션이 고정되어 있을 경우에는 FindWindow를 사용하는 것이 더 유리합니다).
다음 코드를 InitInstance의 선두에 넣습니다.


HANDLE hMapping;

hMapping = CreateFileMapping( (HANDLE) 0xffffffff, NULL, PAGE_READONLY, 0, 4, "MyTestMap" );
if( hMapping )
{
if( GetLastError() == ERROR_ALREADY_EXISTS )
{

// 프로그램이 이미 실행 중임을 알리는 메시지를 띄운다.

MessageBox( NULL, "이미 실행 중입니다.", "경고", MB_OK );
ExitProcess(1);
}
}


위의 코드는 하나의 실행파일을 실행할 수 있는 방법이지만
기존의 실행되어 있는 프로그램을 앞으로 띄우는 일까지 할 수는 없습니다.
이를 하려면 InitInstance의 코드를 다음과 같이 수정합니다.


HANDLE hMapping;

hMapping = CreateFileMapping( (HANDLE) 0xffffffff, NULL, PAGE_READWRITE, 0, 32, "MyTestMap" );

if( hMapping )
{
if( GetLastError() == ERROR_ALREADY_EXISTS )
{

// 프로그램이 이미 실행 중임을 알리는 메시지를 띄운다.

MessageBox( NULL, "이미 실행 중입니다.", "경고", MB_OK );
ExitProcess(1);
}

// 기존 파일맵핑 객체를 연다.
// 기존 파일 맵핑 객체의 선두에 이전 프로그램의 메인 윈도우 핸들이 들어있다.

hMapping = OpenFileMapping(FILE_MAP_WRITE, FALSE, "MyTestMap");
LPDWORD lpDword = (LPDWORD)MapViewOfFile(hMapping, FILE_MAP_READ, 0, 0, 4);
HWND hWnd = (HWND)*lpDword;

// 윈도우를 전면으로 내세우기 전에 먼저 아이콘 상태에 있을지도 모르는 윈도우를 원래 크기로 되돌린다.
// IsIconic 함수를 호출하여 아이콘 상태 여부를 확인해도 될 것이다.

ShowWindow(hWnd, SW_SHOW);
SetForegroundWindow(hWnd);

// 파일 맵핑 객체를 닫는다.

UnmapViewOfFile(lpDword);
ExitProcess(1);
}

.....

// Dispatch commands specified on the command line

if (!ProcessShellCommand(cmdInfo))
return FALSE;

// 다음을 추가한다.

LPDWORD lpDword = (LPDWORD)MapViewOfFile(hMapping, FILE_MAP_WRITE, 0, 0, 4);
*lpDword = (DWORD)m_pMainWnd->m_hWnd;
UnmapViewOfFile(lpDword);

// -------------------

m_pMainWnd->ShowWindow(SW_SHOW);
m_pMainWnd->UpdateWindow();