aboutsummaryrefslogtreecommitdiffstats
path: root/src/jake2/client/SCR.java
diff options
context:
space:
mode:
Diffstat (limited to 'src/jake2/client/SCR.java')
-rw-r--r--src/jake2/client/SCR.java3946
1 files changed, 1965 insertions, 1981 deletions
diff --git a/src/jake2/client/SCR.java b/src/jake2/client/SCR.java
index f92adcc..9ff5021 100644
--- a/src/jake2/client/SCR.java
+++ b/src/jake2/client/SCR.java
@@ -2,27 +2,27 @@
* SCR.java
* Copyright (C) 2003
*
- * $Id: SCR.java,v 1.7 2004-08-27 21:07:01 hzi Exp $
+ * $Id: SCR.java,v 1.8 2004-09-22 19:22:08 salomo Exp $
*/
/*
-Copyright (C) 1997-2001 Id Software, Inc.
+ Copyright (C) 1997-2001 Id Software, Inc.
-This program is free software; you can redistribute it and/or
-modify it under the terms of the GNU General Public License
-as published by the Free Software Foundation; either version 2
-of the License, or (at your option) any later version.
+ This program is free software; you can redistribute it and/or
+ modify it under the terms of the GNU General Public License
+ as published by the Free Software Foundation; either version 2
+ of the License, or (at your option) any later version.
-This program is distributed in the hope that it will be useful,
-but WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
-See the GNU General Public License for more details.
+ See the GNU General Public License for more details.
-You should have received a copy of the GNU General Public License
-along with this program; if not, write to the Free Software
-Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
+ You should have received a copy of the GNU General Public License
+ along with this program; if not, write to the Free Software
+ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
-*/
+ */
package jake2.client;
@@ -32,6 +32,7 @@ import jake2.game.cvar_t;
import jake2.qcommon.*;
import jake2.sound.*;
import jake2.sys.Sys;
+import jake2.util.Lib;
import jake2.util.Vargs;
import java.awt.Dimension;
@@ -41,1971 +42,1954 @@ import java.awt.Dimension;
*/
public final class SCR extends Globals {
- // cl_scrn.c -- master for refresh, status bar, console, chat, notify, etc
-
- static String[][] sb_nums=
- { { "num_0", "num_1", "num_2", "num_3", "num_4", "num_5", "num_6", "num_7", "num_8", "num_9", "num_minus" }, {
- "anum_0", "anum_1", "anum_2", "anum_3", "anum_4", "anum_5", "anum_6", "anum_7", "anum_8", "anum_9", "anum_minus" }
- };
-
- /*
- full screen console
- put up loading plaque
- blanked background with loading plaque
- blanked background with menu
- cinematics
- full screen image for quit and victory
-
- end of unit intermissions
- */
-
- static float scr_con_current; // aproaches scr_conlines at scr_conspeed
- static float scr_conlines; // 0.0 to 1.0 lines of console to display
-
- static boolean scr_initialized; // ready to draw
-
- static int scr_draw_loading;
-
- // scr_vrect ist in Globals definiert
- // position of render window on screen
-
- static cvar_t scr_viewsize;
- static cvar_t scr_conspeed;
- static cvar_t scr_centertime;
- static cvar_t scr_showturtle;
- static cvar_t scr_showpause;
- static cvar_t scr_printspeed;
-
- static cvar_t scr_netgraph;
- static cvar_t scr_timegraph;
- static cvar_t scr_debuggraph;
- static cvar_t scr_graphheight;
- static cvar_t scr_graphscale;
- static cvar_t scr_graphshift;
- static cvar_t scr_drawall;
- public static cvar_t fps;
-
- static dirty_t scr_dirty= new dirty_t();
- static dirty_t[] scr_old_dirty= { new dirty_t(), new dirty_t()};
-
- static String crosshair_pic;
- static int crosshair_width, crosshair_height;
-
- static class dirty_t {
- int x1;
- int x2;
- int y1;
- int y2;
-
- void set(dirty_t src) {
- x1= src.x1;
- x2= src.x2;
- y1= src.y1;
- y2= src.y2;
- }
-
- void clear() {
- x1= x2= y1= y2= 0;
- }
- }
-
- /*
- ===============================================================================
-
- BAR GRAPHS
-
- ===============================================================================
- */
-
- // typedef struct
- // {
- // float value;
- // int color;
- // } graphsamp_t;
- static class graphsamp_t {
- float value;
- int color;
- }
- static int current;
- static graphsamp_t[] values= new graphsamp_t[1024];
-
- static {
- for (int n= 0; n < 1024; n++)
- values[n]= new graphsamp_t();
- }
-
- /*
- ==============
- SCR_DebugGraph
- ==============
- */
- public static void DebugGraph(float value, int color) {
- values[current & 1023].value= value;
- values[current & 1023].color= color;
- current++;
- }
-
- /*
- ==============
- SCR_DrawDebugGraph
- ==============
- */
- static void DrawDebugGraph() {
- int a, x, y, w, i, h;
- float v;
- int color;
-
- // draw the graph
-
- w= scr_vrect.width;
-
- x= scr_vrect.x;
- y= scr_vrect.y + scr_vrect.height;
- re.DrawFill(x, (int) (y - scr_graphheight.value), w, (int) scr_graphheight.value, 8);
-
- for (a= 0; a < w; a++) {
- i= (current - 1 - a + 1024) & 1023;
- v= values[i].value;
- color= values[i].color;
- v= v * scr_graphscale.value + scr_graphshift.value;
-
- if (v < 0)
- v += scr_graphheight.value * (1 + (int) (-v / scr_graphheight.value));
- h= (int) v % (int) scr_graphheight.value;
- re.DrawFill(x + w - 1 - a, y - h, 1, h, color);
- }
- }
-
- /*
- ===============================================================================
-
- CENTER PRINTING
-
- ===============================================================================
- */
-
- // char scr_centerstring[1024];
- static String scr_centerstring;
- static float scr_centertime_start; // for slow victory printing
- static float scr_centertime_off;
- static int scr_center_lines;
- static int scr_erase_center;
-
- /*
- ==============
- SCR_CenterPrint
-
- Called for important messages that should stay in the center of the screen
- for a few moments
- ==============
- */
- static void CenterPrint(String str) {
- //char *s;
- int s;
- StringBuffer line= new StringBuffer(64);
- int i, j, l;
-
- //strncpy (scr_centerstring, str, sizeof(scr_centerstring)-1);
- scr_centerstring= str;
- scr_centertime_off= scr_centertime.value;
- scr_centertime_start= cl.time;
-
- // count the number of lines for centering
- scr_center_lines= 1;
- s= 0;
- while (s < str.length()) {
- if (str.charAt(s) == '\n')
- scr_center_lines++;
- s++;
- }
-
- // echo it to the console
- Com.Printf(
- "\n\n\35\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\37\n\n");
-
- s= 0;
-
- if (str.length() != 0) {
- do {
- // scan the width of the line
-
- for (l= 0; l < 40 && (l + s) < str.length(); l++)
- if (str.charAt(s + l) == '\n' || str.charAt(s + l) == 0)
- break;
- for (i= 0; i < (40 - l) / 2; i++)
- line.append(' ');
-
- for (j= 0; j < l; j++) {
- line.append(str.charAt(s + j));
- }
-
- line.append('\n');
-
- Com.Printf(line.toString());
-
- while (s < str.length() && str.charAt(s) != '\n')
- s++;
-
- if (s == str.length())
- break;
- s++; // skip the \n
- }
- while (true);
- }
- Com.Printf(
- "\n\n\35\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\37\n\n");
- Console.ClearNotify();
- }
-
- static void DrawCenterString() {
- String cs= scr_centerstring + "\0";
- int start;
- int l;
- int j;
- int x, y;
- int remaining;
-
- if (cs == null)
- return;
- if (cs.length() == 0)
- return;
-
- // the finale prints the characters one at a time
- remaining= 9999;
-
- scr_erase_center= 0;
- start= 0;
-
- if (scr_center_lines <= 4)
- y= (int) (viddef.height * 0.35);
- else
- y= 48;
-
- do {
- // scan the width of the line
- for (l= 0; l < 40; l++)
- if (start + l == cs.length() - 1 || cs.charAt(start + l) == '\n')
- break;
- x= (viddef.width - l * 8) / 2;
- SCR.AddDirtyPoint(x, y);
- for (j= 0; j < l; j++, x += 8) {
- re.DrawChar(x, y, cs.charAt(start + j));
- if (remaining == 0)
- return;
- remaining--;
- }
- SCR.AddDirtyPoint(x, y + 8);
-
- y += 8;
-
- while (start < cs.length() && cs.charAt(start) != '\n')
- start++;
-
- if (start == cs.length())
- break;
- start++; // skip the \n
- }
- while (true);
- }
-
- static void CheckDrawCenterString() {
- scr_centertime_off -= cls.frametime;
-
- if (scr_centertime_off <= 0)
- return;
-
- DrawCenterString();
- }
-
- // =============================================================================
-
- /*
- =================
- SCR_CalcVrect
-
- Sets scr_vrect, the coordinates of the rendered window
- =================
- */
- static void CalcVrect() {
- int size;
-
- // bound viewsize
- if (scr_viewsize.value < 40)
- Cvar.Set("viewsize", "40");
- if (scr_viewsize.value > 100)
- Cvar.Set("viewsize", "100");
-
- size= (int) scr_viewsize.value;
-
- scr_vrect.width= viddef.width * size / 100;
- scr_vrect.width &= ~7;
-
- scr_vrect.height= viddef.height * size / 100;
- scr_vrect.height &= ~1;
-
- scr_vrect.x= (viddef.width - scr_vrect.width) / 2;
- scr_vrect.y= (viddef.height - scr_vrect.height) / 2;
- }
-
- /*
- =================
- SCR_SizeUp_f
-
- Keybinding command
- =================
- */
- static void SizeUp_f() {
- Cvar.SetValue("viewsize", scr_viewsize.value + 10);
- }
-
- /*
- =================
- SCR_SizeDown_f
-
- Keybinding command
- =================
- */
- static void SizeDown_f() {
- Cvar.SetValue("viewsize", scr_viewsize.value - 10);
- }
-
- /*
- =================
- SCR_Sky_f
-
- Set a specific sky and rotation speed
- =================
- */
- static void Sky_f() {
- float rotate;
- float[] axis= { 0, 0, 0 };
-
- if (Cmd.Argc() < 2) {
- Com.Printf("Usage: sky <basename> <rotate> <axis x y z>\n");
- return;
- }
- if (Cmd.Argc() > 2)
- rotate= Float.parseFloat(Cmd.Argv(2));
- else
- rotate= 0;
- if (Cmd.Argc() == 6) {
- axis[0]= Float.parseFloat(Cmd.Argv(3));
- axis[1]= Float.parseFloat(Cmd.Argv(4));
- axis[2]= Float.parseFloat(Cmd.Argv(5));
- }
- else {
- axis[0]= 0;
- axis[1]= 0;
- axis[2]= 1;
- }
-
- re.SetSky(Cmd.Argv(1), rotate, axis);
- }
-
- // ============================================================================
-
- /*
- ==================
- SCR_Init
- ==================
- */
- static void Init() {
- scr_viewsize= Cvar.Get("viewsize", "100", CVAR_ARCHIVE);
- scr_conspeed= Cvar.Get("scr_conspeed", "3", 0);
- scr_showturtle= Cvar.Get("scr_showturtle", "0", 0);
- scr_showpause= Cvar.Get("scr_showpause", "1", 0);
- scr_centertime= Cvar.Get("scr_centertime", "2.5", 0);
- scr_printspeed= Cvar.Get("scr_printspeed", "8", 0);
- scr_netgraph= Cvar.Get("netgraph", "1", 0);
- scr_timegraph= Cvar.Get("timegraph", "1", 0);
- scr_debuggraph= Cvar.Get("debuggraph", "1", 0);
- scr_graphheight= Cvar.Get("graphheight", "32", 0);
- scr_graphscale= Cvar.Get("graphscale", "1", 0);
- scr_graphshift= Cvar.Get("graphshift", "0", 0);
- scr_drawall= Cvar.Get("scr_drawall", "1", 0);
- fps= Cvar.Get("fps", "0", 0);
-
- //
- // register our commands
- //
- Cmd.AddCommand("timerefresh", new xcommand_t() {
- public void execute() {
- TimeRefresh_f();
- }
- });
- Cmd.AddCommand("loading", new xcommand_t() {
- public void execute() {
- Loading_f();
- }
- });
- Cmd.AddCommand("sizeup", new xcommand_t() {
- public void execute() {
- SizeUp_f();
- }
- });
- Cmd.AddCommand("sizedown", new xcommand_t() {
- public void execute() {
- SizeDown_f();
- }
- });
- Cmd.AddCommand("sky", new xcommand_t() {
- public void execute() {
- Sky_f();
- }
- });
-
- scr_initialized= true;
- }
-
- /*
- ==============
- SCR_DrawNet
- ==============
- */
- static void DrawNet() {
- if (cls.netchan.outgoing_sequence - cls.netchan.incoming_acknowledged < CMD_BACKUP - 1)
- return;
-
- re.DrawPic(scr_vrect.x + 64, scr_vrect.y, "net");
- }
-
- /*
- ==============
- SCR_DrawPause
- ==============
- */
- static void DrawPause() {
- Dimension dim= new Dimension();
-
- if (scr_showpause.value == 0) // turn off for screenshots
- return;
-
- if (cl_paused.value == 0)
- return;
-
- re.DrawGetPicSize(dim, "pause");
- re.DrawPic((viddef.width - dim.width) / 2, viddef.height / 2 + 8, "pause");
- }
-
- /*
- ==============
- SCR_DrawLoading
- ==============
- */
- static void DrawLoading() {
- Dimension dim= new Dimension();
-
- if (scr_draw_loading == 0)
- return;
-
- scr_draw_loading= 0;
- re.DrawGetPicSize(dim, "loading");
- re.DrawPic((viddef.width - dim.width) / 2, (viddef.height - dim.height) / 2, "loading");
- }
-
- // =============================================================================
-
- /*
- ==================
- SCR_RunConsole
-
- Scroll it up or down
- ==================
- */
- static void RunConsole() {
- // decide on the height of the console
- if (cls.key_dest == key_console)
- scr_conlines= 0.5f; // half screen
- else
- scr_conlines= 0; // none visible
-
- if (scr_conlines < scr_con_current) {
- scr_con_current -= scr_conspeed.value * cls.frametime;
- if (scr_conlines > scr_con_current)
- scr_con_current= scr_conlines;
-
- }
- else if (scr_conlines > scr_con_current) {
- scr_con_current += scr_conspeed.value * cls.frametime;
- if (scr_conlines < scr_con_current)
- scr_con_current= scr_conlines;
- }
- }
-
- /*
- ==================
- SCR_DrawConsole
- ==================
- */
- static void DrawConsole() {
- Console.CheckResize();
-
- if (cls.state == ca_disconnected || cls.state == ca_connecting) { // forced full screen console
- Console.DrawConsole(1.0f);
- return;
- }
-
- if (cls.state != ca_active || !cl.refresh_prepped) { // connected, but can't render
- Console.DrawConsole(0.5f);
- re.DrawFill(0, viddef.height / 2, viddef.width, viddef.height / 2, 0);
- return;
- }
-
- if (scr_con_current != 0) {
- Console.DrawConsole(scr_con_current);
- }
- else {
- if (cls.key_dest == key_game || cls.key_dest == key_message)
- Console.DrawNotify(); // only draw notify in game
- }
- }
-
- // =============================================================================
-
- /*
- ================
- SCR_BeginLoadingPlaque
- ================
- */
- public static void BeginLoadingPlaque() {
- S.StopAllSounds();
- cl.sound_prepped= false; // don't play ambients
-
- if (cls.disable_screen != 0)
- return;
- if (developer.value != 0)
- return;
- if (cls.state == ca_disconnected)
- return; // if at console, don't bring up the plaque
- if (cls.key_dest == key_console)
- return;
- if (cl.cinematictime > 0)
- scr_draw_loading= 2; // clear to balack first
- else
- scr_draw_loading= 1;
-
- UpdateScreen();
- cls.disable_screen= Sys.Milliseconds();
- cls.disable_servercount= cl.servercount;
- }
-
- /*
- ================
- SCR_EndLoadingPlaque
- ================
- */
- public static void EndLoadingPlaque() {
- cls.disable_screen= 0;
- Console.ClearNotify();
- }
-
- /*
- ================
- SCR_Loading_f
- ================
- */
- static void Loading_f() {
- BeginLoadingPlaque();
- }
-
- /*
- ================
- SCR_TimeRefresh_f
- ================
- */
- static void TimeRefresh_f() {
- int i;
- int start, stop;
- float time;
-
- if (cls.state != ca_active)
- return;
-
- start= Sys.Milliseconds();
-
- if (Cmd.Argc() == 2) { // run without page flipping
- re.BeginFrame(0);
- for (i= 0; i < 128; i++) {
- cl.refdef.viewangles[1]= i / 128.0f * 360.0f;
- re.RenderFrame(cl.refdef);
- }
- re.EndFrame();
- }
- else {
- for (i= 0; i < 128; i++) {
- cl.refdef.viewangles[1]= i / 128.0f * 360.0f;
-
- re.BeginFrame(0);
- re.RenderFrame(cl.refdef);
- re.EndFrame();
- }
- }
-
- stop= Sys.Milliseconds();
- time= (stop - start) / 1000.0f;
- Com.Printf("%f seconds (%f fps)\n", new Vargs(2).add(time).add(128.0f / time));
- }
-
- static void DirtyScreen() {
- AddDirtyPoint(0, 0);
- AddDirtyPoint(viddef.width - 1, viddef.height - 1);
- }
-
- /*
- ==============
- SCR_TileClear
-
- Clear any parts of the tiled background that were drawn on last frame
- ==============
- */
-
- static dirty_t clear= new dirty_t();
-
- static void TileClear() {
- int i;
- int top, bottom, left, right;
- clear.clear();
-
- if (scr_drawall.value != 0)
- DirtyScreen(); // for power vr or broken page flippers...
-
- if (scr_con_current == 1.0f)
- return; // full screen console
- if (scr_viewsize.value == 100)
- return; // full screen rendering
- if (cl.cinematictime > 0)
- return; // full screen cinematic
-
- // erase rect will be the union of the past three frames
- // so tripple buffering works properly
- clear.set(scr_dirty);
- for (i= 0; i < 2; i++) {
- if (scr_old_dirty[i].x1 < clear.x1)
- clear.x1= scr_old_dirty[i].x1;
- if (scr_old_dirty[i].x2 > clear.x2)
- clear.x2= scr_old_dirty[i].x2;
- if (scr_old_dirty[i].y1 < clear.y1)
- clear.y1= scr_old_dirty[i].y1;
- if (scr_old_dirty[i].y2 > clear.y2)
- clear.y2= scr_old_dirty[i].y2;
- }
-
- scr_old_dirty[1].set(scr_old_dirty[0]);
- scr_old_dirty[0].set(scr_dirty);
-
- scr_dirty.x1= 9999;
- scr_dirty.x2= -9999;
- scr_dirty.y1= 9999;
- scr_dirty.y2= -9999;
-
- // don't bother with anything convered by the console)
- top= (int) (scr_con_current * viddef.height);
- if (top >= clear.y1)
- clear.y1= top;
-
- if (clear.y2 <= clear.y1)
- return; // nothing disturbed
-
- top= scr_vrect.y;
- bottom= top + scr_vrect.height - 1;
- left= scr_vrect.x;
- right= left + scr_vrect.width - 1;
-
- if (clear.y1 < top) { // clear above view screen
- i= clear.y2 < top - 1 ? clear.y2 : top - 1;
- re.DrawTileClear(clear.x1, clear.y1, clear.x2 - clear.x1 + 1, i - clear.y1 + 1, "backtile");
- clear.y1= top;
- }
- if (clear.y2 > bottom) { // clear below view screen
- i= clear.y1 > bottom + 1 ? clear.y1 : bottom + 1;
- re.DrawTileClear(clear.x1, i, clear.x2 - clear.x1 + 1, clear.y2 - i + 1, "backtile");
- clear.y2= bottom;
- }
- if (clear.x1 < left) { // clear left of view screen
- i= clear.x2 < left - 1 ? clear.x2 : left - 1;
- re.DrawTileClear(clear.x1, clear.y1, i - clear.x1 + 1, clear.y2 - clear.y1 + 1, "backtile");
- clear.x1= left;
- }
- if (clear.x2 > right) { // clear left of view screen
- i= clear.x1 > right + 1 ? clear.x1 : right + 1;
- re.DrawTileClear(i, clear.y1, clear.x2 - i + 1, clear.y2 - clear.y1 + 1, "backtile");
- clear.x2= right;
- }
-
- }
-
- // ===============================================================
-
- static final int STAT_MINUS= 10; // num frame for '-' stats digit
-
- static final int ICON_WIDTH= 24;
- static final int ICON_HEIGHT= 24;
- static final int CHAR_WIDTH= 16;
- static final int ICON_SPACE= 8;
-
- /*
- ================
- SizeHUDString
-
- Allow embedded \n in the string
- ================
- */
- static void SizeHUDString(String string, Dimension dim) {
- int lines, width, current;
-
- lines= 1;
- width= 0;
-
- current= 0;
- for (int i= 0; i < string.length(); i++) {
- if (string.charAt(i) == '\n') {
- lines++;
- current= 0;
- }
- else {
- current++;
- if (current > width)
- width= current;
- }
-
- }
-
- dim.width= width * 8;
- dim.height= lines * 8;
- }
-
- static void DrawHUDString(String string, int x, int y, int centerwidth, int xor) {
- int margin;
- //char line[1024];
- StringBuffer line= new StringBuffer(1024);
- int i;
-
- margin= x;
-
- for (int l= 0; l < string.length();) {
- // scan out one line of text from the string
- line= new StringBuffer(1024);
- while (l < string.length() && string.charAt(l) != '\n') {
- line.append(string.charAt(l));
- l++;
- }
-
- if (centerwidth != 0)
- x= margin + (centerwidth - line.length() * 8) / 2;
- else
- x= margin;
- for (i= 0; i < line.length(); i++) {
- re.DrawChar(x, y, line.charAt(i) ^ xor);
- x += 8;
- }
- if (l < string.length()) {
- l++; // skip the \n
- x= margin;
- y += 8;
- }
- }
- }
-
- /*
- ==============
- SCR_DrawField
- ==============
- */
- static void DrawField(int x, int y, int color, int width, int value) {
- char ptr;
- String num;
- int l;
- int frame;
-
- if (width < 1)
- return;
-
- // draw number string
- if (width > 5)
- width= 5;
-
- AddDirtyPoint(x, y);
- AddDirtyPoint(x + width * CHAR_WIDTH + 2, y + 23);
-
- num= "" + value;
- l= num.length();
- if (l > width)
- l= width;
- x += 2 + CHAR_WIDTH * (width - l);
-
- ptr= num.charAt(0);
-
- for (int i= 0; i < l; i++) {
- ptr= num.charAt(i);
- if (ptr == '-')
- frame= STAT_MINUS;
- else
- frame= ptr - '0';
-
- re.DrawPic(x, y, sb_nums[color][frame]);
- x += CHAR_WIDTH;
- }
- }
-
- /*
- ===============
- SCR_TouchPics
-
- Allows rendering code to cache all needed sbar graphics
- ===============
- */
- static void TouchPics() {
- int i, j;
-
- for (i= 0; i < 2; i++)
- for (j= 0; j < 11; j++)
- re.RegisterPic(sb_nums[i][j]);
-
- if (crosshair.value != 0.0f) {
- if (crosshair.value > 3.0f || crosshair.value < 0.0f)
- crosshair.value= 3.0f;
-
- crosshair_pic= "ch" + (int) crosshair.value;
- Dimension dim= new Dimension();
- re.DrawGetPicSize(dim, crosshair_pic);
- crosshair_width= dim.width;
- crosshair_height= dim.height;
- if (crosshair_width == 0)
- crosshair_pic= "";
- }
- }
-
- /*
- ================
- SCR_ExecuteLayoutString
-
- ================
- */
- static void ExecuteLayoutString(String s) {
- int x, y;
- int value;
- String token;
- int width;
- int index;
- clientinfo_t ci;
-
- if (cls.state != ca_active || !cl.refresh_prepped)
- return;
-
- // if (!s[0])
- if (s == null || s.length() == 0)
- return;
-
- x= 0;
- y= 0;
- width= 3;
-
- Com.ParseHelp ph= new Com.ParseHelp(s);
-
- while (!ph.isEof()) {
- token= Com.Parse(ph);
- if (token.equals("xl")) {
- token= Com.Parse(ph);
- x= atoi(token);
- continue;
- }
- if (token.equals("xr")) {
- token= Com.Parse(ph);
- x= viddef.width + atoi(token);
- continue;
- }
- if (token.equals("xv")) {
- token= Com.Parse(ph);
- x= viddef.width / 2 - 160 + atoi(token);
- continue;
- }
-
- if (token.equals("yt")) {
- token= Com.Parse(ph);
- y= atoi(token);
- continue;
- }
- if (token.equals("yb")) {
- token= Com.Parse(ph);
- y= viddef.height + atoi(token);
- continue;
- }
- if (token.equals("yv")) {
- token= Com.Parse(ph);
- y= viddef.height / 2 - 120 + atoi(token);
- continue;
- }
-
- if (token.equals("pic")) { // draw a pic from a stat number
- token= Com.Parse(ph);
- value= cl.frame.playerstate.stats[atoi(token)];
- if (value >= MAX_IMAGES)
- Com.Error(ERR_DROP, "Pic >= MAX_IMAGES");
- if (cl.configstrings[CS_IMAGES + value] != null) {
- AddDirtyPoint(x, y);
- AddDirtyPoint(x + 23, y + 23);
- re.DrawPic(x, y, cl.configstrings[CS_IMAGES + value]);
- }
- continue;
- }
-
- if (token.equals("client")) { // draw a deathmatch client block
- int score, ping, time;
-
- token= Com.Parse(ph);
- x= viddef.width / 2 - 160 + atoi(token);
- token= Com.Parse(ph);
- y= viddef.height / 2 - 120 + atoi(token);
- AddDirtyPoint(x, y);
- AddDirtyPoint(x + 159, y + 31);
-
- token= Com.Parse(ph);
- value= atoi(token);
- if (value >= MAX_CLIENTS || value < 0)
- Com.Error(ERR_DROP, "client >= MAX_CLIENTS");
- ci= cl.clientinfo[value];
-
- token= Com.Parse(ph);
- score= atoi(token);
-
- token= Com.Parse(ph);
- ping= atoi(token);
-
- token= Com.Parse(ph);
- time= atoi(token);
-
- Console.DrawAltString(x + 32, y, ci.name);
- Console.DrawString(x + 32, y + 8, "Score: ");
- Console.DrawAltString(x + 32 + 7 * 8, y + 8, "" + score);
- Console.DrawString(x + 32, y + 16, "Ping: " + ping);
- Console.DrawString(x + 32, y + 24, "Time: " + time);
-
- if (ci.icon == null)
- ci= cl.baseclientinfo;
- re.DrawPic(x, y, ci.iconname);
- continue;
- }
-
- if (token.equals("ctf")) { // draw a ctf client block
- int score, ping;
-
- token= Com.Parse(ph);
- x= viddef.width / 2 - 160 + atoi(token);
- token= Com.Parse(ph);
- y= viddef.height / 2 - 120 + atoi(token);
- AddDirtyPoint(x, y);
- AddDirtyPoint(x + 159, y + 31);
-
- token= Com.Parse(ph);
- value= atoi(token);
- if (value >= MAX_CLIENTS || value < 0)
- Com.Error(ERR_DROP, "client >= MAX_CLIENTS");
- ci= cl.clientinfo[value];
-
- token= Com.Parse(ph);
- score= atoi(token);
-
- token= Com.Parse(ph);
- ping= atoi(token);
- if (ping > 999)
- ping= 999;
-
- // sprintf(block, "%3d %3d %-12.12s", score, ping, ci->name);
- String block= Com.sprintf("%3d %3d %-12.12s", new Vargs(3).add(score).add(ping).add(ci.name));
-
- if (value == cl.playernum)
- Console.DrawAltString(x, y, block);
- else
- Console.DrawString(x, y, block);
- continue;
- }
-
- if (token.equals("picn")) { // draw a pic from a name
- token= Com.Parse(ph);
- AddDirtyPoint(x, y);
- AddDirtyPoint(x + 23, y + 23);
- re.DrawPic(x, y, token);
- continue;
- }
-
- if (token.equals("num")) { // draw a number
- token= Com.Parse(ph);
- width= atoi(token);
- token= Com.Parse(ph);
- value= cl.frame.playerstate.stats[atoi(token)];
- DrawField(x, y, 0, width, value);
- continue;
- }
-
- if (token.equals("hnum")) { // health number
- int color;
-
- width= 3;
- value= cl.frame.playerstate.stats[STAT_HEALTH];
- if (value > 25)
- color= 0; // green
- else if (value > 0)
- color= (cl.frame.serverframe >> 2) & 1; // flash
- else
- color= 1;
-
- if ((cl.frame.playerstate.stats[STAT_FLASHES] & 1) != 0)
- re.DrawPic(x, y, "field_3");
-
- DrawField(x, y, color, width, value);
- continue;
- }
-
- if (token.equals("anum")) { // ammo number
- int color;
-
- width= 3;
- value= cl.frame.playerstate.stats[STAT_AMMO];
- if (value > 5)
- color= 0; // green
- else if (value >= 0)
- color= (cl.frame.serverframe >> 2) & 1; // flash
- else
- continue; // negative number = don't show
-
- if ((cl.frame.playerstate.stats[STAT_FLASHES] & 4) != 0)
- re.DrawPic(x, y, "field_3");
-
- DrawField(x, y, color, width, value);
- continue;
- }
-
- if (token.equals("rnum")) { // armor number
- int color;
-
- width= 3;
- value= cl.frame.playerstate.stats[STAT_ARMOR];
- if (value < 1)
- continue;
-
- color= 0; // green
-
- if ((cl.frame.playerstate.stats[STAT_FLASHES] & 2) != 0)
- re.DrawPic(x, y, "field_3");
-
- DrawField(x, y, color, width, value);
- continue;
- }
-
- if (token.equals("stat_string")) {
- token= Com.Parse(ph);
- index= atoi(token);
- if (index < 0 || index >= MAX_CONFIGSTRINGS)
- Com.Error(ERR_DROP, "Bad stat_string index");
- index= cl.frame.playerstate.stats[index];
- if (index < 0 || index >= MAX_CONFIGSTRINGS)
- Com.Error(ERR_DROP, "Bad stat_string index");
- Console.DrawString(x, y, cl.configstrings[index]);
- continue;
- }
-
- if (token.equals("cstring")) {
- token= Com.Parse(ph);
- DrawHUDString(token, x, y, 320, 0);
- continue;
- }
-
- if (token.equals("string")) {
- token= Com.Parse(ph);
- Console.DrawString(x, y, token);
- continue;
- }
-
- if (token.equals("cstring2")) {
- token= Com.Parse(ph);
- DrawHUDString(token, x, y, 320, 0x80);
- continue;
- }
-
- if (token.equals("string2")) {
- token= Com.Parse(ph);
- Console.DrawAltString(x, y, token);
- continue;
- }
-
- if (token.equals("if")) { // draw a number
- token= Com.Parse(ph);
- value= cl.frame.playerstate.stats[atoi(token)];
- if (value == 0) { // skip to endif
- // while (s && strcmp(token, "endif") )
- // {
- // token = Com.Parse(ph);
- // }
-
- while (!ph.isEof() && !(token= Com.Parse(ph)).equals("endif"));
-
- }
-
- continue;
- }
-
- }
- }
-
- /*
- ================
- SCR_DrawStats
-
- The status bar is a small layout program that
- is based on the stats array
- ================
- */
- static void DrawStats() {
- //TODO:
- SCR.ExecuteLayoutString(cl.configstrings[CS_STATUSBAR]);
- }
-
- /*
- ================
- SCR_DrawLayout
-
- ================
- */
- static final int STAT_LAYOUTS= 13;
-
- static void DrawLayout() {
- if (cl.frame.playerstate.stats[STAT_LAYOUTS] != 0)
- SCR.ExecuteLayoutString(cl.layout);
- }
-
- // =======================================================
-
- /*
- ==================
- SCR_UpdateScreen
-
- This is called every frame, and can also be called explicitly to flush
- text to the screen.
- ==================
- */
- static void UpdateScreen2() {
- int numframes;
- int i;
- float[] separation= { 0, 0 };
-
- // if the screen is disabled (loading plaque is up, or vid mode changing)
- // do nothing at all
- if (cls.disable_screen != 0) {
- if (Sys.Milliseconds() - cls.disable_screen > 120000) {
- cls.disable_screen= 0;
- Com.Printf("Loading plaque timed out.\n");
- }
- return;
- }
-
- if (!scr_initialized || !con.initialized)
- return; // not initialized yet
-
- /*
- ** range check cl_camera_separation so we don't inadvertently fry someone's
- ** brain
- */
- if (cl_stereo_separation.value > 1.0)
- Cvar.SetValue("cl_stereo_separation", 1.0f);
- else if (cl_stereo_separation.value < 0)
- Cvar.SetValue("cl_stereo_separation", 0.0f);
-
- if (cl_stereo.value != 0) {
- numframes= 2;
- separation[0]= -cl_stereo_separation.value / 2;
- separation[1]= cl_stereo_separation.value / 2;
- }
- else {
- separation[0]= 0;
- separation[1]= 0;
- numframes= 1;
- }
-
- for (i= 0; i < numframes; i++) {
- re.BeginFrame(separation[i]);
-
- if (scr_draw_loading == 2) { // loading plaque over black screen
- Dimension dim= new Dimension();
-
- re.CinematicSetPalette(null);
- scr_draw_loading= 0; // false
- re.DrawGetPicSize(dim, "loading");
- re.DrawPic((viddef.width - dim.width) / 2, (viddef.height - dim.height) / 2, "loading");
- }
- // if a cinematic is supposed to be running, handle menus
- // and console specially
- else if (cl.cinematictime > 0) {
- if (cls.key_dest == key_menu) {
- if (cl.cinematicpalette_active) {
- re.CinematicSetPalette(null);
- cl.cinematicpalette_active= false;
- }
- Menu.Draw();
- }
- else if (cls.key_dest == key_console) {
- if (cl.cinematicpalette_active) {
- re.CinematicSetPalette(null);
- cl.cinematicpalette_active= false;
- }
- DrawConsole();
- }
- else {
- // TODO impl: cl_cin.c for cinematics
- DrawCinematic();
- }
- }
- else {
- // make sure the game palette is active
- if (cl.cinematicpalette_active) {
- re.CinematicSetPalette(null);
- cl.cinematicpalette_active= false;
- }
-
- // do 3D refresh drawing, and then update the screen
- CalcVrect();
-
- // clear any dirty part of the background
- TileClear();
-
- V.RenderView(separation[i]);
-
- DrawStats();
-
- if ((cl.frame.playerstate.stats[STAT_LAYOUTS] & 1) != 0)
- DrawLayout();
- if ((cl.frame.playerstate.stats[STAT_LAYOUTS] & 2) != 0)
- CL.DrawInventory();
-
- DrawNet();
- CheckDrawCenterString();
- DrawFPS();
-
- //
- // if (scr_timegraph->value)
- // SCR_DebugGraph (cls.frametime*300, 0);
- //
- // if (scr_debuggraph->value || scr_timegraph->value || scr_netgraph->value)
- // SCR_DrawDebugGraph ();
- //
- DrawPause();
- DrawConsole();
- Menu.Draw();
- DrawLoading();
- }
- }
-
- Globals.re.EndFrame();
- }
-
- /*
- =================
- SCR_DrawCrosshair
- =================
- */
- static void DrawCrosshair() {
- if (crosshair.value == 0.0f)
- return;
-
- if (crosshair.modified) {
- crosshair.modified= false;
- SCR.TouchPics();
- }
-
- if (crosshair_pic.length() == 0)
- return;
-
- re.DrawPic(
- scr_vrect.x + ((scr_vrect.width - crosshair_width) >> 1),
- scr_vrect.y + ((scr_vrect.height - crosshair_height) >> 1),
- crosshair_pic);
- }
-
- private static xcommand_t updateScreenCallback= new xcommand_t() {
- public void execute() {
- UpdateScreen2();
- }
- };
-
- // wird anstelle von der richtigen UpdateScreen benoetigt
- public static void UpdateScreen() {
- Globals.re.updateScreen(updateScreenCallback);
- }
-
- /*
- =================
- SCR_AddDirtyPoint
- =================
- */
- static void AddDirtyPoint(int x, int y) {
- if (x < scr_dirty.x1)
- scr_dirty.x1= x;
- if (x > scr_dirty.x2)
- scr_dirty.x2= x;
- if (y < scr_dirty.y1)
- scr_dirty.y1= y;
- if (y > scr_dirty.y2)
- scr_dirty.y2= y;
- }
-
- private static int lastframes= 0;
- private static int lasttime= 0;
- private static String fpsvalue= "";
-
- static void DrawFPS() {
- if (fps.value > 0.0f) {
- if (fps.modified) {
- fps.modified= false;
- Cvar.SetValue("cl_maxfps", 1000);
- }
-
- int diff= cls.realtime - lasttime;
- if (diff > (int) (fps.value * 1000)) {
- fpsvalue= (cls.framecount - lastframes) * 100000 / diff / 100.0f + " fps";
- lastframes= cls.framecount;
- lasttime= cls.realtime;
- }
- int x= viddef.width - 8 * fpsvalue.length() - 2;
- for (int i= 0; i < fpsvalue.length(); i++) {
- re.DrawChar(x, 2, fpsvalue.charAt(i));
- x += 8;
- }
- }
- else if (fps.modified) {
- fps.modified= false;
- Cvar.SetValue("cl_maxfps", 90);
- }
- }
-
- /*
- =================================================================
-
- cl_cin.c
-
- Play Cinematics
-
- =================================================================
- */
-
- // typedef struct
- // {
- // byte *data;
- // int count;
- // } cblock_t;
- //
- // typedef struct
- // {
- // qboolean restart_sound;
- // int s_rate;
- // int s_width;
- // int s_channels;
- //
- // int width;
- // int height;
- // byte *pic;
- // byte *pic_pending;
- //
- // // order 1 huffman stuff
- // int *hnodes1; // [256][256][2];
- // int numhnodes1[256];
- //
- // int h_used[512];
- // int h_count[512];
- // } cinematics_t;
- //
- // cinematics_t cin;
- //
- // /*
- // =================================================================
- //
- // PCX LOADING
- //
- // =================================================================
- // */
- //
- //
- // /*
- // ==============
- // SCR_LoadPCX
- // ==============
- // */
- // void SCR_LoadPCX (char *filename, byte **pic, byte **palette, int *width, int *height)
- // {
- // byte *raw;
- // pcx_t *pcx;
- // int x, y;
- // int len;
- // int dataByte, runLength;
- // byte *out, *pix;
- //
- // *pic = NULL;
- //
- // //
- // // load the file
- // //
- // len = FS_LoadFile (filename, (void **)&raw);
- // if (!raw)
- // return; // Com_Printf ("Bad pcx file %s\n", filename);
- //
- // //
- // // parse the PCX file
- // //
- // pcx = (pcx_t *)raw;
- // raw = &pcx->data;
- //
- // if (pcx->manufacturer != 0x0a
- // || pcx->version != 5
- // || pcx->encoding != 1
- // || pcx->bits_per_pixel != 8
- // || pcx->xmax >= 640
- // || pcx->ymax >= 480)
- // {
- // Com_Printf ("Bad pcx file %s\n", filename);
- // return;
- // }
- //
- // out = Z_Malloc ( (pcx->ymax+1) * (pcx->xmax+1) );
- //
- // *pic = out;
- //
- // pix = out;
- //
- // if (palette)
- // {
- // *palette = Z_Malloc(768);
- // memcpy (*palette, (byte *)pcx + len - 768, 768);
- // }
- //
- // if (width)
- // *width = pcx->xmax+1;
- // if (height)
- // *height = pcx->ymax+1;
- //
- // for (y=0 ; y<=pcx->ymax ; y++, pix += pcx->xmax+1)
- // {
- // for (x=0 ; x<=pcx->xmax ; )
- // {
- // dataByte = *raw++;
- //
- // if((dataByte & 0xC0) == 0xC0)
- // {
- // runLength = dataByte & 0x3F;
- // dataByte = *raw++;
- // }
- // else
- // runLength = 1;
- //
- // while(runLength-- > 0)
- // pix[x++] = dataByte;
- // }
- //
- // }
- //
- // if ( raw - (byte *)pcx > len)
- // {
- // Com_Printf ("PCX file %s was malformed", filename);
- // Z_Free (*pic);
- // *pic = NULL;
- // }
- //
- // FS_FreeFile (pcx);
- // }
- //
- // =============================================================
-
- /*
- ==================
- SCR_StopCinematic
- ==================
- */
- static void StopCinematic() {
- cl.cinematictime= 0; // done
- // if (cin.pic)
- // {
- // Z_Free (cin.pic);
- // cin.pic = NULL;
- // }
- // if (cin.pic_pending)
- // {
- // Z_Free (cin.pic_pending);
- // cin.pic_pending = NULL;
- // }
- if (cl.cinematicpalette_active) {
- re.CinematicSetPalette(null);
- cl.cinematicpalette_active= false;
- }
- // if (cl.cinematic_file)
- // {
- // fclose (cl.cinematic_file);
- // cl.cinematic_file = NULL;
- // }
- // if (cin.hnodes1)
- // {
- // Z_Free (cin.hnodes1);
- // cin.hnodes1 = NULL;
- // }
- //
- // // switch back down to 11 khz sound if necessary
- // if (cin.restart_sound)
- // {
- // cin.restart_sound = false;
- // CL_Snd_Restart_f ();
- // }
- //
- }
-
- /*
- ====================
- SCR_FinishCinematic
-
- Called when either the cinematic completes, or it is aborted
- ====================
- */
- static void FinishCinematic() {
- // tell the server to advance to the next map / cinematic
- MSG.WriteByte(cls.netchan.message, clc_stringcmd);
- SZ.Print(cls.netchan.message, "nextserver " + cl.servercount + '\n');
- }
-
- // ==========================================================================
-
- // /*
- // ==================
- // SmallestNode1
- // ==================
- // */
- // int SmallestNode1 (int numhnodes)
- // {
- // int i;
- // int best, bestnode;
- //
- // best = 99999999;
- // bestnode = -1;
- // for (i=0 ; i<numhnodes ; i++)
- // {
- // if (cin.h_used[i])
- // continue;
- // if (!cin.h_count[i])
- // continue;
- // if (cin.h_count[i] < best)
- // {
- // best = cin.h_count[i];
- // bestnode = i;
- // }
- // }
- //
- // if (bestnode == -1)
- // return -1;
- //
- // cin.h_used[bestnode] = true;
- // return bestnode;
- // }
- //
- //
- // /*
- // ==================
- // Huff1TableInit
- //
- // Reads the 64k counts table and initializes the node trees
- // ==================
- // */
- // void Huff1TableInit (void)
- // {
- // int prev;
- // int j;
- // int *node, *nodebase;
- // byte counts[256];
- // int numhnodes;
- //
- // cin.hnodes1 = Z_Malloc (256*256*2*4);
- // memset (cin.hnodes1, 0, 256*256*2*4);
- //
- // for (prev=0 ; prev<256 ; prev++)
- // {
- // memset (cin.h_count,0,sizeof(cin.h_count));
- // memset (cin.h_used,0,sizeof(cin.h_used));
- //
- // // read a row of counts
- // FS_Read (counts, sizeof(counts), cl.cinematic_file);
- // for (j=0 ; j<256 ; j++)
- // cin.h_count[j] = counts[j];
- //
- // // build the nodes
- // numhnodes = 256;
- // nodebase = cin.hnodes1 + prev*256*2;
- //
- // while (numhnodes != 511)
- // {
- // node = nodebase + (numhnodes-256)*2;
- //
- // // pick two lowest counts
- // node[0] = SmallestNode1 (numhnodes);
- // if (node[0] == -1)
- // break; // no more
- //
- // node[1] = SmallestNode1 (numhnodes);
- // if (node[1] == -1)
- // break;
- //
- // cin.h_count[numhnodes] = cin.h_count[node[0]] + cin.h_count[node[1]];
- // numhnodes++;
- // }
- //
- // cin.numhnodes1[prev] = numhnodes-1;
- // }
- // }
- //
- // /*
- // ==================
- // Huff1Decompress
- // ==================
- // */
- // cblock_t Huff1Decompress (cblock_t in)
- // {
- // byte *input;
- // byte *out_p;
- // int nodenum;
- // int count;
- // cblock_t out;
- // int inbyte;
- // int *hnodes, *hnodesbase;
- //// int i;
- //
- // // get decompressed count
- // count = in.data[0] + (in.data[1]<<8) + (in.data[2]<<16) + (in.data[3]<<24);
- // input = in.data + 4;
- // out_p = out.data = Z_Malloc (count);
- //
- // // read bits
- //
- // hnodesbase = cin.hnodes1 - 256*2; // nodes 0-255 aren't stored
- //
- // hnodes = hnodesbase;
- // nodenum = cin.numhnodes1[0];
- // while (count)
- // {
- // inbyte = *input++;
- // //-----------
- // if (nodenum < 256)
- // {
- // hnodes = hnodesbase + (nodenum<<9);
- // *out_p++ = nodenum;
- // if (!--count)
- // break;
- // nodenum = cin.numhnodes1[nodenum];
- // }
- // nodenum = hnodes[nodenum*2 + (inbyte&1)];
- // inbyte >>=1;
- // //-----------
- // if (nodenum < 256)
- // {
- // hnodes = hnodesbase + (nodenum<<9);
- // *out_p++ = nodenum;
- // if (!--count)
- // break;
- // nodenum = cin.numhnodes1[nodenum];
- // }
- // nodenum = hnodes[nodenum*2 + (inbyte&1)];
- // inbyte >>=1;
- // //-----------
- // if (nodenum < 256)
- // {
- // hnodes = hnodesbase + (nodenum<<9);
- // *out_p++ = nodenum;
- // if (!--count)
- // break;
- // nodenum = cin.numhnodes1[nodenum];
- // }
- // nodenum = hnodes[nodenum*2 + (inbyte&1)];
- // inbyte >>=1;
- // //-----------
- // if (nodenum < 256)
- // {
- // hnodes = hnodesbase + (nodenum<<9);
- // *out_p++ = nodenum;
- // if (!--count)
- // break;
- // nodenum = cin.numhnodes1[nodenum];
- // }
- // nodenum = hnodes[nodenum*2 + (inbyte&1)];
- // inbyte >>=1;
- // //-----------
- // if (nodenum < 256)
- // {
- // hnodes = hnodesbase + (nodenum<<9);
- // *out_p++ = nodenum;
- // if (!--count)
- // break;
- // nodenum = cin.numhnodes1[nodenum];
- // }
- // nodenum = hnodes[nodenum*2 + (inbyte&1)];
- // inbyte >>=1;
- // //-----------
- // if (nodenum < 256)
- // {
- // hnodes = hnodesbase + (nodenum<<9);
- // *out_p++ = nodenum;
- // if (!--count)
- // break;
- // nodenum = cin.numhnodes1[nodenum];
- // }
- // nodenum = hnodes[nodenum*2 + (inbyte&1)];
- // inbyte >>=1;
- // //-----------
- // if (nodenum < 256)
- // {
- // hnodes = hnodesbase + (nodenum<<9);
- // *out_p++ = nodenum;
- // if (!--count)
- // break;
- // nodenum = cin.numhnodes1[nodenum];
- // }
- // nodenum = hnodes[nodenum*2 + (inbyte&1)];
- // inbyte >>=1;
- // //-----------
- // if (nodenum < 256)
- // {
- // hnodes = hnodesbase + (nodenum<<9);
- // *out_p++ = nodenum;
- // if (!--count)
- // break;
- // nodenum = cin.numhnodes1[nodenum];
- // }
- // nodenum = hnodes[nodenum*2 + (inbyte&1)];
- // inbyte >>=1;
- // }
- //
- // if (input - in.data != in.count && input - in.data != in.count+1)
- // {
- // Com_Printf ("Decompression overread by %i", (input - in.data) - in.count);
- // }
- // out.count = out_p - out.data;
- //
- // return out;
- // }
- //
- // /*
- // ==================
- // SCR_ReadNextFrame
- // ==================
- // */
- // byte *SCR_ReadNextFrame (void)
- // {
- // int r;
- // int command;
- // byte samples[22050/14*4];
- // byte compressed[0x20000];
- // int size;
- // byte *pic;
- // cblock_t in, huf1;
- // int start, end, count;
- //
- // // read the next frame
- // r = fread (&command, 4, 1, cl.cinematic_file);
- // if (r == 0) // we'll give it one more chance
- // r = fread (&command, 4, 1, cl.cinematic_file);
- //
- // if (r != 1)
- // return NULL;
- // command = LittleLong(command);
- // if (command == 2)
- // return NULL; // last frame marker
- //
- // if (command == 1)
- // { // read palette
- // FS_Read (cl.cinematicpalette, sizeof(cl.cinematicpalette), cl.cinematic_file);
- // cl.cinematicpalette_active=0; // dubious.... exposes an edge case
- // }
- //
- // // decompress the next frame
- // FS_Read (&size, 4, cl.cinematic_file);
- // size = LittleLong(size);
- // if (size > sizeof(compressed) || size < 1)
- // Com_Error (ERR_DROP, "Bad compressed frame size");
- // FS_Read (compressed, size, cl.cinematic_file);
- //
- // // read sound
- // start = cl.cinematicframe*cin.s_rate/14;
- // end = (cl.cinematicframe+1)*cin.s_rate/14;
- // count = end - start;
- //
- // FS_Read (samples, count*cin.s_width*cin.s_channels, cl.cinematic_file);
- //
- // S_RawSamples (count, cin.s_rate, cin.s_width, cin.s_channels, samples);
- //
- // in.data = compressed;
- // in.count = size;
- //
- // huf1 = Huff1Decompress (in);
- //
- // pic = huf1.data;
- //
- // cl.cinematicframe++;
- //
- // return pic;
- // }
- //
- //
- /*
- ==================
- SCR_RunCinematic
-
- ==================
- */
- static void RunCinematic() {
- int frame;
-
- if (cl.cinematictime <= 0) {
- StopCinematic();
- return;
- }
-
- // if (cl.cinematicframe == -1)
- // return; // static image
- //
- // if (cls.key_dest != key_game)
- // { // pause if menu or console is up
- // cl.cinematictime = cls.realtime - cl.cinematicframe*1000/14;
- // return;
- // }
- //
- // frame = (cls.realtime - cl.cinematictime)*14.0/1000;
- // if (frame <= cl.cinematicframe)
- // return;
- // if (frame > cl.cinematicframe+1)
- // {
- // Com_Printf ("Dropped frame: %i > %i\n", frame, cl.cinematicframe+1);
- // cl.cinematictime = cls.realtime - cl.cinematicframe*1000/14;
- // }
- // if (cin.pic)
- // Z_Free (cin.pic);
- // cin.pic = cin.pic_pending;
- // cin.pic_pending = NULL;
- // cin.pic_pending = SCR_ReadNextFrame ();
- // if (!cin.pic_pending)
- // {
- // SCR_StopCinematic ();
- // SCR_FinishCinematic ();
- // cl.cinematictime = 1; // hack to get the black screen behind loading
- // SCR_BeginLoadingPlaque ();
- // cl.cinematictime = 0;
- // return;
- // }
- }
-
- /*
- ==================
- SCR_DrawCinematic
-
- Returns true if a cinematic is active, meaning the view rendering
- should be skipped
- ==================
- */
- static boolean DrawCinematic() {
- // if (cl.cinematictime <= 0)
- // {
- return false;
- // }
- //
- // if (cls.key_dest == key_menu)
- // { // blank screen and pause if menu is up
- // re.CinematicSetPalette(NULL);
- // cl.cinematicpalette_active = false;
- // return true;
- // }
- //
- // if (!cl.cinematicpalette_active)
- // {
- // re.CinematicSetPalette(cl.cinematicpalette);
- // cl.cinematicpalette_active = true;
- // }
- //
- // if (!cin.pic)
- // return true;
- //
- // re.DrawStretchRaw (0, 0, viddef.width, viddef.height,
- // cin.width, cin.height, cin.pic);
- //
- // return true;
- }
-
- /*
- ==================
- SCR_PlayCinematic
-
- ==================
- */
- static void PlayCinematic(String arg) {
- // int width, height;
- // byte *palette;
- // char name[MAX_OSPATH], *dot;
- // int old_khz;
- //
- // // make sure CD isn't playing music
- //CDAudio.Stop();
-
- cl.cinematicframe= 0;
- // dot = strstr (arg, ".");
- // if (dot && !strcmp (dot, ".pcx"))
- // { // static pcx image
- // Com_sprintf (name, sizeof(name), "pics/%s", arg);
- // SCR_LoadPCX (name, &cin.pic, &palette, &cin.width, &cin.height);
- // cl.cinematicframe = -1;
- // cl.cinematictime = 1;
- // SCR_EndLoadingPlaque ();
- // cls.state = ca_active;
- // if (!cin.pic)
- // {
- // Com_Printf ("%s not found.\n", name);
- // cl.cinematictime = 0;
- // }
- // else
- // {
- // memcpy (cl.cinematicpalette, palette, sizeof(cl.cinematicpalette));
- // Z_Free (palette);
- // }
- // return;
- // }
- //
- // Com_sprintf (name, sizeof(name), "video/%s", arg);
- // FS_FOpenFile (name, &cl.cinematic_file);
- // if (!cl.cinematic_file)
- // {
- // Com_Error (ERR_DROP, "Cinematic %s not found.\n", name);
- FinishCinematic();
- cl.cinematictime= 0; // done
- return;
- // }
- //
- // SCR_EndLoadingPlaque ();
- //
- // cls.state = ca_active;
- //
- // FS_Read (&width, 4, cl.cinematic_file);
- // FS_Read (&height, 4, cl.cinematic_file);
- // cin.width = LittleLong(width);
- // cin.height = LittleLong(height);
- //
- // FS_Read (&cin.s_rate, 4, cl.cinematic_file);
- // cin.s_rate = LittleLong(cin.s_rate);
- // FS_Read (&cin.s_width, 4, cl.cinematic_file);
- // cin.s_width = LittleLong(cin.s_width);
- // FS_Read (&cin.s_channels, 4, cl.cinematic_file);
- // cin.s_channels = LittleLong(cin.s_channels);
- //
- // Huff1TableInit ();
- //
- // // switch up to 22 khz sound if necessary
- // old_khz = Cvar_VariableValue ("s_khz");
- // if (old_khz != cin.s_rate/1000)
- // {
- // cin.restart_sound = true;
- // Cvar_SetValue ("s_khz", cin.s_rate/1000);
- // CL_Snd_Restart_f ();
- // Cvar_SetValue ("s_khz", old_khz);
- // }
- //
- // cl.cinematicframe = 0;
- // cin.pic = SCR_ReadNextFrame ();
- // cl.cinematictime = Sys_Milliseconds ();
- }
+ // cl_scrn.c -- master for refresh, status bar, console, chat, notify, etc
+
+ static String[][] sb_nums = {
+ { "num_0", "num_1", "num_2", "num_3", "num_4", "num_5", "num_6",
+ "num_7", "num_8", "num_9", "num_minus" },
+ { "anum_0", "anum_1", "anum_2", "anum_3", "anum_4", "anum_5",
+ "anum_6", "anum_7", "anum_8", "anum_9", "anum_minus" } };
+
+ /*
+ * full screen console put up loading plaque blanked background with loading
+ * plaque blanked background with menu cinematics full screen image for quit
+ * and victory
+ *
+ * end of unit intermissions
+ */
+
+ static float scr_con_current; // aproaches scr_conlines at scr_conspeed
+
+ static float scr_conlines; // 0.0 to 1.0 lines of console to display
+
+ static boolean scr_initialized; // ready to draw
+
+ static int scr_draw_loading;
+
+ // scr_vrect ist in Globals definiert
+ // position of render window on screen
+
+ static cvar_t scr_viewsize;
+
+ static cvar_t scr_conspeed;
+
+ static cvar_t scr_centertime;
+
+ static cvar_t scr_showturtle;
+
+ static cvar_t scr_showpause;
+
+ static cvar_t scr_printspeed;
+
+ static cvar_t scr_netgraph;
+
+ static cvar_t scr_timegraph;
+
+ static cvar_t scr_debuggraph;
+
+ static cvar_t scr_graphheight;
+
+ static cvar_t scr_graphscale;
+
+ static cvar_t scr_graphshift;
+
+ static cvar_t scr_drawall;
+
+ public static cvar_t fps;
+
+ static dirty_t scr_dirty = new dirty_t();
+
+ static dirty_t[] scr_old_dirty = { new dirty_t(), new dirty_t() };
+
+ static String crosshair_pic;
+
+ static int crosshair_width, crosshair_height;
+
+ static class dirty_t {
+ int x1;
+
+ int x2;
+
+ int y1;
+
+ int y2;
+
+ void set(dirty_t src) {
+ x1 = src.x1;
+ x2 = src.x2;
+ y1 = src.y1;
+ y2 = src.y2;
+ }
+
+ void clear() {
+ x1 = x2 = y1 = y2 = 0;
+ }
+ }
+
+ /*
+ * ===============================================================================
+ *
+ * BAR GRAPHS
+ *
+ * ===============================================================================
+ */
+
+ // typedef struct
+ // {
+ // float value;
+ // int color;
+ // } graphsamp_t;
+ static class graphsamp_t {
+ float value;
+
+ int color;
+ }
+
+ static int current;
+
+ static graphsamp_t[] values = new graphsamp_t[1024];
+
+ static {
+ for (int n = 0; n < 1024; n++)
+ values[n] = new graphsamp_t();
+ }
+
+ /*
+ * ============== SCR_DebugGraph ==============
+ */
+ public static void DebugGraph(float value, int color) {
+ values[current & 1023].value = value;
+ values[current & 1023].color = color;
+ current++;
+ }
+
+ /*
+ * ============== SCR_DrawDebugGraph ==============
+ */
+ static void DrawDebugGraph() {
+ int a, x, y, w, i, h;
+ float v;
+ int color;
+
+ // draw the graph
+
+ w = scr_vrect.width;
+
+ x = scr_vrect.x;
+ y = scr_vrect.y + scr_vrect.height;
+ re.DrawFill(x, (int) (y - scr_graphheight.value), w,
+ (int) scr_graphheight.value, 8);
+
+ for (a = 0; a < w; a++) {
+ i = (current - 1 - a + 1024) & 1023;
+ v = values[i].value;
+ color = values[i].color;
+ v = v * scr_graphscale.value + scr_graphshift.value;
+
+ if (v < 0)
+ v += scr_graphheight.value
+ * (1 + (int) (-v / scr_graphheight.value));
+ h = (int) v % (int) scr_graphheight.value;
+ re.DrawFill(x + w - 1 - a, y - h, 1, h, color);
+ }
+ }
+
+ /*
+ * ===============================================================================
+ *
+ * CENTER PRINTING
+ *
+ * ===============================================================================
+ */
+
+ // char scr_centerstring[1024];
+ static String scr_centerstring;
+
+ static float scr_centertime_start; // for slow victory printing
+
+ static float scr_centertime_off;
+
+ static int scr_center_lines;
+
+ static int scr_erase_center;
+
+ /*
+ * ============== SCR_CenterPrint
+ *
+ * Called for important messages that should stay in the center of the
+ * screen for a few moments ==============
+ */
+ static void CenterPrint(String str) {
+ //char *s;
+ int s;
+ StringBuffer line = new StringBuffer(64);
+ int i, j, l;
+
+ //strncpy (scr_centerstring, str, sizeof(scr_centerstring)-1);
+ scr_centerstring = str;
+ scr_centertime_off = scr_centertime.value;
+ scr_centertime_start = cl.time;
+
+ // count the number of lines for centering
+ scr_center_lines = 1;
+ s = 0;
+ while (s < str.length()) {
+ if (str.charAt(s) == '\n')
+ scr_center_lines++;
+ s++;
+ }
+
+ // echo it to the console
+ Com
+ .Printf("\n\n\35\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\37\n\n");
+
+ s = 0;
+
+ if (str.length() != 0) {
+ do {
+ // scan the width of the line
+
+ for (l = 0; l < 40 && (l + s) < str.length(); l++)
+ if (str.charAt(s + l) == '\n' || str.charAt(s + l) == 0)
+ break;
+ for (i = 0; i < (40 - l) / 2; i++)
+ line.append(' ');
+
+ for (j = 0; j < l; j++) {
+ line.append(str.charAt(s + j));
+ }
+
+ line.append('\n');
+
+ Com.Printf(line.toString());
+
+ while (s < str.length() && str.charAt(s) != '\n')
+ s++;
+
+ if (s == str.length())
+ break;
+ s++; // skip the \n
+ } while (true);
+ }
+ Com
+ .Printf("\n\n\35\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\36\37\n\n");
+ Console.ClearNotify();
+ }
+
+ static void DrawCenterString() {
+ String cs = scr_centerstring + "\0";
+ int start;
+ int l;
+ int j;
+ int x, y;
+ int remaining;
+
+ if (cs == null)
+ return;
+ if (cs.length() == 0)
+ return;
+
+ // the finale prints the characters one at a time
+ remaining = 9999;
+
+ scr_erase_center = 0;
+ start = 0;
+
+ if (scr_center_lines <= 4)
+ y = (int) (viddef.height * 0.35);
+ else
+ y = 48;
+
+ do {
+ // scan the width of the line
+ for (l = 0; l < 40; l++)
+ if (start + l == cs.length() - 1
+ || cs.charAt(start + l) == '\n')
+ break;
+ x = (viddef.width - l * 8) / 2;
+ SCR.AddDirtyPoint(x, y);
+ for (j = 0; j < l; j++, x += 8) {
+ re.DrawChar(x, y, cs.charAt(start + j));
+ if (remaining == 0)
+ return;
+ remaining--;
+ }
+ SCR.AddDirtyPoint(x, y + 8);
+
+ y += 8;
+
+ while (start < cs.length() && cs.charAt(start) != '\n')
+ start++;
+
+ if (start == cs.length())
+ break;
+ start++; // skip the \n
+ } while (true);
+ }
+
+ static void CheckDrawCenterString() {
+ scr_centertime_off -= cls.frametime;
+
+ if (scr_centertime_off <= 0)
+ return;
+
+ DrawCenterString();
+ }
+
+ // =============================================================================
+
+ /*
+ * ================= SCR_CalcVrect
+ *
+ * Sets scr_vrect, the coordinates of the rendered window =================
+ */
+ static void CalcVrect() {
+ int size;
+
+ // bound viewsize
+ if (scr_viewsize.value < 40)
+ Cvar.Set("viewsize", "40");
+ if (scr_viewsize.value > 100)
+ Cvar.Set("viewsize", "100");
+
+ size = (int) scr_viewsize.value;
+
+ scr_vrect.width = viddef.width * size / 100;
+ scr_vrect.width &= ~7;
+
+ scr_vrect.height = viddef.height * size / 100;
+ scr_vrect.height &= ~1;
+
+ scr_vrect.x = (viddef.width - scr_vrect.width) / 2;
+ scr_vrect.y = (viddef.height - scr_vrect.height) / 2;
+ }
+
+ /*
+ * ================= SCR_SizeUp_f
+ *
+ * Keybinding command =================
+ */
+ static void SizeUp_f() {
+ Cvar.SetValue("viewsize", scr_viewsize.value + 10);
+ }
+
+ /*
+ * ================= SCR_SizeDown_f
+ *
+ * Keybinding command =================
+ */
+ static void SizeDown_f() {
+ Cvar.SetValue("viewsize", scr_viewsize.value - 10);
+ }
+
+ /*
+ * ================= SCR_Sky_f
+ *
+ * Set a specific sky and rotation speed =================
+ */
+ static void Sky_f() {
+ float rotate;
+ float[] axis = { 0, 0, 0 };
+
+ if (Cmd.Argc() < 2) {
+ Com.Printf("Usage: sky <basename> <rotate> <axis x y z>\n");
+ return;
+ }
+ if (Cmd.Argc() > 2)
+ rotate = Float.parseFloat(Cmd.Argv(2));
+ else
+ rotate = 0;
+ if (Cmd.Argc() == 6) {
+ axis[0] = Float.parseFloat(Cmd.Argv(3));
+ axis[1] = Float.parseFloat(Cmd.Argv(4));
+ axis[2] = Float.parseFloat(Cmd.Argv(5));
+ } else {
+ axis[0] = 0;
+ axis[1] = 0;
+ axis[2] = 1;
+ }
+
+ re.SetSky(Cmd.Argv(1), rotate, axis);
+ }
+
+ // ============================================================================
+
+ /*
+ * ================== SCR_Init ==================
+ */
+ static void Init() {
+ scr_viewsize = Cvar.Get("viewsize", "100", CVAR_ARCHIVE);
+ scr_conspeed = Cvar.Get("scr_conspeed", "3", 0);
+ scr_showturtle = Cvar.Get("scr_showturtle", "0", 0);
+ scr_showpause = Cvar.Get("scr_showpause", "1", 0);
+ scr_centertime = Cvar.Get("scr_centertime", "2.5", 0);
+ scr_printspeed = Cvar.Get("scr_printspeed", "8", 0);
+ scr_netgraph = Cvar.Get("netgraph", "1", 0);
+ scr_timegraph = Cvar.Get("timegraph", "1", 0);
+ scr_debuggraph = Cvar.Get("debuggraph", "1", 0);
+ scr_graphheight = Cvar.Get("graphheight", "32", 0);
+ scr_graphscale = Cvar.Get("graphscale", "1", 0);
+ scr_graphshift = Cvar.Get("graphshift", "0", 0);
+ scr_drawall = Cvar.Get("scr_drawall", "1", 0);
+ fps = Cvar.Get("fps", "0", 0);
+
+ //
+ // register our commands
+ //
+ Cmd.AddCommand("timerefresh", new xcommand_t() {
+ public void execute() {
+ TimeRefresh_f();
+ }
+ });
+ Cmd.AddCommand("loading", new xcommand_t() {
+ public void execute() {
+ Loading_f();
+ }
+ });
+ Cmd.AddCommand("sizeup", new xcommand_t() {
+ public void execute() {
+ SizeUp_f();
+ }
+ });
+ Cmd.AddCommand("sizedown", new xcommand_t() {
+ public void execute() {
+ SizeDown_f();
+ }
+ });
+ Cmd.AddCommand("sky", new xcommand_t() {
+ public void execute() {
+ Sky_f();
+ }
+ });
+
+ scr_initialized = true;
+ }
+
+ /*
+ * ============== SCR_DrawNet ==============
+ */
+ static void DrawNet() {
+ if (cls.netchan.outgoing_sequence - cls.netchan.incoming_acknowledged < CMD_BACKUP - 1)
+ return;
+
+ re.DrawPic(scr_vrect.x + 64, scr_vrect.y, "net");
+ }
+
+ /*
+ * ============== SCR_DrawPause ==============
+ */
+ static void DrawPause() {
+ Dimension dim = new Dimension();
+
+ if (scr_showpause.value == 0) // turn off for screenshots
+ return;
+
+ if (cl_paused.value == 0)
+ return;
+
+ re.DrawGetPicSize(dim, "pause");
+ re.DrawPic((viddef.width - dim.width) / 2, viddef.height / 2 + 8,
+ "pause");
+ }
+
+ /*
+ * ============== SCR_DrawLoading ==============
+ */
+ static void DrawLoading() {
+ Dimension dim = new Dimension();
+
+ if (scr_draw_loading == 0)
+ return;
+
+ scr_draw_loading = 0;
+ re.DrawGetPicSize(dim, "loading");
+ re.DrawPic((viddef.width - dim.width) / 2,
+ (viddef.height - dim.height) / 2, "loading");
+ }
+
+ // =============================================================================
+
+ /*
+ * ================== SCR_RunConsole
+ *
+ * Scroll it up or down ==================
+ */
+ static void RunConsole() {
+ // decide on the height of the console
+ if (cls.key_dest == key_console)
+ scr_conlines = 0.5f; // half screen
+ else
+ scr_conlines = 0; // none visible
+
+ if (scr_conlines < scr_con_current) {
+ scr_con_current -= scr_conspeed.value * cls.frametime;
+ if (scr_conlines > scr_con_current)
+ scr_con_current = scr_conlines;
+
+ } else if (scr_conlines > scr_con_current) {
+ scr_con_current += scr_conspeed.value * cls.frametime;
+ if (scr_conlines < scr_con_current)
+ scr_con_current = scr_conlines;
+ }
+ }
+
+ /*
+ * ================== SCR_DrawConsole ==================
+ */
+ static void DrawConsole() {
+ Console.CheckResize();
+
+ if (cls.state == ca_disconnected || cls.state == ca_connecting) { // forced
+ // full
+ // screen
+ // console
+ Console.DrawConsole(1.0f);
+ return;
+ }
+
+ if (cls.state != ca_active || !cl.refresh_prepped) { // connected, but
+ // can't render
+ Console.DrawConsole(0.5f);
+ re.DrawFill(0, viddef.height / 2, viddef.width, viddef.height / 2,
+ 0);
+ return;
+ }
+
+ if (scr_con_current != 0) {
+ Console.DrawConsole(scr_con_current);
+ } else {
+ if (cls.key_dest == key_game || cls.key_dest == key_message)
+ Console.DrawNotify(); // only draw notify in game
+ }
+ }
+
+ // =============================================================================
+
+ /*
+ * ================ SCR_BeginLoadingPlaque ================
+ */
+ public static void BeginLoadingPlaque() {
+ S.StopAllSounds();
+ cl.sound_prepped = false; // don't play ambients
+
+ if (cls.disable_screen != 0)
+ return;
+ if (developer.value != 0)
+ return;
+ if (cls.state == ca_disconnected)
+ return; // if at console, don't bring up the plaque
+ if (cls.key_dest == key_console)
+ return;
+ if (cl.cinematictime > 0)
+ scr_draw_loading = 2; // clear to balack first
+ else
+ scr_draw_loading = 1;
+
+ UpdateScreen();
+ cls.disable_screen = Sys.Milliseconds();
+ cls.disable_servercount = cl.servercount;
+ }
+
+ /*
+ * ================ SCR_EndLoadingPlaque ================
+ */
+ public static void EndLoadingPlaque() {
+ cls.disable_screen = 0;
+ Console.ClearNotify();
+ }
+
+ /*
+ * ================ SCR_Loading_f ================
+ */
+ static void Loading_f() {
+ BeginLoadingPlaque();
+ }
+
+ /*
+ * ================ SCR_TimeRefresh_f ================
+ */
+ static void TimeRefresh_f() {
+ int i;
+ int start, stop;
+ float time;
+
+ if (cls.state != ca_active)
+ return;
+
+ start = Sys.Milliseconds();
+
+ if (Cmd.Argc() == 2) { // run without page flipping
+ re.BeginFrame(0);
+ for (i = 0; i < 128; i++) {
+ cl.refdef.viewangles[1] = i / 128.0f * 360.0f;
+ re.RenderFrame(cl.refdef);
+ }
+ re.EndFrame();
+ } else {
+ for (i = 0; i < 128; i++) {
+ cl.refdef.viewangles[1] = i / 128.0f * 360.0f;
+
+ re.BeginFrame(0);
+ re.RenderFrame(cl.refdef);
+ re.EndFrame();
+ }
+ }
+
+ stop = Sys.Milliseconds();
+ time = (stop - start) / 1000.0f;
+ Com.Printf("%f seconds (%f fps)\n", new Vargs(2).add(time).add(
+ 128.0f / time));
+ }
+
+ static void DirtyScreen() {
+ AddDirtyPoint(0, 0);
+ AddDirtyPoint(viddef.width - 1, viddef.height - 1);
+ }
+
+ /*
+ * ============== SCR_TileClear
+ *
+ * Clear any parts of the tiled background that were drawn on last frame
+ * ==============
+ */
+
+ static dirty_t clear = new dirty_t();
+
+ static void TileClear() {
+ int i;
+ int top, bottom, left, right;
+ clear.clear();
+
+ if (scr_drawall.value != 0)
+ DirtyScreen(); // for power vr or broken page flippers...
+
+ if (scr_con_current == 1.0f)
+ return; // full screen console
+ if (scr_viewsize.value == 100)
+ return; // full screen rendering
+ if (cl.cinematictime > 0)
+ return; // full screen cinematic
+
+ // erase rect will be the union of the past three frames
+ // so tripple buffering works properly
+ clear.set(scr_dirty);
+ for (i = 0; i < 2; i++) {
+ if (scr_old_dirty[i].x1 < clear.x1)
+ clear.x1 = scr_old_dirty[i].x1;
+ if (scr_old_dirty[i].x2 > clear.x2)
+ clear.x2 = scr_old_dirty[i].x2;
+ if (scr_old_dirty[i].y1 < clear.y1)
+ clear.y1 = scr_old_dirty[i].y1;
+ if (scr_old_dirty[i].y2 > clear.y2)
+ clear.y2 = scr_old_dirty[i].y2;
+ }
+
+ scr_old_dirty[1].set(scr_old_dirty[0]);
+ scr_old_dirty[0].set(scr_dirty);
+
+ scr_dirty.x1 = 9999;
+ scr_dirty.x2 = -9999;
+ scr_dirty.y1 = 9999;
+ scr_dirty.y2 = -9999;
+
+ // don't bother with anything convered by the console)
+ top = (int) (scr_con_current * viddef.height);
+ if (top >= clear.y1)
+ clear.y1 = top;
+
+ if (clear.y2 <= clear.y1)
+ return; // nothing disturbed
+
+ top = scr_vrect.y;
+ bottom = top + scr_vrect.height - 1;
+ left = scr_vrect.x;
+ right = left + scr_vrect.width - 1;
+
+ if (clear.y1 < top) { // clear above view screen
+ i = clear.y2 < top - 1 ? clear.y2 : top - 1;
+ re.DrawTileClear(clear.x1, clear.y1, clear.x2 - clear.x1 + 1, i
+ - clear.y1 + 1, "backtile");
+ clear.y1 = top;
+ }
+ if (clear.y2 > bottom) { // clear below view screen
+ i = clear.y1 > bottom + 1 ? clear.y1 : bottom + 1;
+ re.DrawTileClear(clear.x1, i, clear.x2 - clear.x1 + 1, clear.y2 - i
+ + 1, "backtile");
+ clear.y2 = bottom;
+ }
+ if (clear.x1 < left) { // clear left of view screen
+ i = clear.x2 < left - 1 ? clear.x2 : left - 1;
+ re.DrawTileClear(clear.x1, clear.y1, i - clear.x1 + 1, clear.y2
+ - clear.y1 + 1, "backtile");
+ clear.x1 = left;
+ }
+ if (clear.x2 > right) { // clear left of view screen
+ i = clear.x1 > right + 1 ? clear.x1 : right + 1;
+ re.DrawTileClear(i, clear.y1, clear.x2 - i + 1, clear.y2 - clear.y1
+ + 1, "backtile");
+ clear.x2 = right;
+ }
+
+ }
+
+ // ===============================================================
+
+ static final int STAT_MINUS = 10; // num frame for '-' stats digit
+
+ static final int ICON_WIDTH = 24;
+
+ static final int ICON_HEIGHT = 24;
+
+ static final int CHAR_WIDTH = 16;
+
+ static final int ICON_SPACE = 8;
+
+ /*
+ * ================ SizeHUDString
+ *
+ * Allow embedded \n in the string ================
+ */
+ static void SizeHUDString(String string, Dimension dim) {
+ int lines, width, current;
+
+ lines = 1;
+ width = 0;
+
+ current = 0;
+ for (int i = 0; i < string.length(); i++) {
+ if (string.charAt(i) == '\n') {
+ lines++;
+ current = 0;
+ } else {
+ current++;
+ if (current > width)
+ width = current;
+ }
+
+ }
+
+ dim.width = width * 8;
+ dim.height = lines * 8;
+ }
+
+ static void DrawHUDString(String string, int x, int y, int centerwidth,
+ int xor) {
+ int margin;
+ //char line[1024];
+ StringBuffer line = new StringBuffer(1024);
+ int i;
+
+ margin = x;
+
+ for (int l = 0; l < string.length();) {
+ // scan out one line of text from the string
+ line = new StringBuffer(1024);
+ while (l < string.length() && string.charAt(l) != '\n') {
+ line.append(string.charAt(l));
+ l++;
+ }
+
+ if (centerwidth != 0)
+ x = margin + (centerwidth - line.length() * 8) / 2;
+ else
+ x = margin;
+ for (i = 0; i < line.length(); i++) {
+ re.DrawChar(x, y, line.charAt(i) ^ xor);
+ x += 8;
+ }
+ if (l < string.length()) {
+ l++; // skip the \n
+ x = margin;
+ y += 8;
+ }
+ }
+ }
+
+ /*
+ * ============== SCR_DrawField ==============
+ */
+ static void DrawField(int x, int y, int color, int width, int value) {
+ char ptr;
+ String num;
+ int l;
+ int frame;
+
+ if (width < 1)
+ return;
+
+ // draw number string
+ if (width > 5)
+ width = 5;
+
+ AddDirtyPoint(x, y);
+ AddDirtyPoint(x + width * CHAR_WIDTH + 2, y + 23);
+
+ num = "" + value;
+ l = num.length();
+ if (l > width)
+ l = width;
+ x += 2 + CHAR_WIDTH * (width - l);
+
+ ptr = num.charAt(0);
+
+ for (int i = 0; i < l; i++) {
+ ptr = num.charAt(i);
+ if (ptr == '-')
+ frame = STAT_MINUS;
+ else
+ frame = ptr - '0';
+
+ re.DrawPic(x, y, sb_nums[color][frame]);
+ x += CHAR_WIDTH;
+ }
+ }
+
+ /*
+ * =============== SCR_TouchPics
+ *
+ * Allows rendering code to cache all needed sbar graphics ===============
+ */
+ static void TouchPics() {
+ int i, j;
+
+ for (i = 0; i < 2; i++)
+ for (j = 0; j < 11; j++)
+ re.RegisterPic(sb_nums[i][j]);
+
+ if (crosshair.value != 0.0f) {
+ if (crosshair.value > 3.0f || crosshair.value < 0.0f)
+ crosshair.value = 3.0f;
+
+ crosshair_pic = "ch" + (int) crosshair.value;
+ Dimension dim = new Dimension();
+ re.DrawGetPicSize(dim, crosshair_pic);
+ crosshair_width = dim.width;
+ crosshair_height = dim.height;
+ if (crosshair_width == 0)
+ crosshair_pic = "";
+ }
+ }
+
+ /*
+ * ================ SCR_ExecuteLayoutString
+ *
+ * ================
+ */
+ static void ExecuteLayoutString(String s) {
+ int x, y;
+ int value;
+ String token;
+ int width;
+ int index;
+ clientinfo_t ci;
+
+ if (cls.state != ca_active || !cl.refresh_prepped)
+ return;
+
+ // if (!s[0])
+ if (s == null || s.length() == 0)
+ return;
+
+ x = 0;
+ y = 0;
+ width = 3;
+
+ Com.ParseHelp ph = new Com.ParseHelp(s);
+
+ while (!ph.isEof()) {
+ token = Com.Parse(ph);
+ if (token.equals("xl")) {
+ token = Com.Parse(ph);
+ x = Lib.atoi(token);
+ continue;
+ }
+ if (token.equals("xr")) {
+ token = Com.Parse(ph);
+ x = viddef.width + Lib.atoi(token);
+ continue;
+ }
+ if (token.equals("xv")) {
+ token = Com.Parse(ph);
+ x = viddef.width / 2 - 160 + Lib.atoi(token);
+ continue;
+ }
+
+ if (token.equals("yt")) {
+ token = Com.Parse(ph);
+ y = Lib.atoi(token);
+ continue;
+ }
+ if (token.equals("yb")) {
+ token = Com.Parse(ph);
+ y = viddef.height + Lib.atoi(token);
+ continue;
+ }
+ if (token.equals("yv")) {
+ token = Com.Parse(ph);
+ y = viddef.height / 2 - 120 + Lib.atoi(token);
+ continue;
+ }
+
+ if (token.equals("pic")) { // draw a pic from a stat number
+ token = Com.Parse(ph);
+ value = cl.frame.playerstate.stats[Lib.atoi(token)];
+ if (value >= MAX_IMAGES)
+ Com.Error(ERR_DROP, "Pic >= MAX_IMAGES");
+ if (cl.configstrings[CS_IMAGES + value] != null) {
+ AddDirtyPoint(x, y);
+ AddDirtyPoint(x + 23, y + 23);
+ re.DrawPic(x, y, cl.configstrings[CS_IMAGES + value]);
+ }
+ continue;
+ }
+
+ if (token.equals("client")) { // draw a deathmatch client block
+ int score, ping, time;
+
+ token = Com.Parse(ph);
+ x = viddef.width / 2 - 160 + Lib.atoi(token);
+ token = Com.Parse(ph);
+ y = viddef.height / 2 - 120 + Lib.atoi(token);
+ AddDirtyPoint(x, y);
+ AddDirtyPoint(x + 159, y + 31);
+
+ token = Com.Parse(ph);
+ value = Lib.atoi(token);
+ if (value >= MAX_CLIENTS || value < 0)
+ Com.Error(ERR_DROP, "client >= MAX_CLIENTS");
+ ci = cl.clientinfo[value];
+
+ token = Com.Parse(ph);
+ score = Lib.atoi(token);
+
+ token = Com.Parse(ph);
+ ping = Lib.atoi(token);
+
+ token = Com.Parse(ph);
+ time = Lib.atoi(token);
+
+ Console.DrawAltString(x + 32, y, ci.name);
+ Console.DrawString(x + 32, y + 8, "Score: ");
+ Console.DrawAltString(x + 32 + 7 * 8, y + 8, "" + score);
+ Console.DrawString(x + 32, y + 16, "Ping: " + ping);
+ Console.DrawString(x + 32, y + 24, "Time: " + time);
+
+ if (ci.icon == null)
+ ci = cl.baseclientinfo;
+ re.DrawPic(x, y, ci.iconname);
+ continue;
+ }
+
+ if (token.equals("ctf")) { // draw a ctf client block
+ int score, ping;
+
+ token = Com.Parse(ph);
+ x = viddef.width / 2 - 160 + Lib.atoi(token);
+ token = Com.Parse(ph);
+ y = viddef.height / 2 - 120 + Lib.atoi(token);
+ AddDirtyPoint(x, y);
+ AddDirtyPoint(x + 159, y + 31);
+
+ token = Com.Parse(ph);
+ value = Lib.atoi(token);
+ if (value >= MAX_CLIENTS || value < 0)
+ Com.Error(ERR_DROP, "client >= MAX_CLIENTS");
+ ci = cl.clientinfo[value];
+
+ token = Com.Parse(ph);
+ score = Lib.atoi(token);
+
+ token = Com.Parse(ph);
+ ping = Lib.atoi(token);
+ if (ping > 999)
+ ping = 999;
+
+ // sprintf(block, "%3d %3d %-12.12s", score, ping, ci->name);
+ String block = Com.sprintf("%3d %3d %-12.12s", new Vargs(3)
+ .add(score).add(ping).add(ci.name));
+
+ if (value == cl.playernum)
+ Console.DrawAltString(x, y, block);
+ else
+ Console.DrawString(x, y, block);
+ continue;
+ }
+
+ if (token.equals("picn")) { // draw a pic from a name
+ token = Com.Parse(ph);
+ AddDirtyPoint(x, y);
+ AddDirtyPoint(x + 23, y + 23);
+ re.DrawPic(x, y, token);
+ continue;
+ }
+
+ if (token.equals("num")) { // draw a number
+ token = Com.Parse(ph);
+ width = Lib.atoi(token);
+ token = Com.Parse(ph);
+ value = cl.frame.playerstate.stats[Lib.atoi(token)];
+ DrawField(x, y, 0, width, value);
+ continue;
+ }
+
+ if (token.equals("hnum")) { // health number
+ int color;
+
+ width = 3;
+ value = cl.frame.playerstate.stats[STAT_HEALTH];
+ if (value > 25)
+ color = 0; // green
+ else if (value > 0)
+ color = (cl.frame.serverframe >> 2) & 1; // flash
+ else
+ color = 1;
+
+ if ((cl.frame.playerstate.stats[STAT_FLASHES] & 1) != 0)
+ re.DrawPic(x, y, "field_3");
+
+ DrawField(x, y, color, width, value);
+ continue;
+ }
+
+ if (token.equals("anum")) { // ammo number
+ int color;
+
+ width = 3;
+ value = cl.frame.playerstate.stats[STAT_AMMO];
+ if (value > 5)
+ color = 0; // green
+ else if (value >= 0)
+ color = (cl.frame.serverframe >> 2) & 1; // flash
+ else
+ continue; // negative number = don't show
+
+ if ((cl.frame.playerstate.stats[STAT_FLASHES] & 4) != 0)
+ re.DrawPic(x, y, "field_3");
+
+ DrawField(x, y, color, width, value);
+ continue;
+ }
+
+ if (token.equals("rnum")) { // armor number
+ int color;
+
+ width = 3;
+ value = cl.frame.playerstate.stats[STAT_ARMOR];
+ if (value < 1)
+ continue;
+
+ color = 0; // green
+
+ if ((cl.frame.playerstate.stats[STAT_FLASHES] & 2) != 0)
+ re.DrawPic(x, y, "field_3");
+
+ DrawField(x, y, color, width, value);
+ continue;
+ }
+
+ if (token.equals("stat_string")) {
+ token = Com.Parse(ph);
+ index = Lib.atoi(token);
+ if (index < 0 || index >= MAX_CONFIGSTRINGS)
+ Com.Error(ERR_DROP, "Bad stat_string index");
+ index = cl.frame.playerstate.stats[index];
+ if (index < 0 || index >= MAX_CONFIGSTRINGS)
+ Com.Error(ERR_DROP, "Bad stat_string index");
+ Console.DrawString(x, y, cl.configstrings[index]);
+ continue;
+ }
+
+ if (token.equals("cstring")) {
+ token = Com.Parse(ph);
+ DrawHUDString(token, x, y, 320, 0);
+ continue;
+ }
+
+ if (token.equals("string")) {
+ token = Com.Parse(ph);
+ Console.DrawString(x, y, token);
+ continue;
+ }
+
+ if (token.equals("cstring2")) {
+ token = Com.Parse(ph);
+ DrawHUDString(token, x, y, 320, 0x80);
+ continue;
+ }
+
+ if (token.equals("string2")) {
+ token = Com.Parse(ph);
+ Console.DrawAltString(x, y, token);
+ continue;
+ }
+
+ if (token.equals("if")) { // draw a number
+ token = Com.Parse(ph);
+ value = cl.frame.playerstate.stats[Lib.atoi(token)];
+ if (value == 0) { // skip to endif
+ // while (s && strcmp(token, "endif") )
+ // {
+ // token = Com.Parse(ph);
+ // }
+
+ while (!ph.isEof()
+ && !(token = Com.Parse(ph)).equals("endif"))
+ ;
+
+ }
+
+ continue;
+ }
+
+ }
+ }
+
+ /*
+ * ================ SCR_DrawStats
+ *
+ * The status bar is a small layout program that is based on the stats array
+ * ================
+ */
+ static void DrawStats() {
+ //TODO:
+ SCR.ExecuteLayoutString(cl.configstrings[CS_STATUSBAR]);
+ }
+
+ /*
+ * ================ SCR_DrawLayout
+ *
+ * ================
+ */
+ static final int STAT_LAYOUTS = 13;
+
+ static void DrawLayout() {
+ if (cl.frame.playerstate.stats[STAT_LAYOUTS] != 0)
+ SCR.ExecuteLayoutString(cl.layout);
+ }
+
+ // =======================================================
+
+ /*
+ * ================== SCR_UpdateScreen
+ *
+ * This is called every frame, and can also be called explicitly to flush
+ * text to the screen. ==================
+ */
+ static void UpdateScreen2() {
+ int numframes;
+ int i;
+ float[] separation = { 0, 0 };
+
+ // if the screen is disabled (loading plaque is up, or vid mode
+ // changing)
+ // do nothing at all
+ if (cls.disable_screen != 0) {
+ if (Sys.Milliseconds() - cls.disable_screen > 120000) {
+ cls.disable_screen = 0;
+ Com.Printf("Loading plaque timed out.\n");
+ }
+ return;
+ }
+
+ if (!scr_initialized || !con.initialized)
+ return; // not initialized yet
+
+ /*
+ * * range check cl_camera_separation so we don't inadvertently fry
+ * someone's * brain
+ */
+ if (cl_stereo_separation.value > 1.0)
+ Cvar.SetValue("cl_stereo_separation", 1.0f);
+ else if (cl_stereo_separation.value < 0)
+ Cvar.SetValue("cl_stereo_separation", 0.0f);
+
+ if (cl_stereo.value != 0) {
+ numframes = 2;
+ separation[0] = -cl_stereo_separation.value / 2;
+ separation[1] = cl_stereo_separation.value / 2;
+ } else {
+ separation[0] = 0;
+ separation[1] = 0;
+ numframes = 1;
+ }
+
+ for (i = 0; i < numframes; i++) {
+ re.BeginFrame(separation[i]);
+
+ if (scr_draw_loading == 2) { // loading plaque over black screen
+ Dimension dim = new Dimension();
+
+ re.CinematicSetPalette(null);
+ scr_draw_loading = 0; // false
+ re.DrawGetPicSize(dim, "loading");
+ re.DrawPic((viddef.width - dim.width) / 2,
+ (viddef.height - dim.height) / 2, "loading");
+ }
+ // if a cinematic is supposed to be running, handle menus
+ // and console specially
+ else if (cl.cinematictime > 0) {
+ if (cls.key_dest == key_menu) {
+ if (cl.cinematicpalette_active) {
+ re.CinematicSetPalette(null);
+ cl.cinematicpalette_active = false;
+ }
+ Menu.Draw();
+ } else if (cls.key_dest == key_console) {
+ if (cl.cinematicpalette_active) {
+ re.CinematicSetPalette(null);
+ cl.cinematicpalette_active = false;
+ }
+ DrawConsole();
+ } else {
+ // TODO impl: cl_cin.c for cinematics
+ DrawCinematic();
+ }
+ } else {
+ // make sure the game palette is active
+ if (cl.cinematicpalette_active) {
+ re.CinematicSetPalette(null);
+ cl.cinematicpalette_active = false;
+ }
+
+ // do 3D refresh drawing, and then update the screen
+ CalcVrect();
+
+ // clear any dirty part of the background
+ TileClear();
+
+ V.RenderView(separation[i]);
+
+ DrawStats();
+
+ if ((cl.frame.playerstate.stats[STAT_LAYOUTS] & 1) != 0)
+ DrawLayout();
+ if ((cl.frame.playerstate.stats[STAT_LAYOUTS] & 2) != 0)
+ CL_inv.DrawInventory();
+
+ DrawNet();
+ CheckDrawCenterString();
+ DrawFPS();
+
+ //
+ // if (scr_timegraph->value)
+ // SCR_DebugGraph (cls.frametime*300, 0);
+ //
+ // if (scr_debuggraph->value || scr_timegraph->value ||
+ // scr_netgraph->value)
+ // SCR_DrawDebugGraph ();
+ //
+ DrawPause();
+ DrawConsole();
+ Menu.Draw();
+ DrawLoading();
+ }
+ }
+
+ Globals.re.EndFrame();
+ }
+
+ /*
+ * ================= SCR_DrawCrosshair =================
+ */
+ static void DrawCrosshair() {
+ if (crosshair.value == 0.0f)
+ return;
+
+ if (crosshair.modified) {
+ crosshair.modified = false;
+ SCR.TouchPics();
+ }
+
+ if (crosshair_pic.length() == 0)
+ return;
+
+ re.DrawPic(scr_vrect.x + ((scr_vrect.width - crosshair_width) >> 1),
+ scr_vrect.y + ((scr_vrect.height - crosshair_height) >> 1),
+ crosshair_pic);
+ }
+
+ private static xcommand_t updateScreenCallback = new xcommand_t() {
+ public void execute() {
+ UpdateScreen2();
+ }
+ };
+
+ // wird anstelle von der richtigen UpdateScreen benoetigt
+ public static void UpdateScreen() {
+ Globals.re.updateScreen(updateScreenCallback);
+ }
+
+ /*
+ * ================= SCR_AddDirtyPoint =================
+ */
+ static void AddDirtyPoint(int x, int y) {
+ if (x < scr_dirty.x1)
+ scr_dirty.x1 = x;
+ if (x > scr_dirty.x2)
+ scr_dirty.x2 = x;
+ if (y < scr_dirty.y1)
+ scr_dirty.y1 = y;
+ if (y > scr_dirty.y2)
+ scr_dirty.y2 = y;
+ }
+
+ private static int lastframes = 0;
+
+ private static int lasttime = 0;
+
+ private static String fpsvalue = "";
+
+ static void DrawFPS() {
+ if (fps.value > 0.0f) {
+ if (fps.modified) {
+ fps.modified = false;
+ Cvar.SetValue("cl_maxfps", 1000);
+ }
+
+ int diff = cls.realtime - lasttime;
+ if (diff > (int) (fps.value * 1000)) {
+ fpsvalue = (cls.framecount - lastframes) * 100000 / diff
+ / 100.0f + " fps";
+ lastframes = cls.framecount;
+ lasttime = cls.realtime;
+ }
+ int x = viddef.width - 8 * fpsvalue.length() - 2;
+ for (int i = 0; i < fpsvalue.length(); i++) {
+ re.DrawChar(x, 2, fpsvalue.charAt(i));
+ x += 8;
+ }
+ } else if (fps.modified) {
+ fps.modified = false;
+ Cvar.SetValue("cl_maxfps", 90);
+ }
+ }
+
+ /*
+ * =================================================================
+ *
+ * cl_cin.c
+ *
+ * Play Cinematics
+ *
+ * =================================================================
+ */
+
+ // typedef struct
+ // {
+ // byte *data;
+ // int count;
+ // } cblock_t;
+ //
+ // typedef struct
+ // {
+ // qboolean restart_sound;
+ // int s_rate;
+ // int s_width;
+ // int s_channels;
+ //
+ // int width;
+ // int height;
+ // byte *pic;
+ // byte *pic_pending;
+ //
+ // // order 1 huffman stuff
+ // int *hnodes1; // [256][256][2];
+ // int numhnodes1[256];
+ //
+ // int h_used[512];
+ // int h_count[512];
+ // } cinematics_t;
+ //
+ // cinematics_t cin;
+ //
+ // /*
+ // =================================================================
+ //
+ // PCX LOADING
+ //
+ // =================================================================
+ // */
+ //
+ //
+ // /*
+ // ==============
+ // SCR_LoadPCX
+ // ==============
+ // */
+ // void SCR_LoadPCX (char *filename, byte **pic, byte **palette, int *width,
+ // int *height)
+ // {
+ // byte *raw;
+ // pcx_t *pcx;
+ // int x, y;
+ // int len;
+ // int dataByte, runLength;
+ // byte *out, *pix;
+ //
+ // *pic = NULL;
+ //
+ // //
+ // // load the file
+ // //
+ // len = FS_LoadFile (filename, (void **)&raw);
+ // if (!raw)
+ // return; // Com_Printf ("Bad pcx file %s\n", filename);
+ //
+ // //
+ // // parse the PCX file
+ // //
+ // pcx = (pcx_t *)raw;
+ // raw = &pcx->data;
+ //
+ // if (pcx->manufacturer != 0x0a
+ // || pcx->version != 5
+ // || pcx->encoding != 1
+ // || pcx->bits_per_pixel != 8
+ // || pcx->xmax >= 640
+ // || pcx->ymax >= 480)
+ // {
+ // Com_Printf ("Bad pcx file %s\n", filename);
+ // return;
+ // }
+ //
+ // out = Z_Malloc ( (pcx->ymax+1) * (pcx->xmax+1) );
+ //
+ // *pic = out;
+ //
+ // pix = out;
+ //
+ // if (palette)
+ // {
+ // *palette = Z_Malloc(768);
+ // memcpy (*palette, (byte *)pcx + len - 768, 768);
+ // }
+ //
+ // if (width)
+ // *width = pcx->xmax+1;
+ // if (height)
+ // *height = pcx->ymax+1;
+ //
+ // for (y=0 ; y<=pcx->ymax ; y++, pix += pcx->xmax+1)
+ // {
+ // for (x=0 ; x<=pcx->xmax ; )
+ // {
+ // dataByte = *raw++;
+ //
+ // if((dataByte & 0xC0) == 0xC0)
+ // {
+ // runLength = dataByte & 0x3F;
+ // dataByte = *raw++;
+ // }
+ // else
+ // runLength = 1;
+ //
+ // while(runLength-- > 0)
+ // pix[x++] = dataByte;
+ // }
+ //
+ // }
+ //
+ // if ( raw - (byte *)pcx > len)
+ // {
+ // Com_Printf ("PCX file %s was malformed", filename);
+ // Z_Free (*pic);
+ // *pic = NULL;
+ // }
+ //
+ // FS_FreeFile (pcx);
+ // }
+ //
+ // =============================================================
+ /*
+ * ================== SCR_StopCinematic ==================
+ */
+ static void StopCinematic() {
+ cl.cinematictime = 0; // done
+ // if (cin.pic)
+ // {
+ // Z_Free (cin.pic);
+ // cin.pic = NULL;
+ // }
+ // if (cin.pic_pending)
+ // {
+ // Z_Free (cin.pic_pending);
+ // cin.pic_pending = NULL;
+ // }
+ if (cl.cinematicpalette_active) {
+ re.CinematicSetPalette(null);
+ cl.cinematicpalette_active = false;
+ }
+ // if (cl.cinematic_file)
+ // {
+ // fclose (cl.cinematic_file);
+ // cl.cinematic_file = NULL;
+ // }
+ // if (cin.hnodes1)
+ // {
+ // Z_Free (cin.hnodes1);
+ // cin.hnodes1 = NULL;
+ // }
+ //
+ // // switch back down to 11 khz sound if necessary
+ // if (cin.restart_sound)
+ // {
+ // cin.restart_sound = false;
+ // CL_Snd_Restart_f ();
+ // }
+ //
+ }
+
+ /*
+ * ==================== SCR_FinishCinematic
+ *
+ * Called when either the cinematic completes, or it is aborted
+ * ====================
+ */
+ static void FinishCinematic() {
+ // tell the server to advance to the next map / cinematic
+ MSG.WriteByte(cls.netchan.message, clc_stringcmd);
+ SZ.Print(cls.netchan.message, "nextserver " + cl.servercount + '\n');
+ }
+
+ // ==========================================================================
+
+ // /*
+ // ==================
+ // SmallestNode1
+ // ==================
+ // */
+ // int SmallestNode1 (int numhnodes)
+ // {
+ // int i;
+ // int best, bestnode;
+ //
+ // best = 99999999;
+ // bestnode = -1;
+ // for (i=0 ; i<numhnodes ; i++)
+ // {
+ // if (cin.h_used[i])
+ // continue;
+ // if (!cin.h_count[i])
+ // continue;
+ // if (cin.h_count[i] < best)
+ // {
+ // best = cin.h_count[i];
+ // bestnode = i;
+ // }
+ // }
+ //
+ // if (bestnode == -1)
+ // return -1;
+ //
+ // cin.h_used[bestnode] = true;
+ // return bestnode;
+ // }
+ //
+ //
+ // /*
+ // ==================
+ // Huff1TableInit
+ //
+ // Reads the 64k counts table and initializes the node trees
+ // ==================
+ // */
+ // void Huff1TableInit (void)
+ // {
+ // int prev;
+ // int j;
+ // int *node, *nodebase;
+ // byte counts[256];
+ // int numhnodes;
+ //
+ // cin.hnodes1 = Z_Malloc (256*256*2*4);
+ // memset (cin.hnodes1, 0, 256*256*2*4);
+ //
+ // for (prev=0 ; prev<256 ; prev++)
+ // {
+ // memset (cin.h_count,0,sizeof(cin.h_count));
+ // memset (cin.h_used,0,sizeof(cin.h_used));
+ //
+ // // read a row of counts
+ // FS_Read (counts, sizeof(counts), cl.cinematic_file);
+ // for (j=0 ; j<256 ; j++)
+ // cin.h_count[j] = counts[j];
+ //
+ // // build the nodes
+ // numhnodes = 256;
+ // nodebase = cin.hnodes1 + prev*256*2;
+ //
+ // while (numhnodes != 511)
+ // {
+ // node = nodebase + (numhnodes-256)*2;
+ //
+ // // pick two lowest counts
+ // node[0] = SmallestNode1 (numhnodes);
+ // if (node[0] == -1)
+ // break; // no more
+ //
+ // node[1] = SmallestNode1 (numhnodes);
+ // if (node[1] == -1)
+ // break;
+ //
+ // cin.h_count[numhnodes] = cin.h_count[node[0]] + cin.h_count[node[1]];
+ // numhnodes++;
+ // }
+ //
+ // cin.numhnodes1[prev] = numhnodes-1;
+ // }
+ // }
+ //
+ // /*
+ // ==================
+ // Huff1Decompress
+ // ==================
+ // */
+ // cblock_t Huff1Decompress (cblock_t in)
+ // {
+ // byte *input;
+ // byte *out_p;
+ // int nodenum;
+ // int count;
+ // cblock_t out;
+ // int inbyte;
+ // int *hnodes, *hnodesbase;
+ //// int i;
+ //
+ // // get decompressed count
+ // count = in.data[0] + (in.data[1]<<8) + (in.data[2]<<16) +
+ // (in.data[3]<<24);
+ // input = in.data + 4;
+ // out_p = out.data = Z_Malloc (count);
+ //
+ // // read bits
+ //
+ // hnodesbase = cin.hnodes1 - 256*2; // nodes 0-255 aren't stored
+ //
+ // hnodes = hnodesbase;
+ // nodenum = cin.numhnodes1[0];
+ // while (count)
+ // {
+ // inbyte = *input++;
+ // //-----------
+ // if (nodenum < 256)
+ // {
+ // hnodes = hnodesbase + (nodenum<<9);
+ // *out_p++ = nodenum;
+ // if (!--count)
+ // break;
+ // nodenum = cin.numhnodes1[nodenum];
+ // }
+ // nodenum = hnodes[nodenum*2 + (inbyte&1)];
+ // inbyte >>=1;
+ // //-----------
+ // if (nodenum < 256)
+ // {
+ // hnodes = hnodesbase + (nodenum<<9);
+ // *out_p++ = nodenum;
+ // if (!--count)
+ // break;
+ // nodenum = cin.numhnodes1[nodenum];
+ // }
+ // nodenum = hnodes[nodenum*2 + (inbyte&1)];
+ // inbyte >>=1;
+ // //-----------
+ // if (nodenum < 256)
+ // {
+ // hnodes = hnodesbase + (nodenum<<9);
+ // *out_p++ = nodenum;
+ // if (!--count)
+ // break;
+ // nodenum = cin.numhnodes1[nodenum];
+ // }
+ // nodenum = hnodes[nodenum*2 + (inbyte&1)];
+ // inbyte >>=1;
+ // //-----------
+ // if (nodenum < 256)
+ // {
+ // hnodes = hnodesbase + (nodenum<<9);
+ // *out_p++ = nodenum;
+ // if (!--count)
+ // break;
+ // nodenum = cin.numhnodes1[nodenum];
+ // }
+ // nodenum = hnodes[nodenum*2 + (inbyte&1)];
+ // inbyte >>=1;
+ // //-----------
+ // if (nodenum < 256)
+ // {
+ // hnodes = hnodesbase + (nodenum<<9);
+ // *out_p++ = nodenum;
+ // if (!--count)
+ // break;
+ // nodenum = cin.numhnodes1[nodenum];
+ // }
+ // nodenum = hnodes[nodenum*2 + (inbyte&1)];
+ // inbyte >>=1;
+ // //-----------
+ // if (nodenum < 256)
+ // {
+ // hnodes = hnodesbase + (nodenum<<9);
+ // *out_p++ = nodenum;
+ // if (!--count)
+ // break;
+ // nodenum = cin.numhnodes1[nodenum];
+ // }
+ // nodenum = hnodes[nodenum*2 + (inbyte&1)];
+ // inbyte >>=1;
+ // //-----------
+ // if (nodenum < 256)
+ // {
+ // hnodes = hnodesbase + (nodenum<<9);
+ // *out_p++ = nodenum;
+ // if (!--count)
+ // break;
+ // nodenum = cin.numhnodes1[nodenum];
+ // }
+ // nodenum = hnodes[nodenum*2 + (inbyte&1)];
+ // inbyte >>=1;
+ // //-----------
+ // if (nodenum < 256)
+ // {
+ // hnodes = hnodesbase + (nodenum<<9);
+ // *out_p++ = nodenum;
+ // if (!--count)
+ // break;
+ // nodenum = cin.numhnodes1[nodenum];
+ // }
+ // nodenum = hnodes[nodenum*2 + (inbyte&1)];
+ // inbyte >>=1;
+ // }
+ //
+ // if (input - in.data != in.count && input - in.data != in.count+1)
+ // {
+ // Com_Printf ("Decompression overread by %i", (input - in.data) -
+ // in.count);
+ // }
+ // out.count = out_p - out.data;
+ //
+ // return out;
+ // }
+ //
+ // /*
+ // ==================
+ // SCR_ReadNextFrame
+ // ==================
+ // */
+ // byte *SCR_ReadNextFrame (void)
+ // {
+ // int r;
+ // int command;
+ // byte samples[22050/14*4];
+ // byte compressed[0x20000];
+ // int size;
+ // byte *pic;
+ // cblock_t in, huf1;
+ // int start, end, count;
+ //
+ // // read the next frame
+ // r = fread (&command, 4, 1, cl.cinematic_file);
+ // if (r == 0) // we'll give it one more chance
+ // r = fread (&command, 4, 1, cl.cinematic_file);
+ //
+ // if (r != 1)
+ // return NULL;
+ // command = LittleLong(command);
+ // if (command == 2)
+ // return NULL; // last frame marker
+ //
+ // if (command == 1)
+ // { // read palette
+ // FS_Read (cl.cinematicpalette, sizeof(cl.cinematicpalette),
+ // cl.cinematic_file);
+ // cl.cinematicpalette_active=0; // dubious.... exposes an edge case
+ // }
+ //
+ // // decompress the next frame
+ // FS_Read (&size, 4, cl.cinematic_file);
+ // size = LittleLong(size);
+ // if (size > sizeof(compressed) || size < 1)
+ // Com_Error (ERR_DROP, "Bad compressed frame size");
+ // FS_Read (compressed, size, cl.cinematic_file);
+ //
+ // // read sound
+ // start = cl.cinematicframe*cin.s_rate/14;
+ // end = (cl.cinematicframe+1)*cin.s_rate/14;
+ // count = end - start;
+ //
+ // FS_Read (samples, count*cin.s_width*cin.s_channels, cl.cinematic_file);
+ //
+ // S_RawSamples (count, cin.s_rate, cin.s_width, cin.s_channels, samples);
+ //
+ // in.data = compressed;
+ // in.count = size;
+ //
+ // huf1 = Huff1Decompress (in);
+ //
+ // pic = huf1.data;
+ //
+ // cl.cinematicframe++;
+ //
+ // return pic;
+ // }
+ //
+ //
+ /*
+ * ================== SCR_RunCinematic
+ *
+ * ==================
+ */
+ static void RunCinematic() {
+ int frame;
+
+ if (cl.cinematictime <= 0) {
+ StopCinematic();
+ return;
+ }
+
+ // if (cl.cinematicframe == -1)
+ // return; // static image
+ //
+ // if (cls.key_dest != key_game)
+ // { // pause if menu or console is up
+ // cl.cinematictime = cls.realtime - cl.cinematicframe*1000/14;
+ // return;
+ // }
+ //
+ // frame = (cls.realtime - cl.cinematictime)*14.0/1000;
+ // if (frame <= cl.cinematicframe)
+ // return;
+ // if (frame > cl.cinematicframe+1)
+ // {
+ // Com_Printf ("Dropped frame: %i > %i\n", frame, cl.cinematicframe+1);
+ // cl.cinematictime = cls.realtime - cl.cinematicframe*1000/14;
+ // }
+ // if (cin.pic)
+ // Z_Free (cin.pic);
+ // cin.pic = cin.pic_pending;
+ // cin.pic_pending = NULL;
+ // cin.pic_pending = SCR_ReadNextFrame ();
+ // if (!cin.pic_pending)
+ // {
+ // SCR_StopCinematic ();
+ // SCR_FinishCinematic ();
+ // cl.cinematictime = 1; // hack to get the black screen behind loading
+ // SCR_BeginLoadingPlaque ();
+ // cl.cinematictime = 0;
+ // return;
+ // }
+ }
+
+ /*
+ * ================== SCR_DrawCinematic
+ *
+ * Returns true if a cinematic is active, meaning the view rendering should
+ * be skipped ==================
+ */
+ static boolean DrawCinematic() {
+ // if (cl.cinematictime <= 0)
+ // {
+ return false;
+ // }
+ //
+ // if (cls.key_dest == key_menu)
+ // { // blank screen and pause if menu is up
+ // re.CinematicSetPalette(NULL);
+ // cl.cinematicpalette_active = false;
+ // return true;
+ // }
+ //
+ // if (!cl.cinematicpalette_active)
+ // {
+ // re.CinematicSetPalette(cl.cinematicpalette);
+ // cl.cinematicpalette_active = true;
+ // }
+ //
+ // if (!cin.pic)
+ // return true;
+ //
+ // re.DrawStretchRaw (0, 0, viddef.width, viddef.height,
+ // cin.width, cin.height, cin.pic);
+ //
+ // return true;
+ }
+
+ /*
+ * ================== SCR_PlayCinematic
+ *
+ * ==================
+ */
+ static void PlayCinematic(String arg) {
+ // int width, height;
+ // byte *palette;
+ // char name[MAX_OSPATH], *dot;
+ // int old_khz;
+ //
+ // // make sure CD isn't playing music
+ //CDAudio.Stop();
+
+ cl.cinematicframe = 0;
+ // dot = strstr (arg, ".");
+ // if (dot && !strcmp (dot, ".pcx"))
+ // { // static pcx image
+ // Com_sprintf (name, sizeof(name), "pics/%s", arg);
+ // SCR_LoadPCX (name, &cin.pic, &palette, &cin.width, &cin.height);
+ // cl.cinematicframe = -1;
+ // cl.cinematictime = 1;
+ // SCR_EndLoadingPlaque ();
+ // cls.state = ca_active;
+ // if (!cin.pic)
+ // {
+ // Com_Printf ("%s not found.\n", name);
+ // cl.cinematictime = 0;
+ // }
+ // else
+ // {
+ // memcpy (cl.cinematicpalette, palette, sizeof(cl.cinematicpalette));
+ // Z_Free (palette);
+ // }
+ // return;
+ // }
+ //
+ // Com_sprintf (name, sizeof(name), "video/%s", arg);
+ // FS_FOpenFile (name, &cl.cinematic_file);
+ // if (!cl.cinematic_file)
+ // {
+ // Com_Error (ERR_DROP, "Cinematic %s not found.\n", name);
+ FinishCinematic();
+ cl.cinematictime = 0; // done
+ return;
+ // }
+ //
+ // SCR_EndLoadingPlaque ();
+ //
+ // cls.state = ca_active;
+ //
+ // FS_Read (&width, 4, cl.cinematic_file);
+ // FS_Read (&height, 4, cl.cinematic_file);
+ // cin.width = LittleLong(width);
+ // cin.height = LittleLong(height);
+ //
+ // FS_Read (&cin.s_rate, 4, cl.cinematic_file);
+ // cin.s_rate = LittleLong(cin.s_rate);
+ // FS_Read (&cin.s_width, 4, cl.cinematic_file);
+ // cin.s_width = LittleLong(cin.s_width);
+ // FS_Read (&cin.s_channels, 4, cl.cinematic_file);
+ // cin.s_channels = LittleLong(cin.s_channels);
+ //
+ // Huff1TableInit ();
+ //
+ // // switch up to 22 khz sound if necessary
+ // old_khz = Cvar_VariableValue ("s_khz");
+ // if (old_khz != cin.s_rate/1000)
+ // {
+ // cin.restart_sound = true;
+ // Cvar_SetValue ("s_khz", cin.s_rate/1000);
+ // CL_Snd_Restart_f ();
+ // Cvar_SetValue ("s_khz", old_khz);
+ // }
+ //
+ // cl.cinematicframe = 0;
+ // cin.pic = SCR_ReadNextFrame ();
+ // cl.cinematictime = Sys_Milliseconds ();
+ }
} \ No newline at end of file