在cocos2dx 3.0 版本号,回调函数本质4一个CC_CALLBACK_N 替换功能。N的回调函数的参数的数量的代表
auto animation = Animation::create(); auto animate = Animate::create(animation); CallFunc* animateDone = CallFunc::create(CC_CALLBACK_0(PlaneLayer::removePlane,this)); auto sequence = Sequence::create(animate,animateDone,NULL); sprite1->runAction(sequence); void PlaneLayer::removePlane(){ //..... }
auto actionMove = MoveTo::create(randomDuration, Point(0, 0)); auto actionDone = CallFuncN::create(CC_CALLBACK_1(EnemyLayer::enemy1MoveFinished,this)); auto sequence = Sequence::create(actionMove,actionDone,NULL); sprite2->runAction(sequence); void EnemyLayer::enemy1MoveFinished(Node* pSender){ Sprite* sprite2 = (Sprite*)pSender; }
auto pauseNormal = Sprite::create("game_pause_nor.png"); auto pausePressed = Sprite::create("game_pause_pressed.png"); auto menuItem = MenuItemSprite::create(pauseNormal,pausePressed,NULL,CC_CALLBACK_1(ControlLayer::menuPauseCallback,this)); menuItem->setPosition(Point::ZERO); auto menuPause = Menu::create(menuItem,NULL); menuPause->setPosition(Point::ZERO); //回调函数 void ControlLayer::menuPauseCallback(Object* pSender) { //.... }
//单点触摸 virtual bool onTouchBegan(Touch *touch, Event *unused_event); virtual void onTouchMoved(Touch *touch, Event *unused_event); virtual void onTouchEnded(Touch *touch, Event *unused_event); virtual void onTouchCancelled(Touch *touch, Event *unused_event); auto dispatcher = Director::getInstance()->getEventDispatcher(); auto listener = EventListenerTouchOneByOne::create(); listener->onTouchBegan = CC_CALLBACK_2(GameLayer::onTouchBegan,this); listener->onTouchMoved = CC_CALLBACK_2(GameLayer::onTouchMoved,this); listener->onTouchEnded = CC_CALLBACK_2(GameLayer::onTouchEnded,this); listener->setSwallowTouches(true);//不向下传递触摸 dispatcher->addEventListenerWithSceneGraphPriority(listener,this);
。
回来了。
让我先回口血,恩。接着写...
一般来说:
CallFunc用于 不带參数的,
CallFuncN 用于创建 带一个Node节点參数的,Node*节点參数是动作的运行者
CCCallFuncND 比CallFuncN多了一个參数,能够是随意类型的參数 void *,使用方法看以下
auto animation = AnimationCache::getInstance()->animationByName("Enemy1Blowup"); auto animate = Animate::create(animation); CCCallFuncND* animateDone = CCCallFuncND::create(this,callfuncND_selector(EnemyLayer::removeEnemy1),(void*)enemy1); auto sequence = Sequence::create(animate, animateDone,NULL); Sprite* m_sprite = enemy1->getSprite(); m_sprite ->runAction(sequence); void EnemyLayer::removeEnemy1(Node* pTarget, void* data){ Sprite* m_sprite = (Sprite*) pTarget; //node节点为动作的运行者 Enemy* enemy1 = (Enemy*)data; //我们传的自己定义数据enemy1 //... }
CCCallFuncND* animateDone = CCCallFuncND::create(this,callfuncND_selector(EnemyLayer::removeEnemy1),(void*)enemy1);
//写法1 CCCallFuncN* animateDone = CCCallFuncN::create(CC_CALLBACK_1(EnemyLayer::removeEnemy1,this,enemy1)); //写法2 CCCallFunc* animateDone = CCCallFunc::create(CC_CALLBACK_0(EnemyLayer::removeEnemy1,this,enemy1->getSprite(),enemy1)); //写法3,用std::bind CCCallFuncN* animateDone = CCCallFuncN::create(std::bind(&EnemyLayer::removeEnemy1,this,enemy1->getSprite(),enemy1));
恩。是不是有点乱。记不住没关系,我也常常没记住,我们来详细看一下CC_CALLBACK_N究竟是神马玩意
// new callbacks based on C++11 #define CC_CALLBACK_0(__selector__,__target__, ...) std::bind(&__selector__,__target__, ##__VA_ARGS__) #define CC_CALLBACK_1(__selector__,__target__, ...) std::bind(&__selector__,__target__, std::placeholders::_1, ##__VA_ARGS__) #define CC_CALLBACK_2(__selector__,__target__, ...) std::bind(&__selector__,__target__, std::placeholders::_1, std::placeholders::_2, ##__VA_ARGS__) #define CC_CALLBACK_3(__selector__,__target__, ...) std::bind(&__selector__,__target__, std::placeholders::_1, std::placeholders::_2, std::placeholders::_3 ##__VA_ARGS__)
先解释一下:
#include <iostream> #include <functional> using namespace std; typedef std::function<void ()> fp; void g_fun() { cout<<"g_fun()"<<endl; } class A { public: static void A_fun_static() { cout<<"A_fun_static()"<<endl; } void A_fun() { cout<<"A_fun()"<<endl; } void A_fun_int(int i) { cout<<"A_fun_int() "<<i<<endl; } void A_fun_int_double(int i,int p) { cout<<"A_fun_int_double ()"<<i<<","<<p<<endl; } //非静态类成员。由于含有this指针,所以须要使用bind void init() { //绑定不带參数的函数 fp fp1=std::bind(&A::A_fun,this); fp1(); } void init2() { typedef std::function<void (int)> fpi; //绑定带一个參数的函数 fpi f=std::bind(&A::A_fun_int,this,std::placeholders::_1);//參数要使用占位符 std::placeholders::_1表示第一个參数 f(5); } void init3(){ typedef std::function<void (int,double)> fpid; //绑定带两个參数的函数 fpid f=std::bind(&A::A_fun_int_double,this,std::placeholders::_1,std::placeholders::_2); f(5,10); } }; int main() { //绑定到全局函数 fp f2=fp(&g_fun); f2(); //绑定到类静态成员函数 fp f1=fp(&A::A_fun_static); f1(); A().init(); A().init2(); A().init3(); return 0; }
g_fun() A_fun_static() A_fun() A_fun_int() 5 A_fun_int_double ()5,10
std::function --> 绑定到全局函数/类静态成员函数(类静态成员函数与全局函数没有差别)
std::bind --> 绑定到类的非静态成员函数
到这里是不是有豁然开朗的感觉呢。哈哈,知道了bind函数怎么用。然后我们就能够使用std::bind替换CC_CALLBACK_N写法了
auto animation = Animation::create(); auto animate = Animate::create(animation); //CallFunc* animateDone = CallFunc::create(CC_CALLBACK_0(PlaneLayer::removePlane,this)); CallFunc* animateDone = CallFunc::create(std::bind(&PlaneLayer::removePlane,this));//替换 auto sequence = Sequence::create(animate,animateDone,NULL); sprite1->runAction(sequence); void PlaneLayer::removePlane(){ //..... }
比方我们要替换带一个參数的CC_CALLBACK_1
auto actionMove = MoveTo::create(randomDuration, Point(0, 0)); //auto actionDone = CallFuncN::create(CC_CALLBACK_1(EnemyLayer::enemy1MoveFinished,this)); auto actionDone = CallFuncN::create(std::bind(&EnemyLayer::enemy1MoveFinished,this,enemy1));//替换 auto sequence = Sequence::create(actionMove,actionDone,NULL); sprite2->runAction(sequence); void EnemyLayer::enemy1MoveFinished(Node* pSender){ Sprite* sprite2 = (Sprite*)pSender; }
auto animation = AnimationCache::getInstance()->animationByName("Enemy1Blowup"); auto animate = Animate::create(animation); //CCCallFuncND* animateDone = CCCallFuncND::create(this,callfuncND_selector(EnemyLayer::removeEnemy1),(void*)enemy1); CCCallFuncN* animateDone = CCCallFuncN::create(std::bind(&EnemyLayer::removeEnemy1,this,enemy1->getSprite(),enemy1));//替换 auto sequence = Sequence::create(animate, animateDone,NULL); Sprite* m_sprite = enemy1->getSprite(); m_sprite ->runAction(sequence); void EnemyLayer::removeEnemy1(Node* pTarget, void* data){ Sprite* m_sprite = (Sprite*) pTarget; //node节点为动作的运行者 Enemy* enemy1 = (Enemy*)data; //我们传的自己定义数据enemy1 //... }
哈哈,这下子非常清楚了吧。。再也不会混乱了。。
版权声明:本文博客原创文章,博客,未经同意,不得转载。