Cocos2d-X 3.4版-虚拟摇杆控制精灵上下左右《赵云要格斗》

Cocos2d-X 3.4版-虚拟摇杆控制精灵上下左右《赵云要格斗》,第1张

概述首先非常感谢Evankaka大神的无私奉献,传送门:Evankaka神的博客。 在学习大神开源的《赵云要格斗》demo时,为了方便和我一样的小白菜鸟,将其改写为Cocos2d-x3.3版本(根据我个人的理解 做出了一些改动),现在已经改到Evankaka教程的第三节,工作任务少点以后还会陆续更新。 Hero.h: 基于组合优与集成,以及轻量的理念,此类继承自Node即可。 在Hero类里我对Set

首先非常感谢Evankaka大神的无私奉献,传送门:Evankaka神的博客。

在学习大神开源的《赵云要格斗》demo时,为了方便和我一样的小白菜鸟,将其改写为Cocos2d-x3.3版本(根据我个人的理解

做出了一些改动),现在已经改到Evankaka教程的第三节,工作任务少点以后还会陆续更新。

Hero.h:

基于组合优与集成,以及轻量的理念,此类继承自Node即可。

在Hero类里我对SetAnimation,以及AttackAnimation进行了改写,添加了一个函数getAnimation来获取pList文件得到的动作,将其

返回给SetAnimation,AttackAnimation使用。

添加RunEnd运来对run动作结束进行监听。

////  Hero.h//  fight////  Created by Cytzrs on 15/2/2.////#ifndef __fight__Hero__#define __fight__Hero__#include <iostream>#include "cocos-ext.h"using namespace cocos2d;USING_NS_CC_EXT;class Hero:public cocos2d::Node{public:    Hero(voID);    ~Hero(voID);    //根据图片名创建英雄    voID InitHeroSprite(char *hero_name);	//设置动画,num为图片数目,run_directon为精灵脸朝向,false朝右,name_each为name_png中每一小张图片的公共名称部分    voID SetAnimation(const char *name_pList,const char *name_png,const char *name_each,const unsigned int num,bool run_directon);	//停止动画    voID StopAnimation();	//判断是否在跑动画    bool IsRunning;        bool IsAttack;    //英雄运动的方向    bool HeroDirecton;    CREATE_FUNC(Hero);    //判断英雄是否运动到了窗口的中间位置,visibleSize为当前窗口的大小    bool JudgePositona(Size visibleSize);        voID AttackAnimation(const char *name_pList,bool run_directon);        Animation* getAnimation(const char *name_pList,bool run_directon);    voID RunEnd();    voID AttackEnd();private:    Sprite* m_HeroSprite;//精灵    char *Hero_name;//用来保存初始状态的精灵图片名称};#endif /* defined(__fight__Hero__) */

Hero.cpp

