最新文章
Cocos2d-x游戏开发实例详解7:对象释放时机
03-25 13:59
Cocos2d-x游戏开发实例详解6:自动释放池
03-25 13:55
Cocos2d-x游戏开发实例详解5:神奇的自动释放
03-25 13:49
Cocos2d-x游戏开发实例详解4:游戏主循环
03-25 13:44
Cocos2d-x游戏开发实例详解3:无限滚动地图
03-25 13:37
Cocos2d-x游戏开发实例详解2:开始菜单续
03-25 13:32
coocs2dx判断动画完成
本文将分步骤详细讲解在 Cocos2d-x 中判断动画完成的相关内容,涵盖帧动画、精灵表动画等方面。
一、帧动画
在 Cocos2d-x 中,你可以通过一系列图片文件来创建一个动画,示例代码如下:
CCAnimation *animation = CCAnimation::create();
// 从本地文件系统中加载图片文件到 CCSpriteFrame 中,然后添加到 CCAnimation 里
for (int i = 1; i < 15; i++) {
char szImageFileName[128] = {0};
sprintf(szImageFileName, "Images/grossini_dance_%02d.png", i);
animation->addSpriteFrameWithFileName(szImageFileName);
}
animation->setDelayPerUnit(2.8f / 14.0f); // 该动画包含 14 帧,将持续 2.8 秒
animation->setRestoreOriginalFrame(true); // 14 帧播放完之后返回到第一帧
CCAnimate *action = CCAnimate::create(animation);
sprite->runAction(action); // 运行精灵对象
需要注意的是,CCAnimation 由许多精灵帧组成,可设置间隔时间、持续时间等,它实际上是包含着一组数据。而 CCAnimate 是一个动作,它是通过 CCAnimation 对象创建的。
二、精灵表动画
尽管手工动画易于理解,但在游戏开发中使用较少。相反,精灵表动画在 2D 动画中应用广泛。
精灵表实际上是一系列动画帧图片,或者是一个能用于一个场景的图片集。在 OpenGLES 1.1 阶段,精灵表因以下几点被广泛应用:
- 减少文件读写时间:读取一张图片比读取一堆小文件要快。
- 减少内存消耗:OpenGL ES 1.1 仅能使用 2 的几次方大小的图片(即宽度或高度为 2、4、8、64、128、256、512、1024 等)。即便图片达不到这样的宽度和高度,OpenGL ES 1.1 也会分配大于此图片的 2 的 n 次方大小的空间。运用图片集的方式可减少内存碎片。
- 减少 OpenGL ES 绘制调用并加速渲染。
Cocos2d-x v2.0 升级到了 OpenGL ES 2.0,虽然 OpenGL ES 2.0 不再分配 2 的几次方的内存块,但减少读取时间和绘制调用的优势依然存在。
精灵表并非动画的必要条件,但考虑到上述优势,它还是很有效率的。在 Cocos2d-x 中,有多种不同的方式来创建精灵表。
三、通过 .png 和 .plist 文件创建精灵表
在 Cocos2d-x 0.x 和 1.x 版本中,CCSpriteSheet 是为上述目的设计的。在 V2.0 中,CCSpriteBatchNode 替代了 CCSpriteSheet。
CCSpriteBatchNode 对象包含了所有精灵帧的图片纹理。即便它不会绘制,也必须将其添加到场景中,示例代码如下:
CCSpriteBatchNode* spritebatch = CCSpriteBatchNode::create("animations/grossini.png");
下一步,你需要运用 CCSpriteFrameCache 实例来确保帧名字对应帧边界,即确定图片所在的矩形区域,示例代码如下:
CCSpriteFrameCache* cache = CCSpriteFrameCache::sharedSpriteFrameCache();
cache->addSpriteFramesWithFile("animations/grossini.plist");
一旦精灵表和帧加载完成,并且精灵表已被添加到场景中,你可以通过 createWithSpriteFrameName 方法来创建精灵,并通过 addChild 将其添加到精灵表中,示例代码如下:
m_pSprite1 = CCSprite::createWithSpriteFrameName("grossini_dance_01.png");
spritebatch->addChild(m_pSprite1);
addChild(spritebatch);
createWithSpriteFrameName 方法会从 .plist 文件中找到对应的坐标以及矩形区域,然后裁剪 .png 文件的纹理成一个精灵帧。
接下来,我们创建一个 CCArray 对象并将所有的帧动画添加进去。在这个动画示例中,所有 14 帧大小相同,所以可以用一个嵌套的循环遍历它们,添加完 14 帧后结束循环,示例代码如下:
CCArray* animFrames = CCArray::createWithCapacity(15);
char str[100] = {0};
for(int i = 1; i < 15; i++) {
sprintf(str, "grossini_dance_%02d.png", i);
CCSpriteFrame* frame = cache->spriteFrameByName(str);
animFrames->addObject(frame);
}
最后,我们需要创建一个 CCAnimate 动作实例来运行 CCSprite。可以在 CCRepeatForever 动作中包裹 CCAnimate 动作,让动画一直执行下去,示例代码如下:
CCAnimation* animation = CCAnimation::createWithSpriteFrames(animFrames, 0.3f);
m_pSprite1->runAction(CCRepeatForever::create(CCAnimate::create(animation)));
四、文件动画
CCAnimateCache 能够加载一个描述一批节点的 XML/PLIST 文件,包括帧名和它们的矩形区域,这个接口非常容易使用,示例代码如下:
CCAnimationCache *cache = CCAnimationCache::sharedAnimationCache(); // 缓存在 Cocos2d-x 中一直是单例模式
cache->addAnimationsWithFile("animations/animations-2.plist");
CCAnimation* animation = cache->animationByName("dance_1");
CCAnimate* animate = CCAnimate::create(animation);
sprite->runAction(animate);
以上就是在 Cocos2d-x 中创建不同类型动画的详细介绍,但本文未涉及如何判断动画完成,后续可进一步探讨该部分内容。