codemp/game/g_items.c File Reference

#include "g_local.h"
#include "../ghoul2/G2.h"
#include "q_shared.h"
#include "../namespace_begin.h"
#include "../namespace_end.h"

Go to the source code of this file.

Defines

#define RESPAWN_ARMOR   20
#define RESPAWN_TEAM_WEAPON   30
#define RESPAWN_HEALTH   30
#define RESPAWN_AMMO   40
#define RESPAWN_HOLDABLE   60
#define RESPAWN_MEGAHEALTH   120
#define RESPAWN_POWERUP   120
#define ITMSF_SUSPEND   1
#define ITMSF_NOPLAYER   2
#define ITMSF_ALLOWNPC   4
#define ITMSF_NOTSOLID   8
#define ITMSF_VERTICAL   16
#define ITMSF_INVISIBLE   32
#define MAX_MEDPACK_HEAL_AMOUNT   25
#define MAX_MEDPACK_BIG_HEAL_AMOUNT   50
#define MAX_SENTRY_DISTANCE   256
#define SHIELD_HEALTH   250
#define SHIELD_HEALTH_DEC   10
#define MAX_SHIELD_HEIGHT   254
#define MAX_SHIELD_HALFWIDTH   255
#define SHIELD_HALFTHICKNESS   4
#define SHIELD_PLACEDIST   64
#define SHIELD_SIEGE_HEALTH   2000
#define SHIELD_SIEGE_HEALTH_DEC   (SHIELD_SIEGE_HEALTH/25)
#define PAS_DAMAGE   2
#define TURRET_RADIUS   800
#define TURRET_DEATH_DELAY   2000
#define TURRET_LIFETIME   60000
#define TURRET_AMMO_COUNT   40
#define JETPACK_TOGGLE_TIME   1000
#define CLOAK_TOGGLE_TIME   1000
#define TOSSED_ITEM_STAY_PERIOD   20000
#define TOSSED_ITEM_OWNER_NOTOUCH_DUR   1000
#define DISP_HEALTH_ITEM   "item_medpak_instant"
#define DISP_AMMO_ITEM   "ammo_all"
#define EWEB_DEATH_RADIUS   128
#define EWEB_DEATH_DMG   90
#define EWEB_MISSILE_DAMAGE   20
#define EWEB_HEALTH   200
#define EWEB_USE_DEBOUNCE   1000

Functions

int adjustRespawnTime (float preRespawnTime, int itemType, int itemTag)
void ShieldRemove (gentity_t *self)
void ShieldThink (gentity_t *self)
void ShieldDie (gentity_t *self, gentity_t *inflictor, gentity_t *attacker, int damage, int mod)
void ShieldPain (gentity_t *self, gentity_t *attacker, int damage)
void ShieldGoSolid (gentity_t *self)
void ShieldGoNotSolid (gentity_t *self)
void ShieldTouch (gentity_t *self, gentity_t *other, trace_t *trace)
void CreateShield (gentity_t *ent)
qboolean PlaceShield (gentity_t *playerent)
void ItemUse_Binoculars (gentity_t *ent)
void ItemUse_Shield (gentity_t *ent)
void SentryTouch (gentity_t *ent, gentity_t *other, trace_t *trace)
void pas_fire (gentity_t *ent)
void pas_adjust_enemy (gentity_t *ent)
void turret_die (gentity_t *self, gentity_t *inflictor, gentity_t *attacker, int damage, int mod)
void sentryExpire (gentity_t *self)
void pas_think (gentity_t *ent)
void SP_PAS (gentity_t *base)
void ItemUse_Sentry (gentity_t *ent)
gentity_tNPC_SpawnType (gentity_t *ent, char *npc_type, char *targetname, qboolean isVehicle)
void ItemUse_Seeker (gentity_t *ent)
void ItemUse_MedPack_Big (gentity_t *ent)
void ItemUse_MedPack (gentity_t *ent)
void Jetpack_Off (gentity_t *ent)
void Jetpack_On (gentity_t *ent)
void ItemUse_Jetpack (gentity_t *ent)
void Jedi_Cloak (gentity_t *self)
void Jedi_Decloak (gentity_t *self)
void ItemUse_UseCloak (gentity_t *ent)
void SpecialItemThink (gentity_t *ent)
void G_SpecialSpawnItem (gentity_t *ent, gitem_t *item)
void G_PrecacheDispensers (void)
void ItemUse_UseDisp (gentity_t *ent, int type)
void EWebDisattach (gentity_t *owner, gentity_t *eweb)
void EWebPrecache (void)
void BG_CycleInven (playerState_t *ps, int direction)
void EWebDie (gentity_t *self, gentity_t *inflictor, gentity_t *attacker, int damage, int mod)
void EWebPain (gentity_t *self, gentity_t *attacker, int damage)
void EWeb_SetBoneAngles (gentity_t *ent, char *bone, vec3_t angles)
void EWeb_SetBoneAnim (gentity_t *eweb, int startFrame, int endFrame)
void EWebFire (gentity_t *owner, gentity_t *eweb)
void EWebPositionUser (gentity_t *owner, gentity_t *eweb)
void EWebUpdateBoneAngles (gentity_t *owner, gentity_t *eweb)
int BG_EmplacedView (vec3_t baseAngles, vec3_t angles, float *newYaw, float constraint)
void EWebThink (gentity_t *self)
gentity_tEWeb_Create (gentity_t *spawner)
void ItemUse_UseEWeb (gentity_t *ent)
int Pickup_Powerup (gentity_t *ent, gentity_t *other)
int Pickup_Holdable (gentity_t *ent, gentity_t *other)
void Add_Ammo (gentity_t *ent, int weapon, int count)
int Pickup_Ammo (gentity_t *ent, gentity_t *other)
int Pickup_Weapon (gentity_t *ent, gentity_t *other)
int Pickup_Health (gentity_t *ent, gentity_t *other)
int Pickup_Armor (gentity_t *ent, gentity_t *other)
void RespawnItem (gentity_t *ent)
qboolean CheckItemCanBePickedUpByNPC (gentity_t *item, gentity_t *pickerupper)
void Touch_Item (gentity_t *ent, gentity_t *other, trace_t *trace)
gentity_tLaunchItem (gitem_t *item, vec3_t origin, vec3_t velocity)
gentity_tDrop_Item (gentity_t *ent, gitem_t *item, float angle)
void Use_Item (gentity_t *ent, gentity_t *other, gentity_t *activator)
void FinishSpawningItem (gentity_t *ent)
void G_CheckTeamItems (void)
void ClearRegisteredItems (void)
void RegisterItem (gitem_t *item)
void SaveRegisteredItems (void)
int G_ItemDisabled (gitem_t *item)
void G_SpawnItem (gentity_t *ent, gitem_t *item)
void G_BounceItem (gentity_t *ent, trace_t *trace)
void G_RunItem (gentity_t *ent)

Variables

gentity_tdroppedRedFlag
gentity_tdroppedBlueFlag
qboolean itemRegistered [MAX_ITEMS]


Define Documentation

#define CLOAK_TOGGLE_TIME   1000
 

Definition at line 1236 of file g_items.c.

Referenced by ItemUse_UseCloak().

#define DISP_AMMO_ITEM   "ammo_all"
 

Definition at line 1334 of file g_items.c.

Referenced by G_PrecacheDispensers(), and ItemUse_UseDisp().

#define DISP_HEALTH_ITEM   "item_medpak_instant"
 

Definition at line 1333 of file g_items.c.

Referenced by G_PrecacheDispensers(), and ItemUse_UseDisp().

#define EWEB_DEATH_DMG   90
 

Definition at line 1443 of file g_items.c.

Referenced by EWebDie().

#define EWEB_DEATH_RADIUS   128
 

Definition at line 1442 of file g_items.c.

Referenced by EWebDie().

#define EWEB_HEALTH   200
 

Definition at line 1856 of file g_items.c.

Referenced by EWeb_Create().

#define EWEB_MISSILE_DAMAGE   20
 

Definition at line 1623 of file g_items.c.

Referenced by EWebFire().

#define EWEB_USE_DEBOUNCE   1000
 

Definition at line 1982 of file g_items.c.

Referenced by ItemUse_UseEWeb().

#define ITMSF_ALLOWNPC   4
 

Definition at line 32 of file g_items.c.

Referenced by Touch_Item().

#define ITMSF_INVISIBLE   32
 

Definition at line 35 of file g_items.c.

#define ITMSF_NOPLAYER   2
 

Definition at line 31 of file g_items.c.

#define ITMSF_NOTSOLID   8
 

Definition at line 33 of file g_items.c.

#define ITMSF_SUSPEND   1
 

Definition at line 30 of file g_items.c.

Referenced by FinishSpawningItem().

#define ITMSF_VERTICAL   16
 

Definition at line 34 of file g_items.c.

#define JETPACK_TOGGLE_TIME   1000
 

Definition at line 1164 of file g_items.c.

Referenced by ItemUse_Jetpack().

#define MAX_MEDPACK_BIG_HEAL_AMOUNT   50
 

Definition at line 43 of file g_items.c.

Referenced by ItemUse_MedPack_Big().

#define MAX_MEDPACK_HEAL_AMOUNT   25
 

Definition at line 42 of file g_items.c.

Referenced by ItemUse_MedPack().

#define MAX_SENTRY_DISTANCE   256
 

Definition at line 44 of file g_items.c.

#define MAX_SHIELD_HALFWIDTH   255
 

Definition at line 94 of file g_items.c.

Referenced by CreateShield().

#define MAX_SHIELD_HEIGHT   254
 

Definition at line 93 of file g_items.c.

Referenced by CreateShield().

#define PAS_DAMAGE   2
 

Definition at line 513 of file g_items.c.

#define RESPAWN_AMMO   40
 

Definition at line 24 of file g_items.c.

Referenced by adjustRespawnTime(), and Pickup_Ammo().

#define RESPAWN_ARMOR   20
 

Definition at line 21 of file g_items.c.

Referenced by Pickup_Armor().

#define RESPAWN_HEALTH   30
 

Definition at line 23 of file g_items.c.

Referenced by Pickup_Health().

#define RESPAWN_HOLDABLE   60
 

Definition at line 25 of file g_items.c.

Referenced by Pickup_Holdable().

#define RESPAWN_MEGAHEALTH   120
 

Definition at line 26 of file g_items.c.

Referenced by Pickup_Health().

#define RESPAWN_POWERUP   120
 

Definition at line 27 of file g_items.c.

Referenced by Pickup_Powerup().

#define RESPAWN_TEAM_WEAPON   30
 

Definition at line 22 of file g_items.c.

Referenced by Pickup_Weapon().

#define SHIELD_HALFTHICKNESS   4
 

Definition at line 95 of file g_items.c.

Referenced by CreateShield().

#define SHIELD_HEALTH   250
 

Definition at line 91 of file g_items.c.

Referenced by CreateShield().

#define SHIELD_HEALTH_DEC   10
 

Definition at line 92 of file g_items.c.

Referenced by ShieldThink().

#define SHIELD_PLACEDIST   64
 

Definition at line 96 of file g_items.c.

Referenced by PlaceShield().

#define SHIELD_SIEGE_HEALTH   2000
 

Definition at line 98 of file g_items.c.

Referenced by CreateShield().

#define SHIELD_SIEGE_HEALTH_DEC   (SHIELD_SIEGE_HEALTH/25)
 

Definition at line 99 of file g_items.c.

Referenced by ShieldThink().

#define TOSSED_ITEM_OWNER_NOTOUCH_DUR   1000
 

Definition at line 1275 of file g_items.c.

Referenced by G_SpecialSpawnItem().

#define TOSSED_ITEM_STAY_PERIOD   20000
 

Definition at line 1274 of file g_items.c.

Referenced by G_SpecialSpawnItem().

#define TURRET_AMMO_COUNT   40
 

Definition at line 975 of file g_items.c.

Referenced by SP_PAS().

#define TURRET_DEATH_DELAY   2000
 

Definition at line 697 of file g_items.c.

Referenced by pas_think().

#define TURRET_LIFETIME   60000
 

Definition at line 698 of file g_items.c.

Referenced by pas_think().

#define TURRET_RADIUS   800
 

Definition at line 544 of file g_items.c.


Function Documentation

void Add_Ammo gentity_t ent,
int  weapon,
int  count
 

Definition at line 2118 of file g_items.c.

References playerState_s::ammo, ammoData, gentity_s::client, gentity_t, ammoData_s::max, and gclient_s::ps.

Referenced by Pickup_Ammo(), Pickup_Weapon(), and WeaponThink().

02119 {
02120         if ( ent->client->ps.ammo[weapon] < ammoData[weapon].max )
02121         {
02122                 ent->client->ps.ammo[weapon] += count;
02123                 if ( ent->client->ps.ammo[weapon] > ammoData[weapon].max )
02124                 {
02125                         ent->client->ps.ammo[weapon] = ammoData[weapon].max;
02126                 }
02127         }
02128 }

int adjustRespawnTime float  preRespawnTime,
int  itemType,
int  itemTag
 

Definition at line 47 of file g_items.c.

References g_adaptRespawn, vmCvar_t::integer, IT_WEAPON, level, level_locals_t::numPlayingClients, RESPAWN_AMMO, WP_DET_PACK, WP_THERMAL, and WP_TRIP_MINE.

Referenced by Pickup_Ammo(), Pickup_Armor(), Pickup_Health(), Pickup_Holdable(), and Pickup_Weapon().

00048 {
00049         float respawnTime = preRespawnTime;
00050 
00051         if (itemType == IT_WEAPON)
00052         {
00053                 if (itemTag == WP_THERMAL ||
00054                         itemTag == WP_TRIP_MINE ||
00055                         itemTag == WP_DET_PACK)
00056                 { //special case for these, use ammo respawn rate
00057                         respawnTime = RESPAWN_AMMO;
00058                 }
00059         }
00060 
00061         if (!g_adaptRespawn.integer)
00062         {
00063                 return((int)respawnTime);
00064         }
00065 
00066         if (level.numPlayingClients > 4)
00067         {       // Start scaling the respawn times.
00068                 if (level.numPlayingClients > 32)
00069                 {       // 1/4 time minimum.
00070                         respawnTime *= 0.25;
00071                 }
00072                 else if (level.numPlayingClients > 12)
00073                 {       // From 12-32, scale from 0.5 to 0.25;
00074                         respawnTime *= 20.0 / (float)(level.numPlayingClients + 8);
00075                 }
00076                 else 
00077                 {       // From 4-12, scale from 1.0 to 0.5;
00078                         respawnTime *= 8.0 / (float)(level.numPlayingClients + 4);
00079                 }
00080         }
00081 
00082         if (respawnTime < 1.0)
00083         {       // No matter what, don't go lower than 1 second, or the pickups become very noisy!
00084                 respawnTime = 1.0;
00085         }
00086 
00087         return ((int)respawnTime);
00088 }

void BG_CycleInven playerState_t ps,
int  direction
 

Definition at line 2121 of file bg_misc.c.

References BG_GetItemIndexByTag(), BG_IsItemSelectable(), bg_itemlist, HI_NUM_HOLDABLE, IT_HOLDABLE, playerState_t, STAT_HOLDABLE_ITEM, STAT_HOLDABLE_ITEMS, and playerState_s::stats.

Referenced by CG_NextInventory_f(), CG_PrevInventory_f(), and EWebDie().

02122 {
02123         int i;
02124         int dontFreeze = 0;
02125         int original;
02126 
02127         i = bg_itemlist[ps->stats[STAT_HOLDABLE_ITEM]].giTag;
02128         original = i;
02129 
02130         if (direction == 1)
02131         { //next
02132                 i++;
02133                 if (i == HI_NUM_HOLDABLE)
02134                 {
02135                         i = 1;
02136                 }
02137         }
02138         else
02139         { //previous
02140                 i--;
02141                 if (i == 0)
02142                 {
02143                         i = HI_NUM_HOLDABLE-1;
02144                 }
02145         }
02146 
02147         while (i != original)
02148         { //go in a full loop until hitting something, if hit nothing then select nothing
02149                 if (ps->stats[STAT_HOLDABLE_ITEMS] & (1 << i))
02150                 { //we have it, select it.
02151                         if (BG_IsItemSelectable(ps, i))
02152                         {
02153                                 ps->stats[STAT_HOLDABLE_ITEM] = BG_GetItemIndexByTag(i, IT_HOLDABLE);
02154                                 break;
02155                         }
02156                 }
02157 
02158                 if (direction == 1)
02159                 { //next
02160                         i++;
02161                 }
02162                 else
02163                 { //previous
02164                         i--;
02165                 }
02166 
02167                 if (i <= 0)
02168                 { //wrap around to the last
02169                         i = HI_NUM_HOLDABLE-1;
02170                 }
02171                 else if (i >= HI_NUM_HOLDABLE)
02172                 { //wrap around to the first
02173                         i = 1;
02174                 }
02175 
02176                 dontFreeze++;
02177                 if (dontFreeze >= 32)
02178                 { //yeah, sure, whatever (it's 2 am and I'm paranoid and can't frickin think)
02179                         break;
02180                 }
02181         }
02182 }

int BG_EmplacedView vec3_t  baseAngles,
vec3_t  angles,
float *  newYaw,
float  constraint
 

Definition at line 2703 of file bg_misc.c.

02704 {
02705         float dif = AngleSubtract(baseAngles[YAW], angles[YAW]);
02706 
02707         if (dif > constraint ||
02708                 dif < -constraint)
02709         {
02710                 float amt;
02711 
02712                 if (dif > constraint)
02713                 {
02714                         amt = (dif-constraint);
02715                         dif = constraint;
02716                 }
02717                 else if (dif < -constraint)
02718                 {
02719                         amt = (dif+constraint);
02720                         dif = -constraint;
02721                 }
02722                 else
02723                 {
02724                         amt = 0.0f;
02725                 }
02726 
02727                 *newYaw = AngleSubtract(angles[YAW], -dif);
02728 
02729                 if (amt > 1.0f || amt < -1.0f)
02730                 { //significant, force the view
02731                         return 2;
02732                 }
02733                 else
02734                 { //just a little out of range
02735                         return 1;
02736                 }
02737         }
02738 
02739         return 0;
02740 }

qboolean CheckItemCanBePickedUpByNPC gentity_t item,
gentity_t pickerupper
 

Definition at line 2336 of file g_items.c.

References gentity_s::activator, gentity_s::enemy, FL_DROPPED_ITEM, gentity_s::flags, g_entities, gentity_t, level, gentity_s::NPC, entityState_s::number, gentity_s::painDebounceTime, qboolean, qfalse, qtrue, gentity_s::s, SCF_FORCED_MARCH, gNPC_t::scriptFlags, gNPC_t::surrenderTime, level_locals_t::time, entityState_s::time, entityState_s::weapon, and WP_NONE.

Referenced by NPC_SearchForWeapons(), and Touch_Item().

02337 {
02338         if ( (item->flags&FL_DROPPED_ITEM) 
02339                 && item->activator != &g_entities[0] 
02340                 && pickerupper->s.number 
02341                 && pickerupper->s.weapon == WP_NONE 
02342                 && pickerupper->enemy 
02343                 && pickerupper->painDebounceTime < level.time
02344                 && pickerupper->NPC && pickerupper->NPC->surrenderTime < level.time //not surrendering
02345                 && !(pickerupper->NPC->scriptFlags&SCF_FORCED_MARCH) //not being forced to march
02346                 /*&& item->item->giTag != INV_SECURITY_KEY*/ )
02347         {//non-player, in combat, picking up a dropped item that does NOT belong to the player and it *not* a security key
02348                 if ( level.time - item->s.time < 3000 )//was 5000
02349                 {
02350                         return qfalse;
02351                 }
02352                 return qtrue;
02353         }
02354         return qfalse;
02355 }

void ClearRegisteredItems void   ) 
 

Definition at line 2998 of file g_items.c.

References BG_FindItemForWeapon(), g_gametype, G_PrecacheDispensers(), GT_SIEGE, vmCvar_t::integer, itemRegistered, memset(), RegisterItem(), WP_BRYAR_PISTOL, WP_MELEE, WP_SABER, and WP_STUN_BATON.

Referenced by G_InitGame().

02998                                   {
02999         memset( itemRegistered, 0, sizeof( itemRegistered ) );
03000 
03001         // players always start with the base weapon
03002         RegisterItem( BG_FindItemForWeapon( WP_BRYAR_PISTOL ) );
03003         RegisterItem( BG_FindItemForWeapon( WP_STUN_BATON ) );
03004         RegisterItem( BG_FindItemForWeapon( WP_MELEE ) );
03005         RegisterItem( BG_FindItemForWeapon( WP_SABER ) );
03006 
03007         if (g_gametype.integer == GT_SIEGE)
03008         { //kind of cheesy, maybe check if siege class with disp's is gonna be on this map too
03009                 G_PrecacheDispensers();
03010         }
03011 }

void CreateShield gentity_t ent  ) 
 

Definition at line 254 of file g_items.c.

References entityState_s::angles, ceil(), gentity_s::clipmask, entityShared_t::contents, CONTENTS_BODY, CONTENTS_PLAYERCLIP, CONTENTS_SHOTCLIP, entityShared_t::currentOrigin, gentity_s::die, EF_NODRAW, entityState_s::eFlags, EV_GENERAL_SOUND, trace_t::fraction, G_AddEvent(), g_gametype, gentity_t, GT_SIEGE, gentity_s::health, vmCvar_t::integer, level, entityState_s::loopIsSoundset, entityState_s::loopSound, MASK_SHOT, MAX_SHIELD_HALFWIDTH, MAX_SHIELD_HEIGHT, entityShared_t::maxs, entityShared_t::mins, gentity_s::nextthink, NULL, entityState_s::number, gentity_s::pain, qboolean, qfalse, qtrue, gentity_s::r, gentity_s::s, SHIELD_HALFTHICKNESS, SHIELD_HEALTH, SHIELD_SIEGE_HEALTH, ShieldDie(), ShieldGoSolid(), ShieldPain(), ShieldThink(), ShieldTouch(), trace_t::startsolid, gentity_s::takedamage, gentity_s::think, level_locals_t::time, entityState_s::time, entityState_s::time2, gentity_s::touch, trap_LinkEntity(), trap_Trace(), vec3_t, VectorCopy, VectorSet, and YAW.

Referenced by PlaceShield().

