动作往往不是单一,而是复杂的组合。我们可以按照一定的次序将上述基本动作组合起来,形成连贯的一套组合动作。组合动作包括以下几类:顺序、并列、有限次数重复、无限次数重复、反动作和动画。动画我们会在下一节介绍,本节我们重点顺序、并列、有限次数重复、无限次数重复和反动

下面我们通过一个实例介绍一下组合动作的使用,这个实例如下图所示,下图是一个操作菜单场景,选择菜单可以进入到下图动作场景,在下图动作场景中点击Go按钮可以执行我们选择的动作效果,点击Back按钮可以返回到菜单场景。

下面我们再看看具体的程序代码,首先看一下看HelloWorldScene.h文件,它的代码如下:

  1. #ifndef __HELLOWORLD_SCENE_H__
  2. #define __HELLOWORLD_SCENE_H__
  3. #include "cocos2d.h"
  4. #include "MyActionScene.h"                                                                                                                ①
  5. typedef enum {                                                                                                                             ②
  6. kSequence = 100,
  7. kSpawn,
  8. kRepeate,
  9. kRepeatForever1,
  10. kReverse
  11. } ActionTypes;                                                                                                                             ③
  12. class HelloWorld : public cocos2d::Layer
  13. {
  14. public:
  15. static cocos2d::Scene* createScene();
  16. virtual bool init();
  17. void OnClickMenu(cocos2d::Ref* pSender);                                                                              ④
  18. CREATE_FUNC(HelloWorld);
  19. };
  20. #endif // __HELLOWORLD_SCENE_H__

上述代码是中第①行是引入头文件MyActionScene.h。第②~③是定义个枚举类型ActionTypes,枚举类型ActionTypes中定义了5个常量,这5个常量对应5个菜单项。第④行声明了一个函数,用来在选择不同菜单时候的回调。

在上诉代码大家比较熟悉了,我们这里就不再介绍了。下面我们再看看下一个场景MyActionScene,它的MyActionScene.h代码如下:

  1. #ifndef __MYACTION_SCENE_H__
  2. #define __MYACTION_SCENE_H__
  3. #include "cocos2d.h"
  4. #include "HelloWorldScene.h"
  5. class MyAction : public cocos2d::Layer
  6. {
  7. cocos2d::Sprite *sprite;
  8. public:
  9. staticcocos2d::Scene* createScene();
  10. virtual bool init();
  11. CREATE_FUNC(MyAction);
  12. void goMenu(cocos2d::Ref* pSender);
  13. void backMenu(cocos2d::Ref* pSender);
  14. voidOnSequence(cocos2d::Ref* pSender);                                                                              ①
  15. void OnSpawn(cocos2d::Ref* pSender);
  16. void OnRepeat(cocos2d::Ref* pSender);
  17. void OnReverse(cocos2d::Ref* pSender);
  18. void OnRepeatForever(cocos2d::Ref* pSender);                                                            ②
  19. };
  20. #endif // __MYACTION_SCENE_H__

在.h文件中第①~②行代码是声明了5个用于菜单选择的回调函数。

MyActionScene的实现代码MyActionScene.ccp文件,其中点击Go按钮时候调用的函数MyAction::goMenu代码如下:

  1. void MyAction::goMenu(Ref* pSender)
  2. {
  3. log("Tag= %i",this->getTag());
  4. switch (this->getTag()) {
  5. casekSequence:
  6. this->OnSequence(pSender);
  7. break;
  8. casekSpawn:
  9. this->OnSpawn(pSender);
  10. break;
  11. casekRepeate:
  12. this->OnRepeat(pSender);
  13. break;
  14. casekRepeatForever1:
  15. this->OnRepeatForever(pSender);
  16. break;
  17. case kReverse:
  18. this->OnReverse(pSender);
  19. break;
  20. default:
  21. break;
  22. }
  23. }

我们在这个函数中根据选择菜单不同调用不同的函数。

  1. MyActionScene.ccp中MyActionLayer::OnSequence代码如下:
  2. void MyAction::OnSequence(Ref* pSender)
  3. {
  4. Size size = Director::getInstance()->getVisibleSize();
  5. Pointp = Point(size.width/2, 200);
  6. FiniteTimeAction* ac0 =(FiniteTimeAction*)sprite->runAction(Place::create(p));                  ①
  7. FiniteTimeAction* ac1 = (FiniteTimeAction*)sprite->runAction(
  8. MoveTo::create(2,Point(size.width- 130, size.height - 200)));         ②
  9. FiniteTimeAction* ac2 = (FiniteTimeAction*)sprite->runAction(
  10. JumpBy::create(2,Point(8, 8),6, 3));                                          ③
  11. FiniteTimeAction* ac3 =(FiniteTimeAction*)sprite->runAction(Blink::create(2,3));                ④
  12. FiniteTimeAction* ac4 = (FiniteTimeAction*)sprite->runAction(
  13. TintBy::create(0.5,0,255,255));                                                   ⑤
  14. sprite->runAction(Sequence::create(ac0,ac1, ac2, ac3, ac4, ac0, NULL));                             ⑥
  15. }

