MFC Department of Digital Contents Sang Il Park

  • Slides: 77
Download presentation
MFC 시작하기 Department of Digital Contents Sang Il Park

MFC 시작하기 Department of Digital Contents Sang Il Park

간단한 메시지 기반 프로그래밍의 예 #include <iostream> using namespace std; int main() { int

간단한 메시지 기반 프로그래밍의 예 #include <iostream> using namespace std; int main() { int i; while(true) { cout<<"Input: "; cin>>i; Message Loop Message Handler } switch(i) { case 1: cout<<"Sejong University"<<endl; break; case 2: cout<<"Digital Contents"<<endl; break; case 3: cout<<"Bye!"<<endl; return 0; break; default: break; } } return 0;

좀 더 멋있게… void procedure(int msg) { switch(msg) { case 1: cout<<"Sejong University"<<endl; break;

좀 더 멋있게… void procedure(int msg) { switch(msg) { case 1: cout<<"Sejong University"<<endl; break; case 2: cout<<"Digital Contents"<<endl; break; case 3: int main() cout<<"Bye!"<<endl; { exit(0); int i; break; default: while(true) break; { } cout<<"Input: "; } cin>>i; procedure(i); } return 0; }

A Simple win 32 code // // FUNCTION: Wnd. Proc(HWND, UINT, WPARAM, LPARAM) //

A Simple win 32 code // // FUNCTION: Wnd. Proc(HWND, UINT, WPARAM, LPARAM) // // PURPOSE: Processes messages for the main window. // // // WM_COMMAND - process the application menu // FUNCTION: My. Register. Class() // WM_PAINT - Paint the main window // // WM_DESTROY - post a quit message and return // PURPOSE: Registers the window class. // // COMMENTS: LRESULT CALLBACK Wnd. Proc(HWND h. Wnd, UINT message, WPARAM w. Param, LPARAM // l. Param) // This function and its usage are only necessary if you {want this code // test. Win 32. cpp : Defines the entry point for the application. // to be compatible with Win 32 systems prior to the 'Register. Class. Ex' int wm. Id, wm. Event; // // function that was added to Windows 95. It is important to call this PAINTSTRUCT ps; function HDC hdc; #include "stdafx. h" // so that the application will get 'well formed' small icons associated #include "test. Win 32. h" // with it. switch (message) // { #define MAX_LOADSTRING 100 ATOM My. Register. Class(HINSTANCE h. Instance) case WM_COMMAND: { wm. Id = LOWORD(w. Param); // Global Variables: WNDCLASSEX wcex; wm. Event = HIWORD(w. Param); HINSTANCE h. Inst; // Parse the menu selections: wcex. cb. Size = sizeof(WNDCLASSEX); switch (wm. Id) // current instance { TCHAR sz. Title[MAX_LOADSTRING]; wcex. style case IDM_ABOUT: // The title bar = CS_HREDRAW | CS_VREDRAW; // Message. Box(h. Wnd, text wcex. lpfn. Wnd. Proc = Wnd. Proc; _T("haha"), _T("about"), MB_OK); TCHAR sz. Window. Class[MAX_LOADSTRING]; wcex. cb. Cls. Extra = 0; Dialog. Box(h. Inst, // the main window class name wcex. cb. Wnd. Extra = 0; MAKEINTRESOURCE(IDD_ABOUTBOX), h. Wnd, About); wcex. h. Instance = h. Instance; break; // Forward declarations of functions included in this code module: wcex. h. Icon case IDM_EXIT: ATOM = Load. Icon(h. Instance, MAKEINTRESOURCE(IDI_TESTWIN 32)); My. Register. Class(HINSTANCE h. Instance); wcex. h. Cursor = Destroy. Window(h. Wnd); BOOL Load. Cursor(NULL, IDC_ARROW); break; Init. Instance(HINSTANCE, int); wcex. hbr. Background = (HBRUSH)(COLOR_WINDOW+1); default: LRESULT CALLBACK Wnd. Proc(HWND, UINT, WPARAM, LPARAM); wcex. lpsz. Menu. Name = MAKEINTRESOURCE(IDC_TESTWIN 32); return INT_PTR CALLBACK About(HWND, UINT, WPARAM, LPARAM); wcex. lpsz. Class. Name = sz. Window. Class; Def. Window. Proc(h. Wnd, message, w. Param, l. Param); wcex. h. Icon. Sm = } int APIENTRY _t. Win. Main(HINSTANCE h. Instance, Load. Icon(wcex. h. Instance, MAKEINTRESOURCE(IDI_SMALL)); break; HINSTANCE h. Prev. Instance, case WM_PAINT: LPTSTR lp. Cmd. Line, return Register. Class. Ex(&wcex); hdc = Begin. Paint(h. Wnd, &ps); int n. Cmd. Show) } // TODO: Add any drawing code here. . . { RECT rect; UNREFERENCED_PARAMETER(h. Prev. Instance); // Get. Client. Rect(h. Wnd, &rect); UNREFERENCED_PARAMETER(lp. Cmd. Line); // FUNCTION: Init. Instance(HINSTANCE, int) Draw. Text(hdc, _T("hello, Windows"), // 1, &rect, DT_SINGLELINE|DT_CENTER|DT_VCENTER); // TODO: Place code here. // PURPOSE: Saves instance handle and creates main window End. Paint(h. Wnd, &ps); MSG msg; // break; HACCEL h. Accel. Table; // COMMENTS: case WM_DESTROY: // Post. Quit. Message(0); // Initialize global strings // In this function, we save the instance handle in a global variable break; Load. String(h. Instance, IDS_APP_TITLE, andsz. Title, default: MAX_LOADSTRING); // create and display the main program window. return Def. Window. Proc(h. Wnd, message, Load. String(h. Instance, IDC_TESTWIN 32, sz. Window. Class, // w. Param, l. Param); MAX_LOADSTRING); BOOL Init. Instance(HINSTANCE h. Instance, int n. Cmd. Show) } My. Register. Class(h. Instance); { return 0; HWND h. Wnd; } // Perform application initialization: if (!Init. Instance (h. Instance, n. Cmd. Show)) h. Inst = h. Instance; // Store instance handle in our global//variable Message handler for about box. { INT_PTR CALLBACK About(HWND h. Dlg, UINT message, WPARAM w. Param, LPARAM return FALSE; h. Wnd = Create. Window(sz. Window. Class, sz. Title, WS_OVERLAPPEDWINDOW, l. Param) } CW_USEDEFAULT, 0, NULL, h. Instance, NULL); { UNREFERENCED_PARAMETER(l. Param); h. Accel. Table = Load. Accelerators(h. Instance, if (!h. Wnd) switch (message) MAKEINTRESOURCE(IDC_TESTWIN 32)); { { return FALSE; case WM_INITDIALOG: // Main message loop: } return (INT_PTR)TRUE; while (Get. Message(&msg, NULL, 0, 0)) { Show. Window(h. Wnd, n. Cmd. Show); case WM_COMMAND: if (!Translate. Accelerator(msg. hwnd, Update. Window(h. Wnd); if (LOWORD(w. Param) == IDOK || h. Accel. Table, &msg)) LOWORD(w. Param) == IDCANCEL) { return TRUE; { } End. Dialog(h. Dlg, Translate. Message(&msg); LOWORD(w. Param)); return Dispatch. Message(&msg); (INT_PTR)TRUE; } } } break; } return (int) msg. w. Param; return (INT_PTR)FALSE; } }

Code in short BOOL Init. Instance(…) { h. Wnd = Create. Window(…); int APIENTRY

Code in short BOOL Init. Instance(…) { h. Wnd = Create. Window(…); int APIENTRY _t. Win. Main(…) { // Perform application initialization: if (!Init. Instance (h. Instance, n. Cmd. Show)) { return FALSE; } // Main message loop: while (Get. Message(&msg, NULL, 0, 0)) { if (!Translate. Accelerator(…)) { Translate. Message(&msg); Dispatch. Message(&msg); } } } return (int) msg. w. Param; Show. Window(h. Wnd, n. Cmd. Show); Update. Window(h. Wnd); } return TRUE; LRESULT CALLBACK Wnd. Proc(…) { switch (message) { case WM_COMMAND: break; case WM_PAINT: break; case WM_DESTROY: Post. Quit. Message(0); break; default: return; } return 0; }

Code in short BOOL Init. Instance(…) { h. Wnd = Create. Window(…); int APIENTRY

Code in short BOOL Init. Instance(…) { h. Wnd = Create. Window(…); int APIENTRY _t. Win. Main(…) { // Perform application initialization: if (!Init. Instance (h. Instance, n. Cmd. Show)) { return FALSE; } // Main message loop: while (Get. Message(&msg, NULL, 0, 0)) { if (!Translate. Accelerator(…)) { Translate. Message(&msg); Dispatch. Message(&msg); } } } return (int) msg. w. Param; Show. Window(h. Wnd, n. Cmd. Show); Update. Window(h. Wnd); } return TRUE; LRESULT CALLBACK Wnd. Proc(…) { switch (message) { case WM_COMMAND: break; case WM_PAINT: break; case WM_DESTROY: Post. Quit. Message(0); break; default: return; } return 0; }

MFC ?

MFC ?

The simplest MFC application • • • Single Document No Document/View architecture support No

The simplest MFC application • • • Single Document No Document/View architecture support No database support No Active. X control No Docking toolbar No Initial status bar

Look into the codes

Look into the codes

C++? CLASS?

C++? CLASS?

구조체의 정의 • Example) struct student { char name[30]; int number; float grade; };

구조체의 정의 • Example) struct student { char name[30]; int number; float grade; };

구조체 타입의 변수 선언 구조체이름 구조체변수이름; struct student { char name[30]; int number; float

구조체 타입의 변수 선언 구조체이름 구조체변수이름; struct student { char name[30]; int number; float grade; }; student a, b;

멤버로의 접근 구조체변수이름. 맴버변수이름 struct score { int korean; int math; }; score a;

멤버로의 접근 구조체변수이름. 맴버변수이름 struct score { int korean; int math; }; score a; a. korean = 30; a. math = 80;

구조체의 맴버 변수 접근 예 struct rectangle { int x, y; int width, height;

구조체의 맴버 변수 접근 예 struct rectangle { int x, y; int width, height; }; rectangle rc; rectangle * p = &rc; rc. x=10; (*p). x = 10; p->x = 10; 모두 같다

디폴트 생성자(Default Constructors) • 디폴트 생성자의 추가 class Point { public: int x, y;

디폴트 생성자(Default Constructors) • 디폴트 생성자의 추가 class Point { public: int x, y; void Print(); Point(); }; Point: : Point() { x = 0; y = 0; } // 실제 실행 시. . Point pt; pt. Print(); // 생성자가 호출된다.

인자가 있는 생성자 • 인자가 있는 생성자의 추가 class Point { public: int x,

인자가 있는 생성자 • 인자가 있는 생성자의 추가 class Point { public: int x, y; void Print(); Point(int initial. X, int initial. Y); }; Point: : Point(int initial. X, int initial. Y) { x = initial. X; y = initial. Y; } // 중간 생략 Point pt(3, 5); pt. Print();

소멸자 • 소멸자를 사용해서 할당한 메모리를 해제하는 예 class Dynamic. Array { public: int*

소멸자 • 소멸자를 사용해서 할당한 메모리를 해제하는 예 class Dynamic. Array { public: int* arr; Dynamic. Array(int array. Size); ~Dynamic. Array(); }; Dynamic. Array: : Dynamic. Array(int array. Size) { // 동적으로 메모리를 할당한다. arr = new int [array. Size]; } Dynamic. Array: : ~Dynamic. Array() { // 메모리를 해제한다. delete[] arr; arr = NULL; }

접근 권한 설정하기(1) • 멤버의 접근 권한을 설정하는 예 class Access. Control { public:

접근 권한 설정하기(1) • 멤버의 접근 권한을 설정하는 예 class Access. Control { public: char public. Data; void public. Func() {}; protected: int protected. Data; void protected. Func() {}; private: float private. Data; void private. Func() {}; }; int main() { // 객체를 생성하고, 각 멤버에 접근해보자 Access. Control ac; ac. public. Data = 'A'; ac. public. Func(); ac. protected. Data = 100; ac. protected. Func(); ac. private. Data = 4. 5 f; ac. private. Func(); return 0; } // // // 성공 성공 실패 실패

Homework #1 • 클래스 상속의 연습 – My. Shape Class 정의하기 • 맴버변수: float

Homework #1 • 클래스 상속의 연습 – My. Shape Class 정의하기 • 맴버변수: float _x, _y • 생성자: My. Shape(float x, float y) _x와 _y의 값을 설정 • 맴버함수: void Draw() const – 아래와 같은 내용 출력 [SHAPE] position = ( ‘_x값’, ‘_y값’ ) – My. Rect Class 정의하기 • • My. Shape Class로부터 상속 맴버변수: float _width, _height 생성자: My. Rect(float x, float y, float w, float h) 맴버함수: void Draw() const – 아래와 같은 내용 출력 [RECTANGLE] position = ( ‘_x값’, ‘_y값’), size = (‘_width’, ‘_height’)

Homework #1 • 클래스 상속의 연습 – My. Circle Class 정의하기 • • My.

Homework #1 • 클래스 상속의 연습 – My. Circle Class 정의하기 • • My. Shape Class로부터 상속 맴버변수: float _radius 생성자: My. Circle(float x, float y, float radius) 맴버함수: void Draw() const – 아래와 같은 내용 출력 [CIRCLE] position = ( ‘_x값’, ‘_y값’), radius = ‘_radius’

Homework #1 • 클래스 상속의 연습의 test - 다음과 같은 main 함수를 이용 int

Homework #1 • 클래스 상속의 연습의 test - 다음과 같은 main 함수를 이용 int main() { My. Shape* shapes[5] = {NULL}; shapes[0] shapes[1] shapes[2] shapes[3] shapes[4] = = = new new new My. Circle( 100, 50); My. Rect( 300, 100, 100); My. Rect( 200, 100, 50, 150); My. Circle(100, 300, 150); My. Rect( 200, 200); for (int i = 0; i < 5; ++i) shapes[i]->Draw(); for (i = 0; i < 5; ++i) { delete shapes[i]; shapes[i] = NULL; } }

s e ass cl Look into the codes

s e ass cl Look into the codes

프로그램 내부 구조 the. App (CSimple. App : CWin. App) m_p. Main. Frame (CMain.

프로그램 내부 구조 the. App (CSimple. App : CWin. App) m_p. Main. Frame (CMain. Frame : CFrame. Wnd) m_wnd. View (CChild. View : CWnd)

응용 프로그램 실행순서 CSimple. App the. App; Win. Main() { } // MFC 내부에

응용 프로그램 실행순서 CSimple. App the. App; Win. Main() { } // MFC 내부에 숨겨짐 the. App. Init. Instance(); // 초기화 the. App. Run(); // 메시지 루프 the. App. Exit. Instance(); // 종료

응용 프로그램 클래스 (1/4) // Simple. h class CSimple. App : public CWin. App

응용 프로그램 클래스 (1/4) // Simple. h class CSimple. App : public CWin. App { public: CSimple. App(); virtual BOOL Init. Instance(); }; afx_msg void On. App. About(); DECLARE_MESSAGE_MAP() 58

응용 프로그램 클래스 (2/4) MFC 기본 header file을 모아놓음 #include "stdafx. h" #include "simple.

응용 프로그램 클래스 (2/4) MFC 기본 header file을 모아놓음 #include "stdafx. h" #include "simple. h" #include "Main. Frm. h“ // Simple. cpp BEGIN_MESSAGE_MAP(CSimple. App, CWin. App) ON_COMMAND(ID_APP_ABOUT, On. App. About) END_MESSAGE_MAP() CSimple. App: : CSimple. App() { } CSimple. App the. App; // 응용프로그램 자신에 해당하는 전역객체 59

응용 프로그램 클래스 (3/4) BOOL CSimple. App: : Init. Instance() { Set. Registry. Key(_T("Local

응용 프로그램 클래스 (3/4) BOOL CSimple. App: : Init. Instance() { Set. Registry. Key(_T("Local App. Wizard-Generated Applications")); CMain. Frame* p. Frame = new CMain. Frame; m_p. Main. Wnd = p. Frame; p. Frame->Load. Frame(IDR_MAINFRAME, WS_OVERLAPPEDWINDOW | FWS_ADDTOTITLE, NULL); p. Frame->Show. Window(SW_SHOW); p. Frame->Update. Window(); } return TRUE; 60

응용 프로그램 클래스 (3/4) BOOL CSimple. App: : Init. Instance() { Set. Registry. Key(_T("Local

응용 프로그램 클래스 (3/4) BOOL CSimple. App: : Init. Instance() { Set. Registry. Key(_T("Local App. Wizard-Generated Applications")); CMain. Frame* p. Frame = new CMain. Frame; m_p. Main. Wnd = p. Frame; p. Frame->Load. Frame(IDR_MAINFRAME, WS_OVERLAPPEDWINDOW | FWS_ADDTOTITLE, NULL); p. Frame->Show. Window(SW_SHOW); p. Frame->Update. Window(); } return TRUE; 61

응용 프로그램 실행순서 CSimple. App the. App; Win. Main() { } // MFC 내부에

응용 프로그램 실행순서 CSimple. App the. App; Win. Main() { } // MFC 내부에 숨겨짐 the. App. Init. Instance(); // 초기화 the. App. Run(); // 메시지 루프 the. App. Exit. Instance(); // 종료

프레임 윈도우 클래스 (1/5) // Main. Frm. h class CMain. Frame : public CFrame.

프레임 윈도우 클래스 (1/5) // Main. Frm. h class CMain. Frame : public CFrame. Wnd { public: CMain. Frame(); protected: DECLARE_DYNAMIC(CMain. Frame) public: virtual BOOL Pre. Create. Window(CREATESTRUCT& cs); virtual BOOL On. Cmd. Msg(UINT n. ID, int n. Code, void* p. Extra, AFX_CMDHANDLERINFO* p. Handler. Info); virtual ~CMain. Frame(); CChild. View m_wnd. View; protected: afx_msg int On. Create(LPCREATESTRUCT lp. Create. Struct); afx_msg void On. Set. Focus(CWnd *p. Old. Wnd); DECLARE_MESSAGE_MAP() }; 65

프레임 윈도우 클래스 (2/5) // Main. Frm. cpp IMPLEMENT_DYNAMIC(CMain. Frame, CFrame. Wnd) BEGIN_MESSAGE_MAP(CMain. Frame,

프레임 윈도우 클래스 (2/5) // Main. Frm. cpp IMPLEMENT_DYNAMIC(CMain. Frame, CFrame. Wnd) BEGIN_MESSAGE_MAP(CMain. Frame, CFrame. Wnd) ON_WM_CREATE() ON_WM_SETFOCUS() END_MESSAGE_MAP() CMain. Frame: : CMain. Frame() { } CMain. Frame: : ~CMain. Frame() { } 66

프레임 윈도우 클래스 (3/5) int CMain. Frame: : On. Create(LPCREATESTRUCT lp. Create. Struct) {

프레임 윈도우 클래스 (3/5) int CMain. Frame: : On. Create(LPCREATESTRUCT lp. Create. Struct) { if (CFrame. Wnd: : On. Create(lp. Create. Struct) == -1) return -1; if (!m_wnd. View. Create(NULL, AFX_WS_DEFAULT_VIEW, CRect(0, 0, 0, 0), this, AFX_IDW_PANE_FIRST, NULL)) { TRACE 0("Failed to create view windown"); return -1; } } return 0; 67

프레임 윈도우 클래스 (4/5) BOOL CMain. Frame: : Pre. Create. Window(CREATESTRUCT& cs) { if(

프레임 윈도우 클래스 (4/5) BOOL CMain. Frame: : Pre. Create. Window(CREATESTRUCT& cs) { if( !CFrame. Wnd: : Pre. Create. Window(cs) ) return FALSE; cs. dw. Ex. Style &= ~WS_EX_CLIENTEDGE; cs. lpsz. Class = Afx. Register. Wnd. Class(0); return TRUE; } 68

프레임 윈도우 클래스 (4/5) struct CREATESTRUCT{ LPVOID lp. Create. Params; HINSTANCE h. Instance; HMENU

프레임 윈도우 클래스 (4/5) struct CREATESTRUCT{ LPVOID lp. Create. Params; HINSTANCE h. Instance; HMENU h. Menu; HWND hwnd. Parent; int cy; int cx; int y; int x; LONG style; LPCTSTR lpsz. Name; LPCTSTR lpsz. Class; DWORD dw. Ex. Style; }; 69

프레임 윈도우 클래스 (5/5) void CMain. Frame: : On. Set. Focus(CWnd* p. Old. Wnd)

프레임 윈도우 클래스 (5/5) void CMain. Frame: : On. Set. Focus(CWnd* p. Old. Wnd) { m_wnd. View. Set. Focus(); } BOOL CMain. Frame: : On. Cmd. Msg(UINT n. ID, int n. Code, void* p. Extra, AFX_CMDHANDLERINFO* p. Handler. Info) { if (m_wnd. View. On. Cmd. Msg(n. ID, n. Code, p. Extra, p. Handler. Info)) return TRUE; } return CFrame. Wnd: : On. Cmd. Msg(n. ID, n. Code, p. Extra, p. Handler. Info); 70

뷰 클래스 (1/4) // Child. View. h class CChild. View : public CWnd {

뷰 클래스 (1/4) // Child. View. h class CChild. View : public CWnd { public: CChild. View(); protected: virtual BOOL Pre. Create. Window(CREATESTRUCT& cs); public: virtual ~CChild. View(); protected: afx_msg void On. Paint(); DECLARE_MESSAGE_MAP() }; 72

뷰 클래스 (2/4) // Child. View. cpp CChild. View: : CChild. View() { }

뷰 클래스 (2/4) // Child. View. cpp CChild. View: : CChild. View() { } CChild. View: : ~CChild. View() { } BEGIN_MESSAGE_MAP(CChild. View, CWnd ) ON_WM_PAINT() END_MESSAGE_MAP() 73

뷰 클래스 (3/4) BOOL CChild. View: : Pre. Create. Window(CREATESTRUCT& cs) { if (!CWnd:

뷰 클래스 (3/4) BOOL CChild. View: : Pre. Create. Window(CREATESTRUCT& cs) { if (!CWnd: : Pre. Create. Window(cs)) return FALSE; cs. dw. Ex. Style |= WS_EX_CLIENTEDGE; cs. style &= ~WS_BORDER; cs. lpsz. Class = Afx. Register. Wnd. Class ( CS_HREDRAW|CS_VREDRAW|CS_DBLCLKS, : : Load. Cursor(NULL, IDC_ARROW), HBRUSH(COLOR_WINDOW+1), NULL); } return TRUE; Style: http: //msdn 2. microsoft. com/en-us/library/ms 632600(VS. 85). aspx 74 Ex. Style: http: //msdn 2. microsoft. com/en-us/library/ms 632680(VS. 85). aspx System Color: http: //msdn 2. microsoft. com/en-us/library/ms 724371. aspx

뷰 클래스 (4/4) void CChild. View: : On. Paint() { CPaint. DC dc(this); dc.

뷰 클래스 (4/4) void CChild. View: : On. Paint() { CPaint. DC dc(this); dc. Text. Out(100, _T("안녕하세요. “)); } 75