这个游戏代码很少,用来了解下Cocos2d-x大致的工作流程
开发环境为win7 64位+VS2013+Cocos2d-x3.4,创建项目过程省略。
参考资料http://cn.cocos2d-x.org/tutorial/show?id=2529
这个游戏只需要更改创建好的项目中两个文件,分别是HelloWorldScene.h和HelloWorldScene.cpp,所需的图片和声音资源在这里下载Resources连个文件在这里下载代码
HelloWorldScene.h的代码和注释如下
#ifndef __HELLOWORLD_SCENE_H__
#define __HELLOWORLD_SCENE_H__
#include "cocos2d.h"
#include "SimpleAudioEngine.h"//支持简单声音文件
USING_NS_CC;
class HelloWorld : public cocos2d::Layer
{
public:
// there's no 'id' in cpp, so we recommend returning the class instance pointer
static cocos2d::Scene* createScene();
// Here's a difference. Method 'init' in cocos2d-x returns bool, instead of returning 'id' in cocos2d-iphone
virtual bool init();//初始化函数
void addMonster(float dt);//添加一个怪兽
// a selector callback
void menuCloseCallback(cocos2d::Ref* pSender);
virtual bool onTouchBegan(Touch* pTouch, Event* pEvent);//在触摸事件开始时调用
virtual void onTouchMoved(Touch* pTouch, Event* pEvent);//在滑动事件发生时调用
virtual void onTouchEnded(Touch* pTouch, Event* pEvent);//在触摸事件结束时调用
// implement the "static create()" method manually
CREATE_FUNC(HelloWorld);
bool onContactBegin(const PhysicsContact& contact);//检测到发生物理碰撞时调用
private:
std::vector Monster;//声明一个精灵类表示怪兽
std::vector projectile;//声明一个精灵类表示飞镖
EventListenerTouchOneByOne* touch_listener;//声明一个时间监听器坚挺触碰事件
Sprite* _player;//声明一个精灵类表示玩家
int i, j;定义两个变量
};
#endif // __HELLOWORLD_SCENE_H__
HelloWorldScene.cpp代码和注释如下
#include "HelloWorldScene.h"
USING_NS_CC;
Scene* HelloWorld::createScene()
{
// 'scene' is an autorelease object
//1
auto scene = Scene::createWithPhysics();//创建一个物理世界
//2
scene->getPhysicsWorld()->setGravity(Vect(0, 0));//设置重力参数,这里表示水平和垂直方向都没有重力加速度
//3
scene->getPhysicsWorld()->setDebugDrawMask(PhysicsWorld::DEBUGDRAW_NONE);//调试参数,DEBUGDRAW_NONE表示关闭调试
// 'layer' is an autorelease object
auto layer = HelloWorld::create();
// add layer as a child to scene
scene->addChild(layer);
// return the scene
return scene;
}
// on "init" you need to initialize your instance
bool HelloWorld::init()
{
//////////////////////////////
// 1. super init first
if ( !Layer::init() )
{
return false;
}
i = 0;
j = 0;
Size visibleSize = Director::getInstance()->getVisibleSize();
Vec2 origin = Director::getInstance()->getVisibleOrigin();
/////////////////////////////
// 2. add a menu item with "X" image, which is clicked to quit the program
// you may modify it.
// add a "close" icon to exit the progress. it's an autorelease object
auto closeItem = MenuItemImage::create(
"CloseNormal.png",
"CloseSelected.png",
CC_CALLBACK_1(HelloWorld::menuCloseCallback, this));
closeItem->setPosition(Vec2(origin.x + visibleSize.width - closeItem->getContentSize().width/2 ,
origin.y + closeItem->getContentSize().height/2));
// create menu, it's an autorelease object
auto menu = Menu::create(closeItem, NULL);
menu->setPosition(Vec2::ZERO);
this->addChild(menu, 1);
/////////////////////////////
// 3. add your codes below...
CocosDenshion::SimpleAudioEngine::sharedEngine()->playBackgroundMusic("mt.mp3", true);//添加背景音乐,现在的问题是,点击鼠标后就会停止
touch_listener = EventListenerTouchOneByOne::create();
touch_listener->setSwallowTouches(false);//不向下触摸,简单点来说,比如有两个sprite,A和B,A在上,B在下(未知重叠),触摸A的时候,B不受影响
touch_listener->onTouchBegan = CC_CALLBACK_2(HelloWorld::onTouchBegan, this);//调用触摸时间处理函数
touch_listener->onTouchMoved = CC_CALLBACK_2(HelloWorld::onTouchMoved, this);
touch_listener->onTouchEnded = CC_CALLBACK_2(HelloWorld::onTouchEnded, this);
touch_listener->onTouchCancelled = CC_CALLBACK_2(HelloWorld::onTouchCancelled, this);
_eventDispatcher->addEventListenerWithSceneGraphPriority(touch_listener, this);//与事件监听器绑定
// add a label shows "Hello World"
// create and initialize a label
auto label = Label::createWithTTF("Hello World", "fonts/Marker Felt.ttf", 24);
// position the label on the center of the screen
label->setPosition(Vec2(origin.x + visibleSize.width/2,
origin.y + visibleSize.height - label->getContentSize().height));
// add the label as a child to this layer
this->addChild(label, 1);
// add "HelloWorld" splash screen"
auto sprite = Sprite::create("HelloWorld.png");
// position the sprite on the center of the screen
sprite->setPosition(Vec2(visibleSize.width/2 + origin.x, visibleSize.height/2 + origin.y));
// add the sprite as a child to this layer
this->addChild(sprite, 0);
LayerColor* _layer = LayerColor::create(Color4B(255, 255, 255, 255), visibleSize.width, visibleSize.height);//设置背景颜色
this->addChild(_layer);
_player = Sprite::create("player_hd.png");//添加精灵
_player->setPosition(visibleSize.width/8, visibleSize.height/2);//设置精灵的位置
this->addChild(_player);
this->schedule(schedule_selector(HelloWorld::addMonster), 1);
EventListenerPhysicsContact *contact_listener = EventListenerPhysicsContact::create();//创建物理碰撞检测监听器
contact_listener->onContactBegin = CC_CALLBACK_1(HelloWorld::onContactBegin, this);
_eventDispatcher->addEventListenerWithSceneGraphPriority(contact_listener, this);//绑定物理碰撞检测监听器
return true;
}
void HelloWorld::menuCloseCallback(Ref* pSender)
{
#if (CC_TARGET_PLATFORM == CC_PLATFORM_WP8) || (CC_TARGET_PLATFORM == CC_PLATFORM_WINRT)
MessageBox("You pressed the close button. Windows Store Apps do not implement a close button.","Alert");
return;
#endif
Director::getInstance()->end();
#if (CC_TARGET_PLATFORM == CC_PLATFORM_IOS)
exit(0);
#endif
}
void HelloWorld::addMonster(float dt)
{
Size visibleSize = Director::getInstance()->getVisibleSize();
Sprite* MonsterExample = Sprite::create("monster_hd.png");
i = i + 1;
auto OneBody = PhysicsBody::createBox(MonsterExample->getContentSize());//创建物理刚体
//MonsterExample = Sprite::create("monster_hd.png");
OneBody->setContactTestBitmask(0x08);//设置碰撞检测参数,不为0即开启碰撞检测
MonsterExample->setPhysicsBody(OneBody);//绑定刚体与精灵
MonsterExample->setPosition(
visibleSize.width + MonsterExample->getContentSize().width,
MonsterExample->getContentSize().height / 2 + CCRANDOM_0_1()*(visibleSize.height - MonsterExample->getContentSize().height / 2));//设置精灵出现的位置
Monster.push_back(MonsterExample);
this->addChild(Monster.back(), i);
MoveTo* Move = MoveTo::create(3, Vec2(-Monster.back()->getContentSize().width / 2, Monster.back()->getPosition().y));//设置精灵的移动方向与速度
Monster.back()->runAction(Move);
}
bool HelloWorld::onTouchBegan(Touch* pTouch, Event*pEvent)
{
Size visibleSize = Director::getInstance()->getVisibleSize();
Point touchLocation = pTouch->getLocationInView();
touchLocation = Director::getInstance()->convertToGL(touchLocation);
Sprite* projectileExmaple = Sprite::create("projectile_hd.png");
CocosDenshion::SimpleAudioEngine::sharedEngine()->playBackgroundMusic("smzy.mp3", true);
j += 1;
auto OneBody = PhysicsBody::createBox(projectileExmaple->getContentSize());
OneBody->setContactTestBitmask(0x04);
projectileExmaple->setPhysicsBody(OneBody);
projectileExmaple->setPosition(visibleSize.width / 8, visibleSize.height / 2);
projectile.push_back(projectileExmaple);
this->addChild(projectile.back(), j);
Point offset = ccpSub(touchLocation, _player->getPosition());
float ratio = offset.y / offset.x;
int targetX = _player->getContentSize().width / 2 + visibleSize.width;
int targetY = (targetX*ratio) + _player->getPosition().y;
Vec2 targetPosition = Vec2(targetX, targetY);
MoveTo* Move = MoveTo::create(2, targetPosition);
projectile.back()->runAction(Move);
return true;
}
void HelloWorld::onTouchMoved(Touch* pTouch, Event* pEvent)
{
}
void HelloWorld::onTouchEnded(Touch* pTouch, Event* pEvent)
{
}
bool HelloWorld::onContactBegin(const PhysicsContact& contact)//首先获得两个碰撞的刚体的对象,然后从界面中移除
{
PhysicsBody* a = contact.getShapeA()->getBody();
PhysicsBody* b = contact.getShapeB()->getBody();
this->removeChild(a->getNode());
this->removeChild(b->getNode());
return true;
}