WindowsAPI-첫 번째 예제
윈도우즈 API 완전정복1 - 예제가 있어서 포스팅 해보겠습니다.
<윈도우를 만드는 과정>
WndClass 정의
|
RegisterClass: 윈도우 클래스를 등록
|
CreateWindow :메모리 상에 윈도우를 만듬
|
ShowWindow: 화면에 표시
|
메시지루프
#include <Windows.h>
LRESULT CALLBACK WndProc(HWND,UINT,WPARAM,LPARAM);
HINSTANCE g_hInst;
LPCTSTR lpszClass=TEXT("First");
int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmdPram, 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;
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,NULL,0,0))
{
TranslateMessage(&Message);
DispatchMessage(&Message);
}
return (int)Message.wParam;
}
LRESULT CALLBACK WndProc(HWND hWnd,UINT iMessage, WPARAM wParam, LPARAM IParam)
{
switch(iMessage){
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return(DefWindowProc(hWnd,iMessage,wParam,IParam));
}
<분석>
-시작점
int APIENTRY WinMain(HINSTANCE hInstance, HINSTANCE hPrevInstance, LPSTR lpszCmdPram, int nCmdShow)-모든 윈도우즈 프로그램의 시작점은 WinMain 이다.
-APIENTRY 지정나는 윈도우즈 표준 호출 규약인 _stdcall을 사용한다는 뜻이다.
인수 의미
------------------------------------------------------------------------------------------
hInstance 프로그램의 인스턴스 핸들이다.
hPrevInstance 16비트와의 호환성을 위한 것이므로 신경X
lpszCmdParam 명령행으로 입력된 프로그램 인수이다.
nCmdShow 프로그램이 실행될 형태이며 최소화, 보통 모양등이 전달
이중 hInstance 이외에는 잘 사용되지 않는다. 인스턴스(Instance)라는 말은 실행중인 프로그램 하나를 칭하는 용어이다. 윈도우즈는 여러 개의 프로그램이 동시에 실행되는 멀티 태스킹 시스템일 뿐만 아니라 하나의 프로그램이 여러 번 실행될 수도 있다. 이때 실행되고 있는 각각의 프로그램을 프로그램 인스턴스라고 하며 간단히 줄여서 인스턴스라고 한다.
예를 들어 Notepad.exe를 두개 실행시키면 같은 Notepad.exe이지만 OS는 각각 다른 메모리를 사용하는 다른 프로그램으로 인식한다. 각 메모장은 서로 다른 인스턴스 핸들을 가지며 OS는 이 인스턴스 핸들값으로 두 개의 메모장을 서로 구별한다.
즉 hInstance란 프로그램 자체를 일컫는 정수값이며 프로그램 내부에서 자기 자신을 가리키는 1인칭 대명사이다.
많은 API 함수들이 hInstance값을 인수로 요구하는데 그래서 이 예제에서는 WinMain의 인수로 전달된 hInstance값을 전역변수 g_hInst에 대입해 두었다(위의 빨간색 표시). hInstance 인수는 기억 부류가 지역변수이기 때문에 WinMain 밖에서는 사용할 수 없기 때문이다. 이 예제에서는 g_hInst 값을 당장 사용하지 않지만, 앞으로의 예제에서는 이 값을 수시로 사용하게 될 것이다. g_hInst외에 lpszClass라는 전역 문자열이 정의되어 있는데, 이 문자열은 윈도우 클래스를 정의하는데 사용되며 윈도우의 타이틀 바에 표시되기도 한다.
-First 예제에서는 다음 두 변수를 전역으로 선언해 사용하고 있다.
HINSTANCE g_hInst;
LPCTSTR lpszClass=TEXT("First");
-메시지 처리 함수
이 프로그램은 두 개의 함수만 정의하고 있다. 하나는 프로그램의 시작점은 WinMain이며 나머지 하나는 WndProc이다. WndProc은 사용자와 시스템이 보내오는 메시지를 처리하는 아주 중요한 일을 한다. 윈도우즈에서는 아주 특별한 경우를 제외하곤ㄴ 이 두 개의 함수가 모두 있어야 한다.
WinMain은 메인 윈도우를 만들고 화면에 윈도우를 표시하기만 할 뿐이며 대부분의 일은 WndProc에서 이루어진다. WinMain은 프로그램을 초기화 하고 시작시키만 하므로 모양이 대체로 일정한데 WndProc은 프로그램의 실질적이고도 고유한 처리를 하는 곳이므로 프로그램에 따라 천차만별로 달라진다.
따라서 소스를 문석할 때 주의깊게 봐야할 부분은 WndProc이다.
-윈도우 클래스
WinMain의 가장 중요한 역할은 메인 윈도우를 만드는 것입니다. 그래야 사용자로부터 입력을 받을 수 있고 결과를 출력할 수 있기 때문입니다. 윈도우를 만들려면 윈도우 클래스를 먼저 등록한 후 CreateWindow 함수를 호출해야 합니다.
윈도우 클래스: -만들어질 윈도우의 여러 가지 특성을 정의하는 구조체
-모든 윈도우는 윈도우 클래스의 정보를 기반으로 만들어짐
typedef struct tagWNDCLASS
{
UINT style;
WNDPROC lpfnWndProc;
int cbClsExtra;
int cbWndExtra;
HINSTANCE hInstance;
HICON hIcon;
HCURSOR hCursor;
HBRUSH hbrBackground;
LPCSTR lpszMenuName;
LPCSTR lpszClassName;
}WNDCLASS;
style: 윈도우가 어떤 형태를 가질 것인가 지정
보통( CS_HREDRAW와 CS_VREDRAW가 or 로 연결되 많이 쓰임) 이는 윈도우의 수직 or 수평 크기가 변할 경우 윈도우를 다시 그린다는 뜻
hInstance: 윈도우 클래스를 등록하는 프로그램의 번호 WinMain의 인수로 전달된 hInstance값을 그대로 대입
-윈도우 생성
1.CreateWindow함수를 사용
(CreateWindow: 윈도우에 관한 모든 정보를 메모리에 만든 후 윈도우를 대표하는 번호인 윈도우 핸들을 리턴)
HWND CreateWindow(lpszClassName, lpszWindowName, dwStyle, x, y, nWidth, nHeight, hwndParent, hmenu, hinst, IpvParam)
lpszClassName: 생성하고자 하는 윈도우 클래스를 지정하는 문자열
lpszWindowName: 윈도우의 타이틀 바에 나타날 문자열
dwStyle: 만들고자 하는 윈도우의 형태를 지정(보통 WS_OVERLAPPEDWINDOW)
X, Y,n Width, mHeight: 뜻 그래도 이해, (최적화 CW_USEDEFAULT)
hwndParent: NULL로 지정하면 데스크 탑을 부모로 가져 바탕화면 어디서든 돌아다님
hmenu: NULL일 경우 메뉴 없는 윈도우가 만들어짐
hinst: 프로그램의 핸들을 지정
lpvParam: 보통 NULL값을 가짐
2.ShowWindow함수를 사용
Bool ShowWindow(hWnd, nCmdShow);
hWnd=CreateWindow(lpszClass,lpszClass,WS_OVERLAPPEDWINDOW,CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,CW_USEDEFAULT,NULL,(HMENU)NULL,hInstance,NULL);
ShowWindow(hWnd,nCmdShow);
이 두 줄의 코드로 윈도우를 화면에 나타내게 한다.
{
TranslateMessage(&Message);
DispatchMessage(&Message);
}
return (int)Message.wParam;
}
1.BOOL GetMessage(LPMSG lpMsg, HWND hWnd, UINT wMsgFilterMin, UINT wMsgFilterMax);
메시지 큐에서 메시지를 읽어오는 함수이다. 메시지는 MSG 구조체에 저장된다. 메시지 큐는 시스템이나 사용자로부터 발생된 메시지가 잠시 대기하는 일종의 메시지 임시 저장 영역!!!
즉 반복해서 메시지를 읽어오다가 얽어온 메시지가 WM_QUIT일 경우 FALSE를 리턴 반복문이 멈추게 된다.
2.BOOL TranslateMessage(CONST MSG *lpMsg);
이 함수는 키보드의 눌림(WM_KEYDOWN) 메시지가 발생할 때 문자가 입력되었다는 메시지(WM_CHAR)를 만드는 역할을 한다.
3.LONG DispatchMessage(CONST MSG *lpmsg);
이 함수는 메시지 큐에서 꺼낸 메시지를 윈도우 메시지 처리함수인 WndProc로 전달
LRESULT CALLBACK WndProc(HWND hWnd,UINT iMessage, WPARAM wParam, LPARAM IParam)
{
switch(iMessage){
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return(DefWindowProc(hWnd,iMessage,wParam,IParam));
}
1.인수
hWnd: 메시지를 받을 윈도우 핸들
iMessage: WM_SIZE, WM_KEYDOWN, WM_DESTROY(Alt+F4 등) 등의 값을 가짐
wParam, lParam: iMessage의 메시지에 따른 부가적인 정보를 가짐
2. 구문
ShowWindow(hWnd,nCmdShow);
이 두 줄의 코드로 윈도우를 화면에 나타내게 한다.
-메시지 루프
while(GetMessage(&Message,NULL,0,0)){
TranslateMessage(&Message);
DispatchMessage(&Message);
}
return (int)Message.wParam;
}
1.BOOL GetMessage(LPMSG lpMsg, HWND hWnd, UINT wMsgFilterMin, UINT wMsgFilterMax);
메시지 큐에서 메시지를 읽어오는 함수이다. 메시지는 MSG 구조체에 저장된다. 메시지 큐는 시스템이나 사용자로부터 발생된 메시지가 잠시 대기하는 일종의 메시지 임시 저장 영역!!!
즉 반복해서 메시지를 읽어오다가 얽어온 메시지가 WM_QUIT일 경우 FALSE를 리턴 반복문이 멈추게 된다.
2.BOOL TranslateMessage(CONST MSG *lpMsg);
이 함수는 키보드의 눌림(WM_KEYDOWN) 메시지가 발생할 때 문자가 입력되었다는 메시지(WM_CHAR)를 만드는 역할을 한다.
3.LONG DispatchMessage(CONST MSG *lpmsg);
이 함수는 메시지 큐에서 꺼낸 메시지를 윈도우 메시지 처리함수인 WndProc로 전달
-WndProc(윈도우 프로시저)
LRESULT CALLBACK WndProc(HWND hWnd,UINT iMessage, WPARAM wParam, LPARAM IParam)
{
switch(iMessage){
case WM_DESTROY:
PostQuitMessage(0);
return 0;
}
return(DefWindowProc(hWnd,iMessage,wParam,IParam));
}
1.인수
hWnd: 메시지를 받을 윈도우 핸들
iMessage: WM_SIZE, WM_KEYDOWN, WM_DESTROY(Alt+F4 등) 등의 값을 가짐
wParam, lParam: iMessage의 메시지에 따른 부가적인 정보를 가짐
2. 구문
PostQuitMessage: WM_QUIT 메시지를 보냄 WM_QUIT 메시지가 전송되면 GetMessage 함수의 리턴값이 FALSE가 되어 루프를 빠져나오게 된다.
-윈도우즈 API 정복1
0 개의 댓글