Skip to content

Commit 3fd1e5d

Browse files
authored
Merge pull request #267 from Vladislav4KZ/spectator-fixes-and-improvements
Spectator fixes and improvements
2 parents 8e77e47 + f9f8570 commit 3fd1e5d

File tree

6 files changed

+170
-12
lines changed

6 files changed

+170
-12
lines changed

cl_dll/hud.h

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -918,6 +918,11 @@ class CHudSpectatorGui: public CHudBase
918918
char m_szNameAndHealth[80];
919919
} label;
920920
int m_hTimerTexture;
921+
int m_hChecked;
922+
int m_hArrowDown;
923+
int m_hArrowUp;
924+
int m_hArrowLeft;
925+
int m_hArrowRight;
921926

922927
enum {
923928
ROOT_MENU = (1<<0),

cl_dll/hud/spectator_gui.cpp

Lines changed: 116 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -99,21 +99,69 @@ int CHudSpectatorGui::VidInit()
9999
}
100100

101101
m_hTimerTexture = gRenderAPI.GL_LoadTexture("gfx/vgui/timer.tga", NULL, 0, TF_NEAREST |TF_NOMIPMAP|TF_CLAMP );
102+
m_hChecked = gRenderAPI.GL_LoadTexture("gfx/vgui/640_checked.tga", NULL, 0, TF_NEAREST | TF_NOMIPMAP | TF_CLAMP );
103+
m_hArrowDown = gRenderAPI.GL_LoadTexture("gfx/vgui/1920_arrowdown.tga", NULL, 0, TF_NEAREST | TF_NOMIPMAP | TF_CLAMP );
104+
m_hArrowUp = gRenderAPI.GL_LoadTexture("gfx/vgui/1920_arrowup.tga", NULL, 0, TF_NEAREST | TF_NOMIPMAP | TF_CLAMP );
105+
m_hArrowLeft = gRenderAPI.GL_LoadTexture("gfx/vgui/1920_arrowleft.tga", NULL, 0, TF_NEAREST | TF_NOMIPMAP | TF_CLAMP );
106+
m_hArrowRight = gRenderAPI.GL_LoadTexture("gfx/vgui/1920_arrowright.tga", NULL, 0, TF_NEAREST | TF_NOMIPMAP | TF_CLAMP );
102107
return 1;
103108
}
104109

105110
void CHudSpectatorGui::Shutdown()
106111
{
107112
gRenderAPI.GL_FreeTexture( m_hTimerTexture );
113+
gRenderAPI.GL_FreeTexture( m_hChecked );
114+
gRenderAPI.GL_FreeTexture( m_hArrowDown );
115+
gRenderAPI.GL_FreeTexture( m_hArrowUp );
116+
gRenderAPI.GL_FreeTexture( m_hArrowLeft );
117+
gRenderAPI.GL_FreeTexture( m_hArrowRight );
108118
}
109119

110-
inline void DrawButtonWithText( int x1, int y1, int wide, int tall, const char *sz, int r, int g, int b )
120+
inline void DrawButtonWithText( int x1, int y1, int wide, int tall, const char *sz, int r, int g, int b, bool highlight = false )
111121
{
112122
DrawUtils::DrawRectangle(x1, y1, wide, tall);
123+
124+
if ( highlight )
125+
{
126+
FillRGBABlend(x1, y1, wide, tall, r, g, b, 48);
127+
}
128+
113129
DrawUtils::DrawHudString(x1 + INT_XPOS(0.5), y1 + tall*0.5 - gHUD.GetCharHeight() * 0.5, x1 + wide, sz,
114130
r, g, b );
115131
}
116132

