]> icculus.org git repositories - divverent/nexuiz.git/blob - data/qcsrc/client/sbar.qc
using the clientinfo entities for the ping times
[divverent/nexuiz.git] / data / qcsrc / client / sbar.qc
1
2 float sb_lines; // still don't know what to do with that NOTE: check dp's sbar.c to see what that should be
3
4 vector sbar;
5
6 entity sortedPlayers;
7 entity sortedTeams;
8
9 .float sb_frags;
10 .float sb_team;
11 .float sb_player;
12
13 void Sbar_FinaleOverlay()
14 {
15 }
16
17 void Sbar_DrawWeapon(float nr, float fade, float active)
18 {
19         vector pos, vsize, color;
20         float value;
21         
22         value = (active) ? 1 : 0.6;
23         color_x = color_y = color_z = value;
24         
25         if(sbar_hudselector == 1)
26         {
27                 // width = 300, height = 100
28                 const float w_width = 32, w_height = 12, w_space = 2, font_size = 8;
29                 
30                 pos_x = (vid_conwidth - w_width * 9) * 0.5 + w_width * nr;
31                 pos_y = (vid_conheight - w_height);
32                 pos_z = 0;
33                 vsize_x = w_width;
34                 vsize_y = w_height;
35                 vsize_z = 0;
36                 drawpic(pos, strcat("gfx/inv_weapon", ftos(nr)), vsize, color, value * fade * sbar_alpha_fg, 0);
37                 pos_x += w_space;
38                 pos_y += w_space;
39                 vsize_x = font_size;
40                 vsize_y = font_size;
41                 vsize_z = 0;
42                 drawstring(pos, ftos(nr+1), vsize, '1 1 0', sbar_alpha_fg, 0);
43
44         }
45         else
46         {
47                 // width = 300, height = 100
48                 const float w2_width = 300, w2_height = 100, w2_space = 10;
49                 const float w2_scale = 0.4;
50
51                 pos_x = vid_conwidth - (w2_width + w2_space) * w2_scale;
52                 pos_y = (w2_height + w2_space) * w2_scale * nr + w2_space;
53                 pos_z = 0;
54                 vsize_x = w2_width * w2_scale;
55                 vsize_y = w2_height * w2_scale;
56                 vsize_z = 0;
57                 
58                 drawpic(pos, strcat("gfx/inv_weapon", ftos(nr)), vsize, color, value * fade * sbar_alpha_fg, 0);
59         }
60 }
61 void Sbar_DrawXNum (vector pos, float num, float digits, float lettersize, vector rgb, float a, float dflags)
62 {
63         float l, i;
64         string str, tmp;
65         float minus;
66         vector vsize;
67
68         vsize_x = vsize_y = lettersize;
69         vsize_z = 0;
70
71         if(num < 0)
72         {
73                 minus = true;
74                 num = -num;
75                 pos_x -= lettersize;
76         } else
77                 minus = false;
78         
79         if(digits < 0)
80         {
81                 tmp = ftos(num);
82                 digits = -digits;
83                 str = strcat(substring("0000000000", 0, digits - strlen(tmp)), tmp);
84         } else
85                 str = ftos(num);
86         
87         l = strlen(str);
88
89         if(l > digits)
90         {
91                 str = substring(str, l-digits, 999);
92                 l = strlen(str);
93         } else if(l < digits)
94                 pos_x += (digits-l) * lettersize;
95
96         if(minus)
97         {
98                 drawpic(sbar + pos, "gfx/num_minus", vsize, rgb, a * sbar_alpha_fg, dflags);
99                 pos_x += lettersize;
100         }
101
102         for(i = 0; i < l; ++i)
103         {
104                 drawpic(sbar + pos, strcat("gfx/num_", substring(str, i, 1)), vsize, rgb, a * sbar_alpha_fg, dflags);
105                 pos_x += lettersize;
106         }
107 }
108
109 float Sbar_PlayerCmp(entity l, entity r)
110 {
111         if(teamplay)
112         {
113                 if(l.sb_team < r.sb_team)
114                         return true;
115                 else if(l.sb_team > r.sb_team)
116                         return false;
117         }
118         if(l.sb_frags > r.sb_frags)
119                 return true;
120         else if(l.sb_frags < r.sb_frags)
121                 return false;
122         return (l.sb_player > r.sb_player);
123 }
124 float Sbar_TeamCmp(entity l, entity r)
125 {
126         if(l.sb_frags > r.sb_frags)
127                 return true;
128         else if(l.sb_frags < r.sb_frags)
129                 return false;
130         return (l.sb_player > r.sb_player);
131 }
132
133 void Sbar_SortFrags()
134 {
135         float i;
136         entity tmp;
137         entity t1, t2, t3, t4, ts;
138         
139         Sort_Remove(sortedPlayers);
140         sortedPlayers = Sort_New(Sbar_PlayerCmp);
141
142         numteams = 0;
143         if(teamplay)
144         {
145                 Sort_Remove(sortedTeams);
146         
147                 t1 = spawn();
148                 t2 = spawn();
149                 t3 = spawn();
150                 t4 = spawn();
151                 ts = spawn();
152         
153                 t1.sb_team = COLOR_TEAM1;
154                 t2.sb_team = COLOR_TEAM2;
155                 t3.sb_team = COLOR_TEAM3;
156                 t4.sb_team = COLOR_TEAM4;
157                 ts.sb_team = COLOR_SPECTATOR;
158
159                 t1.sb_player = t2.sb_player = t3.sb_player = t4.sb_player = ts.sb_player = 0;
160                 t1.sb_frags = t2.sb_frags = t3.sb_frags = t4.sb_frags = 0;
161                 sortedTeams = Sort_New(Sbar_TeamCmp);
162                 
163                 for(i = 0; i < maxclients; ++i)
164                 {
165                         if(strlen(getplayerkey(i, "name")) <= 0)
166                                 continue;
167                 
168                         tmp = spawn();
169                         tmp.sb_player = i;
170                         tmp.sb_frags = stof(getplayerkey(i, "frags"));
171                         if(tmp.sb_frags == -666)
172                                 tmp.sb_team = COLOR_SPECTATOR;
173                         else
174                                 tmp.sb_team = GetPlayerColor(i);
175
176                         switch(tmp.sb_team)
177                         {
178                         case COLOR_TEAM1: t1.sb_frags += tmp.sb_frags; t1.sb_player++; break;
179                         case COLOR_TEAM2: t2.sb_frags += tmp.sb_frags; t2.sb_player++; break;
180                         case COLOR_TEAM3: t3.sb_frags += tmp.sb_frags; t3.sb_player++; break;
181                         case COLOR_TEAM4: t4.sb_frags += tmp.sb_frags; t4.sb_player++; break;
182                         case COLOR_SPECTATOR: ts.sb_frags += tmp.sb_frags; ts.sb_player++; break;
183                         }
184
185                         if(i == player_localentnum-1)
186                                 myteam = tmp.sb_team;
187
188                         Sort_Add(sortedPlayers, tmp);
189                 }
190                 if(t1.sb_player) ++numteams;
191                 if(t2.sb_player) ++numteams;
192                 if(t3.sb_player) ++numteams;
193                 if(t4.sb_player) ++numteams;
194
195                 Sort_Add(sortedTeams, t1);
196                 Sort_Add(sortedTeams, t2);
197                 Sort_Add(sortedTeams, t3);
198                 Sort_Add(sortedTeams, t4);
199                 Sort_Add(sortedTeams, ts);
200
201         } else {
202                 for(i = 0; i < maxclients; ++i)
203                 {
204                         if(strlen(getplayerkey(i, "name")) <= 0)
205                                 continue;
206                 
207                         tmp = spawn();
208                         tmp.sb_player = i;
209                         tmp.sb_frags = stof(getplayerkey(i, "frags"));
210                         if(tmp.sb_frags == -666)
211                                 tmp.sb_team = COLOR_SPECTATOR;
212                         else
213                                 tmp.sb_team = COLOR_TEAM1;
214                         Sort_Add(sortedPlayers, tmp);
215                 }
216         }
217 }
218
219 void Sbar_PrintScoreboardItem(vector pos, entity pl, float is_self, float mask)
220 {
221         vector tmp;
222         string str;
223         
224         tmp_y = tmp_z = 0;
225         pos_x += 56;
226
227         str = bufstr_get(databuf, DATABUF_PING + pl.sb_player);
228         tmp_x = 4*8 - strlen(str) * 8 - 56;
229         drawstring(pos + tmp, str, '8 8 0', '0.8 0.8 0.8', 0.8, 0);
230
231         if(!(mask & 1))
232         {
233                 str = ftos(pl.sb_frags);
234                 tmp_x = 4*8 - strlen(str) * 8;
235                 drawstring(pos + tmp, str, '8 8 0', '1 1 1', 1, 0);
236         }
237
238         if(is_self)
239                 drawstring(pos + '40 0 0', "\x0D", '8 8 0', '1 1 1', 1, 0);
240         str = getplayerkey(pl.sb_player, "name");
241         tmp_x = 5*8 - strlen(str) * 8 + 56;
242         drawcolorcodedstring(pos + '48 0 0', str, '8 8 0', 1, 0);
243 }
244 void Sbar_PrintScoreboardTeamItem(vector pos, entity tm, vector rgb, string name)
245 {
246         vector tmp;
247         string str;
248         
249         tmp_y = tmp_z = 0;
250         pos_x += 56;
251
252         str = ftos(tm.sb_frags);
253         tmp_x = 4*8 - strlen(str) * 8;
254         drawstring(pos + tmp, str, '8 8 0', rgb, 1, 0);
255
256         drawstring(pos + '48 0 0', name, '8 8 0', rgb, 1, 0);
257 }
258
259 void Sbar_DrawScoreboard()
260 {
261         // Assume: frags are already sorted
262         float xmin, xmax, ymin, ymax;
263         vector pos, teammin, teammax, rgb;
264         entity pl, tm;
265         float specs;
266         specs = false;
267
268         xmin = vid_conwidth / 4;
269         xmax = vid_conwidth - xmin;
270         ymin = 64;
271         ymax = vid_conheight - 50;
272
273         pos_x = xmin;
274         pos_y = ymin;
275         pos_z = 0;
276
277         teammin = teammax = '0 0 0';
278         teammin_x = xmin - 2;
279         teammax_x = xmax - 2;
280         
281         drawstring(pos, "ping", '8 8 0', '1 1 1', 1, 0);
282         drawstring(pos + '48 0 0', "frags", '8 8 0', '1 1 1', 1, 0);
283         drawstring(pos + '104 0 0', "name", '8 8 0', '1 1 1', 1, 0);
284         pos += '0 16 0';
285         
286         if(teamplay)
287         {
288                 //for(t = 0; t < 4; ++t)
289                 for(tm = sortedTeams.sort_next; tm; tm = tm.sort_next)
290                 {
291                         if(!tm.sb_player || tm.sb_team == COLOR_SPECTATOR) // no players in it?
292                                 continue;
293
294                         teammin_y = pos_y - 2;
295                         teammax_y = pos_y + 2 + 10 * (tm.sb_player+1);
296                         rgb = GetTeamRGB(tm.sb_team);
297                         drawfill(teammin, teammax - teammin, rgb, 0.2, DRAWFLAG_NORMAL);
298                         Sbar_PrintScoreboardTeamItem(pos, tm, rgb, GetTeamName(tm.sb_team));
299                         pos += '0 12 0';
300                         //for(i = 0; i < maxclients; ++i)
301                         for(pl = sortedPlayers.sort_next; pl; pl = pl.sort_next)
302                         {
303                                 if(pl.sb_team != tm.sb_team)
304                                         continue;
305                                 Sbar_PrintScoreboardItem(pos, pl, (pl.sb_player == player_localentnum - 1), 0);
306                                 pos += '0 10 0';
307                         }
308                         
309                         pos += '0 12 0';
310                 }
311
312                 // rgb := tempvector :)
313                 rgb = pos + '0 12 0';
314                 //pos += '64 24 0';
315                 pos_y += 24;
316                 //for(i = 0; i < maxclients; ++i)
317                 for(pl = sortedPlayers.sort_next; pl; pl = pl.sort_next)
318                 {
319                         if(pl.sb_team != COLOR_SPECTATOR)
320                                 continue;
321                         //drawcolorcodedstring(pos, getplayerkey(pl.sb_player, "name"), '8 8 0', 1, 0);
322                         Sbar_PrintScoreboardItem(pos, pl, (pl.sb_player == player_localentnum - 1), 1);
323                         pos += '0 10 0';
324                         specs = true;
325                 }
326                         
327                 if(specs)
328                         drawstring(rgb, "Spectators", '8 8 0', '1 1 1', 1, 0);
329         } else {
330                 //for(i = 0; i < maxclients; ++i)
331                 for(pl = sortedPlayers.sort_next; pl; pl = pl.sort_next)
332                 {
333                         if(pl.sb_team != COLOR_TEAM1)
334                                 continue;
335                         //drawstring(pos, ftos(pl.sb_frags), '8 8 0', '1 1 1', 1, 0);
336                         //drawcolorcodedstring(pos + '64 0 0', getplayerkey(pl.sb_player, "name"), '8 8 0', 1, 0);
337                         Sbar_PrintScoreboardItem(pos, pl, (pl.sb_player == player_localentnum - 1), 0);
338                         pos += '0 12 0';
339                 }
340                 rgb = pos + '0 12 0';
341                 //pos += '64 24 0';
342                 pos_y += 24;
343                 for(pl = sortedPlayers.sort_next; pl; pl = pl.sort_next)
344                 {
345                         if(pl.sb_team != COLOR_SPECTATOR)
346                                 continue;
347                         specs = true;
348                         //drawcolorcodedstring(pos, getplayerkey(pl.sb_player, "name"), '8 8 0', 1, 0);
349                         Sbar_PrintScoreboardItem(pos, pl, (pl.sb_player == player_localentnum - 1), 1);
350                         pos += '0 12 0';
351                 }
352                 if(specs)
353                         drawstring(rgb, "Spectators", '8 8 0', '1 1 1', 1, 0);
354         }
355 }
356
357
358 void Sbar_Score(float margin)
359 {
360         float timelimit, timeleft, minutes, seconds, distribution, myplace;
361         vector sbar_save, place;
362         entity tm, pl, me;
363         sbar_save = sbar;
364
365         sbar_y = vid_conheight - (32+12);
366         sbar_x -= margin;
367         
368         place = '-48 -12 0';
369         if(teamplay)
370         {
371                 // Layout:
372                 //
373                 //   team1 team3 team4
374                 //
375                 //         TEAM2
376                 //for(i = 0; i < 4; ++i)
377                 for(tm = sortedTeams.sort_next; tm; tm = tm.sort_next)
378                 {
379                         if(tm.sb_team == COLOR_SPECTATOR || !tm.sb_player) // no players? don't display
380                                 continue;
381                         // -32*4 = -128
382                         if(tm.sb_team == myteam)
383                                 Sbar_DrawXNum('-128 0', tm.sb_frags, 4, 32, GetTeamRGB(tm.sb_team), 1, DRAWFLAG_NORMAL);
384                         else
385                         {
386                                 Sbar_DrawXNum(place, tm.sb_frags, 4, 12, GetTeamRGB(tm.sb_team), 1, DRAWFLAG_NORMAL);
387                                 place_x -= 4*12;
388                         }
389                 }
390         } else {
391                 // me vector := [team/connected frags id]
392                 myplace = 0;
393                 for(me = sortedPlayers.sort_next; me; me = me.sort_next)
394                 {
395                         if(me.sb_team != COLOR_SPECTATOR)
396                                 ++myplace;
397                         if(me.sb_player == player_localentnum - 1)
398                                 break;
399                 }
400                 pl = sortedPlayers.sort_next;
401                 if(pl == me)
402                         pl = pl.sort_next;
403                 
404                 if(pl && myplace != 1)
405                 {
406                         distribution = me.sb_frags - pl.sb_frags;
407                 } else if(pl) {
408                         distribution = me.sb_frags - pl.sb_frags;
409                 } else
410                         distribution = 0;
411                 
412                 if(myplace == 1)
413                         Sbar_DrawXNum('-36 -12', myplace, 3, 12, '1 1 1', 1, DRAWFLAG_NORMAL);
414                 else if(myplace == 2)
415                         Sbar_DrawXNum('-36 -12', myplace, 3, 12, '1 1 0', 1, DRAWFLAG_NORMAL);
416                 else
417                         Sbar_DrawXNum('-36 -12', myplace, 3, 12, '1 0 0', 1, DRAWFLAG_NORMAL);
418
419                 if(distribution >= 0)
420                 {
421                         Sbar_DrawXNum('-84 -12', distribution, 4, 12, ' 1 1 1', 1, DRAWFLAG_NORMAL);
422                         Sbar_DrawXNum('-128 0', me.sb_frags, 4, 32, '1 1 1', 1, DRAWFLAG_NORMAL);
423                 } else if(distribution >= -5)
424                 {
425                         Sbar_DrawXNum('-84 -12', distribution, 4, 12, ' 1 1 0', 1, DRAWFLAG_NORMAL);
426                         Sbar_DrawXNum('-128 0', me.sb_frags, 4, 32, '1 1 0', 1, DRAWFLAG_NORMAL);
427                 } else {
428                         Sbar_DrawXNum('-84 -12', distribution, 4, 12, ' 1 0 0', 1, DRAWFLAG_NORMAL);
429                         Sbar_DrawXNum('-128 0', me.sb_frags, 4, 32, '1 0 0', 1, DRAWFLAG_NORMAL);
430                 }
431         }
432         timelimit = getstatf(STAT_TIMELIMIT);
433         if(timelimit)
434         {
435                 timeleft = max(0, timelimit * 60 - time);
436                 minutes = floor(timeleft / 60);
437                 seconds = floor(timeleft - minutes*60);
438                 if(minutes >= 5)
439                 {
440                         Sbar_DrawXNum('-72 32', minutes, 3, 12, '1 1 1', 1, DRAWFLAG_NORMAL);
441                         drawpic(sbar + '-36 32', "gfx/num_colon", '12 12', '1 1 1', sbar_alpha_fg, 0);
442                         Sbar_DrawXNum('-24 32', seconds, -2, 12, '1 1 1', 1, DRAWFLAG_NORMAL);
443                 } else if(minutes >= 1)
444                 {
445                         Sbar_DrawXNum('-72 32', minutes, 3, 12, '1 1 0', 1, DRAWFLAG_NORMAL);
446                         drawpic(sbar + '-36 32', "gfx/num_colon", '12 12', '1 1 0', sbar_alpha_fg, 0);
447                         Sbar_DrawXNum('-24 32', seconds, -2, 12, '1 1 0', 1, DRAWFLAG_NORMAL);
448                 } else {
449                         Sbar_DrawXNum('-24 32', seconds, -2, 12, '1 0 0', 1, DRAWFLAG_NORMAL);
450                 }
451         } else {
452                 minutes = floor(time / 60);
453                 seconds = floor(time - minutes*60);
454                 Sbar_DrawXNum('-72 32', minutes, 3, 12, '1 1 1', 1, DRAWFLAG_NORMAL);
455                 drawpic(sbar + '-36 32', "gfx/num_colon", '12 12', '1 1 1', sbar_alpha_fg, 0);
456                 Sbar_DrawXNum('-24 32', seconds, -2, 12, '1 1 1', 1, DRAWFLAG_NORMAL);
457         }
458         sbar = sbar_save;
459 }
460
461 void Sbar_MiniscoreItem(vector pos, entity pl, float is_self)
462 {
463         float x;
464         pos_x += 72;
465         
466         if(teamplay)
467                 drawfill(pos + '0 1 0', '40 6 0', GetTeamRGB(pl.sb_team)*0.5, 1, DRAWFLAG_NORMAL);
468         else
469                 drawfill(pos + '0 1 0', '40 6 0', '0.5 0.5 0.5', 0.5, DRAWFLAG_NORMAL);
470         x = pos_x;
471         pos_x += 5*8;
472         pos_x -= strlen(ftos(pl.sb_frags))*8;
473         drawstring(pos, ftos(pl.sb_frags), '8 8 0', '1 1 1', 1, DRAWFLAG_NORMAL);
474         pos_x = x;
475         if(is_self)
476         {
477                 pos_x += 48;
478                 drawstring(pos, "\x0D", '8 8 0', '1 1 1', 1, DRAWFLAG_NORMAL);
479                 pos_x += 8;
480         } else
481                 pos_x += 56;
482         drawcolorcodedstring(pos, getplayerkey(pl.sb_player, "name"), '8 8 0', 1, 0);
483 }
484
485 void Sbar_MiniscoreTeamItem(vector pos, float color, float frags, float is_self)
486 {
487         float x;
488         pos_x += 72;
489         
490         if(teamplay)
491                 drawfill(pos + '0 1 0', '40 6 0', GetTeamRGB(color)*0.5, 1, DRAWFLAG_NORMAL);
492         else
493                 drawfill(pos + '0 1 0', '40 6 0', '0.5 0.5 0.5', 0.5, DRAWFLAG_NORMAL);
494         x = pos_x;
495         pos_x += 5*8;
496         pos_x -= strlen(ftos(frags))*8;
497         drawstring(pos, ftos(frags), '8 8 0', '1 1 1', 1, DRAWFLAG_NORMAL);
498         pos_x = x;
499         if(is_self)
500         {
501                 pos_x += 48;
502                 drawstring(pos, "\x0D", '8 8 0', '1 1 1', 1, DRAWFLAG_NORMAL);
503                 pos_x += 8;
504         } else
505                 pos_x += 56;
506         drawstring(pos, GetTeamName(color), '8 8 0', '1 1 1', 1, DRAWFLAG_NORMAL);
507 }
508
509 void Sbar_MiniDeathmatchOverlay(vector pos)
510 {
511         float i, numlines, up, down;
512         entity me, tm, pl;
513         float miniscoreboard_size;
514         miniscoreboard_size = cvar("sbar_miniscoreboard_size");
515         
516         if(miniscoreboard_size == 0)
517                 return;
518         pos_y = vid_conheight - 8;
519         
520         if(miniscoreboard_size < 0)
521                 numlines = (vid_conheight - sbar_y + 7) / 8;
522         else
523                 numlines = miniscoreboard_size;
524
525         // give up if there isn't enough room
526         if(pos_x >= vid_conwidth || pos_y >= vid_conheight || numlines < 1)
527                 return;
528
529         // me vector := [team/connected frags id]
530         for(me = sortedPlayers.sort_next; me; me = me.sort_next)
531         {
532                 if(me.sb_player == player_localentnum - 1)
533                         break;
534         }
535
536         if(teamplay)
537                 numlines -= numteams;
538
539         // figure out how many players above and below we can show
540         up = floor(numlines/2);
541         down = up;
542         if((up + down) > numlines)
543                 down = numlines - up;
544
545         // render bottom-up
546         for(pl = me.sort_next; pl && down > 0; pl = pl.sort_next)
547         {
548                 if(pl.sb_team == COLOR_SPECTATOR)
549                         continue;
550                 Sbar_MiniscoreItem(pos, pl, false);
551                 pos_y -= 9;
552                 --down;
553         }
554         Sbar_MiniscoreItem(pos, me, true);
555         pos_y -= 9;
556         up += down; // if there weren't enough lines below... add them
557         for(pl = me.sort_prev; pl != sortedPlayers && up > 0; pl = pl.sort_prev)
558         {
559                 if(pl.sb_team == COLOR_SPECTATOR)
560                         continue;
561                 Sbar_MiniscoreItem(pos, pl, false);
562                 pos_y -= 9;
563                 --up;
564         }
565
566         if(teamplay)
567         {
568                 for(tm = sortedTeams.sort_next; tm.sort_next; tm = tm.sort_next);
569                 for(; tm != sortedTeams; tm = tm.sort_prev)
570                 {
571                         if(!tm.sb_player || tm.sb_team == COLOR_SPECTATOR) // no players?
572                                 continue;
573                         Sbar_MiniscoreTeamItem(pos, tm.sb_team, tm.sb_frags, (tm.sb_team == me.sb_team));
574                         pos_y -= 9;
575                 }
576         }
577 }
578
579 void Sbar_Draw (void)
580 {
581         float i;
582         float x, fade;
583         float stat_items;
584
585         Sbar_SortFrags();
586
587         sb_lines = 24;
588         
589         if (sb_showscores)
590                 Sbar_DrawScoreboard();
591         else if (intermission == 1)
592         {
593                 Sbar_DrawScoreboard();
594                 return;
595         }
596         else if (intermission == 2)
597                 Sbar_FinaleOverlay();
598         else
599         {
600                 if (sb_showscores || (getstati(STAT_HEALTH) <= 0 && cvar("cl_deathscoreboard")))
601                 {
602                         sbar_x = (vid_conwidth - 640.0)*0.5;
603                         sbar_y = vid_conheight - 47;
604                         //Sbar_DrawAlphaPic (sbar_x, sbar_y, sb_scorebar, sbar_alpha_bg.value);
605                         //drawpic('0 0', "gfx/scorebar", '0 0 0', '1 1 1', cvar("sbar_alpha_bg"), 0);
606                         Sbar_DrawScoreboard ();
607                 }
608                 else
609                 {
610                         if (sb_lines && sbar_hudselector == 1)
611                         {
612                                 stat_items = getstati(STAT_ITEMS);
613
614                                 sbar_x = (vid_conwidth - 320.0)*0.5;
615                                 sbar_y = vid_conheight - 24.0 - 16.0;
616                                 sbar_z = 0;
617                         
618                                 fade = 3.2 - 2 * (time - weapontime);
619                                 fade = bound(0.7, fade, 1);
620
621                                 x = 1.0;
622                                 for(i = 0; i < 8; ++i)
623                                 {
624                                         if(stat_items & x)
625                                         {
626                                                 Sbar_DrawWeapon(i+1, fade, (i + 2 == activeweapon));
627                                         }
628                                         x *= 2;
629                                 }
630                                 x *= 2*2*2*2;
631                                 if(stat_items & x)
632                                 {
633                                         Sbar_DrawWeapon(0, fade, (activeweapon == 1));
634                                 }
635
636                                 // armor
637                                 x = getstati(STAT_ARMOR);
638                                 if (x > 0)
639                                 {
640                                         // "gfx/sb_armor"
641                                         //Sbar_DrawStretchPic (72, 0, sb_armor[0], sbar_alpha_fg.value, 24, 24);
642                                         drawpic(sbar + '72 0', "gfx/sb_armor", '24 24 0', '1 1 1', sbar_alpha_fg, 0);
643                                         if(x > 200)
644                                                 Sbar_DrawXNum('0 0', x, 3, 24, '0 1 0', 1, 0);
645                                         else if(x > 100)
646                                                 Sbar_DrawXNum('0 0', x, 3, 24, '0.2 1 0', 1, 0);
647                                         else if(x > 50)
648                                                 Sbar_DrawXNum('0 0', x, 3, 24, '0.6 0.7 0.8', 1, 0);
649                                         else if(x > 25)
650                                                 Sbar_DrawXNum('0 0', x, 3, 24, '1 1 0.2', 1, 0);
651                                         else
652                                                 Sbar_DrawXNum('0 0', x, 3, 24, '0.7 0 0', 1, 0);
653                                 }
654
655                                 // health
656                                 x = getstati(STAT_HEALTH);
657                                 if (x != 0)
658                                 {
659                                         // "gfx/sb_health"
660                                         //Sbar_DrawStretchPic (184, 0, sb_health, sbar_alpha_fg.value, 24, 24);
661                                         drawpic(sbar + '184 0', "gfx/sb_health", '24 24 0', '1 1 1', sbar_alpha_fg, 0);
662                                         if(x > 200)
663                                                 Sbar_DrawXNum('112 0', x, 3, 24, '0 1 0', 1, 0);
664                                         else if(x > 100)
665                                                 Sbar_DrawXNum('112 0', x, 3, 24, '0.2 1 0', 1, 0);
666                                         else if(x > 50)
667                                                 Sbar_DrawXNum('112 0', x, 3, 24, '0.6 0.7 0.8', 1, 0);
668                                         else if(x > 25)
669                                                 Sbar_DrawXNum('112 0', x, 3, 24, '1 1 0.2', 1, 0);
670                                         else
671                                                 Sbar_DrawXNum('112 0', x, 3, 24, '0.7 0 0', 1, 0);
672                                 }
673
674                                 // ammo
675                                 x = getstati(STAT_AMMO);
676                                 if ((stat_items & (NEX_IT_SHELLS | NEX_IT_BULLETS | NEX_IT_ROCKETS | NEX_IT_CELLS)) || x != 0)
677                                 {
678                                         if (stat_items & NEX_IT_SHELLS)
679                                                 drawpic(sbar + '296 0', "gfx/sb_shells", '24 24 0', '1 1 1', sbar_alpha_fg, 0);
680                                         else if (stat_items & NEX_IT_BULLETS)
681                                                 drawpic(sbar + '296 0', "gfx/sb_bullets", '24 24 0', '1 1 1', sbar_alpha_fg, 0);
682                                         else if (stat_items & NEX_IT_ROCKETS)
683                                                 drawpic(sbar + '296 0', "gfx/sb_rocket", '24 24 0', '1 1 1', sbar_alpha_fg, 0);
684                                         else if (stat_items & NEX_IT_CELLS)
685                                                 drawpic(sbar + '296 0', "gfx/sb_cells", '24 24 0', '1 1 1', sbar_alpha_fg, 0);
686                                         if(x > 10)
687                                                 Sbar_DrawXNum('224 0', x, 3, 24, '0.6 0.7 0.8', 1, 0);
688                                         else
689                                                 Sbar_DrawXNum('224 0', x, 3, 24, '0.7 0 0', 1, 0);
690                                 }
691
692                                 if (sbar_x + 320 + 160 <= vid_conwidth)
693                                         Sbar_MiniDeathmatchOverlay(sbar + '320 0');
694                                 if (sbar_x > 0)
695                                         Sbar_Score(16);
696                                 // The margin can be at most 8 to support 640x480 console size:
697                                 //   320 + 2 * (144 + 16) = 640
698                         }
699                         else if (sb_lines)
700                         {
701                         
702                                 stat_items = getstati(STAT_ITEMS);
703                         
704                                 sbar_x = (vid_conwidth - 640.0)*0.5;
705                                 sbar_y = vid_conheight - 47;
706                                 sbar_z = 0;
707
708                                 fade = 3 - 2 * (time - weapontime);
709
710                                 x = 1.0;
711                                 for(i = 0; i < 8; ++i)
712                                 {
713                                         if(stat_items & x)
714                                         {
715                                                 Sbar_DrawWeapon(i+1, fade, (i + 2 == activeweapon));
716                                         }
717                                         x *= 2;
718                                 }
719                                 x *= 2*2*2*2;
720                                 if(stat_items & x)
721                                 {
722                                         Sbar_DrawWeapon(0, fade, (activeweapon == 1));
723                                 }
724
725                                 if (sb_lines > 24)
726                                         drawpic(sbar, "gfx/sbar", '0 0 0', '1 1 1', sbar_alpha_fg, 0);
727                                 else
728                                         drawpic(sbar, "gfx/sbar_minimal", '0 0 0', '1 1 1', sbar_alpha_fg, 0);
729
730                                 // armor
731                                 // (340-3*24) = 268
732                                 Sbar_DrawXNum('268 12', getstati(STAT_ARMOR), 3, 24, '0.6 0.7 0.8', 1, 0);
733
734                                 // health
735                                 // (154-3*24) = 82
736                                 x = getstati(STAT_HEALTH);
737                                 if(x > 100)
738                                         Sbar_DrawXNum('82 12', x, 3, 24, '1 1 1', 1, 0);
739                                 else if(x <= 25 && time - floor(time) > 0.5)
740                                         Sbar_DrawXNum('82 12', x, 3, 24, '0.7 0 0', 1, 0);
741                                 else
742                                         Sbar_DrawXNum('81 12', x, 3, 24, '0.6 0.7 0.8', 1, 0);
743
744                                 // AK dont draw ammo for the laser
745                                 x = getstati(STAT_AMMO);
746                                 if(activeweapon != 12)
747                                 {
748                                         // (519-3*24) = 447
749                                         if (stat_items & NEX_IT_SHELLS)
750                                                 drawpic(sbar + '519 0', "gfx/sb_shells", '0 0 0', '1 1 1', sbar_alpha_fg, 0);
751                                         else if (stat_items & NEX_IT_BULLETS)
752                                                 drawpic(sbar + '519 0', "gfx/sb_bullets", '0 0 0', '1 1 1', sbar_alpha_fg, 0);
753                                         else if (stat_items & NEX_IT_ROCKETS)
754                                                 drawpic(sbar + '519 0', "gfx/sb_rocket", '0 0 0', '1 1 1', sbar_alpha_fg, 0);
755                                         else if (stat_items & NEX_IT_CELLS)
756                                                 drawpic(sbar + '519 0', "gfx/sb_cells", '0 0 0', '1 1 1', sbar_alpha_fg, 0);
757                                         if(x > 10)
758                                                 Sbar_DrawXNum('447 12', x, 3, 24, '0.6 0.7 0.8', 1, 0);
759                                         else
760                                                 Sbar_DrawXNum('447 12', x, 3, 24, '0.7 0 0', 1, 0);
761                                 }
762
763                                 if (sb_lines > 24)
764                                         drawpic(sbar, "gfx/sbar_overlay", '0 0 0', '1 1 1', 1, DRAWFLAG_MODULATE);
765
766                                 if (sbar_x + 600 + 160 <= vid_conwidth)
767                                         Sbar_MiniDeathmatchOverlay (sbar + '600 0');
768
769                                 if (sbar_x > 0)
770                                         Sbar_Score(-16);
771                                 // Because:
772                                 //   Mini scoreboard uses 12*4 per other team, that is, 144
773                                 //   pixels when there are four teams...
774                                 //   Nexuiz by default sets vid_conwidth to 800... makes
775                                 //   sbar_x == 80...
776                                 //   so we need to shift it by 64 pixels to the right to fit
777                                 //   BUT: then it overlaps with the image that gets drawn
778                                 //   for viewsize 100! Therefore, just account for 3 teams,
779                                 //   that is, 96 pixels mini scoreboard size, needing 16 pixels
780                                 //   to the right!
781                         }
782                 
783                 
784                         if(gametype == GAME_KEYHUNT)
785                         {
786                                 CSQC_kh_hud();
787                         } else if(gametype == GAME_CTF)
788                         {
789                                 CSQC_ctf_hud();
790                         }
791                 }
792         }
793 }
794
795 void CSQC_ctf_hud(void)
796 {
797         // cvar("sbar_flagstatus_right") move the flag icons right
798         // cvar("sbar_flagstatus_pos") pixel position of the nexuiz flagstatus icons
799         float redflag, blueflag;
800         float stat_items;
801         vector pos;
802         
803         stat_items = getstati(STAT_ITEMS);
804         redflag = (stat_items/32768) & 3;
805         blueflag = (stat_items/131072) & 3;
806
807         pos_x = (cvar("sbar_flagstatus_right")) ? vid_conwidth - 10 - sbar_x - 64 : 10 - sbar_x;
808         pos_z = 0;
809
810         if(sbar_hudselector == 1)
811                 pos_y = (vid_conheight - sbar_y) - cvar("sbar_flagstatus_pos") - 64;
812         else
813                 pos_y = -117;
814
815         pos += sbar;
816
817         switch(redflag)
818         {
819         case 1: drawpic(pos, "gfx/sb_flag_red_taken", '0 0 0', '1 1 1', 1, DRAWFLAG_NORMAL); break;
820         case 2: drawpic(pos, "gfx/sb_flag_red_lost", '0 0 0', '1 1 1', 1, DRAWFLAG_NORMAL); break;
821         case 3: drawpic(pos, "gfx/sb_flag_red_carrying", '0 0 0', '1 1 1', 1, DRAWFLAG_NORMAL); break;
822         }
823
824         pos_y -= 64;
825         
826         switch(blueflag)
827         {
828         case 1: drawpic(pos, "gfx/sb_flag_blue_taken", '0 0 0', '1 1 1', 1, 0); break;
829         case 2: drawpic(pos, "gfx/sb_flag_blue_lost", '0 0 0', '1 1 1', 1, 0); break;
830         case 3: drawpic(pos, "gfx/sb_flag_blue_carrying", '0 0 0', '1 1 1', 1, 0); break;
831         }
832 }