2
===========================================================================
3
Copyright (C) 1999-2005 Id Software, Inc.
5
This file is part of Quake III Arena source code.
7
Quake III Arena source code is free software; you can redistribute it
8
and/or modify it under the terms of the GNU General Public License as
9
published by the Free Software Foundation; either version 2 of the License,
10
or (at your option) any later version.
12
Quake III Arena source code is distributed in the hope that it will be
13
useful, but WITHOUT ANY WARRANTY; without even the implied warranty of
14
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15
GNU General Public License for more details.
17
You should have received a copy of the GNU General Public License
18
along with Quake III Arena source code; if not, write to the Free Software
19
Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
20
===========================================================================
23
#ifndef MISSIONPACK // bk001204
24
#error This file not be used for classic Q3A.
28
#include "../ui/ui_shared.h"
30
extern displayContextDef_t cgDC;
33
// set in CG_ParseTeamInfo
35
//static int sortedTeamPlayers[TEAM_MAXOVERLAY];
36
//static int numSortedTeamPlayers;
37
int drawTeamOverlayModificationCount = -1;
39
//static char systemChat[256];
40
//static char teamChat1[256];
41
//static char teamChat2[256];
43
void CG_InitTeamChat(void) {
44
memset(teamChat1, 0, sizeof(teamChat1));
45
memset(teamChat2, 0, sizeof(teamChat2));
46
memset(systemChat, 0, sizeof(systemChat));
49
void CG_SetPrintString(int type, const char *p) {
50
if (type == SYSTEM_PRINT) {
51
strcpy(systemChat, p);
53
strcpy(teamChat2, teamChat1);
58
void CG_CheckOrderPending(void) {
59
if (cgs.gametype < GT_CTF) {
62
if (cgs.orderPending) {
63
//clientInfo_t *ci = cgs.clientinfo + sortedTeamPlayers[cg_currentSelectedPlayer.integer];
64
const char *p1, *p2, *b;
66
switch (cgs.currentOrder) {
67
case TEAMTASK_OFFENSE:
68
p1 = VOICECHAT_ONOFFENSE;
69
p2 = VOICECHAT_OFFENSE;
70
b = "+button7; wait; -button7";
72
case TEAMTASK_DEFENSE:
73
p1 = VOICECHAT_ONDEFENSE;
74
p2 = VOICECHAT_DEFEND;
75
b = "+button8; wait; -button8";
78
p1 = VOICECHAT_ONPATROL;
79
p2 = VOICECHAT_PATROL;
80
b = "+button9; wait; -button9";
83
p1 = VOICECHAT_ONFOLLOW;
84
p2 = VOICECHAT_FOLLOWME;
85
b = "+button10; wait; -button10";
88
p1 = VOICECHAT_ONCAMPING;
91
case TEAMTASK_RETRIEVE:
92
p1 = VOICECHAT_ONGETFLAG;
93
p2 = VOICECHAT_RETURNFLAG;
96
p1 = VOICECHAT_ONFOLLOWCARRIER;
97
p2 = VOICECHAT_FOLLOWFLAGCARRIER;
101
if (cg_currentSelectedPlayer.integer == numSortedTeamPlayers) {
103
trap_SendConsoleCommand(va("cmd vsay_team %s\n", p2));
105
// for the player self
106
if (sortedTeamPlayers[cg_currentSelectedPlayer.integer] == cg.snap->ps.clientNum && p1) {
107
trap_SendConsoleCommand(va("teamtask %i\n", cgs.currentOrder));
108
//trap_SendConsoleCommand(va("cmd say_team %s\n", p2));
109
trap_SendConsoleCommand(va("cmd vsay_team %s\n", p1));
111
//trap_SendConsoleCommand(va("cmd say_team %s, %s\n", ci->name,p));
112
trap_SendConsoleCommand(va("cmd vtell %d %s\n", sortedTeamPlayers[cg_currentSelectedPlayer.integer], p2));
116
trap_SendConsoleCommand(b);
118
cgs.orderPending = qfalse;
122
static void CG_SetSelectedPlayerName( void ) {
123
if (cg_currentSelectedPlayer.integer >= 0 && cg_currentSelectedPlayer.integer < numSortedTeamPlayers) {
124
clientInfo_t *ci = cgs.clientinfo + sortedTeamPlayers[cg_currentSelectedPlayer.integer];
126
trap_Cvar_Set("cg_selectedPlayerName", ci->name);
127
trap_Cvar_Set("cg_selectedPlayer", va("%d", sortedTeamPlayers[cg_currentSelectedPlayer.integer]));
128
cgs.currentOrder = ci->teamTask;
131
trap_Cvar_Set("cg_selectedPlayerName", "Everyone");
134
int CG_GetSelectedPlayer( void ) {
135
if (cg_currentSelectedPlayer.integer < 0 || cg_currentSelectedPlayer.integer >= numSortedTeamPlayers) {
136
cg_currentSelectedPlayer.integer = 0;
138
return cg_currentSelectedPlayer.integer;
141
void CG_SelectNextPlayer( void ) {
142
CG_CheckOrderPending();
143
if (cg_currentSelectedPlayer.integer >= 0 && cg_currentSelectedPlayer.integer < numSortedTeamPlayers) {
144
cg_currentSelectedPlayer.integer++;
146
cg_currentSelectedPlayer.integer = 0;
148
CG_SetSelectedPlayerName();
151
void CG_SelectPrevPlayer( void ) {
152
CG_CheckOrderPending();
153
if (cg_currentSelectedPlayer.integer > 0 && cg_currentSelectedPlayer.integer < numSortedTeamPlayers) {
154
cg_currentSelectedPlayer.integer--;
156
cg_currentSelectedPlayer.integer = numSortedTeamPlayers;
158
CG_SetSelectedPlayerName();
162
static void CG_DrawPlayerArmorIcon( rectDef_t *rect, qboolean draw2D ) {
168
if ( cg_drawStatus.integer == 0 ) {
172
cent = &cg_entities[cg.snap->ps.clientNum];
175
if ( draw2D || ( !cg_draw3dIcons.integer && cg_drawIcons.integer) ) { // bk001206 - parentheses
176
CG_DrawPic( rect->x, rect->y + rect->h/2 + 1, rect->w, rect->h, cgs.media.armorIcon );
177
} else if (cg_draw3dIcons.integer) {
178
VectorClear( angles );
182
angles[YAW] = ( cg.time & 2047 ) * 360 / 2048.0;
184
CG_Draw3DModel( rect->x, rect->y, rect->w, rect->h, cgs.media.armorModel, 0, origin, angles );
189
static void CG_DrawPlayerArmorValue(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle) {
195
cent = &cg_entities[cg.snap->ps.clientNum];
198
value = ps->stats[STAT_ARMOR];
202
trap_R_SetColor( color );
203
CG_DrawPic(rect->x, rect->y, rect->w, rect->h, shader);
204
trap_R_SetColor( NULL );
206
Com_sprintf (num, sizeof(num), "%i", value);
207
value = CG_Text_Width(num, scale, 0);
208
CG_Text_Paint(rect->x + (rect->w - value) / 2, rect->y + rect->h, scale, color, num, 0, 0, textStyle);
212
#ifndef MISSIONPACK // bk001206
213
static float healthColors[4][4] = {
214
// { 0.2, 1.0, 0.2, 1.0 } , { 1.0, 0.2, 0.2, 1.0 }, {0.5, 0.5, 0.5, 1} };
215
// bk0101016 - float const
216
{ 1.0f, 0.69f, 0.0f, 1.0f } , // normal
217
{ 1.0f, 0.2f, 0.2f, 1.0f }, // low health
218
{ 0.5f, 0.5f, 0.5f, 1.0f}, // weapon firing
219
{ 1.0f, 1.0f, 1.0f, 1.0f } }; // health > 100
222
static void CG_DrawPlayerAmmoIcon( rectDef_t *rect, qboolean draw2D ) {
228
cent = &cg_entities[cg.snap->ps.clientNum];
231
if ( draw2D || (!cg_draw3dIcons.integer && cg_drawIcons.integer) ) { // bk001206 - parentheses
233
icon = cg_weapons[ cg.predictedPlayerState.weapon ].ammoIcon;
235
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, icon );
237
} else if (cg_draw3dIcons.integer) {
238
if ( cent->currentState.weapon && cg_weapons[ cent->currentState.weapon ].ammoModel ) {
239
VectorClear( angles );
243
angles[YAW] = 90 + 20 * sin( cg.time / 1000.0 );
244
CG_Draw3DModel( rect->x, rect->y, rect->w, rect->h, cg_weapons[ cent->currentState.weapon ].ammoModel, 0, origin, angles );
249
static void CG_DrawPlayerAmmoValue(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle) {
255
cent = &cg_entities[cg.snap->ps.clientNum];
258
if ( cent->currentState.weapon ) {
259
value = ps->ammo[cent->currentState.weapon];
262
trap_R_SetColor( color );
263
CG_DrawPic(rect->x, rect->y, rect->w, rect->h, shader);
264
trap_R_SetColor( NULL );
266
Com_sprintf (num, sizeof(num), "%i", value);
267
value = CG_Text_Width(num, scale, 0);
268
CG_Text_Paint(rect->x + (rect->w - value) / 2, rect->y + rect->h, scale, color, num, 0, 0, textStyle);
277
static void CG_DrawPlayerHead(rectDef_t *rect, qboolean draw2D) {
283
VectorClear( angles );
285
if ( cg.damageTime && cg.time - cg.damageTime < DAMAGE_TIME ) {
286
frac = (float)(cg.time - cg.damageTime ) / DAMAGE_TIME;
287
size = rect->w * 1.25 * ( 1.5 - frac * 0.5 );
289
stretch = size - rect->w * 1.25;
290
// kick in the direction of damage
291
x -= stretch * 0.5 + cg.damageX * stretch * 0.5;
293
cg.headStartYaw = 180 + cg.damageX * 45;
295
cg.headEndYaw = 180 + 20 * cos( crandom()*M_PI );
296
cg.headEndPitch = 5 * cos( crandom()*M_PI );
298
cg.headStartTime = cg.time;
299
cg.headEndTime = cg.time + 100 + random() * 2000;
301
if ( cg.time >= cg.headEndTime ) {
302
// select a new head angle
303
cg.headStartYaw = cg.headEndYaw;
304
cg.headStartPitch = cg.headEndPitch;
305
cg.headStartTime = cg.headEndTime;
306
cg.headEndTime = cg.time + 100 + random() * 2000;
308
cg.headEndYaw = 180 + 20 * cos( crandom()*M_PI );
309
cg.headEndPitch = 5 * cos( crandom()*M_PI );
312
size = rect->w * 1.25;
315
// if the server was frozen for a while we may have a bad head start time
316
if ( cg.headStartTime > cg.time ) {
317
cg.headStartTime = cg.time;
320
frac = ( cg.time - cg.headStartTime ) / (float)( cg.headEndTime - cg.headStartTime );
321
frac = frac * frac * ( 3 - 2 * frac );
322
angles[YAW] = cg.headStartYaw + ( cg.headEndYaw - cg.headStartYaw ) * frac;
323
angles[PITCH] = cg.headStartPitch + ( cg.headEndPitch - cg.headStartPitch ) * frac;
325
CG_DrawHead( x, rect->y, rect->w, rect->h, cg.snap->ps.clientNum, angles );
328
static void CG_DrawSelectedPlayerHealth( rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle ) {
333
ci = cgs.clientinfo + sortedTeamPlayers[CG_GetSelectedPlayer()];
336
trap_R_SetColor( color );
337
CG_DrawPic(rect->x, rect->y, rect->w, rect->h, shader);
338
trap_R_SetColor( NULL );
340
Com_sprintf (num, sizeof(num), "%i", ci->health);
341
value = CG_Text_Width(num, scale, 0);
342
CG_Text_Paint(rect->x + (rect->w - value) / 2, rect->y + rect->h, scale, color, num, 0, 0, textStyle);
347
static void CG_DrawSelectedPlayerArmor( rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle ) {
351
ci = cgs.clientinfo + sortedTeamPlayers[CG_GetSelectedPlayer()];
355
trap_R_SetColor( color );
356
CG_DrawPic(rect->x, rect->y, rect->w, rect->h, shader);
357
trap_R_SetColor( NULL );
359
Com_sprintf (num, sizeof(num), "%i", ci->armor);
360
value = CG_Text_Width(num, scale, 0);
361
CG_Text_Paint(rect->x + (rect->w - value) / 2, rect->y + rect->h, scale, color, num, 0, 0, textStyle);
367
qhandle_t CG_StatusHandle(int task) {
368
qhandle_t h = cgs.media.assaultShader;
370
case TEAMTASK_OFFENSE :
371
h = cgs.media.assaultShader;
373
case TEAMTASK_DEFENSE :
374
h = cgs.media.defendShader;
376
case TEAMTASK_PATROL :
377
h = cgs.media.patrolShader;
379
case TEAMTASK_FOLLOW :
380
h = cgs.media.followShader;
383
h = cgs.media.campShader;
385
case TEAMTASK_RETRIEVE :
386
h = cgs.media.retrieveShader;
388
case TEAMTASK_ESCORT :
389
h = cgs.media.escortShader;
392
h = cgs.media.assaultShader;
398
static void CG_DrawSelectedPlayerStatus( rectDef_t *rect ) {
399
clientInfo_t *ci = cgs.clientinfo + sortedTeamPlayers[CG_GetSelectedPlayer()];
402
if (cgs.orderPending) {
404
if ( cg.time > cgs.orderTime - 2500 && (cg.time >> 9 ) & 1 ) {
407
h = CG_StatusHandle(cgs.currentOrder);
409
h = CG_StatusHandle(ci->teamTask);
411
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, h );
416
static void CG_DrawPlayerStatus( rectDef_t *rect ) {
417
clientInfo_t *ci = &cgs.clientinfo[cg.snap->ps.clientNum];
419
qhandle_t h = CG_StatusHandle(ci->teamTask);
420
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, h);
425
static void CG_DrawSelectedPlayerName( rectDef_t *rect, float scale, vec4_t color, qboolean voice, int textStyle) {
427
ci = cgs.clientinfo + ((voice) ? cgs.currentVoiceClient : sortedTeamPlayers[CG_GetSelectedPlayer()]);
429
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, ci->name, 0, 0, textStyle);
433
static void CG_DrawSelectedPlayerLocation( rectDef_t *rect, float scale, vec4_t color, int textStyle ) {
435
ci = cgs.clientinfo + sortedTeamPlayers[CG_GetSelectedPlayer()];
437
const char *p = CG_ConfigString(CS_LOCATIONS + ci->location);
441
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, p, 0, 0, textStyle);
445
static void CG_DrawPlayerLocation( rectDef_t *rect, float scale, vec4_t color, int textStyle ) {
446
clientInfo_t *ci = &cgs.clientinfo[cg.snap->ps.clientNum];
448
const char *p = CG_ConfigString(CS_LOCATIONS + ci->location);
452
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, p, 0, 0, textStyle);
458
static void CG_DrawSelectedPlayerWeapon( rectDef_t *rect ) {
461
ci = cgs.clientinfo + sortedTeamPlayers[CG_GetSelectedPlayer()];
463
if ( cg_weapons[ci->curWeapon].weaponIcon ) {
464
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cg_weapons[ci->curWeapon].weaponIcon );
466
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cgs.media.deferShader);
471
static void CG_DrawPlayerScore( rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle ) {
473
int value = cg.snap->ps.persistant[PERS_SCORE];
476
trap_R_SetColor( color );
477
CG_DrawPic(rect->x, rect->y, rect->w, rect->h, shader);
478
trap_R_SetColor( NULL );
480
Com_sprintf (num, sizeof(num), "%i", value);
481
value = CG_Text_Width(num, scale, 0);
482
CG_Text_Paint(rect->x + (rect->w - value) / 2, rect->y + rect->h, scale, color, num, 0, 0, textStyle);
486
static void CG_DrawPlayerItem( rectDef_t *rect, float scale, qboolean draw2D) {
488
vec3_t origin, angles;
490
value = cg.snap->ps.stats[STAT_HOLDABLE_ITEM];
492
CG_RegisterItemVisuals( value );
495
CG_RegisterItemVisuals( value );
496
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cg_items[ value ].icon );
498
VectorClear( angles );
502
angles[YAW] = ( cg.time & 2047 ) * 360 / 2048.0;
503
CG_Draw3DModel(rect->x, rect->y, rect->w, rect->h, cg_items[ value ].models[0], 0, origin, angles );
510
static void CG_DrawSelectedPlayerPowerup( rectDef_t *rect, qboolean draw2D ) {
515
ci = cgs.clientinfo + sortedTeamPlayers[CG_GetSelectedPlayer()];
520
for (j = 0; j < PW_NUM_POWERUPS; j++) {
521
if (ci->powerups & (1 << j)) {
523
item = BG_FindItemForPowerup( j );
525
CG_DrawPic( x, y, rect->w, rect->h, trap_R_RegisterShader( item->icon ) );
537
static void CG_DrawSelectedPlayerHead( rectDef_t *rect, qboolean draw2D, qboolean voice ) {
542
vec3_t mins, maxs, angles;
545
ci = cgs.clientinfo + ((voice) ? cgs.currentVoiceClient : sortedTeamPlayers[CG_GetSelectedPlayer()]);
548
if ( cg_draw3dIcons.integer ) {
554
// offset the origin y and z to center the head
555
trap_R_ModelBounds( cm, mins, maxs );
557
origin[2] = -0.5 * ( mins[2] + maxs[2] );
558
origin[1] = 0.5 * ( mins[1] + maxs[1] );
560
// calculate distance so the head nearly fills the box
561
// assume heads are taller than wide
562
len = 0.7 * ( maxs[2] - mins[2] );
563
origin[0] = len / 0.268; // len / tan( fov/2 )
565
// allow per-model tweaking
566
VectorAdd( origin, ci->headOffset, origin );
572
CG_Draw3DModel( rect->x, rect->y, rect->w, rect->h, ci->headModel, ci->headSkin, origin, angles );
573
} else if ( cg_drawIcons.integer ) {
574
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, ci->modelIcon );
577
// if they are deferred, draw a cross out
578
if ( ci->deferred ) {
579
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cgs.media.deferShader );
586
static void CG_DrawPlayerHealth(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle ) {
593
value = ps->stats[STAT_HEALTH];
596
trap_R_SetColor( color );
597
CG_DrawPic(rect->x, rect->y, rect->w, rect->h, shader);
598
trap_R_SetColor( NULL );
600
Com_sprintf (num, sizeof(num), "%i", value);
601
value = CG_Text_Width(num, scale, 0);
602
CG_Text_Paint(rect->x + (rect->w - value) / 2, rect->y + rect->h, scale, color, num, 0, 0, textStyle);
607
static void CG_DrawRedScore(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle ) {
610
if ( cgs.scores1 == SCORE_NOT_PRESENT ) {
611
Com_sprintf (num, sizeof(num), "-");
614
Com_sprintf (num, sizeof(num), "%i", cgs.scores1);
616
value = CG_Text_Width(num, scale, 0);
617
CG_Text_Paint(rect->x + rect->w - value, rect->y + rect->h, scale, color, num, 0, 0, textStyle);
620
static void CG_DrawBlueScore(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle ) {
624
if ( cgs.scores2 == SCORE_NOT_PRESENT ) {
625
Com_sprintf (num, sizeof(num), "-");
628
Com_sprintf (num, sizeof(num), "%i", cgs.scores2);
630
value = CG_Text_Width(num, scale, 0);
631
CG_Text_Paint(rect->x + rect->w - value, rect->y + rect->h, scale, color, num, 0, 0, textStyle);
634
// FIXME: team name support
635
static void CG_DrawRedName(rectDef_t *rect, float scale, vec4_t color, int textStyle ) {
636
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, cg_redTeamName.string , 0, 0, textStyle);
639
static void CG_DrawBlueName(rectDef_t *rect, float scale, vec4_t color, int textStyle ) {
640
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, cg_blueTeamName.string, 0, 0, textStyle);
643
static void CG_DrawBlueFlagName(rectDef_t *rect, float scale, vec4_t color, int textStyle ) {
645
for ( i = 0 ; i < cgs.maxclients ; i++ ) {
646
if ( cgs.clientinfo[i].infoValid && cgs.clientinfo[i].team == TEAM_RED && cgs.clientinfo[i].powerups & ( 1<< PW_BLUEFLAG )) {
647
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, cgs.clientinfo[i].name, 0, 0, textStyle);
653
static void CG_DrawBlueFlagStatus(rectDef_t *rect, qhandle_t shader) {
654
if (cgs.gametype != GT_CTF && cgs.gametype != GT_1FCTF) {
655
if (cgs.gametype == GT_HARVESTER) {
656
vec4_t color = {0, 0, 1, 1};
657
trap_R_SetColor(color);
658
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cgs.media.blueCubeIcon );
659
trap_R_SetColor(NULL);
664
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, shader );
666
gitem_t *item = BG_FindItemForPowerup( PW_BLUEFLAG );
668
vec4_t color = {0, 0, 1, 1};
669
trap_R_SetColor(color);
670
if( cgs.blueflag >= 0 && cgs.blueflag <= 2 ) {
671
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cgs.media.flagShaders[cgs.blueflag] );
673
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cgs.media.flagShaders[0] );
675
trap_R_SetColor(NULL);
680
static void CG_DrawBlueFlagHead(rectDef_t *rect) {
682
for ( i = 0 ; i < cgs.maxclients ; i++ ) {
683
if ( cgs.clientinfo[i].infoValid && cgs.clientinfo[i].team == TEAM_RED && cgs.clientinfo[i].powerups & ( 1<< PW_BLUEFLAG )) {
685
VectorClear( angles );
686
angles[YAW] = 180 + 20 * sin( cg.time / 650.0 );;
687
CG_DrawHead( rect->x, rect->y, rect->w, rect->h, 0,angles );
693
static void CG_DrawRedFlagName(rectDef_t *rect, float scale, vec4_t color, int textStyle ) {
695
for ( i = 0 ; i < cgs.maxclients ; i++ ) {
696
if ( cgs.clientinfo[i].infoValid && cgs.clientinfo[i].team == TEAM_BLUE && cgs.clientinfo[i].powerups & ( 1<< PW_REDFLAG )) {
697
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, cgs.clientinfo[i].name, 0, 0, textStyle);
703
static void CG_DrawRedFlagStatus(rectDef_t *rect, qhandle_t shader) {
704
if (cgs.gametype != GT_CTF && cgs.gametype != GT_1FCTF) {
705
if (cgs.gametype == GT_HARVESTER) {
706
vec4_t color = {1, 0, 0, 1};
707
trap_R_SetColor(color);
708
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cgs.media.redCubeIcon );
709
trap_R_SetColor(NULL);
714
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, shader );
716
gitem_t *item = BG_FindItemForPowerup( PW_REDFLAG );
718
vec4_t color = {1, 0, 0, 1};
719
trap_R_SetColor(color);
720
if( cgs.redflag >= 0 && cgs.redflag <= 2) {
721
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cgs.media.flagShaders[cgs.redflag] );
723
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cgs.media.flagShaders[0] );
725
trap_R_SetColor(NULL);
730
static void CG_DrawRedFlagHead(rectDef_t *rect) {
732
for ( i = 0 ; i < cgs.maxclients ; i++ ) {
733
if ( cgs.clientinfo[i].infoValid && cgs.clientinfo[i].team == TEAM_BLUE && cgs.clientinfo[i].powerups & ( 1<< PW_REDFLAG )) {
735
VectorClear( angles );
736
angles[YAW] = 180 + 20 * sin( cg.time / 650.0 );;
737
CG_DrawHead( rect->x, rect->y, rect->w, rect->h, 0,angles );
743
static void CG_HarvesterSkulls(rectDef_t *rect, float scale, vec4_t color, qboolean force2D, int textStyle ) {
745
vec3_t origin, angles;
747
int value = cg.snap->ps.generic1;
749
if (cgs.gametype != GT_HARVESTER) {
757
Com_sprintf (num, sizeof(num), "%i", value);
758
value = CG_Text_Width(num, scale, 0);
759
CG_Text_Paint(rect->x + (rect->w - value), rect->y + rect->h, scale, color, num, 0, 0, textStyle);
761
if (cg_drawIcons.integer) {
762
if (!force2D && cg_draw3dIcons.integer) {
767
angles[YAW] = ( cg.time & 2047 ) * 360 / 2048.0;
768
if( cg.snap->ps.persistant[PERS_TEAM] == TEAM_BLUE ) {
769
handle = cgs.media.redCubeModel;
771
handle = cgs.media.blueCubeModel;
773
CG_Draw3DModel( rect->x, rect->y, 35, 35, handle, 0, origin, angles );
775
if( cg.snap->ps.persistant[PERS_TEAM] == TEAM_BLUE ) {
776
handle = cgs.media.redCubeIcon;
778
handle = cgs.media.blueCubeIcon;
780
CG_DrawPic( rect->x + 3, rect->y + 16, 20, 20, handle );
785
static void CG_OneFlagStatus(rectDef_t *rect) {
786
if (cgs.gametype != GT_1FCTF) {
789
gitem_t *item = BG_FindItemForPowerup( PW_NEUTRALFLAG );
791
if( cgs.flagStatus >= 0 && cgs.flagStatus <= 4 ) {
792
vec4_t color = {1, 1, 1, 1};
794
if (cgs.flagStatus == FLAG_TAKEN_RED) {
795
color[1] = color[2] = 0;
797
} else if (cgs.flagStatus == FLAG_TAKEN_BLUE) {
798
color[0] = color[1] = 0;
800
} else if (cgs.flagStatus == FLAG_DROPPED) {
803
trap_R_SetColor(color);
804
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cgs.media.flagShaders[index] );
811
static void CG_DrawCTFPowerUp(rectDef_t *rect) {
814
if (cgs.gametype < GT_CTF) {
817
value = cg.snap->ps.stats[STAT_PERSISTANT_POWERUP];
819
CG_RegisterItemVisuals( value );
820
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, cg_items[ value ].icon );
826
static void CG_DrawTeamColor(rectDef_t *rect, vec4_t color) {
827
CG_DrawTeamBackground(rect->x, rect->y, rect->w, rect->h, color[3], cg.snap->ps.persistant[PERS_TEAM]);
830
static void CG_DrawAreaPowerUp(rectDef_t *rect, int align, float special, float scale, vec4_t color) {
832
int sorted[MAX_POWERUPS];
833
int sortedTime[MAX_POWERUPS];
847
inc = (align == HUD_VERTICAL) ? &r2.y : &r2.x;
851
if ( ps->stats[STAT_HEALTH] <= 0 ) {
855
// sort the list by time remaining
857
for ( i = 0 ; i < MAX_POWERUPS ; i++ ) {
858
if ( !ps->powerups[ i ] ) {
861
t = ps->powerups[ i ] - cg.time;
862
// ZOID--don't draw if the power up has unlimited time (999 seconds)
863
// This is true of the CTF flags
864
if ( t <= 0 || t >= 999000) {
868
// insert into the list
869
for ( j = 0 ; j < active ; j++ ) {
870
if ( sortedTime[j] >= t ) {
871
for ( k = active - 1 ; k >= j ; k-- ) {
872
sorted[k+1] = sorted[k];
873
sortedTime[k+1] = sortedTime[k];
883
// draw the icons and timers
884
for ( i = 0 ; i < active ; i++ ) {
885
item = BG_FindItemForPowerup( sorted[i] );
888
t = ps->powerups[ sorted[i] ];
889
if ( t - cg.time >= POWERUP_BLINKS * POWERUP_BLINK_TIME ) {
890
trap_R_SetColor( NULL );
894
f = (float)( t - cg.time ) / POWERUP_BLINK_TIME;
896
modulate[0] = modulate[1] = modulate[2] = modulate[3] = f;
897
trap_R_SetColor( modulate );
900
CG_DrawPic( r2.x, r2.y, r2.w * .75, r2.h, trap_R_RegisterShader( item->icon ) );
902
Com_sprintf (num, sizeof(num), "%i", sortedTime[i] / 1000);
903
CG_Text_Paint(r2.x + (r2.w * .75) + 3 , r2.y + r2.h, scale, color, num, 0, 0, 0);
904
*inc += r2.w + special;
908
trap_R_SetColor( NULL );
912
float CG_GetValue(int ownerDraw) {
917
cent = &cg_entities[cg.snap->ps.clientNum];
921
case CG_SELECTEDPLAYER_ARMOR:
922
ci = cgs.clientinfo + sortedTeamPlayers[CG_GetSelectedPlayer()];
925
case CG_SELECTEDPLAYER_HEALTH:
926
ci = cgs.clientinfo + sortedTeamPlayers[CG_GetSelectedPlayer()];
929
case CG_PLAYER_ARMOR_VALUE:
930
return ps->stats[STAT_ARMOR];
932
case CG_PLAYER_AMMO_VALUE:
933
if ( cent->currentState.weapon ) {
934
return ps->ammo[cent->currentState.weapon];
937
case CG_PLAYER_SCORE:
938
return cg.snap->ps.persistant[PERS_SCORE];
940
case CG_PLAYER_HEALTH:
941
return ps->stats[STAT_HEALTH];
955
qboolean CG_OtherTeamHasFlag(void) {
956
if (cgs.gametype == GT_CTF || cgs.gametype == GT_1FCTF) {
957
int team = cg.snap->ps.persistant[PERS_TEAM];
958
if (cgs.gametype == GT_1FCTF) {
959
if (team == TEAM_RED && cgs.flagStatus == FLAG_TAKEN_BLUE) {
961
} else if (team == TEAM_BLUE && cgs.flagStatus == FLAG_TAKEN_RED) {
967
if (team == TEAM_RED && cgs.redflag == FLAG_TAKEN) {
969
} else if (team == TEAM_BLUE && cgs.blueflag == FLAG_TAKEN) {
979
qboolean CG_YourTeamHasFlag(void) {
980
if (cgs.gametype == GT_CTF || cgs.gametype == GT_1FCTF) {
981
int team = cg.snap->ps.persistant[PERS_TEAM];
982
if (cgs.gametype == GT_1FCTF) {
983
if (team == TEAM_RED && cgs.flagStatus == FLAG_TAKEN_RED) {
985
} else if (team == TEAM_BLUE && cgs.flagStatus == FLAG_TAKEN_BLUE) {
991
if (team == TEAM_RED && cgs.blueflag == FLAG_TAKEN) {
993
} else if (team == TEAM_BLUE && cgs.redflag == FLAG_TAKEN) {
1003
// THINKABOUTME: should these be exclusive or inclusive..
1005
qboolean CG_OwnerDrawVisible(int flags) {
1007
if (flags & CG_SHOW_TEAMINFO) {
1008
return (cg_currentSelectedPlayer.integer == numSortedTeamPlayers);
1011
if (flags & CG_SHOW_NOTEAMINFO) {
1012
return !(cg_currentSelectedPlayer.integer == numSortedTeamPlayers);
1015
if (flags & CG_SHOW_OTHERTEAMHASFLAG) {
1016
return CG_OtherTeamHasFlag();
1019
if (flags & CG_SHOW_YOURTEAMHASENEMYFLAG) {
1020
return CG_YourTeamHasFlag();
1023
if (flags & (CG_SHOW_BLUE_TEAM_HAS_REDFLAG | CG_SHOW_RED_TEAM_HAS_BLUEFLAG)) {
1024
if (flags & CG_SHOW_BLUE_TEAM_HAS_REDFLAG && (cgs.redflag == FLAG_TAKEN || cgs.flagStatus == FLAG_TAKEN_RED)) {
1026
} else if (flags & CG_SHOW_RED_TEAM_HAS_BLUEFLAG && (cgs.blueflag == FLAG_TAKEN || cgs.flagStatus == FLAG_TAKEN_BLUE)) {
1032
if (flags & CG_SHOW_ANYTEAMGAME) {
1033
if( cgs.gametype >= GT_TEAM) {
1038
if (flags & CG_SHOW_ANYNONTEAMGAME) {
1039
if( cgs.gametype < GT_TEAM) {
1044
if (flags & CG_SHOW_HARVESTER) {
1045
if( cgs.gametype == GT_HARVESTER ) {
1052
if (flags & CG_SHOW_ONEFLAG) {
1053
if( cgs.gametype == GT_1FCTF ) {
1060
if (flags & CG_SHOW_CTF) {
1061
if( cgs.gametype == GT_CTF ) {
1066
if (flags & CG_SHOW_OBELISK) {
1067
if( cgs.gametype == GT_OBELISK ) {
1074
if (flags & CG_SHOW_HEALTHCRITICAL) {
1075
if (cg.snap->ps.stats[STAT_HEALTH] < 25) {
1080
if (flags & CG_SHOW_HEALTHOK) {
1081
if (cg.snap->ps.stats[STAT_HEALTH] >= 25) {
1086
if (flags & CG_SHOW_SINGLEPLAYER) {
1087
if( cgs.gametype == GT_SINGLE_PLAYER ) {
1092
if (flags & CG_SHOW_TOURNAMENT) {
1093
if( cgs.gametype == GT_TOURNAMENT ) {
1098
if (flags & CG_SHOW_DURINGINCOMINGVOICE) {
1101
if (flags & CG_SHOW_IF_PLAYER_HAS_FLAG) {
1102
if (cg.snap->ps.powerups[PW_REDFLAG] || cg.snap->ps.powerups[PW_BLUEFLAG] || cg.snap->ps.powerups[PW_NEUTRALFLAG]) {
1111
static void CG_DrawPlayerHasFlag(rectDef_t *rect, qboolean force2D) {
1112
int adj = (force2D) ? 0 : 2;
1113
if( cg.predictedPlayerState.powerups[PW_REDFLAG] ) {
1114
CG_DrawFlagModel( rect->x + adj, rect->y + adj, rect->w - adj, rect->h - adj, TEAM_RED, force2D);
1115
} else if( cg.predictedPlayerState.powerups[PW_BLUEFLAG] ) {
1116
CG_DrawFlagModel( rect->x + adj, rect->y + adj, rect->w - adj, rect->h - adj, TEAM_BLUE, force2D);
1117
} else if( cg.predictedPlayerState.powerups[PW_NEUTRALFLAG] ) {
1118
CG_DrawFlagModel( rect->x + adj, rect->y + adj, rect->w - adj, rect->h - adj, TEAM_FREE, force2D);
1122
static void CG_DrawAreaSystemChat(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader) {
1123
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, systemChat, 0, 0, 0);
1126
static void CG_DrawAreaTeamChat(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader) {
1127
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color,teamChat1, 0, 0, 0);
1130
static void CG_DrawAreaChat(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader) {
1131
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, teamChat2, 0, 0, 0);
1134
const char *CG_GetKillerText(void) {
1136
if ( cg.killerName[0] ) {
1137
s = va("Fragged by %s", cg.killerName );
1143
static void CG_DrawKiller(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle ) {
1144
// fragged by ... line
1145
if ( cg.killerName[0] ) {
1146
int x = rect->x + rect->w / 2;
1147
CG_Text_Paint(x - CG_Text_Width(CG_GetKillerText(), scale, 0) / 2, rect->y + rect->h, scale, color, CG_GetKillerText(), 0, 0, textStyle);
1153
static void CG_DrawCapFragLimit(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle) {
1154
int limit = (cgs.gametype >= GT_CTF) ? cgs.capturelimit : cgs.fraglimit;
1155
CG_Text_Paint(rect->x, rect->y, scale, color, va("%2i", limit),0, 0, textStyle);
1158
static void CG_Draw1stPlace(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle) {
1159
if (cgs.scores1 != SCORE_NOT_PRESENT) {
1160
CG_Text_Paint(rect->x, rect->y, scale, color, va("%2i", cgs.scores1),0, 0, textStyle);
1164
static void CG_Draw2ndPlace(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle) {
1165
if (cgs.scores2 != SCORE_NOT_PRESENT) {
1166
CG_Text_Paint(rect->x, rect->y, scale, color, va("%2i", cgs.scores2),0, 0, textStyle);
1170
const char *CG_GetGameStatusText(void) {
1172
if ( cgs.gametype < GT_TEAM) {
1173
if (cg.snap->ps.persistant[PERS_TEAM] != TEAM_SPECTATOR ) {
1174
s = va("%s place with %i",CG_PlaceString( cg.snap->ps.persistant[PERS_RANK] + 1 ),cg.snap->ps.persistant[PERS_SCORE] );
1177
if ( cg.teamScores[0] == cg.teamScores[1] ) {
1178
s = va("Teams are tied at %i", cg.teamScores[0] );
1179
} else if ( cg.teamScores[0] >= cg.teamScores[1] ) {
1180
s = va("Red leads Blue, %i to %i", cg.teamScores[0], cg.teamScores[1] );
1182
s = va("Blue leads Red, %i to %i", cg.teamScores[1], cg.teamScores[0] );
1188
static void CG_DrawGameStatus(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle ) {
1189
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, CG_GetGameStatusText(), 0, 0, textStyle);
1192
const char *CG_GameTypeString(void) {
1193
if ( cgs.gametype == GT_FFA ) {
1194
return "Free For All";
1195
} else if ( cgs.gametype == GT_TEAM ) {
1196
return "Team Deathmatch";
1197
} else if ( cgs.gametype == GT_CTF ) {
1198
return "Capture the Flag";
1199
} else if ( cgs.gametype == GT_1FCTF ) {
1200
return "One Flag CTF";
1201
} else if ( cgs.gametype == GT_OBELISK ) {
1203
} else if ( cgs.gametype == GT_HARVESTER ) {
1208
static void CG_DrawGameType(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader, int textStyle ) {
1209
CG_Text_Paint(rect->x, rect->y + rect->h, scale, color, CG_GameTypeString(), 0, 0, textStyle);
1212
static void CG_Text_Paint_Limit(float *maxX, float x, float y, float scale, vec4_t color, const char* text, float adjust, int limit) {
1218
// const unsigned char *s = text; // bk001206 - unsigned
1219
const char *s = text;
1222
fontInfo_t *font = &cgDC.Assets.textFont;
1223
if (scale <= cg_smallFont.value) {
1224
font = &cgDC.Assets.smallFont;
1225
} else if (scale > cg_bigFont.value) {
1226
font = &cgDC.Assets.bigFont;
1228
useScale = scale * font->glyphScale;
1229
trap_R_SetColor( color );
1231
if (limit > 0 && len > limit) {
1235
while (s && *s && count < len) {
1236
glyph = &font->glyphs[(int)*s]; // TTimo: FIXME: getting nasty warnings without the cast, hopefully this doesn't break the VM build
1237
if ( Q_IsColorString( s ) ) {
1238
memcpy( newColor, g_color_table[ColorIndex(*(s+1))], sizeof( newColor ) );
1239
newColor[3] = color[3];
1240
trap_R_SetColor( newColor );
1244
float yadj = useScale * glyph->top;
1245
if (CG_Text_Width(s, useScale, 1) + x > max) {
1249
CG_Text_PaintChar(x, y - yadj,
1258
x += (glyph->xSkip * useScale) + adjust;
1264
trap_R_SetColor( NULL );
1271
#define PIC_WIDTH 12
1273
void CG_DrawNewTeamInfo(rectDef_t *rect, float text_x, float text_y, float scale, vec4_t color, qhandle_t shader) {
1276
int i, j, len, count;
1279
float pwidth, lwidth, maxx, leftOver;
1284
// max player name width
1286
count = (numSortedTeamPlayers > 8) ? 8 : numSortedTeamPlayers;
1287
for (i = 0; i < count; i++) {
1288
ci = cgs.clientinfo + sortedTeamPlayers[i];
1289
if ( ci->infoValid && ci->team == cg.snap->ps.persistant[PERS_TEAM]) {
1290
len = CG_Text_Width( ci->name, scale, 0);
1296
// max location name width
1298
for (i = 1; i < MAX_LOCATIONS; i++) {
1299
p = CG_ConfigString(CS_LOCATIONS + i);
1301
len = CG_Text_Width(p, scale, 0);
1309
for (i = 0; i < count; i++) {
1310
ci = cgs.clientinfo + sortedTeamPlayers[i];
1311
if ( ci->infoValid && ci->team == cg.snap->ps.persistant[PERS_TEAM]) {
1314
for (j = 0; j <= PW_NUM_POWERUPS; j++) {
1315
if (ci->powerups & (1 << j)) {
1317
item = BG_FindItemForPowerup( j );
1320
CG_DrawPic( xx, y, PIC_WIDTH, PIC_WIDTH, trap_R_RegisterShader( item->icon ) );
1326
// FIXME: max of 3 powerups shown properly
1327
xx = rect->x + (PIC_WIDTH * 3) + 2;
1329
CG_GetColorForHealth( ci->health, ci->armor, hcolor );
1330
trap_R_SetColor(hcolor);
1331
CG_DrawPic( xx, y + 1, PIC_WIDTH - 2, PIC_WIDTH - 2, cgs.media.heartShader );
1333
//Com_sprintf (st, sizeof(st), "%3i %3i", ci->health, ci->armor);
1334
//CG_Text_Paint(xx, y + text_y, scale, hcolor, st, 0, 0);
1337
xx += PIC_WIDTH + 1;
1339
// weapon used is not that useful, use the space for task
1341
if ( cg_weapons[ci->curWeapon].weaponIcon ) {
1342
CG_DrawPic( xx, y, PIC_WIDTH, PIC_WIDTH, cg_weapons[ci->curWeapon].weaponIcon );
1344
CG_DrawPic( xx, y, PIC_WIDTH, PIC_WIDTH, cgs.media.deferShader );
1348
trap_R_SetColor(NULL);
1349
if (cgs.orderPending) {
1351
if ( cg.time > cgs.orderTime - 2500 && (cg.time >> 9 ) & 1 ) {
1354
h = CG_StatusHandle(cgs.currentOrder);
1357
h = CG_StatusHandle(ci->teamTask);
1361
CG_DrawPic( xx, y, PIC_WIDTH, PIC_WIDTH, h);
1364
xx += PIC_WIDTH + 1;
1366
leftOver = rect->w - xx;
1367
maxx = xx + leftOver / 3;
1371
CG_Text_Paint_Limit(&maxx, xx, y + text_y, scale, color, ci->name, 0, 0);
1373
p = CG_ConfigString(CS_LOCATIONS + ci->location);
1378
xx += leftOver / 3 + 2;
1381
CG_Text_Paint_Limit(&maxx, xx, y + text_y, scale, color, p, 0, 0);
1383
if ( y + text_y + 2 > rect->y + rect->h ) {
1392
void CG_DrawTeamSpectators(rectDef_t *rect, float scale, vec4_t color, qhandle_t shader) {
1393
if (cg.spectatorLen) {
1396
if (cg.spectatorWidth == -1) {
1397
cg.spectatorWidth = 0;
1398
cg.spectatorPaintX = rect->x + 1;
1399
cg.spectatorPaintX2 = -1;
1402
if (cg.spectatorOffset > cg.spectatorLen) {
1403
cg.spectatorOffset = 0;
1404
cg.spectatorPaintX = rect->x + 1;
1405
cg.spectatorPaintX2 = -1;
1408
if (cg.time > cg.spectatorTime) {
1409
cg.spectatorTime = cg.time + 10;
1410
if (cg.spectatorPaintX <= rect->x + 2) {
1411
if (cg.spectatorOffset < cg.spectatorLen) {
1412
cg.spectatorPaintX += CG_Text_Width(&cg.spectatorList[cg.spectatorOffset], scale, 1) - 1;
1413
cg.spectatorOffset++;
1415
cg.spectatorOffset = 0;
1416
if (cg.spectatorPaintX2 >= 0) {
1417
cg.spectatorPaintX = cg.spectatorPaintX2;
1419
cg.spectatorPaintX = rect->x + rect->w - 2;
1421
cg.spectatorPaintX2 = -1;
1424
cg.spectatorPaintX--;
1425
if (cg.spectatorPaintX2 >= 0) {
1426
cg.spectatorPaintX2--;
1431
maxX = rect->x + rect->w - 2;
1432
CG_Text_Paint_Limit(&maxX, cg.spectatorPaintX, rect->y + rect->h - 3, scale, color, &cg.spectatorList[cg.spectatorOffset], 0, 0);
1433
if (cg.spectatorPaintX2 >= 0) {
1434
float maxX2 = rect->x + rect->w - 2;
1435
CG_Text_Paint_Limit(&maxX2, cg.spectatorPaintX2, rect->y + rect->h - 3, scale, color, cg.spectatorList, 0, cg.spectatorOffset);
1437
if (cg.spectatorOffset && maxX > 0) {
1438
// if we have an offset ( we are skipping the first part of the string ) and we fit the string
1439
if (cg.spectatorPaintX2 == -1) {
1440
cg.spectatorPaintX2 = rect->x + rect->w - 2;
1443
cg.spectatorPaintX2 = -1;
1451
void CG_DrawMedal(int ownerDraw, rectDef_t *rect, float scale, vec4_t color, qhandle_t shader) {
1452
score_t *score = &cg.scores[cg.selectedScore];
1457
switch (ownerDraw) {
1459
value = score->accuracy;
1462
value = score->assistCount;
1465
value = score->defendCount;
1468
value = score->excellentCount;
1471
value = score->impressiveCount;
1474
value = score->perfect;
1477
value = score->guantletCount;
1480
value = score->captures;
1485
if (ownerDraw != CG_PERFECT) {
1486
if (ownerDraw == CG_ACCURACY) {
1487
text = va("%i%%", (int)value);
1492
text = va("%i", (int)value);
1503
trap_R_SetColor(color);
1504
CG_DrawPic( rect->x, rect->y, rect->w, rect->h, shader );
1508
value = CG_Text_Width(text, scale, 0);
1509
CG_Text_Paint(rect->x + (rect->w - value) / 2, rect->y + rect->h + 10 , scale, color, text, 0, 0, 0);
1511
trap_R_SetColor(NULL);
1517
void CG_OwnerDraw(float x, float y, float w, float h, float text_x, float text_y, int ownerDraw, int ownerDrawFlags, int align, float special, float scale, vec4_t color, qhandle_t shader, int textStyle) {
1520
if ( cg_drawStatus.integer == 0 ) {
1524
//if (ownerDrawFlags != 0 && !CG_OwnerDrawVisible(ownerDrawFlags)) {
1533
switch (ownerDraw) {
1534
case CG_PLAYER_ARMOR_ICON:
1535
CG_DrawPlayerArmorIcon(&rect, ownerDrawFlags & CG_SHOW_2DONLY);
1537
case CG_PLAYER_ARMOR_ICON2D:
1538
CG_DrawPlayerArmorIcon(&rect, qtrue);
1540
case CG_PLAYER_ARMOR_VALUE:
1541
CG_DrawPlayerArmorValue(&rect, scale, color, shader, textStyle);
1543
case CG_PLAYER_AMMO_ICON:
1544
CG_DrawPlayerAmmoIcon(&rect, ownerDrawFlags & CG_SHOW_2DONLY);
1546
case CG_PLAYER_AMMO_ICON2D:
1547
CG_DrawPlayerAmmoIcon(&rect, qtrue);
1549
case CG_PLAYER_AMMO_VALUE:
1550
CG_DrawPlayerAmmoValue(&rect, scale, color, shader, textStyle);
1552
case CG_SELECTEDPLAYER_HEAD:
1553
CG_DrawSelectedPlayerHead(&rect, ownerDrawFlags & CG_SHOW_2DONLY, qfalse);
1556
CG_DrawSelectedPlayerHead(&rect, ownerDrawFlags & CG_SHOW_2DONLY, qtrue);
1559
CG_DrawSelectedPlayerName(&rect, scale, color, qtrue, textStyle);
1561
case CG_SELECTEDPLAYER_STATUS:
1562
CG_DrawSelectedPlayerStatus(&rect);
1564
case CG_SELECTEDPLAYER_ARMOR:
1565
CG_DrawSelectedPlayerArmor(&rect, scale, color, shader, textStyle);
1567
case CG_SELECTEDPLAYER_HEALTH:
1568
CG_DrawSelectedPlayerHealth(&rect, scale, color, shader, textStyle);
1570
case CG_SELECTEDPLAYER_NAME:
1571
CG_DrawSelectedPlayerName(&rect, scale, color, qfalse, textStyle);
1573
case CG_SELECTEDPLAYER_LOCATION:
1574
CG_DrawSelectedPlayerLocation(&rect, scale, color, textStyle);
1576
case CG_SELECTEDPLAYER_WEAPON:
1577
CG_DrawSelectedPlayerWeapon(&rect);
1579
case CG_SELECTEDPLAYER_POWERUP:
1580
CG_DrawSelectedPlayerPowerup(&rect, ownerDrawFlags & CG_SHOW_2DONLY);
1582
case CG_PLAYER_HEAD:
1583
CG_DrawPlayerHead(&rect, ownerDrawFlags & CG_SHOW_2DONLY);
1585
case CG_PLAYER_ITEM:
1586
CG_DrawPlayerItem(&rect, scale, ownerDrawFlags & CG_SHOW_2DONLY);
1588
case CG_PLAYER_SCORE:
1589
CG_DrawPlayerScore(&rect, scale, color, shader, textStyle);
1591
case CG_PLAYER_HEALTH:
1592
CG_DrawPlayerHealth(&rect, scale, color, shader, textStyle);
1595
CG_DrawRedScore(&rect, scale, color, shader, textStyle);
1598
CG_DrawBlueScore(&rect, scale, color, shader, textStyle);
1601
CG_DrawRedName(&rect, scale, color, textStyle);
1604
CG_DrawBlueName(&rect, scale, color, textStyle);
1606
case CG_BLUE_FLAGHEAD:
1607
CG_DrawBlueFlagHead(&rect);
1609
case CG_BLUE_FLAGSTATUS:
1610
CG_DrawBlueFlagStatus(&rect, shader);
1612
case CG_BLUE_FLAGNAME:
1613
CG_DrawBlueFlagName(&rect, scale, color, textStyle);
1615
case CG_RED_FLAGHEAD:
1616
CG_DrawRedFlagHead(&rect);
1618
case CG_RED_FLAGSTATUS:
1619
CG_DrawRedFlagStatus(&rect, shader);
1621
case CG_RED_FLAGNAME:
1622
CG_DrawRedFlagName(&rect, scale, color, textStyle);
1624
case CG_HARVESTER_SKULLS:
1625
CG_HarvesterSkulls(&rect, scale, color, qfalse, textStyle);
1627
case CG_HARVESTER_SKULLS2D:
1628
CG_HarvesterSkulls(&rect, scale, color, qtrue, textStyle);
1630
case CG_ONEFLAG_STATUS:
1631
CG_OneFlagStatus(&rect);
1633
case CG_PLAYER_LOCATION:
1634
CG_DrawPlayerLocation(&rect, scale, color, textStyle);
1637
CG_DrawTeamColor(&rect, color);
1639
case CG_CTF_POWERUP:
1640
CG_DrawCTFPowerUp(&rect);
1642
case CG_AREA_POWERUP:
1643
CG_DrawAreaPowerUp(&rect, align, special, scale, color);
1645
case CG_PLAYER_STATUS:
1646
CG_DrawPlayerStatus(&rect);
1648
case CG_PLAYER_HASFLAG:
1649
CG_DrawPlayerHasFlag(&rect, qfalse);
1651
case CG_PLAYER_HASFLAG2D:
1652
CG_DrawPlayerHasFlag(&rect, qtrue);
1654
case CG_AREA_SYSTEMCHAT:
1655
CG_DrawAreaSystemChat(&rect, scale, color, shader);
1657
case CG_AREA_TEAMCHAT:
1658
CG_DrawAreaTeamChat(&rect, scale, color, shader);
1661
CG_DrawAreaChat(&rect, scale, color, shader);
1664
CG_DrawGameType(&rect, scale, color, shader, textStyle);
1666
case CG_GAME_STATUS:
1667
CG_DrawGameStatus(&rect, scale, color, shader, textStyle);
1670
CG_DrawKiller(&rect, scale, color, shader, textStyle);
1680
CG_DrawMedal(ownerDraw, &rect, scale, color, shader);
1683
CG_DrawTeamSpectators(&rect, scale, color, shader);
1686
if (cg_currentSelectedPlayer.integer == numSortedTeamPlayers) {
1687
CG_DrawNewTeamInfo(&rect, text_x, text_y, scale, color, shader);
1690
case CG_CAPFRAGLIMIT:
1691
CG_DrawCapFragLimit(&rect, scale, color, shader, textStyle);
1694
CG_Draw1stPlace(&rect, scale, color, shader, textStyle);
1697
CG_Draw2ndPlace(&rect, scale, color, shader, textStyle);
1704
void CG_MouseEvent(int x, int y) {
1707
if ( (cg.predictedPlayerState.pm_type == PM_NORMAL || cg.predictedPlayerState.pm_type == PM_SPECTATOR) && cg.showScores == qfalse) {
1708
trap_Key_SetCatcher(0);
1713
if (cgs.cursorX < 0)
1715
else if (cgs.cursorX > 640)
1719
if (cgs.cursorY < 0)
1721
else if (cgs.cursorY > 480)
1724
n = Display_CursorType(cgs.cursorX, cgs.cursorY);
1725
cgs.activeCursor = 0;
1726
if (n == CURSOR_ARROW) {
1727
cgs.activeCursor = cgs.media.selectCursor;
1728
} else if (n == CURSOR_SIZER) {
1729
cgs.activeCursor = cgs.media.sizeCursor;
1732
if (cgs.capturedItem) {
1733
Display_MouseMove(cgs.capturedItem, x, y);
1735
Display_MouseMove(NULL, cgs.cursorX, cgs.cursorY);
1746
void CG_HideTeamMenu( void ) {
1747
Menus_CloseByName("teamMenu");
1748
Menus_CloseByName("getMenu");
1757
void CG_ShowTeamMenu( void ) {
1758
Menus_OpenByName("teamMenu");
1768
type 0 - no event handling
1773
void CG_EventHandling(int type) {
1774
cgs.eventHandling = type;
1775
if (type == CGAME_EVENT_NONE) {
1777
} else if (type == CGAME_EVENT_TEAMMENU) {
1778
//CG_ShowTeamMenu();
1779
} else if (type == CGAME_EVENT_SCOREBOARD) {
1786
void CG_KeyEvent(int key, qboolean down) {
1792
if ( cg.predictedPlayerState.pm_type == PM_NORMAL || (cg.predictedPlayerState.pm_type == PM_SPECTATOR && cg.showScores == qfalse)) {
1793
CG_EventHandling(CGAME_EVENT_NONE);
1794
trap_Key_SetCatcher(0);
1798
//if (key == trap_Key_GetKey("teamMenu") || !Display_CaptureItem(cgs.cursorX, cgs.cursorY)) {
1799
// if we see this then we should always be visible
1800
// CG_EventHandling(CGAME_EVENT_NONE);
1801
// trap_Key_SetCatcher(0);
1806
Display_HandleKey(key, down, cgs.cursorX, cgs.cursorY);
1808
if (cgs.capturedItem) {
1809
cgs.capturedItem = NULL;
1811
if (key == K_MOUSE2 && down) {
1812
cgs.capturedItem = Display_CaptureItem(cgs.cursorX, cgs.cursorY);
1817
int CG_ClientNumFromName(const char *p) {
1819
for (i = 0; i < cgs.maxclients; i++) {
1820
if (cgs.clientinfo[i].infoValid && Q_stricmp(cgs.clientinfo[i].name, p) == 0) {
1827
void CG_ShowResponseHead(void) {
1828
Menus_OpenByName("voiceMenu");
1829
trap_Cvar_Set("cl_conXOffset", "72");
1830
cg.voiceTime = cg.time;
1833
void CG_RunMenuScript(char **args) {
1837
void CG_GetTeamColor(vec4_t *color) {
1838
if (cg.snap->ps.persistant[PERS_TEAM] == TEAM_RED) {
1840
(*color)[3] = 0.25f;
1841
(*color)[1] = (*color)[2] = 0.0f;
1842
} else if (cg.snap->ps.persistant[PERS_TEAM] == TEAM_BLUE) {
1843
(*color)[0] = (*color)[1] = 0.0f;
1845
(*color)[3] = 0.25f;
1847
(*color)[0] = (*color)[2] = 0.0f;
1848
(*color)[1] = 0.17f;
1849
(*color)[3] = 0.25f;