For VM 0-03-00
Lots of little bug-fixes and stuff
This commit is contained in:
Victor Chow 2001-07-09 00:32:10 +00:00
parent a772993171
commit bb4f35017c
21 changed files with 461 additions and 125 deletions

View file

@ -2689,6 +2689,59 @@ static void CG_DrawTourneyScoreboard() {
#endif #endif
} }
/*
=====================
CG_DrawDamageBlend
Elder: Does a fullscreen alpha blend like Quake 2 when hurt
=====================
*/
#define MAX_DAMAGE_ALPHA 0.75
#define MAX_BLEND_TIME 1500
static void CG_DrawDamageBlend()
{
float dmg;
vec4_t damageColor;
//Leave if no true damage, disabled, or ragepro
if ( !cg.rq3_trueDamage || !rxn_painblend.integer ||
cgs.glconfig.hardwareType == GLHW_RAGEPRO)
{
return;
}
//Clamp blend time
if (cg.rq3_blendTime > MAX_BLEND_TIME)
cg.rq3_blendTime = MAX_BLEND_TIME;
//Reset if we've gone past our blendTime
if (cg.time - cg.damageTime > cg.rq3_blendTime) {
//cg.rq3_trueDamage = 0;
cg.rq3_blendTime = 0;
return;
}
VectorCopy(colorRed, damageColor);
dmg = cg.rq3_trueDamage;
//clamp at 100 health
if (dmg > 100)
dmg = 100;
damageColor[3] = MAX_DAMAGE_ALPHA * (dmg / 100.0) * (1.0 - (cg.time - cg.damageTime) / cg.rq3_blendTime);
if (damageColor[3] > MAX_DAMAGE_ALPHA)
damageColor[3] = MAX_DAMAGE_ALPHA;
else if (damageColor[3] < 0)
damageColor[3] = 0;
CG_FillRect(0,0, SCREEN_WIDTH, SCREEN_HEIGHT, damageColor);
}
/* /*
===================== =====================
CG_DrawActive CG_DrawActive
@ -2746,6 +2799,9 @@ void CG_DrawActive( stereoFrame_t stereoView ) {
VectorCopy( baseOrg, cg.refdef.vieworg ); VectorCopy( baseOrg, cg.refdef.vieworg );
} }
// Elder: draw damage blend
CG_DrawDamageBlend();
// draw status bar and other floating elements // draw status bar and other floating elements
CG_Draw2D(); CG_Draw2D();
} }

View file

@ -525,7 +525,18 @@ static void CG_Missile( centity_t *cent ) {
// spin as it moves // spin as it moves
if ( s1->pos.trType != TR_STATIONARY ) { if ( s1->pos.trType != TR_STATIONARY ) {
RotateAroundDirection( ent.axis, cg.time / 4 ); //Spin knife like a wheel
if ( s1->weapon == WP_KNIFE ) {
vec3_t knifeVelocity;
BG_EvaluateTrajectoryDelta(&s1->pos, cg.time, knifeVelocity);
vectoangles(knifeVelocity, cent->lerpAngles);
cent->lerpAngles[0] += cg.time / 6;
AnglesToAxis( cent->lerpAngles, ent.axis );
}
else
RotateAroundDirection( ent.axis, cg.time / 4 );
} else { } else {
#ifdef MISSIONPACK #ifdef MISSIONPACK
if ( s1->weapon == WP_PROX_LAUNCHER ) { if ( s1->weapon == WP_PROX_LAUNCHER ) {

View file

@ -1764,18 +1764,20 @@ void CG_EntityEvent( centity_t *cent, vec3_t position ) {
#ifdef MISSIONPACK #ifdef MISSIONPACK
case EV_PROXIMITY_MINE_STICK: case EV_PROXIMITY_MINE_STICK:
DEBUGNAME("EV_PROXIMITY_MINE_STICK"); DEBUGNAME("EV_PROXIMITY_MINE_STICK");
//Elder: removed
if( es->eventParm & SURF_FLESH ) { if( es->eventParm & SURF_FLESH ) {
trap_S_StartSound (NULL, es->number, CHAN_AUTO, cgs.media.wstbimplSound ); //trap_S_StartSound (NULL, es->number, CHAN_AUTO, cgs.media.wstbimplSound );
} else if( es->eventParm & SURF_METALSTEPS ) { } else if( es->eventParm & SURF_METALSTEPS ) {
trap_S_StartSound (NULL, es->number, CHAN_AUTO, cgs.media.wstbimpmSound ); //trap_S_StartSound (NULL, es->number, CHAN_AUTO, cgs.media.wstbimpmSound );
} else { } else {
trap_S_StartSound (NULL, es->number, CHAN_AUTO, cgs.media.wstbimpdSound ); //trap_S_StartSound (NULL, es->number, CHAN_AUTO, cgs.media.wstbimpdSound );
} }
break; break;
case EV_PROXIMITY_MINE_TRIGGER: case EV_PROXIMITY_MINE_TRIGGER:
DEBUGNAME("EV_PROXIMITY_MINE_TRIGGER"); DEBUGNAME("EV_PROXIMITY_MINE_TRIGGER");
trap_S_StartSound (NULL, es->number, CHAN_AUTO, cgs.media.wstbactvSound ); //Elder: removed
//trap_S_StartSound (NULL, es->number, CHAN_AUTO, cgs.media.wstbactvSound );
break; break;
case EV_KAMIKAZE: case EV_KAMIKAZE:
DEBUGNAME("EV_KAMIKAZE"); DEBUGNAME("EV_KAMIKAZE");

View file

@ -189,20 +189,20 @@ void CG_DrawInformation( void ) {
//Elder: Initial y-position //Elder: Initial y-position
y = 96; y = 96;
// don't print server lines if playing a local game // map-specific message (long map name)
trap_Cvar_VariableStringBuffer( "sv_running", buf, sizeof( buf ) ); s = CG_ConfigString( CS_MESSAGE );
if ( !atoi( buf ) ) { if ( s[0] ) {
// map-specific message (long map name)
s = CG_ConfigString( CS_MESSAGE );
if ( s[0] ) {
//UI_DrawProportionalString( 4, y, s, //UI_DrawProportionalString( 4, y, s,
//UI_LEFT|UI_SMALLFONT|UI_DROPSHADOW, colorWhite ); //UI_LEFT|UI_SMALLFONT|UI_DROPSHADOW, colorWhite );
//Q_strncpyz(buf, s, 1024); //Q_strncpyz(buf, s, 1024);
//Q_CleanStr(buf); //Q_CleanStr(buf);
CG_DrawSmallStringColor(x, y, s, colorWhite); CG_DrawSmallStringColor(x, y, s, colorWhite);
y += SMALLCHAR_HEIGHT; y += SMALLCHAR_HEIGHT;
} }
// don't print server lines if playing a local game
trap_Cvar_VariableStringBuffer( "sv_running", buf, sizeof( buf ) );
if ( !atoi( buf ) ) {
// server hostname // server hostname
Q_strncpyz(buf, Info_ValueForKey( info, "sv_hostname" ), 1024); Q_strncpyz(buf, Info_ValueForKey( info, "sv_hostname" ), 1024);

View file

@ -368,7 +368,7 @@ typedef struct weaponInfo_s {
qhandle_t barrelModel; qhandle_t barrelModel;
qhandle_t flashModel; qhandle_t flashModel;
//Elder: added third person model to weaponInfo structure //Elder: added third person model to weaponInfo structure
qhandle_t thirdModel; qhandle_t firstModel;
vec3_t weaponMidpoint; // so it will rotate centered instead of by tag vec3_t weaponMidpoint; // so it will rotate centered instead of by tag
@ -593,6 +593,11 @@ typedef struct {
float damageTime; float damageTime;
float damageX, damageY, damageValue; float damageX, damageY, damageValue;
//Elder: added for alpha pain blend
int rq3_trueDamage; //Q3 doesn't hold the actual damage amount in cg.damageValue
//float rq3_lastPainAlpha;
float rq3_blendTime; //How long we take to fade out
// status bar head // status bar head
float headYaw; float headYaw;
float headEndPitch; float headEndPitch;
@ -711,7 +716,7 @@ typedef struct {
//Elder: akimbo stuff - since it's valid every game //Elder: akimbo stuff - since it's valid every game
qhandle_t akimboModel; qhandle_t akimboModel;
qhandle_t akimboFlashModel; qhandle_t akimboFlashModel;
qhandle_t akimbo3rdModel; qhandle_t akimbo1stModel;
qhandle_t akimboHandModel; qhandle_t akimboHandModel;
@ -788,6 +793,14 @@ typedef struct {
qhandle_t dishFlashModel; qhandle_t dishFlashModel;
qhandle_t lightningExplosionModel; qhandle_t lightningExplosionModel;
// Elder: RQ3 item models
qhandle_t rq3_kevlarModel;
qhandle_t rq3_bandolierModel;
qhandle_t rq3_silencerModel;
qhandle_t rq3_laserModel;
qhandle_t rq3_slippersModel;
// weapon effect shaders // weapon effect shaders
qhandle_t railExplosionShader; qhandle_t railExplosionShader;
qhandle_t plasmaExplosionShader; qhandle_t plasmaExplosionShader;
@ -988,10 +1001,11 @@ typedef struct {
sfxHandle_t n_healthSound; sfxHandle_t n_healthSound;
sfxHandle_t hgrenb1aSound; sfxHandle_t hgrenb1aSound;
sfxHandle_t hgrenb2aSound; sfxHandle_t hgrenb2aSound;
sfxHandle_t wstbimplSound; //Elder: removed
sfxHandle_t wstbimpmSound; //sfxHandle_t wstbimplSound;
sfxHandle_t wstbimpdSound; //sfxHandle_t wstbimpmSound;
sfxHandle_t wstbactvSound; //sfxHandle_t wstbimpdSound;
//sfxHandle_t wstbactvSound;
} cgMedia_t; } cgMedia_t;
@ -1168,6 +1182,8 @@ extern vmCvar_t rxn_drawWeapon;
extern vmCvar_t rxn_glasstime; extern vmCvar_t rxn_glasstime;
//Elder: muzzle flash toggle //Elder: muzzle flash toggle
extern vmCvar_t rxn_flash; extern vmCvar_t rxn_flash;
//Elder: turn on or off alpha blending
extern vmCvar_t rxn_painblend;
extern vmCvar_t cg_drawFriend; extern vmCvar_t cg_drawFriend;
extern vmCvar_t cg_teamChatsOnly; extern vmCvar_t cg_teamChatsOnly;
extern vmCvar_t cg_noVoiceChats; extern vmCvar_t cg_noVoiceChats;

View file

@ -142,6 +142,8 @@ vmCvar_t rxn_drawWeapon;
vmCvar_t rxn_glasstime; vmCvar_t rxn_glasstime;
//Elder: muzzle flash toggle //Elder: muzzle flash toggle
vmCvar_t rxn_flash; vmCvar_t rxn_flash;
//Elder: turn on or off alpha blending
vmCvar_t rxn_painblend;
vmCvar_t cg_drawFriend; vmCvar_t cg_drawFriend;
vmCvar_t cg_teamChatsOnly; vmCvar_t cg_teamChatsOnly;
vmCvar_t cg_noVoiceChats; vmCvar_t cg_noVoiceChats;
@ -295,7 +297,8 @@ cvarTable_t cvarTable[] = {
{ &rxn_drawWeapon, "rxn_drawWeapon", "2", CVAR_ARCHIVE }, { &rxn_drawWeapon, "rxn_drawWeapon", "2", CVAR_ARCHIVE },
{ &rxn_glasstime, "rxn_glasstime", "0", CVAR_ARCHIVE }, { &rxn_glasstime, "rxn_glasstime", "0", CVAR_ARCHIVE },
//Elder: added //Elder: added
{ &rxn_flash, "rxn_flash", "1", CVAR_ARCHIVE } { &rxn_flash, "rxn_flash", "1", CVAR_ARCHIVE },
{ &rxn_painblend, "rxn_painblend", "1", CVAR_ARCHIVE }
// { &cg_pmove_fixed, "cg_pmove_fixed", "0", CVAR_USERINFO | CVAR_ARCHIVE } // { &cg_pmove_fixed, "cg_pmove_fixed", "0", CVAR_USERINFO | CVAR_ARCHIVE }
}; };
@ -754,10 +757,11 @@ static void CG_RegisterSounds( void ) {
cgs.media.n_healthSound = trap_S_RegisterSound("sound/items/n_health.wav", qfalse ); cgs.media.n_healthSound = trap_S_RegisterSound("sound/items/n_health.wav", qfalse );
cgs.media.hgrenb1aSound = trap_S_RegisterSound("sound/weapons/grenade/hgrenb1a.wav", qfalse); cgs.media.hgrenb1aSound = trap_S_RegisterSound("sound/weapons/grenade/hgrenb1a.wav", qfalse);
cgs.media.hgrenb2aSound = trap_S_RegisterSound("sound/weapons/grenade/hgrenb2a.wav", qfalse); cgs.media.hgrenb2aSound = trap_S_RegisterSound("sound/weapons/grenade/hgrenb2a.wav", qfalse);
cgs.media.wstbimplSound = trap_S_RegisterSound("sound/weapons/proxmine/wstbimpl.wav", qfalse); //Elder: removed
cgs.media.wstbimpmSound = trap_S_RegisterSound("sound/weapons/proxmine/wstbimpm.wav", qfalse); //cgs.media.wstbimplSound = trap_S_RegisterSound("sound/weapons/proxmine/wstbimpl.wav", qfalse);
cgs.media.wstbimpdSound = trap_S_RegisterSound("sound/weapons/proxmine/wstbimpd.wav", qfalse); //cgs.media.wstbimpmSound = trap_S_RegisterSound("sound/weapons/proxmine/wstbimpm.wav", qfalse);
cgs.media.wstbactvSound = trap_S_RegisterSound("sound/weapons/proxmine/wstbactv.wav", qfalse); //cgs.media.wstbimpdSound = trap_S_RegisterSound("sound/weapons/proxmine/wstbimpd.wav", qfalse);
//cgs.media.wstbactvSound = trap_S_RegisterSound("sound/weapons/proxmine/wstbactv.wav", qfalse);
} }
@ -975,9 +979,16 @@ static void CG_RegisterGraphics( void ) {
//Elder: akimbos - some of the stuff isn't in yet :p //Elder: akimbos - some of the stuff isn't in yet :p
cgs.media.akimboModel = trap_R_RegisterModel( "models/weapons2/akimbo/akimbo.md3" ); cgs.media.akimboModel = trap_R_RegisterModel( "models/weapons2/akimbo/akimbo.md3" );
cgs.media.akimboFlashModel = trap_R_RegisterModel( "models/weapons2/akimbo/akimbo_flash.md3" ); cgs.media.akimboFlashModel = trap_R_RegisterModel( "models/weapons2/akimbo/akimbo_flash.md3" );
cgs.media.akimbo3rdModel = trap_R_RegisterModel( "models/weapons2/akimbo_3rd.md3" ); cgs.media.akimbo1stModel = trap_R_RegisterModel( "models/weapons2/akimbo_1st.md3" );
cgs.media.akimboHandModel = trap_R_RegisterModel( "models/weapons2/akimbo/akimbo_hand.md3" ); cgs.media.akimboHandModel = trap_R_RegisterModel( "models/weapons2/akimbo/akimbo_hand.md3" );
//Elder: item cache
cgs.media.rq3_bandolierModel = trap_R_RegisterModel( "models/items/bandolier.md3" );
cgs.media.rq3_kevlarModel = trap_R_RegisterModel( "models/items/kevlar.md3" );
cgs.media.rq3_silencerModel = trap_R_RegisterModel( "models/items/silencer.md3" );
cgs.media.rq3_laserModel = trap_R_RegisterModel( "models/items/laser.md3" );
cgs.media.rq3_slippersModel = trap_R_RegisterModel( "models/items/slippers.md3" );
cgs.media.smoke2 = trap_R_RegisterModel( "models/weapons2/shells/s_shell.md3" ); cgs.media.smoke2 = trap_R_RegisterModel( "models/weapons2/shells/s_shell.md3" );
cgs.media.balloonShader = trap_R_RegisterShader( "sprites/balloon3" ); cgs.media.balloonShader = trap_R_RegisterShader( "sprites/balloon3" );
@ -1975,6 +1986,8 @@ void CG_EventHandling(int type) {
void CG_KeyEvent(int key, qboolean down) { void CG_KeyEvent(int key, qboolean down) {
//Elder: Let's see what we're pressing
//CG_Printf("Key: %i, isDown: %d\n", key, down);
} }
void CG_MouseEvent(int x, int y) { void CG_MouseEvent(int x, int y) {

View file

@ -57,7 +57,8 @@ void CG_CheckAmmo( void ) {
if ( total == 0 ) { if ( total == 0 ) {
cg.lowAmmoWarning = 2; cg.lowAmmoWarning = 2;
} else { } else {
cg.lowAmmoWarning = 1; //Elder: only allow completely empty ammo warning sounds
//cg.lowAmmoWarning = 1;
} }
// play a sound on transitions // play a sound on transitions
@ -81,8 +82,17 @@ void CG_DamageFeedback( int yawByte, int pitchByte, int damage ) {
float dist; float dist;
float yaw, pitch; float yaw, pitch;
//Elder: removed
// show the attacking player's head and name in corner // show the attacking player's head and name in corner
cg.attackerTime = cg.time; //cg.attackerTime = cg.time;
//Elder: added
cg.rq3_trueDamage = damage;
//Elder: memset in cg_main.c should let us increment safely
if (damage * 10 < 100)
cg.rq3_blendTime += 100;
else
cg.rq3_blendTime += damage * 10;
// the lower on health you are, the greater the view kick will be // the lower on health you are, the greater the view kick will be
health = cg.snap->ps.stats[STAT_HEALTH]; health = cg.snap->ps.stats[STAT_HEALTH];

View file

@ -622,7 +622,6 @@ static void CG_DamageBlendBlob( void ) {
return; return;
} }
memset( &ent, 0, sizeof( ent ) ); memset( &ent, 0, sizeof( ent ) );
ent.reType = RT_SPRITE; ent.reType = RT_SPRITE;
ent.renderfx = RF_FIRST_PERSON; ent.renderfx = RF_FIRST_PERSON;

View file

@ -515,17 +515,18 @@ void CG_RegisterWeapon( int weaponNum ) {
//Elder: added to cache 3rd-person models (hopefully) //Elder: added to cache 3rd-person models (hopefully)
strcpy( path, item->world_model[0] ); strcpy( path, item->world_model[0] );
COM_StripExtension( path, path ); COM_StripExtension( path, path );
strcat( path, "_3rd.md3" ); //Elder: changed from _3rd to _1st
weaponInfo->thirdModel = trap_R_RegisterModel( path ); strcat( path, "_1st.md3" );
weaponInfo->firstModel = trap_R_RegisterModel( path );
if ( !weaponInfo->handsModel ) { if ( !weaponInfo->handsModel ) {
//Elder: WTF!? //Elder: WTF!?
weaponInfo->handsModel = trap_R_RegisterModel( "models/weapons2/m3/m3_hand.md3" ); weaponInfo->handsModel = trap_R_RegisterModel( "models/weapons2/m3/m3_hand.md3" );
} }
//Elder: if no _3rd model, point to the weaponModel... this may get funky :) //Elder: if no _1st model, point to the weaponModel... this may get funky :)
if ( !weaponInfo->thirdModel ) { if ( !weaponInfo->firstModel ) {
weaponInfo->thirdModel = weaponInfo->weaponModel; weaponInfo->firstModel = weaponInfo->weaponModel;
} }
weaponInfo->loopFireSound = qfalse; weaponInfo->loopFireSound = qfalse;
@ -737,7 +738,8 @@ void CG_RegisterWeapon( int weaponNum ) {
break; break;
case WP_GRENADE: case WP_GRENADE:
weaponInfo->missileModel = trap_R_RegisterModel( "models/weapons2/grenade/grenade_3rd.md3" ); //Changed from _3rd
weaponInfo->missileModel = trap_R_RegisterModel( "models/weapons2/grenade/grenade.md3" );
weaponInfo->missileTrailFunc = CG_GrenadeTrail; weaponInfo->missileTrailFunc = CG_GrenadeTrail;
weaponInfo->wiTrailTime = 700; weaponInfo->wiTrailTime = 700;
weaponInfo->trailRadius = 32; weaponInfo->trailRadius = 32;
@ -1099,8 +1101,8 @@ void CG_AddPlayerWeapon( refEntity_t *parent, playerState_t *ps, centity_t *cent
//} //}
if (ps == NULL) if (ps == NULL)
{ {
//Elder: We are in third person, use the third-person model //Elder: We are in third person, use the third-person model (DEFAULT)
gun.hModel = weapon->thirdModel; gun.hModel = weapon->weaponModel;
/* Elder: use the cached model above /* Elder: use the cached model above
switch (weaponNum)//Blaze: Used to make the third person weapon models different then 1st person switch (weaponNum)//Blaze: Used to make the third person weapon models different then 1st person
@ -1140,8 +1142,8 @@ void CG_AddPlayerWeapon( refEntity_t *parent, playerState_t *ps, centity_t *cent
*/ */
} }
else { else {
//Elder: we are in first-person, use the first-person (default) model //Elder: we are in first-person, use the first-person (NOT default) model
gun.hModel = weapon->weaponModel; gun.hModel = weapon->firstModel;
} }
if (!gun.hModel) { if (!gun.hModel) {
@ -1289,11 +1291,11 @@ void CG_AddPlayerWeapon( refEntity_t *parent, playerState_t *ps, centity_t *cent
if ( rxn_flash.integer ) { if ( rxn_flash.integer ) {
if (ps) { if (ps) {
//Elder: draw flash based on first-person view //Elder: draw flash based on first-person view
CG_PositionRotatedEntityOnTag( &flash, &gun, weapon->weaponModel, "tag_flash"); CG_PositionRotatedEntityOnTag( &flash, &gun, weapon->firstModel, "tag_flash");
} }
else { else {
//Elder: draw flash based on 3rd-person view //Elder: draw flash based on 3rd-person view
CG_PositionRotatedEntityOnTag( &flash, &gun, weapon->thirdModel, "tag_flash"); CG_PositionRotatedEntityOnTag( &flash, &gun, weapon->weaponModel, "tag_flash");
} }
trap_R_AddRefEntityToScene( &flash ); trap_R_AddRefEntityToScene( &flash );

View file

@ -185,13 +185,15 @@ gitem_t bg_itemlist[] =
/* precache */ "", /* precache */ "",
/* sounds */ "" /* sounds */ ""
}, },
//Blaze: 3rd Person Models //Blaze: 3rd Person Models
//Elder: 07/06/2001: Now known as 1st-person models!
//Knife //Knife
{ {
"knife_3rd", "knife_1st",
NULL, NULL,
{"models/weapons2/knife/knife_3rd.md3",0,0,0}, {"models/weapons2/knife/knife_1st.md3",0,0,0},
"icons/iconw_knife", "icons/iconw_knife",
RQ3_KNIFE_NAME, RQ3_KNIFE_NAME,
1, 1,
@ -203,9 +205,9 @@ gitem_t bg_itemlist[] =
//Pistol //Pistol
{ {
"pistol_3rd", "pistol_1st",
NULL, NULL,
{ "models/weapons2/mk23/mk23_3rd.md3", { "models/weapons2/mk23/mk23_1st.md3",
0, 0, 0}, 0, 0, 0},
"icons/iconw_mk23", "icons/iconw_mk23",
RQ3_PISTOL_NAME, RQ3_PISTOL_NAME,
@ -218,9 +220,9 @@ gitem_t bg_itemlist[] =
//M4 //M4
{ {
"m4_3rd", "m4_1st",
NULL, NULL,
{ "models/weapons2/m4/m4_3rd.md3", { "models/weapons2/m4/m4_1st.md3",
0, 0, 0}, 0, 0, 0},
"icons/iconw_m4", "icons/iconw_m4",
RQ3_M4_NAME, RQ3_M4_NAME,
@ -233,9 +235,9 @@ gitem_t bg_itemlist[] =
//SSG3000 //SSG3000
{ {
"ssg3000_3rd", "ssg3000_1st",
NULL, NULL,
{ "models/weapons2/ssg3000/ssg3000_3rd.md3", { "models/weapons2/ssg3000/ssg3000_1st.md3",
0, 0, 0}, 0, 0, 0},
"icons/iconw_ssg", "icons/iconw_ssg",
RQ3_SSG3000_NAME, RQ3_SSG3000_NAME,
@ -248,9 +250,9 @@ gitem_t bg_itemlist[] =
//MP5 //MP5
{ {
"mp5_3rd", "mp5_1st",
NULL, NULL,
{ "models/weapons2/mp5/mp5_3rd.md3", { "models/weapons2/mp5/mp5_1st.md3",
0, 0, 0}, 0, 0, 0},
"icons/iconw_mp5", "icons/iconw_mp5",
RQ3_MP5_NAME, RQ3_MP5_NAME,
@ -263,9 +265,9 @@ gitem_t bg_itemlist[] =
//Handcannon //Handcannon
{ {
"handcannon_3rd", "handcannon_1st",
NULL, NULL,
{ "models/weapons2/handcannon/handcannon_3rd.md3", { "models/weapons2/handcannon/handcannon_1st.md3",
0, 0, 0}, 0, 0, 0},
"icons/iconw_sawedoff", "icons/iconw_sawedoff",
RQ3_HANDCANNON_NAME, RQ3_HANDCANNON_NAME,
@ -278,9 +280,9 @@ gitem_t bg_itemlist[] =
//Shotgun //Shotgun
{ {
"m3_3rd", "m3_1st",
NULL, NULL,
{ "models/weapons2/m3/m3_3rd.md3", { "models/weapons2/m3/m3_1st.md3",
0, 0, 0}, 0, 0, 0},
"icons/iconw_m3", "icons/iconw_m3",
RQ3_M3_NAME, RQ3_M3_NAME,
@ -293,9 +295,9 @@ gitem_t bg_itemlist[] =
//Akimbo Placeholder //Akimbo Placeholder
{ {
"akimbo_3rd", "akimbo_1st",
NULL, NULL,
{ "models/weapons2/akimbo/akimbo_3rd.md3", { "models/weapons2/akimbo/akimbo_1st.md3",
0, 0, 0}, 0, 0, 0},
"icons/iconw_akimbo", "icons/iconw_akimbo",
RQ3_AKIMBO_NAME, RQ3_AKIMBO_NAME,
@ -309,9 +311,9 @@ gitem_t bg_itemlist[] =
//Grenade //Grenade
{ {
"grenade_3rd", "grenade_1st",
NULL, NULL,
{ "models/weapons2/grenade/grenade_3rd.md3", { "models/weapons2/grenade/grenade_1st.md3",
0, 0, 0}, 0, 0, 0},
"icons/iconw_gren", "icons/iconw_gren",
RQ3_GRENADE_NAME, RQ3_GRENADE_NAME,
@ -466,13 +468,14 @@ Only in CTF games
/* sounds */ "" /* sounds */ ""
}, },
//Elder: RQ3 Items
{ {
"item_kevlar", "item_kevlar",
"sound/items/kevlar.wav", "sound/items/kevlar.wav",
{ "models/items/kevlar.md3", { "models/items/kevlar.md3",
0, 0, 0}, 0, 0, 0},
"icons/kevlar", "icons/iconi_kevlar",
"Kevlar Vest", RQ3_KEVLAR_NAME,
0, 0,
IT_HOLDABLE, IT_HOLDABLE,
HI_KEVLAR, HI_KEVLAR,
@ -480,6 +483,62 @@ Only in CTF games
"" ""
}, },
{
"item_silencer",
"sound/items/silencer.wav",
{ "models/items/silencer.md3",
0, 0, 0},
"icons/iconi_silencer",
RQ3_SILENCER_NAME,
0,
IT_HOLDABLE,
HI_SILENCER,
"",
""
},
{
"item_laser",
"sound/items/laser.wav",
{ "models/items/laser.md3",
0, 0, 0},
"icons/iconi_laser",
RQ3_LASER_NAME,
0,
IT_HOLDABLE,
HI_LASER,
"",
""
},
{
"item_bandolier",
"sound/items/bandolier.wav",
{ "models/items/bandolier.md3",
0, 0, 0},
"icons/iconi_bandolier",
RQ3_BANDOLIER_NAME,
0,
IT_HOLDABLE,
HI_BANDOLIER,
"",
""
},
{
"item_slippers",
"sound/items/slippers.wav",
{ "models/items/slippers.md3",
0, 0, 0},
"icons/iconi_slippers",
RQ3_SLIPPERS_NAME,
0,
IT_HOLDABLE,
HI_SLIPPERS,
"",
""
},
#ifdef MISSIONPACK #ifdef MISSIONPACK
/*QUAKED holdable_kamikaze (.3 .3 1) (-16 -16 -16) (16 16 16) suspended /*QUAKED holdable_kamikaze (.3 .3 1) (-16 -16 -16) (16 16 16) suspended
@ -718,12 +777,13 @@ Only in One Flag CTF games
IT_WEAPON, IT_WEAPON,
WP_PROX_LAUNCHER, WP_PROX_LAUNCHER,
/* precache */ "", /* precache */ "",
/* sounds */ "sound/weapons/proxmine/wstbtick.wav " //Elder: removing so we get rid of those error messages
/* sounds */ /*"sound/weapons/proxmine/wstbtick.wav "
"sound/weapons/proxmine/wstbactv.wav " "sound/weapons/proxmine/wstbactv.wav "
"sound/weapons/proxmine/wstbimpl.wav " "sound/weapons/proxmine/wstbimpl.wav "
"sound/weapons/proxmine/wstbimpm.wav " "sound/weapons/proxmine/wstbimpm.wav "
"sound/weapons/proxmine/wstbimpd.wav " "sound/weapons/proxmine/wstbimpd.wav "
"sound/weapons/proxmine/wstbactv.wav" "sound/weapons/proxmine/wstbactv.wav"*/
}, },
/*QUAKED weapon_chaingun (.3 .3 1) (-16 -16 -16) (16 16 16) suspended /*QUAKED weapon_chaingun (.3 .3 1) (-16 -16 -16) (16 16 16) suspended

View file

@ -1185,6 +1185,8 @@ static void PM_CrashLand( void ) {
} }
else { else {
PM_AddEvent( PM_FootstepForSurface() ); PM_AddEvent( PM_FootstepForSurface() );
//Elder: added? useful?
pm->ps->stats[STAT_FALLDAMAGE] = 0;
} }
} }
@ -1997,11 +1999,24 @@ static void PM_Weapon( void ) {
//G_Printf("Taking away ammo\n"); //G_Printf("Taking away ammo\n");
pm->ps->ammo[ pm->ps->weapon ]--; pm->ps->ammo[ pm->ps->weapon ]--;
} }
//Elder: special weapon case handling
//Elder: remove knives from inventory if out of ammo
if (pm->ps->weapon == WP_KNIFE && pm->ps->ammo[ WP_KNIFE ] == 0)
{
pm->ps->stats[STAT_WEAPONS] &= ~( 1 << WP_KNIFE);
}
//Elder: remove grenade from inventory if out of ammo
else if (pm->ps->weapon == WP_GRENADE && pm->ps->ammo[ WP_GRENADE ] == 0)
{
pm->ps->stats[STAT_WEAPONS] &= ~( 1 << WP_GRENADE);
}
//Elder: remove one more bullet/shell if handcannon/akimbo //Elder: remove one more bullet/shell if handcannon/akimbo
if (pm->ps->weapon == WP_HANDCANNON) { else if (pm->ps->weapon == WP_HANDCANNON)
{
pm->ps->ammo[ pm->ps->weapon ]--; pm->ps->ammo[ pm->ps->weapon ]--;
} }
//Elder: take away an extra bullet if available - handled in g_weapon.c as well //Elder: take away an extra bullet if available - handled in g_weapon.c as well
else if (pm->ps->weapon == WP_AKIMBO && pm->ps->ammo[ WP_AKIMBO ] > 0) { else if (pm->ps->weapon == WP_AKIMBO && pm->ps->ammo[ WP_AKIMBO ] > 0) {
pm->ps->ammo[ WP_AKIMBO ] --; pm->ps->ammo[ WP_AKIMBO ] --;

View file

@ -520,7 +520,7 @@ typedef enum {
} powerup_t; } powerup_t;
//Elder: swapped around //Elder: swapped around + full Bando name and typo fix on "slipers"
typedef enum { typedef enum {
HI_NONE, HI_NONE,
@ -532,8 +532,8 @@ typedef enum {
HI_KEVLAR, HI_KEVLAR,
HI_LASER, HI_LASER,
HI_SILENCER, HI_SILENCER,
HI_BANDO, HI_BANDOLIER,
HI_SLIPERS, HI_SLIPPERS,
HI_NUM_HOLDABLE HI_NUM_HOLDABLE
} holdable_t; } holdable_t;

View file

@ -57,6 +57,8 @@ qboolean JumpKick( gentity_t *ent )
gentity_t *tent; gentity_t *tent;
gentity_t *traceEnt; gentity_t *traceEnt;
int damage; int damage;
//Elder: for kick sound
qboolean kickSuccess;
// set aiming directions // set aiming directions
AngleVectors (ent->client->ps.viewangles, forward, right, up); AngleVectors (ent->client->ps.viewangles, forward, right, up);
@ -75,17 +77,9 @@ qboolean JumpKick( gentity_t *ent )
return qfalse; return qfalse;
} }
DoorKick( &tr, ent, muzzle, forward ); kickSuccess = DoorKick( &tr, ent, muzzle, forward );
traceEnt = &g_entities[ tr.entityNum ]; traceEnt = &g_entities[ tr.entityNum ];
// send blood impact
if ( traceEnt->takedamage && traceEnt->client ) {
tent = G_TempEntity( tr.endpos, EV_MISSILE_HIT );
tent->s.otherEntityNum = traceEnt->s.number;
tent->s.eventParm = DirToByte( tr.plane.normal );
tent->s.weapon = ent->s.weapon;
}
if ( !traceEnt->takedamage) { if ( !traceEnt->takedamage) {
return qfalse; return qfalse;
} }
@ -98,8 +92,39 @@ qboolean JumpKick( gentity_t *ent )
} }
damage = 20; damage = 20;
G_Damage( traceEnt, ent, ent, forward, tr.endpos,
damage, DAMAGE_NO_LOCATIONAL, MOD_KICK ); //Elder: can't hit if crouching but can still hit "dead" bodies :)
if (traceEnt->client && traceEnt->health > 0 && traceEnt->r.maxs[2] < 20)
{
return qfalse;
}
else {
G_Damage( traceEnt, ent, ent, forward, tr.endpos,
damage, DAMAGE_NO_LOCATIONAL, MOD_KICK );
}
// send blood impact
if ( traceEnt->takedamage && traceEnt->client ) {
tent = G_TempEntity( tr.endpos, EV_MISSILE_HIT );
tent->s.otherEntityNum = traceEnt->s.number;
tent->s.eventParm = DirToByte( tr.plane.normal );
tent->s.weapon = ent->s.weapon;
kickSuccess = qtrue;
}
if (traceEnt->client && traceEnt->client->ps.stats[STAT_UNIQUEWEAPONS] > 0)
{
//Elder: toss a unique weapon if kicked
//Todo: Need to make sure to cancel any reload attempts
//Todo: need to send a message to attacker and target about weapon kick
ThrowWeapon(traceEnt);
//trap_SendServerCommand( ent-g_entities, va("print \"You kicked %s's %s from his hands!\n\"", traceEnt->client->pers.netname, (traceEnt->client->ps.weapon)->pickup_name);
//trap_SendServerCommand( targ-g_entities, va("print \"Head Damage.\n\""));
}
//Elder: for the kick //Elder: for the kick
// do our special form of knockback here // do our special form of knockback here
@ -111,8 +136,29 @@ qboolean JumpKick( gentity_t *ent )
if (self->enemy->velocity[2] > 0) if (self->enemy->velocity[2] > 0)
self->enemy->groundentity = NULL; self->enemy->groundentity = NULL;
*/ */
//Elder: kick knockback for AQ2 -- recall variable kick = 400
if (traceEnt->client)
{
//Elder: for kick knockback
vec3_t size, vTemp;
//Make the "size" vector - hopefully this is right
VectorSubtract(traceEnt->r.maxs, traceEnt->r.mins, size);
G_Printf("Size: %s\n", vtos(size));
VectorMA(traceEnt->r.absmin, 0.5, size, vTemp);
VectorSubtract(vTemp, tr.endpos, vTemp);
VectorNormalize(vTemp);
VectorMA(traceEnt->client->ps.velocity, 400, vTemp, traceEnt->client->ps.velocity);
if (traceEnt->client->ps.velocity[2] > 0)
traceEnt->s.groundEntityNum = ENTITYNUM_NONE;
}
//Elder: Our set of locally called sounds //Elder: Our set of locally called sounds
G_AddEvent ( ent, EV_RQ3_SOUND, RQ3_SOUND_KICK); if (kickSuccess)
G_AddEvent ( ent, EV_RQ3_SOUND, RQ3_SOUND_KICK);
return qtrue; return qtrue;
} }
@ -137,6 +183,9 @@ void P_DamageFeedback( gentity_t *player ) {
} }
// total points of damage shot at the player this frame // total points of damage shot at the player this frame
if (client->damage_blood > 0)
G_Printf("(%i) Damage_blood: %i\n", player->s.clientNum, client->damage_blood);
count = client->damage_blood + client->damage_armor; count = client->damage_blood + client->damage_armor;
if ( count == 0 ) { if ( count == 0 ) {
return; // didn't take any damage return; // didn't take any damage
@ -221,7 +270,9 @@ void P_DamageFeedback( gentity_t *player ) {
//Elder: headshot sound //Elder: headshot sound
case LOCATION_HEAD: case LOCATION_HEAD:
case LOCATION_FACE: case LOCATION_FACE:
G_AddEvent ( player, EV_RQ3_SOUND, RQ3_SOUND_HEADSHOT); //Elder: takes more bandwidth but guarantees a headshot sound
G_Sound(player, CHAN_AUTO, G_SoundIndex("sound/misc/headshot.wav"));
//G_AddEvent ( player, EV_RQ3_SOUND, RQ3_SOUND_HEADSHOT);
break; break;
default: default:
G_AddEvent( player, EV_PAIN, player->health ); G_AddEvent( player, EV_PAIN, player->health );
@ -338,7 +389,8 @@ G_SetClientSound
void G_SetClientSound( gentity_t *ent ) { void G_SetClientSound( gentity_t *ent ) {
#ifdef MISSIONPACK #ifdef MISSIONPACK
if( ent->s.eFlags & EF_TICKING ) { if( ent->s.eFlags & EF_TICKING ) {
ent->client->ps.loopSound = G_SoundIndex( "sound/weapons/proxmine/wstbtick.wav"); //Elder: removed
//ent->client->ps.loopSound = G_SoundIndex( "sound/weapons/proxmine/wstbtick.wav");
} }
else else
#endif #endif
@ -621,6 +673,7 @@ void ClientTimerActions( gentity_t *ent, int msec ) {
if ( client->ps.stats[STAT_ARMOR] > 100) {// max is 100 client->ps.stats[STAT_MAX_HEALTH] ) { if ( client->ps.stats[STAT_ARMOR] > 100) {// max is 100 client->ps.stats[STAT_MAX_HEALTH] ) {
client->ps.stats[STAT_ARMOR]--; client->ps.stats[STAT_ARMOR]--;
} }
//Blaze: Do bandaging stuff //Blaze: Do bandaging stuff
if (ent->client->bleedtick > 1) if (ent->client->bleedtick > 1)
{ {
@ -632,6 +685,7 @@ void ClientTimerActions( gentity_t *ent, int msec ) {
ent->client->bleed_remain = 0; ent->client->bleed_remain = 0;
ent->client->bleeding = 0; ent->client->bleeding = 0;
ent->client->bleedtick = 0; ent->client->bleedtick = 0;
ent->client->bleedBandageCount = 0;
//Elder: added //Elder: added
//ent->client->isBandaging = qfalse; //ent->client->isBandaging = qfalse;
//Elder: remove bandage work //Elder: remove bandage work
@ -750,6 +804,8 @@ void ClientEvents( gentity_t *ent, int oldEventSequence ) {
damage = ent->client->ps.stats[STAT_FALLDAMAGE]; damage = ent->client->ps.stats[STAT_FALLDAMAGE];
VectorSet (dir, 0, 0, 1); VectorSet (dir, 0, 0, 1);
ent->pain_debounce_time = level.time + 200; // no normal pain sound ent->pain_debounce_time = level.time + 200; // no normal pain sound
//Elder: added so we can trigger AQ2 pain blends
ent->client->ps.damageEvent++;
G_Damage (ent, NULL, NULL, NULL, NULL, damage, 0, MOD_FALLING); G_Damage (ent, NULL, NULL, NULL, NULL, damage, 0, MOD_FALLING);
break; break;
@ -1475,7 +1531,8 @@ void ClientEndFrame( gentity_t *ent ) {
if (level.time % 30000 < 1) if (level.time % 30000 < 1)
{ {
G_Printf("Spawn an Item\n"); G_Printf("Spawn an Item\n");
rq3_item = BG_FindItem( "Kevlar Vest" ); //rq3_item = BG_FindItem( "Kevlar Vest" );
rq3_item = BG_FindItemForHoldable( HI_KEVLAR );
rq3_temp = SelectSpawnPoint(ent->client->ps.origin,spawn_origin, spawn_angles); rq3_temp = SelectSpawnPoint(ent->client->ps.origin,spawn_origin, spawn_angles);
Drop_Item (rq3_temp, rq3_item, 0); Drop_Item (rq3_temp, rq3_item, 0);
} }

View file

@ -1647,9 +1647,11 @@ void Cmd_Bandage (gentity_t *ent)
ent->client->ps.weaponTime += 6000; ent->client->ps.weaponTime += 6000;
ent->client->bleedtick = 4; ent->client->bleedtick = 4;
//Elder: added to track health to bleed off
ent->client->bleedBandageCount = BLEED_BANDAGE;
//Elder: added //Elder: added
//ent->client->isBandaging = qtrue; ent->client->ps.stats[STAT_RQ3] |= RQ3_BANDAGE_WORK;
ent->client->ps.stats[STAT_RQ3] |= RQ3_BANDAGE_WORK;
//Elder: moved to g_active where it will be unset after 2 bleedticks //Elder: moved to g_active where it will be unset after 2 bleedticks
//ent->client->ps.stats[STAT_RQ3] &= !RQ3_LEGDAMAGE; //ent->client->ps.stats[STAT_RQ3] &= !RQ3_LEGDAMAGE;
} }

View file

@ -97,7 +97,7 @@ void TossClientItems( gentity_t *self ) {
*/ */
//Elder: run through player STAT_WEAPONS and drop any unique weapons //Elder: run through player STAT_WEAPONS and drop any unique weapons
//That way, we can also account for the bandolier automatically //That way, we can also account for servers with extra weapons
//BTW, that means no cheating to get all weapons or it'll spawn mad!! //BTW, that means no cheating to get all weapons or it'll spawn mad!!
weaponInventory = self->client->ps.stats[STAT_WEAPONS]; weaponInventory = self->client->ps.stats[STAT_WEAPONS];
@ -113,6 +113,7 @@ void TossClientItems( gentity_t *self ) {
item = BG_FindItemForWeapon( WP_M3 ); item = BG_FindItemForWeapon( WP_M3 );
Drop_Item( self, item, angle); Drop_Item( self, item, angle);
self->client->pers.hadUniqueWeapon[ WP_M3 ] = qfalse; self->client->pers.hadUniqueWeapon[ WP_M3 ] = qfalse;
self->client->ps.stats[STAT_UNIQUEWEAPONS]--;
angle += 30; angle += 30;
} }
@ -120,6 +121,7 @@ void TossClientItems( gentity_t *self ) {
item = BG_FindItemForWeapon( WP_M4 ); item = BG_FindItemForWeapon( WP_M4 );
Drop_Item( self, item, angle); Drop_Item( self, item, angle);
self->client->pers.hadUniqueWeapon[ WP_M4 ] = qfalse; self->client->pers.hadUniqueWeapon[ WP_M4 ] = qfalse;
self->client->ps.stats[STAT_UNIQUEWEAPONS]--;
angle += 30; angle += 30;
} }
@ -127,6 +129,7 @@ void TossClientItems( gentity_t *self ) {
item = BG_FindItemForWeapon( WP_MP5 ); item = BG_FindItemForWeapon( WP_MP5 );
Drop_Item( self, item, angle); Drop_Item( self, item, angle);
self->client->pers.hadUniqueWeapon[ WP_MP5 ] = qfalse; self->client->pers.hadUniqueWeapon[ WP_MP5 ] = qfalse;
self->client->ps.stats[STAT_UNIQUEWEAPONS]--;
angle += 30; angle += 30;
} }
@ -134,6 +137,7 @@ void TossClientItems( gentity_t *self ) {
item = BG_FindItemForWeapon( WP_HANDCANNON ); item = BG_FindItemForWeapon( WP_HANDCANNON );
Drop_Item( self, item, angle); Drop_Item( self, item, angle);
self->client->pers.hadUniqueWeapon[ WP_HANDCANNON ] = qfalse; self->client->pers.hadUniqueWeapon[ WP_HANDCANNON ] = qfalse;
self->client->ps.stats[STAT_UNIQUEWEAPONS]--;
angle += 30; angle += 30;
} }
@ -141,6 +145,7 @@ void TossClientItems( gentity_t *self ) {
item = BG_FindItemForWeapon( WP_SSG3000 ); item = BG_FindItemForWeapon( WP_SSG3000 );
Drop_Item( self, item, angle); Drop_Item( self, item, angle);
self->client->pers.hadUniqueWeapon[ WP_SSG3000 ] = qfalse; self->client->pers.hadUniqueWeapon[ WP_SSG3000 ] = qfalse;
self->client->ps.stats[STAT_UNIQUEWEAPONS]--;
angle += 30; angle += 30;
} }
@ -1372,9 +1377,12 @@ void G_Damage( gentity_t *targ, gentity_t *inflictor, gentity_t *attacker,
targ->health, take, asave ); targ->health, take, asave );
} }
// Elder: moved below location damage
// add to the damage inflicted on a player this frame // add to the damage inflicted on a player this frame
// the total will be turned into screen blends and view angle kicks // the total will be turned into screen blends and view angle kicks
// at the end of the frame // at the end of the frame
/*
if ( client ) { if ( client ) {
if ( attacker ) { if ( attacker ) {
client->ps.persistant[PERS_ATTACKER] = attacker->s.number; client->ps.persistant[PERS_ATTACKER] = attacker->s.number;
@ -1392,6 +1400,7 @@ void G_Damage( gentity_t *targ, gentity_t *inflictor, gentity_t *attacker,
client->damage_fromWorld = qtrue; client->damage_fromWorld = qtrue;
} }
} }
*/
// See if it's the player hurting the emeny flag carrier // See if it's the player hurting the emeny flag carrier
#ifdef MISSIONPACK #ifdef MISSIONPACK
@ -1440,8 +1449,9 @@ void G_Damage( gentity_t *targ, gentity_t *inflictor, gentity_t *attacker,
tookShellHit[playernum] = 1; tookShellHit[playernum] = 1;
} }
else { else {
//Grenade stuff //Grenade stuff - don't print if you hurt yourself
trap_SendServerCommand( attacker-g_entities, va("print \"You hit %s^7\n\"", targ->client->pers.netname)); if (targ != attacker)
trap_SendServerCommand( attacker-g_entities, va("print \"You hit %s^7\n\"", targ->client->pers.netname));
} }
} }
@ -1626,6 +1636,29 @@ void G_Damage( gentity_t *targ, gentity_t *inflictor, gentity_t *attacker,
// End Duffman // End Duffman
} }
// add to the damage inflicted on a player this frame
// the total will be turned into screen blends and view angle kicks
// at the end of the frame
if ( client ) {
if ( attacker ) {
client->ps.persistant[PERS_ATTACKER] = attacker->s.number;
} else {
client->ps.persistant[PERS_ATTACKER] = ENTITYNUM_WORLD;
}
client->damage_armor += asave;
client->damage_blood += take;
client->damage_knockback += knockback;
if ( dir ) {
VectorCopy ( dir, client->damage_from );
client->damage_fromWorld = qfalse;
} else {
VectorCopy ( targ->r.currentOrigin, client->damage_from );
client->damage_fromWorld = qtrue;
}
}
// do the damage // do the damage
if (take) { if (take) {
// G_Printf("(%d) taken as damage\n",take); // G_Printf("(%d) taken as damage\n",take);

View file

@ -12,8 +12,11 @@
#define GAMEVERSION "reaction" #define GAMEVERSION "reaction"
#define BODY_QUEUE_SIZE 8 #define BODY_QUEUE_SIZE 8
//Blaze: How long someone bleads for //Blaze: How long someone bleeds for
#define BLEED_TIME 10 // 10 = 1 second is time for losing 1 health at slowest bleed rate #define BLEED_TIME 10 // 10 = 1 second is time for losing 1 health at slowest bleed rate
//Elder: Everyone knows you lose 6 health from the moment you start bandaging
//Let's enforce that in-code because it's sometimes 7 or even 8
#define BLEED_BANDAGE 6
// types of locations that can be hit // types of locations that can be hit
#define LOC_HDAM 1 // head #define LOC_HDAM 1 // head
@ -339,6 +342,7 @@ struct gclient_s {
//qboolean isBleeding; //Blaze: is client bleeding //qboolean isBleeding; //Blaze: is client bleeding
// int legDamage; //Blaze: Client has leg damage - holds number of hits too // int legDamage; //Blaze: Client has leg damage - holds number of hits too
int bleedtick; //Blaze: Holds # of seconds till bleeding stops. int bleedtick; //Blaze: Holds # of seconds till bleeding stops.
int bleedBandageCount; //Elder: hack to restrict amount of bleeding to 6 points
//Elder: server only needs to know for sniper spread - ARGH //Elder: server only needs to know for sniper spread - ARGH
// int zoomed; // Hawkins (SSG zoom) // int zoomed; // Hawkins (SSG zoom)

View file

@ -155,7 +155,8 @@ static void ProximityMine_Activate( gentity_t *ent ) {
ent->health = 1; ent->health = 1;
ent->die = ProximityMine_Die; ent->die = ProximityMine_Die;
ent->s.loopSound = G_SoundIndex( "sound/weapons/proxmine/wstbtick.wav" ); //Elder: removed
//ent->s.loopSound = G_SoundIndex( "sound/weapons/proxmine/wstbtick.wav" );
// build the proximity trigger // build the proximity trigger
trigger = G_Spawn (); trigger = G_Spawn ();
@ -434,12 +435,14 @@ void G_MissileImpact( gentity_t *ent, trace_t *trace ) {
//spawn a knife at its trajectory end-point //spawn a knife at its trajectory end-point
xr_item = BG_FindItemForWeapon( WP_KNIFE ); xr_item = BG_FindItemForWeapon( WP_KNIFE );
BG_EvaluateTrajectoryDelta(&ent->s.pos, level.time, knifeVelocity);
if (other->s.eType == ET_BREAKABLE) { if (other->s.eType == ET_BREAKABLE) {
VectorScale(trace->plane.normal, 10, knifeVelocity); VectorScale(knifeVelocity, -0.25, knifeVelocity);
knifeVelocity[1] -= 50;
//breakable "hit"; make it fall to the ground //breakable "hit"; make it fall to the ground
xr_drop = LaunchItem(xr_item, trace->endpos, knifeVelocity, FL_DROPPED_ITEM); xr_drop = LaunchItem(xr_item, trace->endpos, knifeVelocity, FL_DROPPED_ITEM);
//but still set it as a thrown knife //but still set it as a thrown knife
//xr_drop->flags |= FL_THROWN_KNIFE; //xr_drop->flags |= FL_THROWN_KNIFE;
@ -447,8 +450,10 @@ void G_MissileImpact( gentity_t *ent, trace_t *trace ) {
//and transfer into shared entityState //and transfer into shared entityState
VectorScale(trace->plane.normal, 16, temp); VectorScale(trace->plane.normal, 16, temp);
VectorAdd(trace->endpos, temp, knifeOffset); VectorAdd(trace->endpos, temp, knifeOffset);
VectorCopy(xr_drop->s.origin, temp);
VectorAdd(temp, knifeOffset, xr_drop->s.origin); //VectorCopy(xr_drop->s.origin, temp);
VectorAdd(xr_drop->s.origin, knifeOffset, xr_drop->s.origin);
VectorCopy(xr_drop->s.origin, xr_drop->r.currentOrigin); VectorCopy(xr_drop->s.origin, xr_drop->r.currentOrigin);
} }
else { else {
@ -458,28 +463,24 @@ void G_MissileImpact( gentity_t *ent, trace_t *trace ) {
//Elder: make the knife stick out a bit more //Elder: make the knife stick out a bit more
//and transfer into shared entityState //and transfer into shared entityState
VectorCopy(ent->s.pos.trDelta, temp); VectorCopy(knifeVelocity, temp);
VectorNormalize(temp); VectorNormalize(temp);
VectorScale(temp, -4, temp); VectorScale(temp, -4, temp);
VectorAdd(trace->endpos, temp, knifeOffset); VectorAdd(trace->endpos, temp, knifeOffset);
VectorCopy(xr_drop->s.origin, temp);
VectorAdd(temp, knifeOffset, xr_drop->s.origin);
}
//Elder: make the knife stick out a bit more //VectorCopy(xr_drop->s.origin, temp);
//and transfer into shared entityState VectorAdd(xr_drop->s.origin, knifeOffset, xr_drop->s.origin);
//VectorScale(trace->plane.normal, 4, temp); }
//VectorAdd(trace->endpos, temp, knifeOffset);
//VectorCopy(xr_drop->s.origin, temp);
//VectorAdd(temp, knifeOffset, xr_drop->s.origin);
//Elder: transfer entity data into the shared entityState //Elder: transfer entity data into the shared entityState
//They are rotated on the client side in cg_ents.c //They are rotated on the client side in cg_ents.c
//G_Printf("movedir: %s\n", vtos(ent->s.pos.trDelta)); //G_Printf("movedir: %s\n", vtos(ent->s.pos.trDelta));
xr_drop->s.eFlags = xr_drop->flags; xr_drop->s.eFlags = xr_drop->flags;
//vectoangles( trace->plane.normal, xr_drop->s.angles ); //vectoangles( trace->plane.normal, xr_drop->s.angles );
vectoangles( ent->s.pos.trDelta, xr_drop->s.angles );
vectoangles( knifeVelocity, xr_drop->s.angles);
xr_drop->s.angles[0] += 90; xr_drop->s.angles[0] += 90;
} }
} }
@ -599,6 +600,19 @@ void G_RunMissile( gentity_t *ent ) {
return; // exploded return; // exploded
} }
} }
//Elder: make knife follow the trajectory - not real but oh well...
/* Done in CG_Missile locally to save bandwidth
if (ent->classname == "weapon_knife")
{
vec3_t knifeVelocity;
BG_EvaluateTrajectoryDelta(&ent->s.pos, level.time, knifeVelocity);
vectoangles(knifeVelocity, ent->s.angles);
ent->s.angles[0] += level.time % 360;
}
*/
#ifdef MISSIONPACK #ifdef MISSIONPACK
// if the prox mine wasn't yet outside the player body // if the prox mine wasn't yet outside the player body
if (ent->s.weapon == WP_PROX_LAUNCHER && !ent->count) { if (ent->s.weapon == WP_PROX_LAUNCHER && !ent->count) {
@ -732,6 +746,12 @@ gentity_t *fire_knife (gentity_t *self, vec3_t start, vec3_t dir)
gentity_t *bolt; gentity_t *bolt;
// vec3_t gVec;
// gVec[0] = 0;
// gVec[1] = g_gravity.value;
// gVec[2] = 0;
VectorNormalize (dir); VectorNormalize (dir);
bolt = G_Spawn(); bolt = G_Spawn();
@ -757,6 +777,13 @@ gentity_t *fire_knife (gentity_t *self, vec3_t start, vec3_t dir)
SnapVector( bolt->s.pos.trDelta ); // save net bandwidth SnapVector( bolt->s.pos.trDelta ); // save net bandwidth
VectorCopy (start, bolt->r.currentOrigin); VectorCopy (start, bolt->r.currentOrigin);
VectorCopy (dir, bolt->s.apos.trBase);
VectorCopy (dir, bolt->r.currentAngles);
//Saving stuff for Makro's knife equations
VectorCopy( start, bolt->s.origin2);
VectorCopy( dir, bolt->s.angles2);
return bolt; return bolt;
} }

View file

@ -611,7 +611,6 @@ void Reached_BinaryMover( gentity_t *ent ) {
// return to pos1 after a delay // return to pos1 after a delay
ent->think = ReturnToPos1; ent->think = ReturnToPos1;
ent->nextthink = level.time + ent->wait; ent->nextthink = level.time + ent->wait;
;
} }
// fire targets // fire targets
@ -630,7 +629,7 @@ void Reached_BinaryMover( gentity_t *ent ) {
} }
// close areaportals // close areaportals
if ( ent->teammaster == ent || !ent->teammaster ) { if ( ent->teammaster == ent || !ent->teammaster) {
trap_AdjustAreaPortalState( ent, qfalse ); trap_AdjustAreaPortalState( ent, qfalse );
} }
@ -1178,7 +1177,7 @@ void SP_func_door (gentity_t *ent) {
char *sSndStart; char *sSndStart;
//Elder: can set sounds from here //Elder: can set sounds from here
G_SpawnString( "soundstart", "sound/movers/doors/dr1_strt.wav", &sSndStart ); G_SpawnString( "soundstart", "sound/movers/doors/dr1_end.wav", &sSndStart );
G_SpawnString( "soundstop", "sound/movers/doors/dr1_end.wav", &sSndStop ); G_SpawnString( "soundstop", "sound/movers/doors/dr1_end.wav", &sSndStop );
G_SpawnString( "soundmove", "sound/movers/doors/dr1_strt.wav", &sSndMove ); G_SpawnString( "soundmove", "sound/movers/doors/dr1_strt.wav", &sSndMove );
@ -1259,6 +1258,10 @@ void SP_func_door (gentity_t *ent) {
} }
} }
//Elder: open areaportals for start_open doors
if ( (ent->spawnflags & 1) == 1 && (ent->teammaster == ent || !ent->teammaster) ) {
trap_AdjustAreaPortalState( ent, qtrue );
}
} }
@ -1293,7 +1296,7 @@ void SP_func_door_rotating ( gentity_t *ent ) {
char *sSndStart; char *sSndStart;
//Elder: can set sounds from here //Elder: can set sounds from here
G_SpawnString( "soundstart", "sound/movers/doors/dr1_strt.wav", &sSndStart ); G_SpawnString( "soundstart", "sound/movers/doors/dr1_end.wav", &sSndStart );
G_SpawnString( "soundstop", "sound/movers/doors/dr1_end.wav", &sSndStop ); G_SpawnString( "soundstop", "sound/movers/doors/dr1_end.wav", &sSndStop );
G_SpawnString( "soundmove", "sound/movers/doors/dr1_strt.wav", &sSndMove ); G_SpawnString( "soundmove", "sound/movers/doors/dr1_strt.wav", &sSndMove );

View file

@ -783,7 +783,8 @@ KNIFE ATTACKS
======================================================================== ========================================================================
*/ */
int Knife_Attack ( gentity_t *self, int damage) //Elder: changed to void function
void Knife_Attack ( gentity_t *self, int damage)
{ {
trace_t tr; trace_t tr;
vec3_t end; vec3_t end;
@ -806,14 +807,18 @@ int Knife_Attack ( gentity_t *self, int damage)
{ {
if (hitent->takedamage) if (hitent->takedamage)
{ {
G_Damage (hitent, self, self, forward, tr.endpos, damage, 0, MOD_KNIFE ); //Elder: no knock-back on knife slashes
return -2; G_Damage (hitent, self, self, forward, tr.endpos, damage, DAMAGE_NO_KNOCKBACK, MOD_KNIFE );
return;
//return -2;
} }
} }
else else
return 0; //return 0;
return;
} }
return 0; // we hit the sky, call it a miss return;
//return 0; // we hit the sky, call it a miss
} }
static int knives = 0; static int knives = 0;

View file

@ -1,22 +1,43 @@
#include "g_local.h" #include "g_local.h"
//Elder: someone should comment this b/c it's hard to follow
//Makes the damage "non-instant" like AQ2
void CheckBleeding(gentity_t *targ) void CheckBleeding(gentity_t *targ)
{ {
int damage; int damage;
int temp; int temp;
if (!(targ->client->bleeding) || (targ->health <=0)) return; if (!(targ->client->bleeding) || (targ->health <=0)) return;
temp = (int)(targ->client->bleeding * .2); temp = (int)(targ->client->bleeding * .2);
targ->client->bleeding -= temp; targ->client->bleeding -= temp;
if (temp <= 0) temp=1;
if (temp <= 0) temp = 1;
targ->client->bleed_remain += temp; targ->client->bleed_remain += temp;
damage = (int)(targ->client->bleed_remain/BLEED_TIME); damage = (int)(targ->client->bleed_remain/BLEED_TIME);
if (targ->client->bleed_remain >= BLEED_TIME) if (targ->client->bleed_remain >= BLEED_TIME)
{ {
targ->health -= damage; if ( (targ->client->ps.stats[STAT_RQ3] & RQ3_BANDAGE_WORK) == RQ3_BANDAGE_WORK &&
if (targ->health <=0) targ->client->bleedBandageCount < 1)
{ {
player_die(targ,&g_entities[targ->client->lasthurt_client],&g_entities[targ->client->lasthurt_client],damage,targ->client->lasthurt_mod); //Elder: skip damage being dealt
}
else
{
targ->health -= damage;
}
//Elder: hack to count off health so we only lose 6 health on a bandage
if ( (targ->client->ps.stats[STAT_RQ3] & RQ3_BANDAGE_WORK) == RQ3_BANDAGE_WORK)
{
targ->client->bleedBandageCount--;
}
if (targ->health <= 0)
{
player_die(targ, &g_entities[targ->client->lasthurt_client], &g_entities[targ->client->lasthurt_client], damage, targ->client->lasthurt_mod);
} }
else else
{ {
@ -25,7 +46,7 @@ void CheckBleeding(gentity_t *targ)
} }
} }
//Elder: apparently does nothing //Elder: apparently does nothing and is unused
void StartBandage(gentity_t *ent) void StartBandage(gentity_t *ent)
{ {
ent->client->bleeding = 0; ent->client->bleeding = 0;

View file

@ -166,12 +166,12 @@ void UI_DrawConnectScreen( qboolean overlay ) {
//UI_DrawProportionalString( 320, 96, "Press Esc to abort", UI_CENTER|UI_SMALLFONT|UI_DROPSHADOW, menu_text_color ); //UI_DrawProportionalString( 320, 96, "Press Esc to abort", UI_CENTER|UI_SMALLFONT|UI_DROPSHADOW, menu_text_color );
// display global MOTD at bottom // display global MOTD at bottom
UI_DrawProportionalString( x, 384, UI_DrawProportionalString( x, 352,
Info_ValueForKey( cstate.updateInfoString, "motd" ), UI_LEFT|UI_SMALLFONT, menu_text_color ); Info_ValueForKey( cstate.updateInfoString, "motd" ), UI_LEFT|UI_SMALLFONT, menu_text_color );
// print any server info (server full, bad version, etc) // print any server info (server full, bad version, etc)
if ( cstate.connState < CA_CONNECTED ) { if ( cstate.connState < CA_CONNECTED ) {
UI_DrawProportionalString( x, 400, cstate.messageString, UI_LEFT|UI_SMALLFONT, menu_text_color ); UI_DrawProportionalString( x, 384, cstate.messageString, UI_LEFT|UI_SMALLFONT, menu_text_color );
} }
#if 0 #if 0