学习《Windows程序设计》记录

第六章 Windows图形界面,第五章图形界面

读书《Windows程序设计》记录

 

概念贴士:

1.  每一个GUI应用程序至少应当创制一个窗口,称为主窗口,它作为用户与应用程序间的主界面来提供劳动。大部分应用程序也直接或直接地创造其他窗口,来形成与主窗口相关的干活。

 

2.  应用程序的主窗口包含题目栏、菜单栏、Windows系统菜单、最小化按钮、最大化按钮、回复按钮、关闭按钮、可改变大小的边框、窗口客户区、垂直滚动条和水平滚动条。

 

3.  VC++6.0创造GUI程序:  1)创设VC++6.0,选取命令“文件”,点击“新建”;

                2)选择“工程”,点击“Win32
Application”选项;

                3)输入工程名、存放路径;

                4)点击OK按钮,选拔第①项“三个简易Win32应用程序”;

                5)点击“实现”按钮,达成GUI程序工程成立。

 

4.  Win32程序的入口函数将是WinMain函数,而不是控制台程序的main函数。

 

5.  GUI应用程序的入口函数是WinMain,那是一个自定义的回调函数。其中APIENTRAV4Y是_stdcall的宏定义,表明WinMain函数选取的是Windows标准调用格局。

 

6.  用户创造窗口后,就要对窗口的行为承担。当Windows向程序发送消息时,它调用程序中的2个函数,这么些函数的参数精确地描述了Windows发送的新闻。在先后中称那些函数为窗口函数(Window
Procedure)或消息处理函数。它是一个自定义的回调函数。

 

7.  系统为应用程序传递全部的输入到它的一一窗口,各类窗口都关系2个窗口函数,每当那几个窗口有输入时,系统调用该函数。窗口函数处理输入,然后再将控制权交给系统。

 

8.  基于窗口界面包车型大巴Windows应用程序是事件驱动(event-driven)的。为了博取输入,它们并不做展现的函数调用,而是等待系统传递输入给它们。

 

9.  在桌面上呈现三个窗口的具体步骤(相当于主程序的协会流程):

        1)注册窗口类(RegisterClassEx);

        2)创造窗口(CreateWindowEx);

        3)在桌面彰显窗口(ShowWindow);

        4)更新窗口客户区(UpdateWindow);

        5)进入无限的音讯获得和拍卖的大循环。  首先是赢得新闻(GetMessage).假若有音信到达,则将新闻分派到回到函数进行处理(DispatchMessage)。假使消息是WM_QUIT,则GetMessage函数再次回到FALSE,整个音讯循环甘休。新闻具体的处理进程是在MainWndProc函数中开始展览的。

 

 

代码解释:

FirstWindow

  PS:那是1个最简易的窗口程序源代码,成效是弹出3个独立的Windows窗口。这个代码可作为未来用API写Windows程序的中坚框架。

 1 // 窗口学习01.cpp : Defines the entry point for the application.
 2 //
 3 
 4 #include "stdafx.h"
 5 LRESULT CALLBACK MainWndProc(HWND,UINT,WPARAM,LPARAM);
 6 int APIENTRY WinMain(HINSTANCE hInstance,
 7                      HINSTANCE hPrevInstance,
 8                      LPSTR     lpCmdLine,
 9                      int       nCmdShow)
10 {
11      // TODO: Place code here.
12     char szClassName[]="MainWClass";
13     WNDCLASSEX wndclass;
14     //用于描述主窗口的参数填充WNDCLASSEX结构
15     wndclass.cbSize=sizeof(wndclass);                    //结构的大小
16     wndclass.style=CS_HREDRAW|CS_VREDRAW;                //指定如果大小改变就重画
17     wndclass.lpfnWndProc=MainWndProc;                    //窗口函数指针
18     wndclass.cbClsExtra=0;                                //没有额外的类内存
19     wndclass.cbWndExtra=0;                                //没有额外的窗口内存;
20     wndclass.hInstance=hInstance;                        //实例句柄
21     wndclass.hIcon=::LoadIcon(NULL,IDI_APPLICATION);    //使用预定义图标
22     wndclass.hCursor=::LoadCursor(NULL,IDC_ARROW);        //使用预定义的光标
23     wndclass.hbrBackground=(HBRUSH)::GetStockObject(WHITE_BRUSH);    //使用白色背景画刷
24     wndclass.lpszMenuName=NULL;                            //不指定菜单
25     wndclass.lpszClassName=szClassName;                    //窗口类的名称
26     wndclass.hIconSm=NULL;                                //没有类的小图标
27     
28     //注册这个窗口类
29     ::RegisterClassEx(&wndclass);
30     
31     //创建主窗口
32     HWND hwnd=::CreateWindowEx(
33         0,                                              //dwExStyle,扩展样式
34         szClassName,                                    //lpClassName,类名
35         "My first Window!",                             //lpWindowName,标题
36         WS_OVERLAPPEDWINDOW,                            //dwStyle,窗口风格
37         CW_USEDEFAULT,                                  //X,初始X坐标
38         CW_USEDEFAULT,                                  //Y,初始Y坐标
39         CW_USEDEFAULT,                                  //nWidth,宽度
40         CW_USEDEFAULT,                                  //nHeight,高度
41         NULL,                                           //hWndParent,父窗口句柄
42         NULL,                                           //hMenu,菜单句柄
43         hInstance,                                      //hInstance,程序实例句柄
44         NULL);                                          //lpParam,用户数据
45         
46     if(hwnd==NULL)
47     {
48         ::MessageBox(NULL,"创建窗口出错!","error",MB_OK);
49         return -1;
50     }
51 
52     //显示窗口,刷新窗口客户区
53     ::ShowWindow(hwnd,nCmdShow);
54     ::UpdateWindow(hwnd);
55 
56     //从消息队列中取出消息,交给窗口函数处理,知道GetMessage返回FALSE,结束消息循环
57     MSG msg;
58     while(::GetMessage(&msg,NULL,0,0))
59     {
60         //转化键盘消息
61         ::TranslateMessage(&msg);
62         //将消息发送到相应的窗口函数
63         ::DispatchMessage(&msg);
64     }
65 
66     //当GetMessage返回FALSE时程序结束
67     return msg.wParam;
68 }
69 
70 LRESULT CALLBACK MainWndProc(HWND hwnd,UINT message,WPARAM wParam,LPARAM lParam)
71 {
72     char szText[]="最简单的窗口程序!";
73     switch(message)
74     {
75     case WM_PAINT:                //窗口客户区需要重画
76         {
77             HDC hdc;
78             PAINTSTRUCT ps;
79 
80             //使无效的客户区变得有效,并取得设备环境句柄
81             hdc=::BeginPaint(hwnd,&ps);
82             //显示文字
83             ::TextOut(hdc,10,10,szText,strlen(szText));
84             ::EndPaint(hwnd,&ps);
85             return 0;
86         }
87     case WM_DESTROY:            //正在销毁窗口
88 
89         //向消息队列投递一个WM_QUIT消息,促使GetMessage函数返回0,结束消息循环
90         ::PostQuitMessage(0);
91         return 0;
92     }
93 
94     //将我们不处理的消息交给系统做默认处理
95     return ::DefWindowProc(hwnd,message,wParam,lParam);
96 }

 

 

 程序分析:

1.  登记窗口类:

  注册窗口类的API函数是RegisterClassEx,最后的“Ex”是扩张的情致,因为它是Win16的RegisterClass函数的开始展览。3个窗口类定义了窗口的片段关键质量,如:图标、光标、背景象和承担处理音信的窗口函数等。这几个属性定义在WNDCLASSEX结构中。

 1 typedef struct_WNDCLASSEX{
 2     UINT cbSize;                        //WNDCLASSEX结构的大小
 3     UINT style;                         //从这个窗口类派生的窗口具有的风格
 4     WNDPROC lpfnWndProc;                //即 window procedure,窗口消息处理函数指针
 5     int cbClsExtra;                     //指定紧跟在窗口类结构后的附加字节数
 6     int cbWndExtra;                     //指定紧跟在窗口事例后的附加字节数
 7     HANDLE hInstance;                   //本模板的实例句柄
 8     HICON hIcon;                        //窗口左上角图标的句柄
 9     HCURSOR hCursor;                    //光标的句柄
10     HBRUSH hbrBackground;               //背景画刷的句柄
11     LPCTSTR lpszMenuName;               //菜单名
12     LPCTSTR lpszClassName;              //该窗口类的名称
13     HICON hIconSm;                      //小图标句柄
14 }WNDCLASSEX;

  PS:

  RegisterClassEx的绝无仅有参数是那个结构的地方。注册窗口类后就足以将类名和其窗口函数、类的风格及其余的类属性联系起来。当进程在CreateWindowEx函数中钦定1个类名的时候,系统就用这些窗口函数、风格和与此类名相关的任何属性创建窗口。

  主程序中CS_HREDRAW|CS_VREDRAW风格内定要是窗口客户区的宽窄或可观改变了,则重画这么些窗口。前缀CS_意为class
style,在WINUSEOdyssey.H中定义了全副可选样式。

  主程序中LoadIcon函数装载了一个预订义的图标(命名为IDI_APPLICATION),LoadCursor函数装载了一个预约义的光标(命名为IDC_A昂CoraROW)。假诺要装载自定义的图标或光标的话,应该先向工程中添加七个能源脚本(前边打字程序将会波及),然后再通过菜单命令“Insert/Resource…”添加那么些资源。

  WHITE_BRUSH是一个Windows预订义的画刷对象类型,GetStockObject函数取得那个画刷对象的句柄,传递给hbrBackground成员。我们也得以本身创建多个画刷对象,以便内定喜欢的颜料作为窗口的背景象。例如上面代码将窗口的背景观设为白灰色。

