cocos2d-x游戏开发 跑酷(两) 物理世界
原创。转载请注明出处:http://blog.csdn.net/dawn_moon/article/details/21240343
泰然的跑酷用的chipmunk物理引擎。我没有细致学过这个东西。
只是我看了一下他们的使用方法,感觉跟box2d差点儿相同。box2d用纯真的面向对象C++开发,用在这里应该没有问题,试一下。
泰然的project没有增加box2d模块。所以须要增加。
将external/Box2D增加project,将没用的引用删掉。增加后结构例如以下
然后新建一个PlayScene类。開始创建物理世界。
为了方便调试box2d物理世界,须要接入debug渲染器。将TestCpp/Classes/Box2DTestBed/下的GLES-Render.h和GLES-Render.cpp增加到project,这个能够绘制出物理模型的形状。
由于box2d针对0-10米的仿真做过优化。所以我这里将像素大小映射到10左右
- #define RATIO 32
- //
- // PlayScene.h
- // Parkour
- //
- // Created by lerry on 14-3-14.
- // Copyright (c) 2014年 Goonear Co.,Ltd. All rights reserved.
- //
- #ifndef __Parkour__PlayScene__
- #define __Parkour__PlayScene__
- #include "cocos2d.h"
- #include "Box2D.h"
- #include "GLES-Render.h"
- #define RATIO 32
- #define GROUND_HEIGHT 57
- #define RUUNER_STARTX 80
- class PlayScene : public cocos2d::CCLayer
- {
- b2World* mWorld;
- GLESDebugDraw* mDebugDraw;
- private:
- // 初始化物理世界
- void initPhysics();
- // 绘制物理世界debug区域
- void draw();
- // 开启物理世界debug
- void setDebug(bool isDebug);
- public:
- virtual bool init();
- virtual void update(float dt);
- CREATE_FUNC(PlayScene);
- static cocos2d::CCScene* scene();
- };
- #endif /* defined(__Parkour__PlayScene__) */
如今主要有一个初始化物理世界的函数initPhysics()函数,在这里创建了一个地板。
- void PlayScene::initPhysics()
- {
- mWorld = new b2World(b2Vec2(0, -10));
- mWorld->SetAllowSleeping(true);
- mWorld->SetContinuousPhysics(true);
- // mWorld->SetContactListener(this);
- // 地板body
- b2Body* ground = NULL;
- b2BodyDef bd;
- ground = mWorld->CreateBody(&bd);
- // 地板
- b2EdgeShape shape;
- shape.Set(b2Vec2(0, GROUND_HEIGHT / RATIO), b2Vec2(INT_MAX, GROUND_HEIGHT / RATIO));
- ground->CreateFixture(&shape, 0.0f);
- setDebug(true);
- }
这里创建了一个边缘形状。边缘形状类似静态物体。可是它没有体积。box2d里面的碰撞算法要求碰撞的两个物体至少一个要有体积。所以边缘形状不能和边缘形状碰撞。能够和其它形状类物体碰撞。
box2d的物理世界有自己的世界循环函数。跟cocos2d-x的update函数类似,所以在update函数里面调用box2d的迭代函数
- void PlayScene::update(float dt)
- {
- // 物理世界的迭代函数
- mWorld->Step(dt, 10, 8);
- }
Step函数的參数解释一下,第一个时间參数,单步迭代步长,第二个參数单步时间内速度迭代次数。第三个參数但不是件内位置迭代次数。
这几个參数有建议值。我这里就取这几个值。
然后在MainScene.cpp的onPlay函数里面填上回调的实现:
- // startbutton回调
- void MainScene::onPay()
- {
- CCLog("onPlay click");
- // 创建带过渡的场景
- CCScene* s = CCTransitionFade::create(1, PlayScene::scene());
- CCDirector::sharedDirector()->replaceScene(s);
- }
这里加了一个过渡场景,跑起来看到一条线。初步完毕。