00255 {
00256         trace_t         tr;
00257         vec3_t          mins, maxs, end, posTraceEnd, negTraceEnd, start;
00258         int                     height, posWidth, negWidth, halfWidth = 0;
00259         qboolean        xaxis;
00260         int                     paramData = 0;
00261         static int      shieldID;
00262 
00263         // trace upward to find height of shield
00264         VectorCopy(ent->r.currentOrigin, end);
00265         end[2] += MAX_SHIELD_HEIGHT;
00266         trap_Trace (&tr, ent->r.currentOrigin, NULL, NULL, end, ent->s.number, MASK_SHOT );
00267         height = (int)(MAX_SHIELD_HEIGHT * tr.fraction);
00268 
00269         // use angles to find the proper axis along which to align the shield
00270         VectorSet(mins, -SHIELD_HALFTHICKNESS, -SHIELD_HALFTHICKNESS, 0);
00271         VectorSet(maxs, SHIELD_HALFTHICKNESS, SHIELD_HALFTHICKNESS, height);
00272         VectorCopy(ent->r.currentOrigin, posTraceEnd);
00273         VectorCopy(ent->r.currentOrigin, negTraceEnd);
00274 
00275         if ((int)(ent->s.angles[YAW]) == 0) // shield runs along y-axis
00276         {
00277                 posTraceEnd[1]+=MAX_SHIELD_HALFWIDTH;
00278                 negTraceEnd[1]-=MAX_SHIELD_HALFWIDTH;
00279                 xaxis = qfalse;
00280         }
00281         else  // shield runs along x-axis
00282         {
00283                 posTraceEnd[0]+=MAX_SHIELD_HALFWIDTH;
00284                 negTraceEnd[0]-=MAX_SHIELD_HALFWIDTH;
00285                 xaxis = qtrue;
00286         }
00287 
00288         // trace horizontally to find extend of shield
00289         // positive trace
00290         VectorCopy(ent->r.currentOrigin, start);
00291         start[2] += (height>>1);
00292         trap_Trace (&tr, start, 0, 0, posTraceEnd, ent->s.number, MASK_SHOT );
00293         posWidth = MAX_SHIELD_HALFWIDTH * tr.fraction;
00294         // negative trace
00295         trap_Trace (&tr, start, 0, 0, negTraceEnd, ent->s.number, MASK_SHOT );
00296         negWidth = MAX_SHIELD_HALFWIDTH * tr.fraction;
00297 
00298         // kef -- monkey with dimensions and place origin in center
00299         halfWidth = (posWidth + negWidth)>>1;
00300         if (xaxis)
00301         {
00302                 ent->r.currentOrigin[0] = ent->r.currentOrigin[0] - negWidth + halfWidth;
00303         }
00304         else
00305         {
00306                 ent->r.currentOrigin[1] = ent->r.currentOrigin[1] - negWidth + halfWidth;
00307         }
00308         ent->r.currentOrigin[2] += (height>>1);
00309 
00310         // set entity's mins and maxs to new values, make it solid, and link it
00311         if (xaxis)
00312         {
00313                 VectorSet(ent->r.mins, -halfWidth, -SHIELD_HALFTHICKNESS, -(height>>1));
00314                 VectorSet(ent->r.maxs, halfWidth, SHIELD_HALFTHICKNESS, height>>1);
00315         }
00316         else
00317         {
00318                 VectorSet(ent->r.mins, -SHIELD_HALFTHICKNESS, -halfWidth, -(height>>1));
00319                 VectorSet(ent->r.maxs, SHIELD_HALFTHICKNESS, halfWidth, height);
00320         }
00321         ent->clipmask = MASK_SHOT;
00322 
00323         // Information for shield rendering.
00324 
00325 //      xaxis - 1 bit
00326 //      height - 0-254 8 bits
00327 //      posWidth - 0-255 8 bits
00328 //  negWidth - 0 - 255 8 bits
00329 
00330         paramData = (xaxis << 24) | (height << 16) | (posWidth << 8) | (negWidth);
00331         ent->s.time2 = paramData;
00332 
00333         if ( g_gametype.integer == GT_SIEGE )
00334         {
00335                 ent->health = ceil((float)(SHIELD_SIEGE_HEALTH*1));
00336         }
00337         else
00338         {
00339                 ent->health = ceil((float)(SHIELD_HEALTH*1));
00340         }
00341 
00342         ent->s.time = ent->health;//???
00343         ent->pain = ShieldPain;
00344         ent->die = ShieldDie;
00345         ent->touch = ShieldTouch;
00346 
00347         // see if we're valid
00348         trap_Trace (&tr, ent->r.currentOrigin, ent->r.mins, ent->r.maxs, ent->r.currentOrigin, ent->s.number, CONTENTS_BODY ); 
00349 
00350         if (tr.startsolid)
00351         {       // Something in the way!
00352                 // make the shield non-solid very briefly
00353                 ent->r.contents = 0;
00354                 ent->s.eFlags |= EF_NODRAW;
00355                 // nextthink needs to have a large enough interval to avoid excess accumulation of Activate messages
00356                 ent->nextthink = level.time + 200;
00357                 ent->think = ShieldGoSolid;
00358                 ent->takedamage = qfalse;
00359                 trap_LinkEntity(ent);
00360         }
00361         else
00362         {       // Get solid.
00363                 ent->r.contents = CONTENTS_PLAYERCLIP|CONTENTS_SHOTCLIP;//CONTENTS_SOLID;
00364 
00365                 ent->nextthink = level.time;
00366                 ent->think = ShieldThink;
00367 
00368                 ent->takedamage = qtrue;
00369                 trap_LinkEntity(ent);
00370 
00371                 // Play raising sound...
00372                 G_AddEvent(ent, EV_GENERAL_SOUND, shieldActivateSound);
00373                 ent->s.loopSound = shieldLoopSound;
00374                 ent->s.loopIsSoundset = qfalse;
00375         }
00376 
00377         ShieldGoSolid(ent);
00378 
00379         return;
00380 }

gentity_t* Drop_Item gentity_t ent,
gitem_t item,
float  angle
 

Definition at line 2742 of file g_items.c.

References AngleVectors(), entityState_s::apos, crandom, gentity_t, gitem_t, LaunchItem(), NULL, PITCH, entityState_s::pos, gentity_s::s, trajectory_t::trBase, vec3_t, VectorCopy, VectorScale, and YAW.

Referenced by TossClientItems().

02742                                                                    {
02743         vec3_t  velocity;
02744         vec3_t  angles;
02745 
02746         VectorCopy( ent->s.apos.trBase, angles );
02747         angles[YAW] += angle;
02748         angles[PITCH] = 0;      // always forward
02749 
02750         AngleVectors( angles, velocity, NULL, NULL );
02751         VectorScale( velocity, 150, velocity );
02752         velocity[2] += 200 + crandom() * 50;
02753         
02754         return LaunchItem( item, ent->s.pos.trBase, velocity );
02755 }

gentity_t* EWeb_Create gentity_t spawner  ) 
 

Definition at line 1859 of file g_items.c.

References trace_t::allsolid, gentity_s::angle, entityState_s::angles, AngleVectors(), entityState_s::apos, CHAN_AUTO, gentity_s::client, gentity_s::clipmask, entityShared_t::contents, entityShared_t::currentAngles, gentity_s::die, trace_t::endpos, trace_t::entityNum, ENTITYNUM_WORLD, EWEB_HEALTH, EWeb_SetBoneAngles(), EWeb_SetBoneAnim(), EWebDie(), gclient_s::ewebHealth, EWebPain(), EWebThink(), trace_t::fraction, entityState_s::g2radius, G_FreeEntity(), G_ModelIndex(), G_ScaleNetHealth(), G_SetOrigin(), G_Sound(), G_SoundIndex(), G_Spawn(), gentity_s::genericValue10, gentity_s::genericValue11, gentity_s::genericValue8, gentity_s::genericValue9, gentity_t, gentity_s::ghoul2, gentity_s::health, level, MASK_PLAYERSOLID, gentity_s::maxHealth, entityShared_t::maxs, entityShared_t::mins, entityState_s::modelGhoul2, entityState_s::modelindex, gentity_s::nextthink, NULL, entityState_s::number, playerState_s::origin, entityState_s::origin2, entityState_s::owner, entityShared_t::ownerNum, gentity_s::pain, gentity_s::physicsObject, gclient_s::ps, qtrue, gentity_s::r, gentity_s::s, gclient_s::sess, clientSession_t::sessionTeam, trace_t::startsolid, STAT_WEAPONS, playerState_s::stats, gentity_s::takedamage, entityState_s::teamowner, gentity_s::think, level_locals_t::time, trap_G2API_AddBolt(), trap_G2API_InitGhoul2Model(), trap_LinkEntity(), trap_Trace(), trajectory_t::trBase, vec3_origin, vec3_t, VectorCopy, VectorMA, VectorSet, playerState_s::viewangles, entityState_s::weapon, and WP_NONE.

Referenced by ItemUse_UseEWeb().

01860 {
01861         const char *modelName = "models/map_objects/hoth/eweb_model.glm";
01862         int failSound = G_SoundIndex("sound/interface/shieldcon_empty");
01863         gentity_t *ent;
01864         trace_t tr;
01865         vec3_t fAng, fwd, pos, downPos, s;
01866         vec3_t mins, maxs;
01867 
01868         VectorSet(mins, -32, -32, -24);
01869         VectorSet(maxs, 32, 32, 24);
01870 
01871         VectorSet(fAng, 0, spawner->client->ps.viewangles[1], 0);
01872         AngleVectors(fAng, fwd, 0, 0);
01873 
01874         VectorCopy(spawner->client->ps.origin, s);
01875         //allow some fudge
01876         s[2] += 12.0f;
01877 
01878         VectorMA(s, 48.0f, fwd, pos);
01879 
01880         trap_Trace(&tr, s, mins, maxs, pos, spawner->s.number, MASK_PLAYERSOLID);
01881 
01882         if (tr.allsolid || tr.startsolid || tr.fraction != 1.0f)
01883         { //can't spawn here, we are in solid
01884                 G_Sound(spawner, CHAN_AUTO, failSound);
01885                 return NULL;
01886         }
01887 
01888         ent = G_Spawn();
01889 
01890         ent->clipmask = MASK_PLAYERSOLID;
01891         ent->r.contents = MASK_PLAYERSOLID;
01892 
01893         ent->physicsObject = qtrue;
01894 
01895         //for the sake of being able to differentiate client-side between this and an emplaced gun
01896         ent->s.weapon = WP_NONE;
01897 
01898         VectorCopy(pos, downPos);
01899         downPos[2] -= 18.0f;
01900         trap_Trace(&tr, pos, mins, maxs, downPos, spawner->s.number, MASK_PLAYERSOLID);
01901 
01902         if (tr.startsolid || tr.allsolid || tr.fraction == 1.0f || tr.entityNum < ENTITYNUM_WORLD)
01903         { //didn't hit ground.
01904                 G_FreeEntity(ent);
01905                 G_Sound(spawner, CHAN_AUTO, failSound);
01906                 return NULL;
01907         }
01908 
01909         VectorCopy(tr.endpos, pos);
01910 
01911         G_SetOrigin(ent, pos);
01912 
01913         VectorCopy(fAng, ent->s.apos.trBase);
01914         VectorCopy(fAng, ent->r.currentAngles);
01915 
01916         ent->s.owner = spawner->s.number;
01917         ent->s.teamowner = spawner->client->sess.sessionTeam;
01918 
01919         ent->takedamage = qtrue;
01920 
01921         if (spawner->client->ewebHealth <= 0)
01922         { //refresh the owner's e-web health if its last e-web did not exist or was killed
01923                 spawner->client->ewebHealth = EWEB_HEALTH;
01924         }
01925 
01926         //resume health of last deployment
01927         ent->maxHealth = EWEB_HEALTH;
01928         ent->health = spawner->client->ewebHealth;
01929         G_ScaleNetHealth(ent);
01930 
01931         ent->die = EWebDie;
01932         ent->pain = EWebPain;
01933 
01934         ent->think = EWebThink;
01935         ent->nextthink = level.time;
01936 
01937         //set up the g2 model info
01938         ent->s.modelGhoul2 = 1;
01939         ent->s.g2radius = 128;
01940         ent->s.modelindex = G_ModelIndex((char *)modelName);
01941 
01942         trap_G2API_InitGhoul2Model(&ent->ghoul2, modelName, 0, 0, 0, 0, 0);
01943 
01944         if (!ent->ghoul2)
01945         { //should not happen, but just to be safe.
01946                 G_FreeEntity(ent);
01947                 return NULL;
01948         }
01949 
01950         //initialize bone angles
01951         EWeb_SetBoneAngles(ent, "cannon_Yrot", vec3_origin);
01952         EWeb_SetBoneAngles(ent, "cannon_Xrot", vec3_origin);
01953 
01954         ent->genericValue10 = trap_G2API_AddBolt(ent->ghoul2, 0, "*cannonflash"); //muzzle bolt
01955         ent->genericValue9 = trap_G2API_AddBolt(ent->ghoul2, 0, "cannon_Yrot"); //for placing the owner relative to rotation
01956 
01957         //set the constraints for this guy as an emplaced weapon, and his constraint angles
01958         ent->s.origin2[0] = 360.0f; //360 degrees in either direction
01959 
01960         VectorCopy(fAng, ent->s.angles); //consider "angle 0" for constraint
01961 
01962         //angle of y rot bone
01963         ent->angle = 0.0f;
01964 
01965         ent->r.ownerNum = spawner->s.number;
01966         trap_LinkEntity(ent);
01967 
01968         //store off the owner's current weapons, we will be forcing him to use the "emplaced" weapon
01969         ent->genericValue11 = spawner->client->ps.stats[STAT_WEAPONS];
01970 
01971         //start the "unfolding" anim
01972         EWeb_SetBoneAnim(ent, 4, 20);
01973         //don't allow use until the anim is done playing (rough time estimate)
01974         ent->genericValue8 = level.time + 500;
01975 
01976         VectorCopy(mins, ent->r.mins);
01977         VectorCopy(maxs, ent->r.maxs);
01978 
01979         return ent;
01980 }

void EWeb_SetBoneAngles gentity_t ent,
char *  bone,
vec3_t  angles
 

Definition at line 1499 of file g_items.c.

References BONE_ANGLES_POSTMULT, entityState_s::boneAngles1, entityState_s::boneAngles2, entityState_s::boneAngles3, entityState_s::boneAngles4, entityState_s::boneIndex1, entityState_s::boneIndex2, entityState_s::boneIndex3, entityState_s::boneIndex4, entityState_s::boneOrient, byte, Com_Printf(), G_BoneIndex(), gentity_t, gentity_s::ghoul2, level, NEGATIVE_X, NEGATIVE_Z, NULL, POSITIVE_Y, gentity_s::s, level_locals_t::time, trap_G2API_SetBoneAngles(), vec3_t, and VectorCopy.

Referenced by EWeb_Create(), and EWebUpdateBoneAngles().

01500 {
01501 #ifdef _XBOX
01502         byte *thebone = &ent->s.boneIndex1;
01503         byte *firstFree = NULL;
01504 #else
01505         int *thebone = &ent->s.boneIndex1;
01506         int *firstFree = NULL;
01507 #endif
01508         int i = 0;
01509         int boneIndex = G_BoneIndex(bone);
01510         int flags, up, right, forward;
01511         vec3_t *boneVector = &ent->s.boneAngles1;
01512         vec3_t *freeBoneVec = NULL;
01513 
01514         while (thebone)
01515         {
01516                 if (!*thebone && !firstFree)
01517                 { //if the value is 0 then this index is clear, we can use it if we don't find the bone we want already existing.
01518                         firstFree = thebone;
01519                         freeBoneVec = boneVector;
01520                 }
01521                 else if (*thebone)
01522                 {
01523                         if (*thebone == boneIndex)
01524                         { //this is it
01525                                 break;
01526                         }
01527                 }
01528 
01529                 switch (i)
01530                 {
01531                 case 0:
01532                         thebone = &ent->s.boneIndex2;
01533                         boneVector = &ent->s.boneAngles2;
01534                         break;
01535                 case 1:
01536                         thebone = &ent->s.boneIndex3;
01537                         boneVector = &ent->s.boneAngles3;
01538                         break;
01539                 case 2:
01540                         thebone = &ent->s.boneIndex4;
01541                         boneVector = &ent->s.boneAngles4;
01542                         break;
01543                 default:
01544                         thebone = NULL;
01545                         boneVector = NULL;
01546                         break;
01547                 }
01548 
01549                 i++;
01550         }
01551 
01552         if (!thebone)
01553         { //didn't find it, create it
01554                 if (!firstFree)
01555                 { //no free bones.. can't do a thing then.
01556                         Com_Printf("WARNING: E-Web has no free bone indexes\n");
01557                         return;
01558                 }
01559 
01560                 thebone = firstFree;
01561 
01562                 *thebone = boneIndex;
01563                 boneVector = freeBoneVec;
01564         }
01565 
01566         //If we got here then we have a vector and an index.
01567 
01568         //Copy the angles over the vector in the entitystate, so we can use the corresponding index
01569         //to set the bone angles on the client.
01570         VectorCopy(angles, *boneVector);
01571 
01572         //Now set the angles on our server instance if we have one.
01573 
01574         if (!ent->ghoul2)
01575         {
01576                 return;
01577         }
01578 
01579         flags = BONE_ANGLES_POSTMULT;
01580         up = POSITIVE_Y;
01581         right = NEGATIVE_Z;
01582         forward = NEGATIVE_X;
01583 
01584         //first 3 bits is forward, second 3 bits is right, third 3 bits is up
01585         ent->s.boneOrient = ((forward)|(right<<3)|(up<<6));
01586 
01587         trap_G2API_SetBoneAngles( ent->ghoul2,
01588                                         0,
01589                                         bone,
01590                                         angles, 
01591                                         flags,
01592                                         up,
01593                                         right,
01594                                         forward,
01595                                         NULL,
01596                                         100,
01597                                         level.time ); 
01598 }

void EWeb_SetBoneAnim gentity_t eweb,
int  startFrame,
int  endFrame
 

Definition at line 1601 of file g_items.c.

References BONE_ANIM_BLEND, BONE_ANIM_OVERRIDE_FREEZE, EF_G2ANIMATING, entityState_s::eFlags, gentity_t, gentity_s::ghoul2, entityState_s::legsAnim, level, gentity_s::s, level_locals_t::time, entityState_s::torsoAnim, entityState_s::torsoFlip, and trap_G2API_SetBoneAnim().

Referenced by EWeb_Create(), and EWebThink().

01602 {
01603         //set info on the entity so it knows to start the anim on the client next snapshot.
01604         eweb->s.eFlags |= EF_G2ANIMATING;
01605 
01606         if (eweb->s.torsoAnim == startFrame && eweb->s.legsAnim == endFrame)
01607         { //already playing this anim, let's flag it to restart
01608                 eweb->s.torsoFlip = !eweb->s.torsoFlip;
01609         }
01610         else
01611         {
01612                 eweb->s.torsoAnim = startFrame;
01613                 eweb->s.legsAnim = endFrame;
01614         }
01615 
01616         //now set the animation on the server ghoul2 instance.
01617         assert(eweb->ghoul2);
01618         trap_G2API_SetBoneAnim(eweb->ghoul2, 0, "model_root", startFrame, endFrame,
01619                 (BONE_ANIM_OVERRIDE_FREEZE|BONE_ANIM_BLEND), 1.0f, level.time, -1, 100);
01620 }

void EWebDie gentity_t self,
gentity_t inflictor,
gentity_t attacker,
int  damage,
int  mod
 

Definition at line 1449 of file g_items.c.

References BG_CycleInven(), bg_itemlist, gentity_s::client, entityShared_t::currentOrigin, EFFECT_EXPLOSION_DETPACK, ENTITYNUM_NONE, EWEB_DEATH_DMG, EWEB_DEATH_RADIUS, EWebDisattach(), gclient_s::ewebHealth, g_entities, G_PlayEffect(), G_RadiusDamage(), gentity_t, HI_EWEB, gentity_s::inuse, IT_HOLDABLE, MOD_SUICIDE, entityShared_t::ownerNum, gclient_s::ps, gentity_s::r, STAT_HOLDABLE_ITEM, STAT_HOLDABLE_ITEMS, playerState_s::stats, vec3_t, and VectorSet.

Referenced by EWeb_Create(), and EWebThink().

01450 {
01451         vec3_t fxDir;
01452 
01453         G_RadiusDamage(self->r.currentOrigin, self, EWEB_DEATH_DMG, EWEB_DEATH_RADIUS, self, self, MOD_SUICIDE);
01454 
01455         VectorSet(fxDir, 1.0f, 0.0f, 0.0f);
01456         G_PlayEffect(EFFECT_EXPLOSION_DETPACK, self->r.currentOrigin, fxDir);
01457 
01458         if (self->r.ownerNum != ENTITYNUM_NONE)
01459         {
01460                 gentity_t *owner = &g_entities[self->r.ownerNum];
01461 
01462                 if (owner->inuse && owner->client)
01463                 {
01464                         EWebDisattach(owner, self);
01465 
01466                         //make sure it resets next time we spawn one in case we someone obtain one before death
01467                         owner->client->ewebHealth = -1;
01468 
01469                         //take it away from him, it is gone forever.
01470                         owner->client->ps.stats[STAT_HOLDABLE_ITEMS] &= ~(1<<HI_EWEB);
01471 
01472                         if (owner->client->ps.stats[STAT_HOLDABLE_ITEM] > 0 &&
01473                                 bg_itemlist[owner->client->ps.stats[STAT_HOLDABLE_ITEM]].giType == IT_HOLDABLE &&
01474                                 bg_itemlist[owner->client->ps.stats[STAT_HOLDABLE_ITEM]].giTag == HI_EWEB)
01475                         { //he has it selected so deselect it and select the first thing available
01476                                 owner->client->ps.stats[STAT_HOLDABLE_ITEM] = 0;
01477                                 BG_CycleInven(&owner->client->ps, 1);
01478                         }
01479                 }
01480         }
01481 }

void EWebDisattach gentity_t owner,
gentity_t eweb
 

Definition at line 1417 of file g_items.c.

References gentity_s::client, playerState_s::emplacedIndex, gclient_s::ewebIndex, G_FreeEntity(), gentity_s::genericValue11, gentity_t, gentity_s::health, level, gentity_s::nextthink, gclient_s::ps, STAT_WEAPONS, playerState_s::stats, gentity_s::think, and level_locals_t::time.

Referenced by EWebDie(), EWebPositionUser(), EWebThink(), and ItemUse_UseEWeb().

