如何创建一个win32程序

2 篇文章 0 订阅

学过一段时间的c++,建立的都是win32 console application,我来介绍一下如何建立一个简单的win32程序,相比win32 console application,会有大家常见的窗口,更像程序一些。

     首先要写类似于main函数的WinMain,

int WINAPI WinMain( HINSTANCE hinstance,
HINSTANCE hprevinstance,
LPSTR lpcmdline,
int ncmdshow)

       WINAPI是干什么的呢?它是调用声明,相当于_stdcal。c++默认的调用声明是_cdecl。两者区别为:

      _stdcal函数在结束后自己清栈,_cdecl由调用者(不是指人自己,指的是调用的程序)清栈。当函数参数个数可变的时候,只能_cdecl调用,在不知道个数的情况下,函数自己不知道怎么清栈;不同的编译器会按不同的方式堆栈,这样会使得如果使用_cdecl声明时,调用者不一定可以成功清栈。

(参考了http://blog.csdn.net/dengziliang001/article/details/17448789)

      hinstance是Windows为应用程序产生的实例句柄,可以看成这个就是程序的地址,跟踪程序。

      hprevinstance,现在已经不使用这个参数了。

      lpcmdline,与main中的命令行差不多,基本写程序时不用管。

      ncmdshow,带有如何打开主应用程序窗口的信息,比如最大化,最小化,一般用的多的是ShowWindow(),ncmd不怎么用。

      函数体怎么写呢?看看下面:

      WNDCLASSEX winclass; // this will hold the class we create
       HWND   hwnd;// generic window handle
       MSG   msg;// generic message
       HDC        hdc;      // graphics device context


      // first fill in the window class stucture
      winclass.cbSize     = sizeof(WNDCLASSEX);
      winclass.style = CS_DBLCLKS | CS_OWNDC | 
                                             CS_HREDRAW | CS_VREDRAW;
    winclass.lpfnWndProc = WindowProc;
    winclass.cbClsExtra = 0;
    winclass.cbWndExtra = 0;
    winclass.hInstance = hinstance;
    winclass.hIcon = LoadIcon(NULL, IDI_APPLICATION);
    winclass.hCursor = LoadCursor(NULL, IDC_ARROW); 
winclass.hbrBackground = (HBRUSH)GetStockObject(BLACK_BRUSH);
winclass.lpszMenuName = NULL;
winclass.lpszClassName = WINDOW_CLASS_NAME;
winclass.hIconSm             = LoadIcon(NULL, IDI_APPLICATION);

        WNDCLASSEX是一个类,因为你要创建一个窗口,然后在上面输入输出操作,WNDCLSSEX可以看成一个窗口类,而winclass可以看成实例(即变量),hwnd,msg,hdc在后面会讲到,首先要做的是填winclass的各个属性,后面的一大串全是设置属性,比较重要的是   winclass.style,它指出了窗口的重要属性,如窗口宽度变化后会重画,高度变化后会重画,剩下的参数查msdn就知道了。

        然后你需要去注册这个类,

        if (!RegisterClassEx(&winclass))
    return(0);

        外面的if,当没注册成功就返回0,防止程序没注册成功,往下运行出现未知的错误。

        然后就是创建一个窗口,

     if (!(hwnd = CreateWindowEx(NULL,                  // extended style
                            WINDOW_CLASS_NAME,     // class
   "Demo", // title
   WS_OVERLAPPEDWINDOW | WS_VISIBLE,
   0,0, // initial x,y
   500,400,  // initial width, height
   NULL,   // handle to parent 
   NULL,   // handle to menu
   hinstance,// instance of this application
   NULL)))  // extra creation parms
     return(0);

         CreateWindowEx()会返回一个指向窗口的的句柄,相当于它的地址。

         上面的一系列都可以直接复制张贴,根据需要,改一改属性即可,然后我一般会编一个循环,去处理消息。

    while(TRUE)
{
    
if (PeekMessage(&msg,NULL,0,0,PM_REMOVE))
  { 
   TranslateMessage(&msg);
            DispatchMessage(&msg);
  } // end if
    } // end while
return(msg.wParam);
}
其中 if (PeekMessage(&msg,NULL,0,0,PM_REMOVE))
   { 
   TranslateMessage(&msg);
            DispatchMessage(&msg);
   } 

         理解成先判断有没有消息,有的话就传递给相应的程序处理,消息可以使单击鼠标左键,关闭窗口等。

之后return,就写好主函数。

         除了主函数还需要写一个消息处理函数,每个窗口都有一个窗口处理函数,而关联两者,就是在设置窗口属性时的winclass.lpfnWndProc= WindowProc,WindowProc是处理函数的名字,当窗口有相应的消息的时候,就会调用处理函数处理.下面是一个窗口处理函数:

         LRESULT CALLBACK WindowProc(HWND hwnd, 
                          UINT msg, 
                                                                         WPARAM wparam, 
                                                                         LPARAM lparam)
{

PAINTSTRUCT ps;

switch(msg){

case WM_CREATE: 

        {
        } break;
     case WM_PAINT: 
{
        BeginPaint(hwnd,&ps); 
            EndPaint(hwnd,&ps);
               return(0);
    } break;
     case WM_DESTROY: 
{
     PostQuitMessage(0);

     return(0);
} break;
  default:break;

return (DefWindowProc(hwnd, msg, wparam, lparam));

首先看一下函数的参数,hwnd 是调用窗口的句柄,便于对窗口操作,msg有消息类型的信息,wparam,lparam包含具体消息的细节。


总之其实上面的都可以直接复制张贴,至于该怎么操作只需要改一下处理函数,还有在while循环里做些填充。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值