]> de.git.xonotic.org Git - xonotic/darkplaces.git/blobdiff - host_cmd.c
revised water shader, less refraction, more focus on reflections
[xonotic/darkplaces.git] / host_cmd.c
index f37626bd9701ea9502788374aeffda2e40961890..dbd917dc66b7909b64caa62b4bb8c1b96ba1a89c 100644 (file)
@@ -19,6 +19,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
 */
 
 #include "quakedef.h"
+#include "sv_demo.h"
 
 int current_skill;
 cvar_t sv_cheats = {0, "sv_cheats", "0", "enables cheat commands in any game, and cheat impulses in dpmod"};
@@ -46,7 +47,6 @@ void Host_Quit_f (void)
                Sys_Quit (0);
 }
 
-
 /*
 ==================
 Host_Status_f
@@ -81,6 +81,7 @@ void Host_Status_f (void)
        print ("version:  %s build %s\n", gamename, buildstring);
        print ("protocol: %i (%s)\n", Protocol_NumberForEnum(sv.protocol), Protocol_NameForEnum(sv.protocol));
        print ("map:      %s\n", sv.name);
+       print ("timing:   %s\n", Host_TimingReport());
        print ("players:  %i active (%i max)\n\n", players, svs.maxclients);
        for (j = 0, client = svs.clients;j < svs.maxclients;j++, client++)
        {
@@ -97,7 +98,7 @@ void Host_Status_f (void)
                }
                else
                        hours = 0;
-               print ("#%-3u %-16.16s^%i  %3i  %2i:%02i:%02i\n", j+1, client->name, STRING_COLOR_DEFAULT, client->frags, hours, minutes, seconds);
+               print ("#%-3u %-16.16s  %3i  %2i:%02i:%02i\n", j+1, client->name, client->frags, hours, minutes, seconds);
                print ("   %s\n", client->netconnection ? client->netconnection->address : "botclient");
        }
 }
@@ -428,33 +429,6 @@ LOAD / SAVE GAME
 
 #define        SAVEGAME_VERSION        5
 
-/*
-===============
-Host_SavegameComment
-
-Writes a SAVEGAME_COMMENT_LENGTH character comment describing the current
-===============
-*/
-void Host_SavegameComment (char *text)
-{
-       int             i;
-       char    kills[20];
-
-       for (i=0 ; i<SAVEGAME_COMMENT_LENGTH ; i++)
-               text[i] = ' ';
-       // LordHavoc: added min() to prevent overflow
-       memcpy (text, cl.levelname, min(strlen(cl.levelname), SAVEGAME_COMMENT_LENGTH));
-       sprintf (kills,"kills:%3i/%3i", cl.stats[STAT_MONSTERS], cl.stats[STAT_TOTALMONSTERS]);
-       memcpy (text+22, kills, strlen(kills));
-       // convert space to _ to make stdio happy
-       // LordHavoc: convert control characters to _ as well
-       for (i=0 ; i<SAVEGAME_COMMENT_LENGTH ; i++)
-               if (text[i] <= ' ')
-                       text[i] = '_';
-       text[SAVEGAME_COMMENT_LENGTH] = '\0';
-}
-
-
 /*
 ===============
 Host_Savegame_f
@@ -467,34 +441,29 @@ void Host_Savegame_f (void)
        int             i;
        char    comment[SAVEGAME_COMMENT_LENGTH+1];
 
-       if (cls.state != ca_connected || !sv.active)
+       if (!sv.active)
        {
-               Con_Print("Not playing a local game.\n");
+               Con_Print("Can't save - no server running.\n");
                return;
        }
 
-       if (cl.intermission)
+       if (cl.islocalgame)
        {
-               Con_Print("Can't save in intermission.\n");
-               return;
-       }
+               // singleplayer checks
+               if (cl.intermission)
+               {
+                       Con_Print("Can't save in intermission.\n");
+                       return;
+               }
 
-       for (i = 0;i < svs.maxclients;i++)
-       {
-               if (svs.clients[i].active)
+               if (svs.clients[0].active && svs.clients[0].edict->fields.server->deadflag)
                {
-                       if (i > 0)
-                       {
-                               Con_Print("Can't save multiplayer games.\n");
-                               return;
-                       }
-                       if (svs.clients[i].edict->fields.server->deadflag)
-                       {
-                               Con_Print("Can't savegame with a dead player\n");
-                               return;
-                       }
+                       Con_Print("Can't savegame with a dead player\n");
+                       return;
                }
        }
+       else
+               Con_Print("Warning: saving a multiplayer game may have strange results when restored (to properly resume, all players must join in the same player slots and then the game can be reloaded).\n");
 
        if (Cmd_Argc() != 2)
        {
@@ -519,8 +488,19 @@ void Host_Savegame_f (void)
                return;
        }
 
+       SV_VM_Begin();
+
        FS_Printf(f, "%i\n", SAVEGAME_VERSION);
-       Host_SavegameComment (comment);
+
+       memset(comment, 0, sizeof(comment));
+       sprintf(comment, "%-21s kills:%3i/%3i", PRVM_GetString(prog->edicts->fields.server->message), (int)prog->globals.server->killed_monsters, (int)prog->globals.server->total_monsters);
+       // convert space to _ to make stdio happy
+       // LordHavoc: convert control characters to _ as well
+       for (i=0 ; i<SAVEGAME_COMMENT_LENGTH ; i++)
+               if (comment[i] <= ' ')
+                       comment[i] = '_';
+       comment[SAVEGAME_COMMENT_LENGTH] = '\0';
+
        FS_Printf(f, "%s\n", comment);
        for (i=0 ; i<NUM_SPAWN_PARMS ; i++)
                FS_Printf(f, "%f\n", svs.clients[0].spawn_parms[i]);
@@ -537,8 +517,6 @@ void Host_Savegame_f (void)
                        FS_Print(f,"m\n");
        }
 
-       SV_VM_Begin();
-
        PRVM_ED_WriteGlobals (f);
        for (i=0 ; i<prog->num_edicts ; i++)
                PRVM_ED_Write (f, PRVM_EDICT_NUM(i));
@@ -725,7 +703,7 @@ void Host_Loadgame_f (void)
        SV_VM_End();
 
        // make sure we're connected to loopback
-       if (cls.state == ca_disconnected || !(cls.state == ca_connected && cls.netcon != NULL && LHNETADDRESS_GetAddressType(&cls.netcon->peeraddress) == LHNETADDRESSTYPE_LOOP))
+       if (sv.active && cls.state == ca_disconnected)
                CL_EstablishConnection("local:1");
 }
 
@@ -754,11 +732,6 @@ void Host_Name_f (void)
        else
                strlcpy (newName, Cmd_Args(), sizeof (newName));
 
-       for (i = 0, j = 0;newName[i];i++)
-               if (newName[i] != '\r' && newName[i] != '\n')
-                       newName[j++] = newName[i];
-       newName[j] = 0;
-
        if (cmd_source == src_command)
        {
                Cvar_Set ("_cl_name", newName);
@@ -776,6 +749,11 @@ void Host_Name_f (void)
        // point the string back at updateclient->name to keep it safe
        strlcpy (host_client->name, newName, sizeof (host_client->name));
 
+       for (i = 0, j = 0;host_client->name[i];i++)
+               if (host_client->name[i] != '\r' && host_client->name[i] != '\n')
+                       host_client->name[j++] = host_client->name[i];
+       host_client->name[j] = 0;
+
        COM_StringLengthNoColors(host_client->name, 0, &valid_colors);
        if(!valid_colors) // NOTE: this also proves the string is not empty, as "" is a valid colored string
        {
@@ -796,16 +774,42 @@ void Host_Name_f (void)
                }
        }
 
+       // find the last color tag offset and decide if we need to add a reset tag
+       for (i = 0, j = -1;host_client->name[i];i++)
+       {
+               if (host_client->name[i] == STRING_COLOR_TAG)
+               {
+                       if (host_client->name[i+1] >= '0' && host_client->name[i+1] <= '9')
+                       {
+                               j = i;
+                               // if this happens to be a reset  tag then we don't need one
+                               if (host_client->name[i+1] == '0' + STRING_COLOR_DEFAULT)
+                                       j = -1;
+                               i++;
+                               continue;
+                       }
+                       if (host_client->name[i+1] == STRING_COLOR_TAG)
+                       {
+                               i++;
+                               continue;
+                       }
+               }
+       }
+       // does not end in the default color string, so add it
+       if (j >= 0 && strlen(host_client->name) < sizeof(host_client->name) - 2)
+               memcpy(host_client->name + strlen(host_client->name), STRING_COLOR_DEFAULT_STR, strlen(STRING_COLOR_DEFAULT_STR) + 1);
+
        host_client->edict->fields.server->netname = PRVM_SetEngineString(host_client->name);
        if (strcmp(host_client->old_name, host_client->name))
        {
                if (host_client->spawned)
-                       SV_BroadcastPrintf("%s^%i changed name to %s\n", host_client->old_name, STRING_COLOR_DEFAULT, host_client->name);
+                       SV_BroadcastPrintf("%s changed name to %s\n", host_client->old_name, host_client->name);
                strlcpy(host_client->old_name, host_client->name, sizeof(host_client->old_name));
                // send notification to all clients
                MSG_WriteByte (&sv.reliable_datagram, svc_updatename);
                MSG_WriteByte (&sv.reliable_datagram, host_client - svs.clients);
                MSG_WriteString (&sv.reliable_datagram, host_client->name);
+               SV_WriteNetnameIntoDemo(host_client);
        }
 }
 
@@ -970,13 +974,13 @@ void Host_Say(qboolean teamonly)
        }
        // note this uses the chat prefix \001
        if (!fromServer && !teamonly)
-               dpsnprintf (text, sizeof(text), "\001%s" STRING_COLOR_DEFAULT_STR ": %s", host_client->name, p1);
+               dpsnprintf (text, sizeof(text), "\001%s: %s", host_client->name, p1);
        else if (!fromServer && teamonly)
-               dpsnprintf (text, sizeof(text), "\001(%s" STRING_COLOR_DEFAULT_STR "): %s", host_client->name, p1);
+               dpsnprintf (text, sizeof(text), "\001(%s): %s", host_client->name, p1);
        else if(*(sv_adminnick.string))
-               dpsnprintf (text, sizeof(text), "\001<%s" STRING_COLOR_DEFAULT_STR "> %s", sv_adminnick.string, p1);
+               dpsnprintf (text, sizeof(text), "\001<%s> %s", sv_adminnick.string, p1);
        else
-               dpsnprintf (text, sizeof(text), "\001<%s" STRING_COLOR_DEFAULT_STR "> %s", hostname.string, p1);
+               dpsnprintf (text, sizeof(text), "\001<%s> %s", hostname.string, p1);
        p2 = text + strlen(text);
        while ((const char *)p2 > (const char *)text && (p2[-1] == '\r' || p2[-1] == '\n' || (p2[-1] == '\"' && quoted)))
        {
@@ -1364,7 +1368,7 @@ void Host_PreSpawn_f (void)
                SZ_Write (&host_client->netconnection->message, sv.signon.data, sv.signon.cursize);
                MSG_WriteByte (&host_client->netconnection->message, svc_signonnum);
                MSG_WriteByte (&host_client->netconnection->message, 2);
-               host_client->sendsignon = true;         // send this message, this will be cleared later
+               host_client->sendsignon = 0;            // enable unlimited sends again
        }
 
        // reset the name change timer because the client will send name soon
@@ -1427,7 +1431,7 @@ void Host_Spawn_f (void)
                PRVM_ExecuteProgram (prog->globals.server->ClientConnect, "QC function ClientConnect is missing");
 
                if (svs.maxclients > 1 || cls.state == ca_dedicated)
-                       Con_Printf("%s^%i entered the game\n", host_client->name, STRING_COLOR_DEFAULT);
+                       Con_Printf("%s entered the game\n", host_client->name);
 
                PRVM_ExecuteProgram (prog->globals.server->PutClientInServer, "QC function PutClientInServer is missing");
        }
@@ -1508,7 +1512,6 @@ void Host_Spawn_f (void)
 
        MSG_WriteByte (&host_client->netconnection->message, svc_signonnum);
        MSG_WriteByte (&host_client->netconnection->message, 3);
-       host_client->sendsignon = true;         // send this message, this will be cleared later
 }
 
 /*