01418 {
01419     owner->client->ewebIndex = 0;
01420         owner->client->ps.emplacedIndex = 0;
01421         if (owner->health > 0)
01422         {
01423                 owner->client->ps.stats[STAT_WEAPONS] = eweb->genericValue11;
01424         }
01425         else
01426         {
01427                 owner->client->ps.stats[STAT_WEAPONS] = 0;
01428         }
01429         eweb->think = G_FreeEntity;
01430         eweb->nextthink = level.time;
01431 }

void EWebFire gentity_t owner,
gentity_t eweb
 

Definition at line 1624 of file g_items.c.

References entityState_s::apos, gentity_s::bounceCount, gentity_s::classname, gentity_s::clipmask, CONTENTS_LIGHTSABER, CreateMissile(), entityShared_t::currentOrigin, gentity_s::damage, DAMAGE_DEATH_KNOCKBACK, gentity_s::dflags, EWEB_MISSILE_DAMAGE, G_EffectIndex(), G_PlayEffectID(), gentity_s::genericValue10, gentity_t, gentity_s::ghoul2, level, MASK_SHOT, gentity_s::methodOfDeath, MOD_TURBLAST, gentity_s::modelScale, NEGATIVE_Y, NULL, entityState_s::number, ORIGIN, gentity_s::passThroughNum, qfalse, gentity_s::r, gentity_s::s, level_locals_t::time, trap_G2API_GetBoltMatrix(), trajectory_t::trBase, vec3_t, vectoangles(), VectorMA, entityState_s::weapon, and WP_TURRET.

Referenced by EWebThink().

01625 {
01626         mdxaBone_t boltMatrix;
01627         gentity_t *missile;
01628         vec3_t p, d, bPoint;
01629 
01630         if (eweb->genericValue10 == -1)
01631         { //oh no
01632                 assert(!"Bad e-web bolt");
01633                 return;
01634         }
01635 
01636         //get the muzzle point
01637         trap_G2API_GetBoltMatrix(eweb->ghoul2, 0, eweb->genericValue10, &boltMatrix, eweb->s.apos.trBase, eweb->r.currentOrigin, level.time, NULL, eweb->modelScale);
01638         BG_GiveMeVectorFromMatrix(&boltMatrix, ORIGIN, p);
01639         BG_GiveMeVectorFromMatrix(&boltMatrix, NEGATIVE_Y, d);
01640 
01641         //Start the thing backwards into the bounding box so it can't start inside other solid things
01642         VectorMA(p, -16.0f, d, bPoint);
01643 
01644         //create the missile
01645         missile = CreateMissile( bPoint, d, 1200.0f, 10000, owner, qfalse );
01646 
01647         missile->classname = "generic_proj";
01648         missile->s.weapon = WP_TURRET;
01649 
01650         missile->damage = EWEB_MISSILE_DAMAGE;
01651         missile->dflags = DAMAGE_DEATH_KNOCKBACK;
01652         missile->methodOfDeath = MOD_TURBLAST;
01653         missile->clipmask = (MASK_SHOT|CONTENTS_LIGHTSABER);
01654 
01655         //ignore the e-web entity
01656         missile->passThroughNum = eweb->s.number+1;
01657 
01658         //times it can bounce before it dies
01659         missile->bounceCount = 8;
01660 
01661         //play the muzzle flash
01662         vectoangles(d, d);
01663         G_PlayEffectID(G_EffectIndex("turret/muzzle_flash.efx"), p, d);
01664 }

void EWebPain gentity_t self,
gentity_t attacker,
int  damage
 

Definition at line 1484 of file g_items.c.

References gentity_s::client, ENTITYNUM_NONE, gclient_s::ewebHealth, g_entities, gentity_t, gentity_s::health, gentity_s::inuse, entityShared_t::ownerNum, and gentity_s::r.

Referenced by EWeb_Create().

01485 {
01486         //update the owner's health status of me
01487         if (self->r.ownerNum != ENTITYNUM_NONE)
01488         {
01489                 gentity_t *owner = &g_entities[self->r.ownerNum];
01490 
01491                 if (owner->inuse && owner->client)
01492                 {
01493                         owner->client->ewebHealth = self->health;
01494                 }
01495         }
01496 }

void EWebPositionUser gentity_t owner,
gentity_t eweb
 

Definition at line 1667 of file g_items.c.

References trace_t::allsolid, AngleSubtract(), entityState_s::apos, BOTH_STRAFE_LEFT1, BOTH_STRAFE_RIGHT1, gentity_s::client, clientPersistant_t::cmd, entityShared_t::currentOrigin, trace_t::endpos, EWebDisattach(), trace_t::fraction, G_SetAnim(), G_SetOrigin(), gentity_s::genericValue9, gentity_t, gentity_s::ghoul2, playerState_s::legsAnim, playerState_s::legsTimer, level, MASK_PLAYERSOLID, entityShared_t::maxs, entityShared_t::mins, gentity_s::modelScale, NEGATIVE_X, NULL, entityState_s::number, playerState_s::origin, ORIGIN, gclient_s::pers, gclient_s::ps, gentity_s::r, gentity_s::s, SETANIM_FLAG_HOLD, SETANIM_FLAG_OVERRIDE, SETANIM_LEGS, trace_t::startsolid, level_locals_t::time, trap_G2API_GetBoltMatrix(), trap_Trace(), trajectory_t::trBase, vec3_t, vectoangles(), VectorCopy, VectorMA, VectorSubtract, playerState_s::viewangles, and YAW.

Referenced by EWebUpdateBoneAngles().

01668 {
01669         mdxaBone_t boltMatrix;
01670         vec3_t p, d;
01671         trace_t tr;
01672 
01673         trap_G2API_GetBoltMatrix(eweb->ghoul2, 0, eweb->genericValue9, &boltMatrix, eweb->s.apos.trBase, eweb->r.currentOrigin, level.time, NULL, eweb->modelScale);
01674         BG_GiveMeVectorFromMatrix(&boltMatrix, ORIGIN, p);
01675         BG_GiveMeVectorFromMatrix(&boltMatrix, NEGATIVE_X, d);
01676 
01677         VectorMA(p, 32.0f, d, p);
01678         p[2] = eweb->r.currentOrigin[2];
01679 
01680         p[2] += 4.0f;
01681 
01682         trap_Trace(&tr, owner->client->ps.origin, owner->r.mins, owner->r.maxs, p, owner->s.number, MASK_PLAYERSOLID);
01683 
01684         if (!tr.startsolid && !tr.allsolid && tr.fraction == 1.0f)
01685         { //all clear, we can move there
01686                 vec3_t pDown;
01687 
01688                 VectorCopy(p, pDown);
01689                 pDown[2] -= 7.0f;
01690                 trap_Trace(&tr, p, owner->r.mins, owner->r.maxs, pDown, owner->s.number, MASK_PLAYERSOLID);
01691 
01692                 if (!tr.startsolid && !tr.allsolid)
01693                 {
01694                         VectorSubtract(owner->client->ps.origin, tr.endpos, d);
01695                         if (VectorLength(d) > 1.0f)
01696                         { //we moved, do some animating
01697                                 vec3_t dAng;
01698                                 int aFlags = SETANIM_FLAG_HOLD;
01699 
01700                                 vectoangles(d, dAng);
01701                                 dAng[YAW] = AngleSubtract(owner->client->ps.viewangles[YAW], dAng[YAW]);
01702                                 if (dAng[YAW] > 0.0f)
01703                                 {
01704                                         if (owner->client->ps.legsAnim == BOTH_STRAFE_RIGHT1)
01705                                         { //reset to change direction
01706                                                 aFlags |= SETANIM_FLAG_OVERRIDE;
01707                                         }
01708                                         G_SetAnim(owner, &owner->client->pers.cmd, SETANIM_LEGS, BOTH_STRAFE_LEFT1, aFlags, 0);
01709                                 }
01710                                 else
01711                                 {
01712                                         if (owner->client->ps.legsAnim == BOTH_STRAFE_LEFT1)
01713                                         { //reset to change direction
01714                                                 aFlags |= SETANIM_FLAG_OVERRIDE;
01715                                         }
01716                                         G_SetAnim(owner, &owner->client->pers.cmd, SETANIM_LEGS, BOTH_STRAFE_RIGHT1, aFlags, 0);
01717                                 }
01718                         }
01719                         else if (owner->client->ps.legsAnim == BOTH_STRAFE_RIGHT1 || owner->client->ps.legsAnim == BOTH_STRAFE_LEFT1)
01720                         { //don't keep animating in place
01721                                 owner->client->ps.legsTimer = 0;
01722                         }
01723 
01724                         G_SetOrigin(owner, tr.endpos);
01725                         VectorCopy(tr.endpos, owner->client->ps.origin);
01726                 }
01727         }
01728         else
01729         { //can't move here.. stop using the thing I guess
01730                 EWebDisattach(owner, eweb);
01731         }
01732 }

void EWebPrecache void   ) 
 

Definition at line 1434 of file g_items.c.

References BG_FindItemForWeapon(), G_EffectIndex(), RegisterItem(), and WP_TURRET.

Referenced by SP_worldspawn().

01435 {
01436         RegisterItem( BG_FindItemForWeapon(WP_TURRET) );
01437         G_EffectIndex("detpack/explosion.efx");
01438         G_EffectIndex("turret/muzzle_flash.efx");
01439 }

void EWebThink gentity_t self  ) 
 

Definition at line 1776 of file g_items.c.

References entityState_s::angles, BG_EmplacedView(), BUTTON_ATTACK, usercmd_s::buttons, gentity_s::client, clientPersistant_t::cmd, CON_CONNECTED, clientPersistant_t::connected, playerState_s::emplacedIndex, ENTITYNUM_NONE, EWeb_SetBoneAnim(), EWebDie(), EWebDisattach(), EWebFire(), gclient_s::ewebIndex, EWebUpdateBoneAngles(), g_entities, G_RunExPhys(), gentity_s::genericValue3, gentity_s::genericValue5, gentity_s::genericValue8, gentity_t, gentity_s::health, gentity_s::inuse, level, MOD_SUICIDE, gentity_s::nextthink, NULL, entityState_s::number, entityState_s::origin2, entityShared_t::ownerNum, gclient_s::pers, gclient_s::ps, qboolean, qfalse, qtrue, gentity_s::r, gentity_s::s, STAT_WEAPONS, playerState_s::stats, level_locals_t::time, playerState_s::viewangles, playerState_s::weapon, WP_EMPLACED_GUN, and YAW.

Referenced by EWeb_Create().

01777 {
01778         qboolean killMe = qfalse;
01779         const float gravity = 3.0f;
01780         const float mass = 0.09f;
01781         const float bounce = 1.1f;
01782 
01783         if (self->r.ownerNum == ENTITYNUM_NONE)
01784         {
01785                 killMe = qtrue;
01786         }
01787         else
01788         {
01789                 gentity_t *owner = &g_entities[self->r.ownerNum];
01790 
01791                 if (!owner->inuse || !owner->client || owner->client->pers.connected != CON_CONNECTED ||
01792                         owner->client->ewebIndex != self->s.number || owner->health < 1)
01793                 {
01794                         killMe = qtrue;
01795                 }
01796                 else if (owner->client->ps.emplacedIndex != self->s.number)
01797                 { //just go back to the inventory then
01798                         EWebDisattach(owner, self);
01799                         return;
01800                 }
01801 
01802                 if (!killMe)
01803                 {
01804                         float yaw;
01805 
01806                         if (BG_EmplacedView(owner->client->ps.viewangles, self->s.angles, &yaw, self->s.origin2[0]))
01807                         {
01808                                 owner->client->ps.viewangles[YAW] = yaw;
01809                         }
01810                         owner->client->ps.weapon = WP_EMPLACED_GUN;
01811                         owner->client->ps.stats[STAT_WEAPONS] = WP_EMPLACED_GUN;
01812 
01813                         if (self->genericValue8 < level.time)
01814                         { //make sure the anim timer is done
01815                                 EWebUpdateBoneAngles(owner, self);
01816                                 if (!owner->client->ewebIndex)
01817                                 { //was removed during position function
01818                                         return;
01819                                 }
01820 
01821                                 if (owner->client->pers.cmd.buttons & BUTTON_ATTACK)
01822                                 {
01823                                         if (self->genericValue5 < level.time)
01824                                         { //we can fire another shot off
01825                                                 EWebFire(owner, self);
01826 
01827                                                 //cheap firing anim
01828                                                 EWeb_SetBoneAnim(self, 2, 4);
01829                                                 self->genericValue3 = 1;
01830 
01831                                                 //set fire debounce time
01832                                                 self->genericValue5 = level.time + 100;
01833                                         }
01834                                 }
01835                                 else if (self->genericValue5 < level.time && self->genericValue3)
01836                                 { //reset the anim back to non-firing
01837                                         EWeb_SetBoneAnim(self, 0, 1);
01838                                         self->genericValue3 = 0;
01839                                 }
01840                         }
01841                 }
01842         }
01843 
01844         if (killMe)
01845         { //something happened to the owner, let's explode
01846                 EWebDie(self, self, self, 999, MOD_SUICIDE);
01847                 return;
01848         }
01849 
01850         //run some physics on it real quick so it falls and stuff properly
01851         G_RunExPhys(self, gravity, mass, bounce, qfalse, NULL, 0);
01852 
01853         self->nextthink = level.time;
01854 }

void EWebUpdateBoneAngles gentity_t owner,
gentity_t eweb
 

Definition at line 1735 of file g_items.c.

References gentity_s::angle, entityState_s::angles, AngleSubtract(), gentity_s::client, EWeb_SetBoneAngles(), gclient_s::ewebIndex, EWebPositionUser(), gentity_t, PITCH, gclient_s::ps, gentity_s::s, vec3_t, VectorClear, playerState_s::viewangles, and YAW.

Referenced by EWebThink().

01736 {
01737         vec3_t yAng;
01738         float ideal;
01739         float incr;
01740         const float turnCap = 4.0f; //max degrees we can turn per update
01741         
01742         VectorClear(yAng);
01743         ideal = AngleSubtract(owner->client->ps.viewangles[YAW], eweb->s.angles[YAW]);
01744         incr = AngleSubtract(ideal, eweb->angle);
01745 
01746         if (incr > turnCap)
01747         {
01748                 incr = turnCap;
01749         }
01750         else if (incr < -turnCap)
01751         {
01752                 incr = -turnCap;
01753         }
01754 
01755         eweb->angle += incr;
01756 
01757         yAng[0] = eweb->angle;
01758         EWeb_SetBoneAngles(eweb, "cannon_Yrot", yAng);
01759 
01760         EWebPositionUser(owner, eweb);
01761         if (!owner->client->ewebIndex)
01762         { //was removed during position function
01763                 return;
01764         }
01765 
01766         VectorClear(yAng);
01767         yAng[2] = AngleSubtract(owner->client->ps.viewangles[PITCH], eweb->s.angles[PITCH])*0.8f;
01768         EWeb_SetBoneAngles(eweb, "cannon_Xrot", yAng);
01769 }

void FinishSpawningItem gentity_t ent  ) 
 

Definition at line 2779 of file g_items.c.

References bg_itemlist, gentity_s::classname, entityShared_t::contents, CONTENTS_TRIGGER, EF_NODRAW, entityState_s::eFlags, trace_t::endpos, trace_t::entityNum, ET_ITEM, entityState_s::eType, FL_TEAMSLAVE, gentity_s::flags, g_forcePowerDisable, G_FreeEntity(), g_gametype, G_Printf(), G_SetOrigin(), gentity_t, gitem_s::giTag, gitem_s::giType, entityState_s::groundEntityNum, GT_CTF, GT_CTY, GT_DUEL, GT_HOLOCRON, GT_JEDIMASTER, GT_POWERDUEL, GT_SIEGE, HasSetSaberOnly(), HI_MEDPAC, HI_MEDPAC_BIG, HI_SEEKER, HI_SENTRY_GUN, HI_SHIELD, vmCvar_t::integer, IT_AMMO, IT_ARMOR, IT_HEALTH, IT_HOLDABLE, IT_POWERUP, IT_TEAM, gentity_s::item, ITMSF_SUSPEND, MASK_SOLID, entityShared_t::maxs, entityShared_t::mins, entityState_s::modelindex, entityState_s::modelindex2, entityState_s::number, entityState_s::origin, PW_BLUEFLAG, PW_FORCE_BOON, PW_FORCE_ENLIGHTENED_DARK, PW_FORCE_ENLIGHTENED_LIGHT, PW_NEUTRALFLAG, PW_REDFLAG, gentity_s::r, gentity_s::s, gentity_s::spawnflags, trace_t::startsolid, gentity_s::targetname, gentity_s::touch, Touch_Item(), trap_LinkEntity(), trap_Trace(), gentity_s::use, Use_Item(), vec3_t, VectorSet, and vtos().

Referenced by Cmd_Give_f(), and G_SpawnItem().

02779                                           {
02780         trace_t         tr;
02781         vec3_t          dest;
02782 //      gitem_t         *item;
02783 
02784 //      VectorSet( ent->r.mins, -ITEM_RADIUS, -ITEM_RADIUS, -ITEM_RADIUS );
02785 //      VectorSet( ent->r.maxs, ITEM_RADIUS, ITEM_RADIUS, ITEM_RADIUS );
02786 
02787         if (g_gametype.integer == GT_SIEGE)
02788         { //in siege remove all powerups
02789                 if (ent->item->giType == IT_POWERUP)
02790                 {
02791                         G_FreeEntity(ent);
02792                         return;
02793                 }
02794         }
02795 
02796         if (g_gametype.integer != GT_JEDIMASTER)
02797         {
02798                 if (HasSetSaberOnly())
02799                 {
02800                         if (ent->item->giType == IT_AMMO)
02801                         {
02802                                 G_FreeEntity( ent );
02803                                 return;
02804                         }
02805 
02806                         if (ent->item->giType == IT_HOLDABLE)
02807                         {
02808                                 if (ent->item->giTag == HI_SEEKER ||
02809                                         ent->item->giTag == HI_SHIELD ||
02810                                         ent->item->giTag == HI_SENTRY_GUN)
02811                                 {
02812                                         G_FreeEntity( ent );
02813                                         return;
02814                                 }
02815                         }
02816                 }
02817         }
02818         else
02819         { //no powerups in jedi master
02820                 if (ent->item->giType == IT_POWERUP)
02821                 {
02822                         G_FreeEntity(ent);
02823                         return;
02824                 }
02825         }
02826 
02827         if (g_gametype.integer == GT_HOLOCRON)
02828         {
02829                 if (ent->item->giType == IT_POWERUP)
02830                 {
02831                         if (ent->item->giTag == PW_FORCE_ENLIGHTENED_LIGHT ||
02832                                 ent->item->giTag == PW_FORCE_ENLIGHTENED_DARK)
02833                         {
02834                                 G_FreeEntity(ent);
02835                                 return;
02836                         }
02837                 }
02838         }
02839 
02840         if (g_forcePowerDisable.integer)
02841         { //if force powers disabled, don't add force powerups
02842                 if (ent->item->giType == IT_POWERUP)
02843                 {
02844                         if (ent->item->giTag == PW_FORCE_ENLIGHTENED_LIGHT ||
02845                                 ent->item->giTag == PW_FORCE_ENLIGHTENED_DARK ||
02846                                 ent->item->giTag == PW_FORCE_BOON)
02847                         {
02848                                 G_FreeEntity(ent);
02849                                 return;
02850                         }
02851                 }
02852         }
02853 
02854         if (g_gametype.integer == GT_DUEL || g_gametype.integer == GT_POWERDUEL)
02855         {
02856                 if ( ent->item->giType == IT_ARMOR ||
02857                         ent->item->giType == IT_HEALTH ||
02858                         (ent->item->giType == IT_HOLDABLE && (ent->item->giTag == HI_MEDPAC || ent->item->giTag == HI_MEDPAC_BIG)) )
02859                 {
02860                         G_FreeEntity(ent);
02861                         return;
02862                 }
02863         }
02864 
02865         if (g_gametype.integer != GT_CTF &&
02866                 g_gametype.integer != GT_CTY &&
02867                 ent->item->giType == IT_TEAM)
02868         {
02869                 int killMe = 0;
02870 
02871                 switch (ent->item->giTag)
02872                 {
02873                 case PW_REDFLAG:
02874                         killMe = 1;
02875                         break;
02876                 case PW_BLUEFLAG:
02877                         killMe = 1;
02878                         break;
02879                 case PW_NEUTRALFLAG:
02880                         killMe = 1;
02881                         break;
02882                 default:
02883                         break;
02884                 }
02885 
02886                 if (killMe)
02887                 {
02888                         G_FreeEntity( ent );
02889                         return;
02890                 }
02891         }
02892 
02893         VectorSet (ent->r.mins, -8, -8, -0);
02894         VectorSet (ent->r.maxs, 8, 8, 16);
02895 
02896         ent->s.eType = ET_ITEM;
02897         ent->s.modelindex = ent->item - bg_itemlist;            // store item number in modelindex
02898         ent->s.modelindex2 = 0; // zero indicates this isn't a dropped item
02899 
02900         ent->r.contents = CONTENTS_TRIGGER;
02901         ent->touch = Touch_Item;
02902         // useing an item causes it to respawn
02903         ent->use = Use_Item;
02904 
02905         // create a Ghoul2 model if the world model is a glm
02906 /*      item = &bg_itemlist[ ent->s.modelindex ];
02907         if (!stricmp(&item->world_model[0][strlen(item->world_model[0]) - 4], ".glm"))
02908         {
02909                 trap_G2API_InitGhoul2Model(&ent->s, item->world_model[0], G_ModelIndex(item->world_model[0] ), 0, 0, 0, 0);
02910                 ent->s.radius = 60;
02911         }
02912 */
02913         if ( ent->spawnflags & ITMSF_SUSPEND ) {
02914                 // suspended
02915                 G_SetOrigin( ent, ent->s.origin );
02916         } else {
02917                 // drop to floor
02918 
02919                 //if it is directly even with the floor it will return startsolid, so raise up by 0.1
02920                 //and temporarily subtract 0.1 from the z maxs so that going up doesn't push into the ceiling
02921                 ent->s.origin[2] += 0.1;
02922                 ent->r.maxs[2] -= 0.1;
02923 
02924                 VectorSet( dest, ent->s.origin[0], ent->s.origin[1], ent->s.origin[2] - 4096 );
02925                 trap_Trace( &tr, ent->s.origin, ent->r.mins, ent->r.maxs, dest, ent->s.number, MASK_SOLID );
02926                 if ( tr.startsolid ) {
02927                         G_Printf ("FinishSpawningItem: %s startsolid at %s\n", ent->classname, vtos(ent->s.origin));
02928                         G_FreeEntity( ent );
02929                         return;
02930                 }
02931 
02932                 //add the 0.1 back after the trace
02933                 ent->r.maxs[2] += 0.1;
02934 
02935                 // allow to ride movers
02936                 ent->s.groundEntityNum = tr.entityNum;
02937 
02938                 G_SetOrigin( ent, tr.endpos );
02939         }
02940 
02941         // team slaves and targeted items aren't present at start
02942         if ( ( ent->flags & FL_TEAMSLAVE ) || ent->targetname ) {
02943                 ent->s.eFlags |= EF_NODRAW;
02944                 ent->r.contents = 0;
02945                 return;
02946         }
02947 
02948         // powerups don't spawn in for a while
02949         /*
02950         if ( ent->item->giType == IT_POWERUP ) {
02951                 float   respawn;
02952 
02953                 respawn = 45 + crandom() * 15;
02954                 ent->s.eFlags |= EF_NODRAW;
02955                 ent->r.contents = 0;
02956                 ent->nextthink = level.time + respawn * 1000;
02957                 ent->think = RespawnItem;
02958                 return;
02959         }
02960         */
02961 
02962         trap_LinkEntity (ent);
02963 }

