• Cocos2d-x之物理世界(物体之间的碰撞)


    Cocos2d-x之物理世界(物体之间的碰撞)

    在HelloWorldScene.h中添加如下内容,并让其继承public b2ContactListener

    private:

        b2Body *groundBody;//创建一个地板

    public:

    //继承的b2ContactListener实现

    virtual void BeginContact(b2Contact* contact);

    HelloWorldScene。cpp

      1 #include "HelloWorldScene.h"
      2 #include "cocostudio/CocoStudio.h"
      3 #include "ui/CocosGUI.h"
      4 
      5 USING_NS_CC;
      6 
      7 using namespace cocostudio::timeline;
      8 
      9 //定义中间的比例为80(box2d和cocos2d的转换比例)
     10 #define RATIO 80.0f
     11 
     12 Scene* HelloWorld::createScene()
     13 {
     14     // 'scene' is an autorelease object
     15     auto scene = Scene::create();
     16     
     17     // 'layer' is an autorelease object
     18     auto layer = HelloWorld::create();
     19 
     20     // add layer as a child to scene
     21     scene->addChild(layer);
     22 
     23     // return the scene
     24     return scene;
     25 }
     26 
     27 // on "init" you need to initialize your instance
     28 bool HelloWorld::init()
     29 {
     30     //////////////////////////////
     31     // 1. super init first
     32     if ( !Layer::init() )
     33     {
     34         return false;
     35     }
     36     //创建一个世界,b2world(二维矢量类型的,指定世界的加速度的方向
     37     //b2Vec2(加速度的方向,向下的,所以x轴没有为0,y轴为-10))这样才能往下落
     38     world = new b2World(b2Vec2(0, -10));
     39     
     40     //设置链接的监听器
     41     world->SetContactListener(this);
     42     
     43     
     44     
     45 //    //添加一个矩形,然后调用scheduleUpdate方法,实现矩形的下落,随着重力加速向下运动
     46 //    addRect();
     47     
     48     //添加一个地板
     49     addGround();
     50     
     51     //复制矩形的代码后,他只是不受重力的影响
     52 //    //让矩形在x轴平移
     53 //    addRect(0, 5, b2_kinematicBody);
     54 
     55 //    //让矩形在y轴向上移动,然后向下加速运动
     56 //    addRect(8, 5, b2_dynamicBody);
     57     
     58     //让矩形在y轴向上移动,然后向下加速运动
     59     addRect(5, 3, b2_dynamicBody);
     60     
     61     
     62     //调用update方法,实现每帧都改变物理世界中的物体
     63     scheduleUpdate();
     64 
     65     return true;
     66 }
     67 
     68 
     69 //实现模拟物理世界的方法(当前一帧与上一帧的时间差)
     70 void HelloWorld::update(float dt){
     71     
     72     //使用这个step方法来一步一步的模拟我们的物理世界
     73     //(时间差(当前一步与最后一步的时间差,即当前一帧与上一帧的时间差),
     74     //速度迭代,模拟物理世界的过程中难免会有误差,所以就用速度迭代的次数来避免误差,官方建议8次,
     75     //位置的迭代,官方建议3次)
     76     world->Step(dt, 8, 3);
     77     
     78     //为了获取矩形,所以在这里定义一个Sprite
     79     Sprite *s;
     80     
     81     //获取移动的矩形
     82     //在这里获取到所有的子集的对象
     83     //遍历所有的子集对象,
     84     for (b2Body *b = world->GetBodyList(); b; b = b->GetNext()) {
     85 //        //判断,因为只有一个动态的物体,所以可以这么判断,否则,要用别的方法
     86 //        if (b->GetType() == b2_dynamicBody) {
     87         //让所有的类型都要刷新
     88             //获取到移动的物体的y 位置
     89 //            log("%f",b->GetPosition().y);
     90         
     91             if (b->GetUserData()) {
     92                 s = (Sprite*)b->GetUserData();
     93                 
     94                 //让Sprite与body同步
     95                 s->setPosition(b->GetPosition().x * RATIO, b->GetPosition().y * RATIO);
     96             }
     97 //        }
     98     }
     99 }
    100 
    101 
    102 
    103 //创建矩形,并且让其随着重力开始运动,有加速度的向下移动
    104 void HelloWorld::addRect(){
    105     
    106     //config box2d
    107     ///*******************************************************************
    108     //定义一个b2BodyDef物体
    109     b2BodyDef def;
    110     
    111 //    //指定def的初始化的position,x轴是0,y轴是10,代表着从10往下落
    112 //    def.position = b2Vec2(0, 10);
    113     //定义完比例后开始修改位置,因为最高为6米,所以y轴定义为5,x轴最大为10米
    114     def.position = b2Vec2(3, 5);
    115     
    116     //配置物体的属性
    117     //b2_dynamicBody是枚举类型的,代表运动的物体,
    118     //还有b2_staticBody  代表静态的物体
    119     //还有b2_kinematicBody  代表悬浮的物体
    120     def.type = b2_dynamicBody;//此时这是个运动的物体
    121     
    122     //创建一个物体(物体的相关的定义)
    123     b2Body *body = world->CreateBody(&def);
    124     
    125     ///*******************************************************************
    126     
    127     
    128     
    129     
    130     //指定物体的fixture
    131     ///*******************************************************************
    132     
    133     b2PolygonShape shape;
    134     shape.SetAsBox(0.5, 0.5);//设置一个一米的箱子
    135     
    136     
    137     b2FixtureDef fixtureDef;
    138     //指定fixtuer的属性
    139     fixtureDef.density = 1;//密度
    140     fixtureDef.friction = 0.3;//摩擦系数
    141     fixtureDef.shape = &shape;
    142     body->CreateFixture(&fixtureDef);
    143     
    144     ///*******************************************************************
    145     
    146     
    147     
    148     
    149     
    150     //config cocos shape
    151     ///*******************************************************************
    152     //定义一个图形
    153     auto s = Sprite::create();
    154 //    //指定他的Texture图形区域
    155 //    s->setTextureRect(Rect(0, 0, 80, 80));
    156 
    157     //指定加入fixture的图形的区域
    158     s->setTextureRect(Rect(0, 0, 0.5 * 2 * RATIO, 0.5 * 2 * RATIO));
    159     
    160     //将其添加到层中
    161     addChild(s);
    162     
    163     //配置位置
    164     //cocos2d的图形区域的位置是(800 x 600)
    165     //box2d的范围单位是米,官方文档上的比较精确的范围是10米之内
    166     //意味着800px的位置当成10米是比较合理的,所以中间的比例是80
    167     
    168 //    //因为每一帧都同步了,所以此处可以不要了,
    169 //    //因为update中的s->setPosition(b->GetPosition().x * RATIO,
    170 //    //b->GetPosition().y * RATIO);所以就不要了
    171 //    //配置s的位置
    172 //    s->setPosition(Point(def.position.x * RATIO, def.position.y * RATIO));
    173     
    174     //将图形和body相关起来
    175     body->SetUserData(s);//这样就将图形和body绑定起来了
    176     
    177     ///*******************************************************************
    178 }
    179 
    180 
    181 
    182 
    183 //直接复制上面的代码
    184 //创建矩形,并且让其随着重力开始运动,有加速度的向下移动
    185 void HelloWorld::addRect(float positionx, float positiony, b2BodyType type){
    186     
    187     //config box2d
    188     ///*******************************************************************
    189     //定义一个b2BodyDef物体
    190     b2BodyDef def;
    191     
    192     //    //指定def的初始化的position,x轴是0,y轴是10,代表着从10往下落
    193     //    def.position = b2Vec2(0, 10);
    194     //定义完比例后开始修改位置,因为最高为6米,所以y轴定义为5,x轴最大为10米
    195     def.position = b2Vec2(positionx, positiony);
    196     
    197 //    //设置矩形的线性初速度,x轴平移
    198 //    def.linearVelocity = b2Vec2(1, 0);
    199 
    200     //设置矩形的线性速度,y轴向上的速度
    201     def.linearVelocity = b2Vec2(0, 10);
    202     
    203     
    204     //配置物体的属性
    205     //b2_dynamicBody是枚举类型的,代表运动的物体,
    206     //还有b2_staticBody  代表静态的物体
    207     //还有b2_kinematicBody  代表悬浮的物体
    208     def.type = type;//此时这是个运动的物体
    209     
    210     //创建一个物体(物体的相关的定义)
    211     b2Body *body = world->CreateBody(&def);
    212     
    213     ///*******************************************************************
    214     
    215     
    216     
    217     
    218     //指定物体的fixture
    219     ///*******************************************************************
    220     
    221     b2PolygonShape shape;
    222     shape.SetAsBox(0.5, 0.5);//设置一个一米的箱子
    223     
    224     
    225     b2FixtureDef fixtureDef;
    226     //指定fixtuer的属性
    227     fixtureDef.density = 1;//密度
    228     fixtureDef.friction = 0.3;//摩擦系数
    229     fixtureDef.shape = &shape;
    230     body->CreateFixture(&fixtureDef);
    231     
    232     ///*******************************************************************
    233     
    234     
    235     
    236     
    237     
    238     //config cocos shape
    239     ///*******************************************************************
    240     //定义一个图形
    241     auto s = Sprite::create();
    242     //    //指定他的Texture图形区域
    243     //    s->setTextureRect(Rect(0, 0, 80, 80));
    244     
    245     //指定加入fixture的图形的区域
    246     s->setTextureRect(Rect(0, 0, 0.5 * 2 * RATIO, 0.5 * 2 * RATIO));
    247     
    248     //将其添加到层中
    249     addChild(s);
    250     
    251     //配置位置
    252     //cocos2d的图形区域的位置是(800 x 600)
    253     //box2d的范围单位是米,官方文档上的比较精确的范围是10米之内
    254     //意味着800px的位置当成10米是比较合理的,所以中间的比例是80
    255     
    256     //    //因为每一帧都同步了,所以此处可以不要了,
    257     //    //因为update中的s->setPosition(b->GetPosition().x * RATIO,
    258     //    //b->GetPosition().y * RATIO);所以就不要了
    259     //    //配置s的位置
    260     //    s->setPosition(Point(def.position.x * RATIO, def.position.y * RATIO));
    261     
    262     //将图形和body相关起来
    263     body->SetUserData(s);//这样就将图形和body绑定起来了
    264     
    265     ///*******************************************************************
    266     
    267     
    268     
    269     
    270 }
    271 
    272 
    273 //添加一个地板
    274 void HelloWorld::addGround(){
    275     
    276     //创建一个静态的物体
    277     
    278     b2BodyDef def;
    279     //指定位置
    280 //    def.position = b2Vec2(0, 0);
    281     //为了让创建的地板铺满底部,
    282     def.position = b2Vec2(400 / RATIO, 0);
    283     //指定def的类型,静态的物体
    284     def.type = b2_staticBody;
    285     
    286 //    b2Body *body = world->CreateBody(&def);    
    287     groundBody = world->CreateBody(&def);
    288     
    289     
    290     b2PolygonShape groundShape;
    291     //默认情况下指的是半宽和半高,单位为米
    292     groundShape.SetAsBox(400 / RATIO, 0.5);
    293     
    294     b2FixtureDef fixuredef;
    295     //指定fixture的属性
    296     fixuredef.density = 1;//密度
    297     fixuredef.friction = 0.3;//摩擦系数
    298     //为其指定一个图形区域,让其与其他图形有一个碰撞的作用
    299     fixuredef.shape = &groundShape;
    300     
    301 //    body->CreateFixture(&fixuredef);
    302     groundBody->CreateFixture(&fixuredef);
    303     
    304     
    305 }
    306 
    307 
    308 
    309 void HelloWorld::BeginContact(b2Contact *contact){
    310     
    311     //链接的两个对象的fixture
    312     //不管怎么样,最终都要落到地板上
    313     if (contact->GetFixtureA()->GetBody() == groundBody || contact->GetFixtureB()->GetBody() == groundBody) {
    314         log("有物体落在地板上*——*");
    315     }
    316     
    317     
    318 }
  • 相关阅读:
    Nightingale 加发邮件功能
    Centos7 系统进程解析
    Nightingale 夜莺监控系统 安装
    iptables:应用防火墙规则:ptables-restore: line xxx failed [失败]
    CAD2011卸载不干净 无法重装问题
    Make Globle HS 全局热备
    Swarm工具使用
    docker-registry构建私有的镜像仓库
    MySQL Replication
    javascript 设计模式之单例模式
  • 原文地址:https://www.cnblogs.com/dudu580231/p/4388903.html
Copyright © 2020-2023  润新知