原創作品,轉載請标明:http://blog.csdn.net/jackystudio/article/details/12554167
雖然cocos2d-x v3.0 alpha版已經出來了,也改進了不少,有興趣的可以去嘗嘗鮮。因為後面可能還會配合cocoStudio寫一下部落格,而現在v1.0.0.0版本需要配合cocos2d-x v2.2.0使用。是以這裡選擇了V2.2.0版的cocos2d-x。
一個新的東西,從頭開始吧!從HelloWorld出發看一下一個cocos2d-x遊戲是怎麼跑起來的。先看看它的結構。
1.main函數
還是原來配方還是熟悉的味道。。。霸氣的main函數依然是程式的入口點:
[cpp] view plain copy
- //main.cpp
- int APIENTRY _tWinMain(HINSTANCE hInstance,
- HINSTANCE hPrevInstance,
- LPTSTR lpCmdLine,
- int nCmdShow)
- {
- UNREFERENCED_PARAMETER(hPrevInstance);//該宏用于通知編譯器不用檢測變量是否使用,如果你喜歡用LV4級的警告。
- UNREFERENCED_PARAMETER(lpCmdLine);
- // create the application instance
- AppDelegate app;//建立AppDelegate執行個體
- CCEGLView* eglView = CCEGLView::sharedOpenGLView();//擷取CCEGLView的單一執行個體,因為還未建立,是以這裡會進行建立
- eglView->setViewName("HelloCpp");//設定eglView屬性
- eglView->setFrameSize(2048, 1536);
- eglView->setFrameZoomFactor(0.4f);
- return CCApplication::sharedApplication()->run();//調用run運作程式
- }
其中:
(1)AppDelegate繼承于CCApplication,是整個遊戲的程式類,如果有用過MFC的就很清楚,類似于CxxxApp。
(2)CCEGLView封裝了使用openGL作為顯示底層API的一個基本的Windows窗體的建立和控制。
可以簡單的認為,一個控制了程式的邏輯,而另一個負責遊戲的顯示。
2.CCEGLView類
我們先看看上一步的CCEGLView::sharedOpenGLView()做了什麼。
[cpp] view plain copy
- CCEGLView* CCEGLView::sharedOpenGLView()
- {
- if (s_pEglView == NULL)//s_pEglView是一個CCEGLView指針,靜态成員變量
- {
- s_pEglView = new CCEGLView();
- if(!s_pEglView->Create())//main中調用時,會執行這一步
- {
- delete s_pEglView;
- s_pEglView = NULL;
- }
- }
- return s_pEglView;
- }
再看看,create做了什麼
[cpp] view plain copy
- //...
- m_hWnd = CreateWindowEx( // 建立窗體
- WS_EX_APPWINDOW | WS_EX_WINDOWEDGE, // Extended Style For The Window
- kWindowClassName, // Class Name
- wszBuf, // Window Title
- WS_CAPTION | WS_POPUPWINDOW | WS_MINIMIZEBOX, // Defined Window Style
- 0, 0, // Window Position
- 1000, // Window Width
- 1000, // Window Height
- NULL, // No Parent Window
- NULL, // No Menu
- hInstance, // Instance
- NULL );
看到上面這一步了吧,使用Win32寫過窗體的童鞋,就知道建立一個窗體需要哪些動作:
(1)填充視窗類結構WNDCLASS
(2)注冊視窗
(3)建立視窗
(4)顯示視窗(這一步沒有在CCEGLView中實作,而是在後面的CCApplication中實作,因為這裡視窗的屬性還沒有進行設定)
一樣的,建立一個cocos2d-x的win32視窗也是要經過這些步驟。具體的就看源碼吧,這裡不逐句解釋了。就是要注意有個WinProc函數,是用于處理主視窗消息。
3.CCApplication類
我們再看看CCApplication::sharedApplication()->run()執行的又是什麼東西。
[cpp] view plain copy
- int CCApplication::run()
- {
- PVRFrameEnableControlWindow(false);
- // Main message loop:
- MSG msg;
- LARGE_INTEGER nFreq;
- LARGE_INTEGER nLast;
- LARGE_INTEGER nNow;
- QueryPerformanceFrequency(&nFreq);//擷取目前系統頻率和計數
- QueryPerformanceCounter(&nLast);
- // Initialize instance and cocos2d.
- if (!applicationDidFinishLaunching())//虛函數,調用子類的重載,這裡也會設定一些顯示視窗的屬性
- {
- return 0;
- }
- CCEGLView* pMainWnd = CCEGLView::sharedOpenGLView();擷取CCEGLView的單一執行個體
- pMainWnd->centerWindow();
- ShowWindow(pMainWnd->getHWnd(), SW_SHOW);//這裡顯示視窗
- while (1)//消息循環
- {
- if (! PeekMessage(&msg, NULL, 0, 0, PM_REMOVE))
- {
- // 擷取目前的計數
- QueryPerformanceCounter(&nNow);
- // 判斷時間流逝,是否該繪制下一幀
- if (nNow.QuadPart - nLast.QuadPart > m_nAnimationInterval.QuadPart)
- {
- nLast.QuadPart = nNow.QuadPart;
- CCDirector::sharedDirector()->mainLoop();//渲染場景(清除顯示裝置,重繪場景)
- }
- else
- {
- Sleep(0);
- }
- continue;
- }
- if (WM_QUIT == msg.message)//擷取退出消息,跳出循環
- {
- // Quit message loop.
- break;
- }
- // 處理Windows消息
- if (! m_hAccelTable || ! TranslateAccelerator(msg.hwnd, m_hAccelTable, &msg))
- {
- TranslateMessage(&msg);
- DispatchMessage(&msg);
- }
- }
- return (int) msg.wParam;
- }
好了,解釋的應該算比較清楚了,雖然沒有每一個函數都進去。。。這裡再總結一下:
(1)首先先擷取目前系統的頻率和計數。這是一個很大的值,是以用了一個LARGE_INTEGER型變量來存儲。
(2)調用子類的applicationDidFinishLaunching(),執行進入程式後的一些初始化工作。
(3)擷取CCEGLView單例,顯示視窗。
(4)進入循環While(1),重繪每一幀的場景。
好了,更多關于CCApplication的請看源碼吧。
4.AppDelegate類
從上面的分析我們知道CCApplication::run()函數中會調用子類(AppDelegate)的applicationDidFinishLaunching函數,而這裡也就是我們要設定視窗屬性和運作遊戲的地方了。
[cpp] view plain copy
- bool AppDelegate::applicationDidFinishLaunching() {
- //第一次初始化導演,導演也是個單例類
- CCDirector* pDirector = CCDirector::sharedDirector();
- //獲得CCEGLView單例,設定視窗屬性和fps等等
- CCEGLView* pEGLView = CCEGLView::sharedOpenGLView();
- ...
- // 建立場景
- CCScene *pScene = HelloWorld::scene();
- // 進入場景
- pDirector->runWithScene(pScene);
- return true;
- }
好了,最後再總結成一張圖,cocos2d-x遊戲就是這麼跑起來的~