void G_BounceItem gentity_t ent,
trace_t trace
 

Definition at line 3130 of file g_items.c.

References BG_EvaluateTrajectoryDelta(), entityShared_t::currentOrigin, DotProduct, trace_t::endpos, trace_t::entityNum, ET_GENERAL, ET_HOLOCRON, entityState_s::eType, trace_t::fraction, g_entities, G_SetOrigin(), gentity_t, entityState_s::groundEntityNum, level, cplane_s::normal, gentity_s::physicsBounce, gentity_s::physicsObject, trace_t::plane, entityState_s::pos, level_locals_t::previousTime, gentity_s::r, gentity_s::s, entityState_s::shouldtarget, level_locals_t::time, gentity_s::touch, trajectory_t::trBase, trajectory_t::trDelta, trajectory_t::trTime, vec3_t, VectorAdd, VectorCopy, VectorMA, VectorScale, entityState_s::weapon, and WP_DET_PACK.

Referenced by G_RunItem().

03130                                                     {
03131         vec3_t  velocity;
03132         float   dot;
03133         int             hitTime;
03134 
03135         // reflect the velocity on the trace plane
03136         hitTime = level.previousTime + ( level.time - level.previousTime ) * trace->fraction;
03137         BG_EvaluateTrajectoryDelta( &ent->s.pos, hitTime, velocity );
03138         dot = DotProduct( velocity, trace->plane.normal );
03139         VectorMA( velocity, -2*dot, trace->plane.normal, ent->s.pos.trDelta );
03140 
03141         // cut the velocity to keep from bouncing forever
03142         VectorScale( ent->s.pos.trDelta, ent->physicsBounce, ent->s.pos.trDelta );
03143 
03144         if ((ent->s.weapon == WP_DET_PACK && ent->s.eType == ET_GENERAL && ent->physicsObject))
03145         { //detpacks only
03146                 if (ent->touch)
03147                 {
03148                         ent->touch(ent, &g_entities[trace->entityNum], trace);
03149                         return;
03150                 }
03151         }
03152 
03153         // check for stop
03154         if ( trace->plane.normal[2] > 0 && ent->s.pos.trDelta[2] < 40 ) {
03155                 trace->endpos[2] += 1.0;        // make sure it is off ground
03156                 SnapVector( trace->endpos );
03157                 G_SetOrigin( ent, trace->endpos );
03158                 ent->s.groundEntityNum = trace->entityNum;
03159                 return;
03160         }
03161 
03162         VectorAdd( ent->r.currentOrigin, trace->plane.normal, ent->r.currentOrigin);
03163         VectorCopy( ent->r.currentOrigin, ent->s.pos.trBase );
03164         ent->s.pos.trTime = level.time;
03165 
03166         if (ent->s.eType == ET_HOLOCRON ||
03167                 (ent->s.shouldtarget && ent->s.eType == ET_GENERAL && ent->physicsObject))
03168         { //holocrons and sentry guns
03169                 if (ent->touch)
03170                 {
03171                         ent->touch(ent, &g_entities[trace->entityNum], trace);
03172                 }
03173         }
03174 }

void G_CheckTeamItems void   ) 
 

Definition at line 2973 of file g_items.c.

References BG_FindItem(), bg_itemlist, g_gametype, G_Printf(), gitem_t, GT_CTF, GT_CTY, vmCvar_t::integer, itemRegistered, S_COLOR_YELLOW, and Team_InitGame().

Referenced by G_InitGame().

02973                               {
02974 
02975         // Set up team stuff
02976         Team_InitGame();
02977 
02978         if( g_gametype.integer == GT_CTF || g_gametype.integer == GT_CTY ) {
02979                 gitem_t *item;
02980 
02981                 // check for the two flags
02982                 item = BG_FindItem( "team_CTF_redflag" );
02983                 if ( !item || !itemRegistered[ item - bg_itemlist ] ) {
02984                         G_Printf( S_COLOR_YELLOW "WARNING: No team_CTF_redflag in map" );
02985                 }
02986                 item = BG_FindItem( "team_CTF_blueflag" );
02987                 if ( !item || !itemRegistered[ item - bg_itemlist ] ) {
02988                         G_Printf( S_COLOR_YELLOW "WARNING: No team_CTF_blueflag in map" );
02989                 }
02990         }
02991 }

int G_ItemDisabled gitem_t item  ) 
 

Definition at line 3061 of file g_items.c.

References gitem_s::classname, Com_sprintf(), gitem_t, name, and trap_Cvar_VariableIntegerValue().

Referenced by G_SpawnItem().

03061                                     {
03062 
03063         char name[128];
03064 
03065         Com_sprintf(name, sizeof(name), "disable_%s", item->classname);
03066         return trap_Cvar_VariableIntegerValue( name );
03067 }

void G_PrecacheDispensers void   ) 
 

Definition at line 1336 of file g_items.c.

References BG_FindItem(), DISP_AMMO_ITEM, DISP_HEALTH_ITEM, gitem_t, and RegisterItem().

Referenced by ClearRegisteredItems().

01337 {
01338         gitem_t *item;
01339                 
01340         item = BG_FindItem(DISP_HEALTH_ITEM);
01341         if (item)
01342         {
01343                 RegisterItem(item);
01344         }
01345 
01346         item = BG_FindItem(DISP_AMMO_ITEM);
01347         if (item)
01348         {
01349                 RegisterItem(item);
01350         }
01351 }

void G_RunItem gentity_t ent  ) 
 

Definition at line 3183 of file g_items.c.

References BG_EvaluateTrajectory(), gentity_s::clipmask, CONTENTS_BODY, CONTENTS_NODROP, entityShared_t::currentOrigin, trace_t::endpos, trace_t::fraction, G_BounceItem(), G_FreeEntity(), G_RunThink(), gentity_t, gitem_s::giType, entityState_s::groundEntityNum, IT_TEAM, gentity_s::item, level, MASK_PLAYERSOLID, entityShared_t::maxs, entityShared_t::mins, entityShared_t::ownerNum, entityState_s::pos, gentity_s::r, gentity_s::s, trace_t::startsolid, Team_FreeEntity(), level_locals_t::time, TR_GRAVITY, TR_STATIONARY, trap_LinkEntity(), trap_PointContents(), trap_Trace(), trajectory_t::trTime, trajectory_t::trType, vec3_t, and VectorCopy.

Referenced by G_RunFrame().

03183                                  {
03184         vec3_t          origin;
03185         trace_t         tr;
03186         int                     contents;
03187         int                     mask;
03188 
03189         // if groundentity has been set to -1, it may have been pushed off an edge
03190         if ( ent->s.groundEntityNum == -1 ) {
03191                 if ( ent->s.pos.trType != TR_GRAVITY ) {
03192                         ent->s.pos.trType = TR_GRAVITY;
03193                         ent->s.pos.trTime = level.time;
03194                 }
03195         }
03196 
03197         if ( ent->s.pos.trType == TR_STATIONARY ) {
03198                 // check think function
03199                 G_RunThink( ent );
03200                 return;
03201         }
03202 
03203         // get current position
03204         BG_EvaluateTrajectory( &ent->s.pos, level.time, origin );
03205 
03206         // trace a line from the previous position to the current position
03207         if ( ent->clipmask ) {
03208                 mask = ent->clipmask;
03209         } else {
03210                 mask = MASK_PLAYERSOLID & ~CONTENTS_BODY;//MASK_SOLID;
03211         }
03212         trap_Trace( &tr, ent->r.currentOrigin, ent->r.mins, ent->r.maxs, origin, 
03213                 ent->r.ownerNum, mask );
03214 
03215         VectorCopy( tr.endpos, ent->r.currentOrigin );
03216 
03217         if ( tr.startsolid ) {
03218                 tr.fraction = 0;
03219         }
03220 
03221         trap_LinkEntity( ent ); // FIXME: avoid this for stationary?
03222 
03223         // check think function
03224         G_RunThink( ent );
03225 
03226         if ( tr.fraction == 1 ) {
03227                 return;
03228         }
03229 
03230         // if it is in a nodrop volume, remove it
03231         contents = trap_PointContents( ent->r.currentOrigin, -1 );
03232         if ( contents & CONTENTS_NODROP ) {
03233                 if (ent->item && ent->item->giType == IT_TEAM) {
03234                         Team_FreeEntity(ent);
03235                 } else {
03236                         G_FreeEntity( ent );
03237                 }
03238                 return;
03239         }
03240 
03241         G_BounceItem( ent, &tr );
03242 }

void G_SpawnItem gentity_t ent,
gitem_t item
 

Definition at line 3079 of file g_items.c.

References FinishSpawningItem(), FRAMETIME, g_duelWeaponDisable, G_FreeEntity(), g_gametype, G_ItemDisabled(), G_SoundIndex(), G_SpawnFloat(), g_weaponDisable, gentity_t, gitem_s::giTag, gitem_t, gitem_s::giType, GT_DUEL, GT_JEDIMASTER, GT_POWERDUEL, vmCvar_t::integer, IT_POWERUP, IT_WEAPON, gentity_s::item, level, gentity_s::nextthink, gentity_s::physicsBounce, gentity_s::random, RegisterItem(), gentity_s::speed, gentity_s::think, level_locals_t::time, and gentity_s::wait.

Referenced by Cmd_Give_f(), G_CallSpawn(), and SP_gametype_item().

03079                                                  {
03080         int wDisable = 0;
03081 
03082         G_SpawnFloat( "random", "0", &ent->random );
03083         G_SpawnFloat( "wait", "0", &ent->wait );
03084 
03085         if (g_gametype.integer == GT_DUEL || g_gametype.integer == GT_POWERDUEL)
03086         {
03087                 wDisable = g_duelWeaponDisable.integer;
03088         }
03089         else
03090         {
03091                 wDisable = g_weaponDisable.integer;
03092         }
03093 
03094         if (item->giType == IT_WEAPON &&
03095                 wDisable &&
03096                 (wDisable & (1 << item->giTag)))
03097         {
03098                 if (g_gametype.integer != GT_JEDIMASTER)
03099                 {
03100                         G_FreeEntity( ent );
03101                         return;
03102                 }
03103         }
03104 
03105         RegisterItem( item );
03106         if ( G_ItemDisabled(item) )
03107                 return;
03108 
03109         ent->item = item;
03110         // some movers spawn on the second frame, so delay item
03111         // spawns until the third frame so they can ride trains
03112         ent->nextthink = level.time + FRAMETIME * 2;
03113         ent->think = FinishSpawningItem;
03114 
03115         ent->physicsBounce = 0.50;              // items are bouncy
03116 
03117         if ( item->giType == IT_POWERUP ) {
03118                 G_SoundIndex( "sound/items/respawn1" );
03119                 G_SpawnFloat( "noglobalsound", "0", &ent->speed);
03120         }
03121 }

void G_SpecialSpawnItem gentity_t ent,
gitem_t item
 

Definition at line 1295 of file g_items.c.

References bg_itemlist, entityState_s::brokenLimbs, gentity_s::clipmask, entityShared_t::contents, CONTENTS_TRIGGER, EF_CLIENTSMOOTH, entityState_s::eFlags, ET_ITEM, entityState_s::eType, gentity_s::genericValue10, gentity_s::genericValue11, gentity_s::genericValue5, gentity_s::genericValue9, gentity_t, gitem_t, gentity_s::item, level, MASK_SOLID, entityShared_t::maxs, entityShared_t::mins, entityState_s::modelindex, gentity_s::nextthink, entityShared_t::ownerNum, gentity_s::physicsBounce, gentity_s::r, RegisterItem(), gentity_s::s, SpecialItemThink(), gentity_s::think, level_locals_t::time, TOSSED_ITEM_OWNER_NOTOUCH_DUR, TOSSED_ITEM_STAY_PERIOD, gentity_s::touch, Touch_Item(), and VectorSet.

Referenced by ItemUse_UseDisp().

01296 {
01297         RegisterItem( item );
01298         ent->item = item;
01299 
01300         //go away if no one wants me
01301         ent->genericValue5 = level.time + TOSSED_ITEM_STAY_PERIOD;
01302         ent->think = SpecialItemThink;
01303         ent->nextthink = level.time + 50;
01304         ent->clipmask = MASK_SOLID;
01305 
01306         ent->physicsBounce = 0.50;              // items are bouncy
01307         VectorSet (ent->r.mins, -8, -8, -0);
01308         VectorSet (ent->r.maxs, 8, 8, 16);
01309 
01310         ent->s.eType = ET_ITEM;
01311         ent->s.modelindex = ent->item - bg_itemlist;            // store item number in modelindex
01312 
01313         ent->r.contents = CONTENTS_TRIGGER;
01314         ent->touch = Touch_Item;
01315 
01316         //can't touch owner for x seconds
01317         ent->genericValue11 = ent->r.ownerNum;
01318         ent->genericValue10 = level.time + TOSSED_ITEM_OWNER_NOTOUCH_DUR;
01319 
01320         //so we know to remove when picked up, not respawn
01321         ent->genericValue9 = 1;
01322 
01323         //kind of a lame value to use, but oh well. This means don't
01324         //pick up this item clientside with prediction, because we
01325         //aren't sending over all the data necessary for the player
01326         //to know if he can.
01327         ent->s.brokenLimbs = 1;
01328 
01329         //since it uses my server-only physics
01330         ent->s.eFlags |= EF_CLIENTSMOOTH;
01331 }

void ItemUse_Binoculars gentity_t ent  ) 
 

Definition at line 472 of file g_items.c.

References gentity_s::client, gentity_t, level, gclient_s::ps, qfalse, level_locals_t::time, WEAPON_READY, playerState_s::weaponstate, playerState_s::zoomFov, playerState_s::zoomLocked, playerState_s::zoomMode, and playerState_s::zoomTime.

Referenced by ClientEvents(), and ClientThink_real().

00473 {
00474         if (!ent || !ent->client)
00475         {
00476                 return;
00477         }
00478 
00479         if (ent->client->ps.weaponstate != WEAPON_READY)
00480         { //So we can't fool it and reactivate while switching to the saber or something.
00481                 return;
00482         }
00483 
00484         /*
00485         if (ent->client->ps.weapon == WP_SABER)
00486         { //No.
00487                 return;
00488         }
00489         */
00490 
00491         if (ent->client->ps.zoomMode == 0) // not zoomed or currently zoomed with the disruptor
00492         {
00493                 ent->client->ps.zoomMode = 2;
00494                 ent->client->ps.zoomLocked = qfalse;
00495                 ent->client->ps.zoomFov = 40.0f;
00496         }
00497         else if (ent->client->ps.zoomMode == 2)
00498         {
00499                 ent->client->ps.zoomMode = 0;
00500                 ent->client->ps.zoomTime = level.time;
00501         }
00502 }

void ItemUse_Jetpack gentity_t ent  ) 
 

Definition at line 1201 of file g_items.c.

References gentity_s::client, EF_DEAD, playerState_s::eFlags, gentity_t, gentity_s::health, Jetpack_Off(), Jetpack_On(), JETPACK_TOGGLE_TIME, playerState_s::jetpackFuel, gclient_s::jetPackOn, gclient_s::jetPackToggleTime, level, PM_DEAD, playerState_s::pm_type, gclient_s::ps, STAT_HEALTH, playerState_s::stats, and level_locals_t::time.

Referenced by ClientEvents(), ClientThink_real(), and TryUse().

01202 {
01203         assert(ent && ent->client);
01204 
01205         if (ent->client->jetPackToggleTime >= level.time)
01206         {
01207                 return;
01208         }
01209 
01210         if (ent->health <= 0 ||
01211                 ent->client->ps.stats[STAT_HEALTH] <= 0 ||
01212                 (ent->client->ps.eFlags & EF_DEAD) ||
01213                 ent->client->ps.pm_type == PM_DEAD)
01214         { //can't use it when dead under any circumstances.
01215                 return;
01216         }
01217 
01218         if (!ent->client->jetPackOn &&
01219                 ent->client->ps.jetpackFuel < 5)
01220         { //too low on fuel to start it up
01221                 return;
01222         }
01223 
01224         if (ent->client->jetPackOn)
01225         {
01226                 Jetpack_Off(ent);
01227         }
01228         else
01229         {
01230                 Jetpack_On(ent);
01231         }
01232 
01233         ent->client->jetPackToggleTime = level.time + JETPACK_TOGGLE_TIME;
01234 }

void ItemUse_MedPack gentity_t ent  ) 
 

Definition at line 1159 of file g_items.c.

References gentity_t, and MAX_MEDPACK_HEAL_AMOUNT.

Referenced by ClientEvents(), and ClientThink_real().

01160 {
01161         MedPackGive(ent, MAX_MEDPACK_HEAL_AMOUNT);
01162 }

void ItemUse_MedPack_Big gentity_t ent  ) 
 

Definition at line 1154 of file g_items.c.

References gentity_t, and MAX_MEDPACK_BIG_HEAL_AMOUNT.

Referenced by ClientEvents(), and ClientThink_real().

01155 {
01156         MedPackGive(ent, MAX_MEDPACK_BIG_HEAL_AMOUNT);
01157 }

void ItemUse_Seeker gentity_t ent  ) 
 

Definition at line 1096 of file g_items.c.

References gentity_s::activator, gentity_s::client, d_siegeSeekerNPC, playerState_s::droneExistTime, playerState_s::droneFireTime, EF_SEEKERDRONE, playerState_s::eFlags, g_gametype, gentity_t, GT_SIEGE, vmCvar_t::integer, level, NPC_SpawnType(), NPCTEAM_ENEMY, NPCTEAM_NEUTRAL, NPCTEAM_PLAYER, NULL, entityState_s::number, entityState_s::owner, entityShared_t::ownerNum, gclient_s::playerTeam, gclient_s::ps, qfalse, gentity_s::r, gentity_s::s, gclient_s::sess, clientSession_t::sessionTeam, TEAM_BLUE, TEAM_RED, and level_locals_t::time.

Referenced by ClientEvents(), and ClientThink_real().

01097 {
01098         if ( g_gametype.integer == GT_SIEGE && d_siegeSeekerNPC.integer )
01099         {//actualy spawn a remote NPC
01100                 gentity_t *remote = NPC_SpawnType( ent, "remote", NULL, qfalse );
01101                 if ( remote && remote->client )
01102                 {//set it to my team
01103                         remote->s.owner = remote->r.ownerNum = ent->s.number;
01104                         remote->activator = ent;
01105                         if ( ent->client->sess.sessionTeam == TEAM_BLUE )
01106                         {
01107                                 remote->client->playerTeam = NPCTEAM_PLAYER;
01108                         }
01109                         else if ( ent->client->sess.sessionTeam == TEAM_RED )
01110                         {
01111                                 remote->client->playerTeam = NPCTEAM_ENEMY;
01112                         }
01113                         else
01114                         {
01115                                 remote->client->playerTeam = NPCTEAM_NEUTRAL;
01116                         }
01117                 }       
01118         }
01119         else
01120         {
01121                 ent->client->ps.eFlags |= EF_SEEKERDRONE;
01122                 ent->client->ps.droneExistTime = level.time + 30000;
01123                 ent->client->ps.droneFireTime = level.time + 1500;
01124         }
01125 }

void ItemUse_Sentry gentity_t ent  ) 
 

Definition at line 1014 of file g_items.c.

References entityShared_t::absmax, entityShared_t::absmin, gentity_s::alliedTeam, AngleVectors(), gentity_s::classname, gentity_s::client, gentity_s::clipmask, entityShared_t::contents, CONTENTS_SOLID, ENTITYNUM_NONE, ET_GENERAL, entityState_s::eType, playerState_s::fd, entityState_s::g2radius, g_gametype, G_ModelIndex(), G_SetOrigin(), G_Spawn(), gentity_s::genericValue2, gentity_s::genericValue3, gentity_s::genericValue4, gentity_s::genericValue5, gentity_s::genericValue8, gentity_t, GT_TEAM, vmCvar_t::integer, level, MASK_SOLID, entityShared_t::maxs, entityShared_t::mins, entityState_s::modelGhoul2, entityState_s::modelindex, gentity_s::nextthink, NULL, entityState_s::number, playerState_s::origin, entityState_s::owner, gentity_s::parent, PITCH, entityState_s::pos, gclient_s::ps, qtrue, gentity_s::r, ROLL, gentity_s::s, forcedata_s::sentryDeployed, SentryTouch(), gclient_s::sess, clientSession_t::sessionTeam, entityState_s::shouldtarget, entityState_s::solid, SP_PAS(), entityState_s::teamowner, level_locals_t::time, gentity_s::touch, TR_GRAVITY, trap_LinkEntity(), trajectory_t::trBase, trajectory_t::trTime, trajectory_t::trType, vec3_t, VectorCopy, VectorSet, playerState_s::viewangles, and YAW.

Referenced by ClientEvents(), and ClientThink_real().