wndclass.hbrBackground=::CreateSolidBrush(RGB(0xa6,0xca,0xf0));            //创建一个纯色的刷子
......
::DeleteObject(wndclass.hbrBackground);                                    //最后别忘了删除创建的刷子,释放资源

  填充完WNDCLASSEX结构,就可以展开登记了。RegisterClassEx函数调用失利将回到0.

 

2.  创设窗口:

  要开创窗口,用注册的窗口类的类名调用CreateWindowEx函数即可。

 1 HWND hwnd=::CreateWindowEx(
 2                 0,                                        //dwExStyle,拓展样式
 3                 szClassName,                              //lpClassName,类名
 4                 "My first Window!",                       //lpWindowName,标题
 5                 WS_OVERLAPPEDWINDOW,                      //dwStyle,窗口风格
 6                 CW_USEDEFAULT,                            //X,初始X坐标
 7                 CW_USEDEFAULT,                            //Y,初始Y坐标
 8                 CW_USEDEFAULT,                            //nWidth,宽度
 9                 CW_USEDEFAULT,                            //nHeight,高度
10                 NULL,                                     //hWndParent,父窗口句柄
11                 NULL,                                     //hMenu,菜单句柄
12                 hInstance,                                //hInstance,程序实例句柄
13                 NULL);                                    //lpParam,用户数据
14        

  PS:

  函数调用成功将回来窗口句柄,战败重返NULL。第5个参数dwStyle的值是WS_OVE科雷傲LAPPEDWINDOW,即重叠式窗口(Overlapped
Window)。由它钦命的窗口有题目栏、系统菜单、可以改变大小的边框,以及最大化、最小化和倒闭按钮。这几个三个规范窗口的体裁。

  上边列出部分宽广风格的概念,它们是以WS(Windows
Style的缩写)为前缀的预订义的值。

    • WS_BO奥迪Q5DERAV4  创立三个单边框的窗口
    • WS_CAPTION    创造3个有标题框的窗口(包涵WS_BODER风格)
    • WS_CHIlD  成立几个子窗口。那些风格不可能与WS_POPVP风格合用
    • WS_DISABLED  成立八个开始状态为禁止的子窗口。2个禁止状态的窗口不能够承受来自用户的输入音讯
    • WS_DLGFRAME  创制贰个带对话框边框风格的窗口。这种风格的窗口无法带标题条
    • WS_HSCROLL  成立一个有档次滚动条的窗口
    • WS_VSCROLL  成立3个有垂直滚动条的窗口
    • WS_ICONIC  创造2个方始状态为最小化状态的窗口。与WS_MINIMIZE风格一模一样
    • WS_MAXIMIZE  创造3个颇具最大化按钮的窗口。该风格无法喝WS_EX_CONTEXTHELP风格同时出现,同时务必钦赐WS_SYSMENU风格。
    • WS_THICKFRAME  创制1个可调边框的窗口,与WS_SIZEBOX风格一模一样
    • WS_VISIBLE  创制一个初步状态为可知的窗口

     等等。

 

3.  在桌面展现窗口:

1 ::ShowWindow(hwnd,nCmdShow);

  PS:

  ShowWindow函数用于安装内定窗口的呈现状态,上边代码中的nCmdShow是系统传递给WinMain函数的参数。函数的第三个参数能够有五个不相同的取值(具体情形请索引查看SDK文书档案),例如上边包车型地铁代码将躲藏句柄hWnd钦赐的窗口。

::ShowWindow(hWnd,SW_HIDE);            //nCmdShow参数的取值可以是SW_SHOW、SW_HIDE、SW_MINIMIZE等

 

 4.  更新窗口客户区:

1 ::UpdateWindow(hwnd);

  PS:

  假使钦赐窗口的换代区域不为空的话,UpdateWindow函数通过向那一个窗口发送三个WM_PAINT新闻更新它的客户区。当窗口呈未来显示屏上时,窗口的客户区被在WNDCLASSEX中钦定的刷子擦去了,调用UpdateWindow函数将促使客户区重画,以体现其情节。

 

5.  进入无限的音讯循环:

  程序上边将跻身无限的巡回中。在调用UpdateWindow函数之后,整个窗口已经显得在桌面上,程序必须准备从用户接受键盘和鼠标输入了。Windows为每一个线程维护了一个新闻队列,每当有3个输入发生,Windows就把用户的输入翻译成新闻放在音信队列中。利用GetMessage函数能够从调用线程的音讯队列中取出2个音信来填充MSG结构。

1 ::GetMessage(&msg,NULL,0,0);

  PS:

  假使新闻队列中平昔不音信(即没有用户输入),这一个函数会一向等待下去,知道有音讯进入到新闻队列截止。msg是四个MSG结构类型的变量,那一个布局定义了新闻的具备属性。

typedef struct tagMSG {
    HWND hwnd;                   //消息要发送的窗口句柄
    UINT message;                //消息标识符,以WM_开头的预定义值(意为Window Message)
    WPARAM wParam;               //消息的参数之一
    LPARAM lParam;               //消息的参数之二
    DWORD time                   //消息放入消息队列的时间
    POINT pt;                    //这是一个POINT数据结构,表示消息放入消息队列时的鼠标位置
}MSG,*PMSG;

  GetMessage函数从新闻队列中拿走的音讯一经不是WM_QUIT,则赶回非零值。一个WM_QUIT音信会促使GetMessage函数重回0,从而甘休音信循环。

::TranslateMessage(&msg);

  此调用把键盘输入翻译成为可传递的新闻。

::DispatchMessage(&msg);

  DispatchMessage函数分发三个新闻到对应窗口的窗口函数。在上头的例证中,窗口函数是MainWndProc。MainWndProc处理信息后把控制权交给Windows,此时DispatchMessage函数仍旧持续工作,当它回到时,信息循环队列从调用Getmessage函数开首进入下一轮循环。

澳门金沙国际, 

 *6.  拍卖新闻:

  新闻处理函数接收到的拥有音讯都被标识为二个数字,这正是MainWndProc的第四个参数uMsg。这个数字在WINUSELacrosse.H文件中都以以WM_为前缀定义的。

  平日Windows程序设计者用一个switch和case结构来控制音讯处理函数收到了怎么信息,以及怎么样处理那些音讯。全体消息处理函数不处理的消息都必须传给1个名为DefWindowProc的函数让Windows做默许处理,从DefWindowProc函数重回的值也亟须从音讯处理函数重返。

 1 switch(uMsg)
 2 {
 3 case WM_PAINT:
 4     /*处理WM_PAINT消息*/
 5     return 0;
 6 
 7 case WM_DESTROY:
 8     /*处理WM_DESTROY消息*/
 9     return 0;
10 
11 }
12 return ::DefWindowProc(hwnd,message,wParam,lParam);

  PS:

  必供给把装有不处理的音讯交给DefWindowProc函数处理,也要把它的再次回到值再次回到给Windows,不然Windows就错过了与应用程序通讯的路径,也就不能够再决定窗口的行为了,那是违法的。

  WM_PAINT新闻文告应用程序窗口客户区有一块只怕全部变为无效,必须刷新。那表示窗口客户区的内容必须被重画。客户区在以下情状会化为无效:

    1)当窗口第2回被成立时,整个客户区是无用的,因为还没有向上面画任王孝文西。

      第一个WM_PAINT音信被发送到窗口处理函数时,程序有机会向客户区画一些事物。

    2)当改变窗口大小的时候,客户区编制程序无效。

      用户在填写WNDCLASSEX结构的style成员时,将它设置为CS_HREDRAW和CS_VREDRAW,那就径直造成在改变窗口大小时Windows将总体窗口变为无效。

    3)最小化窗口,再将它过来到此前大小时,Windows没有保留整个客户区的始末。

      在图片操作系统下,须求保留的数量太多了。同样地,Windows使这些窗口无效,窗口处理函数就会吸收贰个WM_PAINT音信,本身背负回复客户区内容。

    4)当围着显示器移动窗口,直到窗口被遮盖时,Windows并不曾保留被掩盖的区域。

      这么些区域再次展现时,它就被标识为无效。窗口处理函数会收到多个WM_PAINT新闻来重画窗口的剧情。

  处理WM_PAINT新闻时连连以调用BeginPaint函数伊始。

hdc=::BeginPaint(hwnd,&ps);
//以一个EndPaint函数调用结束
::EndPaint(hwnd,&ps);

  这三个函数中,第1个参数是窗口句柄,第三个参数是指向PAINTSTRUCT结构的指正,这些结构包蕴部分得以在重画客户区时采纳的新闻。

  在调用BeginPaint函数的时候,假若客户区的背景还并未被擦掉的话,Windows将擦除它,擦除背景时利用的刷子由WNDCLASSEX结构的hbrBackground成员钦点。对BeginPain函数的调用将使全部客户区有效,然后再次回到设备条件句柄。在窗口的客户区显示图形和文字时,须要动用这么些装置条件句柄。EndPaint函数负责释放设备条件句柄,使它变得不在能应用。DefWindowProc函数会通过调用BeginPaint和EndPaint函数使客户区有效。

  调用BeginPaint函数后,主程序中调用了TextOut函数。

