1. 程式人生 > >Cocos2d-x學習筆記(十四)-------->粒子特效

Cocos2d-x學習筆記(十四)-------->粒子特效

粒子特效 Cocos2d-x粒子特效原理 不論是2D還是3D,幾乎每個遊戲引擎都會提供一套自己的粒子系統,這些粒子系統的內容和功能大同小異,原因是粒子系統本身就已經成為了遊戲開發的技術規範。粒子系統所模擬的影象效果都有如下特點: (1)整個現象都是由很多個獨立的影象效果組成,這些影象效果都有自己的位置、移動軌跡等特點; (2)這些獨立的影象效果組合或者疊加起來,就形成了要模擬的現象; (3)獨立的影象效果經過一段生命週期之後會從螢幕上消失,進而可以將其狀態重置並重新利用; 以上所謂的獨立影象,就可以抽象稱為粒子,而對整個現象的模擬,就是對多個粒子的控制和管理過程,這就是粒子系統的主要工作。參考粒子系統的執行原理和特點,在x引擎的粒子系統中,提供了兩個最為主要的功能類。
粒子類:每個單獨的粒子是整個粒子特效的一個基本組成部分,每個粒子都具有大量屬性,比如粒子圖片、生命時長、方向、速度、加速度等,這些屬效能夠決定粒子的外觀及行為表現。 粒子發射器:實際上是所有粒子的管理者,是用來進行粒子生成、粒子控制、回收粒子的管理器類。 Cocos2d-x引擎使用單一發射器模式,也就是說每個粒子特效都是獨立的,都具有自己唯一的發射器和大量屬於此發射器的粒子。比如要實現一架飛機的爆炸,我們需要定義兩個獨立的粒子系統,第一個負責顯示爆炸火焰粒子特效,第二個複雜顯示飛機殘片散落特效。有些遊戲引擎可能提供多發射器模式,一個粒子系統同時具有多個粒子發射器,可以發射不同的粒子效果。這兩種模式並沒有明顯的好壞之分,因為它們都能滿足實現複雜粒子效果的需求。
x引擎粒子發射器工作原理 在進行粒子系統建立時,首先把粒子發射器放到某個位置,然後設定要生成的粒子的數量及粒子的起始屬性,然後再開始創建出粒子,並不斷的更新粒子的狀態,粒子在更新運動狀態的同時生命值會不斷地消耗直至死亡。死亡後的粒子被髮射器記錄回收,為保證同一時間內有固定數量的粒子在存活中,發射器會在合適的時間重新初始化並執行回收的粒子。 x引擎在渲染粒子物件時,少則幾十個粒子,多則成百上千。所以粒子物件的繪製必然要使用高效的批量繪製技術,這一特點和精靈Sprite的批量繪製SpriteBatchNode方法比較相似。x引擎使用了CCParticleBatchNode,這個類的強大支援下,使用同一個紋理的粒子物件被高效地繪製到螢幕之上。
CCParticleSystem是x引擎提供的粒子系統類,而在此類基礎上,x引擎還提供了一種更完善的CCParticleSystemQuad作為擴充套件粒子系統。CCParticleSystemQuad使使用者可以在不需要批次節點(BatchNode)時也能夠實現粒子系統的OPENGL頂點和索引緩衝的建立和渲染。但是大家在使用粒子系統時,儘量保證使用同一張圖片資源,儘量使用批次渲染以提高遊戲的執行效率。x引擎還內建了30多種直接可用的粒子特效,這些特效都在CCParticleSystemQuad基礎上定義成了直接可用的類,我們在使用時直接定義物件並修改粒子屬性就能夠得到讓人滿意的效果。 使用
bulletCaseEmitter = new CCParticleSystemQuad();
bulletCaseEmitter->initWithTotalParticles(15);
bulletCaseEmitter->autorelease();

