这种序列帧动画要求每一帧的宽高必须一一致,否则动画播起来会出问题。
需要的图片类似图1.1会把所有的动作拼接到一张图上,这样做也是为了节省内存和减少DrawCall,切换动作的时候只需要重新计算图片的UV,然后把算出来的UV作为新区域贴在原来的那张纹理面片上即可。

Animate是Animation的一部分,一个Animation可以保存多个Animate,也可以理解成Animate只是一个动画片段,Animation是完整的动画控制器。这个结构其实有点像Unity的AnimateClip和Animator。
不多说,上代码,自己去看代码吧,实现不是很难,不多讲了。
程序1.1
Animate.h完整代码
#pragmaoncenamespaceU2D{enumMovementEvent{START,COMPLETE,};classCAnimate:publicCPicture{friendclassCAnimation;private:charname[50];//动画名UINTframeWidth;//每一帧的宽度UINTframeHeight;//每一帧的高度UINTrows;//总行数UINTcols;//总列数UINTstartIndex;//开始的索引编号UINTendIndex;//结束的索引编号UINTcurIndex;//当前的索引编号boolisPlaying;//是否播放boolisLoop;//是否循环UINTframeSpeed;//每一帧的速度UINTframeTimer;//每一帧的时间animate_selectorlistener_movementEvent;//动画事件监听public:CAnimate(char*fileName,UINTrows,UINTcols);CAnimate(CCTexture*tex,UINTrows,UINTcols);voidsetName(char*name){strcpy(this->name,name);}char*getName{returnthis->name;}voidsetFrameIndex(UINTstartIndex,UINTendIndex){this->startIndex=startIndex;this->endIndex=endIndex;curIndex=startIndex;}Vector2getFrameSize{returnVector2(frameWidth,frameHeight);}UINTgetFrameCount{returnendIndex-startIndex+1;}voidplay{isPlaying=true;}voidstop{isPlaying=false;}voidrepeat(boolisLoop){this->isLoop=isLoop;}voidsetDelayUnit(UINTframeSpeed){this->frameSpeed=frameSpeed;}voidsetMovementEventCallFunc(animate_selectorfun_movementEvent);//设置动画事件的回调函数voiddraw;voidall_Anchor_0_0;voidall_Anchor_05_05;public:CAnimate{}~CAnimate(void){}};}
程序1.2
Animate.cpp完整代码
#include"Engine.h"namespaceU2D{CAnimate::CAnimate(char*fileName,UINTrows,UINTcols):CPicture(fileName){strcmp(this->name,fileName);this->rows=rows;this->cols=cols;isPlaying=true;isLoop=true;frameSpeed=10;frameWidth=pTexture->getWidth/cols;frameHeight=pTexture->getHeight/rows;startIndex=0;endIndex=rows*cols-1;curIndex=startIndex;}CAnimate::CAnimate(CCTexture*tex,UINTrows,UINTcols):CPicture(tex){strcmp(this->name,tex->getName);this->rows=rows;this->cols=cols;isPlaying=true;isLoop=true;frameSpeed=10;frameWidth=tex->getWidth/cols;frameHeight=tex->getHeight/rows;startIndex=0;endIndex=rows*cols-1;curIndex=startIndex;}voidCAnimate::setMovementEventCallFunc(animate_selectorfun_movementEvent){this->listener_movementEvent=fun_movementEvent;}voidCAnimate::draw{if(isPlaying){if(frameTimer++%frameSpeed==0){if(curIndex==startIndex){if(listener_movementEvent){if(parent!=NULL){(parent->*listener_movementEvent)(this,MovementEvent::START);}else(parent->*listener_movementEvent)(this,MovementEvent::START);}}if(curIndex==endIndex+1){if(isLoop){curIndex=startIndex;}else{isPlaying=false;curIndex=endIndex;}if(listener_movementEvent){if(parent!=NULL){if(parent!=NULL){(parent->*listener_movementEvent)(this,MovementEvent::COMPLETE);}else(parent->*listener_movementEvent)(this,MovementEvent::COMPLETE);}}}(&srcRect,curIndex%cols*frameWidth,curIndex/cols*frameHeight,(curIndex%cols+1)*frameWidth,(curIndex/cols+1)*frameHeight);curIndex++;}}CPicture::draw;}voidCAnimate::all_Anchor_0_0{}voidCAnimate::all_Anchor_05_05{}}
程序1.3
Animation.h完整代码
#pragmaoncenamespaceU2D{classCAnimation:publicCElement{friendclassCPlayer;protected:list
程序1.4
Animation.cpp完整代码
#include"Engine.h"namespaceU2D{CAnimation::CAnimation{animate=NULL;listener_movementEvent=NULL;}CAnimate*CAnimation::addAnimate(char*animName,char*fileName,UINTrows,UINTcols){CAnimate*anim=findAnimate(animName);//查找这个动画名字,如果找不到就会返回空if(anim!=NULL)//如果不为空就说明找到了returnanim;this->rows=rows;this->cols=cols;this->fileName=fileName;anim=newCAnimate(fileName,rows,cols);//如果为空就new一个对象压进去。并且把名字设置好anim->setName(animName);//设置动画名字anim->setParent(this);//CAnimation是CNode的子类,子类拥有父类的所有数据,所以压入CAnimation就等同于压入了CNode。anim->setMovementEventCallFunc(animate_selector(&CAnimation::animateEvent));//回调函数animateList.push_back(anim);//压进链表setAnimate(animName);//设置动画returnanimateList.back;//把刚压进去的对象返回出去}CAnimate*CAnimation::addAnimate(char*animName,CCTexture*tex,UINTrows,UINTcols){CAnimate*anim=findAnimate(animName);if(anim!=NULL)returnanim;this->rows=rows;this->cols=cols;anim=newCAnimate(tex,rows,cols);anim->setName(animName);anim->setParent(this);anim->setMovementEventCallFunc(animate_selector(&CAnimation::animateEvent));animateList.push_back(anim);setAnimate(animName);returnanimateList.back;}CAnimate*CAnimation::findAnimate(char*animName){list
谢谢大家

哈哈哈 子弹越打越多了
哈哈哈 子弹越打越多了
《刺客信条: 黑旗 记忆重置》回应DLC比本体贵: DLC非必须
《刺客信条:黑旗 记忆重置》的首发表现可以说不错,Steam玩家峰值直逼10万。然而Steam的玩家评价却“褒贬不一”。除了游戏宣发问题外,还有一个原因就是总价超越本体的大量DLC,让玩家觉得育碧“吃相难看”。《刺客…当臭猫扶贫神秘嘉豪号主!
原神: 7.0奥黛塔定位反转! 并非木偶专属, 冰神设计成最大悬念
各位旅行者,今天咱们来聊聊原神7.0版本里一个让人意外的角色调整——奥黛塔的定位变化。千万没想到,原本大家都以为奥黛塔是木偶的专属队友,结果根据她的机制和定位来看,这是一位同时拥有星超导和星扩散的双机制…哪辆车能不被28吨钢卷压成废铁? 哪辆车能不被28吨钢卷压成废铁?
原神: 新超导木偶队顶配配装攻略! 告别刮痧与充能卡顿
很多玩家都有这样的困惑,同样是木偶新超导队伍,部分玩家用四星队友就能打出高额满配伤害,而自己配齐五星阵容,却始终面临伤害刮痧、充能卡顿的问题。其实核心差距并非角色配置,而是多数玩家没有掌握版本更新后,…