Several Changes. New type of breakables.

This commit is contained in:
q3rally 2011-06-17 20:27:16 +00:00
parent 973dd9bc07
commit 3932fd68a3
8 changed files with 459 additions and 437 deletions

View file

@ -847,280 +847,11 @@ void CG_BigExplode( vec3_t playerOrigin ) {
}
/*
===================================================
CG_LightningArc
Generates an arc of lightning between
two abitary vectors
===================================================
*/
void CG_LightningArc( vec3_t start, vec3_t end ) {
refEntity_t arc;
memset( &arc, 0, sizeof( arc ) );
arc.reType = RT_LIGHTNING;
arc.customShader = cgs.media.lightningShader;
VectorCopy( start, arc.origin );
VectorCopy( end, arc.oldorigin );
trap_R_AddRefEntityToScene( &arc );
}
/*
==================
CG_LaunchShard
==================
*/
void CG_LaunchShard( vec3_t origin, vec3_t velocity, qhandle_t hModel ) {
int bounce;
localEntity_t *le;
refEntity_t *re;
le = CG_AllocLocalEntity();
re = &le->refEntity;
le->leType = LE_FRAGMENT;
le->startTime = cg.time;
le->endTime = le->startTime + 30000 + random() * 3000;
VectorCopy( origin, re->origin );
AxisCopy( axisDefault, re->axis );
re->hModel = hModel;
le->pos.trType = TR_GRAVITY;
VectorCopy( origin, le->pos.trBase );
VectorCopy( velocity, le->pos.trDelta );
le->pos.trTime = cg.time;
bounce = le->bounceFactor;
bounce = 0.3;
le->leFlags = LEF_TUMBLE;
le->leBounceSoundType = LEBS_BRASS;
le->leMarkType = LEMT_NONE;
}
/*
===================
CG_BreakGlass
Breaks our brush and generates a few models on launches them all over the map :)
===================
*/
#define GLASS_VELOCITY 175 //175
#define GLASS_JUMP 125 //125
void CG_BreakGlass( vec3_t playerOrigin ) {
vec3_t origin, velocity;
int value;
int count = 20; //20
int states[] = {1,2,3};
int numstates = sizeof(states)/sizeof(states[0]);
while ( count-- ) {
value = states[rand()%numstates];
VectorCopy( playerOrigin, origin );
velocity[0] = crandom() * 165; //165
velocity[1] = crandom() * 125; //125
//velocity[2] = 0; //GLASS_JUMP + crandom() * 1; //165
velocity[2] = GLASS_JUMP + crandom() * 165; //165
switch (value) {
case 1:
CG_LaunchShard( origin, velocity, cgs.media.glass01 );
break;
case 2:
CG_LaunchShard( origin, velocity, cgs.media.glass02 );
break;
case 3:
CG_LaunchShard( origin, velocity, cgs.media.glass03 );
break;
}
}
}
/*
==================
CG_LaunchWood
==================
*/
void CG_LaunchWood( vec3_t origin, vec3_t velocity, qhandle_t hModel ) {
int bounce;
localEntity_t *le;
refEntity_t *re;
le = CG_AllocLocalEntity();
re = &le->refEntity;
le->leType = LE_FRAGMENT;
le->startTime = cg.time;
le->endTime = le->startTime + 30000 + random() * 3000;
VectorCopy( origin, re->origin );
AxisCopy( axisDefault, re->axis );
re->hModel = hModel;
le->pos.trType = TR_GRAVITY;
VectorCopy( origin, le->pos.trBase );
VectorCopy( velocity, le->pos.trDelta );
le->pos.trTime = cg.time;
bounce = le->bounceFactor;
bounce = 0.9; //0.3
//newq3ball
/* pm->ps->velocity[2] = -vel * 0.5; //2
if (pm->ps->velocity[2] <= 0.001) {
pm->ps->velocity[2] = 0;
*/
//endnew
le->leFlags = LEF_TUMBLE;
le->leBounceSoundType = LEBS_BRASS;
le->leMarkType = LEMT_NONE;
}
/*
===================
CG_BREAKWOOD
Breaks our brush and generates a few (here 1 model) on launches them all over the map :)
===================
*/
#define BOX_VELOCITY 60 //175
#define BOX_JUMP 85 //125
void CG_BREAKWOOD( vec3_t playerOrigin ) {
vec3_t origin, velocity;
int value;
int count = 8; //20
int states[] = {1,2,3};
int numstates = sizeof(states)/sizeof(states[0]);
while ( count-- ) {
value = states[rand()%numstates];
VectorCopy( playerOrigin, origin );
velocity[0] = crandom() * 80; //165
velocity[1] = crandom() * 125; //125
velocity[2] = BOX_JUMP + crandom() * 165; //165
//velocity[2] = 165; //165
//newq3ball
// velocity[2] = -velocity[0] * 0.5; //2
// if (velocity[2] <= 0.001) {
// velocity[2] = 0;
// }
//endnew
switch (value) {
case 1:
CG_LaunchWood( origin, velocity, cgs.media.wood01 );
break;
case 2:
CG_LaunchWood( origin, velocity, cgs.media.wood02 );
break;
case 3:
CG_LaunchWood( origin, velocity, cgs.media.wood03 );
break;
}
}
}
/*
==================
CG_LaunchMetal
==================
*/
void CG_LaunchMetal( vec3_t origin, vec3_t velocity, qhandle_t hModel ) {
int bounce;
localEntity_t *le;
refEntity_t *re;
le = CG_AllocLocalEntity();
re = &le->refEntity;
le->leType = LE_FRAGMENT;
le->startTime = cg.time;
le->endTime = le->startTime + 30000 + random() * 3000;
VectorCopy( origin, re->origin );
AxisCopy( axisDefault, re->axis );
re->hModel = hModel;
le->pos.trType = TR_GRAVITY;
VectorCopy( origin, le->pos.trBase );
VectorCopy( velocity, le->pos.trDelta );
le->pos.trTime = cg.time;
bounce = le->bounceFactor;
bounce = 0.9; //0.3
le->leFlags = LEF_TUMBLE;
le->leBounceSoundType = LEBS_BRASS;
le->leMarkType = LEMT_NONE;
}
/*
===================
CG_BREAKMETAL
Breaks our brush and generates a few (here 1 model) on launches them all over the map :)
===================
*/
#define METAL_VELOCITY 60 //175
#define METAL_JUMP 85 //125
void CG_BREAKMETAL( vec3_t playerOrigin ) {
vec3_t origin, velocity;
int value;
int count = 8; //20
int states[] = {1,2,3};
int numstates = sizeof(states)/sizeof(states[0]);
while ( count-- ) {
value = states[rand()%numstates];
VectorCopy( playerOrigin, origin );
velocity[0] = crandom() * 80; //165
velocity[1] = crandom() * 125; //125
velocity[2] = METAL_JUMP + crandom() * 165; //165
//velocity[2] = 165; //165
//newq3ball
// velocity[2] = -velocity[0] * 0.5; //2
// if (velocity[2] <= 0.001) {
// velocity[2] = 0;
// }
//endnew
switch (value) {
case 1:
CG_LaunchMetal( origin, velocity, cgs.media.metal01 );
break;
case 2:
CG_LaunchMetal( origin, velocity, cgs.media.metal02 );
break;
case 3:
CG_LaunchMetal( origin, velocity, cgs.media.metal03 );
break;
}
}
}
/*
==================
CG_LaunchDebris
CG_LaunchFragment
==================
*/
void CG_LaunchDebris( vec3_t origin, vec3_t velocity, qhandle_t hModel ) {
void CG_LaunchFragment( vec3_t origin, vec3_t velocity, leTrailType_t trailType, qhandle_t hModel ) {
localEntity_t *le;
refEntity_t *re;
@ -1142,8 +873,16 @@ void CG_LaunchDebris( vec3_t origin, vec3_t velocity, qhandle_t hModel ) {
le->bounceFactor = 0.6f;
le->leBounceSoundType = LEBS_DEBRIS;
//le->leMarkType = LEMT_BLOOD;
if ( trailType == LETT_BLOOD ) {
le->leBounceSoundType = LEBS_BLOOD;
le->leMarkType = LEMT_BLOOD;
} else {
le->leBounceSoundType = LEBS_NONE;
le->leMarkType = LEMT_NONE;
}
le->leTrailType = trailType;
}
/*
@ -1153,7 +892,7 @@ CG_ShowDebris
Generated a bunch of debris launching out from an entity's location
===================
*/
void CG_ShowDebris( vec3_t srcOrigin, int count, int type ) {
void CG_ShowDebris( vec3_t srcOrigin, int count, int evType ) {
vec3_t origin, velocity;
int i, r;
@ -1162,44 +901,275 @@ void CG_ShowDebris( vec3_t srcOrigin, int count, int type ) {
velocity[0] = crandom()*GIB_VELOCITY;
velocity[1] = crandom()*GIB_VELOCITY;
velocity[2] = GIB_JUMP + crandom()*GIB_VELOCITY;
r = rand() % 8;
if ( type == EV_EMIT_DEBRIS_NORMAL ) {
if ( evType == EV_EMIT_DEBRIS_LIGHT ) {
r = rand() % 8;
if (r == 0)
CG_LaunchDebris( origin, velocity, cgs.media.debris1 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislight1 );
else if (r == 1)
CG_LaunchDebris( origin, velocity, cgs.media.debris2 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislight2 );
else if (r == 2)
CG_LaunchDebris( origin, velocity, cgs.media.debris3 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislight3 );
else if (r == 3)
CG_LaunchDebris( origin, velocity, cgs.media.debris4 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislight4 );
else if (r == 4)
CG_LaunchDebris( origin, velocity, cgs.media.debris5 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislight5 );
else if (r == 5)
CG_LaunchDebris( origin, velocity, cgs.media.debris6 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislight6 );
else if (r == 6)
CG_LaunchDebris( origin, velocity, cgs.media.debris7 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislight7 );
else if (r == 7)
CG_LaunchDebris( origin, velocity, cgs.media.debris8 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislight8 );
}
if ( type == EV_EMIT_DEBRIS_DARK ) {
if ( evType == EV_EMIT_DEBRIS_DARK ) {
r = rand() % 8;
if (r == 0)
CG_LaunchDebris( origin, velocity, cgs.media.debrisdark1 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdark1 );
else if (r == 1)
CG_LaunchDebris( origin, velocity, cgs.media.debrisdark2 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdark2 );
else if (r == 2)
CG_LaunchDebris( origin, velocity, cgs.media.debrisdark3 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdark3 );
else if (r == 3)
CG_LaunchDebris( origin, velocity, cgs.media.debrisdark4 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdark4 );
else if (r == 4)
CG_LaunchDebris( origin, velocity, cgs.media.debrisdark5 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdark5 );
else if (r == 5)
CG_LaunchDebris( origin, velocity, cgs.media.debrisdark6 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdark6 );
else if (r == 6)
CG_LaunchDebris( origin, velocity, cgs.media.debrisdark7 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdark7 );
else if (r == 7)
CG_LaunchDebris( origin, velocity, cgs.media.debrisdark8 );
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdark8 );
}
if ( evType == EV_EMIT_DEBRIS_LIGHT_LARGE ) {
r = rand() % 3;
if (r == 0)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislightlarge1 );
else if (r == 1)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislightlarge2 );
else if (r == 2)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrislightlarge3 );
}
if ( evType == EV_EMIT_DEBRIS_DARK_LARGE ) {
r = rand() % 3;
if (r == 0)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdarklarge1 );
else if (r == 1)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdarklarge2 );
else if (r == 2)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_CONCRETE, cgs.media.debrisdarklarge3 );
}
if ( evType == EV_EMIT_DEBRIS_WOOD ) {
r = rand() % 5;
if (r == 0)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_WOOD, cgs.media.debriswood1 );
else if (r == 1)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_WOOD, cgs.media.debriswood2 );
else if (r == 2)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_WOOD, cgs.media.debriswood3 );
else if (r == 3)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_WOOD, cgs.media.debriswood4 );
else if (r == 4)
CG_LaunchFragment( origin, velocity, LETT_DEBRIS_WOOD, cgs.media.debriswood5 );
}
if ( evType == EV_EMIT_DEBRIS_FLESH ) {
r = rand() % 10;
if (r == 0)
CG_LaunchFragment( origin, velocity, LETT_BLOOD, cgs.media.gibSkull );
else if (r == 1)
CG_LaunchFragment( origin, velocity, LETT_BLOOD, cgs.media.gibBrain );
else if (r == 2)
CG_LaunchFragment( origin, velocity, LETT_BLOOD, cgs.media.gibAbdomen );
else if (r == 3)
CG_LaunchFragment( origin, velocity, LETT_BLOOD, cgs.media.gibArm );
else if (r == 4)
CG_LaunchFragment( origin, velocity, LETT_BLOOD, cgs.media.gibChest );
else if (r == 5)
CG_LaunchFragment( origin, velocity, LETT_BLOOD, cgs.media.gibFist );
else if (r == 6)
CG_LaunchFragment( origin, velocity, LETT_BLOOD, cgs.media.gibFoot );
else if (r == 7)
CG_LaunchFragment( origin, velocity, LETT_BLOOD, cgs.media.gibForearm );
else if (r == 8)
CG_LaunchFragment( origin, velocity, LETT_BLOOD, cgs.media.gibIntestine );
else if (r == 9)
CG_LaunchFragment( origin, velocity, LETT_BLOOD, cgs.media.gibLeg );
}
if ( evType == EV_EMIT_DEBRIS_GLASS ) {
r = rand() % 15; //we're getting twice the number of small shards as big shards this way
if (r == 0 || r == 1)
CG_LaunchFragment( origin, velocity, LETT_NONE, cgs.media.debrisglass1 );
else if (r == 2 || r == 3)
CG_LaunchFragment( origin, velocity, LETT_NONE, cgs.media.debrisglass2 );
else if (r == 4 || r == 5)
CG_LaunchFragment( origin, velocity, LETT_NONE, cgs.media.debrisglass3 );
else if (r == 6 || r == 7)
CG_LaunchFragment( origin, velocity, LETT_NONE, cgs.media.debrisglass4 );
else if (r == 8 || r == 9)
CG_LaunchFragment( origin, velocity, LETT_NONE, cgs.media.debrisglass5 );
else if (r == 10)
CG_LaunchFragment( origin, velocity, LETT_NONE, cgs.media.debrisglasslarge1 );
else if (r == 11)
CG_LaunchFragment( origin, velocity, LETT_NONE, cgs.media.debrisglasslarge2 );
else if (r == 12)
CG_LaunchFragment( origin, velocity, LETT_NONE, cgs.media.debrisglasslarge3 );
else if (r == 13)
CG_LaunchFragment( origin, velocity, LETT_NONE, cgs.media.debrisglasslarge4 );
else if (r == 14)
CG_LaunchFragment( origin, velocity, LETT_NONE, cgs.media.debrisglasslarge5 );
}
}
}
}
/*
===================
CG_StartEarthquake
Starts an earthquake effect
===================
*/
int flagEarthquake = qfalse;
int earthquakeIntensity = 0;
int earthquakeStoptime = 0;
void CG_StartEarthquake(int intensity, int duration)
{
flagEarthquake = qtrue;
if ( intensity < earthquakeIntensity )
return;
earthquakeIntensity = intensity;
earthquakeStoptime = cg.time + duration;
}
void CG_Earthquake()
{
static float terremotoX, terremotoY, terremotoZ;
static terremotoTime = 0;
float realInt;
if ( !flagEarthquake )
return;
if ( earthquakeStoptime < cg.time )
{
flagEarthquake = qfalse;
earthquakeIntensity = 0;
return;
}
if ( terremotoTime < cg.time )
{
terremotoTime = cg.time += 50;
realInt = ((float)earthquakeIntensity + 1.0) / 2.0;
terremotoX = random() * realInt - realInt / 2;
terremotoY = random() * realInt - realInt / 2;
terremotoZ = random() * realInt - realInt / 2;
}
cg.refdefViewAngles[0] += terremotoX;
cg.refdefViewAngles[1] += terremotoY;
cg.refdefViewAngles[2] += terremotoZ;
AnglesToAxis( cg.refdefViewAngles, cg.refdef.viewaxis );
}
/*
===================
CG_ExplosionParticles
Shows particles
===================
*/
void CG_Particles( vec3_t origin, int count, int speed, int lifetime, int radius, int type, byte r, byte g, byte b ) {
int jump; // amount to nudge the particles trajectory vector up by
qhandle_t shader; // shader to use for the particles
int index;
vec3_t randVec, tempVec;
qboolean moveUp;
//jump = 70;
jump = speed;
shader = cgs.media.sparkShader;
for ( index = 0; index < count; index++ ) {
localEntity_t *le;
refEntity_t *re;
le = CG_AllocLocalEntity(); //allocate a local entity
re = &le->refEntity;
le->leFlags = LEF_PUFF_DONT_SCALE; //don't change the particle size
le->leType = LE_MOVE_SCALE_FADE; // particle should fade over time
le->startTime = cg.time; // set the start time of the particle to the current time
le->endTime = cg.time + lifetime + (random() * (lifetime / 2)); //life time will be anywhere between [lifetime] and [lifetime * 1.5]
le->lifeRate = 1.0 / ( le->endTime - le->startTime );
re = &le->refEntity;
re->shaderTime = cg.time / 1000.0f;
re->reType = RT_SPRITE;
re->rotation = 0;
re->radius = radius;
re->customShader = shader;
re->shaderRGBA[0] = r;
re->shaderRGBA[1] = g;
re->shaderRGBA[2] = b;
re->shaderRGBA[3] = 0xFF;
le->color[3] = 1.0;
if ( type == PT_GRAVITY )
le->pos.trType = TR_GRAVITY; // moves in a gravity affected arc
else
le->pos.trType = TR_LINEAR; // moves in straight line, outward from the origin
le->pos.trTime = cg.time;
VectorCopy( origin, le->pos.trBase );
VectorCopy( origin, re->origin );
tempVec[0] = crandom(); //between 1 and -1
tempVec[1] = crandom();
tempVec[2] = crandom();
VectorNormalize(tempVec);
VectorScale(tempVec, speed, randVec);
if ( type == PT_GRAVITY || type == PT_LINEAR_UP )
moveUp = qtrue;
else if ( type == PT_LINEAR_DOWN )
moveUp = qfalse;
else if (crandom() < 0)
moveUp = qtrue;
else
moveUp = qfalse;
if (moveUp)
randVec[2] += jump; //nudge the particles up a bit
else
randVec[2] -= jump; //nudge the particles down a bit
VectorCopy( randVec, le->pos.trDelta );
}
}
/*
===================
CG_ParticlesFromEntityState
Takes entitystate and extracts data inside to use for CG_Particles.
es->constantLight is used for the color of the particles.
es->eventParm is used for the number of particles.
es->generic1 is used for the speed of the particles.
===================
*/
void CG_ParticlesFromEntityState( vec3_t origin, int type, entityState_t *es) {
byte r, g, b;
int lifetime = 3000;
int radius = 3;
int speed = es->generic1;
r = es->constantLight & 255;
g = ( es->constantLight >> 8 ) & 255;
b = ( es->constantLight >> 16 ) & 255;
CG_Particles( origin, es->eventParm, speed, lifetime, radius, type, r, g, b );
}

