1 /*
2 ===========================================================================
3 Copyright (C) 1999-2005 Id Software, Inc.
4
5 This file is part of Quake III Arena source code.
6
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.
11
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.
16
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 ===========================================================================
21 */
22 //
23 //
24 // ui_rankings.c
25 //
26
27 #include "ui_local.h"
28
29
30 #define RANKINGS_FRAME "menu/art/cut_frame"
31
32 #define ID_LOGIN 100
33 #define ID_LOGOUT 101
34 #define ID_CREATE 102
35 #define ID_SPECTATE 103
36 #define ID_SETUP 104
37 #define ID_LEAVE 105
38
39
40 typedef struct
41 {
42 menuframework_s menu;
43 menubitmap_s frame;
44 menutext_s login;
45 menutext_s logout;
46 menutext_s create;
47 menutext_s spectate;
48 menutext_s setup;
49 menutext_s leave;
50 } rankings_t;
51
52 static rankings_t s_rankings;
53
54 static menuframework_s s_rankings_menu;
55 static menuaction_s s_rankings_login;
56 static menuaction_s s_rankings_logout;
57 static menuaction_s s_rankings_create;
58 static menuaction_s s_rankings_spectate;
59 static menuaction_s s_rankings_setup;
60 static menuaction_s s_rankings_leave;
61
62
63 /*
64 ===============
65 Rankings_DrawText
66 ===============
67 */
Rankings_DrawText(void * self)68 void Rankings_DrawText( void* self )
69 {
70 menufield_s *f;
71 qboolean focus;
72 int style;
73 char *txt;
74 char c;
75 float *color;
76 int basex, x, y;
77
78 f = (menufield_s*)self;
79 basex = f->generic.x;
80 y = f->generic.y + 4;
81 focus = (f->generic.parent->cursor == f->generic.menuPosition);
82
83 style = UI_LEFT|UI_SMALLFONT;
84 color = text_color_normal;
85 if( focus ) {
86 style |= UI_PULSE;
87 color = text_color_highlight;
88 }
89
90 // draw the actual text
91 txt = f->field.buffer;
92 color = g_color_table[ColorIndex(COLOR_WHITE)];
93 x = basex;
94 while ( (c = *txt) != 0 ) {
95 UI_DrawChar( x, y, c, style, color );
96 txt++;
97 x += SMALLCHAR_WIDTH;
98 }
99
100 // draw cursor if we have focus
101 if( focus ) {
102 if ( trap_Key_GetOverstrikeMode() ) {
103 c = 11;
104 } else {
105 c = 10;
106 }
107
108 style &= ~UI_PULSE;
109 style |= UI_BLINK;
110
111 UI_DrawChar( basex + f->field.cursor * SMALLCHAR_WIDTH, y, c, style, color_white );
112 }
113 }
114
115 /*
116 ===============
117 Rankings_DrawName
118 ===============
119 */
Rankings_DrawName(void * self)120 void Rankings_DrawName( void* self )
121 {
122 menufield_s *f;
123 int length;
124 char* p;
125
126 f = (menufield_s*)self;
127
128 // GRANK_FIXME - enforce valid characters
129 for( p = f->field.buffer; *p != '\0'; p++ )
130 {
131 //if( ispunct(*p) || isspace(*p) )
132 if( !( ( (*p) >= '0' && (*p) <= '9') || Q_isalpha(*p)) )
133 {
134 *p = '\0';
135 }
136 }
137
138 // strip color codes
139 Q_CleanStr( f->field.buffer );
140 length = strlen( f->field.buffer );
141 if( f->field.cursor > length )
142 {
143 f->field.cursor = length;
144 }
145
146 Rankings_DrawText( f );
147 }
148
149 #if 0 // old version
150 /*
151 ===============
152 Rankings_DrawName
153 ===============
154 */
155 void Rankings_DrawName( void* self )
156 {
157 menufield_s* f;
158 int length;
159
160 f = (menufield_s*)self;
161
162 // strip color codes
163 Q_CleanStr( f->field.buffer );
164 length = strlen( f->field.buffer );
165 if( f->field.cursor > length )
166 {
167 f->field.cursor = length;
168 }
169
170 // show beginning of long names
171 /*
172 if( Menu_ItemAtCursor( f->generic.parent ) != f )
173 {
174 if( f->field.scroll > 0 )
175 {
176 f->field.cursor = 0;
177 f->field.scroll = 0;
178 }
179 }
180 */
181
182 MenuField_Draw( f );
183 }
184 #endif
185
186 /*
187 ===============
188 Rankings_DrawPassword
189 ===============
190 */
Rankings_DrawPassword(void * self)191 void Rankings_DrawPassword( void* self )
192 {
193 menufield_s* f;
194 char password[MAX_EDIT_LINE];
195 int length;
196 int i;
197 char* p;
198
199 f = (menufield_s*)self;
200
201 // GRANK_FIXME - enforce valid characters
202 for( p = f->field.buffer; *p != '\0'; p++ )
203 {
204 //if( ispunct(*p) || isspace(*p) )
205 if( !( ( (*p) >= '0' && (*p) <= '9') || Q_isalpha(*p)) )
206 {
207 *p = '\0';
208 }
209 }
210
211 length = strlen( f->field.buffer );
212 if( f->field.cursor > length )
213 {
214 f->field.cursor = length;
215 }
216
217 // save password
218 Q_strncpyz( password, f->field.buffer, sizeof(password) );
219
220 // mask password with *
221 for( i = 0; i < length; i++ )
222 {
223 f->field.buffer[i] = '*';
224 }
225
226 // draw masked password
227 Rankings_DrawText( f );
228 //MenuField_Draw( f );
229
230 // restore password
231 Q_strncpyz( f->field.buffer, password, sizeof(f->field.buffer) );
232 }
233
234 /*
235 ===============
236 Rankings_MenuEvent
237 ===============
238 */
Rankings_MenuEvent(void * ptr,int event)239 static void Rankings_MenuEvent( void* ptr, int event ) {
240 if( event != QM_ACTIVATED ) {
241 return;
242 }
243
244 switch( ((menucommon_s*)ptr)->id ) {
245 case ID_LOGIN:
246 UI_LoginMenu();
247 break;
248
249 case ID_LOGOUT:
250 // server side masqueraded player logout first
251 trap_CL_UI_RankUserRequestLogout();
252 UI_ForceMenuOff();
253 break;
254
255 case ID_CREATE:
256 UI_SignupMenu();
257 break;
258
259 case ID_SPECTATE:
260 trap_Cmd_ExecuteText( EXEC_APPEND, "cmd rank_spectate\n" );
261 UI_ForceMenuOff();
262 break;
263
264 case ID_SETUP:
265 UI_SetupMenu();
266 break;
267
268 case ID_LEAVE:
269 trap_Cmd_ExecuteText( EXEC_APPEND, "disconnect\n" );
270 UI_ForceMenuOff();
271 break;
272
273 }
274 }
275
276
277 /*
278 ===============
279 Rankings_MenuInit
280 ===============
281 */
Rankings_MenuInit(void)282 void Rankings_MenuInit( void ) {
283 grank_status_t status;
284 int y;
285
286 memset( &s_rankings, 0, sizeof(s_rankings) );
287
288 Rankings_Cache();
289
290 s_rankings.menu.wrapAround = qtrue;
291 s_rankings.menu.fullscreen = qfalse;
292
293 s_rankings.frame.generic.type = MTYPE_BITMAP;
294 s_rankings.frame.generic.flags = QMF_INACTIVE;
295 s_rankings.frame.generic.name = RANKINGS_FRAME;
296 s_rankings.frame.generic.x = 142;
297 s_rankings.frame.generic.y = 118;
298 s_rankings.frame.width = 359;
299 s_rankings.frame.height = 256;
300
301 y = 194;
302
303 s_rankings.login.generic.type = MTYPE_PTEXT;
304 s_rankings.login.generic.flags = QMF_CENTER_JUSTIFY|QMF_PULSEIFFOCUS;
305 s_rankings.login.generic.id = ID_LOGIN;
306 s_rankings.login.generic.callback = Rankings_MenuEvent;
307 s_rankings.login.generic.x = 320;
308 s_rankings.login.generic.y = y;
309 s_rankings.login.string = "LOGIN";
310 s_rankings.login.style = UI_CENTER|UI_SMALLFONT;
311 s_rankings.login.color = colorRed;
312 y += 20;
313
314 s_rankings.logout.generic.type = MTYPE_PTEXT;
315 s_rankings.logout.generic.flags = QMF_HIDDEN|QMF_INACTIVE|QMF_CENTER_JUSTIFY|QMF_PULSEIFFOCUS;
316 s_rankings.logout.generic.id = ID_LOGOUT;
317 s_rankings.logout.generic.callback = Rankings_MenuEvent;
318 s_rankings.logout.generic.x = 320;
319 s_rankings.logout.generic.y = y;
320 s_rankings.logout.string = "LOGOUT";
321 s_rankings.logout.style = UI_CENTER|UI_SMALLFONT;
322 s_rankings.logout.color = colorRed;
323
324 s_rankings.create.generic.type = MTYPE_PTEXT;
325 s_rankings.create.generic.flags = QMF_CENTER_JUSTIFY|QMF_PULSEIFFOCUS;
326 s_rankings.create.generic.id = ID_CREATE;
327 s_rankings.create.generic.callback = Rankings_MenuEvent;
328 s_rankings.create.generic.x = 320;
329 s_rankings.create.generic.y = y;
330 s_rankings.create.string = "SIGN UP";
331 s_rankings.create.style = UI_CENTER|UI_SMALLFONT;
332 s_rankings.create.color = colorRed;
333 y += 20;
334
335 s_rankings.spectate.generic.type = MTYPE_PTEXT;
336 s_rankings.spectate.generic.flags = QMF_CENTER_JUSTIFY|QMF_PULSEIFFOCUS;
337 s_rankings.spectate.generic.id = ID_SPECTATE;
338 s_rankings.spectate.generic.callback = Rankings_MenuEvent;
339 s_rankings.spectate.generic.x = 320;
340 s_rankings.spectate.generic.y = y;
341 s_rankings.spectate.string = "SPECTATE";
342 s_rankings.spectate.style = UI_CENTER|UI_SMALLFONT;
343 s_rankings.spectate.color = colorRed;
344 y += 20;
345
346 s_rankings.setup.generic.type = MTYPE_PTEXT;
347 s_rankings.setup.generic.flags = QMF_CENTER_JUSTIFY|QMF_PULSEIFFOCUS;
348 s_rankings.setup.generic.id = ID_SETUP;
349 s_rankings.setup.generic.callback = Rankings_MenuEvent;
350 s_rankings.setup.generic.x = 320;
351 s_rankings.setup.generic.y = y;
352 s_rankings.setup.string = "SETUP";
353 s_rankings.setup.style = UI_CENTER|UI_SMALLFONT;
354 s_rankings.setup.color = colorRed;
355 y += 20;
356
357 s_rankings.leave.generic.type = MTYPE_PTEXT;
358 s_rankings.leave.generic.flags = QMF_CENTER_JUSTIFY|QMF_PULSEIFFOCUS;
359 s_rankings.leave.generic.id = ID_LEAVE;
360 s_rankings.leave.generic.callback = Rankings_MenuEvent;
361 s_rankings.leave.generic.x = 320;
362 s_rankings.leave.generic.y = y;
363 s_rankings.leave.string = "LEAVE ARENA";
364 s_rankings.leave.style = UI_CENTER|UI_SMALLFONT;
365 s_rankings.leave.color = colorRed;
366 y += 20;
367
368 status = (grank_status_t)trap_Cvar_VariableValue("client_status");
369 if( (status != QGR_STATUS_NEW) && (status != QGR_STATUS_SPECTATOR) )
370 {
371 s_rankings.login.generic.flags |= QMF_HIDDEN | QMF_INACTIVE;
372 s_rankings.create.generic.flags |= QMF_HIDDEN | QMF_INACTIVE;
373 s_rankings.spectate.generic.flags |= QMF_HIDDEN | QMF_INACTIVE;
374
375 s_rankings.logout.generic.flags &= ~(QMF_HIDDEN | QMF_INACTIVE);
376 }
377
378 if ( (status == QGR_STATUS_VALIDATING) ||
379 (status == QGR_STATUS_PENDING) ||
380 (status == QGR_STATUS_LEAVING) )
381 {
382 s_rankings.login.generic.flags |= QMF_GRAYED;
383 s_rankings.create.generic.flags |= QMF_GRAYED;
384 s_rankings.logout.generic.flags |= QMF_GRAYED;
385 }
386
387 //GRank FIXME -- don't need setup option any more
388 s_rankings.setup.generic.flags |= QMF_HIDDEN | QMF_INACTIVE;
389
390 Menu_AddItem( &s_rankings.menu, (void*) &s_rankings.frame );
391 Menu_AddItem( &s_rankings.menu, (void*) &s_rankings.login );
392 Menu_AddItem( &s_rankings.menu, (void*) &s_rankings.logout );
393 Menu_AddItem( &s_rankings.menu, (void*) &s_rankings.create );
394 Menu_AddItem( &s_rankings.menu, (void*) &s_rankings.spectate );
395 Menu_AddItem( &s_rankings.menu, (void*) &s_rankings.setup );
396 Menu_AddItem( &s_rankings.menu, (void*) &s_rankings.leave );
397 }
398
399
400 /*
401 ===============
402 Rankings_Cache
403 ===============
404 */
Rankings_Cache(void)405 void Rankings_Cache( void ) {
406 trap_R_RegisterShaderNoMip( RANKINGS_FRAME );
407 }
408
409
410 /*
411 ===============
412 UI_RankingsMenu
413 ===============
414 */
UI_RankingsMenu(void)415 void UI_RankingsMenu( void ) {
416 Rankings_MenuInit();
417 UI_PushMenu ( &s_rankings.menu );
418 }
419
420
421