上述代码实现了顺序动作演示,其中主要使用的类是Sequence,Sequence是派生于ActionInterval属性间隔动作。Sequence作用就是顺序排列若干个动作,然后按先后次序逐个执行。代码⑥行执行Sequence,Sequence的create函数需要动作数组。代码第①行创建Place动作,由于Sequence的create函数需要FiniteTimeAction类型的动作,因此需要将表达式sprite->runAction(Place::create(p))强制转换为FiniteTimeAction*类型。类似的代码第②~⑤行都需要强制类型转换。第②行代码是创建MoveTo动作,第③行代码是创建JumpBy动作。第④行代码是创建Blink动作。第⑤行代码是创建TintBy动作。

MyActionScene.ccp中MyActionLayer::OnSpawn,这个函数是在演示并列动作时候调用的函数,它的代码如下:

  1. void MyAction::OnSpawn(Ref* pSender)
  2. {
  3. Size size = Director::getInstance()->getVisibleSize();
  4. Pointp = Point(size.width/2, 200);
  5. sprite->setRotation(0);                                                                                                          ①
  6. sprite->setPosition(p);                                                                                                        ②
  7. FiniteTimeAction* ac1 = (FiniteTimeAction*)sprite->runAction(
  8. MoveTo::create(2,Point(size.width- 100, size.height - 100)));                     ③
  9. FiniteTimeAction* ac2 =(FiniteTimeAction*)sprite->runAction(RotateTo::create(2, 40));       ④
  10. sprite->runAction(Spawn::create(ac1,ac2,NULL));                                                                      ⑤
  11. }

上述代码实现了并列动作演示,其中主要使用的类是Spawn类也从ActionInterval继承而来,该类作用就是同时并列执行若干个动作,但要求动作都必须 是可以同时执行的。比如:移动式翻转、改变色、改变大小等。第⑤行代码sprite->runAction(Spawn::create(ac1,ac2,NULL))执行并列动作,create函数的动作类型数组。第①行代码sprite->setRotation(0)设置精灵旋转角度保持原来状态。第②行代码sprite->setPosition(p)是重新设置精灵位置。第③行代码创建MoveTo动作。第④行代码创建RotateTo动作。

MyActionScene.ccp中MyActionLayer::OnRepeat,这个函数是在演示重复动作时候调用的函数,它的代码如下:

  1. void MyAction::OnRepeat(Ref* pSender)
  2. {
  3. Size size = Director::getInstance()->getVisibleSize();
  4. Pointp = Point(size.width/2, 200);
  5. sprite->setRotation(0);
  6. sprite->setPosition(p);
  7. FiniteTimeAction* ac1 = (FiniteTimeAction*)sprite->runAction(
  8. MoveTo::create(2,Point(size.width- 100, size.height - 100)));                     ①
  9. FiniteTimeAction* ac2 = (FiniteTimeAction*)sprite->runAction(
  10. JumpBy::create(2,Point(10,10), 20,5));                                                          ②
  11. FiniteTimeAction* ac3 = (FiniteTimeAction*)sprite->runAction(
  12. JumpBy::create(2,Point(-10,-10),20,3));                                                         ③
  13. ActionInterval* seq = Sequence::create(ac1, ac2, ac3, NULL);                                         ④
  14. sprite->runAction(Repeat::create(seq,3));                                                                                    ⑤
  15. }

上述代码实现了重复动作演示,其中主要使用的类是Repeat类也从ActionInterval继承而来。第①行代码是创建MoveTo动作。第②行代码是创建JumpBy动作。第③行代码是创建JumpBy动作。第④行代码是创建顺序动作对象seq,seq的类型为ActionInterval*或FiniteTimeAction*。第⑤行代码sprite->runAction(Repeat::create(seq,3)) 重复运行顺序动作3次,create函数参数的类型是FiniteTimeAction。