////  Hero.cpp//  fight////  Created by Cytzrs on 15/2/2.////#include "Hero.h"#include <String.h>USING_NS_CC;USING_NS_CC_EXT;Hero::Hero(voID){	IsRunning=false;//没在放动画    IsAttack = false;	HeroDirecton=false;//向右运动	Hero_name=NulL;}Hero::~Hero(voID){    }voID Hero::InitHeroSprite(char *hero_name){	Hero_name=hero_name;	this->m_HeroSprite=Sprite::create(hero_name);	this->addChild(m_HeroSprite);}//动画播放,可以是跑、攻击、死亡、受伤等voID Hero::SetAnimation(const char *name_pList,unsigned int num,bool run_directon){    if(HeroDirecton!=run_directon)    {   HeroDirecton=run_directon;        m_HeroSprite->setFlippedX(run_directon);    }    if(IsRunning)        return;    auto ani = getAnimation(name_pList,name_png,name_each,num,run_directon);    auto action = Animate::create(ani);    auto ccback = CallFunc::create(CC_CALLBACK_0(Hero::RunEnd,this));    auto act = Sequence::create(action,ccback,NulL);    m_HeroSprite->runAction(act);        IsRunning=true;}voID Hero::RunEnd(){    IsRunning=false;}Animation* Hero::getAnimation(const char *name_pList,bool run_directon){    auto cache = SpriteFrameCache::getInstance();    cache->addSpriteFramesWithfile(name_pList,name_png);    //    auto sprite = Sprite::createWithSpriteFramename(String::createWithFormat("%s1.png",name_each)->getCString());        m_HeroSprite->setTexture(CCString::createWithFormat("%s1.png",name_each)->getCString());        auto spriteBatch = SpriteBatchNode::create(name_png);    //    spriteBatch->addChild(sprite);    addChild(spriteBatch);        Vector<SpriteFrame*> animFrames(num);    for(int i = 1; i < num; i++)    {        // Obtain frames by alias name        auto frame = cache->getSpriteFrameByname(String::createWithFormat("%s%d.png",i)->getCString());        animFrames.pushBack(frame);    }        auto animation = Animation::createWithSpriteFrames(animFrames,0.3f);        return animation;}voID Hero::StopAnimation(){    if(!IsRunning)        return;	m_HeroSprite->stopAllActions();//当前精灵停止所有动画    //	//恢复精灵原来的初始化贴图//	this->removeChild(m_HeroSprite);//把原来的精灵删除掉//	m_HeroSprite=Sprite::create(Hero_name);//恢复精灵原来的贴图样子//	m_HeroSprite->setFlippedX(HeroDirecton);//	this->addChild(m_HeroSprite);	IsRunning=false;}bool Hero::JudgePositona (Size visibleSize){    if(this->getpositionX()!=visibleSize.wIDth/2)//精灵到达左边        return false;    else        return true;//到达中间位置}voID Hero::AttackAnimation(const char *name_pList,bool run_directon){    if(IsAttack)        return;        auto ani = getAnimation(name_pList,run_directon);    auto action = Animate::create(ani);//    auto ccback = CallFunc::create(this,callfunc_selector(Hero::AttackEnd));    auto ccback = CallFunc::create( CC_CALLBACK_0(Hero::AttackEnd,NulL);    // 14 frames * 1sec = 14 seconds    m_HeroSprite->runAction(act);    IsAttack=true;    }voID Hero::AttackEnd(){    //恢复精灵原来的初始化贴图//    this->removeChild(m_HeroSprite);//把原来的精灵删除掉//    m_HeroSprite=Sprite::create(Hero_name);//恢复精灵原来的贴图样子//    m_HeroSprite->setFlippedX(HeroDirecton);//    this->addChild(m_HeroSprite);    IsAttack=false;}
摇杆类HRocker.h
////  HRocker.h//  fight////  Created by Cytzrs on 15/2/2.////#ifndef __fight__HRocker__#define __fight__HRocker__#include <iostream>#include "cocos2d.h"using namespace cocos2d;//用于标识摇杆与摇杆的背景typedef enum{	tag_rocker,tag_rockerBG,}tagForHRocker;//用于标识摇杆方向typedef enum{	rocker_stay,rocker_right,rocker_up,rocker_left,rocker_down,}tagDirecton;class HRocker:public Layer{public:	HRocker(voID);	~HRocker(voID);    	//创建摇杆(摇杆的 *** 作题图片资源名,摇杆背景图片资源名,起始坐标)	static HRocker* createHRocker(const char *rockerImagename,const char *rockerBGImagename,Point position);	//启动摇杆(显示摇杆、监听摇杆触屏事件)	voID startRocker(bool _isstopOther);	//停止摇杆(隐藏摇杆,取消摇杆的触屏监听)	voID stopRocker();	//判断控制杆方向,用来判断精灵上、下、左、右运动	int rocketDirection;	//当前人物行走方向,用来判断精灵的朝向,精灵脸朝右还是朝左	bool rocketRun;	CREATE_FUNC(HRocker);        voID update(float dt);private:	//自定义初始化函数	voID rockerInit(const char* rockerImagename,const char* rockerBGImagename,Point position);	//是否可 *** 作摇杆	bool isCanMove;	//获取当前摇杆与用户触屏点的角度	float geTrad(Point pos1,Point pos2);	//摇杆背景的坐标	Point rockerBGposition;	//摇杆背景的半径	float rockerBGR;	//触屏事件	virtual bool ontouchBegan(touch *ptouch,Event *pEvent);	virtual voID ontouchmoved(touch *ptouch,Event *pEvent);	virtual voID ontouchended(touch *ptouch,Event *pEvent);    };#endif /* defined(__fight__HRocker__) */
HRocker.cpp
////  HRocker.cpp//  fight////  Created by Cytzrs on 15/2/2.////#include "HRocker.h"const double PI=3.1415;HRocker::HRocker(voID){	rocketRun=false;}HRocker::~HRocker(voID){}//创建摇杆(摇杆的 *** 作题图片资源名,摇杆背景图片资源名,起始坐标)HRocker* HRocker::createHRocker(const char *rockerImagename,Point position){	HRocker *layer = HRocker::create();	if (layer)	{		layer->rockerInit(rockerImagename,rockerBGImagename,position);		return layer;	}	CC_SAFE_DELETE(layer);	return NulL;}//自定义初始化函数voID HRocker::rockerInit(const char* rockerImagename,Point position){	Sprite *spRockerBG = Sprite::create(rockerBGImagename);	spRockerBG->setposition(position);	spRockerBG->setVisible(false);	addChild(spRockerBG,tag_rockerBG);    	Sprite *spRocker = Sprite::create(rockerImagename);	spRocker->setposition(position);	spRocker->setVisible(false);	addChild(spRocker,1,tag_rocker);    	rockerBGposition = position;	rockerBGR = spRockerBG->getContentSize().wIDth*0.5;//	rocketDirection=-1;//表示摇杆方向不变}//启动摇杆(显示摇杆、监听摇杆触屏事件)voID HRocker::startRocker(bool _isstopOther){	Sprite *rocker = (Sprite*)this->getChildByTag(tag_rocker);	rocker->setVisible(true);    	Sprite *rockerBG = (Sprite *)this->getChildByTag(tag_rockerBG);	rockerBG->setVisible(true);        auto Listener = EventListenertouchOneByOne::create();    Listener->ontouchBegan = CC_CALLBACK_2(HRocker::ontouchBegan,this);    Listener->ontouchmoved = CC_CALLBACK_2(HRocker::ontouchmoved,this);    Listener->ontouchended = CC_CALLBACK_2(HRocker::ontouchended,this);    	Director::getInstance()->getEventdispatcher()->addEventListenerWithSceneGraPHPriority(Listener,this);}//停止摇杆(隐藏摇杆,取消摇杆的触屏监听)voID HRocker::stopRocker(){	Sprite *rocker = (Sprite *)this->getChildByTag(tag_rocker);	rocker->setVisible(false);    	Sprite * rockerBG = (Sprite *)this->getChildByTag(tag_rockerBG);	rockerBG->setVisible(false);        Director::getInstance()->getEventdispatcher()->removeAllEventListeners();}//获取当前摇杆与用户触屏点的角度float HRocker::geTrad(Point pos1,Point pos2){	float px1 = pos1.x;	float py1 = pos1.y;	float px2 = pos2.x;	float py2 = pos2.y;    	//得到两点x的距离	float x = px2 - px1;	//得到两点y的距离	float y = py1 - py2;	//算出斜边长度	float xIE = sqrt(pow(x,2) + pow(y,2));	//得到这个角度的余弦值(通过三角函数中的店里:角度余弦值=斜边/斜边)	float cosAngle = x / xIE;	//通过反余弦定理获取到期角度的弧度	float rad = acos(cosAngle);	//注意:当触屏的位置Y坐标<摇杆的Y坐标,我们要去反值-0~-180	if (py2 < py1)	{		rad = -rad;	}	return rad;}Vec2 getAngeleposition(float r,float angle){	return Vec2(r*cos(angle),r*sin(angle));}//抬起事件bool HRocker::ontouchBegan(touch *ptouch,Event *pEvent){	Point point = ptouch->getLocation();	Sprite *rocker = (Sprite *)this->getChildByTag(tag_rocker);	if (rocker->boundingBox().containsPoint(point))	{		isCanMove = true;		log("begin");	}	return true;}//移动事件voID HRocker::ontouchmoved(touch *ptouch,Event *pEvent){	if (!isCanMove)	{		return;	}	Point point = ptouch->getLocation();	Sprite *rocker = (Sprite *)this->getChildByTag(tag_rocker);	//得到摇杆与触屏点所形成的角度	float angle = geTrad(rockerBGposition,point);	//判断两个圆的圆心距是否大于摇杆背景的半径	if (sqrt(pow((rockerBGposition.x - point.x),2) + pow((rockerBGposition.y - point.y),2)) >= rockerBGR)	{        		//保证内部小圆运动的长度限制		rocker->setposition(getAngeleposition(rockerBGR,angle) + Vec2(rockerBGposition.x,rockerBGposition.y));        //	log("touch");	}	else	{		//当没有超过,让摇杆跟随用户触屏点移动即可		rocker->setposition(point);		//log("touch");	}    	//判断方向	if(angle>=-PI/4&&angle<PI/4)	{		rocketDirection=rocker_right;		rocketRun=false;		log("%d",rocketDirection);	}	else if(angle>=PI/4&&angle<3*PI/4)	{		rocketDirection=rocker_up;		log("%d",rocketDirection);	}	else if((angle>=3*PI/4&&angle<=PI)||(angle>=-PI&&angle<-3*PI/4))	{		rocketDirection=rocker_left;		rocketRun=true;		log("%d",rocketDirection);	}	else if(angle>=-3*PI/4&&angle<-PI/4)	{		rocketDirection=rocker_down;		log("%d",rocketDirection);	}}//离开事件voID HRocker::ontouchended(touch *ptouch,Event *pEvent){	if (!isCanMove)	{		return;	}	Sprite *rockerBG = (Sprite*)this->getChildByTag(tag_rockerBG);	Sprite *rocker = (Sprite*)this->getChildByTag(tag_rocker);	rocker->stopAllActions();	rocker->runAction(CCMoveto::create(0.08f,rockerBG->getposition()));	isCanMove = false;	rocketDirection=rocker_stay;	log("%d",rocketDirection);	log("end");}voID HRocker::update(float dt){	if(isCanMove)	{			}}

