From 3fff6ebd81eb127ebba920364ef23fc03936aa06 Mon Sep 17 00:00:00 2001 From: pbrochart Date: Tue, 22 Nov 2022 22:00:10 +0100 Subject: [PATCH] Revision 333 --- README.md | 3 +- code/cgame/cg_draw.c | 45 +++++------- code/cgame/cg_effects.c | 2 +- code/cgame/cg_local.h | 9 +-- code/cgame/cg_localents.c | 11 +-- code/cgame/cg_main.c | 6 +- code/cgame/cg_playerstate.c | 2 +- code/cgame/cg_predict.c | 3 +- code/cgame/cg_scoreboard.c | 42 +++-------- code/cgame/cg_servercmds.c | 38 ++++++---- code/cgame/cg_view.c | 6 +- code/game/ai_chat.c | 7 +- code/game/ai_cmd.c | 6 +- code/game/ai_dmq3.c | 12 ++-- code/game/ai_team.c | 3 +- code/game/bg_pmove.c | 4 +- code/game/bg_public.h | 2 +- code/game/g_client.c | 2 +- code/game/g_cmds.c | 135 +++++++++++++++++++++++------------- code/game/g_combat.c | 2 +- code/game/g_killspree.c | 10 ++- code/game/g_local.h | 1 + code/game/g_main.c | 22 +++--- code/game/g_missile.c | 4 +- code/game/g_vote.c | 21 ++---- code/q3_ui/ui_challenges.c | 2 +- code/ui/ui_shared.c | 3 +- 27 files changed, 201 insertions(+), 202 deletions(-) diff --git a/README.md b/README.md index 99486a0..a00a340 100644 --- a/README.md +++ b/README.md @@ -13,7 +13,7 @@ Revision 310: Display damage indicator thru the walls. Fix duplicate damages with shotgun when they are multiple targets. Add cg_damagePlum: Controls which weapons will draw damage plumes. Default is all: "/g/mg/sg/gl/rl/lg/rg/pg/bfg/cg/ng/pl/". -Revision 311: Added new features for cg_drawGun (4,5,6). +Revision 311: Add new feature for cg_drawGun (4,5,6). Same as 1,2,3 but the weapons are transparent. Revision 312: Some bug fixes from ioquake3. Revision 313: Add double jump, air control and extra @@ -49,3 +49,4 @@ Revision 330: Better fix for cg_drawTeamOverlay. Fix the main spec model in multiview windows. Revision 331: Improve the scoreboard. Revision 332: Fix various bugs. +Revision 333: Bug fixes and cleanup, allow keywords in the text chat. diff --git a/code/cgame/cg_draw.c b/code/cgame/cg_draw.c index 5220c66..f70b44b 100644 --- a/code/cgame/cg_draw.c +++ b/code/cgame/cg_draw.c @@ -3052,7 +3052,11 @@ static void CG_DrawLagometer ( void ) { CG_DrawStringHud ( HUD_NETGRAPHPING, qtrue, ( const char* ) va ( "%ims", cg.snap->ping ) ); if ( cg_nopredict.integer || cg_synchronousClients.integer ) { - CG_DrawBigString ( ax, ay, "snc", 1.0 ); + if ( !cgs.hud[HUD_NETGRAPHPING].inuse ) { + ax = 640 - 48; + ay = 480 - 48; + CG_DrawBigString ( ax, ay, "snc", 1.0 ); + } } CG_DrawDisconnect(); @@ -3561,7 +3565,6 @@ static void CG_DrawCrosshair3D ( void ) { } - /* ================= CG_ScanForCrosshairEntity @@ -3595,14 +3598,8 @@ static void CG_ScanForCrosshairEntity ( int window ) { } // update the fade timer - if ( window ) { - cg.chcn[window] = trace.entityNum; - cg.chct[window] = cg.time; - } - else { - cg.crosshairClientNum = trace.entityNum; - cg.crosshairClientTime = cg.time; - } + cg.crosshairClientNum[window] = trace.entityNum; + cg.crosshairClientTime[window] = cg.time; } @@ -3615,7 +3612,6 @@ static void CG_DrawCrosshairNames ( int window ) { float *color; char *name; int armorcolor, healthcolor; - int crosshairClientNum, crosshairClientTime; if ( !cgs.hud[HUD_TARGETNAME].inuse ) return; @@ -3631,23 +3627,14 @@ static void CG_DrawCrosshairNames ( int window ) { // scan the known entities to see if the crosshair is sighted on one CG_ScanForCrosshairEntity( window ); - if ( window ) { - crosshairClientNum = cg.chcn[window]; - crosshairClientTime = cg.chct[window]; - } - else { - crosshairClientNum = cg.crosshairClientNum; - crosshairClientTime = cg.crosshairClientTime; - } - // draw the name of the player being looked at - color = CG_FadeColor ( crosshairClientTime, cgs.hud[HUD_TARGETNAME].time ); + color = CG_FadeColor ( cg.crosshairClientTime[window], cgs.hud[HUD_TARGETNAME].time ); if ( !color ) { trap_R_SetColor ( NULL ); return; } - name = cgs.clientinfo[ crosshairClientNum ].name; + name = cgs.clientinfo[ cg.crosshairClientNum[window] ].name; CG_DrawStringHud ( HUD_TARGETNAME, qtrue, name ); @@ -3656,27 +3643,27 @@ static void CG_DrawCrosshairNames ( int window ) { if ( cg.snap->ps.persistant[PERS_TEAM] != TEAM_RED && cg.snap->ps.persistant[PERS_TEAM] != TEAM_BLUE ) return; - if ( cg.snap->ps.persistant[PERS_TEAM] != cgs.clientinfo[ crosshairClientNum ].team ) + if ( cg.snap->ps.persistant[PERS_TEAM] != cgs.clientinfo[ cg.crosshairClientNum[window] ].team ) return; if ( ( cgs.hud[HUD_TARGETSTATUS].inuse ) && ( cgs.clientinfo[cg.clientNum].team != TEAM_SPECTATOR ) ) { - if ( cgs.clientinfo[ crosshairClientNum ].health >= 100 ) + if ( cgs.clientinfo[ cg.crosshairClientNum[window] ].health >= 100 ) healthcolor = 2; - else if ( cgs.clientinfo[ crosshairClientNum ].health >= 50 ) + else if ( cgs.clientinfo[ cg.crosshairClientNum[window] ].health >= 50 ) healthcolor = 3; else healthcolor = 1; - if ( cgs.clientinfo[ crosshairClientNum ].armor >= 100 ) + if ( cgs.clientinfo[ cg.crosshairClientNum[window] ].armor >= 100 ) armorcolor = 2; - else if ( cgs.clientinfo[ crosshairClientNum ].armor >= 50 ) + else if ( cgs.clientinfo[ cg.crosshairClientNum[window] ].armor >= 50 ) armorcolor = 3; else armorcolor = 1; CG_DrawStringHud ( HUD_TARGETSTATUS, qfalse, va ( "(^%i%i^7|^%i%i^7)", healthcolor, - cgs.clientinfo[ crosshairClientNum ].health, armorcolor, - cgs.clientinfo[ crosshairClientNum ].armor ) ); + cgs.clientinfo[ cg.crosshairClientNum[window] ].health, armorcolor, + cgs.clientinfo[ cg.crosshairClientNum[window] ].armor ) ); } } diff --git a/code/cgame/cg_effects.c b/code/cgame/cg_effects.c index ea1ea95..b52988b 100644 --- a/code/cgame/cg_effects.c +++ b/code/cgame/cg_effects.c @@ -615,7 +615,7 @@ void CG_DamagePlum( int client, vec3_t org, int damage, int mod ) { retDamagePlum = CG_ParseDamagePlum ( mod ); // only visualize for the client that damaged - if (client != cg.predictedPlayerState.clientNum || !cg_damagePlums.integer || !retDamagePlum) { + if (client != cg.predictedPlayerState.clientNum || cg_damagePlums.integer == 0 || !retDamagePlum) { return; } diff --git a/code/cgame/cg_local.h b/code/cgame/cg_local.h index 8d6be46..5c5e076 100644 --- a/code/cgame/cg_local.h +++ b/code/cgame/cg_local.h @@ -609,8 +609,6 @@ enum{ //=========================SUPERHUD END================================== -#define MAX_MULTIVIEW 4 - #define MAX_REWARDSTACK 10 #define MAX_SOUNDBUFFER 20 @@ -753,8 +751,8 @@ typedef struct { int lastKillTime; // crosshair client ID - int crosshairClientNum; - int crosshairClientTime; + int crosshairClientNum[MAX_MULTIVIEW]; + int crosshairClientTime[MAX_MULTIVIEW]; // powerup active flashing int powerupActive; @@ -869,8 +867,6 @@ typedef struct { int spawnTeam[MAX_SPAWNPOINTS]; int numSpawnpoints; qboolean forceChat; - int chcn[MAX_MULTIVIEW]; - int chct[MAX_MULTIVIEW]; int window; } cg_t; @@ -1756,6 +1752,7 @@ extern vmCvar_t cg_drawSpawnpoints; extern vmCvar_t cg_mapoverview; extern vmCvar_t cg_damagePlums; extern vmCvar_t cg_damagePlum; +extern vmCvar_t cg_damagePlumScale; extern vmCvar_t cg_waterWarp; extern vmCvar_t cg_hudFullScreen; extern vmCvar_t cg_fovAdjust; diff --git a/code/cgame/cg_localents.c b/code/cgame/cg_localents.c index 4fb7362..b2a98ad 100644 --- a/code/cgame/cg_localents.c +++ b/code/cgame/cg_localents.c @@ -807,7 +807,7 @@ CG_AddDamagePlum void CG_AddDamagePlum( localEntity_t *le ) { refEntity_t *re; vec3_t origin, delta, dir, vec, up = {0, 0, 1}; - float c, len, scale; + float c, len, scale, cgscale; int i, damage, digits[10], numdigits, negative; re = &le->refEntity; @@ -844,12 +844,13 @@ void CG_AddDamagePlum( localEntity_t *le ) { VectorNormalize(vec); VectorMA(origin, -8 + 6 * sin(c * 2 * M_PI), vec, origin); + cgscale = Com_Clamp(1, 2, cg_damagePlumScale.value); // if the view would be "inside" the sprite, kill the sprite // so it doesn't add too much overdraw VectorSubtract( origin, cg.refdef.vieworg, delta ); len = VectorLength( delta ); - if ( len < 20 ) { + if ( len < 20 * cgscale ) { CG_FreeLocalEntity( le ); return; } @@ -864,8 +865,8 @@ void CG_AddDamagePlum( localEntity_t *le ) { ( ( cg.time - cg.zoomTime ) / (float)( cg_zoomScaling.value * ZOOM_TIME ) > 1 ) ) ) scale = (float)len / MAX_DISTANCE_ZOOM_NOSCALE; - origin[2] += 49 - cos (c * 4.8) * 34 * scale; - re->radius = NUMBER_SIZE / 2 * scale; + origin[2] += 49 - cos (c * 4.8) * 34 * scale * cgscale; + re->radius = NUMBER_SIZE / 2 * scale * cgscale; negative = qfalse; if (damage < 0) { @@ -884,7 +885,7 @@ void CG_AddDamagePlum( localEntity_t *le ) { } for (i = 0; i < numdigits; i++) { - VectorMA(origin, (float) (((float) numdigits / 2) - i) * NUMBER_SIZE * scale, vec, re->origin); + VectorMA(origin, (float) (((float) numdigits / 2) - i) * NUMBER_SIZE * scale * cgscale, vec, re->origin); re->customShader = cgs.media.numberShaders[digits[numdigits-1-i]]; re->renderfx = RF_DEPTHHACK; trap_R_AddRefEntityToScene( re ); diff --git a/code/cgame/cg_main.c b/code/cgame/cg_main.c index 731ccda..44fec8f 100644 --- a/code/cgame/cg_main.c +++ b/code/cgame/cg_main.c @@ -390,6 +390,7 @@ vmCvar_t cg_drawSpawnpoints; vmCvar_t cg_mapoverview; vmCvar_t cg_damagePlums; vmCvar_t cg_damagePlum; +vmCvar_t cg_damagePlumScale; vmCvar_t cg_waterWarp; vmCvar_t cg_hudFullScreen; vmCvar_t cg_fovAdjust; @@ -634,6 +635,7 @@ static cvarTable_t cvarTable[] = { // bk001129 {&cg_mapoverview, "cg_mapoverview", "0", CVAR_ARCHIVE | CVAR_CHEAT }, {&cg_damagePlums, "cg_damagePlums", "1", CVAR_USERINFO | CVAR_ARCHIVE }, {&cg_damagePlum, "cg_damagePlum", "/g/mg/sg/gl/rl/lg/rg/pg/bfg/cg/ng/pl/", CVAR_USERINFO | CVAR_ARCHIVE }, + {&cg_damagePlumScale, "cg_damagePlumScale", "1.0", CVAR_USERINFO | CVAR_ARCHIVE }, {&cg_waterWarp, "cg_waterWarp", "1", CVAR_ARCHIVE }, {&cg_hudFullScreen, "cg_hudFullScreen", "0", CVAR_ARCHIVE}, {&cg_fovAdjust, "cg_fovAdjust", "0", CVAR_ARCHIVE}, @@ -841,10 +843,10 @@ void CG_UpdateCvars( void ) { } int CG_CrosshairPlayer( void ) { - if ( cg.time > ( cg.crosshairClientTime + 1000 ) ) { + if ( cg.time > ( cg.crosshairClientTime[0] + 1000 ) ) { return -1; } - return cg.crosshairClientNum; + return cg.crosshairClientNum[0]; } int CG_LastAttacker( void ) { diff --git a/code/cgame/cg_playerstate.c b/code/cgame/cg_playerstate.c index 5c4793e..db4d041 100644 --- a/code/cgame/cg_playerstate.c +++ b/code/cgame/cg_playerstate.c @@ -145,7 +145,7 @@ void CG_DamageFeedback( int yawByte, int pitchByte, int damage ) { vectoangles(dir, angles); - cg.v_dmg_roll = kick * left; + cg.v_dmg_roll = kick * left; cg.v_dmg_pitch = -kick * front; cg.v_dmg_angle = angles[YAW]; diff --git a/code/cgame/cg_predict.c b/code/cgame/cg_predict.c index 885c790..d6d2426 100644 --- a/code/cgame/cg_predict.c +++ b/code/cgame/cg_predict.c @@ -121,9 +121,8 @@ static void CG_ClipMoveToEntities ( const vec3_t start, const vec3_t mins, const VectorCopy( cent->lerpOrigin, origin ); } - trap_CM_TransformedBoxTrace ( &trace, start, end, - mins, maxs, cmodel, mask, origin, angles); + mins, maxs, cmodel, mask, origin, angles); if (trace.allsolid || trace.fraction < tr->fraction) { trace.entityNum = ent->number; diff --git a/code/cgame/cg_scoreboard.c b/code/cgame/cg_scoreboard.c index f92a7ec..8afae8f 100644 --- a/code/cgame/cg_scoreboard.c +++ b/code/cgame/cg_scoreboard.c @@ -87,7 +87,7 @@ static void CG_DrawClientScore( int x, int y, int w, int h, score_t *score, floa } // don't draw the client while he's connecting - if( score->ping == -1 )return; + if( score->ping == -1 ) return; ci = &cgs.clientinfo[ score->client ]; @@ -189,7 +189,7 @@ static int CG_TeamScoreboard( int x, int y, int w, int h, team_t team, float *co notEnough = qtrue; // we don't break the loop, so we can get the local client, and display it later - if( score->client == cg.clientNum )localClient = score; + if( score->client == cg.clientNum ) localClient = score; }else{ @@ -205,7 +205,6 @@ static int CG_TeamScoreboard( int x, int y, int w, int h, team_t team, float *co } if( notEnough ){ - CG_DrawStringExt( x, y, "...", colorWhite, qtrue, qfalse, SB_MEDCHAR_WIDTH, SB_MEDCHAR_HEIGHT, 0 ); // draw the local client if he hasn't been drawn yet @@ -221,7 +220,6 @@ static int CG_TeamScoreboard( int x, int y, int w, int h, team_t team, float *co } return count; - } static void CG_DrawSpecs( void ){ @@ -255,11 +253,8 @@ static void CG_DrawSpecs( void ){ } if( notEnough ){ - - if( score->client == cg.clientNum )localClient = score; - + if( score->client == cg.clientNum ) localClient = score; }else{ - if( CG_DrawStrlen( string ) + CG_DrawStrlen( ci->name ) + 3 > SB_SPEC_MAXCHAR && strlen( string ) ){ CG_DrawStringExt( SB_SPEC_X, y, string, colorWhite, qfalse, qfalse, SB_MEDCHAR_WIDTH, SB_MEDCHAR_HEIGHT, 0 ); if( cgs.gametype == GT_TOURNAMENT ){ @@ -269,7 +264,6 @@ static void CG_DrawSpecs( void ){ strcpy( string, va("^7(^2%i^7/^1%i^7)%s^7(^2%i^7)", ci->wins, ci->losses, ci->name, queueNumber ) ); queueNumber++; } - } else strcpy( string, va( "^7%s", ci->name ) ); @@ -278,7 +272,7 @@ static void CG_DrawSpecs( void ){ numLine++; if( numLine >= 2 ){ notEnough = qtrue; - if( score->client == cg.clientNum )localClient = score; + if( score->client == cg.clientNum ) localClient = score; } }else{ if( strlen( string ) ) @@ -295,20 +289,15 @@ static void CG_DrawSpecs( void ){ else strcat( string, va( "^7%s", ci->name ) ); } - } } if( notEnough ){ - strcpy( string, "... " ); - if( localClient != NULL )strcat( string, cgs.clientinfo[ score->client ].name ); // draw the local client if he hasn't been drawn yet + if( localClient != NULL ) strcat( string, cgs.clientinfo[ score->client ].name ); // draw the local client if he hasn't been drawn yet CG_DrawStringExt( SB_SPEC_X, y, string, colorWhite, qfalse, qfalse, SB_MEDCHAR_WIDTH, SB_MEDCHAR_HEIGHT, 0 ); - }else if( strlen( string ) ){ - CG_DrawStringExt( SB_SPEC_X, y, string, colorWhite, qfalse, qfalse, SB_MEDCHAR_WIDTH, SB_MEDCHAR_HEIGHT, 0 ); - } } @@ -325,7 +314,6 @@ static void CG_DrawPicBar( picBar_t *tab, int count, int x, int y, int w, int h if( tab[ i ].percent )strcat( string, "%" ); CG_DrawStringExt( picBarX + h + 3, y - SB_MEDCHAR_HEIGHT/2, string, colorWhite, qtrue, qfalse, SB_MEDCHAR_WIDTH, SB_MEDCHAR_HEIGHT, 0 ); } - } static void CG_DrawMapInfo( void ){ @@ -355,7 +343,6 @@ static void CG_DrawMapInfo( void ){ strcat( string, " // " ); strcat( string, gameNames[ cgs.gametype ] ); CG_DrawStringExt( SB_XPOS + 10, SB_YPOS + 2, string, colorWhite, qtrue, qfalse, TINYCHAR_WIDTH, TINYCHAR_HEIGHT, 0 ); - } qboolean CG_DrawOldScoreboard( void ){ @@ -431,7 +418,6 @@ qboolean CG_DrawOldScoreboard( void ){ if( cgs.blueLocked ) CG_DrawPic( 640-32, SB_TEAM_Y, 32, 32, cgs.media.sbLocked ); }else{ - // current rank if( cg.snap->ps.persistant[ PERS_TEAM ] != TEAM_SPECTATOR ){ strcpy( string, va( "%s place with %i", CG_PlaceString( cg.snap->ps.persistant[ PERS_RANK ] + 1 ), cg.snap->ps.persistant[ PERS_SCORE ] ) ); @@ -444,7 +430,6 @@ qboolean CG_DrawOldScoreboard( void ){ color[ 2 ] = 0.7; color[ 3 ] = 0.25; CG_TeamScoreboard( SB_FFA_X, SB_FFA_Y + 50, SB_FFA_WIDTH, SB_FFA_HEIGHT, TEAM_FREE, color, SB_MAXDISPLAY ); - } // informations about the local/specced player (acc + awards) @@ -527,10 +512,8 @@ qboolean CG_DrawOldScoreboard( void ){ } return qtrue; - } - qboolean CG_DrawOldTourneyScoreboard( void ){ char string[ 128 ]; @@ -583,7 +566,7 @@ qboolean CG_DrawOldTourneyScoreboard( void ){ loop = -1; // loop is used when displaying the stats. -1 : no player, 0 : left player only, 2 : both players for( i=0; iwins, p->losses, p->name ) )/2, y + 15, va("^7(^2%i^7/^1%i^7) %s",p->wins, p->losses, p->name ), colorWhite, qfalse, qtrue, SMALLCHAR_WIDTH, SMALLCHAR_HEIGHT, 0 ); CG_DrawPic( x + side*w*0.8 - offset*SB_INFOICON_SIZE, y + 30, SB_INFOICON_SIZE, SB_INFOICON_SIZE, cgs.media.sbPing ); @@ -684,8 +667,7 @@ qboolean CG_DrawOldTourneyScoreboard( void ){ strcpy( string, "-/-" ); } CG_DrawStringExt( x + side*0.6*w - SB_MEDCHAR_WIDTH*CG_DrawStrlen( string )/2, y, string, colorWhite, qtrue, qfalse, SB_MEDCHAR_WIDTH, SB_MEDCHAR_HEIGHT, 0 ); - - } + } y += h + 10; } } @@ -722,7 +704,6 @@ qboolean CG_DrawOldTourneyScoreboard( void ){ CG_DrawStringExt( x + side*w - offset*SB_MEDCHAR_WIDTH*CG_DrawStrlen( string ), y + h/2 - SB_MEDCHAR_HEIGHT/2, string, colorWhite, qtrue, qfalse, SB_MEDCHAR_WIDTH, SB_MEDCHAR_HEIGHT, 0 ); strcpy( string, va( "%i", score->dmgdone ) ); CG_DrawStringExt( x + side*( w - h*2 ) - offset*SB_MEDCHAR_WIDTH*CG_DrawStrlen( string ), y + h/2 - SB_MEDCHAR_HEIGHT/2, string, colorWhite, qtrue, qfalse, SB_MEDCHAR_WIDTH, SB_MEDCHAR_HEIGHT, 0 ); - } // awards @@ -762,7 +743,7 @@ qboolean CG_DrawOldTourneyScoreboard( void ){ awardCount = 0; for( i=0; i sortedPicBar[ j ].val ){ for( k=awardCount-1; k>=j; k-- ){ @@ -777,11 +758,9 @@ qboolean CG_DrawOldTourneyScoreboard( void ){ sortedPicBar[ j ].val = picBar[ i ].val; sortedPicBar[ j ].percent = picBar[ i ].percent; awardCount++; - if( awardCount >= SB_TOURNEY_AWARDS )break; + if( awardCount >= SB_TOURNEY_AWARDS ) break; } - CG_DrawPicBar( sortedPicBar, awardCount, x + side*w/2, y, w*0.8, h ); - } // spectators @@ -793,5 +772,4 @@ qboolean CG_DrawOldTourneyScoreboard( void ){ } return qtrue; - } diff --git a/code/cgame/cg_servercmds.c b/code/cgame/cg_servercmds.c index 576ec52..4f7cbb1 100644 --- a/code/cgame/cg_servercmds.c +++ b/code/cgame/cg_servercmds.c @@ -101,10 +101,14 @@ void CG_SetGameString ( void ) { count = 0; for ( i = 0; i < 128 ; i++ ) { - if ( playerName[i] == '^' && ( ( playerName[i+1] >= '0' && playerName[i+1] <= '9' ) || ( playerName[i+1] >= 'a' && playerName[i+1] <= 'z' ) || ( playerName[i+1] >= 'A' && playerName[i+1] <= 'Z' ) ) ) { + if ( playerName[i] == '^' && ( ( playerName[i+1] >= '0' && playerName[i+1] <= '9' ) || + ( playerName[i+1] >= 'a' && playerName[i+1] <= 'z' ) || + ( playerName[i+1] >= 'A' && playerName[i+1] <= 'Z' ) ) ) { i++; continue; - } else if ( ( ! ( playerName[i] >= '0' && playerName[i] <= '9' ) && ! ( playerName[i] >= 'a' && playerName[i] <= 'z' ) && ! ( playerName[i] >= 'A' && playerName[i] <= 'Z' ) ) ) { + } else if ( ( ! ( playerName[i] >= '0' && playerName[i] <= '9' ) && + ! ( playerName[i] >= 'a' && playerName[i] <= 'z' ) && + ! ( playerName[i] >= 'A' && playerName[i] <= 'Z' ) ) ) { continue; } @@ -762,7 +766,7 @@ static void CG_ParseRespawnTimer ( void ) { /* ================= -CG_ParseRespawnTimer +CG_ParseReadyMask ================= */ @@ -774,9 +778,11 @@ static void CG_ParseReadyMask ( void ) { return; if ( readyMask != cg.readyMask ) { - for ( i = 0; i < 32 ; i++ ) { - if ( ( cg.readyMask & ( 1 << i ) ) != ( readyMask & ( 1 << i ) ) ) { - + for ( i = 0; i < cgs.maxclients ; i++ ) { + // does not notify if it's a bot because it's always ready + if ( cgs.clientinfo[ i ].botSkill > 0 && cgs.clientinfo[ i ].botSkill <= 5 ) + continue; + if ( ( cg.readyMask & ( 1 << i ) ) != ( readyMask & ( 1 << i ) ) && cgs.clientinfo[ i ].infoValid ) { if ( readyMask & ( 1 << i ) ) CG_CenterPrint ( va ( "%s ^2is ready", cgs.clientinfo[ i ].name ), 120, BIGCHAR_WIDTH ); else @@ -1161,21 +1167,18 @@ void CG_ShaderStateChanged ( void ) { while ( o && *o ) { n = strstr ( o, "=" ); if ( n && *n ) { - strncpy ( originalShader, o, n-o ); - originalShader[n-o] = 0; + Q_strncpyz( originalShader, o, n-o+1 ); n++; t = strstr ( n, ":" ); if ( t && *t ) { - strncpy ( newShader, n, t-n ); - newShader[t-n] = 0; + Q_strncpyz( newShader, n, t-n+1 ); } else { break; } t++; o = strstr ( t, "@" ); if ( o ) { - strncpy ( timeOffset, t, o-t ); - timeOffset[o-t] = 0; + Q_strncpyz( timeOffset, t, o-t+1 ); o++; trap_R_RemapShader ( originalShader, newShader, timeOffset ); } @@ -2022,15 +2025,19 @@ static void CG_ServerCommand ( void ) { //#endif return; } + if ( !strcmp ( cmd, "screenPrint" ) ) { Q_strncpyz ( text, CG_Argv ( 1 ), MAX_SAY_TEXT ); CG_RemoveChatEscapeChar ( text ); CG_AddToChat ( text ); return; } + if ( !strcmp ( cmd, "chat" ) ) { + qboolean nobeep; + nobeep = atoi( CG_Argv( 2 ) ); if ( !cg_teamChatsOnly.integer && !cg_noChat.integer ) { - if ( cg_chatBeep.integer ) + if ( cg_chatBeep.integer && !nobeep ) trap_S_StartLocalSound ( cgs.media.talkSound, CHAN_LOCAL_SOUND ); Q_strncpyz ( text, CG_Argv ( 1 ), MAX_SAY_TEXT ); CG_RemoveChatEscapeChar ( text ); @@ -2041,8 +2048,10 @@ static void CG_ServerCommand ( void ) { } if ( !strcmp ( cmd, "tchat" ) ) { + qboolean nobeep; + nobeep = atoi( CG_Argv( 2 ) ); if ( !cg_noChat.integer ) { - if ( cg_teamChatBeep.integer ) + if ( cg_teamChatBeep.integer && !nobeep ) trap_S_StartLocalSound ( cgs.media.talkSound, CHAN_LOCAL_SOUND ); Q_strncpyz ( text, CG_Argv ( 1 ), MAX_SAY_TEXT ); CG_RemoveChatEscapeChar ( text ); @@ -2051,6 +2060,7 @@ static void CG_ServerCommand ( void ) { } return; } + if ( !strcmp ( cmd, "scores" ) ) { CG_ParseScores(); return; diff --git a/code/cgame/cg_view.c b/code/cgame/cg_view.c index d07af0e..dfc7201 100644 --- a/code/cgame/cg_view.c +++ b/code/cgame/cg_view.c @@ -1219,9 +1219,9 @@ void CG_DrawActiveFrame( int serverTime, stereoFrame_t stereoView, qboolean demo color[0] = colorBlack[0]; color[1] = colorBlack[1]; color[2] = colorBlack[2]; - color[3] = (cg.time - cg.deathtime)/5000.0f; - if( color[3] > 1.0 ) - color[3] = 1.0; + color[3] = (cg.time - cg.deathtime)/3000.0f; + if( color[3] > 0.3f ) + color[3] = 0.3f; CG_FillRect(0, 0, 640, 480, color); } } diff --git a/code/game/ai_chat.c b/code/game/ai_chat.c index 7508c1d..382255d 100644 --- a/code/game/ai_chat.c +++ b/code/game/ai_chat.c @@ -237,8 +237,7 @@ char *BotMapTitle(void) { trap_GetServerinfo(info, sizeof(info)); - strncpy(mapname, Info_ValueForKey( info, "mapname" ), sizeof(mapname)-1); - mapname[sizeof(mapname)-1] = '\0'; + Q_strncpyz(mapname, Info_ValueForKey( info, "mapname" ), sizeof(mapname)); return mapname; } @@ -921,9 +920,9 @@ BotChatTime ================== */ float BotChatTime(bot_state_t *bs) { - int cpm; + //int cpm; - cpm = trap_Characteristic_BInteger(bs->character, CHARACTERISTIC_CHAT_CPM, 1, 4000); + //cpm = trap_Characteristic_BInteger(bs->character, CHARACTERISTIC_CHAT_CPM, 1, 4000); return 2.0; //(float) trap_BotChatLength(bs->cs) * 30 / cpm; } diff --git a/code/game/ai_cmd.c b/code/game/ai_cmd.c index 21e8059..fa40e21 100644 --- a/code/game/ai_cmd.c +++ b/code/game/ai_cmd.c @@ -1198,8 +1198,7 @@ void BotMatch_JoinSubteam(bot_state_t *bs, bot_match_t *match) { //get the sub team name trap_BotMatchVariable(match, TEAMNAME, teammate, sizeof(teammate)); //set the sub team name - strncpy(bs->subteam, teammate, 32); - bs->subteam[31] = '\0'; + Q_strncpyz(bs->subteam, teammate, 32); // trap_BotMatchVariable(match, NETNAME, netname, sizeof(netname)); BotAI_BotInitialChat(bs, "joinedteam", teammate, NULL); @@ -1391,8 +1390,7 @@ void BotMatch_StartTeamLeaderShip(bot_state_t *bs, bot_match_t *match) { if (match->subtype & ST_I) { //get the team mate that will be the team leader trap_BotMatchVariable(match, NETNAME, teammate, sizeof(teammate)); - strncpy(bs->teamleader, teammate, sizeof(bs->teamleader)); - bs->teamleader[sizeof(bs->teamleader)-1] = '\0'; + Q_strncpyz(bs->teamleader, teammate, sizeof(bs->teamleader)); } //chats for someone else else { diff --git a/code/game/ai_dmq3.c b/code/game/ai_dmq3.c index d3ef414..ad5b30a 100644 --- a/code/game/ai_dmq3.c +++ b/code/game/ai_dmq3.c @@ -1508,8 +1508,7 @@ char *ClientName(int client, char *name, int size) { return "[client out of range]"; } trap_GetConfigstring(CS_PLAYERS+client, buf, sizeof(buf)); - strncpy(name, Info_ValueForKey(buf, "n"), size-1); - name[size-1] = '\0'; + Q_strncpyz(name, Info_ValueForKey(buf, "n"), size); Q_CleanStr( name ); return name; } @@ -1527,8 +1526,7 @@ char *ClientSkin(int client, char *skin, int size) { return "[client out of range]"; } trap_GetConfigstring(CS_PLAYERS+client, buf, sizeof(buf)); - strncpy(skin, Info_ValueForKey(buf, "model"), size-1); - skin[size-1] = '\0'; + Q_strncpyz(skin, Info_ValueForKey(buf, "model"), size); return skin; } @@ -1631,8 +1629,7 @@ char *EasyClientName(int client, char *buf, int size) { memmove(ptr, ptr+1, strlen(ptr + 1)+1); } } - strncpy(buf, name, size-1); - buf[size-1] = '\0'; + Q_strncpyz(buf, name, size); return buf; } @@ -3785,8 +3782,7 @@ void BotMapScripts(bot_state_t *bs) { trap_GetServerinfo(info, sizeof(info)); - strncpy(mapname, Info_ValueForKey( info, "mapname" ), sizeof(mapname)-1); - mapname[sizeof(mapname)-1] = '\0'; + Q_strncpyz(mapname, Info_ValueForKey(info, "mapname"), sizeof(mapname)); if (!Q_stricmp(mapname, "q3tourney6")) { vec3_t mins = {700, 204, 672}, maxs = {964, 468, 680}; diff --git a/code/game/ai_team.c b/code/game/ai_team.c index d4fe1b0..dffcb19 100644 --- a/code/game/ai_team.c +++ b/code/game/ai_team.c @@ -2127,8 +2127,7 @@ void BotTeamAI(bot_state_t *bs) { trap_BotEnterChat(bs->cs, 0, CHAT_TEAM); BotSayVoiceTeamOrder(bs, -1, VOICECHAT_STARTLEADER); ClientName(bs->client, netname, sizeof(netname)); - strncpy(bs->teamleader, netname, sizeof(bs->teamleader)); - bs->teamleader[sizeof(bs->teamleader)-1] = '\0'; + Q_strncpyz(bs->teamleader, netname, sizeof(bs->teamleader)); bs->becometeamleader_time = 0; } return; diff --git a/code/game/bg_pmove.c b/code/game/bg_pmove.c index 52c0b81..0ec639a 100644 --- a/code/game/bg_pmove.c +++ b/code/game/bg_pmove.c @@ -799,13 +799,13 @@ static void PM_WalkMove( void ) { if ( pm->ps->pm_flags & PMF_DUCKED ) { float* velocity = pm->ps->velocity; vec3_t vec; - float speed; + //float speed; VectorCopy( velocity, vec ); if ( pml.walking ) { vec[2] = 0; // ignore slope movement } - speed = VectorLength(vec); + //speed = VectorLength(vec); if ( wishspeed > pm->ps->speed * pm_duckScale ) { wishspeed = pm->ps->speed * pm_duckScale; } diff --git a/code/game/bg_public.h b/code/game/bg_public.h index 9de827b..3b2eb9c 100644 --- a/code/game/bg_public.h +++ b/code/game/bg_public.h @@ -109,7 +109,7 @@ Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA #define CS_MAX (CS_PARTICLES+MAX_LOCATIONS) -#define REVISION 332 +#define REVISION 333 #if (CS_MAX) > MAX_CONFIGSTRINGS #error overflow: (CS_MAX) > MAX_CONFIGSTRINGS #endif diff --git a/code/game/g_client.c b/code/game/g_client.c index 98b8ce9..814c38b 100644 --- a/code/game/g_client.c +++ b/code/game/g_client.c @@ -2064,7 +2064,7 @@ void ClientBegin( int clientNum ) { if(strlen(custom_vote_info)) SendCustomVoteCommands(clientNum); - SendReadymask( ent-g_entities ); + SendReadymask( -1 ); if( level.timeout ) Cmd_Timeout_f( ent ); diff --git a/code/game/g_cmds.c b/code/game/g_cmds.c index 8e7bfdf..911dbf9 100644 --- a/code/game/g_cmds.c +++ b/code/game/g_cmds.c @@ -73,7 +73,8 @@ void DeathmatchScoreboardMessage( gentity_t *ent ) { perfect = ( cl->ps.persistant[PERS_RANK] == 0 && cl->ps.persistant[PERS_KILLED] == 0 ) ? 1 : 0; if ( g_gametype.integer == GT_TOURNAMENT ) { - if ( ( ent->client->ps.clientNum == cl->ps.clientNum ) || level.intermissiontime || ent->client->sess.sessionTeam == TEAM_SPECTATOR ) { + if ( ( ent->client->ps.clientNum == cl->ps.clientNum ) || level.intermissiontime || + ent->client->sess.sessionTeam == TEAM_SPECTATOR ) { Com_sprintf (entry, sizeof(entry), " %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i ", level.sortedClients[i], cl->ps.persistant[PERS_SCORE], ping, (level.time - cl->pers.enterTime)/60000, @@ -138,7 +139,8 @@ void DeathmatchScoreboardMessage( gentity_t *ent ) { ); } } else { - if ( ( ent->client->ps.clientNum == cl->ps.clientNum ) || level.intermissiontime || ent->client->sess.sessionTeam == TEAM_SPECTATOR ) { + if ( ( ent->client->ps.clientNum == cl->ps.clientNum ) || level.intermissiontime || + ent->client->sess.sessionTeam == TEAM_SPECTATOR ) { Com_sprintf (entry, sizeof(entry), " %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i %i ", level.sortedClients[i], cl->ps.persistant[PERS_SCORE], ping, (level.time - cl->pers.enterTime)/60000, @@ -474,10 +476,14 @@ void G_StartServerDemos( void ) { count = 0; for ( j = 0; j < 128 ; j++ ) { - if ( playerName[j] == '^' && ( ( playerName[j+1] >= '0' && playerName[j+1] <= '9' ) || ( playerName[j+1] >= 'a' && playerName[j+1] <= 'z' ) || ( playerName[j+1] >= 'A' && playerName[j+1] <= 'Z' ) ) ) { + if ( playerName[j] == '^' && ( ( playerName[j+1] >= '0' && playerName[j+1] <= '9' ) || + ( playerName[j+1] >= 'a' && playerName[j+1] <= 'z' ) || + ( playerName[j+1] >= 'A' && playerName[j+1] <= 'Z' ) ) ) { j++; continue; - } else if ( ( ! ( playerName[j] >= '0' && playerName[j] <= '9' ) && ! ( playerName[j] >= 'a' && playerName[j] <= 'z' ) && ! ( playerName[j] >= 'A' && playerName[j] <= 'Z' ) ) ) { + } else if ( ( ! ( playerName[j] >= '0' && playerName[j] <= '9' ) && + ! ( playerName[j] >= 'a' && playerName[j] <= 'z' ) && + ! ( playerName[j] >= 'A' && playerName[j] <= 'Z' ) ) ) { continue; } @@ -1097,7 +1103,6 @@ void Cmd_TeamTask_f( gentity_t *ent ) { } - /* ================= Cmd_Kill_f @@ -1690,14 +1695,20 @@ void Cmd_FollowCycle_f( gentity_t *ent ) { // leave it where it was } +static qboolean FindWordChatText( char *text, char *pattern ) { + if ( Q_stristr(text, pattern) && Q_PrintStrlen(text) == Q_PrintStrlen(pattern) ) + return qtrue; + else + return qfalse; +} /* ================== -G_Say +G_SayTo ================== */ -static void G_SayTo( gentity_t *ent, gentity_t *other, int mode, int color, const char *name, const char *message ) { +static void G_SayTo( gentity_t *ent, gentity_t *other, int mode, int color, const char *name, const char *message, qboolean nobeep ) { if (!other) { return; } @@ -1723,31 +1734,40 @@ static void G_SayTo( gentity_t *ent, gentity_t *other, int mode, int color, cons return; } - trap_SendServerCommand( other-g_entities, va("%s \"%s%c%c%s\"", + trap_SendServerCommand( other-g_entities, va("%s \"%s%c%c%s\" \"%d\"", mode == SAY_TEAM ? "tchat" : "chat", - name, Q_COLOR_ESCAPE, color, message)); + name, Q_COLOR_ESCAPE, color, message, nobeep)); } +/* +================== +G_Say +================== +*/ #define EC "\x19" void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) { + qboolean console = qfalse; int counter; int j; - gentity_t *other; + gentity_t *other; int color; char name[64]; // don't let text be too long for malicious reasons char text[MAX_SAY_TEXT]; - char location[64]; + char location[64] = {0}; trace_t tr; vec3_t end, forward, right, up, muzzle; - int count; - int enemies; - qboolean powerup; - char userinfo[MAX_INFO_STRING]; + int count; + int enemies = 0; + qboolean powerup; + char userinfo[MAX_INFO_STRING]; float fov; vec3_t angles; vec3_t dist; + char console_text[MAX_SAY_TEXT] = {0}; + char mapname[MAX_MAPNAME]; + qtime_t now; if ((ent->r.svFlags & SVF_BOT) && trap_Cvar_VariableValue( "bot_nochat" )>1) return; @@ -1759,8 +1779,6 @@ void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) mode = SAY_ALL; } - - switch ( mode ) { default: case SAY_ALL: @@ -1793,7 +1811,6 @@ void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) Q_strncpyz( text, chatText, sizeof(text) ); - if ( mode == SAY_TEAM && ent->client->ps.persistant[PERS_TEAM] != TEAM_SPECTATOR ) { for ( counter = 0 ; counter < MAX_SAY_TEXT ; counter++ ) { if ( ( text[counter] == '#' ) && ( counter < MAX_SAY_TEXT - 1 ) ) { @@ -1843,8 +1860,6 @@ void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) text[counter] = '%'; text[counter + 1] = 's'; - enemies = 0; - AngleVectors (ent->client->ps.viewangles, forward, right, up); CalcMuzzlePoint ( ent, forward, right, up, muzzle ); @@ -1854,8 +1869,8 @@ void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) for ( count = 0; count < MAX_GENTITIES; count++ ) { if ( g_entities[count].inuse && g_entities[count].s.eType == ET_PLAYER && - ( g_entities[count].client->ps.persistant[PERS_TEAM] != ent->client->ps.persistant[PERS_TEAM] ) && ( ent->health > 0 ) && - g_entities[count].client->ps.persistant[PERS_TEAM] != TEAM_SPECTATOR ) { + ( g_entities[count].client->ps.persistant[PERS_TEAM] != ent->client->ps.persistant[PERS_TEAM] ) && + ( ent->health > 0 ) && g_entities[count].client->ps.persistant[PERS_TEAM] != TEAM_SPECTATOR ) { trap_Trace(&tr, muzzle, NULL, NULL, g_entities[count].r.currentOrigin, ENTITYNUM_NONE, MASK_SOLID); @@ -1865,8 +1880,6 @@ void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) vectoangles(dist, angles); - //G_Printf(" %f %f %f\n", angles[0], angles[1], angles[2]); - angles[1] = ent->client->ps.viewangles[1] - angles[1]; if ( angles[1] < -180 ) @@ -1881,9 +1894,8 @@ void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) if ( angles[0] > 180 ) angles[0] -= 360; - //G_Printf("angle %f %f\n", angles[1], angles[0] ); - - if ( tr.fraction == 1.0 && ( angles[1] >= -fov/2 && angles[1] <= fov/2) && ( angles[0] >= -fov/2 && angles[0] <= fov/2) ) { + if ( tr.fraction == 1.0 && ( angles[1] >= -fov/2 && angles[1] <= fov/2) && + ( angles[0] >= -fov/2 && angles[0] <= fov/2) ) { powerup = qfalse; if ( g_entities[tr.entityNum].client->ps.powerups[PW_BLUEFLAG] == INT_MAX ) { Com_sprintf( text, sizeof(text), text, va("%s %s", "^4FLAG", "%s" )); @@ -1897,8 +1909,6 @@ void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) Com_sprintf( text, sizeof(text), text, va("%s %s", "^7FLAG", "%s" )); powerup = qtrue; } - /*if( g_entities[tr.entityNum].client->ps.powerups[PW_INVIS] == INT_MAX ) - Com_sprintf( text, sizeof(text), text, va("%s %s", "^7INVIS", "%s" ));*/ if ( g_entities[tr.entityNum].client->ps.powerups[PW_QUAD] == INT_MAX ) { Com_sprintf( text, sizeof(text), text, va("%s %s", "^5QUAD", "%s" )); powerup = qtrue; @@ -1922,13 +1932,8 @@ void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) } } } - if ( enemies == 0 ) - Com_sprintf( text, sizeof(text), text, "0 enemies"); - else if ( enemies == 1 ) - Com_sprintf( text, sizeof(text), text, "1 enemy"); - else - Com_sprintf( text, sizeof(text), text, va("%i enemies", enemies )); - } + Com_sprintf( text, sizeof(text), text, va("%i %s", enemies, enemies == 1 ? "enemy" : "enemies" )); + } else if ( text[counter + 1] == 'F' ) { text[counter] = '%'; text[counter + 1] = 's'; @@ -2080,9 +2085,43 @@ void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) } } + if ( g_adminChatText.integer && mode == SAY_ALL ) { + if ( FindWordChatText( text, "@revision" ) ) { + console_text[0] = '%'; + console_text[1] = 's'; + console = qtrue; + Com_sprintf( console_text, sizeof(console_text), console_text, va("^3%s ^6%i", "Aftershock revision", REVISION ) ); + } + else if ( FindWordChatText( text, "@next" ) ) { + console_text[0] = '%'; + console_text[1] = 's'; + console = qtrue; + if ( g_useMapcycle.integer ) { + trap_Cvar_VariableStringBuffer( "mapname", mapname, sizeof(mapname) ); + Com_sprintf( console_text, sizeof(console_text), console_text, va("^3%s ^6%s", "The next map is", G_GetNextMap(mapname) ) ); + } + else + Com_sprintf( console_text, sizeof( console_text ), console_text, va("%s", "^3Not available without ^6g_useMapcycle" ) ); + } + else if ( FindWordChatText( text, "@time" ) ) { + console_text[0] = '%'; + console_text[1] = 's'; + console = qtrue; + trap_RealTime ( &now ); + Com_sprintf( console_text, sizeof(console_text), console_text, va("^3%s ^6%04d-%02d-%02d %02d:%02d:%02d", + "The server time is", + 1900 + now.tm_year, + 1 + now.tm_mon, + now.tm_mday, + now.tm_hour, + now.tm_min, + now.tm_sec ) ); + } + } + if ( target ) { if ( !target->client->mute[ent->s.clientNum] ) - G_SayTo( ent, target, mode, color, name, text ); + G_SayTo( ent, target, mode, color, name, text, qfalse ); return; } @@ -2095,7 +2134,9 @@ void G_Say( gentity_t *ent, gentity_t *target, int mode, const char *chatText ) for (j = 0; j < level.maxclients; j++) { other = &g_entities[j]; if ( !other->client->mute[ent->s.clientNum] ) - G_SayTo( ent, other, mode, color, name, text ); + G_SayTo( ent, other, mode, color, name, text, qfalse ); + if ( !other->client->mute[ent->s.clientNum] && console ) + G_SayTo( ent, other, mode, color, "", console_text, qtrue ); // no beep for console reply and preserve rcon compatibility } //KK-OAX Admin Command Check from Say/SayTeam line if ( g_adminParseSay.integer ) @@ -2121,7 +2162,7 @@ KK-OAX Modified this to trap the additional arguments from console. ================== */ static void Cmd_Say_f( gentity_t *ent ) { - char *p; + char *p; char arg[MAX_TOKEN_CHARS]; int mode = SAY_ALL; @@ -2197,7 +2238,6 @@ static void Cmd_Tell_f( gentity_t *ent ) { } } - static void G_VoiceTo( gentity_t *ent, gentity_t *other, int mode, const char *id, qboolean voiceonly ) { int color; char *cmd; @@ -2424,8 +2464,7 @@ static void Cmd_VoiceTaunt_f( gentity_t *ent ) { } - -static char *gc_orders[] = { +static char *gc_orders[] = { "hold your position", "hold this position", "come here", @@ -2620,7 +2659,7 @@ void Cmd_Ref_f( gentity_t *ent ) { trap_Cvar_VariableStringBuffer( "nextmap", s, sizeof(s) ); if (*s) { - Com_sprintf( command, sizeof( command ), "%s %d; map_restart; set nextmap \"%s\"", arg1, i,s ); + Com_sprintf( command, sizeof( command ), "%s %d; map_restart; set nextmap \"%s\"", arg1, i, s ); } else { Com_sprintf( command, sizeof( command ), "%s %d; map_restart", arg1, i ); } @@ -2778,7 +2817,6 @@ void Cmd_Ref_f( gentity_t *ent ) { } trap_SendConsoleCommand( EXEC_APPEND, va("%s\n", command ) ); - } /* @@ -3005,7 +3043,7 @@ void Cmd_CallVote_f( gentity_t *ent ) { if ( g_useMapcycle.integer ) { trap_Cvar_VariableStringBuffer("mapname", mapname, sizeof(mapname)); Com_sprintf(level.voteString, sizeof( level.voteString ),"map %s", G_GetNextMap(mapname)); - Com_sprintf( level.voteDisplayString, sizeof( level.voteDisplayString ), "%s (%s)", "Next map?", G_GetNextMap(mapname) ); + Com_sprintf( level.voteDisplayString, sizeof( level.voteDisplayString ), "%s (%s)", "Next map?", G_GetNextMap(mapname) ); } else { trap_Cvar_VariableStringBuffer( "nextmap", s, sizeof(s) ); @@ -3014,7 +3052,7 @@ void Cmd_CallVote_f( gentity_t *ent ) { return; } Com_sprintf( level.voteString, sizeof( level.voteString ), "vstr nextmap"); - Com_sprintf( level.voteDisplayString, sizeof( level.voteDisplayString ), "%s (%s)", "Next map?", G_GetNextMap(mapname) ); + Com_sprintf( level.voteDisplayString, sizeof( level.voteDisplayString ), "%s", "Next map?" ); } //Com_sprintf( level.voteDisplayString, sizeof( level.voteDisplayString ), "%s", level.voteString ); @@ -3587,7 +3625,8 @@ void Cmd_DropFlag_f( gentity_t *other ) { void Cmd_Drop_f( gentity_t *ent ) { - if ( ( ent->client->ps.powerups[PW_NEUTRALFLAG] || ent->client->ps.powerups[PW_REDFLAG] || ent->client->ps.powerups[PW_BLUEFLAG] ) && g_itemDrop.integer & 1 ) + if ( ( ent->client->ps.powerups[PW_NEUTRALFLAG] || ent->client->ps.powerups[PW_REDFLAG] || + ent->client->ps.powerups[PW_BLUEFLAG] ) && g_itemDrop.integer & 1 ) Cmd_DropFlag_f( ent ); else if ( g_itemDrop.integer & 2 ) Cmd_DropWeapon_f( ent ); @@ -3609,7 +3648,6 @@ void Cmd_Lock_f( gentity_t *ent ) { trap_Cvar_Set("g_blueLocked","1"); trap_SendServerCommand( -1, va("screenPrint \"" S_COLOR_BLUE "Blue team" S_COLOR_YELLOW" locked\"") ); } - } void Cmd_Unlock_f( gentity_t *ent ) { @@ -3627,7 +3665,6 @@ void Cmd_Unlock_f( gentity_t *ent ) { trap_Cvar_Set("g_blueLocked","0"); trap_SendServerCommand( -1, va("screenPrint \"" S_COLOR_BLUE "Blue team" S_COLOR_YELLOW" unlocked\"") ); } - } void Cmd_Listplayers_f( gentity_t *ent ) { diff --git a/code/game/g_combat.c b/code/game/g_combat.c index 1e8d213..04a13b1 100644 --- a/code/game/g_combat.c +++ b/code/game/g_combat.c @@ -1530,7 +1530,7 @@ void G_Damage( gentity_t *targ, gentity_t *inflictor, gentity_t *attacker, if( g_gametype.integer == GT_CTF_ELIMINATION && g_elimination_ctf_oneway.integer != 0 && targ == attacker) return; - if ( damage && targ->client && targ != attacker && g_damagePlums.integer ) { + if ( damage && targ->client && targ != attacker && g_damagePlums.integer && targ->health > 0 ) { if ( mod != MOD_SHOTGUN ) { DamagePlum( attacker, targ->r.currentOrigin, damage, mod ); } diff --git a/code/game/g_killspree.c b/code/game/g_killspree.c index 339689a..af6e1c4 100644 --- a/code/game/g_killspree.c +++ b/code/game/g_killspree.c @@ -226,10 +226,7 @@ static char *fillPlaceHolder( char *stringToSearch, char *placeHolder, char *rep if( !( p = strstr( stringToSearch, placeHolder ) ) ) return stringToSearch; - strncpy( output, stringToSearch, p - stringToSearch ); - output[ p - stringToSearch ] = '\0'; - - Q_snprintf( output + ( p - stringToSearch ), output - stringToSearch, "%s%s", replaceWith, p + strlen( placeHolder ) ); + Q_snprintf( output, MAX_SAY_TEXT, "%.*s%s%s", (int)(p - stringToSearch), stringToSearch, replaceWith, p+strlen(placeHolder)); return output; } @@ -251,7 +248,8 @@ static char *CreateMessage( gentity_t *ent, char *message, char *spreeNumber ) //Get the player name. Q_strncpyz( name, ent->client->pers.netname, sizeof( name ) ); //Do Our Replacements - Q_strncpyz( output, fillPlaceHolder( message, "[n]", name ), sizeof( output ) ); + Q_strncpyz( output, fillPlaceHolder( message, "[n]", name ), sizeof( output ) ); + //The following line has a risk of copying output into output. Q_strncpyz can handle the case. Q_strncpyz( output, fillPlaceHolder( output, "[k]", spreeNumber ), sizeof( output ) ); return output; } @@ -507,4 +505,4 @@ void G_checkForMultiKill( gentity_t *ent ) { } - \ No newline at end of file + diff --git a/code/game/g_local.h b/code/game/g_local.h index fa8179c..41fec1a 100644 --- a/code/game/g_local.h +++ b/code/game/g_local.h @@ -1384,6 +1384,7 @@ extern vmCvar_t g_autoRestart; extern vmCvar_t g_writePlayerCoords; extern vmCvar_t g_crosshairNamesFog; extern vmCvar_t g_damagePlums; +extern vmCvar_t g_adminChatText; void trap_Print( const char *text ); void trap_Error( const char *text ) __attribute__((noreturn)); diff --git a/code/game/g_main.c b/code/game/g_main.c index b5a36c4..c20a864 100644 --- a/code/game/g_main.c +++ b/code/game/g_main.c @@ -270,6 +270,7 @@ vmCvar_t g_autoRestart; vmCvar_t g_writePlayerCoords; vmCvar_t g_crosshairNamesFog; vmCvar_t g_damagePlums; +vmCvar_t g_adminChatText; // bk001129 - made static to avoid aliasing static cvarTable_t gameCvarTable[] = { @@ -480,7 +481,7 @@ static cvarTable_t gameCvarTable[] = { { &g_allowRespawnTimer, "g_allowRespawnTimer", "0", CVAR_ARCHIVE, 0, qfalse}, { &g_startWhenReady, "g_startWhenReady", "1", CVAR_ARCHIVE | CVAR_SERVERINFO, 0, qfalse}, - { &g_autoReady, "g_autoReady", "0", CVAR_ARCHIVE | CVAR_SERVERINFO, 0, qfalse}, + { &g_autoReady, "g_autoReady", "0", CVAR_ARCHIVE | CVAR_SERVERINFO, 0, qfalse}, { &g_timeoutAllowed, "g_timeoutAllowed", "0", CVAR_ARCHIVE | CVAR_SERVERINFO, 0, qfalse}, { &g_timeoutTime, "g_timeoutTime", "30000", CVAR_ARCHIVE | CVAR_SERVERINFO, 0, qfalse}, @@ -529,7 +530,8 @@ static cvarTable_t gameCvarTable[] = { { &g_autoRestart, "g_autoRestart", "1", CVAR_ARCHIVE, 0, qfalse }, { &g_writePlayerCoords, "g_writePlayerCoords", "0", CVAR_CHEAT, 0, qfalse }, { &g_crosshairNamesFog, "g_crosshairNamesFog", "0", CVAR_SERVERINFO | CVAR_ARCHIVE, 0, qfalse }, - { &g_damagePlums, "g_damagePlums", "0", CVAR_ARCHIVE, 0, qfalse } + { &g_damagePlums, "g_damagePlums", "0", CVAR_ARCHIVE, 0, qfalse }, + { &g_adminChatText, "g_adminChatText", "0", CVAR_ARCHIVE, 0, qfalse } }; // bk001129 - made static to avoid aliasing @@ -2918,9 +2920,10 @@ void CheckTournament( void ) { if ( level.warmupTime < 0 ) { if ( level.numPlayingClients == 2 ) { if( ( g_startWhenReady.integer && - ( g_entities[level.sortedClients[0]].client->ready || ( g_entities[level.sortedClients[0]].r.svFlags & SVF_BOT ) ) && - ( g_entities[level.sortedClients[1]].client->ready || ( g_entities[level.sortedClients[1]].r.svFlags & SVF_BOT ) ) ) || - !g_startWhenReady.integer || !g_doWarmup.integer || ( g_autoReady.integer > 0 && g_autoReady.integer*1000 < ( level.time - level.timeComplete ) ) ){ + ( g_entities[level.sortedClients[0]].client->ready || ( g_entities[level.sortedClients[0]].r.svFlags & SVF_BOT ) ) && + ( g_entities[level.sortedClients[1]].client->ready || ( g_entities[level.sortedClients[1]].r.svFlags & SVF_BOT ) ) ) || + !g_startWhenReady.integer || !g_doWarmup.integer || ( g_autoReady.integer > 0 && + g_autoReady.integer*1000 < ( level.time - level.timeComplete ) ) ){ // fudge by -1 to account for extra delays if ( g_warmup.integer > 1 ) { level.warmupTime = level.time + ( g_warmup.integer - 1 ) * 1000; @@ -2966,14 +2969,17 @@ void CheckTournament( void ) { if( g_startWhenReady.integer ){ for( i = 0; i < level.numPlayingClients; i++ ){ - if( ( g_entities[level.sortedClients[i]].client->ready || g_entities[level.sortedClients[i]].r.svFlags & SVF_BOT ) && g_entities[level.sortedClients[i]].inuse ) + if( ( g_entities[level.sortedClients[i]].client->ready || g_entities[level.sortedClients[i]].r.svFlags & SVF_BOT ) && + g_entities[level.sortedClients[i]].inuse ) clientsReady++; } } - if( g_doWarmup.integer && g_startWhenReady.integer == 1 && ( clientsReady < level.numPlayingClients/2 + 1 ) && !( g_autoReady.integer > 0 && g_autoReady.integer*1000 < ( level.time - level.timeComplete ) ) ) + if( g_doWarmup.integer && g_startWhenReady.integer == 1 && ( clientsReady < level.numPlayingClients/2 + 1 ) && + !( g_autoReady.integer > 0 && g_autoReady.integer*1000 < ( level.time - level.timeComplete ) ) ) notEnough = qtrue; - if( g_doWarmup.integer && g_startWhenReady.integer == 2 && ( clientsReady < level.numPlayingClients ) && !( g_autoReady.integer > 0 && g_autoReady.integer*1000 < ( level.time - level.timeComplete ) ) ) + if( g_doWarmup.integer && g_startWhenReady.integer == 2 && ( clientsReady < level.numPlayingClients ) && + !( g_autoReady.integer > 0 && g_autoReady.integer*1000 < ( level.time - level.timeComplete ) ) ) notEnough = qtrue; diff --git a/code/game/g_missile.c b/code/game/g_missile.c index 0815281..01db6f4 100644 --- a/code/game/g_missile.c +++ b/code/game/g_missile.c @@ -321,7 +321,7 @@ void ProximityMine_RemoveAll() { mine = NULL; - while ((mine = G_Find (mine, FOFS(classname), "grenade")) != NULL) { + while ((mine = G_Find (mine, FOFS(classname), "prox mine")) != NULL) { mine->think = ProximityMine_Explode; mine->nextthink = level.time + 1; } @@ -338,7 +338,7 @@ void Grenade_RemoveAll( void ) { grenade = NULL; - while ((grenade = G_Find (grenade, FOFS(classname), "prox mine")) != NULL) { + while ((grenade = G_Find (grenade, FOFS(classname), "grenade")) != NULL) { grenade->think = G_ExplodeMissile; grenade->nextthink = level.time + 1; } diff --git a/code/game/g_vote.c b/code/game/g_vote.c index fe4b845..af04ffb 100644 --- a/code/game/g_vote.c +++ b/code/game/g_vote.c @@ -43,11 +43,8 @@ int allowedVote(char *commandStr) { return qfalse; } //Now constructing a string that starts and ends with '/' like: "/clientkick/" - tempStr[0] = '/'; - strncpy(&tempStr[1],commandStr,length); - tempStr[length+1] = '/'; - tempStr[length+2] = '\0'; - if(Q_stristr(voteNames,tempStr) != NULL) + Q_snprintf(tempStr, sizeof(tempStr), "/%s/", commandStr); + if(Q_stristr(voteNames, tempStr) != NULL) return qtrue; else return qfalse; @@ -67,11 +64,8 @@ int allowedRef(char *commandStr) { return qfalse; } //Now constructing a string that starts and ends with '/' like: "/clientkick/" - tempStr[0] = '/'; - strncpy(&tempStr[1],commandStr,length); - tempStr[length+1] = '/'; - tempStr[length+2] = '\0'; - if(Q_stristr(voteNames,tempStr) != NULL) + Q_snprintf(tempStr, sizeof(tempStr), "/%s/", commandStr); + if(Q_stristr(voteNames, tempStr) != NULL) return qtrue; else return qfalse; @@ -210,11 +204,8 @@ int allowedGametype(char *gametypeStr) { //Error: too long return qfalse; } - tempStr[0] = '/'; - strncpy(&tempStr[1],gametypeStr,length); - tempStr[length+1] = '/'; - tempStr[length+2] = '\0'; - if(Q_stristr(voteGametypes,tempStr) != NULL) + Q_snprintf(tempStr, sizeof(tempStr), "/%s/", gametypeStr); + if(Q_stristr(voteGametypes, tempStr) != NULL) return qtrue; else { return qfalse; diff --git a/code/q3_ui/ui_challenges.c b/code/q3_ui/ui_challenges.c index c2ed62c..3033c97 100644 --- a/code/q3_ui/ui_challenges.c +++ b/code/q3_ui/ui_challenges.c @@ -373,7 +373,7 @@ static void UI_Challenges_Init( void ) { challenges.entryIntText[i].style = UI_RIGHT; challenges.entryIntText[i].string = challenges.entryIntString[i]; - strncpy(challenges.entryIntString[i],va("%u",challenges.entryInt[i]),MAX_INT_AS_STRING); + Q_snprintf(challenges.entryIntString[i], MAX_INT_AS_STRING, "%u", challenges.entryInt[i]); y += BIGCHAR_HEIGHT+2; } diff --git a/code/ui/ui_shared.c b/code/ui/ui_shared.c index eba19a2..5755a8d 100644 --- a/code/ui/ui_shared.c +++ b/code/ui/ui_shared.c @@ -2948,8 +2948,7 @@ void Item_Text_Wrapped_Paint(itemDef_t *item) { start = textPtr; p = strchr(textPtr, '\r'); while (p && *p) { - strncpy(buff, start, p-start+1); - buff[p-start] = '\0'; + Q_strncpyz(buff, start, p - start + 1); DC->drawText(x, y, item->textscale, color, buff, 0, 0, item->textStyle); y += height + 5; start += p - start + 1;