概要: 这一章主要了解一个典型的windows程序设计的各个组成部分!要明白并且掌握windows消息驱动型的特点。本章从一个典型的例子出发来讲述程序的各个部分!
1 #include<Windows.h> 2 #include<stdafx.h> 3 LRESULT CALLBACK WndProc(HWND hwnd,UINT,WPARAM,LPARAM); 4 int WINAPI WinMain(HINSTANCE hInstance,HINSTANCE hPreStacne,PSTR szCmdLine,int iCmdLine) 5 { 6 static TCHAR szAppName[]=TEXT("hello world"); 7 HWND hwnd; 8 MSG msg; 9 WNDCLASS wndclass; 10 wndclass.style=CS_HREDRAW |CS_VREDRAW; 11 wndclass.lpfnWndProc=WndProc; 12 wndclass.cbClsExtra= 0; 13 wndclass.cbWndExtra = 0; 14 wndclass.hInstance = hInstance; 15 wndclass.hCursor = LoadCursor(NULL,IDC_ARROW); 16 wndclass.hIcon = LoadIcon(NULL,IDI_APPLICATION); 17 wndclass.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH); 18 19 wndclass.lpszClassName = szAppName; 20 wndclass.lpszMenuName = NULL; 21 if(!RegisterClass(&wndclass)) 22 { 23 MessageBox(NULL,TEXT("The programe requires windows NT"),szAppName,MB_ICONERROR); 24 return 0; 25 } 26 hwnd = CreateWindow(szAppName, 27 TEXT("The hello world programe"), 28 WS_OVERLAPPEDWINDOW, 29 CW_USEDEFAULT, 30 CW_USEDEFAULT, 31 CW_USEDEFAULT, 32 CW_USEDEFAULT, 33 NULL, 34 NULL, 35 hInstance, 36 NULL); 37 ShowWindow(hwnd,iCmdLine); 38 UpdateWindow(hwnd); 39 while(GetMessage(&msg,NULL,0,0)) 40 { 41 TranslateMessage(&msg); 42 DispatchMessage(&msg); 43 } 44 return msg.wParam; 45 46 } 47 LRESULT CALLBACK WndProc(HWND hwnd,UINT message,WPARAM wParam,LPARAM lParam) 48 { 49 HDC hdc; 50 RECT rect; 51 PAINTSTRUCT ps; 52 switch(message) 53 { 54 case WM_CREATE: 55 return 0; 56 case WM_PAINT: 57 hdc =BeginPaint(hwnd,&ps); 58 GetClientRect(hwnd,&rect); 59 DrawText(hdc,TEXT("hello world"),-1,&rect,DT_SINGLELINE|DT_CENTER|DT_VCENTER); 60 EndPaint(hwnd,&ps); 61 return 0; 62 case WM_DESTROY: 63 PostQuitMessage(0); 64 return 0; 65 } 66 return DefWindowProc(hwnd,message,wParam,lParam); 67 }
首先抛开这个程序,先讲几个概念
1.事件驱动型是什么意思?
大多数的windows程序设计最主要的目的是设计消息处理函数,windows这个操作系统会保存很多的消息到这个进程的消息队列中,当移动鼠标,移动对话框,按键盘等等事件的发生时,就会产生消息,windows将这些消息保存到队列中,然后按先进先出的顺序,派给消息处理函数来处理!这就是事件驱动!
2.什么是句柄?
句柄从本质上来讲,是一个整型数。但是我们要知道一个句柄的实际意义就必须从内核对象讲起。
常见的内核对象包括文件对象,进程对象,I/O对象等,实际上每个对象都只是一个内存块,它由内核分配,只能由内核访问(程序员通过API(windows系统提供的函数)来访问这些内存对象)
,调用一个会创建内核对象的函数就会返回一个句柄!,它标志着这个创建的内核对象。将这个句柄传递给各种windows函数表示你想对这个内核对象进行各种操作!这是对句柄的最基本的认识!
程序各个部分的讲解
首先创建了一个WNDCLASS 的对象,一个窗口的建立总是基于一个windows类而创建的,多个窗口是可以基于同一个类,这个类的各种成员可以查看MSDN,这里不一一说明,只说明比较重要的两个成员。其中lpfWndProc 的类型是一个函数指针,这个指针指向的是一个消息处理函数,也就是书上说的窗函数,意味着当windows向这个窗口发送消息的时候,用这个函数来处理!
最后一个成员指的是这个类的名称!
再将这个类的成员初始化后,我们必须对这个类进行注册,也就是使用RegisterClass 这个函数,一旦注册成功,则这个系统就具有了一个以这个窗口类型的结构最后一个成员命名的窗口类型!应用程序就可以以此窗口类型来创建窗口!
接下来的一部分是用来讲怎么创建这个窗口,使用的是CreateWindow这个函数,这个函数的用法我就不想说了,你可以查看msdn,这个函数返回的是这个窗口的文件句柄,也就是说,你以后想要使用这个窗口,你就可以把这个文件句柄传递给这个操作窗口的函数。当程序运行到这个地方的时候,会产生一个WM_CREATE的消息
紧接着是用来显示窗口的的函数ShowWindow(),和UpdateWindow(),最后便是消息的循环,其中GetMessage 是用来从消息队列中获取消息而TranslateMessage是用来将键盘信息转换成字符信息,DispatchMessage()则是向windows发送信息!
信息处理函数:主要是一种switch...case 结构的函数,是用来处理各种windows发送过来的信息!你可以选择性的处理一些信息,其中你不想要处理的信息都要交给DefWindowProc来处理!
总结:本章主要是掌握一个典型的win32应用程序应该是由哪些部分来组成!