结合物理引擎的cocos2dx游戏(保卫果树)
2014-12-09 14:24
351 查看
physic是coco2dx3.0自带的物理引擎,应付一般的需求已经足够啦。
项目地址:
https://github.com/frank1982/Fruits
核心代码:
_arrowArray=Array::create();
_arrowArray->retain();
_birdArray=Array::create();
_birdArray->retain();
设置小鸟和弓箭的存贮array;
auto layer = GameScene::create();
layer->setPhyWorld(scene->getPhysicsWorld());
设置物理世界;
auto listener =
EventListenerTouchOneByOne::create();
listener->setSwallowTouches(true);
auto contactListener=EventListenerPhysicsContact::create();
//设置监听器的碰撞开始函数
contactListener->onContactBegin =
CC_CALLBACK_1(GameScene::onContactBegin,
this);
//添加到事件分发器中
_eventDispatcher->addEventListenerWithSceneGraphPriority(contactListener,
this);
设置物理碰撞(小鸟和弓箭)和触摸检测;
auto str=String::createWithFormat("SCORE: %d",SCORE);
_scoreLabel=LabelTTF::create(str->getCString(),
"Arial", 40);
_scoreLabel->setPosition(visibleSize.width/2,visibleSize.height-_scoreLabel->getContentSize().height);
_scoreLabel->setColor(Color3B::GREEN);
addChild(_scoreLabel,2);
//计算得分;
auto str2=String::createWithFormat("X %d",FRUITS_NUM);
_fruitNum=LabelTTF::create(str2->getCString(),
"Arial", 40);
_fruitNum->setPosition(fruit->getPosition()+Point(50,0));
_fruitNum->setColor(Color3B::RED);
addChild(_fruitNum,2);
//计算剩余果实的数量;
listener->onTouchBegan=[&](Touch* touch,
Event* event){
struct timeval tv;
gettimeofday(&tv,NULL);
_curTouchTime=tv.tv_sec *
1000 + tv.tv_usec /
1000;
if(_curTouchTime-_preTouchTime>=500){
_pointTouch=touch->getLocation();
Point shootVector =
_pointTouch-_bowl->getPosition();
Point normalizedVector =
ccpNormalize(shootVector) ;
float radians =
atan2(normalizedVector.y, - normalizedVector.x);
float degree =
CC_RADIANS_TO_DEGREES(radians);
_bowl->setRotation(degree);
_preTouchTime=_curTouchTime;
return true;
}else{
CCLOG("too much touch");
return false;
}
};
//当检测到触摸时,旋转弓箭的角度,并且500毫秒内只允许点击一次;
listener->onTouchEnded=[&](Touch* touch,
Event* event){
//shoot the arrow
SimpleAudioEngine::sharedEngine()->pauseBackgroundMusic();
SimpleAudioEngine::sharedEngine()->playEffect("music/shoot.mp3");
//播放射击音效;
Point shootVector =
_pointTouch-_bowl->getPosition();
Point normalizedVector =
ccpNormalize(shootVector) ;
CCLog("x speed is: %f, y speed is: %f",shootVector.x,shootVector.y);
_arrow=Sprite::create("Arrow.png");
_arrow->setTag(1);
addChild(_arrow);
//加载弓箭精灵;
_arrow->setPosition(_bowl->getPosition());
_arrow->setScale(arrow_scale);
_arrow->setRotation(_bowl->getRotation());
auto body=PhysicsBody::createBox(_arrow->getContentSize()*arrow_scale);
body->setMass(1.0f);
body->setCategoryBitmask(0x00000010);
body->setContactTestBitmask(0x00000001);
body->setCollisionBitmask(0x00000001);
//设置物理检测参数,弓箭和小鸟会发生碰撞;
_arrow->setPhysicsBody(body);
_arrow->getPhysicsBody()->setVelocity(Vect(normalizedVector.x*_arrowSpeed,normalizedVector.y*_arrowSpeed));
_arrow->getPhysicsBody()->setGravityEnable(true);
//设置初速度,和弓箭的旋转方向一致;
//_arrowArray=Array::create();
_arrowArray->addObject(_arrow);
CCLog("_arrowArray length is %zd",_arrowArray->count());
};
_eventDispatcher->addEventListenerWithSceneGraphPriority(listener,this);
void GameScene::loadBirds(float dt){
Size visibleSize = Director::getInstance()->getVisibleSize();
enum
birdType type[7]={Blue,Yellow,Green,Grey,Red,Orange,Coffee};
int index=(int)(CCRANDOM_0_1()*7);
auto birdSp=Bird::createBird(type[index]);
//random enter position;
float PY=(float)(CCRANDOM_0_1()*visibleSize.height);
birdSp->setPosition(0,PY);
addChild(birdSp,1);
_birdArray->addObject(birdSp);
auto fruit=this->getChildByTag(21);
//random speed;
float Speed=(float)(CCRANDOM_0_1()*2.5+3);
auto seq=Sequence::create(MoveTo::create(Speed, fruit->getPosition()),
DelayTime::create(1.2),CallFunc::create(CC_CALLBACK_0(GameScene::eatApple,
this)),
MoveTo::create(2,
Point(visibleSize.width,fruit->getPosition().y)),NULL);
birdSp->runAction(seq);
CCLOG("bird number is %zd",_birdArray->count());
}
//这里随机会出现一只小鸟,速度和位置都不确定,小鸟会飞到树上停留一下,吃掉苹果;
void GameScene::update(float dt){
Size visibleSize = Director::getInstance()->getVisibleSize();
auto rectWin=CCRectMake(0,
0, visibleSize.width, visibleSize.height);
for(int i=0;i<_arrowArray->count();i++){
auto sp=dynamic_cast<Sprite *>(_arrowArray->getObjectAtIndex(i));
//check if out of window;
if(sp->getPosition().x<=0||sp->getPosition().y>=visibleSize.height||sp->getPosition().x>=visibleSize.width||sp->getPosition().y<=0){
//sp->setVisible(false);
sp->removeAllChildren();
this->removeChild(sp);
_arrowArray->removeObjectAtIndex(i);
CCLog("_arrowArray length is %zd",_arrowArray->count());
}
}
for(int j=0;j<_birdArray->count();j++){
auto sp2=dynamic_cast<Sprite *>(_birdArray->getObjectAtIndex(j));
//check if out of window;
if(sp2->getPosition().x>=visibleSize.width||sp2->getPosition().y<=0){
sp2->removeAllChildren();
this->removeChild(sp2);
_birdArray->removeObjectAtIndex(j);
CCLog("_birdArray length is %zd",_birdArray->count());
}
}
}
//检测小鸟和弓箭是否越出边界;
bool GameScene::onContactBegin(const
PhysicsContact& contact){
CCLOG("get bound");
auto cnt = const_cast<PhysicsContact*>(&contact);
auto spA = cnt->getShapeA()->getBody()->getNode();
auto spB = cnt->getShapeB()->getBody()->getNode();
int tagA = spA->getTag();
int tagB = spB->getTag();
if(tagA == 2) {
spA->getPhysicsBody()->setGravityEnable(true);
spA->getPhysicsBody()->setVelocity(Point(0,-300));
spB->removeAllChildren();
this->removeChild(spB);
_arrowArray->removeObject(spB);
CCLog("_arrowArray length is %zd",_arrowArray->count());
}else if(tagB ==
2){
spB->getPhysicsBody()->setGravityEnable(true);
spB->getPhysicsBody()->setVelocity(Point(0,-300));
this->removeChild(spA);
_arrowArray->removeObject(spA);
CCLog("_arrowArray length is %zd",_arrowArray->count());
}
SCORE+=5;
auto str=String::createWithFormat("SCORE: %d",SCORE)-
aac7
>getCString();
_scoreLabel->setString(str);
return true;
}
//射中小鸟后,小鸟落地,得分;
项目地址:
https://github.com/frank1982/Fruits
核心代码:
_arrowArray=Array::create();
_arrowArray->retain();
_birdArray=Array::create();
_birdArray->retain();
设置小鸟和弓箭的存贮array;
auto layer = GameScene::create();
layer->setPhyWorld(scene->getPhysicsWorld());
设置物理世界;
auto listener =
EventListenerTouchOneByOne::create();
listener->setSwallowTouches(true);
auto contactListener=EventListenerPhysicsContact::create();
//设置监听器的碰撞开始函数
contactListener->onContactBegin =
CC_CALLBACK_1(GameScene::onContactBegin,
this);
//添加到事件分发器中
_eventDispatcher->addEventListenerWithSceneGraphPriority(contactListener,
this);
设置物理碰撞(小鸟和弓箭)和触摸检测;
auto str=String::createWithFormat("SCORE: %d",SCORE);
_scoreLabel=LabelTTF::create(str->getCString(),
"Arial", 40);
_scoreLabel->setPosition(visibleSize.width/2,visibleSize.height-_scoreLabel->getContentSize().height);
_scoreLabel->setColor(Color3B::GREEN);
addChild(_scoreLabel,2);
//计算得分;
auto str2=String::createWithFormat("X %d",FRUITS_NUM);
_fruitNum=LabelTTF::create(str2->getCString(),
"Arial", 40);
_fruitNum->setPosition(fruit->getPosition()+Point(50,0));
_fruitNum->setColor(Color3B::RED);
addChild(_fruitNum,2);
//计算剩余果实的数量;
listener->onTouchBegan=[&](Touch* touch,
Event* event){
struct timeval tv;
gettimeofday(&tv,NULL);
_curTouchTime=tv.tv_sec *
1000 + tv.tv_usec /
1000;
if(_curTouchTime-_preTouchTime>=500){
_pointTouch=touch->getLocation();
Point shootVector =
_pointTouch-_bowl->getPosition();
Point normalizedVector =
ccpNormalize(shootVector) ;
float radians =
atan2(normalizedVector.y, - normalizedVector.x);
float degree =
CC_RADIANS_TO_DEGREES(radians);
_bowl->setRotation(degree);
_preTouchTime=_curTouchTime;
return true;
}else{
CCLOG("too much touch");
return false;
}
};
//当检测到触摸时,旋转弓箭的角度,并且500毫秒内只允许点击一次;
listener->onTouchEnded=[&](Touch* touch,
Event* event){
//shoot the arrow
SimpleAudioEngine::sharedEngine()->pauseBackgroundMusic();
SimpleAudioEngine::sharedEngine()->playEffect("music/shoot.mp3");
//播放射击音效;
Point shootVector =
_pointTouch-_bowl->getPosition();
Point normalizedVector =
ccpNormalize(shootVector) ;
CCLog("x speed is: %f, y speed is: %f",shootVector.x,shootVector.y);
_arrow=Sprite::create("Arrow.png");
_arrow->setTag(1);
addChild(_arrow);
//加载弓箭精灵;
_arrow->setPosition(_bowl->getPosition());
_arrow->setScale(arrow_scale);
_arrow->setRotation(_bowl->getRotation());
auto body=PhysicsBody::createBox(_arrow->getContentSize()*arrow_scale);
body->setMass(1.0f);
body->setCategoryBitmask(0x00000010);
body->setContactTestBitmask(0x00000001);
body->setCollisionBitmask(0x00000001);
//设置物理检测参数,弓箭和小鸟会发生碰撞;
_arrow->setPhysicsBody(body);
_arrow->getPhysicsBody()->setVelocity(Vect(normalizedVector.x*_arrowSpeed,normalizedVector.y*_arrowSpeed));
_arrow->getPhysicsBody()->setGravityEnable(true);
//设置初速度,和弓箭的旋转方向一致;
//_arrowArray=Array::create();
_arrowArray->addObject(_arrow);
CCLog("_arrowArray length is %zd",_arrowArray->count());
};
_eventDispatcher->addEventListenerWithSceneGraphPriority(listener,this);
void GameScene::loadBirds(float dt){
Size visibleSize = Director::getInstance()->getVisibleSize();
enum
birdType type[7]={Blue,Yellow,Green,Grey,Red,Orange,Coffee};
int index=(int)(CCRANDOM_0_1()*7);
auto birdSp=Bird::createBird(type[index]);
//random enter position;
float PY=(float)(CCRANDOM_0_1()*visibleSize.height);
birdSp->setPosition(0,PY);
addChild(birdSp,1);
_birdArray->addObject(birdSp);
auto fruit=this->getChildByTag(21);
//random speed;
float Speed=(float)(CCRANDOM_0_1()*2.5+3);
auto seq=Sequence::create(MoveTo::create(Speed, fruit->getPosition()),
DelayTime::create(1.2),CallFunc::create(CC_CALLBACK_0(GameScene::eatApple,
this)),
MoveTo::create(2,
Point(visibleSize.width,fruit->getPosition().y)),NULL);
birdSp->runAction(seq);
CCLOG("bird number is %zd",_birdArray->count());
}
//这里随机会出现一只小鸟,速度和位置都不确定,小鸟会飞到树上停留一下,吃掉苹果;
void GameScene::update(float dt){
Size visibleSize = Director::getInstance()->getVisibleSize();
auto rectWin=CCRectMake(0,
0, visibleSize.width, visibleSize.height);
for(int i=0;i<_arrowArray->count();i++){
auto sp=dynamic_cast<Sprite *>(_arrowArray->getObjectAtIndex(i));
//check if out of window;
if(sp->getPosition().x<=0||sp->getPosition().y>=visibleSize.height||sp->getPosition().x>=visibleSize.width||sp->getPosition().y<=0){
//sp->setVisible(false);
sp->removeAllChildren();
this->removeChild(sp);
_arrowArray->removeObjectAtIndex(i);
CCLog("_arrowArray length is %zd",_arrowArray->count());
}
}
for(int j=0;j<_birdArray->count();j++){
auto sp2=dynamic_cast<Sprite *>(_birdArray->getObjectAtIndex(j));
//check if out of window;
if(sp2->getPosition().x>=visibleSize.width||sp2->getPosition().y<=0){
sp2->removeAllChildren();
this->removeChild(sp2);
_birdArray->removeObjectAtIndex(j);
CCLog("_birdArray length is %zd",_birdArray->count());
}
}
}
//检测小鸟和弓箭是否越出边界;
bool GameScene::onContactBegin(const
PhysicsContact& contact){
CCLOG("get bound");
auto cnt = const_cast<PhysicsContact*>(&contact);
auto spA = cnt->getShapeA()->getBody()->getNode();
auto spB = cnt->getShapeB()->getBody()->getNode();
int tagA = spA->getTag();
int tagB = spB->getTag();
if(tagA == 2) {
spA->getPhysicsBody()->setGravityEnable(true);
spA->getPhysicsBody()->setVelocity(Point(0,-300));
spB->removeAllChildren();
this->removeChild(spB);
_arrowArray->removeObject(spB);
CCLog("_arrowArray length is %zd",_arrowArray->count());
}else if(tagB ==
2){
spB->getPhysicsBody()->setGravityEnable(true);
spB->getPhysicsBody()->setVelocity(Point(0,-300));
this->removeChild(spA);
_arrowArray->removeObject(spA);
CCLog("_arrowArray length is %zd",_arrowArray->count());
}
SCORE+=5;
auto str=String::createWithFormat("SCORE: %d",SCORE)-
aac7
>getCString();
_scoreLabel->setString(str);
return true;
}
//射中小鸟后,小鸟落地,得分;
相关文章推荐
- Cocos2dx 学习笔记 -TMX和物理引擎的结合
- 关于Cocos2dx这个游戏引擎
- cocos2dx-3.0 中的物理引擎Box2D使用(二)
- cocos2dx-3.0 中的物理引擎Box2D使用(三)
- cocos2dx-3.0 中的物理引擎Box2D使用(四)
- Atitit 游戏引擎---物理系统(1)------爆炸效果
- HTML5游戏开发进阶 4 :物理引擎集成
- cocos2dx概要及开发技术—认识cocos2d-x游戏引擎
- 基于HTML5的WebGL结合Box2DJS物理引擎应用
- 自己动手写cocos2dx游戏引擎(五)——渲染对象
- ubuntu 下 cocos2dx游戏引擎搭建 编译和使用(可以在linux桌面 安卓手机运行)
- 游戏引擎剖析--第5部分: 物理,运动,效果
- cocos2d-x游戏引擎核心(3.x)----事件分发机制之事件从(android,ios,desktop)系统传到cocos2dx的过程浅析
- 【麦可网】Cocos2d-X跨平台游戏开发学习笔记---第二十五课:Cocos2D-X物理引擎之Box2D8-10
- delta3d与ode物理引擎的结合。
- 2、Cocos2dx 3.0游戏开发找小三之引擎简介
- Atitit 游戏引擎---物理系统(1)------爆炸效果
- 游戏引擎剖析 (5) 物理,运动,效果
- 游戏引擎架构----物理部分
- 如何制作一款像超级玛丽兄弟一样基于平台的游戏-第二部分 (xcode,物理引擎,TMXTiledMap相关应用)