133+
// Unified icon drawing helper. align: -1 = left, 0 = center, 1 = right
134+
static void DrawIconOnButton( int x1, int y1, int wide, int tall, int hTex, int align = -1, int r = 255, int g = 255, int b = 255, float alpha = 1.0f, int pad = 15 )
135+
{
136+
if( !hTex )
137+
return;
138+
139+
gRenderAPI.GL_SelectTexture( 0 );
140+
gRenderAPI.GL_Bind( 0, hTex );
141+
gEngfuncs.pTriAPI->RenderMode( kRenderTransAlpha );
142+
gEngfuncs.pTriAPI->Color4f( r / 255.0f, g / 255.0f, b / 255.0f, alpha );
143+
144+
int uploadW = (int)gRenderAPI.RenderGetParm( PARM_TEX_WIDTH, hTex );
145+
int uploadH = (int)gRenderAPI.RenderGetParm( PARM_TEX_HEIGHT, hTex );
146+
147+
148+
// compute quad position in pixels
149+
float quadX = x1;
150+
float quadY = y1 + ( tall - uploadH ) / 2.0f;
151+
152+
if( align == -1 ) // left
153+
quadX = x1 + pad; // small padding from left
154+
else if( align == 0 ) // center
155+
quadX = x1 + ( wide - uploadW ) * 0.5f;
156+
else if( align == 1 ) // right
157+
quadX = x1 + wide - uploadW - pad; // small padding from right
158+
159+
DrawUtils::Draw2DQuad( quadX * gHUD.m_flScale,
160+
quadY * gHUD.m_flScale,
161+
(quadX + (float)uploadW) * gHUD.m_flScale,
162+
(quadY + (float)uploadH) * gHUD.m_flScale );
163+
}
164+
117165
int CHudSpectatorGui::Draw( float flTime )
118166
{
119167
if( !g_iUser1 )
@@ -206,28 +254,89 @@ int CHudSpectatorGui::Draw( float flTime )
206254
if( m_menuFlags & ROOT_MENU )
207255
{
208256
// draw the root menu
209-
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1), "Options", r, g, b);
210-
DrawButtonWithText(INT_XPOS(5), INT_YPOS(8.5), INT_XPOS(1), INT_YPOS(1), "<", r, g, b);
257+
258+
// options
259+
{
260+
// highlight when opened
261+
if( m_menuFlags & MENU_OPTIONS )
262+
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1), "Options", r, g, b, true);
263+
else
264+
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1), "Options", r, g, b );
265+
// arrow on right part of button: down when closed, up when open
266+
if( m_menuFlags & MENU_OPTIONS )
267+
DrawIconOnButton( INT_XPOS(0.5), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1), m_hArrowUp, 1, r, g, b );
268+
else
269+
DrawIconOnButton( INT_XPOS(0.5), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1), m_hArrowDown, 1, r, g, b );
270+
}
271+
272+
DrawUtils::DrawRectangle(INT_XPOS(5), INT_YPOS(8.5), INT_XPOS(1), INT_YPOS(1));
273+
DrawIconOnButton( INT_XPOS(5), INT_YPOS(8.5), INT_XPOS(1), INT_YPOS(1), m_hArrowLeft, 0, r, g, b );
211274

212275
DrawUtils::DrawRectangle(INT_XPOS(6), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1));
213276
// name will be drawn later
214277

