位置: 编程技术 - 正文
推荐整理分享游戏引擎学习——Cocos2d-x-3.4引擎(1.源码粗分析)(游戏引擎官方平台),希望有所帮助,仅作参考,欢迎阅读内容。
文章相关热门搜索词:游戏引擎官方平台,游戏引擎基础知识,游戏引擎入门,游戏引擎app,游戏引擎基础知识,游戏引擎app,游戏引擎是做什么的,游戏引擎基础知识,内容如对您有帮助,希望把文章链接给更多的朋友!
首先利用cocos2d构建一个新项目“Hello World”: 在OSX终端输入:
然后用XCode打开项目。
我们看Mac应用程序的入口,是main.cpp文件,其中的主函数如下:
跟踪进AppDelegate的构造函数:这个构造函数是空的,但看得到该类继承于cocos2d::Application 父类构造函数:
跟进到这里,看得出该处设置了_animationInterval的值,并且将静态成员sm_pSharedApplication赋值为自身。
Application::getInstance()方法:这里断言sm_pSharedApplication是非空的,否则抛出异常。该方法返回了刚刚新建的AppDelegate:sm_pSharedApplication
Application::run()方法:设置OpenGL属性跟踪进,
正如注释,设置OpenGL的属性,包括:红、绿、蓝、透明度、深度、图案 第二句跟进到:
设置了静态变量为自身。 注意到这是一个好方法,对于保持一个App对应一个OpenGL的GLContextAttrs,上文中Application也是一样的原理。
确保app已经finish launching继续run方法,第二句判断
跟踪进去,逐句查看
设置DirectorDirector同样是app唯一的,为确保这一点,采用静态方法创建了类实例:
DisplayLinkDirector是继承于Director的类。 ==不知道这里的(std::nothrow)是什么意思,我猜是从外部内存新建该类的实例,而不从内存创建吧?== 查看init函数,这是bool Director::init(void),一堆的参数设置,可选跳过该节代码。
设置GLView & FPS但注意到Delegate::init()函数中已有:_openGLView = nullptr; 所以此处应当获取的nullptr,将会运行if的内部代码,这里不再跟进了。 但值得注意的是,在创建GLView时就已经设置了glview的大小,在director->setOpenGLView(glview);将glview的大小迁移到director->_winSizeInPoint。 setDisplayStats是设置是否显示FPS信息在屏幕上。 以下给出了新建GLView的代码:
可以看到具体的窗口大小在这里创建了。
新建scene接下来跟踪这句,可以看到这个是定义在HelloWorld类中的,也就是项目文件中的,而不在cocos包中。
1.Scene::create这段代码十分容易理解,new了一个Scene((std::nothrow)),然后对其init,若不成功则调用CC_SAFE_DELETE:
跟踪new Scene:
设置了一些参数,_event应该是一个Listener,Director...调用时的第二个参数是一个回调函数。 跟踪init:
2.HelloWorld::create调用了CREATE_FUNC(HelloWorld);:
这个代码和Scene::create()一模一样(注意到delete的地方也是一样的)。
3.scene->addChild注意,这里调用到的是Node::addChild,而不是Scene中的,Scene只重写(override)了另外两个addChild方法:
Node::addChild方法:
可以看到不同位置的相同代码没有复用宏定义、不同的断言处写法不一,可能是因为cocos的开发人员的一些不精细,但当然不能否定cocos是一个成功的好引擎。
运行runWithScene循环loop继续run方法:
接下来就是循环部分:
循环的判定部分是:(注意到glview对象在创建时是调用的GLViewImpl::create,而其中new的是GLViewImpl对象。)
跟踪到这个跟不下去了:GLFWAPI int glfwWindowShouldClose(GLFWwindow* window);。。。应该是GL的包,这个函数定义在glfw3.h中。
接下来,循环中的重要部分只有以下两句话:
1.mainLoop注意到director对象在创建时是调用的Director::getInstance(),而其中new的是DisplayLinkDirector对象。
逐句解释一下:
第一个if表示是否在下一循环中将director清除,在结束时会被外部其他方法设置为true(或者是在pollEvents方法中,即在循环内)第二个if表示是否在下一循环中重启restartDirector第三个if是实际上每次循环做的事情分别会调用(reset()方法是一个very complicate的方法,在此仅叙出其中的注释部分):
第一部分,清除director注意到,这里的end()方法是定义在GLView类中的纯虚方法,而且_openGLView在新建时是新建的GLViewImpl类型成员,所以调用到:
发现这是在一个mm文件中的,此处已经显示出我们打开的是ios/osx版本的代码。。。 =.=、
第二部分,重启director//TODO 这里微微有些乏(lan)力(duo),以(jue)后(bu)再(xiang)弄懂之。。。
第三部分 前面插的太多,回顾一下第三部分的代码:第一句drawScene():
可以看到,其中穿插了physicsWorld的update过程,然后再进行了GL的绘图过程。 具体的physicsWorld的update过程在以后的学习中再弄清楚(物理引擎是联合box2D进行的,需要系统的学习box2D知识)。
第二句PoolManager::getInstance()->getCurrentPool()->clear() 内存管理机制的自动回收过程。cocos2d的内存管理方式在以后的学习中具体学习,但可以清楚的是,cocos2d使用计数器方式:所有类都继承于一个始祖类Ref,而始祖类中包含三个神奇的内存管理方法:retain();release();autorelease();:
retain使计数器加1;release使计数器减一,若归零则清除之delete this,且从自动管理池中去除;autorelease会将this加入当前的自动管理池(PoolManager::getInstance()->getCurrentPool()->addObject(this);),在每一帧画面时判断其是否应当去除。2.pollEvents跟踪到:
无奈 =.=、 跟踪不下去了。。。 好吧,到此为止。
循环后的部分主要循环的判定条件是:while (!glview->windowShouldClose()):
当window should close时,将跳出循环,结束当前应用程序:
看一下这里所说的,Director::mainLoop确实是一个框架逻辑,但我们希望关闭窗口时,我们应该调用Director::end()方法,还要再调用一次Director::mainLoop()。
即在Director::mainLoop()中,会执行清除Director的工作。
Cocos2d-JS特效 Cocos2d-JS提供了很多特效,这些特效事实上属于间隔动作,特效类cc.GridAction类,也称为网格动作,它的类图如下图所示。网格动作类图网格动作cc.GridActio
Cocos2d-JS动画 与动作密不可分的还有动画,动画又可以分为场景过渡动画和帧动画。场景过渡动画我们在以往介绍过,这一个我们只介绍帧动画。帧动画帧动画就是
【深入了解cocos2d-x 3.x】内置数据结构(2)——Map 其实最没意思的数据结构就是Map和Vector这两个了,完完全全就是std::map和std::vector上面再加了一层引用计数。当然,这也有好处,就是支持std算法以及支
标签: 游戏引擎官方平台
本文链接地址:https://www.jiuchutong.com/biancheng/369064.html 转载请保留说明!友情链接: 武汉网站建设