最后一步在Scene中添加update函数:

voID HelloWorld::update(float delta){	switch(rocker->rocketDirection)	{        case 1:            hero->SetAnimation("run_animation.pList","run_animation.png",8,rocker->rocketRun);            hero->setposition(Vec2(hero->getposition().x+1,hero->getposition().y));            break;        case  2:            hero->SetAnimation("run_animation.pList",rocker->rocketRun);            hero->setposition(Vec2(hero->getposition().x,hero->getposition().y+1));            break;        case 3:            hero->SetAnimation("run_animation.pList",rocker->rocketRun);            hero->setposition(Vec2(hero->getposition().x-1,hero->getposition().y));            break;        case 4:            hero->SetAnimation("run_animation.pList",hero->getposition().y-1));            break;        default:            hero->StopAnimation();            break;            	}}


PS:多写博客,帮助自己,方便他人!

总结

以上是内存溢出为你收集整理的Cocos2d-X 3.4版-虚拟摇杆控制精灵上下左右《赵云要格斗》全部内容,希望文章能够帮你解决Cocos2d-X 3.4版-虚拟摇杆控制精灵上下左右《赵云要格斗》所遇到的程序开发问题。

如果觉得内存溢出网站内容还不错,欢迎将内存溢出网站推荐给程序员好友。

欢迎分享,转载请注明来源:内存溢出

原文地址: http://outofmemory.cn/web/1037468.html

(0)
打赏 微信扫一扫 微信扫一扫 支付宝扫一扫 支付宝扫一扫
上一篇 2022-05-24
下一篇 2022-05-24

发表评论

登录后才能评论

评论列表(0条)

保存