본문 바로가기

윈도우프로그래밍

[윈도우 프로그래밍] 메시지 처리

메시지 처리의 기본 개념

-메시지: 발생된 이벤트의 종류와 정보를 전달하는 일종의 상수 값(양수인 상수) 컴퓨터에서 처리해야되니깐 !!

-> 마우스 클릭, 키보드 입력과 같은 이벤트에 대해 윈도우 시스템은 해당 애플리케이션에 이 "메시지"를 보내요!

-윈도우 프로그래밍에서 가장 중요한 것은 메시지를 처리하는 것 !!

1. 메시지의 종류

-메시지를 처리하는 주체에 따라서

1) 윈도우 메시지 WM_

매개변수를 가지고 있어 메시지를 어떻게 처리할 것인지를 결정하는 데 사용합니다. WM_COMMAN 제외 !

-초기화 메시지: 윈도우의 상태 바뀔 때 발생

-윈도우 관리 메시지: 응용 프로그램이 메뉴나 대화상자 구성할 때 발생

-입력 메시지: 마우스, 키보드로 입력할 때 발생

 

2) 컨트롤 통제 메시지

버튼, 콤보 박스와 같은 제어 객체나 자식 윈도우에서 부모 윈도우로 보내는 메시지

 

3) 명령 메시지: WM_COMMAND 메시지

메뉴, 툴바 등 사용자 인터페이스 객체로부터 발생되는 WM_COMMAND 메시지

 

2. 메시지 맵 = 테이블

-WN32에서는 switch을 이용해서 메시지 처리

-MFC에서는 메시지 처리를 위해 메시지 맵이라는 메커니즘 사용

-> 메시지 번호와 메시지가 발생하였을 때 호출되는 함수의 포인터 등의 정보를 갖고 있는 테이블

-프로그램에 전달된 메시지와 메시지 핸들러 함수 연결하는데 사용

-우리는 메시지 헨들러 함수의 본체만 코딩해주면 됨

-파생 클래스의 메시지 핸들러 함수가 우선입니다.

3. 메시지 처리 단계

윈도우 시스템에서 우리가 발생시킨 이벤트에 따른 메시지를 만들어서 해당 윈도우 애플리케이션에 보내줌 ->그 메시지를 처리할 함수를 윈도우 애플리케이션에 만들어야 ㅎ마

그래서 첫 단계로 윈도우 앱에 멤버 함수로 메시지 처리할 핸들러 함수를 선언하고 두번째로 각 메시지에 해당하는 함수들을 매핑하고 마지막으로 그 함수의 세부 내용을 적으면 처리를 할 수 있음

1. 윈도우 클래스의 멤버 함수로 메시지 핸들러 함수를 선언합니다. //윈도우 애플리케이션에 메시지 들어왔을 때 처리하기 위해서 만듭니다.

2. 메시지 맵에 메시지와 메시지 핸들러 함수를 묶는 메시지의 매크로를 추가합니다. //메시지 들어왔을 때 처리할 함수 연결

3. 메시지 핸들러 함수의 기능을 구현합니다. //메시지가 들어와서 처리할 함수의 세부 내용을 코딩

1. 메시지 핸들러 함수 선언
//매개변수는 생략
//실제 화면이 보여지는 CView 클래스에 선언
class CPracticeView:public CView{
.......
protected:
DECLEARE_MESSAGE_MAP() //메시지 맵 선언

public:
afx_msg int Oncreate(); // OnCreate 핸들러 함수
afx_msg void OnLButtonClk(); // OnLButtonClk 핸들러 함수
afx_msg void OnDestroy(); // OnDestroy 핸들러 함수
......
}

2. 메시지 매크로 추가
//메시지와 메시지 핸들러 함수 연결해주는 역할을 메시지 매크로가 수행
//이 역할은 메시지 매크로를 가지고 있는 메시지 맵이 실행
 BEGIN MESSAGE_MAP(CPracticeView, CView)//메시지 맵이 속하는 클래스 이름, 기본 클래스 인자로
 ......
ON_WM_CREATE() // WM_CREATE 메시지 매크로
ON_WM_LBUTTONCLK() // WM_LBUTTONCLK 메시지 매크로
ON_WM_DESTROY() // WM_DESTROY 메시지 매크로
.....
END MESSAGE_MAP()

3. 메시지 핸들러 함수 구혐
//메시지 핸들러 함수를 정의하였고, 메시지 맵을 활용해서 해당 메시지와 연결도 하였으니
//그 세부 내용을 사용자가 코드로 입력해서 구현해야 합니다.

int  CPracticeView::Oncreate(){
//세부 내용 작성
} 
void  CPracticeView::OnLButtonClk(){
//세부 내용 작성
} 
void  CPracticeView::OnDestroy(){
//세부 내용 작성

}

