原文同步发布于我的wiki,查看原文或更新请移步: 点击打开链接
原理
- Cocos里面的每个Node都有一个和它对应的矩形区域,通过api getBoundingBox()得到。碰撞监测就是判断两个物体的矩形区域是否有交叠,相应的API是intersectsRect。有交叠则认为是碰撞了。
Demo及源码
- 基于cocos 3.4final
- https://github.com/cheyiliu/CollisionDetection
Demo解读
- 每隔5s生成: 两架飞机,并从右往左飞行; 两颗子弹,从左向右飞。
- 每一帧里面作碰撞检测,若有碰撞,则播放相应的动画。
- 为了追踪所有的子弹和飞机,得有对应的辅助数据结构,这里采用Vector。
主要代码
- 开启相关timer
scheduleUpdate();
schedule(schedule_selector(HelloWorld::updateCustom), 5.0f,
kRepeatForever, 0);
- 生成子弹或者飞机并放到对应的辅助数据结构来跟踪
void HelloWorld::buildBullet(int startX, int endX, int actualY) {
log("buildBullet");
std::string name = "bullet1.png";
auto sp = Sprite::createWithSpriteFrameName(name);
Point startPos = Point(startX, actualY);
Point endPos = Point(endX, actualY);
sp->setPosition(startPos);
sp->runAction(
Sequence::create(MoveTo::create(3.0, endPos),
CallFuncN::create(this,
callfuncN_selector(HelloWorld::spriteDone)), NULL));
sp->setRotation(-90);
sp->setTag(TAG_BULLET);
mBullets.pushBack(sp);//放入数组
this->addChild(sp);
}
- 每一帧里作碰撞监测,这里简单demo了下。 更复杂的逻辑处理见扩展阅读
void HelloWorld::update(float dt) {
// log("update, %d", mPlanes.size());
// log("update, %d", mBullets.size());
//碰撞检测
Vector<Sprite*> bulletsToBeRemoved;
Vector<Sprite*> planeToBeRemoved;
for (auto bullet : mBullets) {
for (auto plane : mPlanes) {
if (bullet->boundingBox().intersectsRect(plane->getBoundingBox())) {
log("碰撞了。。。。。。。。");
bulletsToBeRemoved.pushBack(bullet);
planeToBeRemoved.pushBack(plane);
}
}
}
// do remove
for (auto bullet : bulletsToBeRemoved) {
mBullets.eraseObject(bullet);
log("removeChild(bullet)");
this->removeChild(bullet);
}
bulletsToBeRemoved.clear();
for (auto plane : planeToBeRemoved) {
mPlanes.eraseObject(plane);
planeBlowup(plane);
}
planeToBeRemoved.clear();
}
优缺点
- 优点: 对于简单需求,使用起来简单
- 缺点: 要费力的维护几个数组,当需求复杂时不易扩充和复用
效果图
https://github.com/cheyiliu/All-in-One/raw/master/res/cocos2d/CollisionDetection-way1-use-intersectsRect.gif
扩展阅读
- AABB碰撞原理: http://blog.csdn.net/u012945598/article/details/39524343
- 飞机大战碰撞: http://blog.csdn.net/jackystudio/article/details/11917875
时间: 2024-10-08 06:50:52