View file

@ -29,7 +29,6 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
#ifdef MISSIONPACK // bk001205
#include "../../ui/menudef.h"
#endif
//==========================================================================
/*
@ -1344,26 +1343,7 @@ void CG_EntityEvent( centity_t *cent, vec3_t position ) {
// Q3Rally Code END
break;
// Q3Rally Code Start
case EV_BREAK_GLASS:
DEBUGNAME("EV_BREAK_GLASS");
trap_S_StartSound( NULL, es->number, CHAN_BODY, cgs.media.glassSound );
CG_BreakGlass( cent->lerpOrigin );
break;
case EV_BREAKWOOD:
DEBUGNAME("EV_BREAKWOOD");
trap_S_StartSound( NULL, es->number, CHAN_BODY, cgs.media.woodSound );
CG_BREAKWOOD( cent->lerpOrigin );
break;
case EV_BREAKMETAL:
DEBUGNAME("EV_BREAKMETAL");
trap_S_StartSound( NULL, es->number, CHAN_BODY, cgs.media.metalSound );
CG_BREAKMETAL( cent->lerpOrigin );
break;
// Q3Rally Code END
case EV_STOPLOOPINGSOUND:
DEBUGNAME("EV_STOPLOOPINGSOUND");
@ -1375,15 +1355,83 @@ void CG_EntityEvent( centity_t *cent, vec3_t position ) {
DEBUGNAME("EV_DEBUG_LINE");
CG_Beam( cent );
break;
case EV_EMIT_DEBRIS_NORMAL:
DEBUGNAME("EV_EMIT_DEBRIS_NORMAL");
CG_ShowDebris( cent->lerpOrigin, cent->currentState.eventParm, EV_EMIT_DEBRIS_NORMAL );
case EV_EMIT_DEBRIS_LIGHT:
DEBUGNAME("EV_EMIT_DEBRIS_LIGHT");
CG_ShowDebris( cent->lerpOrigin, es->eventParm, EV_EMIT_DEBRIS_LIGHT );
break;
case EV_EMIT_DEBRIS_DARK:
DEBUGNAME("EV_EMIT_DEBRIS_DARK");
CG_ShowDebris( cent->lerpOrigin, cent->currentState.eventParm, EV_EMIT_DEBRIS_DARK );
CG_ShowDebris( cent->lerpOrigin, es->eventParm, EV_EMIT_DEBRIS_DARK );
break;
case EV_EMIT_DEBRIS_LIGHT_LARGE:
DEBUGNAME("EV_EMIT_DEBRIS_LIGHT_LARGE");
CG_ShowDebris( cent->lerpOrigin, es->eventParm, EV_EMIT_DEBRIS_LIGHT_LARGE );
break;
case EV_EMIT_DEBRIS_DARK_LARGE:
DEBUGNAME("EV_EMIT_DEBRIS_DARK_LARGE");
CG_ShowDebris( cent->lerpOrigin, es->eventParm, EV_EMIT_DEBRIS_DARK_LARGE );
break;
case EV_EMIT_DEBRIS_WOOD:
DEBUGNAME("EV_EMIT_DEBRIS_WOOD");
CG_ShowDebris( cent->lerpOrigin, es->eventParm, EV_EMIT_DEBRIS_WOOD );
break;
case EV_EMIT_DEBRIS_FLESH:
DEBUGNAME("EV_EMIT_DEBRIS_FLESH");
CG_ShowDebris( cent->lerpOrigin, es->eventParm, EV_EMIT_DEBRIS_FLESH );
break;
case EV_EMIT_DEBRIS_GLASS:
DEBUGNAME("EV_EMIT_DEBRIS_GLASS");
CG_ShowDebris( cent->lerpOrigin, es->eventParm, EV_EMIT_DEBRIS_GLASS );
break;
case EV_EARTHQUAKE:
DEBUGNAME("EV_EARTHQUAKE");
CG_StartEarthquake((es->eventParm & 0x0F) + 1, ((1 + ((es->eventParm & 0xF0) >> 4)) * 2000) + 1000);
break;
case EV_EXPLOSION:
DEBUGNAME("EV_EXPLOSION");
// show plume (if enabled)
if ( cg_oldRocket.integer == 0 ) {
dir[0] = 0;
dir[1] = 0;
dir[2] = 25;
CG_ParticleExplosion( "explode1", cent->lerpOrigin, dir, 1400, 20, 30 );
}
// show explosion
dir[0] = 0;
dir[1] = 0;
dir[2] = 0;
CG_MakeExplosion( cent->lerpOrigin, dir, cgs.media.dishFlashModel, cgs.media.rocketExplosionShader, 1000, qtrue );
break;
case EV_PARTICLES_GRAVITY:
DEBUGNAME("EV_PARTICLES_GRAVITY");
CG_ParticlesFromEntityState( cent->lerpOrigin, PT_GRAVITY, es );
break;
case EV_PARTICLES_LINEAR:
DEBUGNAME("EV_PARTICLES_LINEAR");
CG_ParticlesFromEntityState( cent->lerpOrigin, PT_LINEAR_BOTH, es );
break;
case EV_PARTICLES_LINEAR_UP:
DEBUGNAME("EV_PARTICLES_LINEAR_UP");
CG_ParticlesFromEntityState( cent->lerpOrigin, PT_LINEAR_UP, es );
break;
case EV_PARTICLES_LINEAR_DOWN:
DEBUGNAME("EV_PARTICLES_LINEAR_DOWN");
CG_ParticlesFromEntityState( cent->lerpOrigin, PT_LINEAR_DOWN, es );
break;
default:

View file

@ -618,10 +618,21 @@ typedef enum {
EV_TAUNT_GUARDBASE,
EV_TAUNT_PATROL,
EV_EMIT_DEBRIS_NORMAL, // a target_debrisemitter that emits light concrete is triggered
EV_EMIT_DEBRIS_DARK // a target_debrisemitter that emits dark concrete is triggered
EV_EMIT_DEBRIS_LIGHT, // emit light concrete chunks
EV_EMIT_DEBRIS_DARK, // emit dark concrete chunks
EV_EMIT_DEBRIS_LIGHT_LARGE, // emit light large concrete chunks
EV_EMIT_DEBRIS_DARK_LARGE, // emit dark large concrete chunks
EV_EMIT_DEBRIS_WOOD, // emit wooden chunks
EV_EMIT_DEBRIS_FLESH, // emit gibs
EV_EMIT_DEBRIS_GLASS, // emite shards of glass
EV_EARTHQUAKE,
EV_EXPLOSION,
EV_PARTICLES_GRAVITY,
EV_PARTICLES_LINEAR,
EV_PARTICLES_LINEAR_UP,
EV_PARTICLES_LINEAR_DOWN,
} entity_event_t;

View file

@ -935,32 +935,16 @@ void G_Damage( gentity_t *targ, gentity_t *inflictor, gentity_t *attacker,
attacker = &g_entities[ENTITYNUM_WORLD];
}
// If we found a BreakGlass brush check and break it
if ( targ->s.eType == ET_BREAKGLASS ) {
targ->health -= damage;
G_BreakGlass( targ, point, mod );
return;
}
// If we found breakable wood brush check and break it
if ( targ->s.eType == ET_BREAKWOOD ) {
targ->health -= damage;
G_BREAKWOOD( targ, point, mod );
return;
}
// If we found breakable metal brush check and break it
if ( targ->s.eType == ET_BREAKMETAL ) {
targ->health -= damage;
G_BREAKMETAL( targ, point, mod );
return;
}
// shootable doors / buttons don't actually have any health // Rotating Doors
// shootable doors / buttons don't actually have any health
if ( targ->s.eType == ET_MOVER ) {
if ( targ->use && (targ->moverState == MOVER_POS1
|| targ->moverState == ROTATOR_POS1) ) {
targ->use( targ, inflictor, attacker );
} else if ( targ->use == NULL ) { // entity is a func_breakable
targ->health -= damage;
if (targ->health <= 0)
Break_Breakable(targ, attacker);
}
return;
}

View file

@ -1815,6 +1815,66 @@ void SP_func_static( gentity_t *ent ) {
VectorCopy( ent->s.origin, ent->r.currentOrigin );
}
/*
===============================================================================
BREAKABLE
===============================================================================
*/
//other is the player that broke the func_breakable
void Break_Breakable(gentity_t *ent, gentity_t *other) {
vec3_t size;
vec3_t center;
int count = 0;
int spawnflags = 0;
gentity_t *tmp;
int type = EV_EMIT_DEBRIS_LIGHT;
// Get the center of the glass (code donated by Perle)
VectorSubtract(ent->r.maxs, ent->r.mins, size);
VectorScale(size, 0.5, size);
VectorAdd(ent->r.mins, size, center);
ent->takedamage = qfalse;
ent->s.eType = ET_INVISIBLE;
G_UseTargets( ent, other );
//need to store properties of the entity in seperate variables because we're going to free the entity
if ( ent->count > 0) {
count = ent->count;
spawnflags = ent->spawnflags;
}
G_FreeEntity( ent );
//spray out debris
if ( count > 0 ) {
tmp = G_TempEntity( center, PickDebrisType( spawnflags ) );
tmp->s.eventParm = count;
}
}
/*QUAKED func_breakable (0 .5 .8) ? see PickDebrisType in g_util.c for spawnflags
A bmodel that just sits there, doing nothing. It is removed when it received a set amount of damage.
"model2" .md3 model to also draw
"color" constantLight color
"light" constantLight radius
"health" the amount of damage required before this entity is removed
*/
void SP_func_breakable( gentity_t *ent ) {
trap_SetBrushModel( ent, ent->model );
InitMover( ent );
VectorCopy( ent->s.origin, ent->s.pos.trBase );
VectorCopy( ent->s.origin, ent->r.currentOrigin );
ent->takedamage = qtrue;
ent->use = NULL;
ent->r.contents = CONTENTS_SOLID;
ent->clipmask = MASK_SOLID;
}
/*
===============================================================================

View file

@ -145,6 +145,7 @@ void SP_info_podium(gentity_t *ent);
void SP_func_plat (gentity_t *ent);
void SP_func_static (gentity_t *ent);
void SP_func_breakable (gentity_t *ent);
void SP_func_rotating (gentity_t *ent);
void SP_func_bobbing (gentity_t *ent);
void SP_func_pendulum( gentity_t *ent );
@ -152,11 +153,7 @@ void SP_func_button (gentity_t *ent);
void SP_func_door (gentity_t *ent);
void SP_func_train (gentity_t *ent);
void SP_func_timer (gentity_t *self);
// Q3Rally Code Start
void SP_func_breakglass (gentity_t *ent);
void SP_func_breakwood (gentity_t *ent);
void SP_func_breakmetal (gentity_t *ent);
// Q3Rally Code END
void SP_trigger_always (gentity_t *ent);
void SP_trigger_multiple (gentity_t *ent);
@ -179,6 +176,7 @@ void SP_target_position (gentity_t *ent);
void SP_target_location (gentity_t *ent);
void SP_target_push (gentity_t *ent);
void SP_target_debrisemitter (gentity_t *ent);
void SP_target_earthquake (gentity_t *ent);
void SP_light (gentity_t *self);
void SP_info_null (gentity_t *self);
@ -249,10 +247,7 @@ spawn_t spawns[] = {
{"func_train", SP_func_train},
{"func_group", SP_info_null},
{"func_timer", SP_func_timer}, // rename trigger_timer?
{"func_breakglass", SP_func_breakglass},
{"func_breakwood", SP_func_breakwood},
{"func_breakmetal", SP_func_breakmetal},
{"func_breakable", SP_func_breakable},
// Triggers are brush objects that cause an effect when contacted
// by a living player, usually involving firing targets.
@ -281,6 +276,7 @@ spawn_t spawns[] = {
{"target_location", SP_target_location},
{"target_push", SP_target_push},
{"target_debrisemitter", SP_target_debrisemitter},
{"target_earthquake", SP_target_earthquake},
{"light", SP_light},
{"path_corner", SP_path_corner},

View file

@ -712,6 +712,39 @@ gentity_t *findradius (gentity_t *from, vec3_t org, float rad)
return NULL;
}
/*
==================
PickDebrisType
returns a type of debris based on the passed spawnflags value
==================
*/
int PickDebrisType( int spawnflags ) {
if ( spawnflags & 1 )
return EV_EMIT_DEBRIS_LIGHT;
if ( spawnflags & 2 )
return EV_EMIT_DEBRIS_DARK;
if ( spawnflags & 4 )
return EV_EMIT_DEBRIS_LIGHT_LARGE;
if ( spawnflags & 8 )
return EV_EMIT_DEBRIS_DARK_LARGE;
if ( spawnflags & 16 )
return EV_EMIT_DEBRIS_WOOD;
if ( spawnflags & 32 )
return EV_EMIT_DEBRIS_FLESH;
if ( spawnflags & 64 )
return EV_EMIT_DEBRIS_GLASS;
//if no compatible spawnflags supplied, return EV_EMIT_DEBRIS_LIGHT
return EV_EMIT_DEBRIS_LIGHT;
}
// Perle - Code helper function
//
qboolean visible( gentity_t *ent1, gentity_t *ent2 ) {

View file

@ -855,92 +855,12 @@ q3rallycode
[Open project files]
0=engine\code\game\g_mover.c
1=engine\code\game\g_combat.c
2=engine\code\game\g_spawn.c
3=engine\code\cgame\cg_main.c
4=engine\code\cgame\cg_effects.c
5=engine\code\game\g_local.h
6=engine\code\game\g_misc.c
7=engine\code\cgame\cg_event.c
8=engine\code\cgame\cg_local.h
9=engine\code\ui\ui_main.c
10=engine\code\server\sv_main.c
11=engine\code\renderer\tr_public.h
12=engine\code\botlib\botlib.h
13=engine\code\client\cl_cgame.c
14=engine\code\client\client.h
15=engine\code\game\ai_main.c
16=engine\code\qcommon\common.c
17=engine\code\qcommon\qcommon.h
18=engine\code\server\server.h
19=engine\code\zlib\adler32.c
20=engine\ChangeLog
21=engine\code\qcommon\files.c
[Selected Project Files]
Main=
Selected=engine\code\game\g_mover.c
Selected=engine\code\game\g_combat.c
[engine\code\game\g_mover.c]
TopLine=1659
Caret=33,1676
TopLine=1817
Caret=21,1827
[engine\code\game\g_combat.c]
TopLine=931
Caret=1,941
[engine\code\game\g_spawn.c]
TopLine=235
Caret=40,250
[engine\code\cgame\cg_main.c]
TopLine=1178
Caret=1,1206
[engine\code\cgame\cg_effects.c]
TopLine=905
Caret=1,919
[engine\code\game\g_local.h]
TopLine=675
Caret=1,691
[engine\code\game\g_misc.c]
TopLine=751
Caret=3,768
[engine\code\cgame\cg_event.c]
TopLine=1337
Caret=1,1351
[engine\code\cgame\cg_local.h]
TopLine=1727
Caret=54,1743
[engine\code\ui\ui_main.c]
TopLine=3236
Caret=1,3250
[engine\code\server\sv_main.c]
TopLine=49
Caret=1,49
[engine\code\renderer\tr_public.h]
TopLine=135
Caret=1,149
[engine\code\botlib\botlib.h]
TopLine=477
Caret=1,491
[engine\code\client\cl_cgame.c]
TopLine=368
Caret=1,382
[engine\code\client\client.h]
TopLine=445
Caret=1,459
[engine\code\game\ai_main.c]
TopLine=1590
Caret=1,1604
[engine\code\qcommon\common.c]
TopLine=2473
Caret=1,2487
[engine\code\qcommon\qcommon.h]
TopLine=665
Caret=1,679
[engine\code\server\server.h]
TopLine=159
Caret=1,173
[engine\code\zlib\adler32.c]
TopLine=1
Caret=1,1
[engine\ChangeLog]
TopLine=61
Caret=1,75
[engine\code\qcommon\files.c]
TopLine=188
Caret=34,201
TopLine=1027
Caret=14,959