1 ::TextOut(hdc,10,10,szText,strlen(szText));

  此函数用于在hdc内定的配备(那里是
显示屏)上彰显文字。(10,10)为坐标地点,szText为要展现的文字,strlen(szText)语句总计出了文本占用的字节数。

  每当客户区变成无效,新闻处理函数WndProc都会接收三个洗呢WM_PAINT新闻。响应此音信的代码取得设备条件句柄后,再一遍将szText的剧情映今后钦赐地方。

  WM_DESTROY是窗口函数必须处理的音信。当用户关闭窗口,而且此窗口已经响应了用户的伸手正在关闭时,音讯处理函数就会收下八个WM_DESTROY新闻。当接受到这一个音讯的时候,表明窗口正在销毁。MainWndProc函数调用PostQuitMessage函数来响应此新闻。

1 ::PostQuitMessage(0);

  那么些函数向程序的新闻队列中插入叁个WM_QUIT音讯。GetMessage函数假若从音讯队列中收获的音讯是WM_QUIT,它将重回0,从而促使WinMain函数离开消息循环,然后应用程序执行以下代码。

1 //当GetMessage返回0时程序结束
2 return msg.wParam;

  此时,msg.wParam的值是传给PostQuitMessage函数的参数的值。return语句将使WinMain函数重返,程序运转停止。

Windows图形界面,第④章图形界面
学习《Windows程序设计》记录 概念贴士: 1.
每一种GUI应用程序至少应当创设3个窗口,称为主窗口,…

学学《Windows程序设计》记录

Visual
C++它大约能够分成四个关键的局地:

 

 

3. Platform SDK。那才是Visual C++和全部Visual
Studio的精华和灵魂,就算大家很少能一向触及到它。大概说来,Platform
SDK是以Microsoft C/C++编写翻译器为宗旨(不是Visual
C++,看掌握了),合作MASM,辅以其它部分工具和文书档案资料。上边说到Developer
Studio没有编写翻译程序的机能,那么那项工作是由什么人来完毕的吗?是CL,是NMAKE,和其余许许多多命令行程序,这么些我们看不到的先后才是结合Visual
Studio的基石。

概念贴士:

概念贴士:

2. MFC。从理论上来讲,MFC也不是专用于Visual C++,Borland
C++,C++Builder和Symantec C++同样能够处理MFC。同时,用Visual
C++编写代码也并不代表一定要用MFC,只要愿意,用Visual
C++来编排SDK程序,只怕采纳STL,ATL,一样没有限定。不过,Visual
C++本来就是为MFC塑造的,Visual
C++中的许多特点和言语扩充也是为MFC而设计的,所以用Visual
C++而不用MFC就十二分吐弃了Visual C++中一点都不小的一片段效率。不过,Visual
C++也不对等MFC。

1.  各样GUI应用程序至少应当创制一个窗口,称为主窗口,它看做用户与应用程序间的主界面来提供劳动。超过一半应用程序也直接或间接地创设别的窗口,来成功与主窗口相关的行事。

1.  各个GUI应用程序至少应当创立四个窗口,称为主窗口,它作为用户与应用程序间的主界面来提供劳务。超过半数应用程序也一向或直接地创造其余窗口,来成功与主窗口相关的劳作。

1. Developer
Studio,那是1个并入开发条件,我们不乏先例工作的99%都以在它上边完毕的,再拉长它的标题赫然写着“Microsoft
Visual C++”,所以众多个人理所当然的以为,那正是Visual
C++了。其实否则,即使Developer
Studio提供了多少个很好的编辑器和许多Wizard,但实则它从不其它编写翻译和链接程序的效应,真正完结那几个工作的幕后英豪后边会介绍。大家也清楚,Developer
Studio并不是专门用来VC的,它也一律用于VB,VJ,VID等Visual
Studio家族的别样同胞兄弟。所以不用把Developer Studio当成Visual C++,
它最四只是Visual C++的3个壳子而已。那或多或少请记住!

 

 

Visual C++6.0不仅是3个C++
编译器,而且是叁个基于Windows操作系统的可视化集成开发环境(integrated
development environment,IDE)。Visual
C++6.0由众多零部件组成,包含编辑器、调节和测试器以及程序向导AppWizard、类向导Class
Wizard等开发工具。 那么些组件通过2个名为Developer
Studio的零件集成为和谐的付出环境。

2.  应用程序的主窗口包含题目栏、菜单栏、Windows系统菜单、最小化按钮、最大化按钮、回复按钮、关闭按钮、可转移大小的边框、窗口客户区、垂直滚动条和程度滚动条。

2.  应用程序的主窗口包蕴标题栏、菜单栏、Windows系统菜单、最小化按钮、最大化按钮、回复按钮、关闭按钮、可转移大小的边框、窗口客户区、垂直滚动条和品位滚动条。

Visual C++
6.0,简称VC可能VC6.0,是微软推出的一款C++编写翻译器,将“高级语言”翻译为“机器语言(低级语言)”的先后。Visual
C++是二个功用强大的可视化软件开发工具。自一九九四年Microsoft集团推出Visual
C++1.0后,随着其新本子的无休止问世,Visual
C++已变成标准程序员进行软件开发的首要选拔工具。即便微软公司生产了 Visual
C++.NET(Visual C++7.0),但它的应用的相当的大的局限性,只适用于Windows
2000、Windows XP和Windows NT4.0。所以实际中,越来越多的是以Visual
C++6.0为平台。

 

 

1.接纳VC++6.0编写翻译C语言文件(.c)

#include <stdio.h>

int main(int argc, char** argv)
{
    printf("Hello World!");
    getch();
    return 0;
}

 澳门金沙国际 1

澳门金沙国际 2

澳门金沙国际 3

澳门金沙国际 4

 

3.  VC++6.0创制GUI程序:  1)创制VC++6.0,选用命令“文件”,点击“新建”;

3.  VC++6.0创制GUI程序:  1)创制VC++6.0,采取命令“文件”,点击“新建”;

2.应用VC++6.0成立MFC对话框程序

 澳门金沙国际 5

澳门金沙国际 6

澳门金沙国际 7

澳门金沙国际 8

澳门金沙国际 9

 

                2)选择“工程”,点击“Win32
Application”选项;

                2)选择“工程”,点击“Win32
Application”选项;

3.选择API创制Win32窗口不难讲解

int APIENTKoleosY WinMain(HINSTANCE hInstance,  //  本模块的实例句柄 

                                          HINSTANCE hPrevInstance,  //
Win16 留下的废品,未来一度毫无了 

                                          LPST路虎极光 lpCmdLine,    //
 命令行参数 

                                          int nCmdShow)      //
 主窗口开端化时的突显方式 

