勾勒一个Windows窗口程序

来源:互联网 发布:淘宝换主图会影响排名 编辑:程序博客网 时间:2024/04/28 07:53

        先用语言叙述:“当我们单击一次鼠标或每按下键盘上的一个键时(称之为事件),操作系统会感知事件,并将事件包装成消息,投递到消息队列中,然后程序会从消息队列中取出消息并响应。所谓消息,就是windows应用程序与操作系统间通信的信使。”

        再具体步骤(其实就是WinMain函数里的步骤):创建窗口四部曲(设计、注册、创建、显示与更新)+Direct3D初始化四部曲(获取接口IDirect3D9的指针、校验硬件定点运算、填充D3DPRESENT_PARAMETERS结构、创建IDirect3DDevice9接口)--------> (setup一些对象。。这里不是重点)--------> 将display函数作为显示函数进入消息循环 --------> 执行清除操作,最终释放IDirect3DDevice9接口。

        另外,需要注意窗口过程函数WndProc没有出现在WinMain函数里,但是身为Windows程序的中枢神经,它真的是无处不在:1.在设计窗口类的时候,将窗口过程函数的地址赋值给wc.lpfnWndProc   = (WNDPROC)d3d::WndProc;   2.在注册窗口类的时候RegisterClass(&wc),系统就有了我们编写的窗口过程函数的地址。   3.在消息循环EnterMsgLoop里获取消息的时候DispatchMessage(&msg)将消息回传给系统,然后系统利用先前注册窗口类时得到的函数指针调用窗口过程函数对其进行处理。

 

WinMain函数:

int WINAPI WinMain(HINSTANCE hinstance,   HINSTANCE prevInstance,    PSTR cmdLine,   int showCmd){if(!d3d::InitD3D(hinstance,Width, Height, true, D3DDEVTYPE_HAL, &Device)){::MessageBox(0, "InitD3D() - FAILED", 0, 0);return 0;}if(!Setup()){::MessageBox(0, "Setup() - FAILED", 0, 0);return 0;}d3d::EnterMsgLoop( Display );Cleanup();Device->Release();return 0;}
创建窗口四部曲+Direct3D初始化四部曲:

bool d3d::InitD3D(HINSTANCE hInstance,int width, int height,bool windowed,D3DDEVTYPE deviceType,IDirect3DDevice9** device){//// Create the main application window.//WNDCLASS wc;  //设计wc.style         = CS_HREDRAW | CS_VREDRAW;wc.lpfnWndProc   = (WNDPROC)d3d::WndProc; wc.cbClsExtra    = 0;wc.cbWndExtra    = 0;wc.hInstance     = hInstance;wc.hIcon         = LoadIcon(0, IDI_APPLICATION);wc.hCursor       = LoadCursor(0, IDC_ARROW);wc.hbrBackground = (HBRUSH)GetStockObject(WHITE_BRUSH);wc.lpszMenuName  = 0;wc.lpszClassName = "Direct3D9App";if( !RegisterClass(&wc) )    //注册{::MessageBox(0, "RegisterClass() - FAILED", 0, 0);return false;}HWND hwnd = 0;   //创建hwnd = ::CreateWindow("Direct3D9App", "Direct3D9App", WS_EX_TOPMOST,0, 0, width, height,0 /*parent hwnd*/, 0 /* menu */, hInstance, 0 /*extra*/); if( !hwnd ){::MessageBox(0, "CreateWindow() - FAILED", 0, 0);return false;}::ShowWindow(hwnd, SW_SHOW);  //显示::UpdateWindow(hwnd);         //更新//// Init D3D: //HRESULT hr = 0;// Step 1: Create the IDirect3D9 object.IDirect3D9* d3d9 = 0;    d3d9 = Direct3DCreate9(D3D_SDK_VERSION);    if( !d3d9 ){::MessageBox(0, "Direct3DCreate9() - FAILED", 0, 0);return false;}// Step 2: Check for hardware vp.D3DCAPS9 caps;d3d9->GetDeviceCaps(D3DADAPTER_DEFAULT, deviceType, &caps);int vp = 0;if( caps.DevCaps & D3DDEVCAPS_HWTRANSFORMANDLIGHT )vp = D3DCREATE_HARDWARE_VERTEXPROCESSING;elsevp = D3DCREATE_SOFTWARE_VERTEXPROCESSING;// Step 3: Fill out the D3DPRESENT_PARAMETERS structure. D3DPRESENT_PARAMETERS d3dpp;d3dpp.BackBufferWidth            = width;d3dpp.BackBufferHeight           = height;d3dpp.BackBufferFormat           = D3DFMT_A8R8G8B8;d3dpp.BackBufferCount            = 1;d3dpp.MultiSampleType            = D3DMULTISAMPLE_NONE;d3dpp.MultiSampleQuality         = 0;d3dpp.SwapEffect                 = D3DSWAPEFFECT_DISCARD; d3dpp.hDeviceWindow              = hwnd;d3dpp.Windowed                   = windowed;d3dpp.EnableAutoDepthStencil     = true; d3dpp.AutoDepthStencilFormat     = D3DFMT_D24S8;d3dpp.Flags                      = 0;d3dpp.FullScreen_RefreshRateInHz = D3DPRESENT_RATE_DEFAULT;d3dpp.PresentationInterval       = D3DPRESENT_INTERVAL_IMMEDIATE;// Step 4: Create the device.hr = d3d9->CreateDevice(D3DADAPTER_DEFAULT, // primary adapterdeviceType,         // device typehwnd,               // window associated with devicevp,                 // vertex processing    &d3dpp,             // present parameters    device);            // return created deviceif( FAILED(hr) ){// try again using a 16-bit depth bufferd3dpp.AutoDepthStencilFormat = D3DFMT_D16;hr = d3d9->CreateDevice(D3DADAPTER_DEFAULT,deviceType,hwnd,vp,&d3dpp,device);if( FAILED(hr) ){d3d9->Release(); // done with d3d9 object::MessageBox(0, "CreateDevice() - FAILED", 0, 0);return false;}}d3d9->Release(); // done with d3d9 objectreturn true;}
将display函数作为显示函数进入消息循环 :

int d3d::EnterMsgLoop( bool (*ptr_display)(float timeDelta) ){MSG msg;::ZeroMemory(&msg, sizeof(MSG));static float lastTime = (float)timeGetTime(); while(msg.message != WM_QUIT){if(::PeekMessage(&msg, 0, 0, 0, PM_REMOVE)){::TranslateMessage(&msg);::DispatchMessage(&msg);}else        {float currTime  = (float)timeGetTime();float timeDelta = (currTime - lastTime)*0.001f;ptr_display(timeDelta);lastTime = currTime;        }    }    return msg.wParam;}

窗口过程函数:

LRESULT CALLBACK d3d::WndProc(HWND hwnd, UINT msg, WPARAM wParam, LPARAM lParam){switch( msg ){case WM_DESTROY:::PostQuitMessage(0);break;case WM_KEYDOWN:if( wParam == VK_ESCAPE )::DestroyWindow(hwnd);break;}return ::DefWindowProc(hwnd, msg, wParam, lParam);}




0 0
原创粉丝点击