|
|
|
@ -22,12 +22,14 @@
@@ -22,12 +22,14 @@
|
|
|
|
|
#include "cbase.h" |
|
|
|
|
#include "monsters.h" |
|
|
|
|
#include "saverestore.h" |
|
|
|
|
#include "locus.h" |
|
|
|
|
|
|
|
|
|
// Monstermaker spawnflags
|
|
|
|
|
#define SF_MONSTERMAKER_START_ON 1 // start active ( if has targetname )
|
|
|
|
|
#define SF_MONSTERMAKER_CYCLIC 4 // drop one monster every time fired.
|
|
|
|
|
#define SF_MONSTERMAKER_MONSTERCLIP 8 // Children are blocked by monsterclip
|
|
|
|
|
#define SF_MONSTERMAKER_LEAVECORPSE 16 // Don't fade corpses.
|
|
|
|
|
#define SF_MONSTERMAKER_FORCESPAWN 32 // AJH Force the monstermaker to spawn regardless of blocking enitites
|
|
|
|
|
#define SF_MONSTERMAKER_NO_WPN_DROP 1024 // Corpses don't drop weapons.
|
|
|
|
|
|
|
|
|
|
//=========================================================
|
|
|
|
@ -125,16 +127,17 @@ void CMonsterMaker::Spawn()
@@ -125,16 +127,17 @@ void CMonsterMaker::Spawn()
|
|
|
|
|
{ |
|
|
|
|
SetUse(&CMonsterMaker :: ToggleUse );// can be turned on/off
|
|
|
|
|
|
|
|
|
|
if( FBitSet( pev->spawnflags, SF_MONSTERMAKER_START_ON ) ) |
|
|
|
|
{ |
|
|
|
|
// start making monsters as soon as monstermaker spawns
|
|
|
|
|
m_fActive = TRUE; |
|
|
|
|
SetThink( &CMonsterMaker::MakerThink ); |
|
|
|
|
} |
|
|
|
|
else |
|
|
|
|
{ |
|
|
|
|
// wait to be activated.
|
|
|
|
|
m_fActive = FALSE; |
|
|
|
|
if( FBitSet( pev->spawnflags, SF_MONSTERMAKER_START_ON ) ) |
|
|
|
|
{ |
|
|
|
|
// start making monsters as soon as monstermaker spawns
|
|
|
|
|
m_fActive = TRUE; |
|
|
|
|
SetThink( &CMonsterMaker::MakerThink ); |
|
|
|
|
SetNextThink(0);//AJH How come this needs to be here all of a sudden?
|
|
|
|
|
} |
|
|
|
|
else |
|
|
|
|
{ |
|
|
|
|
// wait to be activated.
|
|
|
|
|
m_fActive = FALSE; |
|
|
|
|
SetThink(&CMonsterMaker :: SUB_DoNothing ); |
|
|
|
|
} |
|
|
|
|
} |
|
|
|
@ -176,23 +179,70 @@ void CMonsterMaker::TryMakeMonster( void )
@@ -176,23 +179,70 @@ void CMonsterMaker::TryMakeMonster( void )
|
|
|
|
|
return; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
CBaseEntity* pTemp; |
|
|
|
|
if (pev->noise) |
|
|
|
|
{ // AJH dynamic origin for monstermakers
|
|
|
|
|
pTemp = UTIL_FindEntityByTargetname(NULL,STRING(pev->noise),this); |
|
|
|
|
if (pTemp) |
|
|
|
|
{ |
|
|
|
|
pev->vuser1 = pTemp->pev->origin; |
|
|
|
|
// ALERT(at_console,"DEBUG: Monstermaker setting dynamic position %f %f %f \n", pWhere->pev->origin.x,pWhere->pev->origin.y,pWhere->pev->origin.z);
|
|
|
|
|
} |
|
|
|
|
} |
|
|
|
|
else |
|
|
|
|
{ |
|
|
|
|
pev->vuser1=pev->origin; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if (pev->noise1) |
|
|
|
|
{ |
|
|
|
|
//AJH dynamic offset for monstermaker
|
|
|
|
|
Vector vTemp =CalcLocus_Position(this, NULL, STRING(pev->noise1)); |
|
|
|
|
pev->vuser1 = pev->vuser1 + vTemp; |
|
|
|
|
//ALERT(at_console,"DEBUG: Monstermaker dynamic offset is %f %f %f\n",vTemp.x,vTemp.y,vTemp.z);
|
|
|
|
|
//ALERT(at_console,"DEBUG: Monstermaker position now %f %f %f \n", pWhere->pev->origin.x,pWhere->pev->origin.y,pWhere->pev->origin.z);
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if (pev->noise2) |
|
|
|
|
{ |
|
|
|
|
// AJH dynamic angles for monstermakers
|
|
|
|
|
pTemp = UTIL_FindEntityByTargetname(NULL,STRING(pev->noise2),this); |
|
|
|
|
if (pTemp) pev->vuser2=pTemp->pev->angles; |
|
|
|
|
// ALERT(at_console,"DEBUG: Monstermaker setting angles to %f %f %f\n",pWhere->pev->angles.x,pWhere->pev->angles.y,pWhere->pev->angles.z);
|
|
|
|
|
} |
|
|
|
|
else |
|
|
|
|
{ |
|
|
|
|
pev->vuser2=pev->angles; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if (pev->noise3) |
|
|
|
|
{ // AJH dynamic velocity for monstermakers
|
|
|
|
|
pTemp = UTIL_FindEntityByTargetname(NULL,STRING(pev->noise3),this); |
|
|
|
|
if (pTemp) |
|
|
|
|
pev->vuser3 = pTemp->pev->velocity; |
|
|
|
|
//ALERT(at_console,"DEBUG: Monstermaker setting velocity to %f %f %f\n",pWhere->pev->velocity.x,pWhere->pev->velocity.y,pWhere->pev->velocity.z);
|
|
|
|
|
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
//ALERT(at_console,"DEBUG: Montermaker spawnpoint set to %f, %f, %f\n", pWhere->pev->origin.x,pWhere->pev->origin.y,pWhere->pev->origin.z);
|
|
|
|
|
|
|
|
|
|
if( !m_flGround ) |
|
|
|
|
{ |
|
|
|
|
// set altitude. Now that I'm activated, any breakables, etc should be out from under me.
|
|
|
|
|
TraceResult tr; |
|
|
|
|
|
|
|
|
|
UTIL_TraceLine( pev->origin, pev->origin - Vector( 0, 0, 2048 ), ignore_monsters, ENT( pev ), &tr ); |
|
|
|
|
UTIL_TraceLine( pev->vuser1, pev->vuser1 - Vector( 0, 0, 2048 ), ignore_monsters, ENT(pev), &tr ); |
|
|
|
|
m_flGround = tr.vecEndPos.z; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
Vector mins = pev->origin - Vector( 34, 34, 0 ); |
|
|
|
|
Vector maxs = pev->origin + Vector( 34, 34, 0 ); |
|
|
|
|
maxs.z = pev->origin.z; |
|
|
|
|
Vector mins = pev->vuser1 - Vector( 34, 34, 0 ); |
|
|
|
|
Vector maxs = pev->vuser1 + Vector( 34, 34, 0 ); |
|
|
|
|
maxs.z = pev->vuser1.z; |
|
|
|
|
mins.z = m_flGround; |
|
|
|
|
|
|
|
|
|
CBaseEntity *pList[2]; |
|
|
|
|
int count = UTIL_EntitiesInBox( pList, 2, mins, maxs, FL_CLIENT | FL_MONSTER ); |
|
|
|
|
if( count ) |
|
|
|
|
if( !FBitSet( pev->spawnflags, SF_MONSTERMAKER_FORCESPAWN ) && count ) |
|
|
|
|
{ |
|
|
|
|
// don't build a stack of monsters!
|
|
|
|
|
return; |
|
|
|
@ -203,6 +253,8 @@ void CMonsterMaker::TryMakeMonster( void )
@@ -203,6 +253,8 @@ void CMonsterMaker::TryMakeMonster( void )
|
|
|
|
|
// If I have a target, fire. (no locus)
|
|
|
|
|
if ( !FStringNull ( pev->target ) ) |
|
|
|
|
{ |
|
|
|
|
ALERT( at_console, "DEBUG: Monstermaker fires target %s locus is child\n", STRING( pev->target ) ); |
|
|
|
|
|
|
|
|
|
// delay already overloaded for this entity, so can't call SUB_UseTargets()
|
|
|
|
|
FireTargets( STRING(pev->target), this, this, USE_TOGGLE, 0 ); |
|
|
|
|
} |
|
|
|
@ -251,8 +303,9 @@ CBaseMonster* CMonsterMaker::MakeMonster( void )
@@ -251,8 +303,9 @@ CBaseMonster* CMonsterMaker::MakeMonster( void )
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
pevCreate = VARS( pent ); |
|
|
|
|
pevCreate->origin = pev->origin; |
|
|
|
|
pevCreate->angles = pev->angles; |
|
|
|
|
pevCreate->origin = pev->vuser1; //AJH dynamic (*locus) position
|
|
|
|
|
pevCreate->angles = pev->vuser2; |
|
|
|
|
pevCreate->velocity = pev->vuser3; |
|
|
|
|
SetBits( pevCreate->spawnflags, SF_MONSTER_FALL_TO_GROUND ); |
|
|
|
|
|
|
|
|
|
if (pev->spawnflags & SF_MONSTERMAKER_NO_WPN_DROP) |
|
|
|
@ -272,6 +325,8 @@ CBaseMonster* CMonsterMaker::MakeMonster( void )
@@ -272,6 +325,8 @@ CBaseMonster* CMonsterMaker::MakeMonster( void )
|
|
|
|
|
{ |
|
|
|
|
pMonst->m_iClass = this->m_iClass; |
|
|
|
|
pMonst->m_iPlayerReact = this->m_iPlayerReact; |
|
|
|
|
pMonst->m_iTriggerCondition = this->m_iTriggerCondition; //AJH
|
|
|
|
|
pMonst->m_iszTriggerTarget = this->m_iszTriggerTarget; //AJH
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if( !FStringNull( pev->netname ) ) |
|
|
|
@ -304,6 +359,13 @@ CBaseMonster* CMonsterMaker::MakeMonster( void )
@@ -304,6 +359,13 @@ CBaseMonster* CMonsterMaker::MakeMonster( void )
|
|
|
|
|
//=========================================================
|
|
|
|
|
void CMonsterMaker::CyclicUse( CBaseEntity *pActivator, CBaseEntity *pCaller, USE_TYPE useType, float value ) |
|
|
|
|
{ |
|
|
|
|
if( pActivator ) |
|
|
|
|
{ |
|
|
|
|
pev->vuser1 = pActivator->pev->origin; //AJH for *locus position etc
|
|
|
|
|
pev->vuser2 = pActivator->pev->angles; |
|
|
|
|
pev->vuser3 = pActivator->pev->velocity; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
TryMakeMonster(); |
|
|
|
|
// ALERT(at_console,"CyclicUse complete\n");
|
|
|
|
|
} |
|
|
|
@ -313,6 +375,13 @@ void CMonsterMaker::CyclicUse( CBaseEntity *pActivator, CBaseEntity *pCaller, US
@@ -313,6 +375,13 @@ void CMonsterMaker::CyclicUse( CBaseEntity *pActivator, CBaseEntity *pCaller, US
|
|
|
|
|
//=========================================================
|
|
|
|
|
void CMonsterMaker::ToggleUse( CBaseEntity *pActivator, CBaseEntity *pCaller, USE_TYPE useType, float value ) |
|
|
|
|
{ |
|
|
|
|
if( pActivator ) |
|
|
|
|
{ |
|
|
|
|
pev->vuser1 = pActivator->pev->origin; //AJH for *locus position etc
|
|
|
|
|
pev->vuser2 = pActivator->pev->angles; |
|
|
|
|
pev->vuser3 = pActivator->pev->velocity; |
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
if( !ShouldToggle( useType, m_fActive ) ) |
|
|
|
|
return; |
|
|
|
|
|
|
|
|
|