{  //  下面那行代码是本人添加的,用于弹出三个小对话框 

  ::MessageBox(NULL, “Hello, Win32 Application”, “04Win32AppDemo”,
MB_OK); 

  return 0; 

APIENTRY是__stdcall的宏定义,表达 WinMain 函数选用的是 Windows
标准调用格局。

hInstance 钦定了现阶段模块的实例句柄。其实在 Win32 下,模块的实例句柄和模块句

柄是一样的,只是说法不一致,所以可以经过以下语句得到当前可实施模块的实例句柄。 

hInstance = ( HINSTANCE )GetModuleHandle(NULL);  //
 取得应用程序的实例句柄(即模块句柄) 

GetModuleHandle
函数的无比参数是模块的名目,函数会回来这些模块的句柄。模块句柄

的值就是该模块在内部存款和储蓄器中的首地址。假设为 GetModuleHandle 传递 NULL
的话,函数重回的

是可执行文件所在模块的模块句柄,而不论是是在哪个模块中做这些调用的。 

 lpCmdLine 是命令行参数。其值由 CreateProcess
函数的第3个参数钦赐。平时应用程

序在初阶化时检查这几个参数,以控制是或不是打开特定文书档案。 

 nCmdShow 钦赐了窗口开首化时的突显格局。这么些值也是由 CreateProcess
函数字传送递

的。一般以这一个值为参数调用 ShowWindow
就足以了,此函数用于安装窗口的来得状态,

 

LRESULT CALLBACK WindowProc(HWND hwnd, UINT uMsg, WPARAM wParam, LPARAM
lParam); 

CALLBACK 宏是__stdcall 的意思,表达选择 Windows 标准方法传递参数。hWnd
参数标

识了新闻到达的窗口;uMsg  参数是3个被取名的常量(音讯 ID
号),它钦赐了所发的新闻,

当窗口函数接受到音信时,它利用音信 ID 号来决定哪些处理那么些信息;wParam
和 lParam 是

新闻的七个参数,其值取决于 uMsg。 

 

//  窗口函数的函数原形 

LRESULT CALLBACK MainWndProc(HWND, UINT, WPARAM, LPARAM); 

int APIENTRY WinMain(HINSTANCE hInstance, 

第⑤章图形界面,Windows图形界面。                                          HINSTANCE hPrevInstance, 

                                          LPSTR          lpCmdLine, 

                                          int              nCmdShow) 

{  char szClassName[] = “MainWClass”;   

  WNDCLASSEX wndclass; 

  //  用描述主窗口的参数填充 WNDCLASSEX 结构 

  wndclass.cbSize = sizeof(wndclass);        //  结构的大小 

  wndclass.style = CS_HREDRAW|CS_VREDRAW;  //  钦命假设大小改变就重画 

  wndclass.lpfnWndProc = MainWndProc;      //  窗口函数指针 

  wndclass.cbClsExtra = 0;          //  没有额外的类内存 

  wndclass.cbWndExtra = 0;          //  没有额外的窗口内部存款和储蓄器 

  wndclass.hInstance = hInstance;        //  实例句柄   

  wndclass.hIcon = ::LoadIcon(NULL,    IDI_APPLICATION);       //
 使用预订义图标 

  wndclass.hCursor = ::LoadCursor(NULL, IDC_A凯雷德ROW);        //
 使用预约义的光标 

  wndclass.hbrBackground = (HBRUSH)::GetStockObject(WHITE_BRUSH);  //
 使用浅豆绿背景画刷 

  wndclass.lpszMenuName = NULL;        //  不点名菜单 

  wndclass.lpszClassName = szClassName ;      //  窗口类的名目   

  wndclass.hIconSm = NULL;          //  没有类的小图标 

  //  注册那个窗口类 

  ::RegisterClassEx(&wndclass); 

  //  创立主窗口 

  HWND hwnd = ::CreateWindowEx(   

    0,            // dwExStyle,扩大样式   

    szClassName,        // lpClassName,类名       

    “My first Window!”,      // lpWindowName,标题     

    WS_OVEPAJEROLAPPEDWINDOW,  // dwStyle,窗口作风   

    CW_USEDEFAULT,      // X,初始  X  坐标     

    CW_USEDEFAULT,      // Y,初始  Y  坐标     

    CW_USEDEFAULT,      // nWidth,宽度       

    CW_USEDEFAULT,      // nHeight,高度       

    NULL,          // hWndParent,父窗口句柄       

    NULL,          // hMenu,菜单句柄     

    hInstance,          // hlnstance,程序实例句柄     

    NULL) ;          // lpParam,用户数据       

  if(hwnd == NULL) 

  {  ::MessageBox(NULL, “创设窗口出错!”, “error”, MB_OK); 

    return -1; 

  } 

  //  呈现窗口,刷新窗口客户区 

  ::ShowWindow(hwnd, nCmdShow); 

  ::UpdateWindow(hwnd); 

  //  从音信队列中取出新闻,交给窗口函数处理,直到 GetMessage 再次回到FALSE,甘休新闻循环 

  MSG msg;   

  while(::GetMessage(&msg, NULL, 0, 0)) 

  {  //  转化键盘音讯 

    ::TranslateMessage(&msg); 

    //  将音信发送到相应的窗口函数 

    ::DispatchMessage(&msg); 

  } 

  //  当 GetMessage 重临 FALSE 时先后甘休 

  return msg.wParam; 

LRESULT CALLBACK MainWndProc (HWND hwnd, UINT message, WPARAM wParam,
LPARAM lParam) 

{  char szText[] = “最简便的窗口程序!”; 

  switch (message) 

  {       

  case WM_PAINT: //  窗口客户区供给重画 

    {  HDC hdc; 

      PAINTSTRUCT ps; 

      //  使无效的客户区变的管用,并赢得设备条件句柄 

      hdc = ::BeginPaint (hwnd, &ps) ;   

      //  展现文字 

      ::TextOut(hdc, 10, 10, szText, strlen(szText)); 

      ::EndPaint(hwnd, &ps); 

      return 0; 

    }   

  case WM_DESTROY: //  正在销毁窗口 

    //  向消息队列投递三个 WM_QUIT 音讯,促使 GetMessage 函数重返0,截止音信循环 

    ::PostQuitMessage(0) ; 

    return 0 ; 

  } 

  //  将我们不处理的新闻交给系统做暗中同意处理 

  return ::DefWindowProc(hwnd, message, wParam, lParam); 

剖析以上程序,可以得出在桌面上呈现一个窗口的具体步骤,那就是主程序的布局流程。 

(1)注册窗口类(RegisterClassEx) 

(2)成立窗口(CreateWindowEx) 

(3)在桌面呈现窗口(ShowWindow) 

(4)更新窗口客户区(UpdateWindow) 

(5)进入无限的新闻获得和处理的轮回。首先是赢得音讯(GetMessage),若是有消息到

达,则将音信分派到回调函数处理(DispatchMessage),要是新闻是
WM_QUIT,则 GetMessage

函数重临 FALSE,整个音信循环甘休。音讯具体的处理进度是在 MainWndProc
函数中开展的。 

 

1.挂号窗口类 

typedef struct _WNDCLASSEX {     

  UINT cbSize;          // WNDCLASSEX  结构的大小 

          UINT style;        //  从那一个窗口类派生的窗口具有的风格 

          WNDPROC lpfnWndProc;    //  即  window procedure,  
 窗口音讯处理函数指针 

          int cbClsExtra;          //
 钦点紧跟在窗口类协会后的增大字节数 

          int cbWndExtra;        //  钦定紧跟在窗口事例后的增大字节数 

          HANDLE hInstance;      //  本模块的实例句柄 

          HICON hIcon;        //  窗口左上角图标的句柄 

          HCU福特ExplorerSO牧马人 hCursor;      //  光标的句柄 

          HBRUSH hbrBackground;  //  背景画刷的句柄 

          LPCTSTR lpszMenuName;    //  菜单名 

          LPCTSTXC60 lpszClassName;      //  该窗口类的名称 

          HICON hIconSm;       //  小图标句柄   

} WNDCLASSEX; 

 

2.成立窗口 

HWND hwnd = ::CreateWindowEx(   

  0,            // dwExStyle,扩大样式   

  szClassName,        // lpClassName,类名       

  “My first Window!”,      // lpWindowName,标题     

  WS_OVEOdysseyLAPPEDWINDOW,  // dwStyle,窗口作风   

  CW_USEDEFAULT,      // X,初始  X  坐标     

  CW_USEDEFAULT,      // Y,初始  Y  坐标     

  CW_USEDEFAULT,      // nWidth,宽度       

  CW_USEDEFAULT,      // nHeight,高度       

  NULL,          // hWndParent,父窗口句柄   

  NULL,          // hMenu,菜单句柄     

  hInstance,          // hlnstance,程序实例句柄     

  NULL) ;          // lpParam,用户数据     

下边列出了一些普遍风格的概念,它们是以 WS(Windows  Style
的缩写)为前缀的约定

义的值: 

 WS_BORAV4DECRUISER    成立一个单边框的窗口 

 WS_CAPTION    创设2个有标题框的窗口(包含 WS_BODER 风格) 

 WS_CHIlD    创设2个子窗口。这些风格不可能与 WS_POPVP 风格合用 

 WS_DISABLED  
创造3个上马状态为禁止的子窗口。三个禁止状态的窗日无法经受来自用户

            的输人音讯 

 WS_DLGFRAME
 创立一个带对话框边框风格的窗口。这种风格的窗口不能够带标题条 

 WS_HSCROLL    创造八个有程度滚动条的窗口 

 WS_VSCROLL    创设3个有垂直滚动条的窗口 

 WS_ICONIC    创制三个开始状态为最小化状态的窗口。与 WS_MINIMIZE
风格相同 

 WS_MAXIMIZE  成立一个有着最大化按钮的窗口。该风格不可能和
WS_EX_CONTEXTHELP 风

            格同时出现,同时务必钦定 WS_SYSMENU 风格 

 WS_OVE卡宴LAPPED
 产生3个层叠的窗口。1个层叠的窗口有三个标题条和三个边框。与  

            WS_TILED 风格相同 

 WS_OVEOdysseyLAPPEDWINDOW  成立1个持有 WS_OVERLAPPED,WS_CAPTION,    

                WS_SYSMENU  ,WS_THICKFRAME,WS_MINIMIZEBOX, 

                WS_MAXMIZEBOX 风格的层叠窗口 

 WS_POPUP        创设二个弹出式窗口。该风格不可能与 WS_CHLD
风格同时接纳 

 WS_POPUPWINDOW    创制3个全体 WS_BORDER,WS_POPUP,WS_SYSMENU
风格的

                窗口,WS_CAPTION 和 WS_POPUPWINDOW 必须同时设定才能

                使窗口某单可知 

 WS_SIZEBOX        创立1个可调边框的窗口,与 WS_THICKFRAME 风格相同 

 WS_SYSMENU       创立三个在题目条上含蓄窗口菜单的窗口,必须同时设定   

                WS_CAPTION 风格 

 WS_THICKFRAME      创立一个全体可调边框的窗口,与 WS_SIZEBOX
风格相同 

 WS_VISIBLE              创造1个开端状态为可知的窗口 

 

typedef struct tagMSG { 

        HWND hwnd;    //  新闻要发向的窗口句柄 

        UINT message;      //  消息标识符,以 WM_  开首的约定义值(意为
Window Message) 

        WPARAM wParam;        //  消息的参数之一 

        LPARAM lParam;    //  新闻的参数之二 

        DWO福特ExplorerD time;      //  音讯放入音讯队列的岁月 

        POINT pt;        //  那是三个 POINT
 数据结构,表示信息放入音信队列时的鼠标地点 

  } MSG, *PMSG ; 

 

                3)输入工程名、存放路径;

                3)输入工程名、存放路径;

                4)点击OK按钮,采用第②项“三个简易Win32应用程序”;

                4)点击OK按钮,选取第3项“多少个差不离Win32应用程序”;

                5)点击“实现”按钮,完结GUI程序工程创制。

                5)点击“完结”按钮,完毕GUI程序工程制造。

 

 

4.  Win32主次的入口函数将是WinMain函数,而不是控制台程序的main函数。

4.  Win32主次的入口函数将是WinMain函数,而不是控制台程序的main函数。

 

 

5.  GUI应用程序的入口函数是WinMain,那是二个自定义的回调函数。当中APIENTQX56Y是_stdcall的宏定义,表明WinMain函数选用的是Windows标准调用形式。

