用cocos2d-x(入门级)实现简单的赛车移动以及地面刷新、小球点击鼠标左键之后向右上角发射的效果
先贴几张场景的图片:
操作说明:一开始点击鼠标左键可以发射小球,然后点击屏幕上半部分可以控制小车向前开,点击屏幕下半部分可以控制小车向后开。
还有中间的文本显示小车的速度、加速度等信息。
运行环境:win10、cocos2d-x、vs2013。
这个项目包括以下几点知识点(重点):
1.小车运行过程中的速度、加速度的计算方式。(涉及到物理学,不懂得小伙伴可以翻翻物理书哈哈)
2.地面的向前向后移动。
3.小球的发射。(跟小车的移动大同小异)
接下来贴核心代码:
#include "DemoLayer.h"
#define Road_Count 8
#define ACCELERATION 300
#define FRICTION 0.3
CCScene* DemoLayer::scene()
{
// 'scene' is an autorelease object
CCScene *scene = CCScene::create();
// DemoLayer'layer' is an autorelease object
DemoLayer *layer = DemoLayer::create();
// add layer as a child to scene
scene->addChild(layer);
// return the scene
return scene;
}
//初始化函数
bool DemoLayer::init()
{
if ( !CCLayer::init() )
{
return false;
}
//获取屏幕尺寸
size = CCDirector::sharedDirector()->getVisibleSize();
CCPoint origin = CCDirector::sharedDirector()->getVisibleOrigin();
//用纹理缓存(资源池)加载纹理 这里的纹理就是一个点
CCTexture2D *texture = CCTextureCache::sharedTextureCache()->addImage("tex.png");
//创建显示文本
hint = CCLabelTTF::create("" ,"宋体",18);
hint->setColor(ccWHITE);
hint->setPosition(ccp(size.width / 2,100));
this->addChild(hint, 20);
//创建批处理渲染方式的精灵节点
CCSpriteBatchNode *mgr = CCSpriteBatchNode::createWithTexture(texture);
//添加到层中
this->addChild(mgr);
//创建存放地面数组,将地面存入数组
for (int i=0; i<Road_Count; ++i) {
CCSprite *roadCell = CCSprite::createWithTexture(texture,CCRectMake(73, 0, 100, 100));
mgr->addChild(roadCell);
road.addObject(roadCell);
}
//创建小车贴图
car = CCSprite::createWithTexture(texture, CCRectMake(0, 0, 72, 160));
mgr->addChild(car);
car->setPosition(ccp(size.width / 2.0,size.height / 2.0));
//鼠标触摸开启
this->setTouchEnabled(true);
fCarPos = 0;
v = 0;
powerDir = 0;
//小球的创建以及初始化
isBallThrow = false;
vBall = ccp(1000, 2000);
aBall = ccp(0, -9.8*400);
CCTexture2D *texture1 = CCTextureCache::sharedTextureCache()->addImage("ball.png");
ball = CCSprite::createWithTexture(texture1, CCRectMake(0, 0, 64, 64));
ball->setPosition(ccp(36, 100));
this->addChild(ball);
//
schedule(schedule_selector(DemoLayer::frmeFunc),0.01);
return true;
}
void DemoLayer::frmeFunc(float dt)
{
float a = powerDir * ACCELERATION;
v = v * (1-FRICTION * dt) + a * dt;
fCarPos += v * dt;
float fTop =size.height + 100 - (fCarPos - (int)(fCarPos / 100) * 100 ); //最后一块的坐标
//重点(2):地面的移动
for (int i=Road_Count- 1;i>=0;--i) {
CCSprite *roadCell =(CCSprite*) road.objectAtIndex(i);// [road objectAtIndex:i];
roadCell->setPosition(ccp(size.width / 2.0,fTop));
fTop -= 100;
}
//小球的发射,以及发射后的位置的实时更新
if(isBallThrow)
{
vBall = ccpAdd(vBall, ccpMult(aBall, dt));
CCPoint pt = ccp(ball->getPositionX()+vBall.x*dt, ball->getPositionY()+vBall.y*dt);
ball->setPosition(pt);
if(ball->getPositionY()<ball->getContentSize().height)
isBallThrow = false;
}
//显示文本
hint->setString(CCString::createWithFormat( "velocity: %f acceleration: %f displacement: %f",v,a,fCarPos)->getCString());
}
void DemoLayer::registerWithTouchDispatcher()
{
CCDirector* pDirector = CCDirector::sharedDirector();
pDirector->getTouchDispatcher()->addTargetedDelegate(this, 0, true);
}
//触碰开启
bool DemoLayer::ccTouchBegan(CCTouch* touch, CCEvent* event)
{
CCPoint touchLocation = touch->getLocation();
touchLocation = convertToNodeSpace( touchLocation );
if (touchLocation.y > size.height / 2.0){
powerDir = 1;
//重点(3):小球发射的代码,取消注释即可实现小球的发射
isBallThrow = true;
}
else {
powerDir = -1;
}
return true;
}
//触碰结束
void DemoLayer::ccTouchEnded(CCTouch* touch, CCEvent* event)
{
CCPoint touchLocation = touch->getLocation();
CCPoint nodePosition = convertToNodeSpace( touchLocation );
powerDir = 0;
}
注释都写的挺清楚的了,大家还有不明白的地方欢迎评论下方写出来,我看到都会尽量解答你,一起解决问题!
项目源代码下载地址:http://file.yiyuen.com/detail.html?id=1658
这个项目记得要拷贝到D:\cocos2d-x-2.2.6\projects下面再打开哦,不然会提示头文件不能包含。