01016 {
01017         vec3_t fwd, fwdorg;
01018         vec3_t yawonly;
01019         vec3_t mins, maxs;
01020         gentity_t *sentry;
01021 
01022         if (!ent || !ent->client)
01023         {
01024                 return;
01025         }
01026 
01027         VectorSet( mins, -8, -8, 0 );
01028         VectorSet( maxs, 8, 8, 24 );
01029 
01030 
01031         yawonly[ROLL] = 0;
01032         yawonly[PITCH] = 0;
01033         yawonly[YAW] = ent->client->ps.viewangles[YAW];
01034 
01035         AngleVectors(yawonly, fwd, NULL, NULL);
01036 
01037         fwdorg[0] = ent->client->ps.origin[0] + fwd[0]*64;
01038         fwdorg[1] = ent->client->ps.origin[1] + fwd[1]*64;
01039         fwdorg[2] = ent->client->ps.origin[2] + fwd[2]*64;
01040 
01041         sentry = G_Spawn();
01042 
01043         sentry->classname = "sentryGun";
01044         sentry->s.modelindex = G_ModelIndex("models/items/psgun.glm"); //replace ASAP
01045 
01046         sentry->s.g2radius = 30.0f;
01047         sentry->s.modelGhoul2 = 1;
01048 
01049         G_SetOrigin(sentry, fwdorg);
01050         sentry->parent = ent;
01051         sentry->r.contents = CONTENTS_SOLID;
01052         sentry->s.solid = 2;
01053         sentry->clipmask = MASK_SOLID;
01054         VectorCopy(mins, sentry->r.mins);
01055         VectorCopy(maxs, sentry->r.maxs);
01056         sentry->genericValue3 = ent->s.number;
01057         sentry->genericValue2 = ent->client->sess.sessionTeam; //so we can remove ourself if our owner changes teams
01058         sentry->r.absmin[0] = sentry->s.pos.trBase[0] + sentry->r.mins[0];
01059         sentry->r.absmin[1] = sentry->s.pos.trBase[1] + sentry->r.mins[1];
01060         sentry->r.absmin[2] = sentry->s.pos.trBase[2] + sentry->r.mins[2];
01061         sentry->r.absmax[0] = sentry->s.pos.trBase[0] + sentry->r.maxs[0];
01062         sentry->r.absmax[1] = sentry->s.pos.trBase[1] + sentry->r.maxs[1];
01063         sentry->r.absmax[2] = sentry->s.pos.trBase[2] + sentry->r.maxs[2];
01064         sentry->s.eType = ET_GENERAL;
01065         sentry->s.pos.trType = TR_GRAVITY;//STATIONARY;
01066         sentry->s.pos.trTime = level.time;
01067         sentry->touch = SentryTouch;
01068         sentry->nextthink = level.time;
01069         sentry->genericValue4 = ENTITYNUM_NONE; //genericValue4 used as enemy index
01070 
01071         sentry->genericValue5 = 1000;
01072 
01073         sentry->genericValue8 = level.time;
01074 
01075         sentry->alliedTeam = ent->client->sess.sessionTeam;
01076 
01077         ent->client->ps.fd.sentryDeployed = qtrue;
01078 
01079         trap_LinkEntity(sentry);
01080 
01081         sentry->s.owner = ent->s.number;
01082         sentry->s.shouldtarget = qtrue;
01083         if (g_gametype.integer >= GT_TEAM)
01084         {
01085                 sentry->s.teamowner = ent->client->sess.sessionTeam;
01086         }
01087         else
01088         {
01089                 sentry->s.teamowner = 16;
01090         }
01091 
01092         SP_PAS( sentry );
01093 }

void ItemUse_Shield gentity_t ent  ) 
 

Definition at line 504 of file g_items.c.

References gentity_t, and PlaceShield().

Referenced by ClientEvents(), and ClientThink_real().

00505 {
00506         PlaceShield(ent);
00507 }

void ItemUse_UseCloak gentity_t ent  ) 
 

Definition at line 1239 of file g_items.c.

References gentity_s::client, CLOAK_TOGGLE_TIME, playerState_s::cloakFuel, gclient_s::cloakToggleTime, EF_DEAD, playerState_s::eFlags, gentity_t, gentity_s::health, Jedi_Cloak(), Jedi_Decloak(), level, PM_DEAD, playerState_s::pm_type, playerState_s::powerups, gclient_s::ps, PW_CLOAKED, STAT_HEALTH, playerState_s::stats, and level_locals_t::time.

Referenced by ClientEvents().

01240 {
01241         assert(ent && ent->client);
01242 
01243         if (ent->client->cloakToggleTime >= level.time)
01244         {
01245                 return;
01246         }
01247 
01248         if (ent->health <= 0 ||
01249                 ent->client->ps.stats[STAT_HEALTH] <= 0 ||
01250                 (ent->client->ps.eFlags & EF_DEAD) ||
01251                 ent->client->ps.pm_type == PM_DEAD)
01252         { //can't use it when dead under any circumstances.
01253                 return;
01254         }
01255 
01256         if (!ent->client->ps.powerups[PW_CLOAKED] &&
01257                 ent->client->ps.cloakFuel < 5)
01258         { //too low on fuel to start it up
01259                 return;
01260         }
01261 
01262         if ( ent->client->ps.powerups[PW_CLOAKED] )
01263         {//decloak
01264                 Jedi_Decloak( ent );
01265         }
01266         else
01267         {//cloak
01268                 Jedi_Cloak( ent );
01269         }
01270 
01271         ent->client->cloakToggleTime = level.time + CLOAK_TOGGLE_TIME;
01272 }

void ItemUse_UseDisp gentity_t ent,
int  type
 

Definition at line 1353 of file g_items.c.

References AngleVectors(), BG_FindItem(), gentity_s::classname, gitem_s::classname, gentity_s::client, playerState_s::clientNum, entityShared_t::currentOrigin, DISP_AMMO_ITEM, DISP_HEALTH_ITEM, gentity_s::epVelocity, EV_LOCALTIMER, playerState_s::forceHandExtend, G_SetOrigin(), G_Spawn(), G_SpecialSpawnItem(), G_TempEntity(), gentity_t, gitem_t, HANDEXTEND_NONE, HI_HEALTHDISP, level, NULL, entityState_s::number, playerState_s::origin, entityState_s::origin, entityState_s::owner, entityShared_t::ownerNum, gclient_s::ps, gentity_s::r, gentity_s::s, level_locals_t::time, entityState_s::time, entityState_s::time2, TOSS_DEBOUNCE_TIME, gclient_s::tossableItemDebounce, trap_LinkEntity(), vec3_t, VectorCopy, VectorScale, playerState_s::viewangles, playerState_s::viewheight, and playerState_s::weaponTime.

Referenced by TryUse().

01354 {
01355         gitem_t *item = NULL;
01356         gentity_t *eItem;
01357 
01358         if (!ent->client ||
01359                 ent->client->tossableItemDebounce > level.time)
01360         { //can't use it again yet
01361                 return;
01362         }
01363 
01364         if (ent->client->ps.weaponTime > 0 ||
01365                 ent->client->ps.forceHandExtend != HANDEXTEND_NONE)
01366         { //busy doing something else
01367                 return;
01368         }
01369         
01370         ent->client->tossableItemDebounce = level.time + TOSS_DEBOUNCE_TIME;
01371         
01372         if (type == HI_HEALTHDISP)
01373         {
01374                 item = BG_FindItem(DISP_HEALTH_ITEM);
01375         }
01376         else
01377         {
01378                 item = BG_FindItem(DISP_AMMO_ITEM);
01379         }
01380 
01381         if (item)
01382         {
01383                 vec3_t fwd, pos;
01384                 gentity_t       *te;
01385 
01386                 eItem = G_Spawn();
01387                 eItem->r.ownerNum = ent->s.number;
01388                 eItem->classname = item->classname;
01389 
01390                 VectorCopy(ent->client->ps.origin, pos);
01391                 pos[2] += ent->client->ps.viewheight;
01392 
01393                 G_SetOrigin(eItem, pos);
01394                 VectorCopy(eItem->r.currentOrigin, eItem->s.origin);
01395                 trap_LinkEntity(eItem);
01396 
01397                 G_SpecialSpawnItem(eItem, item);
01398 
01399                 AngleVectors(ent->client->ps.viewangles, fwd, NULL, NULL);
01400                 VectorScale(fwd, 128.0f, eItem->epVelocity);
01401                 eItem->epVelocity[2] = 16.0f;
01402 
01403         //      G_SetAnim( ent, NULL, SETANIM_TORSO, BOTH_THERMAL_THROW, SETANIM_FLAG_OVERRIDE|SETANIM_FLAG_HOLD, 0 );
01404 
01405                 te = G_TempEntity( ent->client->ps.origin, EV_LOCALTIMER );
01406                 te->s.time = level.time;
01407                 te->s.time2 = TOSS_DEBOUNCE_TIME;
01408                 te->s.owner = ent->client->ps.clientNum;
01409         }
01410 }

void ItemUse_UseEWeb gentity_t ent  ) 
 

Definition at line 1984 of file g_items.c.

References gentity_s::client, playerState_s::emplacedIndex, EWeb_Create(), EWEB_USE_DEBOUNCE, EWebDisattach(), gclient_s::ewebIndex, gclient_s::ewebTime, playerState_s::forceHandExtend, g_entities, gentity_t, HANDEXTEND_NONE, level, entityState_s::number, gclient_s::ps, gentity_s::s, level_locals_t::time, and playerState_s::weaponTime.

Referenced by ClientEvents(), and ClientThink_real().

01985 {
01986         if (ent->client->ewebTime > level.time)
01987         { //can't use again yet
01988                 return;
01989         }
01990 
01991         if (ent->client->ps.weaponTime > 0 ||
01992                 ent->client->ps.forceHandExtend != HANDEXTEND_NONE)
01993         { //busy doing something else
01994                 return;
01995         }
01996 
01997         if (ent->client->ps.emplacedIndex && !ent->client->ewebIndex)
01998         { //using an emplaced gun already that isn't our own e-web
01999                 return;
02000         }
02001 
02002         if (ent->client->ewebIndex)
02003         { //put it away
02004                 EWebDisattach(ent, &g_entities[ent->client->ewebIndex]);
02005         }
02006         else
02007         { //create it
02008                 gentity_t *eweb = EWeb_Create(ent);
02009 
02010                 if (eweb)
02011                 { //if it's null the thing couldn't spawn (probably no room)
02012                         ent->client->ewebIndex = eweb->s.number;
02013                         ent->client->ps.emplacedIndex = eweb->s.number;
02014                 }
02015         }
02016 
02017         ent->client->ewebTime = level.time + EWEB_USE_DEBOUNCE;
02018 }

void Jedi_Cloak gentity_t self  ) 
 

Definition at line 799 of file NPC_AI_Jedi.c.

00800 {
00801         if ( self )
00802         {
00803                 self->flags |= FL_NOTARGET;
00804                 if ( self->client )
00805                 {
00806                         if ( !self->client->ps.powerups[PW_CLOAKED] )
00807                         {//cloak
00808                                 self->client->ps.powerups[PW_CLOAKED] = Q3_INFINITE;
00809 
00810                                 //FIXME: debounce attacks?
00811                                 //FIXME: temp sound
00812                                 G_Sound( self, CHAN_ITEM, G_SoundIndex("sound/chars/shadowtrooper/cloak.wav") );
00813                         }
00814                 }
00815         }
00816 }

void Jedi_Decloak gentity_t self  ) 
 

Definition at line 818 of file NPC_AI_Jedi.c.

00819 {
00820         if ( self )
00821         {
00822                 self->flags &= ~FL_NOTARGET;
00823                 if ( self->client )
00824                 {
00825                         if ( self->client->ps.powerups[PW_CLOAKED] )
00826                         {//Uncloak
00827                                 self->client->ps.powerups[PW_CLOAKED] = 0;
00828 
00829                                 G_Sound( self, CHAN_ITEM, G_SoundIndex("sound/chars/shadowtrooper/decloak.wav") );
00830                         }
00831                 }
00832         }
00833 }

void Jetpack_Off gentity_t ent  ) 
 

Definition at line 1165 of file g_items.c.

References gentity_s::client, gentity_t, gclient_s::jetPackOn, and qfalse.

Referenced by DoGripAction(), G_Damage(), G_RunFrame(), hurt_touch(), ItemUse_Jetpack(), and player_die().

01166 { //create effects?
01167         assert(ent && ent->client);
01168 
01169         if (!ent->client->jetPackOn)
01170         { //aready off
01171                 return;
01172         }
01173 
01174         ent->client->jetPackOn = qfalse;
01175 }

void Jetpack_On gentity_t ent  ) 
 

Definition at line 1177 of file g_items.c.

References CHAN_AUTO, gentity_s::client, playerState_s::fallingToDeath, playerState_s::fd, forcedata_s::forceGripBeingGripped, G_Sound(), G_SoundIndex(), gentity_t, gclient_s::jetPackOn, level, gclient_s::ps, qtrue, and level_locals_t::time.

Referenced by ItemUse_Jetpack().

01178 { //create effects?
01179         assert(ent && ent->client);
01180 
01181         if (ent->client->jetPackOn)
01182         { //aready on
01183                 return;
01184         }
01185 
01186         if (ent->client->ps.fd.forceGripBeingGripped >= level.time)
01187         { //can't turn on during grip interval
01188                 return;
01189         }
01190 
01191         if (ent->client->ps.fallingToDeath)
01192         { //too late!
01193                 return;
01194         }
01195 
01196         G_Sound(ent, CHAN_AUTO, G_SoundIndex("sound/boba/JETON"));
01197 
01198         ent->client->jetPackOn = qtrue;
01199 }

gentity_t* LaunchItem gitem_t item,
vec3_t  origin,
vec3_t  velocity
 

Definition at line 2658 of file g_items.c.

References entityState_s::angles, bg_itemlist, gentity_s::classname, gitem_s::classname, entityShared_t::contents, CONTENTS_TRIGGER, droppedBlueFlag, droppedRedFlag, EF_DROPPEDWEAPON, entityState_s::eFlags, ET_ITEM, entityState_s::eType, FL_BOUNCE_HALF, FL_DROPPED_ITEM, gentity_s::flags, G_FreeEntity(), g_gametype, G_SetOrigin(), G_Spawn(), gentity_t, gitem_s::giTag, gitem_t, gitem_s::giType, GT_CTF, GT_CTY, vmCvar_t::integer, IT_POWERUP, IT_TEAM, IT_WEAPON, gentity_s::item, ITEM_RADIUS, level, entityShared_t::maxs, entityShared_t::mins, entityState_s::modelindex, entityState_s::modelindex2, gentity_s::nextthink, gentity_s::physicsObject, PITCH, entityState_s::pos, qtrue, gentity_s::r, ROLL, gentity_s::s, strcmp(), Team_CheckDroppedItem(), Team_DroppedFlagThink(), gentity_s::think, level_locals_t::time, gentity_s::touch, Touch_Item(), TR_GRAVITY, trap_LinkEntity(), trajectory_t::trDelta, trajectory_t::trTime, trajectory_t::trType, vec3_t, vectoangles(), VectorCopy, VectorSet, WP_BOWCASTER, WP_DET_PACK, WP_THERMAL, and WP_TRIP_MINE.

Referenced by Drop_Item(), and TossClientWeapon().

02658                                                                        {
02659         gentity_t       *dropped;
02660 
02661         dropped = G_Spawn();
02662 
02663         dropped->s.eType = ET_ITEM;
02664         dropped->s.modelindex = item - bg_itemlist;     // store item number in modelindex
02665         if (dropped->s.modelindex < 0)
02666         {
02667                 dropped->s.modelindex = 0;
02668         }
02669         dropped->s.modelindex2 = 1; // This is non-zero is it's a dropped item
02670 
02671         dropped->classname = item->classname;
02672         dropped->item = item;
02673         VectorSet (dropped->r.mins, -ITEM_RADIUS, -ITEM_RADIUS, -ITEM_RADIUS);
02674         VectorSet (dropped->r.maxs, ITEM_RADIUS, ITEM_RADIUS, ITEM_RADIUS);
02675 
02676         dropped->r.contents = CONTENTS_TRIGGER;
02677 
02678         dropped->touch = Touch_Item;
02679 
02680         G_SetOrigin( dropped, origin );
02681         dropped->s.pos.trType = TR_GRAVITY;
02682         dropped->s.pos.trTime = level.time;
02683         VectorCopy( velocity, dropped->s.pos.trDelta );
02684 
02685         dropped->flags |= FL_BOUNCE_HALF;
02686         if ((g_gametype.integer == GT_CTF || g_gametype.integer == GT_CTY) && item->giType == IT_TEAM) { // Special case for CTF flags
02687                 dropped->think = Team_DroppedFlagThink;
02688                 dropped->nextthink = level.time + 30000;
02689                 Team_CheckDroppedItem( dropped );
02690 
02691                 //rww - so bots know
02692                 if (strcmp(dropped->classname, "team_CTF_redflag") == 0)
02693                 {
02694                         droppedRedFlag = dropped;
02695                 }
02696                 else if (strcmp(dropped->classname, "team_CTF_blueflag") == 0)
02697                 {
02698                         droppedBlueFlag = dropped;
02699                 }
02700         } else { // auto-remove after 30 seconds
02701                 dropped->think = G_FreeEntity;
02702                 dropped->nextthink = level.time + 30000;
02703         }
02704 
02705         dropped->flags = FL_DROPPED_ITEM;
02706 
02707         if (item->giType == IT_WEAPON || item->giType == IT_POWERUP)
02708         {
02709                 dropped->s.eFlags |= EF_DROPPEDWEAPON;
02710         }
02711 
02712         vectoangles(velocity, dropped->s.angles);
02713         dropped->s.angles[PITCH] = 0;
02714 
02715         if (item->giTag == WP_TRIP_MINE ||
02716                 item->giTag == WP_DET_PACK)
02717         {
02718                 dropped->s.angles[PITCH] = -90;
02719         }
02720 
02721         if (item->giTag != WP_BOWCASTER &&
02722                 item->giTag != WP_DET_PACK &&
02723                 item->giTag != WP_THERMAL)
02724         {
02725                 dropped->s.angles[ROLL] = -90;
02726         }
02727 
02728         dropped->physicsObject = qtrue;
02729 
02730         trap_LinkEntity (dropped);
02731 
02732         return dropped;
02733 }

gentity_t * NPC_SpawnType gentity_t ent,
char *  npc_type,
char *  targetname,
qboolean  isVehicle
 

Definition at line 3866 of file NPC_spawn.c.

References entityState_s::angles, AngleVectors(), gentity_s::classname, gentity_s::client, Com_Printf(), gentity_s::count, entityShared_t::currentOrigin, gentity_s::delay, trace_t::endpos, FRAMETIME, G_FreeEntity(), G_NewString(), G_SetOrigin(), G_Spawn(), gentity_t, level, MASK_SOLID, gentity_s::nextthink, NPC_ATST_Precache(), NPC_GalakMech_Precache(), NPC_Gonk_Precache(), NPC_Howler_Precache(), NPC_Interrogator_Precache(), NPC_Mark1_Precache(), NPC_Mark2_Precache(), NPC_MineMonster_Precache(), NPC_Mouse_Precache(), NPC_Probe_Precache(), NPC_Protocol_Precache(), NPC_R2D2_Precache(), NPC_R5D2_Precache(), NPC_Remote_Precache(), NPC_Seeker_Precache(), NPC_Sentry_Precache(), NPC_ShadowTrooper_Precache(), NPC_Spawn_Do(), gentity_s::NPC_targetname, gentity_s::NPC_type, NPC_Wampa_Precache(), NULL, entityState_s::origin, gclient_s::ps, Q_stricmp(), Q_strncmp(), gentity_s::r, gentity_s::s, S_COLOR_RED, S_COLOR_WHITE, gentity_s::think, level_locals_t::time, trap_LinkEntity(), trap_Trace(), vec3_t, VectorCopy, VectorMA, VectorNormalize(), and playerState_s::viewangles.

03867 {
03868         gentity_t               *NPCspawner = G_Spawn();
03869         vec3_t                  forward, end;
03870         trace_t                 trace;
03871 
03872         if(!NPCspawner)
03873         {
03874                 Com_Printf( S_COLOR_RED"NPC_Spawn Error: Out of entities!\n" );
03875                 return NULL;
03876         }
03877 
03878         NPCspawner->think = G_FreeEntity;
03879         NPCspawner->nextthink = level.time + FRAMETIME;
03880         
03881         if ( !npc_type )
03882         {
03883                 return NULL;
03884         }
03885 
03886         if (!npc_type[0])
03887         {
03888                 Com_Printf( S_COLOR_RED"Error, expected one of:\n"S_COLOR_WHITE" NPC spawn [NPC type (from ext_data/NPCs)]\n NPC spawn vehicle [VEH type (from ext_data/vehicles)]\n" );
03889                 return NULL;
03890         }
03891 
03892         if ( !ent || !ent->client )
03893         {//screw you, go away
03894                 return NULL;
03895         }
03896 
03897         //rwwFIXMEFIXME: Care about who is issuing this command/other clients besides 0?
03898         //Spawn it at spot of first player
03899         //FIXME: will gib them!
03900         AngleVectors(ent->client->ps.viewangles, forward, NULL, NULL);
03901         VectorNormalize(forward);
03902         VectorMA(ent->r.currentOrigin, 64, forward, end);
03903         trap_Trace(&trace, ent->r.currentOrigin, NULL, NULL, end, 0, MASK_SOLID);
03904         VectorCopy(trace.endpos, end);
03905         end[2] -= 24;
03906         trap_Trace(&trace, trace.endpos, NULL, NULL, end, 0, MASK_SOLID);
03907         VectorCopy(trace.endpos, end);
03908         end[2] += 24;
03909         G_SetOrigin(NPCspawner, end);
03910         VectorCopy(NPCspawner->r.currentOrigin, NPCspawner->s.origin);
03911         //set the yaw so that they face away from player
03912         NPCspawner->s.angles[1] = ent->client->ps.viewangles[1];
03913 
03914         trap_LinkEntity(NPCspawner);
03915 
03916         NPCspawner->NPC_type = G_NewString( npc_type );
03917 
03918         if ( targetname )
03919         {
03920                 NPCspawner->NPC_targetname = G_NewString(targetname);
03921         }
03922 
03923         NPCspawner->count = 1;
03924 
03925         NPCspawner->delay = 0;
03926 
03927         //NPCspawner->spawnflags |= SFB_NOTSOLID;
03928 
03929         //NPCspawner->playerTeam = TEAM_FREE;
03930         //NPCspawner->behaviorSet[BSET_SPAWN] = "common/guard";
03931         
03932         if ( isVehicle )
03933         {
03934                 NPCspawner->classname = "NPC_Vehicle";
03935         }
03936 
03937         //call precache funcs for James' builds
03938         if ( !Q_stricmp( "gonk", NPCspawner->NPC_type))
03939         {
03940                 NPC_Gonk_Precache();
03941         }
03942         else if ( !Q_stricmp( "mouse", NPCspawner->NPC_type))
03943         {
03944                 NPC_Mouse_Precache();
03945         }
03946         else if ( !Q_strncmp( "r2d2", NPCspawner->NPC_type, 4))
03947         {
03948                 NPC_R2D2_Precache();
03949         }
03950         else if ( !Q_stricmp( "atst", NPCspawner->NPC_type))
03951         {
03952                 NPC_ATST_Precache();
03953         }
03954         else if ( !Q_strncmp( "r5d2", NPCspawner->NPC_type, 4))
03955         {
03956                 NPC_R5D2_Precache();
03957         }
03958         else if ( !Q_stricmp( "mark1", NPCspawner->NPC_type))
03959         {
03960                 NPC_Mark1_Precache();
03961         }
03962         else if ( !Q_stricmp( "mark2", NPCspawner->NPC_type))
03963         {
03964                 NPC_Mark2_Precache();
03965         }
03966         else if ( !Q_stricmp( "interrogator", NPCspawner->NPC_type))
03967         {
03968                 NPC_Interrogator_Precache(NULL);
03969         }
03970         else if ( !Q_stricmp( "probe", NPCspawner->NPC_type))
03971         {
03972                 NPC_Probe_Precache();
03973         }
03974         else if ( !Q_stricmp( "seeker", NPCspawner->NPC_type))
03975         {
03976                 NPC_Seeker_Precache();
03977         }
03978         else if ( !Q_stricmp( "remote", NPCspawner->NPC_type))
03979         {
03980                 NPC_Remote_Precache();
03981         }
03982         else if ( !Q_strncmp( "shadowtrooper", NPCspawner->NPC_type, 13 ) )
03983         {
03984                 NPC_ShadowTrooper_Precache();
03985         }
03986         else if ( !Q_stricmp( "minemonster", NPCspawner->NPC_type ))
03987         {
03988                 NPC_MineMonster_Precache();
03989         }
03990         else if ( !Q_stricmp( "howler", NPCspawner->NPC_type ))
03991         {
03992                 NPC_Howler_Precache();
03993         }
03994         else if ( !Q_stricmp( "sentry", NPCspawner->NPC_type ))
03995         {
03996                 NPC_Sentry_Precache();
03997         }
03998         else if ( !Q_stricmp( "protocol", NPCspawner->NPC_type ))
03999         {
04000                 NPC_Protocol_Precache();
04001         }
04002         else if ( !Q_stricmp( "galak_mech", NPCspawner->NPC_type ))
04003         {
04004                 NPC_GalakMech_Precache();
04005         }
04006         else if ( !Q_stricmp( "wampa", NPCspawner->NPC_type ))
04007         {
04008                 NPC_Wampa_Precache();
04009         }
04010 
04011         return (NPC_Spawn_Do( NPCspawner ));
04012 }