5.  GUI应用程序的入口函数是WinMain,那是一个自定义的回调函数。当中APIENT酷威Y是_stdcall的宏定义,表达WinMain函数采取的是Windows标准调用方式。

 

 

6.  用户成立窗口后,就要对窗口的作为负责。当Windows向程序发送音信时,它调用程序中的一个函数,这几个函数的参数精确地讲述了Windows发送的音讯。在先后中称这几个函数为窗口函数(Window
Procedure)或音信处理函数。它是三个自定义的回调函数。

6.  用户创设窗口后,就要对窗口的行事承担。当Windows向程序发送音信时,它调用程序中的一个函数,那个函数的参数精确地描述了Windows发送的消息。在程序中称那一个函数为窗口函数(Window
Procedure)或音讯处理函数。它是一个自定义的回调函数。

 

 

7.  系统为应用程序传递全体的输入到它的逐一窗口,每种窗口都关系1个窗口函数,每当那个窗口有输入时,系统调用该函数。窗口函数处理输入,然后再将控制权交给系统。

7.  系统为应用程序传递全体的输入到它的逐条窗口,每一种窗口都提到四个窗口函数,每当那些窗口有输入时,系统调用该函数。窗口函数处理输入,然后再将控制权交给系统。

 

 

8.  基于窗口界面包车型客车Windows应用程序是事件驱动(event-driven)的。为了取得输入,它们并不做呈现的函数调用,而是等待系统传递输入给它们。

8.  基于窗口界面包车型大巴Windows应用程序是事件驱动(event-driven)的。为了拿走输入,它们并不做体现的函数调用,而是等待系统传递输入给它们。

 

 

9.  在桌面上呈现三个窗口的具体步骤(也便是主程序的结构流程):

9.  在桌面上呈现二个窗口的具体步骤(也正是主程序的结构流程):

        1)注册窗口类(RegisterClassEx);

        1)注册窗口类(RegisterClassEx);

        2)成立窗口(CreateWindowEx);

        2)创立窗口(CreateWindowEx);

        3)在桌面展现窗口(ShowWindow);

        3)在桌面呈现窗口(ShowWindow);

        4)更新窗口客户区(UpdateWindow);

        4)更新窗口客户区(UpdateWindow);

        5)进入无限的音信获得和拍卖的大循环。  首先是获打消息(GetMessage).即便有音信到达,则将消息分派到回到函数实行拍卖(DispatchMessage)。倘若音信是WM_QUIT,则GetMessage函数重返FALSE,整个音信循环甘休。音信具体的处理进程是在MainWndProc函数中实行的。

        5)进入无限的音讯获得和处理的循环。  首先是取得音信(GetMessage).倘使有音讯到达,则将消息分派到回到函数进行拍卖(DispatchMessage)。若是音讯是WM_QUIT,则GetMessage函数重临FALSE,整个音讯循环截止。音信具体的处理进程是在MainWndProc函数中展开的。

 

 

 

 

代码解释:

代码解释:

FirstWindow

FirstWindow

  PS:那是3个最简单易行的窗口程序源代码,效率是弹出三个名列三甲的Windows窗口。这个代码可视作将来用API写Windows程序的主干框架。

  PS:这是四个最简便易行的窗口程序源代码,作用是弹出三个金榜题名的Windows窗口。这么些代码可作为今后用API写Windows程序的主导框架。

 1 // 窗口学习01.cpp : Defines the entry point for the application.
 2 //
 3 
 4 #include "stdafx.h"
 5 LRESULT CALLBACK MainWndProc(HWND,UINT,WPARAM,LPARAM);
 6 int APIENTRY WinMain(HINSTANCE hInstance,
 7                      HINSTANCE hPrevInstance,
 8                      LPSTR     lpCmdLine,
 9                      int       nCmdShow)
10 {
11      // TODO: Place code here.
12     char szClassName[]="MainWClass";
13     WNDCLASSEX wndclass;
14     //用于描述主窗口的参数填充WNDCLASSEX结构
15     wndclass.cbSize=sizeof(wndclass);                    //结构的大小
16     wndclass.style=CS_HREDRAW|CS_VREDRAW;                //指定如果大小改变就重画
17     wndclass.lpfnWndProc=MainWndProc;                    //窗口函数指针
18     wndclass.cbClsExtra=0;                                //没有额外的类内存
19     wndclass.cbWndExtra=0;                                //没有额外的窗口内存;
20     wndclass.hInstance=hInstance;                        //实例句柄
21     wndclass.hIcon=::LoadIcon(NULL,IDI_APPLICATION);    //使用预定义图标
22     wndclass.hCursor=::LoadCursor(NULL,IDC_ARROW);        //使用预定义的光标
23     wndclass.hbrBackground=(HBRUSH)::GetStockObject(WHITE_BRUSH);    //使用白色背景画刷
24     wndclass.lpszMenuName=NULL;                            //不指定菜单
25     wndclass.lpszClassName=szClassName;                    //窗口类的名称
26     wndclass.hIconSm=NULL;                                //没有类的小图标
27     
28     //注册这个窗口类
29     ::RegisterClassEx(&wndclass);
30     
31     //创建主窗口
32     HWND hwnd=::CreateWindowEx(
33         0,                                              //dwExStyle,扩展样式
34         szClassName,                                    //lpClassName,类名
35         "My first Window!",                             //lpWindowName,标题
36         WS_OVERLAPPEDWINDOW,                            //dwStyle,窗口风格
37         CW_USEDEFAULT,                                  //X,初始X坐标
38         CW_USEDEFAULT,                                  //Y,初始Y坐标
39         CW_USEDEFAULT,                                  //nWidth,宽度
40         CW_USEDEFAULT,                                  //nHeight,高度
41         NULL,                                           //hWndParent,父窗口句柄
42         NULL,                                           //hMenu,菜单句柄
43         hInstance,                                      //hInstance,程序实例句柄
44         NULL);                                          //lpParam,用户数据
45         
46     if(hwnd==NULL)
47     {
48         ::MessageBox(NULL,"创建窗口出错!","error",MB_OK);
49         return -1;
50     }
51 
52     //显示窗口,刷新窗口客户区
53     ::ShowWindow(hwnd,nCmdShow);
54     ::UpdateWindow(hwnd);
55 
56     //从消息队列中取出消息,交给窗口函数处理,知道GetMessage返回FALSE,结束消息循环
57     MSG msg;
58     while(::GetMessage(&msg,NULL,0,0))
59     {
60         //转化键盘消息
61         ::TranslateMessage(&msg);
62         //将消息发送到相应的窗口函数
63         ::DispatchMessage(&msg);
64     }
65 
66     //当GetMessage返回FALSE时程序结束
67     return msg.wParam;
68 }
69 
70 LRESULT CALLBACK MainWndProc(HWND hwnd,UINT message,WPARAM wParam,LPARAM lParam)
71 {
72     char szText[]="最简单的窗口程序!";
73     switch(message)
74     {
75     case WM_PAINT:                //窗口客户区需要重画
76         {
77             HDC hdc;
78             PAINTSTRUCT ps;
79 
80             //使无效的客户区变得有效,并取得设备环境句柄
81             hdc=::BeginPaint(hwnd,&ps);
82             //显示文字
83             ::TextOut(hdc,10,10,szText,strlen(szText));
84             ::EndPaint(hwnd,&ps);
85             return 0;
86         }
87     case WM_DESTROY:            //正在销毁窗口
88 
89         //向消息队列投递一个WM_QUIT消息,促使GetMessage函数返回0,结束消息循环
90         ::PostQuitMessage(0);
91         return 0;
92     }
93 
94     //将我们不处理的消息交给系统做默认处理
95     return ::DefWindowProc(hwnd,message,wParam,lParam);
96 }
 1 // 窗口学习01.cpp : Defines the entry point for the application.
 2 //
 3 
 4 #include "stdafx.h"
 5 LRESULT CALLBACK MainWndProc(HWND,UINT,WPARAM,LPARAM);
 6 int APIENTRY WinMain(HINSTANCE hInstance,
 7                      HINSTANCE hPrevInstance,
 8                      LPSTR     lpCmdLine,
 9                      int       nCmdShow)
