diff options
Diffstat (limited to 'game/client/tf/tf_fx_christmaslights.cpp')
| -rw-r--r-- | game/client/tf/tf_fx_christmaslights.cpp | 214 |
1 files changed, 214 insertions, 0 deletions
diff --git a/game/client/tf/tf_fx_christmaslights.cpp b/game/client/tf/tf_fx_christmaslights.cpp new file mode 100644 index 0000000..3d93d95 --- /dev/null +++ b/game/client/tf/tf_fx_christmaslights.cpp @@ -0,0 +1,214 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: Game-specific impact effect hooks +// +//=============================================================================// +#include "cbase.h" + +#include "c_te_effect_dispatch.h" +#include "tempent.h" +#include "c_te_legacytempents.h" +#include "tf_shareddefs.h" +#include "c_rope.h" + +// NOTE: Always include this last! +#include "tier0/memdbgon.h" + + +// Used for cycling so that they're sequencially ordered on each strand +int g_nHolidayLightColor = 0; + +// 4 light colors +Color g_rgbaHolidayRed( 255, 0, 0, 255 ); +Color g_rgbaHolidayYellow( 2, 110, 197, 255 ); +Color g_rgbaHolidayGreen( 117, 193, 8, 255 ); +Color g_rgbaHolidayBlue( 255, 151, 29, 255 ); + +Color *(rgbaHolidayLightColors[]) = { &g_rgbaHolidayRed, + &g_rgbaHolidayYellow, + &g_rgbaHolidayGreen, + &g_rgbaHolidayBlue }; + + +struct HolidayLightData_t +{ + Vector vOrigin; + int nID; + int nSubID; + float fScale; +}; + + +void CreateHolidayLight( const HolidayLightData_t &holidayLight ); + + +class CHolidayLightManager : public CAutoGameSystemPerFrame +{ +public: + CHolidayLightManager( char const *name ); + + // Methods of IGameSystem + virtual void Update( float frametime ); + + virtual void LevelInitPostEntity( void ); + virtual void LevelShutdownPreEntity(); + + void AddHolidayLight( const CEffectData &data ); + +private: + + CUtlVector< HolidayLightData_t > m_PendingLightData; +}; + +CHolidayLightManager g_CHolidayLightManager( "CHolidayLightManager" ); + + +CHolidayLightManager::CHolidayLightManager( char const *name ) : CAutoGameSystemPerFrame( name ) +{ +} + +// Methods of IGameSystem +void CHolidayLightManager::Update( float frametime ) +{ + for ( int i = 0; i < m_PendingLightData.Count(); ++i ) + { + CreateHolidayLight( m_PendingLightData[ i ] ); + } + + m_PendingLightData.RemoveAll(); +} + +void CHolidayLightManager::LevelInitPostEntity( void ) +{ + m_PendingLightData.RemoveAll(); +} + +void CHolidayLightManager::LevelShutdownPreEntity() +{ + m_PendingLightData.RemoveAll(); +} + +void CHolidayLightManager::AddHolidayLight( const CEffectData &data ) +{ + C_BasePlayer *pPlayer = C_BasePlayer::GetLocalPlayer(); + if ( !pPlayer ) + return; + + // Too far away? + if ( pPlayer->GetAbsOrigin().DistTo( data.m_vOrigin ) > 2000.0f ) + return; + + // In the skybox? + sky3dparams_t *pSky = &(pPlayer->m_Local.m_skybox3d); + if ( pSky->origin->DistTo( data.m_vOrigin ) < 2000.0f ) + return; + + HolidayLightData_t newData; + + newData.vOrigin = data.m_vOrigin; + + // HACK: Use these ints to ID the light later + newData.nID = data.m_nMaterial; + newData.nSubID = data.m_nHitBox; + + // Skybox lights pass in a smaller scale + newData.fScale = data.m_flScale; + + if ( m_PendingLightData.Count() < CTempEnts::MAX_TEMP_ENTITIES / 2 ) + { + m_PendingLightData.AddToTail( newData ); + } +} + + +void TF_HolidayLightCallback( const CEffectData &data ) +{ + g_CHolidayLightManager.AddHolidayLight( data ); +} + +void CreateHolidayLight( const HolidayLightData_t &holidayLight ) +{ + int nHolidayLightStyle = RopeManager()->GetHolidayLightStyle(); + + const model_t *pModel = ( nHolidayLightStyle == 0 ? engine->LoadModel( "effects/christmas_bulb.vmt" ) : engine->LoadModel( "effects/mtp_fluff.vmt" ) ); + if ( !pModel ) + return; + + Assert( pModel ); + + C_LocalTempEntity *pTemp = tempents->FindTempEntByID( holidayLight.nID, holidayLight.nSubID ); + + if ( !pTemp ) + { + // Didn't find one with that ID, so make a new one! + // Randomize the angle + QAngle angOrientation = ( nHolidayLightStyle == 0 ? QAngle( 0.0f, 0.0f, RandomFloat( -180.0f, 180.0f ) ) : vec3_angle ); + pTemp = tempents->SpawnTempModel( pModel, holidayLight.vOrigin, angOrientation, vec3_origin, 2.0f, FTENT_NEVERDIE ); + if ( !pTemp ) + { + return; + } + + pTemp->clientIndex = 0; + + // HACK: Use these ints to ID the light later + pTemp->m_nSkin = holidayLight.nID; + pTemp->hitSound = holidayLight.nSubID; + + // Skybox lights pass in a smaller scale + pTemp->m_flSpriteScale = holidayLight.fScale; + + // Smuggle the color index here + pTemp->m_nHitboxSet = g_nHolidayLightColor; + + // Set the color + pTemp->SetRenderColor( rgbaHolidayLightColors[ g_nHolidayLightColor ]->r(), + rgbaHolidayLightColors[ g_nHolidayLightColor ]->g(), + rgbaHolidayLightColors[ g_nHolidayLightColor ]->b(), + rgbaHolidayLightColors[ g_nHolidayLightColor ]->a() ); + + // Next color in the pattern + g_nHolidayLightColor = ( g_nHolidayLightColor + 1 ) % ARRAYSIZE( rgbaHolidayLightColors ); + + // Animate if needed + pTemp->m_flFrameMax = modelinfo->GetModelFrameCount( pModel ) - 1; + pTemp->flags = ( FTENT_SPRANIMATE | FTENT_SPRANIMATELOOP ); + pTemp->m_flFrameRate = 10; + } + else + { + // Update the position + pTemp->SetAbsOrigin( holidayLight.vOrigin ); + + // Every 10 light strands have a blink cycle + if ( pTemp->m_nSkin % 5 == 0 ) + { + // Magic! Basically this makes the on/off cycle of each color different and offsets it by the segment index. + // That way it looks like a timed pattern but is also chaotic. + int nCycle = ( pTemp->hitSound + static_cast< int >( gpGlobals->curtime * 2.0f ) ) % ( pTemp->m_nHitboxSet + ARRAYSIZE( rgbaHolidayLightColors ) + 1 ); + pTemp->SetRenderColorA( nCycle < ARRAYSIZE( rgbaHolidayLightColors ) ? 255 : 64 ); + } + + // Update the scale + pTemp->m_flSpriteScale = holidayLight.fScale; + + // Extend it's life + pTemp->die = gpGlobals->curtime + 2.0f; + } +} + +DECLARE_CLIENT_EFFECT( "TF_HolidayLight", TF_HolidayLightCallback ); + +void RopesHolidayLightColor( const CCommand &args ) +{ + if ( args.ArgC() < 5 ) + return; + + int nLight = atoi( args[ 1 ] ); + + if ( nLight < 0 || nLight >= ARRAYSIZE( rgbaHolidayLightColors ) ) + return; + + rgbaHolidayLightColors[ nLight ]->SetColor( atoi( args[ 2 ] ), atoi( args[ 3 ] ), atoi( args[ 4 ] ) ); +} +ConCommand r_ropes_holiday_light_color( "r_ropes_holiday_light_color", RopesHolidayLightColor, "Set each light's color: [light0-3] [r0-255] [g0-255] [b0-255]", FCVAR_NONE );
\ No newline at end of file |