void pas_adjust_enemy gentity_t ent  ) 
 

Definition at line 642 of file g_items.c.

References gentity_s::aimDebounceTime, trace_t::allsolid, gentity_s::bounceCount, CHAN_BODY, gentity_s::client, entityShared_t::currentOrigin, gentity_s::enemy, trace_t::entityNum, trace_t::fraction, G_Sound(), G_SoundIndex(), gentity_t, gentity_s::health, level, MASK_SHOT, NULL, entityState_s::number, playerState_s::origin, entityState_s::pos, gclient_s::ps, qboolean, qfalse, qtrue, gentity_s::r, random, gentity_s::s, trace_t::startsolid, level_locals_t::time, trap_Trace(), trajectory_t::trBase, vec3_t, and VectorCopy.

Referenced by pas_think().

00644 {
00645         trace_t tr;
00646         qboolean keep = qtrue;
00647 
00648         if ( ent->enemy->health <= 0 )
00649         {
00650                 keep = qfalse;
00651         }
00652         else
00653         {
00654                 vec3_t          org, org2;
00655 
00656                 VectorCopy(ent->s.pos.trBase, org2);
00657 
00658                 if ( ent->enemy->client )
00659                 {
00660                         VectorCopy( ent->enemy->client->ps.origin, org );
00661                         org[2] -= 15;
00662                 }
00663                 else
00664                 {
00665                         VectorCopy( ent->enemy->r.currentOrigin, org );
00666                 }
00667 
00668                 trap_Trace( &tr, org2, NULL, NULL, org, ent->s.number, MASK_SHOT );
00669 
00670                 if ( tr.allsolid || tr.startsolid || tr.fraction < 0.9f || tr.entityNum == ent->s.number )
00671                 {
00672                         if (tr.entityNum != ent->enemy->s.number)
00673                         {
00674                                 // trace failed
00675                                 keep = qfalse;
00676                         }
00677                 }
00678         }
00679 
00680         if ( keep )
00681         {
00682                 //ent->bounceCount = level.time + 500 + random() * 150;
00683         }
00684         else if ( ent->bounceCount < level.time && ent->enemy ) // don't ping pong on and off
00685         {
00686                 ent->enemy = NULL;
00687                 // shut-down sound
00688                 G_Sound( ent, CHAN_BODY, G_SoundIndex( "sound/chars/turret/shutdown.wav" ));
00689         
00690                 ent->bounceCount = level.time + 500 + random() * 150;
00691 
00692                 // make turret play ping sound for 5 seconds
00693                 ent->aimDebounceTime = level.time + 5000;
00694         }
00695 }

void pas_fire gentity_t ent  ) 
 

Definition at line 521 of file g_items.c.

References gentity_s::client, entityShared_t::currentOrigin, gentity_s::enemy, g_entities, G_RunObject(), gentity_s::genericValue3, gentity_t, MOD_SENTRY, playerState_s::origin, gclient_s::ps, qfalse, gentity_s::r, vec3_t, VectorCopy, VectorNormalize(), VectorSubtract, and WP_FireTurretMissile().

Referenced by pas_think().

00523 {
00524         vec3_t fwd, myOrg, enOrg;
00525 
00526         VectorCopy(ent->r.currentOrigin, myOrg);
00527         myOrg[2] += 24;
00528 
00529         VectorCopy(ent->enemy->client->ps.origin, enOrg);
00530         enOrg[2] += 24;
00531 
00532         VectorSubtract(enOrg, myOrg, fwd);
00533         VectorNormalize(fwd);
00534         
00535         myOrg[0] += fwd[0]*16;
00536         myOrg[1] += fwd[1]*16;
00537         myOrg[2] += fwd[2]*16;
00538 
00539         WP_FireTurretMissile(&g_entities[ent->genericValue3], myOrg, fwd, qfalse, 10, 2300, MOD_SENTRY, ent );
00540 
00541         G_RunObject(ent);
00542 }

void pas_think gentity_t ent  ) 
 

Definition at line 708 of file g_items.c.

References entityShared_t::absmax, AngleNormalize360(), AngleSubtract(), gentity_s::attackDebounceTime, entityState_s::bolt2, CHAN_BODY, gentity_s::client, entityShared_t::contents, CONTENTS_SOLID, gentity_s::count, entityShared_t::currentOrigin, gentity_s::damage, gentity_s::enemy, ENTITYNUM_NONE, fabs(), entityState_s::fireflag, FRAMETIME, g_entities, G_FreeEntity(), G_Sound(), G_SoundIndex(), gentity_s::genericValue2, gentity_s::genericValue3, gentity_s::genericValue8, gentity_t, gentity_s::health, level, entityState_s::loopIsSoundset, entityState_s::loopSound, MAX_CLIENTS, MAX_GENTITIES, entityShared_t::maxs, entityShared_t::mins, gentity_s::nextthink, NULL, entityState_s::number, playerState_s::origin, pas_adjust_enemy(), pas_fire(), PITCH, gclient_s::ps, qboolean, qfalse, qtrue, gentity_s::r, gentity_s::random, gentity_s::s, sentryExpire(), sin(), gentity_s::speed, gentity_s::think, level_locals_t::time, trap_EntitiesInBox(), TURRET_DEATH_DELAY, TURRET_LIFETIME, vec3_t, vectoangles(), VectorCopy, VectorSet, VectorSubtract, and YAW.

Referenced by SP_PAS().

00710 {
00711         qboolean        moved;
00712         float           diffYaw, diffPitch;
00713         vec3_t          enemyDir, org;
00714         vec3_t          frontAngles, backAngles;
00715         vec3_t          desiredAngles;
00716         int                     iEntityList[MAX_GENTITIES];
00717         int                     numListedEntities;
00718         int                     i = 0;
00719         qboolean        clTrapped = qfalse;
00720         vec3_t          testMins, testMaxs;
00721 
00722         testMins[0] = ent->r.currentOrigin[0] + ent->r.mins[0]+4;
00723         testMins[1] = ent->r.currentOrigin[1] + ent->r.mins[1]+4;
00724         testMins[2] = ent->r.currentOrigin[2] + ent->r.mins[2]+4;
00725 
00726         testMaxs[0] = ent->r.currentOrigin[0] + ent->r.maxs[0]-4;
00727         testMaxs[1] = ent->r.currentOrigin[1] + ent->r.maxs[1]-4;
00728         testMaxs[2] = ent->r.currentOrigin[2] + ent->r.maxs[2]-4;
00729 
00730         numListedEntities = trap_EntitiesInBox( testMins, testMaxs, iEntityList, MAX_GENTITIES );
00731 
00732         while (i < numListedEntities)
00733         {
00734                 if (iEntityList[i] < MAX_CLIENTS)
00735                 { //client stuck inside me. go nonsolid.
00736                         int clNum = iEntityList[i];
00737 
00738                         numListedEntities = trap_EntitiesInBox( g_entities[clNum].r.absmin, g_entities[clNum].r.absmax, iEntityList, MAX_GENTITIES );
00739 
00740                         i = 0;
00741                         while (i < numListedEntities)
00742                         {
00743                                 if (iEntityList[i] == ent->s.number)
00744                                 {
00745                                         clTrapped = qtrue;
00746                                         break;
00747                                 }
00748                                 i++;
00749                         }
00750                         break;
00751                 }
00752 
00753                 i++;
00754         }
00755 
00756         if (clTrapped)
00757         {
00758                 ent->r.contents = 0;
00759                 ent->s.fireflag = 0;
00760                 ent->nextthink = level.time + FRAMETIME;
00761                 return;
00762         }
00763         else
00764         {
00765                 ent->r.contents = CONTENTS_SOLID;
00766         }
00767 
00768         if (!g_entities[ent->genericValue3].inuse || !g_entities[ent->genericValue3].client ||
00769                 g_entities[ent->genericValue3].client->sess.sessionTeam != ent->genericValue2)
00770         {
00771                 ent->think = G_FreeEntity;
00772                 ent->nextthink = level.time;
00773                 return;
00774         }
00775 
00776 //      G_RunObject(ent);
00777 
00778         if ( !ent->damage )
00779         {
00780                 ent->damage = 1;
00781                 ent->nextthink = level.time + FRAMETIME;
00782                 return;
00783         }
00784 
00785         if ((ent->genericValue8+TURRET_LIFETIME) < level.time)
00786         {
00787                 G_Sound( ent, CHAN_BODY, G_SoundIndex( "sound/chars/turret/shutdown.wav" ));
00788                 ent->s.bolt2 = ENTITYNUM_NONE;
00789                 ent->s.fireflag = 2;
00790 
00791                 ent->think = sentryExpire;
00792                 ent->nextthink = level.time + TURRET_DEATH_DELAY;
00793                 return;
00794         }
00795 
00796         ent->nextthink = level.time + FRAMETIME;
00797 
00798         if ( ent->enemy )
00799         {
00800                 // make sure that the enemy is still valid
00801                 pas_adjust_enemy( ent );
00802         }
00803 
00804         if (ent->enemy)
00805         {
00806                 if (!ent->enemy->client)
00807                 {
00808                         ent->enemy = NULL;
00809                 }
00810                 else if (ent->enemy->s.number == ent->s.number)
00811                 {
00812                         ent->enemy = NULL;
00813                 }
00814                 else if (ent->enemy->health < 1)
00815                 {
00816                         ent->enemy = NULL;
00817                 }
00818         }
00819 
00820         if ( !ent->enemy )
00821         {
00822                 pas_find_enemies( ent );
00823         }
00824 
00825         if (ent->enemy)
00826         {
00827                 ent->s.bolt2 = ent->enemy->s.number;
00828         }
00829         else
00830         {
00831                 ent->s.bolt2 = ENTITYNUM_NONE;
00832         }
00833 
00834         moved = qfalse;
00835         diffYaw = 0.0f; diffPitch = 0.0f;
00836 
00837         ent->speed = AngleNormalize360( ent->speed );
00838         ent->random = AngleNormalize360( ent->random );
00839 
00840         if ( ent->enemy )
00841         {
00842                 // ...then we'll calculate what new aim adjustments we should attempt to make this frame
00843                 // Aim at enemy
00844                 if ( ent->enemy->client )
00845                 {
00846                         VectorCopy( ent->enemy->client->ps.origin, org );
00847                 }
00848                 else
00849                 {
00850                         VectorCopy( ent->enemy->r.currentOrigin, org );
00851                 }
00852 
00853                 VectorSubtract( org, ent->r.currentOrigin, enemyDir );
00854                 vectoangles( enemyDir, desiredAngles );
00855 
00856                 diffYaw = AngleSubtract( ent->speed, desiredAngles[YAW] );
00857                 diffPitch = AngleSubtract( ent->random, desiredAngles[PITCH] );
00858         }
00859         else
00860         {
00861                 // no enemy, so make us slowly sweep back and forth as if searching for a new one
00862                 diffYaw = sin( level.time * 0.0001f + ent->count ) * 2.0f;
00863         }
00864 
00865         if ( fabs(diffYaw) > 0.25f )
00866         {
00867                 moved = qtrue;
00868 
00869                 if ( fabs(diffYaw) > 10.0f )
00870                 {
00871                         // cap max speed
00872                         ent->speed += (diffYaw > 0.0f) ? -10.0f : 10.0f;
00873                 }
00874                 else
00875                 {
00876                         // small enough
00877                         ent->speed -= diffYaw;
00878                 }
00879         }
00880 
00881 
00882         if ( fabs(diffPitch) > 0.25f )
00883         {
00884                 moved = qtrue;
00885 
00886                 if ( fabs(diffPitch) > 4.0f )
00887                 {
00888                         // cap max speed
00889                         ent->random += (diffPitch > 0.0f) ? -4.0f : 4.0f;
00890                 }
00891                 else
00892                 {
00893                         // small enough
00894                         ent->random -= diffPitch;
00895                 }
00896         }
00897 
00898         // the bone axes are messed up, so hence some dumbness here
00899         VectorSet( frontAngles, -ent->random, 0.0f, 0.0f );
00900         VectorSet( backAngles, 0.0f, 0.0f, ent->speed );
00901 
00902         if ( moved )
00903         {
00904         //ent->s.loopSound = G_SoundIndex( "sound/chars/turret/move.wav" );
00905         }
00906         else
00907         {
00908                 ent->s.loopSound = 0;
00909                 ent->s.loopIsSoundset = qfalse;
00910         }
00911 
00912         if ( ent->enemy && ent->attackDebounceTime < level.time )
00913         {
00914                 ent->count--;
00915 
00916                 if ( ent->count )
00917                 {
00918                         pas_fire( ent );
00919                         ent->s.fireflag = 1;
00920                         ent->attackDebounceTime = level.time + 200;
00921                 }
00922                 else
00923                 {
00924                         //ent->nextthink = 0;
00925                         G_Sound( ent, CHAN_BODY, G_SoundIndex( "sound/chars/turret/shutdown.wav" ));
00926                         ent->s.bolt2 = ENTITYNUM_NONE;
00927                         ent->s.fireflag = 2;
00928 
00929                         ent->think = sentryExpire;
00930                         ent->nextthink = level.time + TURRET_DEATH_DELAY;
00931                 }
00932         }
00933         else
00934         {
00935                 ent->s.fireflag = 0;
00936         }
00937 }

int Pickup_Ammo gentity_t ent,
gentity_t other
 

Definition at line 2130 of file g_items.c.

References Add_Ammo(), adjustRespawnTime(), AMMO_BLASTER, AMMO_DETPACK, AMMO_METAL_BOLTS, AMMO_POWERCELL, AMMO_ROCKETS, AMMO_THERMAL, AMMO_TRIPMINE, gentity_s::client, gentity_s::count, g_gametype, gentity_t, gitem_s::giTag, gitem_s::giType, GT_SIEGE, vmCvar_t::integer, gentity_s::item, gclient_s::ps, gitem_s::quantity, RESPAWN_AMMO, STAT_WEAPONS, playerState_s::stats, WP_DET_PACK, WP_THERMAL, and WP_TRIP_MINE.

Referenced by Touch_Item().

02131 {
02132         int             quantity;
02133 
02134         if ( ent->count ) {
02135                 quantity = ent->count;
02136         } else {
02137                 quantity = ent->item->quantity;
02138         }
02139 
02140         if (ent->item->giTag == -1)
02141         { //an ammo_all, give them a bit of everything
02142                 if ( g_gametype.integer == GT_SIEGE )   // complaints that siege tech's not giving enough ammo.  Does anything else use ammo all?
02143                 {
02144                         Add_Ammo(other, AMMO_BLASTER, 100);
02145                         Add_Ammo(other, AMMO_POWERCELL, 100);
02146                         Add_Ammo(other, AMMO_METAL_BOLTS, 100);
02147                         Add_Ammo(other, AMMO_ROCKETS, 5);
02148                         if (other->client->ps.stats[STAT_WEAPONS] & (1<<WP_DET_PACK))
02149                         {
02150                                 Add_Ammo(other, AMMO_DETPACK, 2);
02151                         }
02152                         if (other->client->ps.stats[STAT_WEAPONS] & (1<<WP_THERMAL))
02153                         {
02154                                 Add_Ammo(other, AMMO_THERMAL, 2);
02155                         }
02156                         if (other->client->ps.stats[STAT_WEAPONS] & (1<<WP_TRIP_MINE))
02157                         {
02158                                 Add_Ammo(other, AMMO_TRIPMINE, 2);
02159                         }
02160                 }
02161                 else
02162                 {
02163                         Add_Ammo(other, AMMO_BLASTER, 50);
02164                         Add_Ammo(other, AMMO_POWERCELL, 50);
02165                         Add_Ammo(other, AMMO_METAL_BOLTS, 50);
02166                         Add_Ammo(other, AMMO_ROCKETS, 2);
02167                 }
02168         }
02169         else
02170         {
02171                 Add_Ammo (other, ent->item->giTag, quantity);
02172         }
02173 
02174         return adjustRespawnTime(RESPAWN_AMMO, ent->item->giType, ent->item->giTag);
02175 }

int Pickup_Armor gentity_t ent,
gentity_t other
 

Definition at line 2270 of file g_items.c.

References adjustRespawnTime(), gentity_s::client, gentity_t, gitem_s::giTag, gitem_s::giType, gentity_s::item, gclient_s::ps, gitem_s::quantity, RESPAWN_ARMOR, STAT_ARMOR, STAT_MAX_HEALTH, and playerState_s::stats.

Referenced by Touch_Item().

02271 {
02272         other->client->ps.stats[STAT_ARMOR] += ent->item->quantity;
02273         if ( other->client->ps.stats[STAT_ARMOR] > other->client->ps.stats[STAT_MAX_HEALTH] * ent->item->giTag ) 
02274         {
02275                 other->client->ps.stats[STAT_ARMOR] = other->client->ps.stats[STAT_MAX_HEALTH] * ent->item->giTag;
02276         }
02277 
02278         return adjustRespawnTime(RESPAWN_ARMOR, ent->item->giType, ent->item->giTag);
02279 }

int Pickup_Health gentity_t ent,
gentity_t other
 

Definition at line 2237 of file g_items.c.

References adjustRespawnTime(), gentity_s::client, gentity_s::count, gentity_t, gitem_s::giTag, gitem_s::giType, gentity_s::health, gentity_s::item, gclient_s::ps, gitem_s::quantity, RESPAWN_HEALTH, RESPAWN_MEGAHEALTH, STAT_HEALTH, STAT_MAX_HEALTH, and playerState_s::stats.

Referenced by Touch_Item().

02237                                                      {
02238         int                     max;
02239         int                     quantity;
02240 
02241         // small and mega healths will go over the max
02242         if ( ent->item->quantity != 5 && ent->item->quantity != 100 ) {
02243                 max = other->client->ps.stats[STAT_MAX_HEALTH];
02244         } else {
02245                 max = other->client->ps.stats[STAT_MAX_HEALTH] * 2;
02246         }
02247 
02248         if ( ent->count ) {
02249                 quantity = ent->count;
02250         } else {
02251                 quantity = ent->item->quantity;
02252         }
02253 
02254         other->health += quantity;
02255 
02256         if (other->health > max ) {
02257                 other->health = max;
02258         }
02259         other->client->ps.stats[STAT_HEALTH] = other->health;
02260 
02261         if ( ent->item->quantity == 100 ) {             // mega health respawns slow
02262                 return RESPAWN_MEGAHEALTH;
02263         }
02264 
02265         return adjustRespawnTime(RESPAWN_HEALTH, ent->item->giType, ent->item->giTag);
02266 }

int Pickup_Holdable gentity_t ent,
gentity_t other
 

Definition at line 2104 of file g_items.c.

References adjustRespawnTime(), bg_itemlist, gentity_s::client, G_LogWeaponItem(), gentity_t, gitem_s::giTag, gitem_s::giType, gentity_s::item, entityState_s::number, gclient_s::ps, RESPAWN_HOLDABLE, gentity_s::s, STAT_HOLDABLE_ITEM, STAT_HOLDABLE_ITEMS, and playerState_s::stats.

Referenced by Touch_Item().

02104                                                         {
02105 
02106         other->client->ps.stats[STAT_HOLDABLE_ITEM] = ent->item - bg_itemlist;
02107 
02108         other->client->ps.stats[STAT_HOLDABLE_ITEMS] |= (1 << ent->item->giTag);
02109 
02110         G_LogWeaponItem(other->s.number, ent->item->giTag);
02111 
02112         return adjustRespawnTime(RESPAWN_HOLDABLE, ent->item->giType, ent->item->giTag);
02113 }

int Pickup_Powerup gentity_t ent,
gentity_t other
 

Definition at line 2024 of file g_items.c.