10 {
11      // TODO: Place code here.
12     char szClassName[]="MainWClass";
13     WNDCLASSEX wndclass;
14     //用于描述主窗口的参数填充WNDCLASSEX结构
15     wndclass.cbSize=sizeof(wndclass);                    //结构的大小
16     wndclass.style=CS_HREDRAW|CS_VREDRAW;                //指定如果大小改变就重画
17     wndclass.lpfnWndProc=MainWndProc;                    //窗口函数指针
18     wndclass.cbClsExtra=0;                                //没有额外的类内存
19     wndclass.cbWndExtra=0;                                //没有额外的窗口内存;
20     wndclass.hInstance=hInstance;                        //实例句柄
21     wndclass.hIcon=::LoadIcon(NULL,IDI_APPLICATION);    //使用预定义图标
22     wndclass.hCursor=::LoadCursor(NULL,IDC_ARROW);        //使用预定义的光标
23     wndclass.hbrBackground=(HBRUSH)::GetStockObject(WHITE_BRUSH);    //使用白色背景画刷
24     wndclass.lpszMenuName=NULL;                            //不指定菜单
25     wndclass.lpszClassName=szClassName;                    //窗口类的名称
26     wndclass.hIconSm=NULL;                                //没有类的小图标
27     
28     //注册这个窗口类
29     ::RegisterClassEx(&wndclass);
30     
31     //创建主窗口
32     HWND hwnd=::CreateWindowEx(
33         0,                                              //dwExStyle,扩展样式
34         szClassName,                                    //lpClassName,类名
35         "My first Window!",                             //lpWindowName,标题
36         WS_OVERLAPPEDWINDOW,                            //dwStyle,窗口风格
37         CW_USEDEFAULT,                                  //X,初始X坐标
38         CW_USEDEFAULT,                                  //Y,初始Y坐标
39         CW_USEDEFAULT,                                  //nWidth,宽度
40         CW_USEDEFAULT,                                  //nHeight,高度
41         NULL,                                           //hWndParent,父窗口句柄
42         NULL,                                           //hMenu,菜单句柄
43         hInstance,                                      //hInstance,程序实例句柄
44         NULL);                                          //lpParam,用户数据
45         
46     if(hwnd==NULL)
47     {
48         ::MessageBox(NULL,"创建窗口出错!","error",MB_OK);
49         return -1;
50     }
51 
52     //显示窗口,刷新窗口客户区
53     ::ShowWindow(hwnd,nCmdShow);
54     ::UpdateWindow(hwnd);
55 
56     //从消息队列中取出消息,交给窗口函数处理,知道GetMessage返回FALSE,结束消息循环
57     MSG msg;
58     while(::GetMessage(&msg,NULL,0,0))
59     {
60         //转化键盘消息
61         ::TranslateMessage(&msg);
62         //将消息发送到相应的窗口函数
63         ::DispatchMessage(&msg);
64     }
65 
66     //当GetMessage返回FALSE时程序结束
67     return msg.wParam;
68 }
69 
70 LRESULT CALLBACK MainWndProc(HWND hwnd,UINT message,WPARAM wParam,LPARAM lParam)
71 {
72     char szText[]="最简单的窗口程序!";
73     switch(message)
74     {
75     case WM_PAINT:                //窗口客户区需要重画
76         {
77             HDC hdc;
78             PAINTSTRUCT ps;
79 
80             //使无效的客户区变得有效,并取得设备环境句柄
81             hdc=::BeginPaint(hwnd,&ps);
82             //显示文字
83             ::TextOut(hdc,10,10,szText,strlen(szText));
84             ::EndPaint(hwnd,&ps);
85             return 0;
86         }
87     case WM_DESTROY:            //正在销毁窗口
88 
89         //向消息队列投递一个WM_QUIT消息,促使GetMessage函数返回0,结束消息循环
90         ::PostQuitMessage(0);
91         return 0;
92     }
93 
94     //将我们不处理的消息交给系统做默认处理
95     return ::DefWindowProc(hwnd,message,wParam,lParam);
96 }

 

 

 

 

 程序分析:

 程序分析:

1.  报了名窗口类:

1.  注册窗口类:

  注册窗口类的API函数是RegisterClassEx,最终的“Ex”是扩充的意趣,因为它是Win16的RegisterClass函数的开始展览。八个窗口类定义了窗口的某个重中之重品质,如:图标、光标、背景观和担负处理音讯的窗口函数等。那个属性定义在WNDCLASSEX结构中。

  注册窗口类的API函数是RegisterClassEx,最终的“Ex”是扩充的意趣,因为它是Win16的RegisterClass函数的拓展。2个窗口类定义了窗口的一对至关首要品质,如:图标、光标、背景观和担负处理新闻的窗口函数等。那一个属性定义在WNDCLASSEX结构中。

 1 typedef struct_WNDCLASSEX{
 2     UINT cbSize;                        //WNDCLASSEX结构的大小
 3     UINT style;                         //从这个窗口类派生的窗口具有的风格
 4     WNDPROC lpfnWndProc;                //即 window procedure,窗口消息处理函数指针
 5     int cbClsExtra;                     //指定紧跟在窗口类结构后的附加字节数
 6     int cbWndExtra;                     //指定紧跟在窗口事例后的附加字节数
 7     HANDLE hInstance;                   //本模板的实例句柄
 8     HICON hIcon;                        //窗口左上角图标的句柄
 9     HCURSOR hCursor;                    //光标的句柄
10     HBRUSH hbrBackground;               //背景画刷的句柄
11     LPCTSTR lpszMenuName;               //菜单名
12     LPCTSTR lpszClassName;              //该窗口类的名称
13     HICON hIconSm;                      //小图标句柄
14 }WNDCLASSEX;
 1 typedef struct_WNDCLASSEX{
 2     UINT cbSize;                        //WNDCLASSEX结构的大小
 3     UINT style;                         //从这个窗口类派生的窗口具有的风格
 4     WNDPROC lpfnWndProc;                //即 window procedure,窗口消息处理函数指针
 5     int cbClsExtra;                     //指定紧跟在窗口类结构后的附加字节数
 6     int cbWndExtra;                     //指定紧跟在窗口事例后的附加字节数
 7     HANDLE hInstance;                   //本模板的实例句柄
 8     HICON hIcon;                        //窗口左上角图标的句柄
 9     HCURSOR hCursor;                    //光标的句柄
10     HBRUSH hbrBackground;               //背景画刷的句柄
11     LPCTSTR lpszMenuName;               //菜单名
12     LPCTSTR lpszClassName;              //该窗口类的名称
13     HICON hIconSm;                      //小图标句柄
14 }WNDCLASSEX;

  PS:

  PS:

  RegisterClassEx的唯一参数是其一布局的地方。注册窗口类后就可以将类名和其窗口函数、类的作风及任何的类属性联系起来。当进程在CreateWindowEx函数中钦命四个类名的时候,系统就用这一个窗口函数、风格和与此类名相关的别的属性创制窗口。

  RegisterClassEx的绝无仅有参数是以此布局的地点。注册窗口类后就能够将类名和其窗口函数、类的作风及其余的类属性联系起来。当进程在CreateWindowEx函数中钦定3个类名的时候,系统就用那几个窗口函数、风格和与此类名相关的其余属性创设窗口。

  主程序中CS_HREDRAW|CS_VREDRAW风格钦点如若窗口客户区的宽窄或可观改变了,则重画这么些窗口。前缀CS_意为class
style,在WINUSE奇骏.H中定义了全体可选样式。

  主程序中CS_HREDRAW|CS_VREDRAW风格钦赐假设窗口客户区的宽度或可观改变了,则重画这几个窗口。前缀CS_意为class
style,在WINUSEMurano.H中定义了百分之百可选样式。

  主程序中LoadIcon函数装载了贰个预约义的图标(命名为IDI_APPLICATION),LoadCursor函数装载了三个预约义的光标(命名为IDC_ACR-VROW)。假使要装载自定义的图标或光标的话,应该先向工程中添加三个财富脚本(前面打字程序将会涉及),然后再通过菜单命令“Insert/Resource…”添加那么些财富。

  主程序中LoadIcon函数装载了五个预约义的图标(命名为IDI_APPLICATION),LoadCursor函数装载了叁个预约义的光标(命名为IDC_A库罗德ROW)。假如要装载自定义的图标或光标的话,应该先向工程中添加贰个财富脚本(前面打字程序将会涉及),然后再通过菜单命令“Insert/Resource…”添加这一个能源。

  WHITE_BRUSH是3个Windows预订义的画刷对象类型,GetStockObject函数取得那几个画刷对象的句柄,传递给hbrBackground成员。大家也能够友善创造2个画刷对象,以便内定喜欢的颜色作为窗口的背景象。例如上面代码将窗口的背景象设为鲜本白。

  WHITE_BRUSH是三个Windows预定义的画刷对象类型,GetStockObject函数取得那么些画刷对象的句柄,传递给hbrBackground成员。我们也得以本身成立八个画刷对象,以便钦命喜欢的颜料作为窗口的背景观。例如下边代码将窗口的背景观设为茄皮浅黄。

wndclass.hbrBackground=::CreateSolidBrush(RGB(0xa6,0xca,0xf0));            //创建一个纯色的刷子
......
::DeleteObject(wndclass.hbrBackground);                                    //最后别忘了删除创建的刷子,释放资源
wndclass.hbrBackground=::CreateSolidBrush(RGB(0xa6,0xca,0xf0));            //创建一个纯色的刷子
......
::DeleteObject(wndclass.hbrBackground);                                    //最后别忘了删除创建的刷子,释放资源

  填充完WNDCLASSEX结构,就能够拓展登记了。RegisterClassEx函数调用失利将回到0.

  填充完WNDCLASSEX结构,就足以拓展注册了。RegisterClassEx函数调用失利将重回0.

 

 

2.  创立窗口:

2.  创造窗口:

  要开创窗口,用注册的窗口类的类名调用CreateWindowEx函数即可。

  要创造窗口,用注册的窗口类的类名调用CreateWindowEx函数即可。

 1 HWND hwnd=::CreateWindowEx(
 2                 0,                                        //dwExStyle,拓展样式
 3                 szClassName,                              //lpClassName,类名
 4                 "My first Window!",                       //lpWindowName,标题
 5                 WS_OVERLAPPEDWINDOW,                      //dwStyle,窗口风格
 6                 CW_USEDEFAULT,                            //X,初始X坐标
 7                 CW_USEDEFAULT,                            //Y,初始Y坐标
 8                 CW_USEDEFAULT,                            //nWidth,宽度
 9                 CW_USEDEFAULT,                            //nHeight,高度
10                 NULL,                                     //hWndParent,父窗口句柄
11                 NULL,                                     //hMenu,菜单句柄
12                 hInstance,                                //hInstance,程序实例句柄
13                 NULL);                                    //lpParam,用户数据
14        
 1 HWND hwnd=::CreateWindowEx(
 2                 0,                                        //dwExStyle,拓展样式
 3                 szClassName,                              //lpClassName,类名
 4                 "My first Window!",                       //lpWindowName,标题
 5                 WS_OVERLAPPEDWINDOW,                      //dwStyle,窗口风格
 6                 CW_USEDEFAULT,                            //X,初始X坐标
 7                 CW_USEDEFAULT,                            //Y,初始Y坐标
 8                 CW_USEDEFAULT,                            //nWidth,宽度
 9                 CW_USEDEFAULT,                            //nHeight,高度
10                 NULL,                                     //hWndParent,父窗口句柄
11                 NULL,                                     //hMenu,菜单句柄
12                 hInstance,                                //hInstance,程序实例句柄
13                 NULL);                                    //lpParam,用户数据
14        

  PS:

  PS:

  函数调用成功将回到窗口句柄,退步重返NULL。第柒个参数dwStyle的值是WS_OVE牧马人LAPPEDWINDOW,即重叠式窗口(Overlapped
Window)。由它钦定的窗口有标题栏、系统菜单、能够转移大小的边框,以及最大化、最小化和关闭按钮。这几个二个行业内部窗口的体制。

  函数调用成功将再次回到窗口句柄,战败重临NULL。第伍个参数dwStyle的值是WS_OVE索罗德LAPPEDWINDOW,即重叠式窗口(Overlapped
Window)。由它内定的窗口有标题栏、系统菜单、能够变更大小的边框,以及最大化、最小化和倒闭按钮。这一个一个标准窗口的体裁。

  上边列出某些科学普及风格的概念,它们是以WS(Windows
Style的缩写)为前缀的预约义的值。

  上边列出一部分宽广风格的概念,它们是以WS(Windows
Style的缩写)为前缀的预订义的值。

    • WS_BO哈弗DECR-V  创设一个单边框的窗口
    • WS_CAPTION    创设一个有标题框的窗口(包涵WS_BODER风格)
    • WS_CHIlD  创设三个子窗口。这一个风格不可能与WS_POPVP风格合用
    • WS_DISABLED  创制二个开首状态为禁止的子窗口。二个禁止状态的窗口不能够承受来自用户的输入音讯
    • WS_DLGFRAME  创设2个带对话框边框风格的窗口。那种风格的窗口不能够带标题条
    • WS_HSCROLL  创设3个有程度滚动条的窗口
    • WS_VSCROLL  创设三个有垂直滚动条的窗口
    • WS_ICONIC  创制叁个起来状态为最小化状态的窗口。与WS_MINIMIZE风格一模一样
    • WS_MAXIMIZE  创造三个享有最大化按钮的窗口。该风格不可能喝WS_EX_CONTEXTHELP风格同时出现,同时务必钦赐WS_SYSMENU风格。
    • WS_THICKFRAME  创设3个可调边框的窗口,与WS_SIZEBOX风格一模一样
    • WS_VISIBLE  成立三个初叶状态为可知的窗口
    • WS_BOCRUISERDE昂Cora  成立三个单边框的窗口
    • WS_CAPTION    创设多个有标题框的窗口(包罗WS_BODER风格)
    • WS_CHIlD  创立叁个子窗口。那几个风格不可能与WS_POPVP风格合用
    • WS_DISABLED  创建一个起先状态为禁止的子窗口。3个禁止状态的窗口不能够承受来自用户的输入消息
    • WS_DLGFRAME  创设两个带对话框边框风格的窗口。那种作风的窗口不能够带标题条
    • WS_HSCROLL  成立3个有水平滚动条的窗口
    • WS_VSCROLL  创设贰个有垂直滚动条的窗口
    • WS_ICONIC  成立四个开首状态为最小化状态的窗口。与WS_MINIMIZE风格一模一样
    • WS_MAXIMIZE  创造3个持有最大化按钮的窗口。该风格不能喝WS_EX_CONTEXTHELP风格同时出现,同时必须钦命WS_SYSMENU风格。
    • WS_THICKFRAME  创设2个可调边框的窗口,与WS_SIZEBOX风格一模一样
    • WS_VISIBLE  创立贰个从头状态为可知的窗口

     等等。

     等等。

 

 

3.  在桌面展现窗口:

3.  在桌面呈现窗口:

1 ::ShowWindow(hwnd,nCmdShow);
1 ::ShowWindow(hwnd,nCmdShow);

  PS:

  PS:

  ShowWindow函数用于安装钦点窗口的突显状态,下面代码中的nCmdShow是系统传递给WinMain函数的参数。函数的第一个参数能够有多个例外的取值(具体情状请索引查看SDK文书档案),例如上边包车型地铁代码将躲藏句柄hWnd钦命的窗口。

  ShowWindow函数用于安装钦赐窗口的来得状态,上边代码中的nCmdShow是系统传递给WinMain函数的参数。函数的第2个参数能够有多个差其他取值(具体情状请索引查看SDK文档),例如下边包车型大巴代码将潜伏句柄hWnd钦定的窗口。

::ShowWindow(hWnd,SW_HIDE);            //nCmdShow参数的取值可以是SW_SHOW、SW_HIDE、SW_MINIMIZE等
::ShowWindow(hWnd,SW_HIDE);            //nCmdShow参数的取值可以是SW_SHOW、SW_HIDE、SW_MINIMIZE等

 

 

 4.  创新窗口客户区:

 4.  翻新窗口客户区:

1 ::UpdateWindow(hwnd);
1 ::UpdateWindow(hwnd);

  PS:

  PS:

  就算钦定窗口的换代区域不为空的话,UpdateWindow函数通过向这些窗口发送四个WM_PAINT音讯更新它的客户区。当窗口突显在荧屏上时,窗口的客户区被在WNDCLASSEX中钦定的刷子擦去了,调用UpdateWindow函数将敦促客户区重画,以显示其内容。

  要是内定窗口的更新区域不为空的话,UpdateWindow函数通过向那么些窗口发送贰个WM_PAINT消息更新它的客户区。当窗口体现在荧屏上时,窗口的客户区被在WNDCLASSEX中钦命的刷子擦去了,调用UpdateWindow函数将敦促客户区重画,以展现其内容。

 

 

5.  进入无限的音讯循环:

5.  进去无限的消息循环:

  程序下面将进入无限的轮回中。在调用UpdateWindow函数之后,整个窗口已经展现在桌面上,程序必须准备从用户接受键盘和鼠标输入了。Windows为各种线程维护了二个新闻队列,每当有二个输入产生,Windows就把用户的输入翻译成消息放在消息队列中。利用GetMessage函数能够从调用线程的信息队列中取出一个信息来填充MSG结构。

  程序上边将进入无限的大循环中。在调用UpdateWindow函数之后,整个窗口已经彰显在桌面上,程序必须准备从用户接受键盘和鼠标输入了。Windows为各样线程维护了二个音信队列,每当有八个输入发生,Windows就把用户的输入翻译成音讯放在音讯队列中。利用GetMessage函数能够从调用线程的新闻队列中取出四个音讯来填充MSG结构。

1 ::GetMessage(&msg,NULL,0,0);
1 ::GetMessage(&msg,NULL,0,0);

  PS:

  PS:

  如若信息队列中从未新闻(即没有用户输入),那些函数会从来等候下去,知道有消息进入到消息队列截至。msg是1个MSG结构类型的变量,这一个组织定义了音信的持有属性。

  假如音信队列中绝非音讯(即没有用户输入),这些函数会一贯等待下去,知道有新闻进入到音信队列截至。msg是1个MSG结构类型的变量,那个布局定义了音讯的具备属性。

typedef struct tagMSG {
    HWND hwnd;                   //消息要发送的窗口句柄
    UINT message;                //消息标识符,以WM_开头的预定义值(意为Window Message)
    WPARAM wParam;               //消息的参数之一
    LPARAM lParam;               //消息的参数之二
    DWORD time                   //消息放入消息队列的时间
    POINT pt;                    //这是一个POINT数据结构,表示消息放入消息队列时的鼠标位置
}MSG,*PMSG;
typedef struct tagMSG {
    HWND hwnd;                   //消息要发送的窗口句柄
    UINT message;                //消息标识符,以WM_开头的预定义值(意为Window Message)
    WPARAM wParam;               //消息的参数之一
    LPARAM lParam;               //消息的参数之二
    DWORD time                   //消息放入消息队列的时间
    POINT pt;                    //这是一个POINT数据结构,表示消息放入消息队列时的鼠标位置
}MSG,*PMSG;

  GetMessage函数从音讯队列中得到的信息一经不是WM_QUIT,则赶回非零值。二个WM_QUIT新闻会促使GetMessage函数重临0,从而甘休音信循环。

  GetMessage函数从新闻队列中获取的新闻一经不是WM_QUIT,则赶回非零值。一个WM_QUIT音讯会促使GetMessage函数重返0,从而停止音信循环。

::TranslateMessage(&msg);
::TranslateMessage(&msg);

  此调用把键盘输入翻译成为可传递的音信。

  此调用把键盘输入翻译成为可传递的音信。

