📄 ch21p1_lasergun.cpp
字号:
#include "Ch21p1_LaserGun.h"
#include "D3DUtil.h"
CLaserGun::CLaserGun()
{
m_bIsFiring = false;
}
CLaserGun::~CLaserGun()
{
}
HRESULT CLaserGun::RestoreDeviceObjects(LPDIRECT3DDEVICE8 pDev, const char *strMeshFilename)
{
HRESULT hr = S_OK;
hr = CGun::RestoreDeviceObjects(pDev, strMeshFilename);
if(FAILED(hr)) return(hr);
hr = m_pd3dDevice->CreateVertexBuffer( 4*sizeof(VERTEX_XYZ_DIFFUSE_TEX1),
D3DUSAGE_WRITEONLY, D3DFVF_XYZ_DIFFUSE_TEX1,
D3DPOOL_MANAGED, &m_pVBLaser );
if(FAILED(hr)) return(hr);
hr = m_pd3dDevice->CreateIndexBuffer( 6*sizeof(WORD),
D3DUSAGE_WRITEONLY,
D3DFMT_INDEX16, D3DPOOL_MANAGED,
&m_pIBLaser );
if(FAILED(hr)) return(hr);
m_pAnim = new CAnimSequence(pDev);
m_pAnim->AddFrame("Ch21p1_Laser.dds", 200000.0f);
std::string strScript;
LoadFileIntoString("Ch21p1_LaserScript.txt", strScript);
m_Emitter.RestoreDeviceObjects(m_pd3dDevice);
m_Emitter.Compile(strScript.c_str());
return(S_OK);
}
void CLaserGun::InvalidateDeviceObjects()
{
CGun::InvalidateDeviceObjects();
SAFE_RELEASE(m_pVBLaser);
SAFE_RELEASE(m_pIBLaser);
SAFE_DELETE(m_pAnim);
m_Emitter.InvalidateDeviceObjects();
}
void CLaserGun::Render(CCamera &camera)
{
if (!m_pd3dDevice) return;
// create a light
{
D3DLIGHT8 light; ZeroMemory(&light, sizeof(D3DLIGHT8));
// Laser gun looks red
D3DUtil_InitLight(light, D3DLIGHT_DIRECTIONAL, -10.0f, 20.0f, -20.0f);
light.Ambient.a = 1.0f;
light.Ambient.g = 0.0f;
light.Ambient.b = 0.0f;
light.Ambient.r = 0.1f;
light.Diffuse.a = 1.0f;
light.Diffuse.g = 0.0f;
light.Diffuse.b = 0.0f;
light.Diffuse.r = 0.3f;
light.Direction = D3DXVECTOR3(1.0f, -1.0f, 1.0f);
m_pd3dDevice->SetRenderState( D3DRS_LIGHTING, TRUE);
m_pd3dDevice->SetLight(0, &light);
m_pd3dDevice->LightEnable(0, true);
}
// if firing, render laser
if (m_Timer.IsRunning()) {
WORD* pIndices;
if( FAILED(m_pIBLaser->Lock( 0, 6*sizeof(WORD), (BYTE**)&pIndices, 0 ))) return;
VERTEX_XYZ_DIFFUSE_TEX1* pVertices;
if(FAILED(m_pVBLaser->Lock(0, 0, (BYTE**)&pVertices, NULL))) return;
pIndices[0] = 3; pIndices[1] = 2; pIndices[2] = 1;
pIndices[3] = 3; pIndices[4] = 1; pIndices[5] = 0;
float a = 1.0f-(m_Timer.GetTime()*2);
if (a < 0.0f) a = 0.0f;
pVertices[0].color = D3DXCOLOR(1.0, 0.0, 0.0, 0.0);
pVertices[1].color = D3DXCOLOR(1.0, 0.0, 0.0, 0.0);
pVertices[2].color = D3DXCOLOR(1.0, 0.0, 0.0, a);
pVertices[3].color = D3DXCOLOR(1.0, 0.0, 0.0, a);
pVertices[0].tu = 0.0f; pVertices[0].tv = 0.0f;
pVertices[1].tu = 1.0f; pVertices[1].tv = 0.0f;
pVertices[2].tu = 1.0f; pVertices[2].tv = 100.0f;
pVertices[3].tu = 0.0f; pVertices[3].tv = 100.0f;
pVertices[0].position = D3DXVECTOR3(-0.15f, -0.05f, -100.0f);
pVertices[1].position = D3DXVECTOR3( 0.15f, -0.05f, -100.0f);
pVertices[2].position = D3DXVECTOR3( 0.15f, -0.05f, -2.0f);
pVertices[3].position = D3DXVECTOR3(-0.15f, -0.05f, -2.0f);
m_pVBLaser->Unlock();
m_pIBLaser->Unlock();
// now render!
m_pd3dDevice->SetTexture(0, m_pAnim->GetCurFrameTexture(m_Timer));
m_pd3dDevice->SetTransform( D3DTS_WORLD, &m_matWorld );
m_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_NONE );
m_pd3dDevice->SetRenderState( D3DRS_LIGHTING, FALSE);
m_pd3dDevice->SetRenderState(D3DRS_ZENABLE, FALSE);
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, TRUE);
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG1, D3DTA_TEXTURE );
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLOROP, D3DTOP_SELECTARG1);
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE );
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE );
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAOP, D3DTOP_MODULATE );
m_pd3dDevice->SetTextureStageState( 1, D3DTSS_COLOROP, D3DTOP_DISABLE );
m_pd3dDevice->SetTextureStageState( 1, D3DTSS_ALPHAOP, D3DTOP_DISABLE );
m_pd3dDevice->SetVertexShader(D3DFVF_XYZ_DIFFUSE_TEX1);
m_pd3dDevice->SetStreamSource( 0, m_pVBLaser, sizeof(VERTEX_XYZ_DIFFUSE_TEX1) );
m_pd3dDevice->SetIndices( m_pIBLaser, 0L );
m_pd3dDevice->DrawIndexedPrimitive( D3DPT_TRIANGLELIST, 0, 4, 0, 2);
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, FALSE);
}
// render gun model
{
float fOffsetZ = -1.0f+(m_Timer.GetTime()*3);
if (fOffsetZ > 0.0f) fOffsetZ = 0.0f;
D3DXMATRIX matWorld;
AssembleWorldMatrix(camera, matWorld,
m_Timer.IsRunning() ?
D3DXVECTOR3(0.0f, 0.0f, fOffsetZ) :
D3DXVECTOR3(0.0f, 0.0f, 0.0f));
m_pd3dDevice->SetTransform( D3DTS_WORLD, &matWorld );
m_pd3dDevice->SetRenderState(D3DRS_ZENABLE, TRUE);
m_pd3dDevice->SetRenderState( D3DRS_CULLMODE, D3DCULL_CCW );
m_pd3dDevice->SetRenderState( D3DRS_LIGHTING, TRUE);
m_pMesh->Render(m_pd3dDevice);
}
// render particle system
m_pd3dDevice->SetRenderState( D3DRS_ALPHABLENDENABLE, TRUE);
m_pd3dDevice->SetRenderState(D3DRS_ZENABLE, FALSE);
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG1, D3DTA_TEXTURE );
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLORARG2, D3DTA_DIFFUSE );
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_COLOROP, D3DTOP_MODULATE);
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAARG1, D3DTA_DIFFUSE );
m_pd3dDevice->SetTextureStageState( 0, D3DTSS_ALPHAOP, D3DTOP_SELECTARG1 );
m_Emitter.Render();
}
void CLaserGun::Update(float fElapsedTime)
{
m_Emitter.Update(fElapsedTime, fElapsedTime);
if (m_Timer.GetTime() > 1.0f) {
m_Timer.Stop();
m_Emitter.Stop();
}
}
void CLaserGun::Fire(CCamera &camera)
{
m_Timer.Start();
m_Emitter.Start();
D3DXMATRIX matEmitterWorld, matInvView, matTrans, matRot, matGunTrans;
float fDet;
D3DXMatrixInverse(&matInvView, &fDet, &camera.GetViewMatrix());
D3DXMatrixTranslation(&matTrans, 0.0f, 0.0f, 0.0f);
D3DXMatrixRotationYawPitchRoll(&matRot, (float)PI, 0.0f, 0.0f);
D3DXMatrixTranslation(&matGunTrans, m_vPos.x, m_vPos.y, m_vPos.z);
m_matWorld = matRot * matGunTrans * matTrans * matInvView;
D3DXMatrixTranslation(&matTrans, 0.0f, 0.0f, 2.8f);
matEmitterWorld = matRot * matGunTrans * matTrans * matInvView;
m_Emitter.SetPos(D3DXVECTOR3(
matEmitterWorld._41,
matEmitterWorld._42,
matEmitterWorld._43)
);
}
bool CLaserGun::CanFire()
{
return(!m_Timer.IsRunning());
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -