Notice
Recent Posts
관리 메뉴

Hacking Arts

WndProc - 메시지 처리하기 본문

Programing/API Programing

WndProc - 메시지 처리하기

Rakehell 2014. 9. 20. 02:12

-메시지 루프를 통해서 윈도우 프로시저로 전달된 메시지는 윈도우 프로시저가 구분하여 작업을 처리하게 된다.

LRESULT CALLBACK WndProc(HWND hWnd, UINT iMessage, WPARAM wParam, LPARAM lParam)
{
	HDC hdc;
	PAINTSTRUCT ps;
	switch(iMessage)
	{
		case WM_CREAT:
			return 0;
		case WM_PAINT:
			hdc=BeginPaint(hWnd, &ps);
			EndPaint(hWnd, &ps);
			return 0;
		case WM_DESTROY:
			PostQuitMessage(0);
			return 0;
	}
	return(DefWindowProc(hWnd, iMessage, wParam, lParam));
}

-WndProc의 인수 정보

 인수

설명 

hWnd

메시지를 받을 윈도우 핸들이다. 

iMessage

전달된 메시지 값이다. 어떤 종류의 메시지인지, 즉 어떤 변화가 발생했는지에 대한 정보를 가지고 있다. 

wParam 

iMessage에 따른 부가 정보를 갖는다. 예를 들어 마우스 왼쪽 버튼이 눌려지면 WM_LBUTTONDOWN 메시지가 발생했을 때, 화면 어디쯤 위치에 마우스 버튼이 눌려졌는지 조합된 형태로  키가 눌려졌는지 등의 정보들이 필요한데, 이러한 정보들이 wParam, lParam으로 전달되며, 실제로 wParam, lParam에 각각 저장되는 정보들은 메시지 별로 다르다.

 lParam


-메시지 구분

iMessage에 전달된 메시지 값이 담겨지며 이 값으로 어떤 메시지가 왔는지 구분한다. 이 때 switch문이 쓰인다. case문으로 분기하여 메시지마다 처리한다. 위의 코드를 보면 알 수 있다.

case 문에서 처리되지 않은 메시지는 DefWindowProc 함수로 넘겨져 처리된다.


-DefWindowProc함수

이 함수는 위에 말했듯이 처리되지 않은 메시지를 처리 해준다. 윈도우 프로시저에서 처럼 4개의 인수를 사용하며 소스코드는 공개되지 않았으며 윈도우 프로시저와 비슷할 것으로 추정된다고 한다.


-함수 호출 규약

함 수 호출 규약이란 함수를 호출할 때 지켜야 하는 약속을 말한다. 함수의 원형을 선언하고 반환형과 함수명 이에 함수 호출 규약을 지정한다.

return_type        call_type    function_name(arg1,arg2);

호출 규약을 지정하는 매크로에는 PASCAL, CALLBACK, APIENTRY, WINAPI 등이 있다.


위에 얘기는 잘 이해가 안된다. 나중에 다시 해봐야 될 것같다.


이렇게 해서 아래와 같은 기반의 코드를 작성 할 수 있다.

#include
#include

LRESULT CALLBACK WndProc(HWND, UINT, WPARAM, LPARAM);
HINSTANCE g_hInst;
LPWSTR lpszClass = L"ApiBase";

int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmdParam, int nCmdShow)
{
	HWND hWnd;
	MSG Message;
	WNDCLASS WndClass;
	g_hInst = hInstance;

	WndClass.cbClsExtra = 0;
	WndClass.cbWndExtra = 0;
	WndClass.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);
	WndClass.hCursor = LoadCursor(NULL, IDC_ARROW);
	WndClass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
	WndClass.hInstance = hInstance;
	WndClass.lpfnWndProc = (WNDPROC)WndProc;
	WndClass.lpszClassName = lpszClass;
	WndClass.lpszMenuName = NULL;
	WndClass.style = CS_HREDRAW | CS_VREDRAW;

	RegisterClass(&WndClass);

	hWnd = CreateWindow(lpszClass, lpszClass, WS_OVERLAPPEDWINDOW, CW_USEDEFAULT,
		CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, NULL, (HMENU)NULL, hInstance, NULL);

	ShowWindow(hWnd, nCmdShow);

	while (GetMessage(&Message, 0, 0, 0)){
		TranslateMessage(&Message);
		DispatchMessage(&Message);
	}

	return Message.wParam;
}

LRESULT CALLBACK WndProc(HWND hWnd, UINT iMessage, WPARAM wParam, LPARAM lParam)
{
	switch (iMessage)
	{
	case WM_DESTROY:
		PostQuitMessage(0);
		return 0;
	}
	return(DefWindowProc(hWnd, iMessage, wParam, lParam));
}


-참고 서적

API Programing / 이창현 / 혜지원