bulletCaseEmitter->setTexture(CCTextureCache::sharedTextureCache()->addImage("bullet_case.png"));
bulletCaseEmitter->setDuration(-1);
bulletCaseEmitter->setGravity(CCPointZero);
bulletCaseEmitter->setAngleVar(10);
bulletCaseEmitter->setSpeed(150);
bulletCaseEmitter->setRadialAccel(-120);
bulletCaseEmitter->setTangentialAccel(50);
bulletCaseEmitter->setPosVar(CCPointZero);
bulletCaseEmitter->setLife(1.0f);
bulletCaseEmitter->setEndSpinVar(2000);
ccColor4F startColor = {1.0f, 1.0f, 1.0f, 1.0f};
bulletCaseEmitter->setStartColor(startColor);
ccColor4F startColorVar = {0.0f, 0.0f, 0.0f, 1.0f};
bulletCaseEmitter->setStartColorVar(startColorVar);
ccColor4F endColor = {1.0f, 1.0f, 1.0f, 0.2f};
bulletCaseEmitter->setEndColor(endColor);
ccColor4F endColorVar = {0.0f, 0.0f, 0.0f, 0.2f};
bulletCaseEmitter->setEndColorVar(endColorVar);
bulletCaseEmitter->setEmissionRate(10);
bulletCaseEmitter->setBlendAdditive(false);
bulletCaseEmitter->setStartSize(16.0f);
bulletCaseEmitter->setEndSize(kParticleStartSizeEqualToEndSize);
gunSprite->getParent()->addChild(bulletCaseEmitter, 13);
bulletCaseEmitter->setPosition(ccp(BULLET_PARTICLE_POS, BULLET_PARTICLE_POS));
上面程式碼定義了一個子彈彈殼不斷從槍膛飛出的粒子特效,在定義此特效時我們通過使用粒子發射器定義了非常多的粒子和發射器屬性。 粒子編輯器使用介紹: 在遊戲開發流程中,通常都會使用粒子編輯器這類工具來編輯、除錯和觀察粒子的效果,在得到滿意的效果後,可以通過粒子編輯器將粒子和編輯器屬性以配置檔案的形式儲存,在x引擎需要播放粒子特效時,讀取配置檔案並生成對應的粒子特效。這種粒子特效的定義和工作方式極大地方便了開發者,讓開發者從複雜的屬性定義程式碼中解放出來。 因為2D遊戲的粒子系統通常都採用了統一的技術規範,所以不同2D遊戲引擎的粒子和發射器屬性卻大同小異,在這種情況下,一款粒子編輯器就可以支援大多數的2D遊戲引擎,也就是說,在市面上的大多數2D遊戲粒子編輯器,都能夠支援x引擎中的粒子系統。粒子編輯器統一輸出的配置檔案是plist格式(全稱是PropertyList,中文譯為屬性列表),這是一種預定義好格式的XML檔案。 例:
<?xml version="1.0" encoding="utf-8"?>
<plist version="1.0">
<dict>
<key>angle</key>
<real>0.000000</real>
<key>angleVariance</key>
<real>360.000000</real>
<key>duration</key>
<real>-1.000000</real>
<key>startParticleSize</key>
<real>9.000000</real>
<key>startParticleSizeVariance</key>
<real>64.000000</real>
<key>finishParticleSize</key>
<real>9.000000</real>
<key>finishParticleSizeVariance</key>
<real>0.000000</real>
<key>gravityx</key>
<real>0.000000</real>
<key>gravityy</key>
<real>0.000000</real>
<key>maxParticles</key>
<real>30.000000</real>
...
</dict>
</plist>
plist配置檔案中的屬性定義都是以KeyValue對的形式出現,例如上面的XML節點<key>angle</key>就是名稱為angle的屬性,它的值就是後面緊跟著的XML節點<real>0.000000</real>,其中的real指明它是浮點資料型別,值是0.000000度。 在Windows下采用particle builderCocos2d-x引擎編輯粒子特效。
粒子屬性介紹Max Particles:全部粒子的總數量,也就是同時能夠顯示的最大粒子數量。 Life span:粒子的生命值,此屬性決定粒子會在多長時間內從生成到消失,此屬性為單個粒子設定生命期。 Life span Variance:生命值浮動值,每個粒子的具體生命時間由生命值和其浮動值一起計算,比如生命值是5秒,浮動值為1秒,則最終的生命值就是4~6秒之間的隨機數值。
Start Size:起始大小,使用畫素作為單位,粒子最終大小需要與浮動值一同計算得出。 Start Size Variance:起始大小浮動值。 Finish Size:結束大小,同樣使用畫素作為單位,粒子最終大小還需要與浮動值一同計算得出。 Finish Size Variance:結束大小浮動值。 Angle:發射角度,最終值還需要與浮動值一同計算得出。 Angle Variance:發射角度浮動值。 Rotation Start:起始旋轉角度,最終值還需要與浮動值一同計算得出。 Rotation Start Variance:起始旋轉角度浮動值。 Rotation End:結束旋轉角度,最終值還需要與浮動值一同計算得出。 Rotation End Variance:起始旋轉角度浮動值。 每個粒子都可以從一個起始顏色漸變到一個最終顏色,從而創造出豔麗的顏色粒子效果。我們至少需要設定起始顏色,因為預設情況下粒子是黑色的,所以如果不設定起始顏色的話,就可能看不到粒子。顏色型別是ccColor4F,這是一個由4個浮點陣列組成的結構體:rgba分別對應透明度。浮點數的數值在0到1之間,1代表最飽和的顏色,如果需要完全白色的粒子顏色的話,就應該把所有rgba都設定為1。以下是粒子的顏色屬性表格。 Start Red:起始紅色通道值。 Start Green:起始綠色通道值。 Start Blue:起始藍色通道值。 Start Alpha:起始透明度通道。 Start Red Variance:起始紅色通道浮動值。 Start Green Variance:起始綠色通道浮動值。 Start Blue Variance:起始藍色通道浮動值。 Start Alpha Variance:起始透明度通道浮動值。 Finish Red:終止紅色通道值。 Finish Green:終止綠色通道值。 Finish Blue:終止藍色通道值。 Finish Alpha:終止透明度通道值。 Finish Red Variance:終止紅色通道值浮動值。 Finish Green Variance:終止綠色通道值浮動值。 Finish Blue Variance:終止藍色通道值浮動值。 Finish Alpha Variance:終止透明度通道浮動值。 發射器屬性簡介: 粒子發射器有兩種型別,一種是重力發射器(用於實現在重力條件下的粒子運動),另一種是放射發射器(用於實現在無重力下的粒子運動)。 通用屬性Duration:持續時間,此屬性決定發射器粒子的時間,如果是設定為2秒,則連續發射2秒後就停止了,如果是-1,表示一直持續發射。 Emitter Type:發射器型別,包括兩種發射器:重力(Gravity)和放射(又叫半徑發射器Radius)。 Source PositionX:發射器x座標。 Source PositionX Variance:發射器x座標浮動值。 Source PositionY:發射器y座標。 Source PositionY Variance:發射器y座標浮動值。 重力發射器型別專用屬性Speed:粒子移動的速度。 Speed Variance:速度浮動值。 Gravity X:粒子X軸加速度大小。 Gravity Y:粒子Y軸加速度大小。 Radial Acceleration:徑向加速度,此值為正數,粒子離發射器越遠速度就越快;此值為負數,粒子離發射器越遠,速度就越慢。 Radial Acceleration Variance:徑向加速度浮動值。 Trangential Acceleration:切向加速度,它可以讓粒子圍著發射器旋轉,粒子旋轉離開發射器越遠,速度越快。此屬性值為正數,粒子逆時針旋轉;此屬性為負數,粒子順時針旋轉。 Trangential Acceleration Variance:切向加速度浮動值。 放射發射器型別專用屬性Max Radius:最大半徑,是粒子效果的節點位置和發射粒子的位置之間的距離。 Max Radius Variance:最大半徑浮動值。 Min Radius:最小半徑,是粒子效果和粒子最終要到達的位置之間的距離。 Rotate Per Second:每秒旋轉,使用此值來影響粒子移動的方向和速度。 Rotate Per Second Variance:每秒旋轉浮動值。 使用
void ParticleBatchHybrid::onEnter()
{
    ParticleDemo::onEnter();

    setColor(ccBLACK);
    removeChild(m_background, true);
    m_background = NULL;

    m_emitter = CCParticleSystemQuad::create("Particles/LavaFlow.plist");
    m_emitter->retain();
    CCParticleBatchNode *batch = CCParticleBatchNode::createWithTexture(m_emitter->getTexture());

    batch->addChild(m_emitter);

    addChild(batch, 10);

     schedule(schedule_selector(ParticleBatchHybrid::switchRender), 2.0f);
 
     CCNode *node = CCNode::create();
     addChild(node);
 
     m_pParent1 = batch;
     m_pParent2 = node;
}
效果
常用x引擎內建粒子特效火焰效果:x引擎使內建的CCParticleFire類實現了這一粒子特效,全部粒子和發射器的屬性定義都由CCParticleFire類實現。唯一要做的就是需要指定粒子使用的2D圖片。 使用
CCParticleFire* fire = CCParticleFire::create();
fire->retain();
fire->setTexture(CCTextureCache::sharedTextureCache()->addImage("fire.png"));

fire->setPosition(ccp(visibleSize.width/2,visibleSize.height/2));
this->addChild(fire);
效果
爆炸效果:x引擎使用內建的CCParticleExplosion類實現爆炸特效,與CCParticleFire一樣,全部粒子和發射器的屬性定義都由CCParticleExplosion類實現。 使用
CCParticleExplosion* boom = CCParticleExplosion::create();
boom->retain();
boom->setTexture(CCTextureCache::sharedTextureCache()->addImage("fire.png"));

boom->setPosition(ccp(visibleSize.width/2,visibleSize.height/2));
this->addChild(boom);
效果
煙霧效果:x引擎使用內建的CCParticleSmoke類實現了這一粒子特效。 使用
CCParticleSmoke* smoke = CCParticleSmoke::create();
smoke->retain();
smoke->setTexture(CCTextureCache::sharedTextureCache()->addImage("fire.png"));

smoke->setPosition(ccp(visibleSize.width/2,visibleSize.height/2));
this->addChild(smoke);
效果
x引擎內建了30多種粒子特效,要想高效地在遊戲中實現粒子特效,更多的是需要掌握粒子特效工具的使用,以及利用好x引擎以及提供給大家的多種粒子特效樣例。