Cocos2d-x Sprite 執行 CCFade~ 這類透明度變化動作的一些問題

原帖地址

http://blog.csdn.net/crayondeng/article/details/12916711


在引擎中提供了幾個有關透明度變化的動作:CCFadeIn,CCFadeOut,CCFadeTo

CCFadeIn:the opacity from 0 to 255

CCFadeOut:the opacity from 255 to 0

CCFadeTo: from the current value to a custom one

   下面簡單記錄一下我所遇到的一些問題:


問題一:父Sprite執行fade動作,子Sprite不執行問題

看到下面的代碼:

  1. CCSize winSize = CCDirector::sharedDirector()->getWinSize();  
  2.     CCSprite* bgSprite = CCSprite::create("HelloWorld.png");  
  3.     bgSprite->setPosition(ccp(winSize.width/2, winSize.height/2));  
  4.     this->addChild(bgSprite);  
  5.       
  6.     CCSprite* sprite = CCSprite::create("Icon.png");  
  7.     sprite->setPosition(ccp(200, 200));  
  8.     bgSprite->addChild(sprite);  
  9.       
  10.     CCFadeOut* fadeout = CCFadeOut::create(1);  
  11.     bgSprite->runAction(fadeout);  
分析:這裏面的父sprite添加了一個子sprite,那麼當父sprite執行fade out的動作,子sprite也是要一樣執行fade out這個動作的,但是實際運行結果是,只有父sprite執行了這個動作,子sprite並沒有執行。
那麼這個問題如何解決呢? ---  一個最笨的方法就是 去getChildren() 然後每一個子sprite再去執行這個動作。

那麼,還有其他方法嗎?

--有的。我們可以用 setCascadeOpacityEnabled 這個方法。

在 CCRGBAProtocol 類定義了這個方法:

  1. /**  
  2.      *  whether or not opacity should be propagated to its children. 
  3.      */  
  4.     virtual bool isCascadeOpacityEnabled(void) = 0;  
  5.     virtual void setCascadeOpacityEnabled(bool cascadeOpacityEnabled) = 0;  

      看到註釋就知道是神馬作用了,當設置爲true的時候,父sprite執行opacity的變化,子sprite也同樣會執行到這個變化。

再具體看看:

  1. void CCNodeRGBA::setCascadeOpacityEnabled(bool cascadeOpacityEnabled)  
  2. {  
  3.     _cascadeOpacityEnabled = cascadeOpacityEnabled;  
  4. }  

  1. virtual void updateDisplayedOpacity(GLubyte opacity) = 0;  

  1. void CCNodeRGBA::updateDisplayedOpacity(GLubyte parentOpacity)  
  2. {  
  3.     _displayedOpacity = _realOpacity * parentOpacity/255.0;  
  4.       
  5.     if (_cascadeOpacityEnabled)  
  6.     {  
  7.         CCObject* pObj;  
  8.         CCARRAY_FOREACH(m_pChildren, pObj)  
  9.         {  
  10.             CCRGBAProtocol* item = dynamic_cast<CCRGBAProtocol*>(pObj);  
  11.             if (item)  
  12.             {  
  13.                 item->updateDisplayedOpacity(_displayedOpacity);  
  14.             }  
  15.         }  
  16.     }  
  17. }  

同樣的,在這個類中還有這個方法:

  1. /** 
  2.      *  whether or not color should be propagated to its children. 
  3.      */  
  4.     virtual bool isCascadeColorEnabled(void) = 0;  
  5.     virtual void setCascadeColorEnabled(bool cascadeColorEnabled) = 0;  
顯然就是爲了在父sprite執行顏色變化的時候,子sprite也可以執行到這個變化。


回到上面的代碼例子,添加: bgSprite->setCascadeOpacityEnabled(true);  這條語句就沒有問題了。


問題二:自定義的sprite執行 CCFade~ 的問題

我自定義了一個sprite類:在這個自定義的精靈內部又添加了兩個子sprite。

  1. SelectedBoxSprite* SelectedBoxSprite::createWithPic(const char *name)  
  2. {  
  3.     SelectedBoxSprite* pobView = new SelectedBoxSprite();  
  4.     if (pobView && pobView->initWithFile(name) && pobView->setUpdateView()) {  
  5.         pobView->autorelease();  
  6.         return pobView;  
  7.     }  
  8.     CC_SAFE_DELETE(pobView);  
  9.     return NULL;  
  10. }  
  11.   
  12. bool SelectedBoxSprite::setUpdateView()  
  13. {  
  14.     bool isRet = false;  
  15.     do {  
  16.         this->setCascadeOpacityEnabled(true);  
  17.           
  18.         CCSprite* spr1 = CCSprite::create("yellow.png");  
  19.         spr1->setAnchorPoint(CCPointZero);  
  20.         spr1->setTag(1);  
  21.         spr1->setPosition(ccp(0, 4));  
  22.         this->addChild(spr1);  
  23.           
  24.         listSpriteArray->addObject(spr1);  
  25.   
  26.         CCSprite* spr2 = CCSprite::create("yellow_1.png");  
  27.         spr2->setAnchorPoint(CCPointZero);  
  28.         spr2->setTag(2);  
  29.         spr2->setPosition(ccp(0, 30));  
  30.         this->addChild(spr2);  
  31.           
  32.         listSpriteArray->addObject(spr2);  
  33.           
  34.         isRet = true;  
  35.     } while (0);  
  36.     return isRet;  
  37. }  


我創建了這樣的一個實例,想要執行CCFadeIn這個動作

  1. SelectedBoxSprite* selectBoxSprite = SelectedBoxSprite::createWithPic("list_box.png");  
  2.     selectBoxSprite->setAnchorPoint(ccp(0.5, 0.5));  
  3.     selectBoxSprite->setPosition(ccp(300, 305));  
  4.     selectBoxSprite->setTag(2);  
  5.     this->addChild(selectBoxSprite,1);  
  6.       
  7.     CCFadeIn* fadein = CCFadeIn::create(1);  
  8.     selectBoxSprite->runAction(fadein);  

但是,發現有問題,就是這個自定義sprite裏面的兩個子sprite不會執行這個fade in動作奮鬥

那麼這麼辦呢?

那我就想 CCFadeOut 也會不會有這個問題呢

  1. CCFadeOut* fadeout = CCFadeOut::create(1);  
  2. selectBoxSprite->runAction(fadeout);  
發現沒有問題,這個自定義的sprite會fade out;


同樣我又試了一下 CCFadeTo ,同樣也是沒有問題

  1. CCFadeTo* fadeto = CCFadeTo::create(1, 0);  
  2. selectBoxSprite->runAction(fadeto);  
這個時候,我冷靜下來看看代碼,發現原來 在fade in之前沒有 將這個精靈的opacity設置爲 0 

  1. //這個很重要,不要忘了  
  2.     selectBoxSprite->setOpacity(0);  
  3.       
  4.     CCFadeIn* fadein = CCFadeIn::create(1);  
  5.     selectBoxSprite->runAction(fadein);  

這樣發現運行就正常了,裏面的兩個子sprite也會運行了。
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章