-클래스 마법사의 주요 기능은 메시지 매핑입니다.

-클래스 마법사 사용하면 위의 세가지 단계에서 마지막 단계의 메시지 핸들러 함수의 본체만 사용자가 구현하면 되고, 나머지는 자동으로 코딩을 해줍니다. 

-클래스 마법사의 "메시지" 창에서 메시지 선택하면 그에 따른 메시지 핸들러 함수 추가해줍니다.-> 두 개 연결해줍니다.(매크로 사용)->우리는 메시지 핸들러 함수 세부 내용만 코딩 ~~~

4. 메시지 핸들러 함수

-윈도우로부터(OS) 애플리케이션에 메시지가 전달될 때 해당 메시지를 처리하는 멤버 함수

 

함수 이름

-윈도우 메시지의 WM_을 떼고 대신 On을 붙여 시작합니다.

-함수 선언 시 afx_msg는 메시지 핸들러 함수라는 것을 나타내는 말입니다.

 

예시를 들어보겠습니다.

WM_KEYDOWN에 대한 메시지 헨들러 함수

(우리가 키보드 클릭하는 이벤트 발생시켜서 윈도우로부터 메시지가 발생했다. 이걸 처리할 메시지 핸들러 함수는 당연히 윈도우 앱에 있겠지???? 그 형태가 뭔지 알아봅시다~~)

-> OnKeyDown() 함수, 선언부는 afx_msg void OnKeyDown(매개변수)

 

 

메시지 박스

-사용자에게 간단한 메시지를 출력하는데 사용되는 대화상자

-MFC에서 메시지 박스를 출력하려면 AfxMessageBox() 함수를 사용합니다.

-AfxMessageBox(출력하고자 하는 문자열, 메시지 박스 출력 스타일, 도움말 id) 함수 사용

-> 메시지 박스 출력 스타일=버튼, 아이콘 OR(|) 연산자로 조합하여 설정

-> 디폴트는 메시지 박스 스타일(MB_OK), 아이콘(MB_ICONEXCLAMATION)

실습 3-1 메시지 박스 생성하기

 

1.  클래스 마법사

-주요 기능 5가지 -창으로 생각 !!

(1) 명령 메시지 설정

(2) 메시지 매핑 설정

(3) 가상함수 설정

(4) 클래스에 멤버변수를 설정

(5) 메서드를 설정

 

마우스 메시지

-마우스를 통한 입력은 메시지 형태로 프로그램에 전달합니다.

-메시지 예시로 WM_MOUSEMOVE, WM_LBUTTONDBCLK ...등등이 있습니다.

<마우스 메시지 헨들러 함수의 매개변수>

nFlags:버튼이 눌리면서 키보드에서 특정한 키가 눌러졌을 때의 값이나 마우스 눌림 값

-> MK_CONTROL, MK_LBUTTON, MK_SHIFT ...

point: 클라이언트 영역의 현재 마우스 좌표 값, CPoint 클래스를 이용해서 제공

-> 윈도우의 클라이언트 영역은 좌측 상단 좌표가 (0,0)인 상태 좌표입니다.

1.  실습 3-2 디지털 시계 만들기

-SetTimer(타이머 id, 1000, null)

-> null로 해두면 OnTImer()가 실행됨

->1000이면 1초마다 메시지 발생

타이머 아이디, wm_timer 발생시킬 시간 간격, wm_timer 메시지 발생될 때 실행되는 함수

-KillTimer( 타이머 아이디)

-> 타이머 해제하는 기능, 인수는 SetTimer에서 설정한 타이머의 아이디

 

-CTime 클래스: 시간과 날짜를 표현하고 저장하기 위한 클래스

-> CTime::GetCurrentTime() 함수: 윈도우 시스템으로부터 윈도우 시스템의 현재 날짜와 시간을 얻어 CTime 객체 반환합니다.

 

키보드 메시지

-키보드 입력도 마우스 입력과 같이 메시지 형태로 프로그램에 전달

-키보드 입력을 처리한다는 것은 키보드 메시지를 어떻게 처리하느냐에 달려있습니다.

-문자가 입력되는 사건에 발생되는 메시지: WM_KEYDOWN -> WM_CHAR -> WM_KEYUP

<키보드 메시지 헨들러 함수의 매개변수>

-nChar: 가상키 코드, 다양한 키에 대한 상수 값으로 정의되어있습니다.(VK_CANCEL, VK_BACK, VK_SHIFT 등등...)

             WM_CHAR의 경우 눌려진 키의 문자 코드!! 상수값으로 나타낼 수 없으니깐.

-nRepCount:키를 계속 누르고 있을 경우 반복된 키의 횟수

-nFlags: alt 키에 관한 정보

실습 3-3 문자를 입력하고 이동시키기

연습 문제

스톱워치 기능 구현하기