MyActionScene.ccp中MyActionLayer::OnRepeatForever,这个函数是在演示无限重复动作时候调用的函数,它的代码如下:

  1. void MyAction::OnRepeatForever(Ref*pSender)
  2. {
  3. Size size = Director::getInstance()->getVisibleSize();
  4. Point p = Point(size.width/2, 500);
  5. sprite->setRotation(0);
  6. sprite->setPosition(p);
  7. ccBezierConfigbezier;                                                                                                         ①
  8. bezier.controlPoint_1 = Point(0, size.height/2);
  9. bezier.controlPoint_2= Point(10, -size.height/2);
  10. bezier.endPosition= Point(10,20);                                                                                  ②
  11. FiniteTimeAction* ac1 =(FiniteTimeAction*)sprite->runAction(BezierBy::create(2,bezier));   ③
  12. FiniteTimeAction* ac2 = (FiniteTimeAction*)sprite->runAction(
  13. TintBy::create(0.5,0, 255, 255));                                                                           ④
  14. FiniteTimeAction* ac1Reverse = ((ActionInterval*)ac1)->reverse();                                          ⑤
  15. FiniteTimeAction* ac2Repeat = (FiniteTimeAction*)sprite->runAction(
  16. Repeat::create((ActionInterval*)ac2,4));                                                    ⑥
  17. FiniteTimeAction* ac3 = (FiniteTimeAction*)sprite->runAction(
  18. Spawn::create(ac1,ac2Repeat,NULL));                                                ⑦
  19. FiniteTimeAction* ac4 = (FiniteTimeAction*)sprite->runAction(
  20. Spawn::create(ac1Reverse,ac2Repeat,NULL));                                           ⑧
  21. ActionInterval* seq = Sequence::create(ac3, ac4, NULL);                                                 ⑨
  22. sprite->runAction(RepeatForever::create(seq));                                                                         ⑩
  23. }

上述代码实现了重复动作演示,其中主要使用的类是RepeatForever,它也从ActionInterval继承而来。第⑩行代码sprite->runAction(RepeatForever::create(seq))是执行无限重复动作,create函数参数的类型是FiniteTimeAction。代码第①~②行是定义贝塞尔曲线控制点。第③行代码创建贝塞尔曲线动作BezierBy。第④行代码创建动作TintBy。第⑤行代码是创建BezierBy动作的反转动作。第⑥行代码是创建重复动作。第⑦和⑧行代码是创建并列动作。第⑨行代码是创建顺序动作。

MyActionScene.ccp中MyActionLayer::OnReverse,这个函数是在演示反动作时候调用的函数,它的代码如下:

  1. void MyAction::OnReverse(Ref* pSender)
  2. {
  3. Size size = Director::getInstance()->getVisibleSize();
  4. Pointp = Point(size.width/2, 300);
  5. sprite->setRotation(0);
  6. sprite->setPosition(p);
  7. FiniteTimeAction* ac1 = (FiniteTimeAction*)sprite->runAction(
  8. MoveBy::create(2,Point(40,60)));                                                        ①
  9. Action* ac2 = ac1->reverse();                                                                                               ②
  10. ActionInterval* seq = Sequence::create(ac1, ac2, NULL);                                                 ③
  11. sprite->runAction(Repeat::create(seq,2));                                                                                    ④
  12. }

上述代码实现了反动作演示,支持顺序动作的反顺序动作,反顺序动作不是一个类,不是所有的动作类都支持反动作。XxxTo 类通常不支持反动作,XxxBy类通常支持。第①行代码是创建一个移动MoveBy动作。第②行代码调用ac1的reverse()函数执行反动作。第③行代码是创建顺序动作。第④行代码sprite->runAction(Repeat::create(seq,2))是执行反动作。

更多内容请关注Cocos2d-x系列图书《Cocos2d-x实战(卷Ⅰ):C++开发》
本书交流讨论网站:http://www.cocoagame.net
欢迎加入cocos2d-x技术讨论群:257760386、327403678

Cocos2d-x手机游戏开发中-组合动作的更多相关文章

  1. Android——Cocosd2d-x手机游戏开发学习思路

    手机APP应用如雨后春笋般冒了出来,而在众多的APP应用中,游戏占据了半壁江山.它丰富着人们的业余生活,增进了人们之间的沟通交流.也有许多开发的朋友对游戏开发情有独钟,他们不止是享受着有很多的人们去下 ...

  2. 学习手机游戏开发的两个方向 Cocos2d-x 和 Unity 3D/2D,哪个前景更好?

    如题! 首先说一说学习手机游戏(移动游戏)这件事. 眼下移动互联网行业的在以井喷状态发展.全球几十亿人都持有智能终端设备(ios android),造就了非常多移动互联网创业机会: 一.移动社交 微信 ...

  3. 二、Cocos2dx概念介绍(游戏开发中不同的坐标系,cocos2dx锚点)

    注:ccp是cocos2dx中的一个宏定义,#define ccp(__X__,__Y__)CCPointMake((float)__X__, (float)__Y__),在此文章中表示坐标信息 1. ...

  4. [C++基金会]位计算 游戏开发中的应用

    定义的位操作:通俗点说,,位计算是计算机操作二进制整数. 无论整数可以用二的方式来表示进度,不同类型的其长度的整数位的是不一样的.INT8要么char靠8个月2 位表示,INT16或者short是由1 ...

  5. Unity3D手机游戏开发

    <Unity3D手机游戏开发> 基本信息 作者: 金玺曾 出版社:清华大学出版社 ISBN:9787302325550 上架时间:2013-8-7 出版日期:2013 年8月 开本:16开 ...

  6. 【Cocos2D研究院之游戏开发】

    http://www.xuanyusong.com/archives/category/ios/cocos2d_game 分类目录归档:[Cocos2D研究院之游戏开发]   201211-19 Co ...

  7. [Unity游戏开发]向量在游戏开发中的应用(三)

    本文已同步发表在CSDN:http://blog.csdn.net/wenxin2011/article/details/51088236 在上一篇博客中讲了利用向量点乘在游戏开发中应用的几种情景.本 ...

  8. [Unity游戏开发]向量在游戏开发中的应用(二)

    本文已同步发表在CSDN:http://blog.csdn.net/wenxin2011/article/details/50972976 在上一篇博客中讲了利用向量方向的性质来解决问题.这篇博客将继 ...

  9. [Unity游戏开发]向量在游戏开发中的应用(一)

    本文已同步发表在CSDN:http://blog.csdn.net/wenxin2011/article/details/50810102 向量在游戏开发中是非常实用的,我们在学校学完向量的知识后,只 ...

随机推荐

  1. 建立名称server

    一.实验的目的:     实现DNSserver功能,提供正向.反向解析 二.实验环境     装有Linux的Windows系统 IP为192.168.6.3的虚拟机 三.实验目的 建立gr.org ...

  2. Linux內核中常用的一些延時方法

    Linux內核中常用的一些延時方法 這些方法在以下路徑下定義:kernel/include/linux/delay.h #ifndef _LINUX_DELAY_H #define _LINUX_DE ...

  3. HDU 1863 畅通工程

    畅通工程 Time Limit: 1000/1000 MS (Java/Others) Memory Limit: 32768/32768 K (Java/Others) Total Submissi ...

  4. delphi 取得汉字的第一个字母

    功能说明://取得汉字的第一个字母 function GetPYIndexChar( hzchar:string):char;begin  caseWORD(hzchar[1])shl8+WORD(h ...

  5. 【转】Delphi调用webservice总结

    原文:http://www.cnblogs.com/zhangzhifeng/archive/2013/08/15/3259084.html Delphi调用C#写的webservice 用delph ...

  6. iOS开发——实用篇Swift篇&项目开发常用实用技术

    项目开发常用实用技术 实现拨打电话 要实现打电话功能,最简单最直接的方式便是:直接跳到拨号界面 (注意:这个需要真机调试,模拟器无效果)     UIApplication.sharedApplica ...

  7. CSAPP缓冲区溢出攻击实验(上)

    CSAPP缓冲区溢出攻击实验(上) 下载实验工具.最新的讲义在这. 网上能找到的实验材料有些旧了,有的地方跟最新的handout对不上.只是没有关系,大体上仅仅是程序名(sendstring)或者參数 ...

  8. day03 Java基础

    1.面试题 (1)short s=1;s=s+1; (2)short s=1;s+=1; 上面两行代码有没有问题,如果有,哪里有问题? 答:第一个有问题,s+1是int类型的值,赋值给short的s, ...

  9. 深入理解C语言中的指针与数组之指针篇(转载)

    前言 其实很早就想要写一篇关于指针和数组的文章,毕竟可以认为这是C语言的根本所在.相信,任意一家公司如果想要考察一个人对C语言的理解,指针和数组绝对是必考的一部分. 但是之前一方面之前一直在忙各种事情 ...

  10. oracle 逗号分割,列转行,行转列

    SQL代码 列转行 select REGEXP_SUBSTR(a.rolecode ,,l) rolecode from ( select 'a,aa,aaa' rolecode from dual ...