2d畫面中常常用一組連續畫面效果紋理替換來實現爆炸效果。
而3d遊戲中,我們經常看到被炸飛的石塊,怪物被爆裂,效果很酷。他們的模型是三維的,怎麼模擬這種效果的呢?熟悉建模的人知道,最精美的模型也是通過三角面片拼接而成。物體爆炸時被肢解成面片,這些面片按一定的方向,從原位置飛四散出去。那麼按什麼方向纔有這種效果呢? 對,面的法線方向,而不是頂點法線方向。
首先來計算模型三角面的法線:
// 從索引緩衝區中取出麪皮頂點的索引號
int p0 = pIndex[p];
int p1 = pIndex[p+1];
int p2 = pIndex[p+2];
//根據索引從頂點緩衝數據區中找到相應的頂點數據
//vA vB是面上的兩條線,據此求出面法線
D3DXVECTOR3 vA = pVerts[p0].pos - pVerts[p1].pos;
D3DXVECTOR3 vB = pVerts[p0].pos - pVerts[p2].pos;
D3DXVECTOR3 vFaceNormal;
D3DXVec3Cross( &vFaceNormal, &vA, &vB );
D3DXVec3Normalize( &vFaceNormal, &vFaceNormal );
//重新設置頂點法線。
pVerts[p0].normal = vFaceNormal;
pVerts[p1].normal = vFaceNormal;
pVerts[p2].normal = vFaceNormal;
在vs shader 中,更新面片的位置:
vOutput VS_main(veInput IN)
{
vOutput OUT;
float3 P = IN.position.xyz + (IN.normal * fNormalZ); //加上偏移量,更新位置。
OUT.T0 = IN.texCoordDiffuse;
OUT.HPOS = mul(float4(P, 1.0f), worldViewProj);
OUT.color = IN.color;
OUT.normal = IN.normal;
return OUT;
}
當fNormalZ大 到一定值後,讓這些爆炸物消失掉,用alpha來過渡,以至於效果不那麼突兀。
float4 PS_main( vOutput IN): COLOR
{
float4 diffuseTexture = tex2D( TextureSampler, IN.T0 );
diffuseTexture.a = fAlphaFactor; //alpha 漸變 1-〉0;
}
在 遊戲循環中,我們只要恰當的改變shader裏的 fNormalZ 和fAlphaFactor值就能看到效果了,當然配合上粒子特效會更酷。