mirror of
https://git.do.srb2.org/STJr/SRB2.git
synced 2025-01-18 07:22:28 +00:00
Allow replacing gametype data through SOC
Make other fixes
This commit is contained in:
parent
f2bbc445a0
commit
b9cab85df0
9 changed files with 524 additions and 259 deletions
|
@ -2360,7 +2360,12 @@ static void Command_Teamchange_f(void)
|
|||
if (COM_Argc() <= 1)
|
||||
{
|
||||
if (G_GametypeHasTeams())
|
||||
CONS_Printf(M_GetText("changeteam <team>: switch to a new team (%s)\n"), "team name or spectator");
|
||||
{
|
||||
if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("changeteam <team>: switch to a new team (%s)\n"), "team name or spectator");
|
||||
else
|
||||
CONS_Printf(M_GetText("changeteam <team>: switch to a new team (%s)\n"), "team name");
|
||||
}
|
||||
else if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("changeteam <team>: switch to a new team (%s)\n"), "spectator or playing");
|
||||
else
|
||||
|
@ -2370,7 +2375,7 @@ static void Command_Teamchange_f(void)
|
|||
|
||||
if (G_GametypeHasTeams())
|
||||
{
|
||||
if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0"))
|
||||
if (G_GametypeHasSpectators() && (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")))
|
||||
NetPacket.packet.newteam = 0;
|
||||
else
|
||||
{
|
||||
|
@ -2378,7 +2383,7 @@ static void Command_Teamchange_f(void)
|
|||
if (M_StringOnlyHasDigits(COM_Argv(1)))
|
||||
{
|
||||
newteam = atoi(COM_Argv(1));
|
||||
if (newteam >= teamsingame)
|
||||
if (newteam == TEAM_NONE || newteam >= teamsingame)
|
||||
newteam = MAXTEAMS;
|
||||
}
|
||||
else
|
||||
|
@ -2407,7 +2412,12 @@ static void Command_Teamchange_f(void)
|
|||
if (error)
|
||||
{
|
||||
if (G_GametypeHasTeams())
|
||||
CONS_Printf(M_GetText("changeteam <team>: switch to a new team (%s)\n"), "team name or spectator");
|
||||
{
|
||||
if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("changeteam <team>: switch to a new team (%s)\n"), "team name or spectator");
|
||||
else
|
||||
CONS_Printf(M_GetText("changeteam <team>: switch to a new team (%s)\n"), "team name");
|
||||
}
|
||||
else if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("changeteam <team>: switch to a new team (%s)\n"), "spectator or playing");
|
||||
return;
|
||||
|
@ -2466,9 +2476,14 @@ static void Command_Teamchange2_f(void)
|
|||
if (COM_Argc() <= 1)
|
||||
{
|
||||
if (G_GametypeHasTeams())
|
||||
CONS_Printf(M_GetText("changeteam <team>: switch to a new team (%s)\n"), "team name or spectator");
|
||||
{
|
||||
if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("changeteam2 <team>: switch to a new team (%s)\n"), "team name or spectator");
|
||||
else
|
||||
CONS_Printf(M_GetText("changeteam2 <team>: switch to a new team (%s)\n"), "team name");
|
||||
}
|
||||
else if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("changeteam <team>: switch to a new team (%s)\n"), "spectator or playing");
|
||||
CONS_Printf(M_GetText("changeteam2 <team>: switch to a new team (%s)\n"), "spectator or playing");
|
||||
else
|
||||
CONS_Alert(CONS_NOTICE, M_GetText("This command cannot be used in this gametype.\n"));
|
||||
return;
|
||||
|
@ -2476,7 +2491,7 @@ static void Command_Teamchange2_f(void)
|
|||
|
||||
if (G_GametypeHasTeams())
|
||||
{
|
||||
if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0"))
|
||||
if (G_GametypeHasSpectators() && (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")))
|
||||
NetPacket.packet.newteam = 0;
|
||||
else
|
||||
{
|
||||
|
@ -2484,7 +2499,7 @@ static void Command_Teamchange2_f(void)
|
|||
if (M_StringOnlyHasDigits(COM_Argv(1)))
|
||||
{
|
||||
newteam = atoi(COM_Argv(1));
|
||||
if (newteam >= teamsingame)
|
||||
if (newteam == TEAM_NONE || newteam >= teamsingame)
|
||||
newteam = MAXTEAMS;
|
||||
}
|
||||
else
|
||||
|
@ -2514,7 +2529,12 @@ static void Command_Teamchange2_f(void)
|
|||
if (error)
|
||||
{
|
||||
if (G_GametypeHasTeams())
|
||||
CONS_Printf(M_GetText("changeteam2 <team>: switch to a new team (%s)\n"), "team name or spectator");
|
||||
{
|
||||
if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("changeteam2 <team>: switch to a new team (%s)\n"), "team name or spectator");
|
||||
else
|
||||
CONS_Printf(M_GetText("changeteam2 <team>: switch to a new team (%s)\n"), "team name");
|
||||
}
|
||||
else if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("changeteam2 <team>: switch to a new team (%s)\n"), "spectator or playing");
|
||||
return;
|
||||
|
@ -2581,7 +2601,12 @@ static void Command_ServerTeamChange_f(void)
|
|||
if (G_TagGametype())
|
||||
CONS_Printf(M_GetText("serverchangeteam <playernum> <team>: switch player to a new team (%s)\n"), "it, notit, playing, or spectator");
|
||||
else if (G_GametypeHasTeams())
|
||||
CONS_Printf(M_GetText("serverchangeteam <playernum> <team>: switch player to a new team (%s)\n"), "team name or spectator");
|
||||
{
|
||||
if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("serverchangeteam <playernum> <team>: switch player to a new team (%s)\n"), "team name or spectator");
|
||||
else
|
||||
CONS_Printf(M_GetText("serverchangeteam <playernum> <team>: switch player to a new team (%s)\n"), "team name");
|
||||
}
|
||||
else if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("serverchangeteam <playernum> <team>: switch player to a new team (%s)\n"), "spectator or playing");
|
||||
else
|
||||
|
@ -2604,7 +2629,7 @@ static void Command_ServerTeamChange_f(void)
|
|||
}
|
||||
else if (G_GametypeHasTeams())
|
||||
{
|
||||
if (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0"))
|
||||
if (G_GametypeHasSpectators() && (!strcasecmp(COM_Argv(1), "spectator") || !strcasecmp(COM_Argv(1), "0")))
|
||||
NetPacket.packet.newteam = 0;
|
||||
else
|
||||
{
|
||||
|
@ -2612,7 +2637,7 @@ static void Command_ServerTeamChange_f(void)
|
|||
if (M_StringOnlyHasDigits(COM_Argv(1)))
|
||||
{
|
||||
newteam = atoi(COM_Argv(1));
|
||||
if (newteam >= teamsingame)
|
||||
if (newteam == TEAM_NONE || newteam >= teamsingame)
|
||||
newteam = MAXTEAMS;
|
||||
}
|
||||
else
|
||||
|
@ -2643,7 +2668,12 @@ static void Command_ServerTeamChange_f(void)
|
|||
if (G_TagGametype())
|
||||
CONS_Printf(M_GetText("serverchangeteam <playernum> <team>: switch player to a new team (%s)\n"), "it, notit, playing, or spectator");
|
||||
else if (G_GametypeHasTeams())
|
||||
CONS_Printf(M_GetText("serverchangeteam <playernum> <team>: switch player to a new team (%s)\n"), "team name or spectator");
|
||||
{
|
||||
if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("serverchangeteam <playernum> <team>: switch player to a new team (%s)\n"), "team name or spectator");
|
||||
else
|
||||
CONS_Printf(M_GetText("serverchangeteam <playernum> <team>: switch player to a new team (%s)\n"), "team name");
|
||||
}
|
||||
else if (G_GametypeHasSpectators())
|
||||
CONS_Printf(M_GetText("serverchangeteam <playernum> <team>: switch player to a new team (%s)\n"), "spectator or playing");
|
||||
return;
|
||||
|
|
|
@ -133,19 +133,16 @@ static inline int lib_freeslot(lua_State *L)
|
|||
}
|
||||
else if (fastcmp(type, "TEAM"))
|
||||
{
|
||||
UINT8 i;
|
||||
for (i = 0; i < MAXTEAMS; i++)
|
||||
if (!teamnames[i]) {
|
||||
CONS_Printf("Team TEAM_%s allocated.\n",word);
|
||||
teamnames[i] = Z_Malloc(strlen(word)+1, PU_STATIC, NULL);
|
||||
strcpy(teamnames[i],word);
|
||||
lua_pushinteger(L, i);
|
||||
numteams++;
|
||||
r++;
|
||||
break;
|
||||
}
|
||||
if (i == MAXTEAMS)
|
||||
if (numteams == MAXTEAMS)
|
||||
CONS_Alert(CONS_WARNING, "Ran out of free team slots!\n");
|
||||
UINT8 i = numteams;
|
||||
CONS_Printf("Team TEAM_%s allocated.\n",word);
|
||||
teamnames[i] = Z_Malloc(strlen(word)+1, PU_STATIC, NULL);
|
||||
strcpy(teamnames[i],word);
|
||||
lua_pushinteger(L, i);
|
||||
numteams++;
|
||||
r++;
|
||||
break;
|
||||
}
|
||||
else if (fastcmp(type, "SPR2"))
|
||||
{
|
||||
|
@ -578,10 +575,8 @@ static int ScanConstants(lua_State *L, boolean mathlib, const char *word)
|
|||
}
|
||||
else if (fastncmp("TEAM_",word,5)) {
|
||||
p = word+5;
|
||||
for (i = 0; i < MAXTEAMS; i++)
|
||||
for (i = 0; i < numteams; i++)
|
||||
{
|
||||
if (!teamnames[i])
|
||||
break;
|
||||
if (fastcmp(p, teamnames[i])) {
|
||||
CacheAndPushConstant(L, word, i);
|
||||
return 1;
|
||||
|
|
466
src/deh_soc.c
466
src/deh_soc.c
|
@ -475,13 +475,12 @@ void readfreeslots(MYFILE *f)
|
|||
}
|
||||
else if (fastcmp(type, "TEAM"))
|
||||
{
|
||||
for (i = 0; i < MAXTEAMS; i++)
|
||||
if (!teamnames[i]) {
|
||||
teamnames[i] = Z_Malloc(strlen(word)+1, PU_STATIC, NULL);
|
||||
strcpy(teamnames[i],word);
|
||||
numteams++;
|
||||
break;
|
||||
}
|
||||
if (numteams < MAXTEAMS)
|
||||
{
|
||||
teamnames[numteams] = Z_Malloc(strlen(word)+1, PU_STATIC, NULL);
|
||||
strcpy(teamnames[numteams],word);
|
||||
numteams++;
|
||||
}
|
||||
}
|
||||
else if (fastcmp(type, "SPR2"))
|
||||
{
|
||||
|
@ -1139,8 +1138,7 @@ void readsprite2(MYFILE *f, INT32 num)
|
|||
Z_Free(s);
|
||||
}
|
||||
|
||||
// copypasted from readPlayer :]
|
||||
void readgametype(MYFILE *f, char *gtname)
|
||||
void readgametype(MYFILE *f, INT32 num)
|
||||
{
|
||||
char *s = Z_Malloc(MAXLINELEN, PU_STATIC, NULL);
|
||||
char *word;
|
||||
|
@ -1148,25 +1146,20 @@ void readgametype(MYFILE *f, char *gtname)
|
|||
char *tmp;
|
||||
INT32 i, j;
|
||||
|
||||
INT16 newgtidx = 0;
|
||||
UINT32 newgtrules = 0;
|
||||
UINT32 newgttol = 0;
|
||||
INT32 newgtpointlimit = 0;
|
||||
INT32 newgttimelimit = 0;
|
||||
UINT8 newgtleftcolor = 0;
|
||||
UINT8 newgtrightcolor = 0;
|
||||
INT16 newgtrankingstype = -1;
|
||||
int newgtinttype = 0;
|
||||
char *gtname = gametypes[num].name;
|
||||
char gtconst[32];
|
||||
char gtdescription[441];
|
||||
char gtconst[MAXLINELEN];
|
||||
UINT8 teamcount = 0;
|
||||
|
||||
UINT8 newgtleftcolor, newgtrightcolor;
|
||||
boolean has_desc_colors[2] = { false, false };
|
||||
|
||||
UINT8 teamcount = gametypes[num].teams.num;
|
||||
UINT8 teamlist[MAXTEAMS];
|
||||
boolean has_teams = false;
|
||||
|
||||
// Empty strings.
|
||||
gtdescription[0] = '\0';
|
||||
gtconst[0] = '\0';
|
||||
|
||||
strcpy(gtdescription, "???");
|
||||
memset(gtconst, 0, sizeof(gtconst));
|
||||
memset(gtdescription, 0, sizeof(gtconst));
|
||||
memcpy(teamlist, gametypes[num].teams.list, sizeof(teamlist[0]) * teamcount);
|
||||
|
||||
do
|
||||
{
|
||||
|
@ -1221,6 +1214,212 @@ void readgametype(MYFILE *f, char *gtname)
|
|||
continue;
|
||||
}
|
||||
|
||||
word2 = strtok(NULL, " = ");
|
||||
if (word2)
|
||||
{
|
||||
if (!word2lwr)
|
||||
word2lwr = Z_Calloc(MAXLINELEN, PU_STATIC, NULL);
|
||||
strlcpy(word2lwr, word2, MAXLINELEN);
|
||||
strupr(word2);
|
||||
}
|
||||
else
|
||||
break;
|
||||
|
||||
if (word2[strlen(word2)-1] == '\n')
|
||||
word2[strlen(word2)-1] = '\0';
|
||||
if (word2lwr[strlen(word2lwr)-1] == '\n')
|
||||
word2lwr[strlen(word2lwr)-1] = '\0';
|
||||
i = atoi(word2);
|
||||
|
||||
// Name
|
||||
if (fastcmp(word, "NAME"))
|
||||
{
|
||||
Z_Free(gametypes[num].name);
|
||||
gametypes[num].name = Z_StrDup(word2lwr);
|
||||
}
|
||||
// Game type rules
|
||||
else if (fastcmp(word, "RULES"))
|
||||
{
|
||||
// GTR_
|
||||
gametypes[num].rules = (UINT32)get_number(word2);
|
||||
}
|
||||
// Identifier
|
||||
else if (fastcmp(word, "IDENTIFIER"))
|
||||
{
|
||||
// GT_
|
||||
strncpy(gtconst, word2, MAXLINELEN);
|
||||
}
|
||||
// Point and time limits
|
||||
else if (fastcmp(word, "DEFAULTPOINTLIMIT"))
|
||||
gametypes[num].pointlimit = (INT32)i;
|
||||
else if (fastcmp(word, "DEFAULTTIMELIMIT"))
|
||||
gametypes[num].timelimit = (INT32)i;
|
||||
// Level platter
|
||||
else if (fastcmp(word, "HEADERCOLOR") || fastcmp(word, "HEADERCOLOUR"))
|
||||
{
|
||||
INT32 color = (INT32)i;
|
||||
if (color >= 0 && color <= 255)
|
||||
{
|
||||
newgtleftcolor = newgtrightcolor = (UINT8)color;
|
||||
has_desc_colors[0] = has_desc_colors[1] = true;
|
||||
}
|
||||
else
|
||||
deh_warning("readgametype %d: Level platter header color %d out of range (0 - 255)", num, i);
|
||||
}
|
||||
else if (fastcmp(word, "HEADERLEFTCOLOR") || fastcmp(word, "HEADERLEFTCOLOUR"))
|
||||
{
|
||||
INT32 color = (INT32)i;
|
||||
if (color >= 0 && color <= 255)
|
||||
{
|
||||
newgtleftcolor = (UINT8)color;
|
||||
has_desc_colors[0] = true;
|
||||
}
|
||||
else
|
||||
deh_warning("readgametype %d: Level platter header left color %d out of range (0 - 255)", num, i);
|
||||
}
|
||||
else if (fastcmp(word, "HEADERRIGHTCOLOR") || fastcmp(word, "HEADERRIGHTCOLOUR"))
|
||||
{
|
||||
INT32 color = (INT32)i;
|
||||
if (color >= 0 && color < 255)
|
||||
{
|
||||
newgtrightcolor = (UINT8)color;
|
||||
has_desc_colors[1] = true;
|
||||
}
|
||||
else
|
||||
deh_warning("readgametype %d: Level platter header right color %d out of range (0 - 255)", num, i);
|
||||
}
|
||||
// Rankings type
|
||||
else if (fastcmp(word, "RANKINGTYPE"))
|
||||
{
|
||||
// Case insensitive
|
||||
gametypes[num].rankings_type = (int)get_number(word2);
|
||||
}
|
||||
// Intermission type
|
||||
else if (fastcmp(word, "INTERMISSIONTYPE"))
|
||||
{
|
||||
// Case sensitive
|
||||
gametypes[num].intermission_type = (int)get_number(word2lwr);
|
||||
}
|
||||
// Type of level
|
||||
else if (fastcmp(word, "TYPEOFLEVEL"))
|
||||
{
|
||||
if (i) // it's just a number
|
||||
gametypes[num].typeoflevel = (UINT32)i;
|
||||
else
|
||||
{
|
||||
UINT32 tol = 0;
|
||||
tmp = strtok(word2,",");
|
||||
do {
|
||||
for (i = 0; TYPEOFLEVEL[i].name; i++)
|
||||
if (fasticmp(tmp, TYPEOFLEVEL[i].name))
|
||||
break;
|
||||
if (!TYPEOFLEVEL[i].name)
|
||||
deh_warning("readgametype %d: unknown typeoflevel flag %s\n", num, tmp);
|
||||
tol |= TYPEOFLEVEL[i].flag;
|
||||
} while((tmp = strtok(NULL,",")) != NULL);
|
||||
gametypes[num].typeoflevel = tol;
|
||||
}
|
||||
}
|
||||
// Teams
|
||||
else if (fastcmp(word, "TEAMLIST"))
|
||||
{
|
||||
tmp = strtok(word2,",");
|
||||
do {
|
||||
if (teamcount == MAXTEAMS)
|
||||
{
|
||||
deh_warning("readgametype %d: too many teams\n", num);
|
||||
break;
|
||||
}
|
||||
char *tmp2 = Z_StrDup(tmp);
|
||||
strupr(tmp2);
|
||||
UINT8 team_id = get_team(tmp2);
|
||||
if (team_id != TEAM_NONE)
|
||||
{
|
||||
teamlist[teamcount++] = team_id;
|
||||
has_teams = true;
|
||||
}
|
||||
else
|
||||
deh_warning("readgametype %d: unknown team %s\n", num, tmp);
|
||||
Z_Free(tmp2);
|
||||
} while((tmp = strtok(NULL,",")) != NULL);
|
||||
}
|
||||
// This SOC probably provided gametype rules as words, instead of using the RULES keyword.
|
||||
// (For example, "NOSPECTATORSPAWN = TRUE")
|
||||
else
|
||||
{
|
||||
UINT32 wordgt = 0;
|
||||
for (j = 0; GAMETYPERULE_LIST[j]; j++)
|
||||
if (fastcmp(word, GAMETYPERULE_LIST[j])) {
|
||||
wordgt |= (1<<j);
|
||||
if (word2[0] == 'T' || word2[0] == 'Y')
|
||||
gametypes[num].rules |= wordgt;
|
||||
else if (word2[0] == 'F' || word2[0] == 'N')
|
||||
gametypes[num].rules &= ~wordgt;
|
||||
break;
|
||||
}
|
||||
if (!wordgt)
|
||||
deh_warning("readgametype %d: unknown word '%s'", num, word);
|
||||
}
|
||||
}
|
||||
} while (!myfeof(f)); // finish when the line is empty
|
||||
|
||||
// Free strings.
|
||||
Z_Free(s);
|
||||
if (word2lwr)
|
||||
Z_Free(word2lwr);
|
||||
|
||||
if (gtdescription[0])
|
||||
G_SetGametypeDescription(num, gtdescription);
|
||||
if (has_desc_colors[0])
|
||||
G_SetGametypeDescriptionLeftColor(num, newgtleftcolor);
|
||||
if (has_desc_colors[1])
|
||||
G_SetGametypeDescriptionRightColor(num, newgtrightcolor);
|
||||
|
||||
// Copy the teams
|
||||
if (has_teams)
|
||||
{
|
||||
gametypes[num].teams.num = teamcount;
|
||||
if (teamcount)
|
||||
memcpy(gametypes[num].teams.list, teamlist, sizeof(teamlist[0]) * teamcount);
|
||||
}
|
||||
|
||||
// Write the constant name.
|
||||
if (gametypes[num].constant_name == NULL)
|
||||
{
|
||||
if (gtconst[0] == '\0')
|
||||
G_AddGametypeConstant(num, gtname);
|
||||
else
|
||||
G_AddGametypeConstant(num, gtconst);
|
||||
}
|
||||
else if (gtconst[0] != '\0')
|
||||
G_AddGametypeConstant(num, gtconst);
|
||||
|
||||
// Update gametype_cons_t accordingly.
|
||||
G_UpdateGametypeSelections();
|
||||
}
|
||||
|
||||
void readteam(MYFILE *f, INT32 num)
|
||||
{
|
||||
char *s = Z_Malloc(MAXLINELEN, PU_STATIC, NULL);
|
||||
char *word;
|
||||
char *word2, *word2lwr = NULL;
|
||||
INT32 i;
|
||||
|
||||
team_t *team = &teams[num];
|
||||
|
||||
do
|
||||
{
|
||||
if (myfgets(s, MAXLINELEN, f))
|
||||
{
|
||||
if (s[0] == '\n')
|
||||
break;
|
||||
|
||||
word = strtok(s, " ");
|
||||
if (word)
|
||||
strupr(word);
|
||||
else
|
||||
break;
|
||||
|
||||
word2 = strtok(NULL, " = ");
|
||||
if (word2)
|
||||
{
|
||||
|
@ -1236,105 +1435,83 @@ void readgametype(MYFILE *f, char *gtname)
|
|||
word2[strlen(word2)-1] = '\0';
|
||||
i = atoi(word2);
|
||||
|
||||
// Game type rules
|
||||
if (fastcmp(word, "RULES"))
|
||||
if (fastcmp(word, "NAME"))
|
||||
{
|
||||
// GTR_
|
||||
newgtrules = (UINT32)get_number(word2);
|
||||
Z_Free(team->name);
|
||||
team->name = Z_StrDup(word2lwr);
|
||||
}
|
||||
// Identifier
|
||||
else if (fastcmp(word, "IDENTIFIER"))
|
||||
else if (fastcmp(word, "FLAGNAME"))
|
||||
{
|
||||
// GT_
|
||||
strncpy(gtconst, word2, MAXLINELEN);
|
||||
Z_Free(team->flag_name);
|
||||
team->flag_name = Z_StrDup(word2lwr);
|
||||
}
|
||||
// Point and time limits
|
||||
else if (fastcmp(word, "DEFAULTPOINTLIMIT"))
|
||||
newgtpointlimit = (INT32)i;
|
||||
else if (fastcmp(word, "DEFAULTTIMELIMIT"))
|
||||
newgttimelimit = (INT32)i;
|
||||
// Level platter
|
||||
else if (fastcmp(word, "HEADERCOLOR") || fastcmp(word, "HEADERCOLOUR"))
|
||||
newgtleftcolor = newgtrightcolor = (UINT8)get_number(word2);
|
||||
else if (fastcmp(word, "HEADERLEFTCOLOR") || fastcmp(word, "HEADERLEFTCOLOUR"))
|
||||
newgtleftcolor = (UINT8)get_number(word2);
|
||||
else if (fastcmp(word, "HEADERRIGHTCOLOR") || fastcmp(word, "HEADERRIGHTCOLOUR"))
|
||||
newgtrightcolor = (UINT8)get_number(word2);
|
||||
// Rankings type
|
||||
else if (fastcmp(word, "RANKINGTYPE"))
|
||||
else if (fastcmp(word, "FLAG"))
|
||||
{
|
||||
// Case insensitive
|
||||
newgtrankingstype = (int)get_number(word2);
|
||||
team->flag = (UINT16)get_number(word2);
|
||||
}
|
||||
// Intermission type
|
||||
else if (fastcmp(word, "INTERMISSIONTYPE"))
|
||||
else if (fastcmp(word, "FLAGTYPE"))
|
||||
{
|
||||
// Case sensitive
|
||||
newgtinttype = (int)get_number(word2lwr);
|
||||
}
|
||||
// Type of level
|
||||
else if (fastcmp(word, "TYPEOFLEVEL"))
|
||||
{
|
||||
if (i) // it's just a number
|
||||
newgttol = (UINT32)i;
|
||||
if (i == 0 && word2[0] != '0') // If word2 isn't a number
|
||||
i = get_mobjtype(word2); // find a thing by name
|
||||
if (i < NUMMOBJTYPES && i > 0)
|
||||
team->flag_mobj_type = i;
|
||||
else
|
||||
{
|
||||
UINT32 tol = 0;
|
||||
tmp = strtok(word2,",");
|
||||
do {
|
||||
for (i = 0; TYPEOFLEVEL[i].name; i++)
|
||||
if (fasticmp(tmp, TYPEOFLEVEL[i].name))
|
||||
break;
|
||||
if (!TYPEOFLEVEL[i].name)
|
||||
deh_warning("readgametype %s: unknown typeoflevel flag %s\n", gtname, tmp);
|
||||
tol |= TYPEOFLEVEL[i].flag;
|
||||
} while((tmp = strtok(NULL,",")) != NULL);
|
||||
newgttol = tol;
|
||||
deh_warning("readteam %d: Thing %d out of range (1 - %d)", num, i, NUMMOBJTYPES-1);
|
||||
}
|
||||
}
|
||||
// Teams
|
||||
else if (fastcmp(word, "TEAMLIST"))
|
||||
else if (fastcmp(word, "COLOR"))
|
||||
{
|
||||
tmp = strtok(word2,",");
|
||||
do {
|
||||
if (teamcount == MAXTEAMS)
|
||||
{
|
||||
deh_warning("readgametype %s: too many teams\n", gtname);
|
||||
break;
|
||||
}
|
||||
UINT8 team_id = TEAM_NONE;
|
||||
for (i = 1; i < MAXTEAMS; i++)
|
||||
{
|
||||
if (!teamnames[i])
|
||||
break;
|
||||
if (fasticmp(tmp, teamnames[i]))
|
||||
{
|
||||
team_id = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (team_id == TEAM_NONE)
|
||||
deh_warning("readgametype %s: unknown team %s\n", gtname, tmp);
|
||||
else
|
||||
{
|
||||
teamlist[teamcount++] = team_id;
|
||||
}
|
||||
} while((tmp = strtok(NULL,",")) != NULL);
|
||||
if (i == 0 && word2[0] != '0') // If word2 isn't a number
|
||||
i = get_skincolor(word2); // find a skincolor by name
|
||||
if (i && i < numskincolors)
|
||||
team->color = i;
|
||||
else
|
||||
{
|
||||
deh_warning("readteam %d: Color %d out of range (1 - %d)", num, i, numskincolors-1);
|
||||
}
|
||||
}
|
||||
else if (fastcmp(word, "WEAPONCOLOR"))
|
||||
{
|
||||
if (i == 0 && word2[0] != '0') // If word2 isn't a number
|
||||
i = get_skincolor(word2); // find a skincolor by name
|
||||
if (i && i < numskincolors)
|
||||
team->weapon_color = i;
|
||||
else
|
||||
{
|
||||
deh_warning("readteam %d: Weapon color %d out of range (1 - %d)", num, i, numskincolors-1);
|
||||
}
|
||||
}
|
||||
else if (fastcmp(word, "MISSILECOLOR"))
|
||||
{
|
||||
if (i == 0 && word2[0] != '0') // If word2 isn't a number
|
||||
i = get_skincolor(word2); // find a skincolor by name
|
||||
if (i && i < numskincolors)
|
||||
team->missile_color = i;
|
||||
else
|
||||
{
|
||||
deh_warning("readteam %d: Missile color %d out of range (1 - %d)", num, i, numskincolors-1);
|
||||
}
|
||||
}
|
||||
else if (fastcmp(word, "ICON"))
|
||||
{
|
||||
G_SetTeamIcon(num, TEAM_ICON, word2lwr);
|
||||
}
|
||||
else if (fastcmp(word, "FLAGICON"))
|
||||
{
|
||||
G_SetTeamIcon(num, TEAM_ICON_FLAG, word2lwr);
|
||||
}
|
||||
else if (fastcmp(word, "GOTFLAGICON"))
|
||||
{
|
||||
G_SetTeamIcon(num, TEAM_ICON_GOT_FLAG, word2lwr);
|
||||
}
|
||||
else if (fastcmp(word, "MISSINGFLAGICON"))
|
||||
{
|
||||
G_SetTeamIcon(num, TEAM_ICON_MISSING_FLAG, word2lwr);
|
||||
}
|
||||
// This SOC probably provided gametype rules as words, instead of using the RULES keyword.
|
||||
// (For example, "NOSPECTATORSPAWN = TRUE")
|
||||
else
|
||||
{
|
||||
UINT32 wordgt = 0;
|
||||
for (j = 0; GAMETYPERULE_LIST[j]; j++)
|
||||
if (fastcmp(word, GAMETYPERULE_LIST[j])) {
|
||||
wordgt |= (1<<j);
|
||||
if (i || word2[0] == 'T' || word2[0] == 'Y')
|
||||
newgtrules |= wordgt;
|
||||
break;
|
||||
}
|
||||
if (!wordgt)
|
||||
deh_warning("readgametype %s: unknown word '%s'", gtname, word);
|
||||
deh_warning("readteam %d: unknown word '%s'", num, word);
|
||||
}
|
||||
}
|
||||
} while (!myfeof(f)); // finish when the line is empty
|
||||
|
@ -1344,43 +1521,8 @@ void readgametype(MYFILE *f, char *gtname)
|
|||
if (word2lwr)
|
||||
Z_Free(word2lwr);
|
||||
|
||||
// Ran out of gametype slots
|
||||
if (gametypecount == NUMGAMETYPEFREESLOTS)
|
||||
{
|
||||
CONS_Alert(CONS_WARNING, "Ran out of free gametype slots!\n");
|
||||
return;
|
||||
}
|
||||
|
||||
// Add the new gametype
|
||||
newgtidx = G_AddGametype(newgtrules);
|
||||
G_AddGametypeTOL(newgtidx, newgttol);
|
||||
G_SetGametypeDescription(newgtidx, gtdescription, newgtleftcolor, newgtrightcolor);
|
||||
|
||||
// Not covered by G_AddGametype alone.
|
||||
if (newgtrankingstype == -1)
|
||||
newgtrankingstype = newgtidx;
|
||||
gametypes[newgtidx].rankings_type = newgtrankingstype;
|
||||
gametypes[newgtidx].intermission_type = newgtinttype;
|
||||
gametypes[newgtidx].pointlimit = newgtpointlimit;
|
||||
gametypes[newgtidx].timelimit = newgttimelimit;
|
||||
|
||||
// Copy the teams
|
||||
gametypes[newgtidx].teams.num = teamcount;
|
||||
if (teamcount)
|
||||
memcpy(gametypes[newgtidx].teams.list, teamlist, sizeof(teamlist[0]) * teamcount);
|
||||
|
||||
// Write the new gametype name.
|
||||
gametypes[newgtidx].name = Z_StrDup(gtname);
|
||||
|
||||
// Write the constant name.
|
||||
if (gtconst[0] == '\0')
|
||||
strncpy(gtconst, gtname, MAXLINELEN);
|
||||
G_AddGametypeConstant(newgtidx, gtconst);
|
||||
|
||||
// Update gametype_cons_t accordingly.
|
||||
G_UpdateGametypeSelections();
|
||||
|
||||
CONS_Printf("Added gametype %s\n", gametypes[newgtidx].name);
|
||||
ST_LoadTeamIcons();
|
||||
G_UpdateTeamSelection();
|
||||
}
|
||||
|
||||
void readlevelheader(MYFILE *f, INT32 num)
|
||||
|
@ -4195,6 +4337,38 @@ skincolornum_t get_skincolor(const char *word)
|
|||
return SKINCOLOR_GREEN;
|
||||
}
|
||||
|
||||
INT16 get_gametype(const char *word)
|
||||
{
|
||||
INT16 i;
|
||||
if (*word >= '0' && *word <= '9')
|
||||
return atoi(word);
|
||||
if (fastncmp("GT_",word,3))
|
||||
word += 3; // take off the GT_
|
||||
for (i = 0; i < gametypecount; i++)
|
||||
{
|
||||
if (fastcmp(word, gametypes[i].constant_name + 3))
|
||||
return i;
|
||||
}
|
||||
deh_warning("Couldn't find gametype named 'GT_%s'",word);
|
||||
return GT_COOP;
|
||||
}
|
||||
|
||||
UINT8 get_team(const char *word)
|
||||
{
|
||||
UINT8 i;
|
||||
if (*word >= '0' && *word <= '9')
|
||||
return atoi(word);
|
||||
if (fastncmp("TEAM_",word,5))
|
||||
word += 5; // take off the TEAM_
|
||||
for (i = 0; i < numteams; i++)
|
||||
{
|
||||
if (fastcmp(word, teamnames[i]))
|
||||
return i;
|
||||
}
|
||||
deh_warning("Couldn't find team named 'TEAM_%s'",word);
|
||||
return TEAM_NONE;
|
||||
}
|
||||
|
||||
spritenum_t get_sprite(const char *word)
|
||||
{ // Returns the value of SPR_ enumerations
|
||||
spritenum_t i;
|
||||
|
|
|
@ -54,9 +54,9 @@ playersprite_t get_sprite2(const char *word);
|
|||
sfxenum_t get_sfx(const char *word);
|
||||
hudnum_t get_huditem(const char *word);
|
||||
menutype_t get_menutype(const char *word);
|
||||
//INT16 get_gametype(const char *word);
|
||||
//powertype_t get_power(const char *word);
|
||||
skincolornum_t get_skincolor(const char *word);
|
||||
INT16 get_gametype(const char *word);
|
||||
UINT8 get_team(const char *word);
|
||||
|
||||
void readwipes(MYFILE *f);
|
||||
void readmaincfg(MYFILE *f);
|
||||
|
@ -71,7 +71,8 @@ void readmenu(MYFILE *f, INT32 num);
|
|||
void readtextprompt(MYFILE *f, INT32 num);
|
||||
void readcutscene(MYFILE *f, INT32 num);
|
||||
void readlevelheader(MYFILE *f, INT32 num);
|
||||
void readgametype(MYFILE *f, char *gtname);
|
||||
void readgametype(MYFILE *f, INT32 num);
|
||||
void readteam(MYFILE *f, INT32 num);
|
||||
void readsprite2(MYFILE *f, INT32 num);
|
||||
void readspriteinfo(MYFILE *f, INT32 num, boolean sprite2);
|
||||
#ifdef HWRENDER
|
||||
|
|
|
@ -172,9 +172,9 @@ static void ignorelines(MYFILE *f)
|
|||
static void DEH_LoadDehackedFile(MYFILE *f, boolean mainfile)
|
||||
{
|
||||
char *s = Z_Malloc(MAXLINELEN, PU_STATIC, NULL);
|
||||
char textline[MAXLINELEN];
|
||||
char *word;
|
||||
char *word2;
|
||||
char word2lwr[MAXLINELEN];
|
||||
INT32 i;
|
||||
|
||||
if (!deh_loaded)
|
||||
|
@ -189,7 +189,6 @@ static void DEH_LoadDehackedFile(MYFILE *f, boolean mainfile)
|
|||
while (!myfeof(f))
|
||||
{
|
||||
myfgets(s, MAXLINELEN, f);
|
||||
memcpy(textline, s, MAXLINELEN);
|
||||
if (s[0] == '\n' || s[0] == '#')
|
||||
continue;
|
||||
|
||||
|
@ -216,10 +215,14 @@ static void DEH_LoadDehackedFile(MYFILE *f, boolean mainfile)
|
|||
continue;
|
||||
}
|
||||
word2 = strtok(NULL, " ");
|
||||
word2lwr[0] = '\0';
|
||||
if (word2) {
|
||||
strcpy(word2lwr, word2);
|
||||
strupr(word2);
|
||||
if (word2[strlen(word2) - 1] == '\n')
|
||||
word2[strlen(word2) - 1] = '\0';
|
||||
if (word2lwr[strlen(word2lwr) - 1] == '\n')
|
||||
word2lwr[strlen(word2lwr) - 1] = '\0';
|
||||
i = atoi(word2);
|
||||
}
|
||||
else
|
||||
|
@ -381,33 +384,61 @@ static void DEH_LoadDehackedFile(MYFILE *f, boolean mainfile)
|
|||
}
|
||||
else if (fastcmp(word, "GAMETYPE"))
|
||||
{
|
||||
// Get the gametype name from textline
|
||||
// instead of word2, so that gametype names
|
||||
// aren't allcaps
|
||||
INT32 c;
|
||||
for (c = 0; c < MAXLINELEN; c++)
|
||||
char *gtname = NULL;
|
||||
if (word2lwr[0])
|
||||
{
|
||||
if (textline[c] == '\0')
|
||||
break;
|
||||
if (textline[c] == ' ')
|
||||
gtname = word2lwr;
|
||||
|
||||
for (size_t j = 0; j < strlen(gtname); j++)
|
||||
{
|
||||
char *gtname = (textline+c+1);
|
||||
if (gtname)
|
||||
if (gtname[j] == '\0')
|
||||
break;
|
||||
if (gtname[j] < 32 || gtname[j] == '\n')
|
||||
{
|
||||
// remove funny characters
|
||||
INT32 j;
|
||||
for (j = 0; j < (MAXLINELEN - c); j++)
|
||||
{
|
||||
if (gtname[j] == '\0')
|
||||
break;
|
||||
if (gtname[j] < 32)
|
||||
gtname[j] = '\0';
|
||||
}
|
||||
readgametype(f, gtname);
|
||||
gtname[j] = '\0';
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (!gtname || !strlen(gtname))
|
||||
{
|
||||
deh_warning("Invalid gametype name");
|
||||
ignorelines(f);
|
||||
}
|
||||
else
|
||||
{
|
||||
INT32 gametype_id = G_GetGametypeByName(gtname);
|
||||
if (gametype_id == -1)
|
||||
{
|
||||
if (!strncmp(gtname, "GT_", 3))
|
||||
gametype_id = get_gametype(gtname + 3);
|
||||
else if (gametypecount != NUMGAMETYPEFREESLOTS)
|
||||
{
|
||||
gametype_id = G_AddGametype();
|
||||
CONS_Printf("Added gametype %s\n", gtname);
|
||||
}
|
||||
else
|
||||
deh_warning("Ran out of free gametype slots");
|
||||
}
|
||||
|
||||
if (gametype_id != -1)
|
||||
readgametype(f, gametype_id);
|
||||
else
|
||||
ignorelines(f);
|
||||
}
|
||||
}
|
||||
else if (fastcmp(word, "TEAM"))
|
||||
{
|
||||
if (i == 0 && word2[0] != '0') // If word2 isn't a number
|
||||
i = get_team(word2); // find a team by name
|
||||
if (i >= 0 && i < MAXTEAMS)
|
||||
readteam(f, i);
|
||||
else
|
||||
{
|
||||
deh_warning("Team %d out of range (0 - %d)", i, MAXTEAMS);
|
||||
ignorelines(f);
|
||||
}
|
||||
}
|
||||
else if (fastcmp(word, "CUTSCENE"))
|
||||
{
|
||||
|
|
66
src/g_game.c
66
src/g_game.c
|
@ -3597,11 +3597,23 @@ void G_UpdateTeamSelection(void)
|
|||
i++;
|
||||
}
|
||||
|
||||
// If no selections were added, somehow, we add at least two fallbacks.
|
||||
if (i == 0)
|
||||
{
|
||||
dummyteam_cons_t[i].value = 0;
|
||||
dummyteam_cons_t[i].strvalue = "Spectator";
|
||||
i++;
|
||||
|
||||
dummyteam_cons_t[i].value = 1;
|
||||
dummyteam_cons_t[i].strvalue = "Playing";
|
||||
i++;
|
||||
}
|
||||
|
||||
dummyteam_cons_t[i].value = 0;
|
||||
dummyteam_cons_t[i].strvalue = NULL;
|
||||
|
||||
cv_dummyteam.defaultvalue = dummyteam_cons_t[0].strvalue;
|
||||
cv_dummyteam.value = 0;
|
||||
cv_dummyteam.value = dummyteam_cons_t[0].value;
|
||||
cv_dummyteam.string = cv_dummyteam.defaultvalue;
|
||||
}
|
||||
|
||||
|
@ -3624,15 +3636,17 @@ void G_SetGametype(INT16 gtype)
|
|||
//
|
||||
// Adds a gametype. Returns the new gametype number.
|
||||
//
|
||||
INT16 G_AddGametype(UINT32 rules)
|
||||
INT16 G_AddGametype(void)
|
||||
{
|
||||
INT16 newgtype = gametypecount;
|
||||
gametypecount++;
|
||||
|
||||
gametypes[newgtype].name = Z_StrDup("???");
|
||||
gametypes[newgtype].rules = rules;
|
||||
gametypes[newgtype].rules = 0;
|
||||
|
||||
G_UpdateGametypeSelections();
|
||||
G_SetGametypeDescription(newgtype, "???");
|
||||
G_SetGametypeDescriptionLeftColor(newgtype, 54);
|
||||
G_SetGametypeDescriptionRightColor(newgtype, 54);
|
||||
|
||||
return newgtype;
|
||||
}
|
||||
|
@ -3670,20 +3684,32 @@ void G_UpdateGametypeSelections(void)
|
|||
}
|
||||
gametype_cons_t[NUMGAMETYPES].value = 0;
|
||||
gametype_cons_t[NUMGAMETYPES].strvalue = NULL;
|
||||
|
||||
cv_newgametype.defaultvalue = gametype_cons_t[0].strvalue;
|
||||
|
||||
if (cv_newgametype.string && G_GetGametypeByName(cv_newgametype.string) == -1)
|
||||
{
|
||||
cv_newgametype.value = 0;
|
||||
cv_newgametype.string = gametype_cons_t[0].strvalue;
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// G_SetGametypeDescription
|
||||
//
|
||||
// Set a description for the specified gametype.
|
||||
// (Level platter)
|
||||
//
|
||||
void G_SetGametypeDescription(INT16 gtype, char *descriptiontext, UINT8 leftcolor, UINT8 rightcolor)
|
||||
void G_SetGametypeDescription(INT16 gtype, const char *descriptiontext)
|
||||
{
|
||||
if (descriptiontext != NULL)
|
||||
strncpy(gametypedesc[gtype].notes, descriptiontext, 441);
|
||||
gametypedesc[gtype].col[0] = leftcolor;
|
||||
gametypedesc[gtype].col[1] = rightcolor;
|
||||
if (descriptiontext)
|
||||
strlcpy(gametypedesc[gtype].notes, descriptiontext, sizeof gametypedesc[gtype].notes);
|
||||
else
|
||||
memset(gametypedesc[gtype].notes, 0, sizeof gametypedesc[gtype].notes);
|
||||
}
|
||||
|
||||
void G_SetGametypeDescriptionLeftColor(INT16 gtype, UINT8 color)
|
||||
{
|
||||
gametypedesc[gtype].col[0] = color;
|
||||
}
|
||||
|
||||
void G_SetGametypeDescriptionRightColor(INT16 gtype, UINT8 color)
|
||||
{
|
||||
gametypedesc[gtype].col[1] = color;
|
||||
}
|
||||
|
||||
tolinfo_t TYPEOFLEVEL[NUMTOLNAMES] = {
|
||||
|
@ -3732,16 +3758,6 @@ void G_AddTOL(UINT32 newtol, const char *tolname)
|
|||
TYPEOFLEVEL[i].flag = newtol;
|
||||
}
|
||||
|
||||
//
|
||||
// G_AddGametypeTOL
|
||||
//
|
||||
// Assigns a type of level to a gametype.
|
||||
//
|
||||
void G_AddGametypeTOL(INT16 gtype, UINT32 newtol)
|
||||
{
|
||||
gametypes[gtype].typeoflevel = newtol;
|
||||
}
|
||||
|
||||
//
|
||||
// G_GetGametypeByName
|
||||
//
|
||||
|
|
|
@ -193,12 +193,14 @@ void G_SaveGameOver(UINT32 slot, boolean modifylives);
|
|||
void G_SetGametype(INT16 gametype);
|
||||
void G_InitGametypes(void);
|
||||
void G_UpdateTeamSelection(void);
|
||||
INT16 G_AddGametype(UINT32 rules);
|
||||
INT16 G_AddGametype(void);
|
||||
void G_AddGametypeConstant(INT16 gtype, const char *newgtconst);
|
||||
void G_UpdateGametypeSelections(void);
|
||||
void G_AddTOL(UINT32 newtol, const char *tolname);
|
||||
void G_AddGametypeTOL(INT16 gtype, UINT32 newtol);
|
||||
void G_SetGametypeDescription(INT16 gtype, char *descriptiontext, UINT8 leftcolor, UINT8 rightcolor);
|
||||
|
||||
void G_SetGametypeDescription(INT16 gtype, const char *descriptiontext);
|
||||
void G_SetGametypeDescriptionLeftColor(INT16 gtype, UINT8 color);
|
||||
void G_SetGametypeDescriptionRightColor(INT16 gtype, UINT8 color);
|
||||
|
||||
INT32 G_GetGametypeByName(const char *gametypestr);
|
||||
boolean G_IsSpecialStage(INT32 mapnum);
|
||||
|
|
|
@ -3411,15 +3411,14 @@ static int lib_gAddGametype(lua_State *L)
|
|||
|
||||
char *gtname = NULL;
|
||||
char *gtconst = NULL;
|
||||
const char *gtdescription = NULL;
|
||||
INT16 newgtidx = 0;
|
||||
char *gtdescription = NULL;
|
||||
UINT32 newgtrules = 0;
|
||||
UINT32 newgttol = 0;
|
||||
INT32 newgtpointlimit = 0;
|
||||
INT32 newgttimelimit = 0;
|
||||
UINT8 newgtleftcolor = 0;
|
||||
UINT8 newgtrightcolor = 0;
|
||||
INT16 newgtrankingstype = -1;
|
||||
UINT8 newgtleftcolor = 54;
|
||||
UINT8 newgtrightcolor = 54;
|
||||
INT16 newgtrankingstype = RANKINGS_DEFAULT;
|
||||
int newgtinttype = 0;
|
||||
UINT8 teamcount = 0;
|
||||
UINT8 teamlist[MAXTEAMS];
|
||||
|
@ -3540,40 +3539,52 @@ static int lib_gAddGametype(lua_State *L)
|
|||
// Set defaults
|
||||
if (gtname == NULL)
|
||||
gtname = Z_StrDup("Unnamed gametype");
|
||||
if (gtdescription == NULL)
|
||||
gtdescription = Z_StrDup("???");
|
||||
|
||||
if (G_GetGametypeByName(gtname) != -1)
|
||||
{
|
||||
luaL_error(L, "gametype %s already exists", gtname);
|
||||
Z_Free(gtname);
|
||||
Z_Free(gtconst);
|
||||
Z_Free(gtdescription);
|
||||
return 0;
|
||||
}
|
||||
|
||||
// Add the new gametype
|
||||
newgtidx = G_AddGametype(newgtrules);
|
||||
G_AddGametypeTOL(newgtidx, newgttol);
|
||||
G_SetGametypeDescription(newgtidx, gtdescription, newgtleftcolor, newgtrightcolor);
|
||||
INT16 gtype = G_AddGametype();
|
||||
|
||||
// Not covered by G_AddGametype alone.
|
||||
if (newgtrankingstype == -1)
|
||||
newgtrankingstype = newgtidx;
|
||||
gametypes[newgtidx].rankings_type = newgtrankingstype;
|
||||
gametypes[newgtidx].intermission_type = newgtinttype;
|
||||
gametypes[newgtidx].pointlimit = newgtpointlimit;
|
||||
gametypes[newgtidx].timelimit = newgttimelimit;
|
||||
gametype_t *gt = &gametypes[gtype];
|
||||
|
||||
gt->name = gtname;
|
||||
|
||||
if (gtconst)
|
||||
G_AddGametypeConstant(gtype, gtconst);
|
||||
else
|
||||
G_AddGametypeConstant(gtype, gtname);
|
||||
|
||||
if (gtdescription)
|
||||
G_SetGametypeDescription(gtype, gtdescription);
|
||||
G_SetGametypeDescriptionLeftColor(gtype, newgtleftcolor);
|
||||
G_SetGametypeDescriptionRightColor(gtype, newgtrightcolor);
|
||||
|
||||
gt->rules = newgtrules;
|
||||
gt->typeoflevel = newgttol;
|
||||
gt->rankings_type = newgtrankingstype;
|
||||
gt->intermission_type = newgtinttype;
|
||||
gt->pointlimit = newgtpointlimit;
|
||||
gt->timelimit = newgttimelimit;
|
||||
|
||||
// Copy the teams
|
||||
gametypes[newgtidx].teams.num = teamcount;
|
||||
gt->teams.num = teamcount;
|
||||
if (teamcount)
|
||||
memcpy(gametypes[newgtidx].teams.list, teamlist, sizeof(teamlist[0]) * teamcount);
|
||||
memcpy(gt->teams.list, teamlist, sizeof(teamlist[0]) * teamcount);
|
||||
|
||||
// Write the new gametype name.
|
||||
gametypes[newgtidx].name = gtname;
|
||||
|
||||
// Write the constant name.
|
||||
if (gtconst == NULL)
|
||||
gtconst = gtname;
|
||||
G_AddGametypeConstant(newgtidx, gtconst);
|
||||
|
||||
// Update gametype_cons_t accordingly.
|
||||
G_UpdateGametypeSelections();
|
||||
|
||||
// done
|
||||
CONS_Printf("Added gametype %s\n", gametypes[newgtidx].name);
|
||||
CONS_Printf("Added gametype %s\n", gt->name);
|
||||
|
||||
Z_Free(gtconst);
|
||||
Z_Free(gtdescription);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -11573,7 +11573,12 @@ void P_SpawnPlayer(INT32 playernum)
|
|||
{
|
||||
// Fix stupid non spectator spectators.
|
||||
if (!p->spectator && !p->ctfteam)
|
||||
p->spectator = true;
|
||||
{
|
||||
if (G_GametypeHasSpectators())
|
||||
p->spectator = true;
|
||||
else
|
||||
p->ctfteam = 1;
|
||||
}
|
||||
|
||||
// Fix team colors.
|
||||
// This code isn't being done right somewhere else. Oh well.
|
||||
|
|
Loading…
Reference in a new issue