215-
DrawButtonWithText(INT_XPOS(10), INT_YPOS(8.5), INT_XPOS(1), INT_YPOS(1), ">", r, g, b );
216-
DrawButtonWithText(INT_XPOS(11.5), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1), "Spectate Options", r, g, b);
278+
DrawUtils::DrawRectangle(INT_XPOS(10), INT_YPOS(8.5), INT_XPOS(1), INT_YPOS(1));
279+
DrawIconOnButton( INT_XPOS(10), INT_YPOS(8.5), INT_XPOS(1), INT_YPOS(1), m_hArrowRight, 0, r, g, b );
280+
281+
// spectate options
282+
{
283+
// highlight when opened
284+
if( m_menuFlags & MENU_SPEC_OPTIONS )
285+
DrawButtonWithText(INT_XPOS(11.5), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1), "Spectate Options", r, g, b, true);
286+
else
287+
DrawButtonWithText(INT_XPOS(11.5), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1), "Spectate Options", r, g, b );
288+
// arrow on right part of button: down when closed, up when open
289+
if( m_menuFlags & MENU_SPEC_OPTIONS )
290+
DrawIconOnButton( INT_XPOS(11.5), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1), m_hArrowUp, 1, r, g, b );
291+
else
292+
DrawIconOnButton( INT_XPOS(11.5), INT_YPOS(8.5), INT_XPOS(4), INT_YPOS(1), m_hArrowDown, 1, r, g, b );
293+
}
294+
217295
if( m_menuFlags & MENU_OPTIONS )
218296
{
219297
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(2.5), INT_XPOS(4), INT_YPOS(1), "Close", r, g, b );
220298
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(3.5), INT_XPOS(4), INT_YPOS(1), "Help", r, g, b );
221-
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(4.5), INT_XPOS(4), INT_YPOS(1), "Settings", r, g, b );
299+
300+
// settings
301+
{
302+
// highlight when opened
303+
if( m_menuFlags & MENU_OPTIONS_SETTINGS )
304+
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(4.5), INT_XPOS(4), INT_YPOS(1), "Settings", r, g, b, true );
305+
else
306+
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(4.5), INT_XPOS(4), INT_YPOS(1), "Settings", r, g, b );
307+
308+
DrawIconOnButton( INT_XPOS(0.5), INT_YPOS(4.5), INT_XPOS(4), INT_YPOS(1), m_hArrowRight, 1, r, g, b );
309+
}
310+
222311
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(5.5), INT_XPOS(4), INT_YPOS(1), "Picture-in-Picture", r, g, b );
312+
if( gHUD.m_Spectator.m_pip && gHUD.m_Spectator.m_pip->value != INSET_OFF )
313+
DrawIconOnButton( INT_XPOS(0.5), INT_YPOS(5.5), INT_XPOS(4), INT_YPOS(1), m_hChecked, -1, r, g, b );
314+
223315
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(6.5), INT_XPOS(4), INT_YPOS(1), "Autodirector", r, g, b );
316+
if( gHUD.m_Spectator.m_autoDirector && gHUD.m_Spectator.m_autoDirector->value )
317+
DrawIconOnButton( INT_XPOS(0.5), INT_YPOS(6.5), INT_XPOS(4), INT_YPOS(1), m_hChecked, -1, r, g, b );
318+
224319
DrawButtonWithText(INT_XPOS(0.5), INT_YPOS(7.5), INT_XPOS(4), INT_YPOS(1), "Show scores", r, g, b );
320+
if( gHUD.m_Scoreboard.m_bForceDraw || gHUD.m_Scoreboard.m_bShowscoresHeld )
321+
DrawIconOnButton( INT_XPOS(0.5), INT_YPOS(7.5), INT_XPOS(4), INT_YPOS(1), m_hChecked, -1, r, g, b );
322+
225323
if( m_menuFlags & MENU_OPTIONS_SETTINGS )
226324
{
227325
DrawButtonWithText(INT_XPOS(4.5), INT_YPOS(4.5), INT_XPOS(4), INT_YPOS(1), "Chat messages", r, g, b );
326+
if( gHUD.m_Spectator.m_HUD_saytext && gHUD.m_Spectator.m_HUD_saytext->value )
327+
DrawIconOnButton( INT_XPOS(4.5), INT_YPOS(4.5), INT_XPOS(4), INT_YPOS(1), m_hChecked, -1, r, g, b );
328+
228329
DrawButtonWithText(INT_XPOS(4.5), INT_YPOS(5.5), INT_XPOS(4), INT_YPOS(1), "Show status", r, g, b );
330+
if( gHUD.m_Spectator.m_drawstatus && gHUD.m_Spectator.m_drawstatus->value )
331+
DrawIconOnButton( INT_XPOS(4.5), INT_YPOS(5.5), INT_XPOS(4), INT_YPOS(1), m_hChecked, -1, r, g, b );
332+
229333
DrawButtonWithText(INT_XPOS(4.5), INT_YPOS(6.5), INT_XPOS(4), INT_YPOS(1), "View cone", r, g, b );
334+
if( gHUD.m_Spectator.m_drawcone && gHUD.m_Spectator.m_drawcone->value )
335+
DrawIconOnButton( INT_XPOS(4.5), INT_YPOS(6.5), INT_XPOS(4), INT_YPOS(1), m_hChecked, -1, r, g, b );
336+
230337
DrawButtonWithText(INT_XPOS(4.5), INT_YPOS(7.5), INT_XPOS(4), INT_YPOS(1), "Player names", r, g, b );
338+
if( gHUD.m_Spectator.m_drawnames && gHUD.m_Spectator.m_drawnames->value )
339+
DrawIconOnButton( INT_XPOS(4.5), INT_YPOS(7.5), INT_XPOS(4), INT_YPOS(1), m_hChecked, -1, r, g, b );
231340
}
232341
}
233342

