使用 WinMain() 和 WindowProc() 建立窗口后,我应该在哪里添加我的实际程序? (C++)

Posted

技术标签:

【中文标题】使用 WinMain() 和 WindowProc() 建立窗口后,我应该在哪里添加我的实际程序? (C++)【英文标题】:Where do I add my actual program after I establish a Window using WinMain() and WindowProc()? (C++) 【发布时间】:2012-01-30 22:27:06 【问题描述】:

首先,很抱歉我对窗口创建过程的无知。今天实际上是我尝试它的第一天。

几天前我开始编写一个基于文本的游戏,我有主菜单和 3 或 4 个不同的功能,可以用文本控制各种事物。然后我被建议查看 Windows API 并为该程序创建一个窗口。我创建了可以在这里看到的窗口:

#include <Windows.h>

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

int WINAPI WinMain(HINSTANCE hInstance, HINSTANCE, PWSTR nCmdLine, int nCmdShow)

    const wchar_t CLASS_NAME[] = L"WindowClass";
    WNDCLASS wc =  ;
    wc.lpfnWndProc = WindowProc;
    wc.lpszClassName = CLASS_NAME;
    wc.hInstance = hInstance;
    RegisterClass(&wc); 


    HWND hwnd = CreateWindowEx( //This creats a new instance of a window
      0,                        
      CLASS_NAME,                
      L"MyFirstWindow",          
      WS_OVERLAPPEDWINDOW,       
      CW_USEDEFAULT,             
      CW_USEDEFAULT,            
      500,                       
      500,                       
      NULL,                      
      NULL,                      
      hInstance,                 
      NULL);                


    if(hwnd == 0)
        return 0;

    ShowWindow(hwnd,nCmdShow); 
    nCmdShow = 1; 

    MSG msg =  ;
    while(GetMessage(&msg,NULL,0,0))
    
      TranslateMessage(&msg);
      DispatchMessage(&msg); 
    
    return 0;
 

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

    switch(uMsg)
    
        case WM_DESTROY:PostQuitMessage(0); return 0;
        case WM_PAINT:
        
            PAINTSTRUCT ps;
            HDC hdc = BeginPaint(hwnd,&ps);
            FillRect(hdc,&ps.rcPaint,(HBRUSH)(COLOR_WINDOW+5)); 
            EndPaint(hwnd, &ps);
        return 0;

        case WM_CLOSE:
        
            if(MessageBox(hwnd,L"Do you want to exit?",L"Exit",MB_OKCANCEL)==IDOK)
                DestroyWindow(hwnd);
           return 0;
    

    return DefWindowProc(hwnd,uMsg,wParam,lParam); 

这看起来有点乱,但你可能无论如何都不需要它。

所以此时我有我的原始程序和创建窗口的程序。我的问题是如何,甚至在哪里放置我的原始程序的代码,以便它可以合并到窗口中。

如果您正在阅读本文并认为我这样做是个彻头彻尾的白痴,我愿意接受比我现在所做的简单得多的想法。

【问题讨论】:

Windows 应用程序是基于事件的。如果不重新考虑其设计,就无法将控制台应用程序直接移植到 Windows 应用程序。没有地方可以转储你的旧代码,这就是你找不到它的原因。 【参考方案1】:

您的代码是使用 c 和 win32 API 函数创建窗口的标准样板。我建议您修改消息泵(它是中间调用 GetMessage 的 while 循环)。而是这样做:

    运行无限循环 查看消息 如果消息不存在,请执行您的代码 包括退出消息在内的其他进程消息

代码如下所示:

while (1)

    if (PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
    
        if (msg.message == WM_QUIT)
            break;
        TranslateMessage(&msg);
        DispatchMessage(&msg);
    
    else 
    
        //Your game code
    

我还想指出,虽然使用 C 学习游戏编程并调用 Win32 API 是一个值得的目标,但您可能想看看 XNA 游戏工作室。

我推荐它的原因是因为它更容易学习,并且您可以更快地制作更有趣的游戏。如果您有兴趣,这里有一些链接可以帮助您入门。

http://joshua-w-wise78.livejournal.com/

http://www.krissteele.net/blogdetails.aspx?id=72

http://www.codeproject.com/KB/game/xna1.aspx

http://msdn.microsoft.com/en-us/library/bb203894.aspx

【讨论】:

【参考方案2】:

如果您的原始程序是一个控制台应用程序,它读取输入和打印输出,那么您可能希望从窗口获取输入来实现您的游戏。

与其从从标准输入读取用户输入然后生成输出到标准输出的角度来看它,您必须从窗口消息传递的角度来考虑它。所以您需要处理 WM_KEYDOWN 消息,然后您可以使用 DrawText() 在您的客户区显示用户输入,或者您可以使用 c++ RichEdit 控件。一旦你处理了 WM_KEYDOWN 消息,你就知道用户按下了什么,然后你的程序就可以做到这一点(当 WM_KEYDOWN 键等于 enter 键时,可能会触发处理一个累积的字符缓冲区?)并将输出写入你的使用 DrawText() 的客户区或使用 SendMessage() 将 WM_KEYDOWN 消息发送到您的 Richedit 窗口。

我认为这就是您所说的基于文本的游戏的意思,无论如何,您只需要开始考虑通过监视 Windows 消息来做所有事情。用户对您的窗口所做的任何事情,Windows 都会向它发送一条消息以告知它。

【讨论】:

以上是关于使用 WinMain() 和 WindowProc() 建立窗口后,我应该在哪里添加我的实际程序? (C++)的主要内容,如果未能解决你的问题,请参考以下文章

Windoows窗口程序一

非虚拟键的 WM_KEYUP (windows.h WindowProc)

C++中WinMain、main和DllMain的区别

WinMain和MFC的差别

关于VC++的Winmain函数(WINAPI是啥?)

windows里边winmain中的四个参数分别是啥意思啊