summaryrefslogtreecommitdiff
path: root/game/client/tf2/c_shield_mobile.cpp
diff options
context:
space:
mode:
authorFluorescentCIAAfricanAmerican <[email protected]>2020-04-22 12:56:21 -0400
committerFluorescentCIAAfricanAmerican <[email protected]>2020-04-22 12:56:21 -0400
commit3bf9df6b2785fa6d951086978a3e66f49427166a (patch)
tree2c0f1f0c63c4832882bc93814ebd2c2b1c6224e5 /game/client/tf2/c_shield_mobile.cpp
downloadarchived-source-engine-2018-hl2-src-master.tar.xz
archived-source-engine-2018-hl2-src-master.zip
Diffstat (limited to 'game/client/tf2/c_shield_mobile.cpp')
-rw-r--r--game/client/tf2/c_shield_mobile.cpp274
1 files changed, 274 insertions, 0 deletions
diff --git a/game/client/tf2/c_shield_mobile.cpp b/game/client/tf2/c_shield_mobile.cpp
new file mode 100644
index 0000000..1de8592
--- /dev/null
+++ b/game/client/tf2/c_shield_mobile.cpp
@@ -0,0 +1,274 @@
+//========= Copyright Valve Corporation, All rights reserved. ============//
+//
+// Purpose: Client's sheild entity
+//
+// $Workfile: $
+// $NoKeywords: $
+//=============================================================================//
+#include "cbase.h"
+#include "C_Shield.h"
+#include "tf_shieldshared.h"
+
+enum
+{
+ NUM_SUBDIVISIONS = 21,
+};
+
+#define EMP_WAVE_AMPLITUDE 8.0f
+
+//-----------------------------------------------------------------------------
+// Mobile version of the shield
+//-----------------------------------------------------------------------------
+
+class C_ShieldMobile;
+class C_ShieldMobileActiveVertList : public IActiveVertList
+{
+public:
+ void Init( C_ShieldMobile *pShield, unsigned char *pVertList );
+
+// IActiveVertList overrides.
+public:
+
+ virtual int GetActiveVertState( int iVert );
+ virtual void SetActiveVertState( int iVert, int bOn );
+
+private:
+ C_ShieldMobile *m_pShield;
+ unsigned char *m_pVertsActive;
+};
+
+
+class C_ShieldMobile : public C_Shield
+{
+ DECLARE_CLASS( C_ShieldMobile, C_Shield );
+public:
+ DECLARE_CLIENTCLASS();
+
+ C_ShieldMobile();
+ ~C_ShieldMobile();
+
+ void OnDataChanged( DataUpdateType_t updateType );
+ virtual void GetBounds( Vector& mins, Vector& maxs );
+
+ virtual void AddEntity( );
+
+ // Return true if the panel is active
+ virtual bool IsPanelActive( int x, int y );
+
+ // Gets at the control point data; who knows how it was made?
+ virtual void GetShieldData( Vector const** ppVerts, float* pOpacity, float* pBlend );
+ virtual const Vector& GetPoint( int x, int y ) { return m_ShieldEffect.GetPoint( x, y ); }
+
+ virtual void SetThetaPhi( float flTheta, float flPhi ) { m_ShieldEffect.SetThetaPhi(flTheta,flPhi); }
+
+public:
+ // networked data
+ unsigned char m_pVertsActive[SHIELD_VERTEX_BYTES];
+ unsigned char m_ShieldState;
+
+private:
+ C_ShieldMobile( const C_ShieldMobile& );
+
+ // Is a particular panel an edge?
+ bool IsVertexValid( float s, float t ) const;
+ void PreRender( );
+
+private:
+ CShieldEffect m_ShieldEffect;
+ C_ShieldMobileActiveVertList m_VertList;
+ float m_flTheta;
+ float m_flPhi;
+};
+
+
+//-----------------------------------------------------------------------------
+// C_ShieldMobileActiveVertList functions
+//-----------------------------------------------------------------------------
+
+void C_ShieldMobileActiveVertList::Init( C_ShieldMobile *pShield, unsigned char *pVertList )
+{
+ m_pShield = pShield;
+ m_pVertsActive = pVertList;
+}
+
+
+int C_ShieldMobileActiveVertList::GetActiveVertState( int iVert )
+{
+ return m_pVertsActive[iVert>>3] & (1 << (iVert & 7));
+}
+
+
+void C_ShieldMobileActiveVertList::SetActiveVertState( int iVert, int bOn )
+{
+ if ( bOn )
+ m_pVertsActive[iVert>>3] |= (1 << (iVert & 7));
+ else
+ m_pVertsActive[iVert>>3] &= ~(1 << (iVert & 7));
+}
+
+
+//-----------------------------------------------------------------------------
+// Data table
+//-----------------------------------------------------------------------------
+
+IMPLEMENT_CLIENTCLASS_DT(C_ShieldMobile, DT_Shield_Mobile, CShieldMobile)
+
+ RecvPropInt( RECVINFO(m_ShieldState) ),
+ RecvPropArray(
+ RecvPropInt( RECVINFO(m_pVertsActive[0])),
+ m_pVertsActive
+ ),
+ RecvPropFloat( RECVINFO(m_flTheta) ),
+ RecvPropFloat( RECVINFO(m_flPhi) ),
+
+END_RECV_TABLE()
+
+
+//-----------------------------------------------------------------------------
+// Various raycasting routines
+//-----------------------------------------------------------------------------
+
+
+void ShieldTraceLine(const Vector &vecStart, const Vector &vecEnd,
+ unsigned int mask, int collisionGroup, trace_t *ptr)
+{
+ UTIL_TraceLine(vecStart, vecEnd, mask, NULL, collisionGroup, ptr );
+}
+
+void ShieldTraceHull(const Vector &vecStart, const Vector &vecEnd,
+ const Vector &hullMin, const Vector &hullMax,
+ unsigned int mask, int collisionGroup, trace_t *ptr)
+{
+ CTraceFilterWorldOnly traceFilter;
+ enginetrace->TraceHull( vecStart, vecEnd, hullMin, hullMax, mask, &traceFilter, ptr );
+}
+
+
+//-----------------------------------------------------------------------------
+// Constructor, destructor
+//-----------------------------------------------------------------------------
+
+C_ShieldMobile::C_ShieldMobile() : m_ShieldEffect(ShieldTraceLine, ShieldTraceHull)
+{
+ m_VertList.Init( this, m_pVertsActive );
+ m_ShieldEffect.SetActiveVertexList( &m_VertList );
+ m_ShieldEffect.Spawn(vec3_origin, vec3_angle);
+ InitShield( SHIELD_NUM_HORIZONTAL_POINTS, SHIELD_NUM_VERTICAL_POINTS, NUM_SUBDIVISIONS );
+}
+
+C_ShieldMobile::~C_ShieldMobile()
+{
+}
+
+//-----------------------------------------------------------------------------
+// Get this after the data changes
+//-----------------------------------------------------------------------------
+
+void C_ShieldMobile::OnDataChanged( DataUpdateType_t updateType )
+{
+ BaseClass::OnDataChanged( updateType );
+
+ m_ShieldEffect.SetCurrentPosition( GetAbsOrigin() );
+ m_ShieldEffect.SetCurrentAngles( GetAbsAngles() );
+ m_ShieldEffect.SetThetaPhi( m_flTheta, m_flPhi );
+
+ // No need to simulate, just compute active panels from network data
+ m_ShieldEffect.ComputeControlPoints();
+ m_ShieldEffect.ComputePanelActivity();
+}
+
+//-----------------------------------------------------------------------------
+// A little pre-render processing
+//-----------------------------------------------------------------------------
+
+void C_ShieldMobile::PreRender( )
+{
+ if (m_ShieldState & SHIELD_MOBILE_EMP)
+ {
+ // Decay fade if we've been EMPed or if we're inactive
+ if (m_FadeValue > 0.0f)
+ {
+ m_FadeValue -= gpGlobals->frametime / SHIELD_EMP_FADE_TIME;
+ if (m_FadeValue < 0.0f)
+ {
+ m_FadeValue = 0.0f;
+
+ // Reset the shield to un-wobbled state
+ m_ShieldEffect.ComputeControlPoints();
+ }
+ else
+ {
+ Vector dir;
+ AngleVectors( m_ShieldEffect.GetCurrentAngles(), & dir );
+
+ // Futz with the control points if we've been EMPed
+ for (int i = 0; i < SHIELD_NUM_CONTROL_POINTS; ++i)
+ {
+ // Get the direction for the point
+ float factor = -EMP_WAVE_AMPLITUDE * sin( i * M_PI * 0.5f + gpGlobals->curtime * M_PI / SHIELD_EMP_WOBBLE_TIME );
+ m_ShieldEffect.GetPoint(i) += dir * factor;
+ }
+ }
+ }
+ }
+ else
+ {
+ // Fade back in, no longer EMPed
+ if (m_FadeValue < 1.0f)
+ {
+ m_FadeValue += gpGlobals->frametime / SHIELD_EMP_FADE_TIME;
+ if (m_FadeValue >= 1.0f)
+ {
+ m_FadeValue = 1.0f;
+ }
+ }
+ }
+}
+
+void C_ShieldMobile::AddEntity( )
+{
+ BaseClass::AddEntity( );
+ PreRender();
+}
+
+//-----------------------------------------------------------------------------
+// Bounds computation
+//-----------------------------------------------------------------------------
+
+void C_ShieldMobile::GetBounds( Vector& mins, Vector& maxs )
+{
+ m_ShieldEffect.ComputeBounds( mins, maxs );
+}
+
+//-----------------------------------------------------------------------------
+// Return true if the panel is active
+//-----------------------------------------------------------------------------
+
+bool C_ShieldMobile::IsPanelActive( int x, int y )
+{
+ return m_ShieldEffect.IsPanelActive(x, y);
+}
+
+//-----------------------------------------------------------------------------
+// Gets at the control point data; who knows how it was made?
+//-----------------------------------------------------------------------------
+
+void C_ShieldMobile::GetShieldData( Vector const** ppVerts, float* pOpacity, float* pBlend )
+{
+ for ( int i = 0; i < SHIELD_NUM_CONTROL_POINTS; ++i )
+ {
+ ppVerts[i] = &m_ShieldEffect.GetControlPoint(i);
+
+ if ( m_pVertsActive[i >> 3] & (1 << (i & 0x7)) )
+ {
+ pOpacity[i] = m_ShieldEffect.ComputeOpacity( *ppVerts[i], GetAbsOrigin() );
+ pBlend[i] = 1.0f;
+ }
+ else
+ {
+ pOpacity[i] = 192.0f;
+ pBlend[i] = 0.0f;
+ }
+ }
+}
+