@@ -438,7 +547,7 @@ void CHudSpectatorGui::UserCmd_ToggleSpectatorMenuOptionsSettings()
438547
if( !(m_menuFlags & MENU_OPTIONS_SETTINGS) )
439548
{
440549
m_menuFlags |= MENU_OPTIONS_SETTINGS;
441-
gMobileAPI.pfnTouchAddClientButton( "_spec_opt_chat_msgs", "*white", "messagemode; _spec_toggle_menu_options_settings",
550+
gMobileAPI.pfnTouchAddClientButton( "_spec_opt_chat_msgs", "*white", "hud_saytext t; _spec_toggle_menu_options_settings",
442551
PLACE_DEFAULT_SIZE_BUTTON_AT_X_Y( 4.5f, 4.5f ), color, 0, 1.0f, 0 );
443552
gMobileAPI.pfnTouchAddClientButton( "_spec_opt_set_status", "*white", "spec_drawstatus t; _spec_toggle_menu_options_settings",
444553
PLACE_DEFAULT_SIZE_BUTTON_AT_X_Y( 4.5f, 5.5f ), color, 0, 1.0f, 0 );

cl_dll/hud_spectator.cpp

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -182,6 +182,42 @@ void SpecPip( void )
182182
const char *name = "spec_pip_internal";
183183
char *arg = gEngfuncs.Cmd_Argv(1);
184184

185+
if( arg[0] == 't' && arg[1] == '\0' )
186+
{
187+
if ( gHUD.m_Spectator.m_pip && (int)gHUD.m_Spectator.m_pip->value != INSET_OFF )
188+
{
189+
gHUD.m_Spectator.SetModes( -1, INSET_OFF );
190+
}
191+
else
192+
{
193+
// ensure overview data and map sprite are loaded before enabling PiP
194+
gHUD.m_Spectator.ParseOverviewFile();
195+
gHUD.m_Spectator.LoadMapSprites();
196+
197+
// if map overview is open in fullscreen, show Locked Chase Cam in inset (player chase)
198+
int insetMode = INSET_MAP_FREE;
199+
if ( g_iUser1 == OBS_MAP_FREE || g_iUser1 == OBS_MAP_CHASE )
200+
insetMode = INSET_CHASE_LOCKED;
201+
gHUD.m_Spectator.SetModes( -1, insetMode );
202+
}
203+
}
204+
else
205+
{
206+
gEngfuncs.Cvar_Set( name, gEngfuncs.Cmd_Argv(1) );
207+
}
208+
}
209+
210+
void HudSayText( void )
211+
{
212+
if ( gEngfuncs.Cmd_Argc() <= 1 )
213+
{
214+
gEngfuncs.Con_Printf( "usage: hud_saytext <0|1>\n" );
215+
return;
216+
}
217+
218+
const char *name = "hud_saytext_internal";
219+
char *arg = gEngfuncs.Cmd_Argv(1);
220+
185221
if( arg[0] == 't' && arg[1] == '\0' )
186222
gEngfuncs.Cvar_SetValue( name, !gEngfuncs.pfnGetCvarFloat(name) );
187223
else
@@ -213,13 +249,15 @@ int CHudSpectator::Init()
213249
gEngfuncs.pfnAddCommand ("spec_drawnames", SpecDrawNames );
214250
gEngfuncs.pfnAddCommand ("spec_drawcone", SpecDrawCone );
215251
gEngfuncs.pfnAddCommand ("spec_drawstatus", SpecDrawStatus );
252+
gEngfuncs.pfnAddCommand ("hud_saytext", HudSayText );
216253
gEngfuncs.pfnAddCommand ("spec_autodirector", SpecAutoDirector );
217254
gEngfuncs.pfnAddCommand ("spec_pip", SpecPip );
218255

219256
m_drawnames = gEngfuncs.pfnRegisterVariable("spec_drawnames_internal","1",0);
220257
m_drawcone = gEngfuncs.pfnRegisterVariable("spec_drawcone_internal","1",0);
221258
m_drawstatus = gEngfuncs.pfnRegisterVariable("spec_drawstatus_internal","1",0);
222259
m_autoDirector = gEngfuncs.pfnRegisterVariable("spec_autodirector_internal","1",0);
260+
m_HUD_saytext = gEngfuncs.pfnRegisterVariable("hud_saytext_internal","1",0);
223261
m_pip = gEngfuncs.pfnRegisterVariable("spec_pip_internal","1",0);
224262
m_lastAutoDirector = 0.0f;
225263

cl_dll/hud_spectator.h

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,10 +13,11 @@
1313

1414

1515
#define INSET_OFF 0
16-
#define INSET_CHASE_FREE 1
17-
#define INSET_IN_EYE 2
18-
#define INSET_MAP_FREE 3
19-
#define INSET_MAP_CHASE 4
16+
#define INSET_CHASE_LOCKED 1
17+
#define INSET_CHASE_FREE 2
18+
#define INSET_IN_EYE 3
19+
#define INSET_MAP_FREE 4
20+
#define INSET_MAP_CHASE 5
2021

2122
#define MAX_SPEC_HUD_MESSAGES 8
2223

@@ -99,6 +100,7 @@ class CHudSpectator : public CHudBase
99100
cvar_t * m_drawnames;
100101
cvar_t * m_drawcone;
101102
cvar_t * m_drawstatus;
103+
cvar_t * m_HUD_saytext;
102104
cvar_t * m_autoDirector;
103105
float m_lastAutoDirector;
104106
cvar_t * m_pip;

cl_dll/saytext.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -55,7 +55,7 @@ int CHudSayText :: Init( void )
5555

5656
InitHUDData();
5757

58-
m_HUD_saytext = gEngfuncs.pfnRegisterVariable( "hud_saytext", "1", 0 );
58+
m_HUD_saytext = gEngfuncs.pfnRegisterVariable( "hud_saytext_internal", "1", 0 );
5959
m_HUD_saytext_time = gEngfuncs.pfnRegisterVariable( "hud_saytext_time", "5", 0 );
6060

6161
m_iFlags |= HUD_INTERMISSION; // is always drawn during an intermission

cl_dll/view.cpp

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1725,6 +1725,10 @@ void V_CalcSpectatorRefdef ( struct ref_params_s * pparams )
17251725
// override some settings in certain modes
17261726
switch ( (int)gHUD.m_Spectator.m_pip->value )
17271727
{
1728+
case INSET_CHASE_LOCKED:
1729+
V_GetChasePos( g_iUser2, NULL, v_origin, v_angles );
1730+
break;
1731+
17281732
case INSET_CHASE_FREE:
17291733
V_GetChasePos( g_iUser2, v_cl_angles, v_origin, v_angles );
17301734
break;

0 commit comments

Comments
 (0)