C#(wp7)兄弟篇Learning Cocos2d-x for XNA(7)——让Sprite动起来
本讲将详细介绍Cocos2d-x游戏中动画Animate的创建方式,通过逐帧数组播放动画和创建动画集合播放动画,比较两者的异同,让Sprite动起来。
工程文件:SpriteAnimationTest.h和SpriteAnimationTest.cpp
SpriteAnimationTest.h
添加两类预处理SpriteAnimateFrameScene和SpriteAnimateFrameLayer
核心代码
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 #ifndef _SPRITE_ANIMATION_TEST_ 2 #define _SPRITE_ANIMATION_TEST_ 3 4 #include "cocos2d.h" 5 6 using namespace cocos2d; 7 8 class SpriteAnimateFrameScene:public CCScene 9 { 10 public: 11 SpriteAnimateFrameScene(); 12 ~SpriteAnimateFrameScene(); 13 14 virtual void onEnter(); 15 }; 16 17 class SpriteAnimateFrameLayer:public CCLayer 18 { 19 public: 20 SpriteAnimateFrameLayer(); 21 ~SpriteAnimateFrameLayer(); 22 }; 23 24 #endif //_SPRITE_ANIMATION_TEST_
通过逐帧数组播放动画,CCSpriteFrame的使用
动画是通过逐帧连续播放图像而形成的动作画面。
既然是逐帧动画,细化话后,即是单帧,通过记录单帧信息,然后再将单帧连续起来,即是逐帧动画。
添加素材文件到Assets/Sprite中,named为PlayerRun.png
在SpriteAnimateFrameLayer::SpriteAnimateFrameLayer()中完成如下步骤:
1.读取素材文件
CCTexture2D* texture=CCTextureCache::sharedTextureCache()->addImage("Sprite/PlayerRun.png");
2.记录单帧信息
1 CCSpriteFrame* frame0=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*0,0,140,140)); 2 CCSpriteFrame* frame1=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*1,0,140,140)); 3 CCSpriteFrame* frame2=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*2,0,140,140)); 4 CCSpriteFrame* frame3=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*3,0,140,140)); 5 CCSpriteFrame* frame4=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*4,0,140,140)); 6 CCSpriteFrame* frame5=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*5,0,140,140)); 7 CCSpriteFrame* frame6=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*6,0,140,140)); 8 CCSpriteFrame* frame7=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*7,0,140,140)); 9 CCSpriteFrame* frame8=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*8,0,140,140)); 10 CCSpriteFrame* frame9=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*9,0,140,140)); 11 CCSpriteFrame* frame10=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*10,0,140,140)); 12 CCSpriteFrame* frame11=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*11,0,140,140));
3.设置起始帧
1 CCSprite* sprite=CCSprite::spriteWithSpriteFrame(frame1); 2 sprite->setPosition(ccp(s.width/2,s.height/2)); 3 this->addChild(sprite,1);
4.生成逐帧数组
1 CCMutableArray<CCSpriteFrame*>* animFrames=new CCMutableArray<CCSpriteFrame*>(12); 2 animFrames->addObject(frame0); 3 animFrames->addObject(frame1); 4 animFrames->addObject(frame2); 5 animFrames->addObject(frame3); 6 animFrames->addObject(frame4); 7 animFrames->addObject(frame5); 8 animFrames->addObject(frame6); 9 animFrames->addObject(frame7); 10 animFrames->addObject(frame8); 11 animFrames->addObject(frame9); 12 animFrames->addObject(frame10); 13 animFrames->addObject(frame11);
5.执行动画
1 CCAnimation* animation=CCAnimation::animationWithFrames(animFrames,0.1f);//Animation动画信息 2 animFrames->release(); 3 CCAnimate* animate=CCAnimate::actionWithAnimation(animation,false); 4 CCActionInterval* seq=(CCActionInterval*)(CCSequence::actions(animate,NULL));//动画间隔 5 sprite->runAction(CCRepeatForever::actionWithAction(animate));
创建动画帧集合,CCSpriteBatchNode使用
对于通过逐帧数组播放动画,同样可以通过CCSpriteBatchNode实现。
动画帧集合即是导入贴图文件.png和导入贴图文件的配置文件.plist
前面都是通过一张图片或图片的部分创建精灵并将其加入到场景中,这样导致的结果是每次添加精灵时,都要逐个渲染精灵,性能低下,一旦过多精灵渲染,将会影响效率。
精灵批处理
使用CCSpriteBatchNode来批处理这些精灵就可以避免帧率的下降。
创建CCSpriteBatchNode的方法
static CCSpriteBatchNode* batchNodeWithTexture(CCTexture2D *tex); static CCSpriteBatchNode* batchNodeWithTexture(CCTexture2D* tex, unsigned int capacity); static CCSpriteBatchNode* batchNodeWithFile(const char* fileImage); static CCSpriteBatchNode* batchNodeWithFile(const char* fileImage, unsigned int capacity);
其中capacity是子节点的数量,当然,不显式设置子节点的数量的话,系统会使用默认值29,在运行时如果超过空间了,会增加33%的容量。
CCSpriteBatchNode有一个限制,就是所使用的图片必须来自同一个文件,如果使用一张图片来创建精灵,你将不能指定精灵的深度,这样,所有的精灵都必须在同一渲染层,不过你可以使用贴图集来避免这个问题,如果你的所有贴图都在同一个文件里,那么你只需创建一个CCSpriteBatchNode就可以了。贴图的大小必须满足2的n次方。
将素材文件png和plist文件添加到Sprite/Plist/中
RoleRun.plist代码
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 <?xml version="1.0" encoding="UTF-8"?> 2 <!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd"> 3 <plist version="1.0"> 4 <dict> 5 <key>frames</key> 6 <dict> 7 <key>RoleRun0.png</key> 8 <dict> 9 <key>frame</key> 10 <string>{{0,0},{100,124}}</string> 11 <key>offset</key> 12 <string>{-4,-7}</string> 13 <key>rotated</key> 14 <false/> 15 <key>sourceColorRect</key> 16 <string>{{16,15},{100,124}}</string> 17 <key>sourceSize</key> 18 <string>{140,140}</string> 19 </dict> 20 <key>RoleRun1.png</key> 21 <dict> 22 <key>frame</key> 23 <string>{{100,0},{92,118}}</string> 24 <key>offset</key> 25 <string>{1,-3}</string> 26 <key>rotated</key> 27 <false/> 28 <key>sourceColorRect</key> 29 <string>{{25,14},{92,118}}</string> 30 <key>sourceSize</key> 31 <string>{140,140}</string> 32 </dict> 33 <key>RoleRun2.png</key> 34 <dict> 35 <key>frame</key> 36 <string>{{192,0},{104,112}}</string> 37 <key>offset</key> 38 <string>{1,-1}</string> 39 <key>rotated</key> 40 <false/> 41 <key>sourceColorRect</key> 42 <string>{{19,15},{104,112}}</string> 43 <key>sourceSize</key> 44 <string>{140,140}</string> 45 </dict> 46 <key>RoleRun3.png</key> 47 <dict> 48 <key>frame</key> 49 <string>{{296,0},{110,114}}</string> 50 <key>offset</key> 51 <string>{-2,-2}</string> 52 <key>rotated</key> 53 <false/> 54 <key>sourceColorRect</key> 55 <string>{{13,15},{110,114}}</string> 56 <key>sourceSize</key> 57 <string>{140,140}</string> 58 </dict> 59 <key>RoleRun4.png</key> 60 <dict> 61 <key>frame</key> 62 <string>{{406,0},{112,118}}</string> 63 <key>offset</key> 64 <string>{-6,-5}</string> 65 <key>rotated</key> 66 <false/> 67 <key>sourceColorRect</key> 68 <string>{{8,16},{112,118}}</string> 69 <key>sourceSize</key> 70 <string>{140,140}</string> 71 </dict> 72 <key>RoleRun5.png</key> 73 <dict> 74 <key>frame</key> 75 <string>{{518,0},{98,118}}</string> 76 <key>offset</key> 77 <string>{-7,-6}</string> 78 <key>rotated</key> 79 <false/> 80 <key>sourceColorRect</key> 81 <string>{{14,17},{98,118}}</string> 82 <key>sourceSize</key> 83 <string>{140,140}</string> 84 </dict> 85 <key>RoleRun6.png</key> 86 <dict> 87 <key>frame</key> 88 <string>{{616,0},{102,122}}</string> 89 <key>offset</key> 90 <string>{-3,-5}</string> 91 <key>rotated</key> 92 <false/> 93 <key>sourceColorRect</key> 94 <string>{{16,14},{102,122}}</string> 95 <key>sourceSize</key> 96 <string>{140,140}</string> 97 </dict> 98 <key>RoleRun7.png</key> 99 <dict> 100 <key>frame</key> 101 <string>{{718,0},{96,118}}</string> 102 <key>offset</key> 103 <string>{2,-1}</string> 104 <key>rotated</key> 105 <false/> 106 <key>sourceColorRect</key> 107 <string>{{24,12},{96,118}}</string> 108 <key>sourceSize</key> 109 <string>{140,140}</string> 110 </dict> 111 <key>RoleRun8.png</key> 112 <dict> 113 <key>frame</key> 114 <string>{{814,0},{96,118}}</string> 115 <key>offset</key> 116 <string>{0,-1}</string> 117 <key>rotated</key> 118 <false/> 119 <key>sourceColorRect</key> 120 <string>{{22,12},{96,118}}</string> 121 <key>sourceSize</key> 122 <string>{140,140}</string> 123 </dict> 124 <key>RoleRun9.png</key> 125 <dict> 126 <key>frame</key> 127 <string>{{910,0},{100,118}}</string> 128 <key>offset</key> 129 <string>{-2,-2}</string> 130 <key>rotated</key> 131 <false/> 132 <key>sourceColorRect</key> 133 <string>{{18,13},{100,118}}</string> 134 <key>sourceSize</key> 135 <string>{140,140}</string> 136 </dict> 137 </dict> 138 <key>metadata</key> 139 <dict> 140 <key>format</key> 141 <integer>2</integer> 142 <key>realTextureFileName</key> 143 <string>RoleRun.png</string> 144 <key>size</key> 145 <string>{2048,128}</string> 146 <key>smartupdate</key> 147 <string>$TexturePacker:SmartUpdate:43e6d77d8691aadfa1c598803e171096$</string> 148 <key>textureFileName</key> 149 <string>RoleRun.png</string> 150 </dict> 151 </dict> 152 </plist>
RoleRun.png图
1.创建批处理节点,读取plist文件
//创建批处理节点,读取plist文件 CCSpriteFrameCache* cache=CCSpriteFrameCache::sharedSpriteFrameCache(); cache->addSpriteFramesWithFile("Sprite/Plist/RoleRun.plist","Sprite/Plist/RoleRun.png");
2. 起始精灵
1 CCSprite* sprite1=CCSprite::spriteWithSpriteFrameName("RoleRun0.png");//纹理plist中包含RoleRun0.png 2 sprite1->setPosition(ccp(s.width/2,s.height/4)); 3 4 CCSpriteBatchNode* spritebatch = CCSpriteBatchNode::batchNodeWithFile("Sprite/Plist/RoleRun.png");//与CCSpriteFrameCache同一纹理 5 spritebatch->addChild(sprite1); 6 addChild(spritebatch);
其中" RoleRun0.png "为plist文件中的节点纹理
3.创建逐帧数组
1 //创建逐帧数组 2 CCMutableArray<CCSpriteFrame*>* animFrames1=new CCMutableArray<CCSpriteFrame*>(10); 3 char str1[100]={0}; 4 for(int i=0;i<10;i++) 5 { 6 sprintf(str1,"RoleRun%d.png",i); 7 CCSpriteFrame* pFrame=cache->spriteFrameByName( str1 ); 8 animFrames1->addObject(pFrame); 9 }
4.执行动画
1 CCAnimation* animation1=CCAnimation::animationWithFrames(animFrames1,0.2); 2 sprite1->runAction(CCRepeatForever::actionWithAction(CCAnimate::actionWithAnimation(animation1,false)));
这样同样可以实现同样的效果
运行效果,两个Sprite都能动起来
SpriteAnimationTest.h完整代码
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 #ifndef _SPRITE_ANIMATION_TEST_ 2 #define _SPRITE_ANIMATION_TEST_ 3 4 #include "cocos2d.h" 5 6 using namespace cocos2d; 7 8 class SpriteAnimateFrameScene:public CCScene 9 { 10 public: 11 SpriteAnimateFrameScene(); 12 ~SpriteAnimateFrameScene(); 13 14 virtual void onEnter(); 15 }; 16 17 class SpriteAnimateFrameLayer:public CCLayer 18 { 19 public: 20 SpriteAnimateFrameLayer(); 21 ~SpriteAnimateFrameLayer(); 22 }; 23 24 #endif //_SPRITE_ANIMATION_TEST_
SpriteAnimationTest.cpp完整代码
![](https://i-blog.csdnimg.cn/blog_migrate/8f900a89c6347c561fdf2122f13be562.gif)
![](https://i-blog.csdnimg.cn/blog_migrate/961ddebeb323a10fe0623af514929fc1.gif)
1 #include "pch.h" 2 #include "Classes\SpriteAnimationTest.h" 3 4 //www.cnblogs.com/suguoqiang 5 //--------------------------------------- 6 // 7 //SpriteAnimateFrameLayer 8 // 9 //--------------------------------------- 10 11 SpriteAnimateFrameLayer::SpriteAnimateFrameLayer() 12 { 13 CCSize s=CCDirector::sharedDirector()->getWinSize(); 14 //CCSpriteFrame 15 //读取素材文件 16 CCTexture2D* texture=CCTextureCache::sharedTextureCache()->addImage("Sprite/PlayerRun.png"); 17 //记录单帧信息 18 CCSpriteFrame* frame0=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*0,0,140,140)); 19 CCSpriteFrame* frame1=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*1,0,140,140)); 20 CCSpriteFrame* frame2=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*2,0,140,140)); 21 CCSpriteFrame* frame3=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*3,0,140,140)); 22 CCSpriteFrame* frame4=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*4,0,140,140)); 23 CCSpriteFrame* frame5=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*5,0,140,140)); 24 CCSpriteFrame* frame6=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*6,0,140,140)); 25 CCSpriteFrame* frame7=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*7,0,140,140)); 26 CCSpriteFrame* frame8=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*8,0,140,140)); 27 CCSpriteFrame* frame9=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*9,0,140,140)); 28 CCSpriteFrame* frame10=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*10,0,140,140)); 29 CCSpriteFrame* frame11=CCSpriteFrame::frameWithTexture(texture,CCRectMake(140*11,0,140,140)); 30 // 起始帧 31 CCSprite* sprite=CCSprite::spriteWithSpriteFrame(frame1); 32 sprite->setPosition(ccp(s.width/2,s.height/2)); 33 this->addChild(sprite,1); 34 //生成逐帧数组 35 CCMutableArray<CCSpriteFrame*>* animFrames=new CCMutableArray<CCSpriteFrame*>(12); 36 animFrames->addObject(frame0); 37 animFrames->addObject(frame1); 38 animFrames->addObject(frame2); 39 animFrames->addObject(frame3); 40 animFrames->addObject(frame4); 41 animFrames->addObject(frame5); 42 animFrames->addObject(frame6); 43 animFrames->addObject(frame7); 44 animFrames->addObject(frame8); 45 animFrames->addObject(frame9); 46 animFrames->addObject(frame10); 47 animFrames->addObject(frame11); 48 //动画Animate 49 CCAnimation* animation=CCAnimation::animationWithFrames(animFrames,0.1f);//Animation动画信息 50 animFrames->release(); 51 CCAnimate* animate=CCAnimate::actionWithAnimation(animation,false); 52 CCActionInterval* seq=(CCActionInterval*)(CCSequence::actions(animate,NULL));//动画间隔 53 sprite->runAction(CCRepeatForever::actionWithAction(animate)); 54 55 //CCSpriteBatchNode 56 //创建批处理节点,读取plist文件 57 CCSpriteFrameCache* cache=CCSpriteFrameCache::sharedSpriteFrameCache(); 58 cache->addSpriteFramesWithFile("Sprite/Plist/RoleRun.plist","Sprite/Plist/RoleRun.png"); 59 60 //起始精灵 61 CCSprite* sprite1=CCSprite::spriteWithSpriteFrameName("RoleRun0.png");//纹理plist中包含RoleRun0.png 62 sprite1->setPosition(ccp(s.width/2,s.height/4)); 63 64 CCSpriteBatchNode* spritebatch = CCSpriteBatchNode::batchNodeWithFile("Sprite/Plist/RoleRun.png");//与CCSpriteFrameCache同一纹理 65 spritebatch->addChild(sprite1); 66 addChild(spritebatch); 67 68 //创建逐帧数组 69 CCMutableArray<CCSpriteFrame*>* animFrames1=new CCMutableArray<CCSpriteFrame*>(10); 70 char str1[100]={0}; 71 for(int i=0;i<10;i++) 72 { 73 sprintf(str1,"RoleRun%d.png",i); 74 CCSpriteFrame* pFrame=cache->spriteFrameByName( str1 ); 75 animFrames1->addObject(pFrame); 76 } 77 78 CCAnimation* animation1=CCAnimation::animationWithFrames(animFrames1,0.2); 79 sprite1->runAction(CCRepeatForever::actionWithAction(CCAnimate::actionWithAnimation(animation1,false))); 80 81 animFrames->release(); 82 animFrames1->release(); 83 } 84 85 SpriteAnimateFrameLayer::~SpriteAnimateFrameLayer() 86 {} 87 88 //--------------------------------------- 89 // 90 //SpriteAnimateFrameScene 91 // 92 //--------------------------------------- 93 94 SpriteAnimateFrameScene::SpriteAnimateFrameScene() 95 {} 96 97 SpriteAnimateFrameScene::~SpriteAnimateFrameScene() 98 {} 99 100 void SpriteAnimateFrameScene::onEnter() 101 { 102 CCScene::onEnter(); 103 CCLayer* pLayer=new SpriteAnimateFrameLayer(); 104 this->addChild(pLayer); 105 pLayer->release(); 106 } 107 108 //www.cnblogs.com/suguoqiang
著作权声明:本文由http://www.cnblogs.com/suguoqiang 原创,欢迎转载分享。请尊重作者劳动,转载时保留该声明和作者博客链接,谢谢!