etqw-sdk/source/game/effects/SnowEffect.cpp

347 lines
9.4 KiB
C++
Raw Normal View History

2008-05-29 00:00:00 +00:00
// Copyright (C) 2007 Id Software, Inc.
//
#include "../precompiled.h"
#pragma hdrstop
#if defined( _DEBUG ) && !defined( ID_REDIRECT_NEWDELETE )
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
#include "../Atmosphere.h"
#include "SnowEffect.h"
#include "../Player.h"
#include "../demos/DemoManager.h"
CLASS_DECLARATION( idEntity, sdSnowEffect )
END_CLASS
/*
==============
sdSnowEffect::Spawn
==============
*/
void sdSnowEffect::Spawn( void ) {
renderEntity_t *re = GetRenderEntity();
re->numInsts = MAX_GROUPS;
re->insts = new sdInstInfo[ re->numInsts ];
idVec3 zero;
idMat3 I;
zero.Zero();
I.Identity();
this->SetPosition( zero, I );
idBounds modelbb = re->hModel->Bounds();
idVec3 extents = (modelbb.GetMaxs() - modelbb.GetMins()) * 0.5f;
idPlayer *p = gameLocal.GetLocalViewPlayer();
idVec3 const &v = p->GetViewPos();
for (int i=0; i<MAX_GROUPS; i++) {
groups[i].time = -1.f;
}
BecomeActive( TH_THINK );
UpdateVisuals();
}
/*
==============
sdSnowEffect::Think
==============
*/
void sdSnowEffect::Think( void ) {
renderEntity_t *re = GetRenderEntity();
if ( re->hModel == NULL ) {
return;
}
idBounds modelbb = re->hModel->Bounds();
idVec3 extents = (modelbb.GetMaxs() - modelbb.GetMins()) * 0.5f;
idPlayer *p = gameLocal.GetLocalViewPlayer();
idVec3 const &v = p->GetViewPos();
for (int i=0; i<MAX_GROUPS; i++) {
groups[i].time -= 1.f / 30.f;
if ( groups[i].time < 0.f ) {
groups[i].axis = idVec3( idRandom::StaticRandom().RandomFloat()- 0.15f , idRandom::StaticRandom().RandomFloat() - 0.5f , idRandom::StaticRandom().RandomFloat() - 0.5f );
groups[i].axis.z *= 40.25f;
groups[i].axis.Normalize();
groups[i].rotate = 0.f;
groups[i].rotateSpeed = idRandom::StaticRandom().RandomFloat() * 50.f + 50.f;
groups[i].rotationPoint = idVec3( idRandom::StaticRandom().RandomFloat() * extents.x,
idRandom::StaticRandom().RandomFloat() * extents.y,
idRandom::StaticRandom().RandomFloat() * extents.z );
groups[i].alpha = 0.f;
groups[i].time = idRandom::StaticRandom().RandomFloat() * 1.f + 1.f;
groups[i].worldPos = v + idVec3( (idRandom::StaticRandom().RandomFloat()-0.5f) * extents.x * 3,
(idRandom::StaticRandom().RandomFloat()-0.5f) * extents.y * 3,
(idRandom::StaticRandom().RandomFloat()-0.5f) * extents.z * 3 );
} else {
if ( groups[i].time > 0.25f ) {
groups[i].alpha += 1.f / 7.5f;
if ( groups[i].alpha > 1.f ) {
groups[i].alpha = 1.f;
}
} else {
groups[i].alpha = groups[i].time * 4.f;
if ( groups[i].alpha < 0.f ) {
groups[i].alpha = 0.f;
}
}
groups[i].worldPos += idVec3( 0.f, 0.f, -600.f ) * 1.f / 30.f;
groups[i].rotate += groups[i].rotateSpeed * 1.f / 30.f;
}
}
int gridx = idMath::Ftoi( idMath::Floor(v.x / extents.x) );
int gridy = idMath::Ftoi( idMath::Floor(v.y / extents.y) );
idBounds bounds;
bounds.Clear();
sdInstInfo *inst = re->insts;
for (int i=0; i<MAX_GROUPS; i++) {
idRotation r( groups[i].rotationPoint, groups[i].axis, groups[i].rotate );
idBounds bb2;
inst->inst.color[0] = 0xff;
inst->inst.color[1] = 0xff;
inst->inst.color[2] = 0xff;
inst->inst.color[3] = 0xff;
inst->fadeOrigin = inst->inst.origin = groups[i].worldPos;
inst->inst.axis = r.ToMat3();
inst->maxVisDist = 0;
inst->minVisDist = 0.f;
bb2.FromTransformedBounds( modelbb, inst->inst.origin, inst->inst.axis );
bounds.AddBounds( bb2 );
inst++;
}
re->flags.overridenBounds = true;
re->bounds = bounds;
UpdateVisuals();
Present();
}
/*
==============
sdSnowPrecipitation::sdSnowPrecipitation
==============
*/
sdSnowPrecipitation::sdSnowPrecipitation( sdPrecipitationParameters const &_parms ) : parms(_parms) {
renderEntity_t *re = GetRenderEntity();
renderEntityHandle = -1;
memset( re, 0, sizeof( renderEntity ) );
re->hModel = parms.model;
re->axis.Identity();
re->origin.Zero();
re->numInsts = MAX_GROUPS;
re->insts = new sdInstInfo[ re->numInsts ];
idBounds modelbb = re->hModel->Bounds();
idVec3 extents = (modelbb.GetMaxs() - modelbb.GetMins()) * 0.5f;
idPlayer *p = gameLocal.GetLocalViewPlayer();
idVec3 const &v = p->GetViewPos();
for (int i=0; i<MAX_GROUPS; i++) {
groups[i].time = -1.f;
}
SetupEffect();
}
/*
==============
sdSnowPrecipitation::~sdSnowPrecipitation
==============
*/
sdSnowPrecipitation::~sdSnowPrecipitation() {
FreeRenderEntity();
delete []renderEntity.insts;
}
/*
==============
sdSnowPrecipitation::SetupEffect
==============
*/
void sdSnowPrecipitation::SetupEffect( void ) {
renderEffect_t &renderEffect = effect.GetRenderEffect();
renderEffect.declEffect = parms.effect;
renderEffect.axis.Identity();
renderEffect.loop = true;
renderEffect.shaderParms[SHADERPARM_RED] = 1.0f;
renderEffect.shaderParms[SHADERPARM_GREEN] = 1.0f;
renderEffect.shaderParms[SHADERPARM_BLUE] = 1.0f;
renderEffect.shaderParms[SHADERPARM_ALPHA] = 1.0f;
renderEffect.shaderParms[SHADERPARM_BRIGHTNESS] = 1.0f;
effectRunning = false;
}
/*
==============
sdSnowPrecipitation::SetMaxActiveParticles
==============
*/
void sdSnowPrecipitation::SetMaxActiveParticles( int num ) {
}
/*
==============
sdSnowPrecipitation::Update
==============
*/
void sdSnowPrecipitation::Update( void ) {
renderEntity_t *re = GetRenderEntity();
if ( re->hModel == NULL ) {
return;
}
idBounds modelbb = re->hModel->Bounds();
idVec3 extents = (modelbb.GetMaxs() - modelbb.GetMins()) * 0.5f;
idPlayer *p = gameLocal.GetLocalViewPlayer();
idVec3 const &v = p->GetViewPos();
for (int i=0; i<MAX_GROUPS; i++) {
groups[i].time -= 1.f / 30.f;
if ( groups[i].time < 0.f ) {
groups[i].axis = idVec3( idRandom::StaticRandom().RandomFloat()- 0.15f , idRandom::StaticRandom().RandomFloat() - 0.5f , idRandom::StaticRandom().RandomFloat() - 0.5f );
groups[i].axis.z *= 40.25f;
groups[i].axis.Normalize();
groups[i].rotate = 0.f;
groups[i].rotateSpeed = idRandom::StaticRandom().RandomFloat() * 50.f + 50.f;
groups[i].rotationPoint = idVec3( idRandom::StaticRandom().RandomFloat() * extents.x,
idRandom::StaticRandom().RandomFloat() * extents.y,
idRandom::StaticRandom().RandomFloat() * extents.z );
groups[i].alpha = 0.f;
groups[i].time = idRandom::StaticRandom().RandomFloat() * 1.f + 1.f;
groups[i].worldPos = v + idVec3( (idRandom::StaticRandom().RandomFloat()-0.5f) * extents.x * 3,
(idRandom::StaticRandom().RandomFloat()-0.5f) * extents.y * 3,
(idRandom::StaticRandom().RandomFloat()-0.5f) * extents.z * 3 );
} else {
if ( groups[i].time > 0.25f ) {
groups[i].alpha += 1.f / 7.5f;
if ( groups[i].alpha > 1.f ) {
groups[i].alpha = 1.f;
}
} else {
groups[i].alpha = groups[i].time * 4.f;
if ( groups[i].alpha < 0.f ) {
groups[i].alpha = 0.f;
}
}
groups[i].worldPos += idVec3( 0.f, 0.f, -600.f ) * 1.f / 30.f;
groups[i].rotate += groups[i].rotateSpeed * 1.f / 30.f;
}
}
int gridx = idMath::Ftoi( idMath::Floor(v.x / extents.x) );
int gridy = idMath::Ftoi( idMath::Floor(v.y / extents.y) );
idBounds bounds;
bounds.Clear();
sdInstInfo *inst = re->insts;
for (int i=0; i<MAX_GROUPS; i++) {
idRotation r( groups[i].rotationPoint, groups[i].axis, groups[i].rotate );
idBounds bb2;
inst->inst.color[0] = 0xff;
inst->inst.color[1] = 0xff;
inst->inst.color[2] = 0xff;
inst->inst.color[3] = 0xff;
inst->fadeOrigin = inst->inst.origin = groups[i].worldPos;
inst->inst.axis = r.ToMat3();
inst->maxVisDist = 0;
inst->minVisDist = 0.f;
bb2.FromTransformedBounds( modelbb, inst->inst.origin, inst->inst.axis );
bounds.AddBounds( bb2 );
inst++;
}
re->flags.overridenBounds = true;
re->bounds = bounds;
if ( renderEntityHandle == -1 ) {
renderEntityHandle = gameRenderWorld->AddEntityDef( re );
} else {
gameRenderWorld->UpdateEntityDef( renderEntityHandle, re );
}
if ( !effect.GetRenderEffect().declEffect ) return;
idVec3 viewOrg;
renderView_t view;
if ( sdDemoManager::GetInstance().CalculateRenderView( &view ) ) {
viewOrg = view.vieworg;
} else {
// If we are inside don't run the bacground effect
idPlayer* player = gameLocal.GetLocalViewPlayer();
if ( player == NULL ) {
return;
}
viewOrg = player->GetRenderView()->vieworg;
}
int area = gameRenderWorld->PointInArea( viewOrg );
bool runEffect = false;
if ( area >= 0 ) {
if ( gameRenderWorld->GetAreaPortalFlags( area ) & ( 1 << PORTAL_OUTSIDE ) ) {
runEffect = true && !g_skipLocalizedPrecipitation.GetBool();
}
}
// Update the background effect
if ( runEffect ) {
effect.GetRenderEffect().origin = viewOrg;
if ( !effectRunning ) {
effect.Start( gameLocal.time );
effectRunning = true;
} else {
effect.Update();
}
} else {
effect.StopDetach();
effectRunning = false;
}
}
/*
==============
sdSnowPrecipitation::Init
==============
*/
void sdSnowPrecipitation::Init( void ) {
}
/*
==============
sdSnowPrecipitation::FreeRenderEntity
==============
*/
void sdSnowPrecipitation::FreeRenderEntity( void ) {
if ( renderEntityHandle != -1 ) {
gameRenderWorld->FreeEntityDef( renderEntityHandle );
renderEntityHandle = -1;
}
if ( !effect.GetRenderEffect().declEffect ) return;
effect.FreeRenderEffect();
}