windows开发cocos2d-x系列(2)—简单解析HelloWorld
前言
上一篇介绍了cocos2d的环境搭建,今天我们来一起运行,编写,以及解析cocos2d-x 3.0的HelloWorld。程序虽小,五脏俱全。
创建一个HelloWorld
我们开始自己创建HelloWorld吧。首先打开windows的cmd窗口,然后在cmd中输入以下命令:
cocos new HelloWorld -p com.momo.helloWorld -l cpp -d projects
HelloWorld是如何显示到窗口的
我们打开项目中的AppDelegate.cpp文件,我们只看applicationDidFinishLaunching函数,如下代码所示:
1 bool AppDelegate::applicationDidFinishLaunching() { 2 // initialize director 3 auto director = Director::getInstance(); 4 auto glview = director->getOpenGLView(); 5 if(!glview) { 6 glview = GLView::create("My Game"); 7 director->setOpenGLView(glview); 8 } 9 10 // turn on display FPS 11 director->setDisplayStats(true); 12 13 // set FPS. the default value is 1.0/60 if you don't call this 14 director->setAnimationInterval(1.0 / 60); 15 16 // create a scene. it's an autorelease object 17 auto scene = MyHelloWorldScene::createScene(); 18 19 // run 20 director->runWithScene(scene); 21 22 return true; 23 }
- director->setDisplayStats(true):设置是否显示游戏的帧数等调试信息。
- director->setAnimationInterval(1.0 / 60):设置游戏的帧率,在这里是每秒60帧。
- auto scene = MyHelloWorldScene::createScene():创建一个场景。
- director->runWithScene(scene):最重要的地方,让场景类显示出来。
帧是游戏开发里一个很重要的概念。在程序世界里,其实一切都是静止的,之所以能够看到游戏在不断的运动,是因为很多静止的画面快速连续切换产生的错觉。就跟那些漫画家画的动漫是相似的。
场景介绍
现在来分析场景类,先看HelloWorldScence.h头文件,如下代码所示:
1 #ifndef __HELLOWORLD_SCENE_H__ 2 #define __HELLOWORLD_SCENE_H__ 3 4 #include "cocos2d.h" 5 6 class HelloWorld : public cocos2d::Layer 7 { 8 public: 9 // there's no 'id' in cpp, so we recommend returning the class instance pointer 10 static cocos2d::Scene* createScene(); 11 12 // Here's a difference. Method 'init' in cocos2d-x returns bool, instead of returning 'id' in cocos2d-iphone 13 virtual bool init(); 14 15 // a selector callback 16 void menuCloseCallback(cocos2d::Ref* pSender); 17 18 // implement the "static create()" method manually 19 CREATE_FUNC(HelloWorld); 20 }; 21 22 #endif // __HELLOWORLD_SCENE_H__
menuCloseCallback是一个回调函数。
createScene函数是不可缺的,在cocos2d-x 3.0里,都通过这样的方式来创建一个场景对象。
再来看看CREATE_FUNC(HelloWorld),CREATE_FUNC是一个宏。宏是c/c++中的一种预编译手段,比如我们定义一个字符串MAX_NUM,规定它代表10,那么在程序里所有的MAX_NUM在编译里都会用10来代替。
#define MAX_NUM 10
#define是c++的关键字,用来标明一个宏。CREATE_FUNC就是一个宏函数,来看看它的具体实现,如下代码所示:
1 #define CREATE_FUNC(__TYPE__) \ 2 static __TYPE__* create() \ 3 { \ 4 __TYPE__ *pRet = new __TYPE__(); \ 5 if (pRet && pRet->init()) \ 6 { \ 7 pRet->autorelease(); \ 8 return pRet; \ 9 } \ 10 else \ 11 { \ 12 delete pRet; \ 13 pRet = NULL; \ 14 return NULL; \ 15 } \ 16 }
- 用#define定义,并且没有返回值;
- 参数没有类型,只有参数名;
- 每一行结尾处都有一个"\"符号(宏定义只能是一条语句,\用于换行,表面上让我们看起来是多行代码,实现对编译器来说,只有一行。这样我们也可以方便地看代码)
参数__TYPE__也是个宏,这个宏函数里所有出现__TYPE__的地方都会被替换成我们传入的HelloWorld。
我们再看HelloWorldScene.cpp中的createScene函数的实现,如下代码所示:
1 Scene* HelloWorld::createScene() 2 { 3 // 'scene' is an autorelease object 4 auto scene = Scene::create(); 5 6 // 'layer' is an autorelease object 7 auto layer = HelloWorld::create(); 8 9 // add layer as a child to scene 10 scene->addChild(layer); 11 12 // return the scene 13 return scene; 14 }
- auto scene = Scene::create():创建一个场景类。这个场景并不是HelloWorld本身。
- auto layer = HelloWorld::create():创建HelloWorld对象,create函数正是用宏 CREATE_FUNC(HelloWorld)定义的。
- scene->addChild(layer):将layer对象添加到scene对象中。
- return scene:返回scene对象。
另外解释一下,auto是c++的关键字,用来声明自动变量,相当于c#中的var关键字。
小结
最后我们再梳理一遍:
- 通过auto scene=HelloWorld::createScene()创建一个场景对象;
- HelloWorld的createScene函数里创建了一个场景对象(Scene),然后将HelloWorld对象(Layer)添加到场景对象;
- HelloWorld对象通过create函数创建,而create函数是由宏CREATE_FUNC(HelloWorld)来定义的;
- 通过direcor->runWithScene(scene)才让场景对象显示在窗口中。
到这里,HelloWorld就介绍完了,后续我们会再介绍cocos2d-x 3.0中关键的一些类。