References AngleVectors(), gentity_s::client, client, level_locals_t::clients, CON_DISCONNECTED, clientPersistant_t::connected, CONTENTS_SOLID, gentity_s::count, DotProduct, ENTITYNUM_NONE, trace_t::fraction, g_gametype, G_LogWeaponPowerup(), gclient_t, gentity_t, gitem_s::giTag, GT_TEAM, vmCvar_t::integer, gentity_s::item, level, level_locals_t::maxclients, NULL, entityState_s::number, playerState_s::origin, gclient_s::pers, PERS_PLAYEREVENTS, playerState_s::persistant, PLAYEREVENT_DENIEDREWARD, entityState_s::pos, playerState_s::powerups, gclient_s::ps, PW_FORCE_BOON, PW_FORCE_ENLIGHTENED_DARK, PW_FORCE_ENLIGHTENED_LIGHT, PW_YSALAMIRI, gitem_s::quantity, RESPAWN_POWERUP, gentity_s::s, gclient_s::sess, clientSession_t::sessionTeam, STAT_HEALTH, playerState_s::stats, level_locals_t::time, trap_Trace(), trajectory_t::trBase, vec3_t, VectorNormalize(), VectorSubtract, and playerState_s::viewangles.

Referenced by Touch_Item().

02024                                                        {
02025         int                     quantity;
02026         int                     i;
02027         gclient_t       *client;
02028 
02029         if ( !other->client->ps.powerups[ent->item->giTag] ) {
02030                 // round timing to seconds to make multiple powerup timers
02031                 // count in sync
02032                 other->client->ps.powerups[ent->item->giTag] = 
02033                         level.time - ( level.time % 1000 );
02034 
02035                 G_LogWeaponPowerup(other->s.number, ent->item->giTag);
02036         }
02037 
02038         if ( ent->count ) {
02039                 quantity = ent->count;
02040         } else {
02041                 quantity = ent->item->quantity;
02042         }
02043 
02044         other->client->ps.powerups[ent->item->giTag] += quantity * 1000;
02045 
02046         if (ent->item->giTag == PW_YSALAMIRI)
02047         {
02048                 other->client->ps.powerups[PW_FORCE_ENLIGHTENED_LIGHT] = 0;
02049                 other->client->ps.powerups[PW_FORCE_ENLIGHTENED_DARK] = 0;
02050                 other->client->ps.powerups[PW_FORCE_BOON] = 0;
02051         }
02052 
02053         // give any nearby players a "denied" anti-reward
02054         for ( i = 0 ; i < level.maxclients ; i++ ) {
02055                 vec3_t          delta;
02056                 float           len;
02057                 vec3_t          forward;
02058                 trace_t         tr;
02059 
02060                 client = &level.clients[i];
02061                 if ( client == other->client ) {
02062                         continue;
02063                 }
02064                 if ( client->pers.connected == CON_DISCONNECTED ) {
02065                         continue;
02066                 }
02067                 if ( client->ps.stats[STAT_HEALTH] <= 0 ) {
02068                         continue;
02069                 }
02070 
02071     // if same team in team game, no sound
02072     // cannot use OnSameTeam as it expects to g_entities, not clients
02073         if ( g_gametype.integer >= GT_TEAM && other->client->sess.sessionTeam == client->sess.sessionTeam  ) {
02074       continue;
02075     }
02076 
02077                 // if too far away, no sound
02078                 VectorSubtract( ent->s.pos.trBase, client->ps.origin, delta );
02079                 len = VectorNormalize( delta );
02080                 if ( len > 192 ) {
02081                         continue;
02082                 }
02083 
02084                 // if not facing, no sound
02085                 AngleVectors( client->ps.viewangles, forward, NULL, NULL );
02086                 if ( DotProduct( delta, forward ) < 0.4 ) {
02087                         continue;
02088                 }
02089 
02090                 // if not line of sight, no sound
02091                 trap_Trace( &tr, client->ps.origin, NULL, NULL, ent->s.pos.trBase, ENTITYNUM_NONE, CONTENTS_SOLID );
02092                 if ( tr.fraction != 1.0 ) {
02093                         continue;
02094                 }
02095 
02096                 // anti-reward
02097                 client->ps.persistant[PERS_PLAYEREVENTS] ^= PLAYEREVENT_DENIEDREWARD;
02098         }
02099         return RESPAWN_POWERUP;
02100 }

int Pickup_Weapon gentity_t ent,
gentity_t other
 

Definition at line 2180 of file g_items.c.

References Add_Ammo(), adjustRespawnTime(), playerState_s::ammo, gentity_s::client, gentity_s::count, FL_DROPPED_ITEM, gentity_s::flags, g_gametype, G_LogWeaponPickup(), g_weaponRespawn, gentity_t, gitem_s::giTag, gitem_s::giType, GT_TEAM, vmCvar_t::integer, gentity_s::item, entityState_s::number, gclient_s::ps, gitem_s::quantity, RESPAWN_TEAM_WEAPON, gentity_s::s, STAT_WEAPONS, playerState_s::stats, and weaponData.

Referenced by Touch_Item().

02180                                                      {
02181         int             quantity;
02182 
02183         if ( ent->count < 0 ) {
02184                 quantity = 0; // None for you, sir!
02185         } else {
02186                 if ( ent->count ) {
02187                         quantity = ent->count;
02188                 } else {
02189                         quantity = ent->item->quantity;
02190                 }
02191 
02192                 // dropped items and teamplay weapons always have full ammo
02193                 if ( ! (ent->flags & FL_DROPPED_ITEM) && g_gametype.integer != GT_TEAM ) {
02194                         // respawning rules
02195 
02196                         // New method:  If the player has less than half the minimum, give them the minimum, else add 1/2 the min.
02197 
02198                         // drop the quantity if the already have over the minimum
02199                         if ( other->client->ps.ammo[ ent->item->giTag ] < quantity*0.5 ) {
02200                                 quantity = quantity - other->client->ps.ammo[ ent->item->giTag ];
02201                         } else {
02202                                 quantity = quantity*0.5;                // only add half the value.
02203                         }
02204 
02205                         // Old method:  If the player has less than the minimum, give them the minimum, else just add 1.
02206 /*
02207                         // drop the quantity if the already have over the minimum
02208                         if ( other->client->ps.ammo[ ent->item->giTag ] < quantity ) {
02209                                 quantity = quantity - other->client->ps.ammo[ ent->item->giTag ];
02210                         } else {
02211                                 quantity = 1;           // only add a single shot
02212                         }
02213                         */
02214                 }
02215         }
02216 
02217         // add the weapon
02218         other->client->ps.stats[STAT_WEAPONS] |= ( 1 << ent->item->giTag );
02219 
02220         //Add_Ammo( other, ent->item->giTag, quantity );
02221         Add_Ammo( other, weaponData[ent->item->giTag].ammoIndex, quantity );
02222 
02223         G_LogWeaponPickup(other->s.number, ent->item->giTag);
02224         
02225         // team deathmatch has slow weapon respawns
02226         if ( g_gametype.integer == GT_TEAM ) 
02227         {
02228                 return adjustRespawnTime(RESPAWN_TEAM_WEAPON, ent->item->giType, ent->item->giTag);
02229         }
02230 
02231         return adjustRespawnTime(g_weaponRespawn.integer, ent->item->giType, ent->item->giTag);
02232 }

qboolean PlaceShield gentity_t playerent  ) 
 

Definition at line 382 of file g_items.c.

References trace_t::allsolid, entityState_s::angles, AngleVectors(), BG_FindItemForHoldable(), gitem_s::classname, gentity_s::classname, gentity_s::client, entityShared_t::contents, CONTENTS_TRIGGER, CreateShield(), EF_NODRAW, entityState_s::eFlags, trace_t::endpos, trace_t::entityNum, ET_SPECIAL, entityState_s::eType, EV_GENERAL_SOUND, fabs(), trace_t::fraction, G_AddEvent(), g_gametype, G_SetOrigin(), G_SoundIndex(), G_Spawn(), gentity_t, gitem_t, entityState_s::groundEntityNum, GT_TEAM, HI_SHIELD, vmCvar_t::integer, level, MASK_SHOT, MASK_SOLID, entityState_s::modelindex, gentity_s::nextthink, NULL, entityState_s::number, playerState_s::origin, entityState_s::otherEntityNum2, entityState_s::owner, gentity_s::parent, gclient_s::ps, qboolean, qfalse, qtrue, gentity_s::r, gentity_s::s, gclient_s::sess, clientSession_t::sessionTeam, SHIELD_PLACEDIST, entityState_s::shouldtarget, trace_t::startsolid, SVF_NOCLIENT, entityShared_t::svFlags, entityState_s::teamowner, gentity_s::think, level_locals_t::time, gentity_s::touch, trap_LinkEntity(), trap_Trace(), gentity_s::use, vec3_t, VectorCopy, VectorMA, VectorSet, playerState_s::viewangles, and YAW.

Referenced by ItemUse_Shield().

00383 {
00384         static const gitem_t *shieldItem = NULL;
00385         gentity_t       *shield = NULL;
00386         trace_t         tr;
00387         vec3_t          fwd, pos, dest, mins = {-4,-4, 0}, maxs = {4,4,4};
00388 
00389         if (shieldAttachSound==0)
00390         {
00391                 shieldLoopSound = G_SoundIndex("sound/movers/doors/forcefield_lp.wav");
00392                 shieldAttachSound = G_SoundIndex("sound/weapons/detpack/stick.wav");
00393                 shieldActivateSound = G_SoundIndex("sound/movers/doors/forcefield_on.wav");
00394                 shieldDeactivateSound = G_SoundIndex("sound/movers/doors/forcefield_off.wav");
00395                 shieldDamageSound = G_SoundIndex("sound/effects/bumpfield.wav");
00396                 shieldItem = BG_FindItemForHoldable(HI_SHIELD);
00397         }
00398 
00399         // can we place this in front of us?
00400         AngleVectors (playerent->client->ps.viewangles, fwd, NULL, NULL);
00401         fwd[2] = 0;
00402         VectorMA(playerent->client->ps.origin, SHIELD_PLACEDIST, fwd, dest);
00403         trap_Trace (&tr, playerent->client->ps.origin, mins, maxs, dest, playerent->s.number, MASK_SHOT );
00404         if (tr.fraction > 0.9)
00405         {//room in front
00406                 VectorCopy(tr.endpos, pos);
00407                 // drop to floor
00408                 VectorSet( dest, pos[0], pos[1], pos[2] - 4096 );
00409                 trap_Trace( &tr, pos, mins, maxs, dest, playerent->s.number, MASK_SOLID );
00410                 if ( !tr.startsolid && !tr.allsolid )
00411                 {
00412                         // got enough room so place the portable shield
00413                         shield = G_Spawn();
00414 
00415                         // Figure out what direction the shield is facing.
00416                         if (fabs(fwd[0]) > fabs(fwd[1]))
00417                         {       // shield is north/south, facing east.
00418                                 shield->s.angles[YAW] = 0;
00419                         }
00420                         else
00421                         {       // shield is along the east/west axis, facing north
00422                                 shield->s.angles[YAW] = 90;
00423                         }
00424                         shield->think = CreateShield;
00425                         shield->nextthink = level.time + 500;   // power up after .5 seconds
00426                         shield->parent = playerent;
00427 
00428                         // Set team number.
00429                         shield->s.otherEntityNum2 = playerent->client->sess.sessionTeam;
00430 
00431                         shield->s.eType = ET_SPECIAL;
00432                         shield->s.modelindex =  HI_SHIELD;      // this'll be used in CG_Useable() for rendering.
00433                         shield->classname = shieldItem->classname;
00434 
00435                         shield->r.contents = CONTENTS_TRIGGER;
00436 
00437                         shield->touch = 0;
00438                         // using an item causes it to respawn
00439                         shield->use = 0; //Use_Item;
00440 
00441                         // allow to ride movers
00442                         shield->s.groundEntityNum = tr.entityNum;
00443 
00444                         G_SetOrigin( shield, tr.endpos );
00445 
00446                         shield->s.eFlags &= ~EF_NODRAW;
00447                         shield->r.svFlags &= ~SVF_NOCLIENT;
00448 
00449                         trap_LinkEntity (shield);
00450 
00451                         shield->s.owner = playerent->s.number;
00452                         shield->s.shouldtarget = qtrue;
00453                         if (g_gametype.integer >= GT_TEAM)
00454                         {
00455                                 shield->s.teamowner = playerent->client->sess.sessionTeam;
00456                         }
00457                         else
00458                         {
00459                                 shield->s.teamowner = 16;
00460                         }
00461 
00462                         // Play placing sound...
00463                         G_AddEvent(shield, EV_GENERAL_SOUND, shieldAttachSound);
00464 
00465                         return qtrue;
00466                 }
00467         }
00468         // no room
00469         return qfalse;
00470 }

void RegisterItem gitem_t item  ) 
 

Definition at line 3020 of file g_items.c.

References bg_itemlist, G_Error(), gitem_t, itemRegistered, and qtrue.

Referenced by ClearRegisteredItems(), EWebPrecache(), finish_spawning_turretG2(), G_PrecacheDispensers(), G_SiegeRegisterWeaponsAndHoldables(), G_SpawnItem(), G_SpecialSpawnItem(), InitShooter(), NPC_ATST_Precache(), NPC_Mark1_Precache(), NPC_Mark2_Precache(), NPC_Precache(), NPC_PrecacheWeapons(), NPC_Probe_Precache(), NPC_Sentry_Precache(), NPC_ShadowTrooper_Precache(), SP_emplaced_gun(), SP_misc_weapon_shooter(), and turret_base_spawn_top().

03020                                    {
03021         if ( !item ) {
03022                 G_Error( "RegisterItem: NULL" );
03023         }
03024         itemRegistered[ item - bg_itemlist ] = qtrue;
03025 }

void RespawnItem gentity_t ent  ) 
 

Definition at line 2288 of file g_items.c.

References entityShared_t::contents, CONTENTS_TRIGGER, EF_ITEMPLACEHOLDER, EF_NODRAW, entityState_s::eFlags, EV_GENERAL_SOUND, EV_GLOBAL_SOUND, EV_ITEM_RESPAWN, entityState_s::eventParm, G_AddEvent(), G_Error(), G_SoundIndex(), G_TempEntity(), gentity_t, gitem_s::giType, IT_POWERUP, gentity_s::item, gentity_s::nextthink, entityState_s::pos, gentity_s::r, rand(), gentity_s::s, gentity_s::speed, SVF_BROADCAST, SVF_NOCLIENT, entityShared_t::svFlags, gentity_s::team, gentity_s::teamchain, gentity_s::teammaster, trap_LinkEntity(), and trajectory_t::trBase.

Referenced by Team_ResetFlag(), Touch_Item(), and Use_Item().

02288                                    {
02289         // randomly select from teamed entities
02290         if (ent->team) {
02291                 gentity_t       *master;
02292                 int     count;
02293                 int choice;
02294 
02295                 if ( !ent->teammaster ) {
02296                         G_Error( "RespawnItem: bad teammaster");
02297                 }
02298                 master = ent->teammaster;
02299 
02300                 for (count = 0, ent = master; ent; ent = ent->teamchain, count++)
02301                         ;
02302 
02303                 choice = rand() % count;
02304 
02305                 for (count = 0, ent = master; count < choice; ent = ent->teamchain, count++)
02306                         ;
02307         }
02308 
02309         ent->r.contents = CONTENTS_TRIGGER;
02310         //ent->s.eFlags &= ~EF_NODRAW;
02311         ent->s.eFlags &= ~(EF_NODRAW | EF_ITEMPLACEHOLDER);
02312         ent->r.svFlags &= ~SVF_NOCLIENT;
02313         trap_LinkEntity (ent);
02314 
02315         if ( ent->item->giType == IT_POWERUP ) {
02316                 // play powerup spawn sound to all clients
02317                 gentity_t       *te;
02318 
02319                 // if the powerup respawn sound should Not be global
02320                 if (ent->speed) {
02321                         te = G_TempEntity( ent->s.pos.trBase, EV_GENERAL_SOUND );
02322                 }
02323                 else {
02324                         te = G_TempEntity( ent->s.pos.trBase, EV_GLOBAL_SOUND );
02325                 }
02326                 te->s.eventParm = G_SoundIndex( "sound/items/respawn1" );
02327                 te->r.svFlags |= SVF_BROADCAST;
02328         }
02329 
02330         // play the normal respawn sound only to nearby clients
02331         G_AddEvent( ent, EV_ITEM_RESPAWN, 0 );
02332 
02333         ent->nextthink = 0;
02334 }

void SaveRegisteredItems void   ) 
 

Definition at line 3036 of file g_items.c.

References bg_numItems, CS_ITEMS, itemRegistered, MAX_ITEMS, and trap_SetConfigstring().

Referenced by G_InitGame().

03036                                  {
03037         char    string[MAX_ITEMS+1];
03038         int             i;
03039         int             count;
03040 
03041         count = 0;
03042         for ( i = 0 ; i < bg_numItems ; i++ ) {
03043                 if ( itemRegistered[i] ) {
03044                         count++;
03045                         string[i] = '1';
03046                 } else {
03047                         string[i] = '0';
03048                 }
03049         }
03050         string[ bg_numItems ] = 0;
03051 
03052 //      G_Printf( "%i items registered\n", count );
03053         trap_SetConfigstring(CS_ITEMS, string);
03054 }

void sentryExpire gentity_t self  ) 
 

Definition at line 702 of file g_items.c.

References gentity_t, MOD_UNKNOWN, and turret_die().

Referenced by pas_think().

00703 {
00704         turret_die(self, self, self, 1000, MOD_UNKNOWN);        
00705 }

void SentryTouch gentity_t ent,
gentity_t other,
trace_t trace
 

Definition at line 515 of file g_items.c.

References gentity_t.

Referenced by ItemUse_Sentry().

00516 {
00517         return;
00518 }

void ShieldDie gentity_t self,
gentity_t inflictor,
gentity_t attacker,
int  damage,
int  mod
 

Definition at line 145 of file g_items.c.

References EV_GENERAL_SOUND, G_AddEvent(), gentity_t, and ShieldRemove().

Referenced by CreateShield().

00146 {
00147         // Play damaging sound...
00148         G_AddEvent(self, EV_GENERAL_SOUND, shieldDamageSound);
00149 
00150         ShieldRemove(self);
00151 }

void ShieldGoNotSolid gentity_t self  ) 
 

Definition at line 211 of file g_items.c.

References entityShared_t::contents, EF_NODRAW, entityState_s::eFlags, EV_GENERAL_SOUND, G_AddEvent(), gentity_t, level, entityState_s::loopIsSoundset, entityState_s::loopSound, gentity_s::nextthink, qfalse, gentity_s::r, gentity_s::s, ShieldGoSolid(), gentity_s::takedamage, gentity_s::think, level_locals_t::time, and trap_LinkEntity().

Referenced by ShieldTouch().

00212 {
00213         // make the shield non-solid very briefly
00214         self->r.contents = 0;
00215         self->s.eFlags |= EF_NODRAW;
00216         // nextthink needs to have a large enough interval to avoid excess accumulation of Activate messages
00217         self->nextthink = level.time + 200;
00218         self->think = ShieldGoSolid;
00219         self->takedamage = qfalse;
00220         trap_LinkEntity(self);
00221 
00222         // Play kill sound...
00223         G_AddEvent(self, EV_GENERAL_SOUND, shieldDeactivateSound);
00224         self->s.loopSound = 0;
00225         self->s.loopIsSoundset = qfalse;
00226 }

void ShieldGoSolid gentity_t self  ) 
 

Definition at line 171 of file g_items.c.

References entityShared_t::contents, CONTENTS_BODY, CONTENTS_SOLID, entityShared_t::currentOrigin, EF_NODRAW, entityState_s::eFlags, EV_GENERAL_SOUND, G_AddEvent(), gentity_t, gentity_s::health, level, entityState_s::loopIsSoundset, entityState_s::loopSound, entityShared_t::maxs, entityShared_t::mins, gentity_s::nextthink, entityState_s::number, qfalse, qtrue, gentity_s::r, gentity_s::s, ShieldGoSolid(), ShieldRemove(), ShieldThink(), trace_t::startsolid, gentity_s::takedamage, gentity_s::think, level_locals_t::time, trap_LinkEntity(), and trap_Trace().

Referenced by CreateShield(), ShieldGoNotSolid(), and ShieldGoSolid().

00172 {
00173         trace_t         tr;
00174 
00175         // see if we're valid
00176         self->health--;
00177         if (self->health <= 0)
00178         {
00179                 ShieldRemove(self);
00180                 return;
00181         }
00182         
00183         trap_Trace (&tr, self->r.currentOrigin, self->r.mins, self->r.maxs, self->r.currentOrigin, self->s.number, CONTENTS_BODY );
00184         if(tr.startsolid)
00185         {       // gah, we can't activate yet
00186                 self->nextthink = level.time + 200;
00187                 self->think = ShieldGoSolid;
00188                 trap_LinkEntity(self);
00189         }
00190         else
00191         { // get hard... huh-huh...
00192                 self->s.eFlags &= ~EF_NODRAW;
00193 
00194                 self->r.contents = CONTENTS_SOLID;
00195                 self->nextthink = level.time + 1000;
00196                 self->think = ShieldThink;
00197                 self->takedamage = qtrue;
00198                 trap_LinkEntity(self);
00199 
00200                 // Play raising sound...
00201                 G_AddEvent(self, EV_GENERAL_SOUND, shieldActivateSound);
00202                 self->s.loopSound = shieldLoopSound;
00203                 self->s.loopIsSoundset = qfalse;
00204         }
00205 
00206         return;
00207 }

void ShieldPain gentity_t self,
gentity_t attacker,
int  damage
 

Definition at line 155 of file g_items.c.

References EV_GENERAL_SOUND, G_AddEvent(), gentity_t, level, gentity_s::nextthink, gentity_s::s, ShieldThink(), gentity_s::think, level_locals_t::time, and entityState_s::trickedentindex.

Referenced by CreateShield().

00156 {
00157         // Set the itemplaceholder flag to indicate the the shield drawing that the shield pain should be drawn.
00158         self->think = ShieldThink;
00159         self->nextthink = level.time + 400;
00160 
00161         // Play damaging sound...
00162         G_AddEvent(self, EV_GENERAL_SOUND, shieldDamageSound);
00163 
00164         self->s.trickedentindex = 1;
00165 
00166         return;
00167 }

void ShieldRemove gentity_t self  ) 
 

Definition at line 108 of file g_items.c.

References EV_GENERAL_SOUND, G_AddEvent(), G_FreeEntity(), gentity_t, level, entityState_s::loopIsSoundset, entityState_s::loopSound, gentity_s::nextthink, qfalse, gentity_s::s, gentity_s::think, and level_locals_t::time.

