• Chapter 5


    Chapter 5 - How to Detect the Collisions

    Our hero can fire bullets now, but the bullets are only visual. So how can they kill their enemies?

    In this chapter, we will introduce Collision Detection to implement it.

    Firstly, it’s necessary to track the enemies and the bullets.

    In the game, we add a tag for these two kinds of sprites to identify them. Let tag = 1 if the sprite is an enemy, and tag = 2 mean it is a bullet. Because CCSprite inherits from CCNode, there is already a member variable m_nTag with methods setTag() and getTag(); we can implement this to identify the different types of sprites.

    Add the two member variables below to HelloWorld in HelloWorldScene.h. These are used to store the existing enemies and bullets.

    1// cpp with cocos2d-x
    2protected:
    3    cocos2d::CCArray *_targets;
    4    cocos2d::CCArray *_projectiles;    
    

    In cocos2d-x, CCMutableArray is an implementation of NSMutableArray in iOS which contains NSObject's and their subclasses. Something different is that you should specify the concrete category of its members.

    Then initialize the two variables in the construct function, new them in init(), and release them in the destruct function.

     1// cpp with cocos2d-x
     2
     3// in init()
     4// Initialize arrays
     5_targets = new CCArray;
     6_projectiles = new CCArray;
     7
     8HelloWorld::~HelloWorld()
     9{
    10  if (_targets)
    11  {
    12    _targets->release();
    13    _targets = NULL;
    14  }
    15
    16  if (_projectiles)
    17  {
    18    _projectiles->release();
    19    _projectiles = NULL;
    20  }
    21
    22  // cpp don't need to call super dealloc
    23  // virtual destructor will do this
    24}
    25
    26HelloWorld::HelloWorld()
    27:_targets(NULL)
    28,_projectiles(NULL)
    29{
    30}    
    

    Now modify addTarget() to add a new target to targets array, and set its tag to be 1.

    1// cpp with cocos2d-x
    2// Add to targets array
    3target->setTag(1);
    4_targets->addObject(target);    
    

    Modify ccTouchesEnded() to add a new bullet to bullets array, and set its tag to be 2.

    1// cpp with cocos2d-x
    2// Add to projectiles array
    3projectile->setTag(2);
    4_projectiles->addObject(projectile);    
    

    Then, modify spriteMoveFinished() as follows. Here we remove the sprites from their corresponding arrays.

     1// cpp with cocos2d-x
     2void HelloWorld::spriteMoveFinished(CCNode* sender)
     3{
     4  CCSprite *sprite = (CCSprite *)sender;
     5  this->removeChild(sprite, true);
     6
     7  if (sprite->getTag() == 1)  // target
     8  {
     9    _targets->removeObject(sprite);
    10  }
    11  else if (sprite->getTag() == 2) // projectile
    12  {
    13    _projectiles->removeObject(sprite);
    14  }
    15}    
    

    The function update() below is used to detect collisions every frame, remove the collided bullet and enemy from the scene.
    Declare it in HelloWorldScene.h and Define it in HelloWorldScene.cpp.

     1// cpp with cocos2d-x
     2void HelloWorld::update(float dt)
     3{
     4    CCArray *projectilesToDelete = new CCArray;
     5    CCArray* targetsToDelete =new CCArray;
     6    CCObject* it = NULL;
     7    CCObject* jt = NULL;
     8
     9    CCARRAY_FOREACH(_bullet, it)
    10    {
    11        CCSprite *projectile = dynamic_cast<CCSprite*>(it);
    12        CCRect projectileRect = CCRectMake(
    13                                           projectile->getPosition().x - (projectile->getContentSize().width/2),
    14                                           projectile->getPosition().y - (projectile->getContentSize().height/2),
    15                                           projectile->getContentSize().width,
    16                                           projectile->getContentSize().height);
    17
    18        CCARRAY_FOREACH(_target, jt)
    19        {
    20            CCSprite *target = dynamic_cast<CCSprite*>(jt);
    21            CCRect targetRect = CCRectMake(
    22                                           target->getPosition().x - (target->getContentSize().width/2),
    23                                           target->getPosition().y - (target->getContentSize().height/2),
    24                                           target->getContentSize().width,
    25                                           target->getContentSize().height);
    26
    27            if (projectileRect.intersectsRect(targetRect))
    28            {
    29                targetsToDelete->addObject(target);
    30                projectilesToDelete->addObject(projectile);
    31            }
    32        }
    33    }
    34
    35    CCARRAY_FOREACH(targetsToDelete, jt)
    36    {
    37        CCSprite *target = dynamic_cast<CCSprite*>(jt);
    38        _target->removeObject(target);
    39        this->removeChild(target, true);
    40    }
    41
    42    CCARRAY_FOREACH(projectilesToDelete, it)
    43    {
    44        CCSprite* projectile = dynamic_cast<CCSprite*>(it);
    45        _bullet->removeObject(projectile);
    46        this->removeChild(projectile, true);
    47    }
    48
    49    projectilesToDelete->release();
    50    targetsToDelete->release();
    51}    
    

    Ok, the last thing we should do is adding update() to the schedule to let it be called every frame.

    1// cpp with cocos2d-x
    2this->schedule( schedule_selector(HelloWorld::update) );    
    

    Compile and run the project, fire the bullets as you like, then: AH..AH.., the enemies are killed one by one.

  • 相关阅读:
    Python之坐标轴刻度细化、坐标轴设置、标题图例添加
    探索性数据分析
    http://blog.csdn.net/milton2017/article/details/54406482
    libsvm学习日记--1
    推荐系统评测指标—准确率(Precision)、召回率(Recall)、F值(F-Measure)
    python中if __name__ == '__main__': 的解析
    Python类
    TweenMax学习一
    vuejsLearn---通过手脚架快速搭建一个vuejs项目
    vuejsLearn--- -- 怎么查看、修改、追加数据---->data对象
  • 原文地址:https://www.cnblogs.com/yssgyw/p/3224265.html
Copyright © 2020-2023  润新知