Cocos3.3横版游戏-Part2-加入主角及控制主角移动

本文介绍了如何在Cocos2d-x游戏开发中加入主角,并通过虚拟摇杆控制主角移动。文章强调逻辑代码与视觉表现的分离,详细讲解了Role类的实现,包括移动、攻击和碰撞检测。通过调整锚点和定义动画,实现了Hero的移动状态和攻击状态。同时,通过JoyStick组件控制Hero的移动,确保其在地图范围内活动,并使镜头跟随主角移动。
摘要由CSDN通过智能技术生成

接上一篇
在这里我们将我们的主角导入,并通过虚拟摇杆控制他
在游戏的设计中,我们尽量做到逻辑代码和视觉表现的代码分离,否则设计到后期整个代码一团糟,无论是维护还是开发新内容都是困难重重.
(我就被某教程的有限状态机(FSM)和动画载入混到一起,结果坑掉了自己的代码)

Role是基础的角色类,包括了移动,攻击,受到攻击,死亡等等的动画及判断动画.
还加入了BodyBox和HitBox,这两个具体作用后续再说
源码中你可以看到

    /* 以下是攻击序列动画,需要用creatAttackAnimation创建,会在动作执行中间添加攻击判定和受伤飘字等*/
    CC_SYNTHESIZE_RETAIN(Action*, m_pnomalattacka, NomalAttackA);   //角色普通攻击A时动画帧序列
    CC_SYNTHESIZE_RETAIN(Action*, m_pnomalattackb, NomalAttackB);   //角色普通攻击B时动画帧序列
    CC_SYNTHESIZE_RETAIN(Action*, m_pnomalattackc, NomalAttackC);   //角色普通攻击C时动画帧序列
    CC_SYNTHESIZE_RETAIN(Action*, m_pnomalattackd, NomalAttackD);   //角色普通攻击D时动画帧序列
    CC_SYNTHESIZE_RETAIN(Action*, m_pchange,  Change);              //角色蓄力时的动画序列
    CC_SYNTHESIZE_RETAIN(Action*, m_pchangeattack,  ChangeAttack);  //角色蓄力攻击时的动画序列

等各种定义

具体的执行代码基本由这个组成

void Role::runIdleAction()
{   
    if(changeState(ACTION_STATE_IDLE))
    {
        this->runAction(m_pidleaction);
    }
}

由此可以看到,主要功能就是播放一个动作

这个是从缓存中载入动画,为此我们需要在GameLayer.cpp的init中加入

SpriteFrameCache::getInstance()->addSpriteFramesWithFile("Boy.plist","Boy.pvr.ccz");

优先载入缓存,之后只需要调用就好了,我在这里写了好几个载入方式,这个是最基本的从0开始,只有3个参数,用于载入普通移动动画还有跳跃之类的.特点是中间不需要插入回调判断(受到敌人攻击或自己攻击判定回调),由于是从0开始的,一次可以将所有的动画读取完.回调函数没法插入,只能在后面加入.
稍微改变下,再多输入一个参数(如下),使得下方的i从framCountBegan开始,我们可以在连续squence中插入回调函数,更加精准进行攻击判定

Animation* Role::createAttackAnimation(const char* formatStr, int frameCountBegan, int frameCountEnd,int fps)
{
    Vector<SpriteFrame*> pFrames; 
    for(int i = frameCountBegan; i < frameCountEnd; i++ )
    {
        const char* imgName = String::createWithFormat(formatStr, i)->getCString();
        SpriteFrame *pFrame = SpriteFrameCache::getInstance()->getSpriteFrameByName(imgName);
        pFrames.insert(i-frameCountBegan,pFrame);
    }
    return Animation::createWithSpriteFrames(pFrames, 1.0f / fps);
}

当然我们的角色可以改变状态必须是不和之前状态相同并且没有死.
如果死了那么就不要动了

bool Role::changeState(ActionState actionState)
{
    if(currActionState == ACTION_STATE_DEAD || currActionState == actionState)
    {
        return false;
    }
    this->stopAllActions();
    this->currActionState = actionState;
    return true;
}

我们应该给角色一个可以受到攻击的范围用于受击判定.最简单的方法是用一个BoundingBox,之后我们只要判断攻击框和受攻击的框有没有相交就好了.

BoundingBox Role::createBoundingBox(Vec2 origin, Size size)
{
    BoundingBox boundingBox;
    boundingBox.original.origin= origin;
    boundingBox.original.size= size;
    boundingBox.actual.origin = this->getPosition() + boundingBox.original.origin;
    boundingBox.actual.size= size;
    return bound
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值