Referenced by ShieldDie(), ShieldGoSolid(), and ShieldThink().

00109 {
00110         self->think = G_FreeEntity;
00111         self->nextthink = level.time + 100;
00112 
00113         // Play kill sound...
00114         G_AddEvent(self, EV_GENERAL_SOUND, shieldDeactivateSound);
00115         self->s.loopSound = 0;
00116         self->s.loopIsSoundset = qfalse;
00117 
00118         return;
00119 }

void ShieldThink gentity_t self  ) 
 

Definition at line 123 of file g_items.c.

References g_gametype, gentity_t, GT_SIEGE, gentity_s::health, vmCvar_t::integer, level, gentity_s::nextthink, gentity_s::s, SHIELD_HEALTH_DEC, SHIELD_SIEGE_HEALTH_DEC, ShieldRemove(), level_locals_t::time, and entityState_s::trickedentindex.

Referenced by CreateShield(), ShieldGoSolid(), and ShieldPain().

00124 {
00125         self->s.trickedentindex = 0;
00126 
00127         if ( g_gametype.integer == GT_SIEGE )
00128         {
00129                 self->health -= SHIELD_SIEGE_HEALTH_DEC;
00130         }
00131         else
00132         {
00133                 self->health -= SHIELD_HEALTH_DEC;
00134         }
00135         self->nextthink = level.time + 1000;
00136         if (self->health <= 0)
00137         {
00138                 ShieldRemove(self);
00139         }
00140         return;
00141 }

void ShieldTouch gentity_t self,
gentity_t other,
trace_t trace
 

Definition at line 230 of file g_items.c.

References gentity_s::client, g_gametype, gentity_t, GT_TEAM, vmCvar_t::integer, entityState_s::number, OnSameTeam(), gentity_s::parent, gentity_s::s, and ShieldGoNotSolid().

Referenced by CreateShield().

00231 {
00232         if (g_gametype.integer >= GT_TEAM)
00233         { // let teammates through
00234                 // compare the parent's team to the "other's" team
00235                 if (self->parent && ( self->parent->client) && (other->client))
00236                 {
00237                         if (OnSameTeam(self->parent, other))
00238                         {
00239                                 ShieldGoNotSolid(self);
00240                         }
00241                 }
00242         }
00243         else
00244         {//let the person who dropped the shield through
00245                 if (self->parent && self->parent->s.number == other->s.number)
00246                 {
00247                         ShieldGoNotSolid(self);
00248                 }
00249         }
00250 }

void SP_PAS gentity_t base  ) 
 

Definition at line 978 of file g_items.c.

References entityState_s::bolt1, entityState_s::bolt2, CHAN_BODY, gentity_s::count, gentity_s::damage, gentity_s::die, ENTITYNUM_NONE, FRAMETIME, G_RunObject(), G_Sound(), G_SoundIndex(), gentity_t, gentity_s::health, level, entityShared_t::maxs, entityShared_t::mins, gentity_s::nextthink, pas_think(), gentity_s::physicsObject, qtrue, gentity_s::r, gentity_s::s, gentity_s::takedamage, gentity_s::think, level_locals_t::time, TURRET_AMMO_COUNT, turret_die(), and VectorSet.

Referenced by ItemUse_Sentry().

00980 {
00981         if ( base->count == 0 )
00982         {
00983                 // give ammo
00984                 base->count = TURRET_AMMO_COUNT;
00985         }
00986 
00987         base->s.bolt1 = 1; //This is a sort of hack to indicate that this model needs special turret things done to it
00988         base->s.bolt2 = ENTITYNUM_NONE; //store our current enemy index
00989 
00990         base->damage = 0; // start animation flag
00991 
00992         VectorSet( base->r.mins, -8, -8, 0 );
00993         VectorSet( base->r.maxs, 8, 8, 24 );
00994 
00995         G_RunObject(base);
00996 
00997         base->think = pas_think;
00998         base->nextthink = level.time + FRAMETIME;
00999 
01000         if ( !base->health )
01001         {
01002                 base->health = 50;
01003         }
01004 
01005         base->takedamage = qtrue;
01006         base->die  = turret_die;
01007 
01008         base->physicsObject = qtrue;
01009 
01010         G_Sound( base, CHAN_BODY, G_SoundIndex( "sound/chars/turret/startup.wav" ));
01011 }

void SpecialItemThink gentity_t ent  ) 
 

Definition at line 1277 of file g_items.c.

References entityShared_t::currentOrigin, G_FreeEntity(), G_RunExPhys(), gentity_s::genericValue5, gentity_t, level, gentity_s::nextthink, NULL, entityState_s::origin, qfalse, gentity_s::r, gentity_s::s, gentity_s::think, level_locals_t::time, and VectorCopy.

Referenced by G_SpecialSpawnItem().

01278 {
01279         float gravity = 3.0f;
01280         float mass = 0.09f;
01281         float bounce = 1.1f;
01282 
01283         if (ent->genericValue5 < level.time)
01284         {
01285                 ent->think = G_FreeEntity;
01286                 ent->nextthink = level.time;
01287                 return;
01288         }
01289 
01290         G_RunExPhys(ent, gravity, mass, bounce, qfalse, NULL, 0);
01291         VectorCopy(ent->r.currentOrigin, ent->s.origin);
01292         ent->nextthink = level.time + 50;
01293 }

void Touch_Item gentity_t ent,
gentity_t other,
trace_t trace
 

Definition at line 2362 of file g_items.c.

References playerState_s::ammo, AMMO_DETPACK, AMMO_THERMAL, AMMO_TRIPMINE, weaponData_s::ammoIndex, BG_AddPredictableEventToPlayerstate(), BG_CanItemBeGrabbed(), CheckItemCanBePickedUpByNPC(), CLASS_ATST, CLASS_GONK, CLASS_MARK1, CLASS_MARK2, CLASS_MOUSE, CLASS_PROBE, CLASS_PROTOCOL, CLASS_R2D2, CLASS_R5D2, CLASS_RANCOR, CLASS_REMOTE, CLASS_SEEKER, CLASS_SENTRY, CLASS_UGNAUGHT, CLASS_VEHICLE, CLASS_WAMPA, gitem_s::classname, gentity_s::client, entityShared_t::contents, crandom, EF_ITEMPLACEHOLDER, EF_NODRAW, entityState_s::eFlags, gentity_s::enemy, ET_NPC, entityState_s::eType, EV_GLOBAL_ITEM_PICKUP, EV_ITEM_PICKUP, entityState_s::eventParm, playerState_s::fd, FL_DROPPED_ITEM, gentity_s::flags, FORCE_DARKSIDE, FORCE_LIGHTSIDE, forcedata_s::forceSide, gentity_s::freeAfterEvent, G_AddEvent(), G_AddPredictableEvent(), G_FreeEntity(), g_gametype, G_LogPrintf(), G_ScaleNetHealth(), G_TempEntity(), G_UseTargets(), entityState_s::generic1, gentity_s::genericValue10, gentity_s::genericValue11, gentity_s::genericValue9, gentity_t, gitem_s::giTag, gitem_s::giType, gNPC_t::goalEntity, gentity_s::health, vmCvar_t::integer, IT_AMMO, IT_ARMOR, IT_HEALTH, IT_HOLDABLE, IT_POWERUP, IT_TEAM, IT_WEAPON, gentity_s::item, ITMSF_ALLOWNPC, level, gentity_s::m_pVehicle, Vehicle_s::m_pVehicleInfo, gentity_s::maxHealth, entityState_s::modelindex, gentity_s::nextthink, gentity_s::NPC, gclient_s::NPC_class, entityState_s::NPC_class, NULL, entityState_s::number, gclient_s::pers, Pickup_Ammo(), Pickup_Armor(), Pickup_Health(), Pickup_Holdable(), Pickup_Powerup(), Pickup_Team(), Pickup_Weapon(), entityState_s::pos, entityState_s::powerups, clientPersistant_t::predictItemPickup, gclient_s::ps, PW_FORCE_ENLIGHTENED_DARK, PW_FORCE_ENLIGHTENED_LIGHT, qboolean, qfalse, qtrue, gentity_s::r, gentity_s::random, respawn(), RespawnItem(), gentity_s::s, entityShared_t::singleClient, gentity_s::spawnflags, gentity_s::speed, SQUAD_STAND_AND_SHOOT, gNPC_t::squadState, STAT_WEAPONS, playerState_s::stats, SVF_BROADCAST, SVF_NOCLIENT, SVF_SINGLECLIENT, entityShared_t::svFlags, gentity_s::think, level_locals_t::time, trap_LinkEntity(), trajectory_t::trBase, vehicleInfo_t::type, gentity_s::unlinkAfterEvent, VH_WALKER, gentity_s::wait, weaponData, WP_DET_PACK, WP_THERMAL, and WP_TRIP_MINE.

Referenced by Cmd_Give_f(), FinishSpawningItem(), G_SpecialSpawnItem(), LaunchItem(), and Use_Target_Give().

02362                                                                    {
02363         int                     respawn;
02364         qboolean        predict;
02365 
02366         if (ent->genericValue10 > level.time &&
02367                 other &&
02368                 other->s.number == ent->genericValue11)
02369         { //this is the ent that we don't want to be able to touch us for x seconds
02370                 return;
02371         }
02372 
02373         if (ent->s.eFlags & EF_ITEMPLACEHOLDER)
02374         {
02375                 return;
02376         }
02377 
02378         if (ent->s.eFlags & EF_NODRAW)
02379         {
02380                 return;
02381         }
02382 
02383         if (ent->item->giType == IT_WEAPON &&
02384                 ent->s.powerups &&
02385                 ent->s.powerups < level.time)
02386         {
02387                 ent->s.generic1 = 0;
02388                 ent->s.powerups = 0;
02389         }
02390 
02391         if (!other->client)
02392                 return;
02393         if (other->health < 1)
02394                 return;         // dead people can't pickup
02395 
02396         if (ent->item->giType == IT_POWERUP &&
02397                 (ent->item->giTag == PW_FORCE_ENLIGHTENED_LIGHT || ent->item->giTag == PW_FORCE_ENLIGHTENED_DARK))
02398         {
02399                 if (ent->item->giTag == PW_FORCE_ENLIGHTENED_LIGHT)
02400                 {
02401                         if (other->client->ps.fd.forceSide != FORCE_LIGHTSIDE)
02402                         {
02403                                 return;
02404                         }
02405                 }
02406                 else
02407                 {
02408                         if (other->client->ps.fd.forceSide != FORCE_DARKSIDE)
02409                         {
02410                                 return;
02411                         }
02412                 }
02413         }
02414 
02415         // the same pickup rules are used for client side and server side
02416         if ( !BG_CanItemBeGrabbed( g_gametype.integer, &ent->s, &other->client->ps ) ) {
02417                 return;
02418         }
02419 
02420         
02421         if ( other->client->NPC_class == CLASS_ATST || 
02422                 other->client->NPC_class == CLASS_GONK || 
02423                 other->client->NPC_class == CLASS_MARK1 || 
02424                 other->client->NPC_class == CLASS_MARK2 || 
02425                 other->client->NPC_class == CLASS_MOUSE || 
02426                 other->client->NPC_class == CLASS_PROBE || 
02427                 other->client->NPC_class == CLASS_PROTOCOL || 
02428                 other->client->NPC_class == CLASS_R2D2 || 
02429                 other->client->NPC_class == CLASS_R5D2 || 
02430                 other->client->NPC_class == CLASS_SEEKER || 
02431                 other->client->NPC_class == CLASS_REMOTE || 
02432                 other->client->NPC_class == CLASS_RANCOR || 
02433                 other->client->NPC_class == CLASS_WAMPA || 
02434                 //other->client->NPC_class == CLASS_JAWA || //FIXME: in some cases it's okay?
02435                 other->client->NPC_class == CLASS_UGNAUGHT || //FIXME: in some cases it's okay?
02436                 other->client->NPC_class == CLASS_SENTRY )
02437         {//FIXME: some flag would be better
02438                 //droids can't pick up items/weapons!
02439                 return;
02440         }
02441 
02442         if ( CheckItemCanBePickedUpByNPC( ent, other ) )
02443         {
02444                 if ( other->NPC && other->NPC->goalEntity && other->NPC->goalEntity->enemy == ent )
02445                 {//they were running to pick me up, they did, so clear goal
02446                         other->NPC->goalEntity = NULL;
02447                         other->NPC->squadState = SQUAD_STAND_AND_SHOOT;
02448                 }
02449         }
02450         else if ( !(ent->spawnflags &  ITMSF_ALLOWNPC) )
02451         {// NPCs cannot pick it up
02452                 if ( other->s.eType == ET_NPC )
02453                 {// Not the player?
02454                         qboolean dontGo = qfalse;
02455                         if (ent->item->giType == IT_AMMO &&
02456                                 ent->item->giTag == -1 &&
02457                                 other->s.NPC_class == CLASS_VEHICLE &&
02458                                 other->m_pVehicle &&
02459                                 other->m_pVehicle->m_pVehicleInfo->type == VH_WALKER)
02460                         { //yeah, uh, atst gets healed by these things
02461                 if (other->maxHealth &&
02462                                         other->health < other->maxHealth)
02463                                 {
02464                                         other->health += 80;
02465                                         if (other->health > other->maxHealth)
02466                                         {
02467                                                 other->health = other->maxHealth;
02468                                         }
02469                                         G_ScaleNetHealth(other);
02470                                         dontGo = qtrue;
02471                                 }
02472                         }
02473 
02474                         if (!dontGo)
02475                         {
02476                                 return;
02477                         }
02478                 }
02479         }
02480 
02481         G_LogPrintf( "Item: %i %s\n", other->s.number, ent->item->classname );
02482 
02483         predict = other->client->pers.predictItemPickup;
02484 
02485         // call the item-specific pickup function
02486         switch( ent->item->giType ) {
02487         case IT_WEAPON:
02488                 respawn = Pickup_Weapon(ent, other);
02489 //              predict = qfalse;
02490                 predict = qtrue;
02491                 break;
02492         case IT_AMMO:
02493                 respawn = Pickup_Ammo(ent, other);
02494                 if (ent->item->giTag == AMMO_THERMAL || ent->item->giTag == AMMO_TRIPMINE || ent->item->giTag == AMMO_DETPACK)
02495                 {
02496                         int weapForAmmo = 0;
02497 
02498                         if (ent->item->giTag == AMMO_THERMAL)
02499                         {
02500                                 weapForAmmo = WP_THERMAL;
02501                         }
02502                         else if (ent->item->giTag == AMMO_TRIPMINE)
02503                         {
02504                                 weapForAmmo = WP_TRIP_MINE;
02505                         }
02506                         else
02507                         {
02508                                 weapForAmmo = WP_DET_PACK;
02509                         }
02510 
02511                         if (other && other->client && other->client->ps.ammo[weaponData[weapForAmmo].ammoIndex] > 0 )
02512                         {
02513                                 other->client->ps.stats[STAT_WEAPONS] |= (1 << weapForAmmo);
02514                         }
02515                 }
02516 //              predict = qfalse;
02517                 predict = qtrue;
02518                 break;
02519         case IT_ARMOR:
02520                 respawn = Pickup_Armor(ent, other);
02521 //              predict = qfalse;
02522                 predict = qtrue;
02523                 break;
02524         case IT_HEALTH:
02525                 respawn = Pickup_Health(ent, other);
02526 //              predict = qfalse;
02527                 predict = qtrue;
02528                 break;
02529         case IT_POWERUP:
02530                 respawn = Pickup_Powerup(ent, other);
02531                 predict = qfalse;
02532 //              predict = qtrue;
02533                 break;
02534         case IT_TEAM:
02535                 respawn = Pickup_Team(ent, other);
02536                 break;
02537         case IT_HOLDABLE:
02538                 respawn = Pickup_Holdable(ent, other);
02539                 break;
02540         default:
02541                 return;
02542         }
02543 
02544         if ( !respawn ) {
02545                 return;
02546         }
02547 
02548         // play the normal pickup sound
02549         if (predict) {
02550                 if (other->client)
02551                 {
02552                         BG_AddPredictableEventToPlayerstate( EV_ITEM_PICKUP, ent->s.number, &other->client->ps);
02553                 }
02554                 else
02555                 {
02556                         G_AddPredictableEvent( other, EV_ITEM_PICKUP, ent->s.number );
02557                 }
02558         } else {
02559                 G_AddEvent( other, EV_ITEM_PICKUP, ent->s.number );
02560         }
02561 
02562         // powerup pickups are global broadcasts
02563         if ( /*ent->item->giType == IT_POWERUP ||*/ ent->item->giType == IT_TEAM) {
02564                 // if we want the global sound to play
02565                 if (!ent->speed) {
02566                         gentity_t       *te;
02567 
02568                         te = G_TempEntity( ent->s.pos.trBase, EV_GLOBAL_ITEM_PICKUP );
02569                         te->s.eventParm = ent->s.modelindex;
02570                         te->r.svFlags |= SVF_BROADCAST;
02571                 } else {
02572                         gentity_t       *te;
02573 
02574                         te = G_TempEntity( ent->s.pos.trBase, EV_GLOBAL_ITEM_PICKUP );
02575                         te->s.eventParm = ent->s.modelindex;
02576                         // only send this temp entity to a single client
02577                         te->r.svFlags |= SVF_SINGLECLIENT;
02578                         te->r.singleClient = other->s.number;
02579                 }
02580         }
02581 
02582         // fire item targets
02583         G_UseTargets (ent, other);
02584 
02585         // wait of -1 will not respawn
02586         if ( ent->wait == -1 ) {
02587                 ent->r.svFlags |= SVF_NOCLIENT;
02588                 ent->s.eFlags |= EF_NODRAW;
02589                 ent->r.contents = 0;
02590                 ent->unlinkAfterEvent = qtrue;
02591                 return;
02592         }
02593 
02594         // non zero wait overrides respawn time
02595         if ( ent->wait ) {
02596                 respawn = ent->wait;
02597         }
02598 
02599         // random can be used to vary the respawn time
02600         if ( ent->random ) {
02601                 respawn += crandom() * ent->random;
02602                 if ( respawn < 1 ) {
02603                         respawn = 1;
02604                 }
02605         }
02606 
02607         // dropped items will not respawn
02608         if ( ent->flags & FL_DROPPED_ITEM ) {
02609                 ent->freeAfterEvent = qtrue;
02610         }
02611 
02612         // picked up items still stay around, they just don't
02613         // draw anything.  This allows respawnable items
02614         // to be placed on movers.
02615         if (!(ent->flags & FL_DROPPED_ITEM) && (ent->item->giType==IT_WEAPON || ent->item->giType==IT_POWERUP))
02616         {
02617                 ent->s.eFlags |= EF_ITEMPLACEHOLDER;
02618                 ent->s.eFlags &= ~EF_NODRAW;
02619         }
02620         else
02621         {
02622                 ent->s.eFlags |= EF_NODRAW;
02623                 ent->r.svFlags |= SVF_NOCLIENT;
02624         }
02625         ent->r.contents = 0;
02626 
02627         if (ent->genericValue9)
02628         { //dropped item, should be removed when picked up
02629                 ent->think = G_FreeEntity;
02630                 ent->nextthink = level.time;
02631                 return;
02632         }
02633 
02634         // ZOID
02635         // A negative respawn times means to never respawn this item (but don't 
02636         // delete it).  This is used by items that are respawned by third party 
02637         // events such as ctf flags
02638         if ( respawn <= 0 ) {
02639                 ent->nextthink = 0;
02640                 ent->think = 0;
02641         } else {
02642                 ent->nextthink = level.time + respawn * 1000;
02643                 ent->think = RespawnItem;
02644         }
02645         trap_LinkEntity( ent );
02646 }

void turret_die gentity_t self,
gentity_t inflictor,
gentity_t attacker,
int  damage,
int  mod
 

Definition at line 940 of file g_items.c.

References entityState_s::angles, gentity_s::die, EFFECT_EXPLOSION_PAS, g_entities, G_FreeEntity(), G_PlayEffect(), G_RadiusDamage(), G_UseTargets(), gentity_s::genericValue3, gentity_t, gentity_s::health, MOD_UNKNOWN, entityState_s::pos, qfalse, gentity_s::s, gentity_s::takedamage, gentity_s::target, gentity_s::think, trajectory_t::trBase, gentity_s::use, and VectorSet.

Referenced by sentryExpire(), and SP_PAS().

00942 {
00943         // Turn off the thinking of the base & use it's targets
00944         self->think = 0;//NULL;
00945         self->use = 0;//NULL;
00946 
00947         if ( self->target )
00948         {
00949                 G_UseTargets( self, attacker );
00950         }
00951 
00952         if (!g_entities[self->genericValue3].inuse || !g_entities[self->genericValue3].client)
00953         {
00954                 G_FreeEntity(self);
00955                 return;
00956         }
00957 
00958         // clear my data
00959         self->die  = 0;//NULL;
00960         self->takedamage = qfalse;
00961         self->health = 0;
00962 
00963         // hack the effect angle so that explode death can orient the effect properly
00964         VectorSet( self->s.angles, 0, 0, 1 );
00965 
00966         G_PlayEffect(EFFECT_EXPLOSION_PAS, self->s.pos.trBase, self->s.angles);
00967         G_RadiusDamage(self->s.pos.trBase, &g_entities[self->genericValue3], 30, 256, self, self, MOD_UNKNOWN);
00968 
00969         g_entities[self->genericValue3].client->ps.fd.sentryDeployed = qfalse;
00970 
00971         //ExplodeDeath( self );
00972         G_FreeEntity( self );
00973 }

void Use_Item gentity_t ent,
gentity_t other,
gentity_t activator
 

Definition at line 2765 of file g_items.c.

References gentity_t, and RespawnItem().

Referenced by FinishSpawningItem().

02765                                                                         {
02766         RespawnItem( ent );
02767 }


Variable Documentation

gentity_t* droppedBlueFlag
 

Definition at line 38 of file g_items.c.

Referenced by CTFFlagMovement(), CTFTakesPriority(), and LaunchItem().

gentity_t* droppedRedFlag
 

Definition at line 37 of file g_items.c.

Referenced by CTFFlagMovement(), CTFTakesPriority(), and LaunchItem().

qboolean itemRegistered[MAX_ITEMS]
 

Definition at line 2966 of file g_items.c.

Referenced by ClearRegisteredItems(), G_CheckTeamItems(), RegisterItem(), and SaveRegisteredItems().