mirror of
https://github.com/mapbase-source/source-sdk-2013.git
synced 2025-01-27 06:07:56 +03:00
Death ragdolls "steal" impact decals from final damage + clientside ragdolls already on the ground receive impact decals
This commit is contained in:
parent
f11d7e0be8
commit
5d484bfa5f
@ -25,6 +25,13 @@ extern ConVar r_drawmodeldecals;
|
|||||||
|
|
||||||
ImpactSoundRouteFn g_pImpactSoundRouteFn = NULL;
|
ImpactSoundRouteFn g_pImpactSoundRouteFn = NULL;
|
||||||
|
|
||||||
|
#ifdef MAPBASE
|
||||||
|
ConVar g_ragdoll_steal_impacts_client( "g_ragdoll_steal_impacts_client", "1", FCVAR_NONE, "Allows clientside death ragdolls to \"steal\" impacts from their source entities. This fixes issues with NPCs dying before decals are applied." );
|
||||||
|
ConVar g_ragdoll_steal_impacts_server( "g_ragdoll_steal_impacts_server", "1", FCVAR_NONE, "Allows serverside death ragdolls to \"steal\" impacts from their source entities. This fixes issues with NPCs dying before decals are applied." );
|
||||||
|
|
||||||
|
ConVar g_ragdoll_client_impact_decals( "g_ragdoll_client_impact_decals", "1", FCVAR_NONE, "Applies decals to clientside ragdolls when they are hit." );
|
||||||
|
#endif
|
||||||
|
|
||||||
//==========================================================================================================================
|
//==========================================================================================================================
|
||||||
// RAGDOLL ENUMERATOR
|
// RAGDOLL ENUMERATOR
|
||||||
//==========================================================================================================================
|
//==========================================================================================================================
|
||||||
@ -32,7 +39,11 @@ CRagdollEnumerator::CRagdollEnumerator( Ray_t& shot, int iDamageType )
|
|||||||
{
|
{
|
||||||
m_rayShot = shot;
|
m_rayShot = shot;
|
||||||
m_iDamageType = iDamageType;
|
m_iDamageType = iDamageType;
|
||||||
|
#ifdef MAPBASE
|
||||||
|
m_pHitEnt = NULL;
|
||||||
|
#else
|
||||||
m_bHit = false;
|
m_bHit = false;
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
IterationRetval_t CRagdollEnumerator::EnumElement( IHandleEntity *pHandleEntity )
|
IterationRetval_t CRagdollEnumerator::EnumElement( IHandleEntity *pHandleEntity )
|
||||||
@ -57,7 +68,11 @@ IterationRetval_t CRagdollEnumerator::EnumElement( IHandleEntity *pHandleEntity
|
|||||||
if ( tr.fraction < 1.0 )
|
if ( tr.fraction < 1.0 )
|
||||||
{
|
{
|
||||||
pModel->ImpactTrace( &tr, m_iDamageType, NULL );
|
pModel->ImpactTrace( &tr, m_iDamageType, NULL );
|
||||||
|
#ifdef MAPBASE
|
||||||
|
m_pHitEnt = pModel;
|
||||||
|
#else
|
||||||
m_bHit = true;
|
m_bHit = true;
|
||||||
|
#endif
|
||||||
|
|
||||||
//FIXME: Yes? No?
|
//FIXME: Yes? No?
|
||||||
return ITERATION_STOP;
|
return ITERATION_STOP;
|
||||||
@ -84,6 +99,22 @@ bool FX_AffectRagdolls( Vector vecOrigin, Vector vecStart, int iDamageType )
|
|||||||
return ragdollEnum.Hit();
|
return ragdollEnum.Hit();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef MAPBASE
|
||||||
|
C_BaseAnimating *FX_AffectRagdolls_GetHit( Vector vecOrigin, Vector vecStart, int iDamageType )
|
||||||
|
{
|
||||||
|
// don't do this when lots of ragdolls are simulating
|
||||||
|
if ( s_RagdollLRU.CountRagdolls(true) > 1 )
|
||||||
|
return false;
|
||||||
|
Ray_t shotRay;
|
||||||
|
shotRay.Init( vecStart, vecOrigin );
|
||||||
|
|
||||||
|
CRagdollEnumerator ragdollEnum( shotRay, iDamageType );
|
||||||
|
partition->EnumerateElementsAlongRay( PARTITION_CLIENT_RESPONSIVE_EDICTS, shotRay, false, &ragdollEnum );
|
||||||
|
|
||||||
|
return ragdollEnum.GetHit();
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
//-----------------------------------------------------------------------------
|
//-----------------------------------------------------------------------------
|
||||||
// Purpose:
|
// Purpose:
|
||||||
// Input : &data -
|
// Input : &data -
|
||||||
@ -104,6 +135,22 @@ bool Impact( Vector &vecOrigin, Vector &vecStart, int iMaterial, int iDamageType
|
|||||||
|
|
||||||
Assert ( pEntity );
|
Assert ( pEntity );
|
||||||
|
|
||||||
|
#ifdef MAPBASE
|
||||||
|
// If the entity already has a ragdoll that was created on the current tick, use that ragdoll instead.
|
||||||
|
// This allows the killing damage's decals to show up on the ragdoll.
|
||||||
|
if (C_BaseAnimating *pAnimating = pEntity->GetBaseAnimating())
|
||||||
|
{
|
||||||
|
if (pAnimating->m_pClientsideRagdoll && WasRagdollCreatedOnCurrentTick( pAnimating->m_pClientsideRagdoll ) && g_ragdoll_steal_impacts_client.GetBool())
|
||||||
|
{
|
||||||
|
pEntity = pAnimating->m_pClientsideRagdoll;
|
||||||
|
}
|
||||||
|
else if (pAnimating->m_pServerRagdoll && WasRagdollCreatedOnCurrentTick( pAnimating->m_pServerRagdoll ) && g_ragdoll_steal_impacts_server.GetBool())
|
||||||
|
{
|
||||||
|
pEntity = pAnimating->m_pServerRagdoll;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
// Clear out the trace
|
// Clear out the trace
|
||||||
memset( &tr, 0, sizeof(trace_t));
|
memset( &tr, 0, sizeof(trace_t));
|
||||||
tr.fraction = 1.0f;
|
tr.fraction = 1.0f;
|
||||||
@ -115,13 +162,52 @@ bool Impact( Vector &vecOrigin, Vector &vecStart, int iMaterial, int iDamageType
|
|||||||
VectorMA( vecStart, flLength + 8.0f, shotDir, traceExt );
|
VectorMA( vecStart, flLength + 8.0f, shotDir, traceExt );
|
||||||
|
|
||||||
// Attempt to hit ragdolls
|
// Attempt to hit ragdolls
|
||||||
|
|
||||||
bool bHitRagdoll = false;
|
bool bHitRagdoll = false;
|
||||||
|
|
||||||
|
#ifdef MAPBASE
|
||||||
|
if ( !pEntity->IsClientCreated() )
|
||||||
|
{
|
||||||
|
C_BaseAnimating *pRagdoll = FX_AffectRagdolls_GetHit( vecOrigin, vecStart, iDamageType );
|
||||||
|
if (pRagdoll)
|
||||||
|
{
|
||||||
|
bHitRagdoll = true;
|
||||||
|
|
||||||
|
if (g_ragdoll_client_impact_decals.GetBool())
|
||||||
|
{
|
||||||
|
pEntity = pRagdoll;
|
||||||
|
|
||||||
|
// HACKHACK: Get the ragdoll's nearest bone for its material
|
||||||
|
int iNearestMaterial = 0;
|
||||||
|
float flNearestDistSqr = FLT_MAX;
|
||||||
|
|
||||||
|
IPhysicsObject *pList[VPHYSICS_MAX_OBJECT_LIST_COUNT];
|
||||||
|
int count = pEntity->VPhysicsGetObjectList( pList, ARRAYSIZE(pList) );
|
||||||
|
for ( int i = 0; i < count; i++ )
|
||||||
|
{
|
||||||
|
Vector vecPosition;
|
||||||
|
QAngle angAngles;
|
||||||
|
pList[i]->GetPosition( &vecPosition, &angAngles );
|
||||||
|
float flDistSqr = (vecStart - vecPosition).LengthSqr();
|
||||||
|
if (flDistSqr < flNearestDistSqr)
|
||||||
|
{
|
||||||
|
iNearestMaterial = pList[i]->GetMaterialIndex();
|
||||||
|
flNearestDistSqr = flDistSqr;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get the material from the surfaceprop
|
||||||
|
surfacedata_t *psurfaceData = physprops->GetSurfaceData( iNearestMaterial );
|
||||||
|
iMaterial = psurfaceData->game.material;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
#else
|
||||||
if ( !pEntity->IsClientCreated() )
|
if ( !pEntity->IsClientCreated() )
|
||||||
{
|
{
|
||||||
bHitRagdoll = FX_AffectRagdolls( vecOrigin, vecStart, iDamageType );
|
bHitRagdoll = FX_AffectRagdolls( vecOrigin, vecStart, iDamageType );
|
||||||
}
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
if ( (nFlags & IMPACT_NODECAL) == 0 )
|
if ( (nFlags & IMPACT_NODECAL) == 0 )
|
||||||
{
|
{
|
||||||
|
@ -58,12 +58,21 @@ public:
|
|||||||
// Actual work code
|
// Actual work code
|
||||||
virtual IterationRetval_t EnumElement( IHandleEntity *pHandleEntity );
|
virtual IterationRetval_t EnumElement( IHandleEntity *pHandleEntity );
|
||||||
|
|
||||||
|
#ifdef MAPBASE
|
||||||
|
bool Hit( void ) const { return m_pHitEnt != NULL; }
|
||||||
|
C_BaseAnimating *GetHit( void ) { return m_pHitEnt; }
|
||||||
|
#else
|
||||||
bool Hit( void ) const { return m_bHit; }
|
bool Hit( void ) const { return m_bHit; }
|
||||||
|
#endif
|
||||||
|
|
||||||
private:
|
private:
|
||||||
Ray_t m_rayShot;
|
Ray_t m_rayShot;
|
||||||
int m_iDamageType;
|
int m_iDamageType;
|
||||||
|
#ifdef MAPBASE
|
||||||
|
C_BaseAnimating *m_pHitEnt;
|
||||||
|
#else
|
||||||
bool m_bHit;
|
bool m_bHit;
|
||||||
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // FX_IMPACT_H
|
#endif // FX_IMPACT_H
|
||||||
|
Loading…
x
Reference in New Issue
Block a user