::DispatchMessage(&msg);
::DispatchMessage(&msg);

  DispatchMessage函数分发三个消息到相应窗口的窗口函数。在下面的例子中,窗口函数是MainWndProc。MainWndProc处理音讯后把控制权交给Windows,此时DispatchMessage函数照旧此起彼伏做事,当它回到时,音信循环队列从调用Getmessage函数开端进入下一轮循环。

  DispatchMessage函数分发二个音讯到对应窗口的窗口函数。在上面包车型大巴事例中,窗口函数是MainWndProc。MainWndProc处理新闻后把控制权交给Windows,此时DispatchMessage函数如故三番五次做事,当它回到时,新闻循环队列从调用Getmessage函数开端进入下一轮循环。

 

 

 *6.  处理音信:

 *6.  拍卖音讯:

  音讯处理函数接收到的保有音讯都被标识为三个数字,这便是MainWndProc的第三个参数uMsg。那些数字在WINUSE奥德赛.H文件中都以以WM_为前缀定义的。

  音信处理函数接收到的有着新闻都被标识为3个数字,那正是MainWndProc的率先个参数uMsg。那几个数字在WINUSE福睿斯.H文件中都以以WM_为前缀定义的。

  经常Windows程序设计者用一个switch和case结构来决定新闻处理函数收到了怎么音讯,以及哪些处理这些新闻。全数音讯处理函数不处理的新闻都必须传给二个名为DefWindowProc的函数让Windows做默许处理,从DefWindowProc函数重返的值也亟须从新闻处理函数重回。

  常常Windows程序设计者用三个switch和case结构来控制音信处理函数收到了怎么着新闻,以及怎么着处理那几个音信。全体信息处理函数不处理的消息都无法不传给二个名为DefWindowProc的函数让Windows做私下认可处理,从DefWindowProc函数重回的值也非得从消息处理函数重回。

 1 switch(uMsg)
 2 {
 3 case WM_PAINT:
 4     /*处理WM_PAINT消息*/
 5     return 0;
 6 
 7 case WM_DESTROY:
 8     /*处理WM_DESTROY消息*/
 9     return 0;
10 
11 }
12 return ::DefWindowProc(hwnd,message,wParam,lParam);
 1 switch(uMsg)
 2 {
 3 case WM_PAINT:
 4     /*处理WM_PAINT消息*/
 5     return 0;
 6 
 7 case WM_DESTROY:
 8     /*处理WM_DESTROY消息*/
 9     return 0;
10 
11 }
12 return ::DefWindowProc(hwnd,message,wParam,lParam);

  PS:

  PS:

  必须要把富有不处理的消息交给DefWindowProc函数处理,也要把它的再次来到值再次回到给Windows,不然Windows就错过了与应用程序通讯的门径,也就不可能再决定窗口的行为了,这是违规的。

  必供给把具备不处理的消息交给DefWindowProc函数处理,也要把它的再次来到值重返给Windows,不然Windows就失去了与应用程序通讯的路径,也就无法再决定窗口的行为了,那是不合规的。

  WM_PAINT音信通告应用程序窗口客户区有一块大概全体变为无效,必须刷新。那意味着窗口客户区的内容必须被重画。客户区在以下景况会变成无效:

  WM_PAINT消息通告应用程序窗口客户区有一块或然全部改成无效,必须刷新。那象征窗口客户区的内容必须被重画。客户区在偏下情形会变成无效:

    1)当窗口第三次被创立时,整个客户区是无效的,因为还不曾向上边画其余事物。

    1)当窗口第①回被创制时,整个客户区是低效的,因为还没有向上边画其他东西。

      第一个WM_PAINT新闻被发送到窗口处理函数时,程序有机会向客户区画一些东西。

      第一个WM_PAINT新闻被发送到窗口处理函数时,程序有机会向客户区画一些事物。

    2)当改变窗口大小的时候,客户区编制程序无效。

    2)当改变窗口大小的时候,客户区编制程序无效。

      用户在填写WNDCLASSEX结构的style成员时,将它设置为CS_HREDRAW和CS_VREDRAW,那就一向造成在变更窗口大小时Windows将全体窗口变为无效。

      用户在填充WNDCLASSEX结构的style成员时,将它设置为CS_HREDRAW和CS_VREDRAW,那就径直促成在变更窗口大时辰Windows将全部窗口变为无效。

    3)最小化窗口,再将它过来到在此之前大小时,Windows没有保留整个客户区的内容。

    3)最小化窗口,再将它过来到在此之前大时辰,Windows没有保留整个客户区的内容。

      在图片操作系统下,须要保留的多少太多了。同样地,Windows使这一个窗口无效,窗口处理函数就会吸收3个WM_PAINT音讯,本人背负回复客户区内容。

      在图纸操作系统下,要求保留的数量太多了。同样地,Windows使这些窗口无效,窗口处理函数就会收下1个WM_PAINT新闻,自个儿担当回复客户区内容。

    4)当围着显示屏移动窗口,直到窗口被掩盖时,Windows并没有保存被覆盖的区域。

    4)当围着显示屏移动窗口,直到窗口被遮住时,Windows并从未保存被遮盖的区域。

      这么些区域再一次呈现时,它就被标识为无用。窗口处理函数会收到一个WM_PAINT信息来重画窗口的始末。

      那么些区域再度体现时,它就被标识为无效。窗口处理函数会收到3个WM_PAINT音信来重画窗口的内容。

  处理WM_PAINT新闻时老是以调用BeginPaint函数起初。

  处理WM_PAINT信息时老是以调用BeginPaint函数起始。

hdc=::BeginPaint(hwnd,&ps);
//以一个EndPaint函数调用结束
::EndPaint(hwnd,&ps);
hdc=::BeginPaint(hwnd,&ps);
//以一个EndPaint函数调用结束
::EndPaint(hwnd,&ps);

  这四个函数中,第1个参数是窗口句柄,第③个参数是指向PAINTSTRUCT结构的指正,这么些布局包含部分足以在重画客户区时使用的音讯。

  那多少个函数中,第一个参数是窗口句柄,第贰个参数是指向PAINTSTRUCT结构的指正,那几个协会包括部分足以在重画客户区时行使的消息。

  在调用BeginPaint函数的时候,借使客户区的背景还尚未被擦掉的话,Windows将擦除它,擦除背景时采纳的刷子由WNDCLASSEX结构的hbrBackground成员钦赐。对BeginPain函数的调用将使任何客户区有效,然后回来设备条件句柄。在窗口的客户区展现图形和文字时,要求选取这几个设备条件句柄。EndPaint函数负责释放设备条件句柄,使它变得不在能应用。DefWindowProc函数会通过调用BeginPaint和EndPaint函数使客户区有效。

  在调用BeginPaint函数的时候,如若客户区的背景还尚无被擦掉的话,Windows将擦除它,擦除背景时使用的刷子由WNDCLASSEX结构的hbrBackground成员钦命。对BeginPain函数的调用将使一切客户区有效,然后重临设备条件句柄。在窗口的客户区突显图形和文字时,供给动用那几个装置条件句柄。EndPaint函数负责释放设备条件句柄,使它变得不在能运用。DefWindowProc函数会通过调用BeginPaint和EndPaint函数使客户区有效。

  调用BeginPaint函数后,主程序中调用了TextOut函数。

  调用BeginPaint函数后,主程序中调用了TextOut函数。

1 ::TextOut(hdc,10,10,szText,strlen(szText));
1 ::TextOut(hdc,10,10,szText,strlen(szText));

  此函数用于在hdc钦命的设备(那里是
显示屏)上显得文字。(10,10)为坐标地点,szText为要体现的文字,strlen(szText)语句总括出了文本占用的字节数。

  此函数用于在hdc内定的设备(那里是
显示屏)上海展览中心示文字。(10,10)为坐标地方,szText为要来得的文字,strlen(szText)语句计算出了文件占用的字节数。

  每当客户区变成无效,新闻处理函数WndProc都会收到1个洗呢WM_PAINT新闻。响应此消息的代码取得设备条件句柄后,再2次将szText的始末展现在内定地点。

  每当客户区变成无效,音信处理函数WndProc都会接到3个洗呢WM_PAINT音讯。响应此音信的代码取得设备条件句柄后,再二次将szText的内容呈现在钦点地点。

  WM_DESTROY是窗口函数必须处理的音信。当用户关闭窗口,而且此窗口已经响应了用户的请求正在关闭时,音信处理函数就会接到1个WM_DESTROY新闻。当接受到这几个新闻的时候,表明窗口正在销毁。MainWndProc函数调用PostQuitMessage函数来响应此音信。

  WM_DESTROY是窗口函数必须处理的音讯。当用户关闭窗口,而且此窗口已经响应了用户的乞请正在关闭时,音信处理函数就会接到二个WM_DESTROY音信。当接受到这些音讯的时候,表达窗口正在销毁。MainWndProc函数调用PostQuitMessage函数来响应此音讯。

1 ::PostQuitMessage(0);
1 ::PostQuitMessage(0);

  这么些函数向程序的音信队列中插入三个WM_QUIT音讯。GetMessage函数如若从新闻队列中拿走的音信是WM_QUIT,它将重返0,从而促使WinMain函数离开新闻循环,然后应用程序执行以下代码。

  这么些函数向程序的音讯队列中插入贰个WM_QUIT音信。GetMessage函数假设从音信队列中拿走的消息是WM_QUIT,它将重临0,从而促使WinMain函数离开音信循环,然后应用程序执行以下代码。

1 //当GetMessage返回0时程序结束
2 return msg.wParam;
1 //当GetMessage返回0时程序结束
2 return msg.wParam;

  此时,msg.wParam的值是传给PostQuitMessage函数的参数的值。return语句将使WinMain函数重临,程序运转甘休。

  此时,msg.wParam的值是传给PostQuitMessage函数的参数的值。return语句将使WinMain函数重临,程序运维结束。

相关文章