mirror of
https://git.do.srb2.org/KartKrew/Kart-Public.git
synced 2025-03-12 22:01:49 +00:00
I needed to commit here so I could switch branches to fix magnet hand xd
This commit is contained in:
parent
16004e5ba9
commit
fe3852f005
8 changed files with 483 additions and 40 deletions
129
src/d_netcmd.c
129
src/d_netcmd.c
|
@ -103,6 +103,10 @@ static void Skin_OnChange(void);
|
|||
static void Skin2_OnChange(void);
|
||||
static void Skin3_OnChange(void);
|
||||
static void Skin4_OnChange(void);
|
||||
static void Follower_OnChange(void);
|
||||
static void Follower2_OnChange(void);
|
||||
static void Follower3_OnChange(void);
|
||||
static void Follower4_OnChange(void);
|
||||
static void Color_OnChange(void);
|
||||
static void Color2_OnChange(void);
|
||||
static void Color3_OnChange(void);
|
||||
|
@ -268,6 +272,12 @@ consvar_t cv_skin2 = {"skin2", DEFAULTSKIN2, CV_SAVE|CV_CALL|CV_NOINIT, NULL, Sk
|
|||
consvar_t cv_skin3 = {"skin3", DEFAULTSKIN3, CV_SAVE|CV_CALL|CV_NOINIT, NULL, Skin3_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_skin4 = {"skin4", DEFAULTSKIN4, CV_SAVE|CV_CALL|CV_NOINIT, NULL, Skin4_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
// player's followers. Also saved.
|
||||
consvar_t cv_follower = {"follower", "-1", CV_SAVE|CV_CALL|CV_NOINIT, NULL, Follower_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_follower2 = {"follower2", "-1", CV_SAVE|CV_CALL|CV_NOINIT, NULL, Follower2_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_follower3 = {"follower3", "-1", CV_SAVE|CV_CALL|CV_NOINIT, NULL, Follower3_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
consvar_t cv_follower4 = {"follower4", "-1", CV_SAVE|CV_CALL|CV_NOINIT, NULL, Follower4_OnChange, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
consvar_t cv_skipmapcheck = {"skipmapcheck", "Off", CV_SAVE, CV_OnOff, NULL, 0, NULL, NULL, 0, 0, NULL};
|
||||
|
||||
INT32 cv_debug;
|
||||
|
@ -747,18 +757,22 @@ void D_RegisterClientCommands(void)
|
|||
CV_RegisterVar(&cv_playername);
|
||||
CV_RegisterVar(&cv_playercolor);
|
||||
CV_RegisterVar(&cv_skin); // r_things.c (skin NAME)
|
||||
CV_RegisterVar(&cv_follower);
|
||||
// secondary player (splitscreen)
|
||||
CV_RegisterVar(&cv_playername2);
|
||||
CV_RegisterVar(&cv_playercolor2);
|
||||
CV_RegisterVar(&cv_skin2);
|
||||
CV_RegisterVar(&cv_follower2);
|
||||
// third player
|
||||
CV_RegisterVar(&cv_playername3);
|
||||
CV_RegisterVar(&cv_playercolor3);
|
||||
CV_RegisterVar(&cv_skin3);
|
||||
CV_RegisterVar(&cv_follower3);
|
||||
// fourth player
|
||||
CV_RegisterVar(&cv_playername4);
|
||||
CV_RegisterVar(&cv_playercolor4);
|
||||
CV_RegisterVar(&cv_skin4);
|
||||
CV_RegisterVar(&cv_follower4);
|
||||
// preferred number of players
|
||||
CV_RegisterVar(&cv_splitplayers);
|
||||
|
||||
|
@ -1241,9 +1255,9 @@ static INT32 snacpending = 0, snac2pending = 0, snac3pending = 0, snac4pending =
|
|||
//
|
||||
static void SendNameAndColor(void)
|
||||
{
|
||||
XBOXSTATIC char buf[MAXPLAYERNAME+2];
|
||||
XBOXSTATIC char buf[MAXPLAYERNAME+3];
|
||||
char *p;
|
||||
|
||||
|
||||
p = buf;
|
||||
|
||||
// normal player colors
|
||||
|
@ -1268,7 +1282,8 @@ static void SendNameAndColor(void)
|
|||
|
||||
if (!strcmp(cv_playername.string, player_names[consoleplayer])
|
||||
&& cv_playercolor.value == players[consoleplayer].skincolor
|
||||
&& !strcmp(cv_skin.string, skins[players[consoleplayer].skin].name))
|
||||
&& !strcmp(cv_skin.string, skins[players[consoleplayer].skin].name)
|
||||
&& cv_follower.value == players[consoleplayer].followerskin)
|
||||
return;
|
||||
|
||||
// We'll handle it later if we're not playing.
|
||||
|
@ -1351,6 +1366,7 @@ static void SendNameAndColor(void)
|
|||
WRITESTRINGN(p, cv_playername.zstring, MAXPLAYERNAME);
|
||||
WRITEUINT8(p, (UINT8)cv_playercolor.value);
|
||||
WRITEUINT8(p, (UINT8)cv_skin.value);
|
||||
WRITESINT8(p, (UINT8)cv_follower.value);
|
||||
SendNetXCmd(XD_NAMEANDCOLOR, buf, p - buf);
|
||||
}
|
||||
|
||||
|
@ -1358,7 +1374,7 @@ static void SendNameAndColor(void)
|
|||
static void SendNameAndColor2(void)
|
||||
{
|
||||
INT32 secondplaya = -1;
|
||||
XBOXSTATIC char buf[MAXPLAYERNAME+2];
|
||||
XBOXSTATIC char buf[MAXPLAYERNAME+3];
|
||||
char *p;
|
||||
|
||||
if (splitscreen < 1 && !botingame)
|
||||
|
@ -1475,13 +1491,14 @@ static void SendNameAndColor2(void)
|
|||
WRITESTRINGN(p, cv_playername2.zstring, MAXPLAYERNAME);
|
||||
WRITEUINT8(p, (UINT8)cv_playercolor2.value);
|
||||
WRITEUINT8(p, (UINT8)cv_skin2.value);
|
||||
WRITESINT8(p, (UINT8)cv_follower2.value);
|
||||
SendNetXCmd2(XD_NAMEANDCOLOR, buf, p - buf);
|
||||
}
|
||||
|
||||
static void SendNameAndColor3(void)
|
||||
{
|
||||
INT32 thirdplaya = -1;
|
||||
XBOXSTATIC char buf[MAXPLAYERNAME+2];
|
||||
XBOXSTATIC char buf[MAXPLAYERNAME+3];
|
||||
char *p;
|
||||
|
||||
if (splitscreen < 2)
|
||||
|
@ -1590,13 +1607,14 @@ static void SendNameAndColor3(void)
|
|||
WRITESTRINGN(p, cv_playername3.zstring, MAXPLAYERNAME);
|
||||
WRITEUINT8(p, (UINT8)cv_playercolor3.value);
|
||||
WRITEUINT8(p, (UINT8)cv_skin3.value);
|
||||
WRITESINT8(p, (UINT8)cv_follower3.value);
|
||||
SendNetXCmd3(XD_NAMEANDCOLOR, buf, p - buf);
|
||||
}
|
||||
|
||||
static void SendNameAndColor4(void)
|
||||
{
|
||||
INT32 fourthplaya = -1;
|
||||
XBOXSTATIC char buf[MAXPLAYERNAME+2];
|
||||
XBOXSTATIC char buf[MAXPLAYERNAME+3];
|
||||
char *p;
|
||||
|
||||
if (splitscreen < 3)
|
||||
|
@ -1713,6 +1731,7 @@ static void SendNameAndColor4(void)
|
|||
WRITESTRINGN(p, cv_playername4.zstring, MAXPLAYERNAME);
|
||||
WRITEUINT8(p, (UINT8)cv_playercolor4.value);
|
||||
WRITEUINT8(p, (UINT8)cv_skin4.value);
|
||||
WRITESINT8(p, (UINT8)cv_follower4.value);
|
||||
SendNetXCmd4(XD_NAMEANDCOLOR, buf, p - buf);
|
||||
}
|
||||
|
||||
|
@ -1721,7 +1740,8 @@ static void Got_NameAndColor(UINT8 **cp, INT32 playernum)
|
|||
player_t *p = &players[playernum];
|
||||
char name[MAXPLAYERNAME+1];
|
||||
UINT8 color, skin;
|
||||
|
||||
SINT8 follower;
|
||||
|
||||
#ifdef PARANOIA
|
||||
if (playernum < 0 || playernum > MAXPLAYERS)
|
||||
I_Error("There is no player %d!", playernum);
|
||||
|
@ -1744,6 +1764,7 @@ static void Got_NameAndColor(UINT8 **cp, INT32 playernum)
|
|||
READSTRINGN(*cp, name, MAXPLAYERNAME);
|
||||
color = READUINT8(*cp);
|
||||
skin = READUINT8(*cp);
|
||||
follower = READSINT8(*cp);
|
||||
|
||||
// set name
|
||||
if (strcasecmp(player_names[playernum], name) != 0)
|
||||
|
@ -1802,6 +1823,9 @@ static void Got_NameAndColor(UINT8 **cp, INT32 playernum)
|
|||
}
|
||||
else
|
||||
SetPlayerSkinByNum(playernum, skin);
|
||||
|
||||
// set follower:
|
||||
SetFollower(playernum, follower);
|
||||
}
|
||||
|
||||
void SendWeaponPref(void)
|
||||
|
@ -5090,6 +5114,97 @@ static void Name4_OnChange(void)
|
|||
SendNameAndColor4();
|
||||
}
|
||||
|
||||
// sends the follower change for players
|
||||
static void Follower_OnChange(void)
|
||||
{
|
||||
if (!Playing())
|
||||
return; // do whatever you want
|
||||
|
||||
// there is a slight chance that we will actually use a string instead so...
|
||||
// let's investigate the string...
|
||||
char str[SKINNAMESIZE+1], cpy[SKINNAMESIZE+1];
|
||||
strcpy(str, cv_follower.string);
|
||||
strcpy(cpy, cv_follower.string);
|
||||
strlwr(str);
|
||||
if (!atoi(cpy)) // yep, that's a string alright...
|
||||
{
|
||||
INT32 num = R_FollowerAvailable(str);
|
||||
if (num == -1) // that's an error.
|
||||
CONS_Alert(CONS_WARNING, M_GetText("Follower '%s' not found\n"), str);
|
||||
|
||||
char set[10];
|
||||
sprintf(set, "%d", num);
|
||||
CV_StealthSet(&cv_follower, set); // set it to a number. It's easier for us to send later :)
|
||||
}
|
||||
SendNameAndColor();
|
||||
}
|
||||
|
||||
static void Follower2_OnChange(void)
|
||||
{
|
||||
if (!Playing() || !splitscreen)
|
||||
return; // do whatever you want
|
||||
|
||||
char str[SKINNAMESIZE+1], cpy[SKINNAMESIZE+1];
|
||||
strcpy(str, cv_follower2.string);
|
||||
strcpy(cpy, cv_follower2.string);
|
||||
strlwr(str);
|
||||
if (!atoi(cpy)) // yep, that's a string alright...
|
||||
{
|
||||
INT32 num = R_FollowerAvailable(str);
|
||||
if (num == -1) // that's an error.
|
||||
CONS_Alert(CONS_WARNING, M_GetText("Follower '%s' not found\n"), str);
|
||||
|
||||
char set[10];
|
||||
sprintf(set, "%d", num);
|
||||
CV_StealthSet(&cv_follower2, set); // set it to a number. It's easier for us to send later :)
|
||||
}
|
||||
SendNameAndColor2();
|
||||
}
|
||||
|
||||
static void Follower3_OnChange(void)
|
||||
{
|
||||
if (!Playing() || !splitscreen)
|
||||
return; // do whatever you want
|
||||
|
||||
char str[SKINNAMESIZE+1], cpy[SKINNAMESIZE+1];
|
||||
strcpy(str, cv_follower3.string);
|
||||
strcpy(cpy, cv_follower3.string);
|
||||
strlwr(str);
|
||||
if (!atoi(cpy)) // yep, that's a string alright...
|
||||
{
|
||||
INT32 num = R_FollowerAvailable(str);
|
||||
if (num == -1) // that's an error.
|
||||
CONS_Alert(CONS_WARNING, M_GetText("Follower '%s' not found\n"), str);
|
||||
|
||||
char set[10];
|
||||
sprintf(set, "%d", num);
|
||||
CV_StealthSet(&cv_follower3, set); // set it to a number. It's easier for us to send later :)
|
||||
}
|
||||
SendNameAndColor3();
|
||||
}
|
||||
|
||||
static void Follower4_OnChange(void)
|
||||
{
|
||||
if (!Playing() || !splitscreen)
|
||||
return; // do whatever you want
|
||||
|
||||
char str[SKINNAMESIZE+1], cpy[SKINNAMESIZE+1];
|
||||
strcpy(str, cv_follower4.string);
|
||||
strcpy(cpy, cv_follower4.string);
|
||||
strlwr(str);
|
||||
if (!atoi(cpy)) // yep, that's a string alright...
|
||||
{
|
||||
INT32 num = R_FollowerAvailable(str);
|
||||
if (num == -1) // that's an error.
|
||||
CONS_Alert(CONS_WARNING, M_GetText("Follower '%s' not found\n"), str);
|
||||
|
||||
char set[10];
|
||||
sprintf(set, "%d", num);
|
||||
CV_StealthSet(&cv_follower4, set); // set it to a number. It's easier for us to send later :)
|
||||
}
|
||||
SendNameAndColor4();
|
||||
}
|
||||
|
||||
/** Sends a skin change for the console player, unless that player is moving.
|
||||
* \sa cv_skin, Skin2_OnChange, Color_OnChange
|
||||
* \author Graue <graue@oceanbase.org>
|
||||
|
|
|
@ -21,18 +21,22 @@
|
|||
extern consvar_t cv_playername;
|
||||
extern consvar_t cv_playercolor;
|
||||
extern consvar_t cv_skin;
|
||||
extern consvar_t cv_follower;
|
||||
// secondary splitscreen player
|
||||
extern consvar_t cv_playername2;
|
||||
extern consvar_t cv_playercolor2;
|
||||
extern consvar_t cv_skin2;
|
||||
extern consvar_t cv_follower2;
|
||||
// third splitscreen player
|
||||
extern consvar_t cv_playername3;
|
||||
extern consvar_t cv_playercolor3;
|
||||
extern consvar_t cv_skin3;
|
||||
extern consvar_t cv_follower3;
|
||||
// fourth splitscreen player
|
||||
extern consvar_t cv_playername4;
|
||||
extern consvar_t cv_playercolor4;
|
||||
extern consvar_t cv_skin4;
|
||||
extern consvar_t cv_follower4;
|
||||
// preferred number of players
|
||||
extern consvar_t cv_splitplayers;
|
||||
|
||||
|
|
|
@ -445,6 +445,7 @@ typedef struct player_s
|
|||
UINT8 kartspeed; // Kart speed stat between 1 and 9
|
||||
UINT8 kartweight; // Kart weight stat between 1 and 9
|
||||
|
||||
INT32 followerskin; // Kart: This player's follower "skin"
|
||||
mobj_t *follower; // Kart: This is the follower object we have. (If any)
|
||||
|
||||
//
|
||||
|
|
145
src/dehacked.c
145
src/dehacked.c
|
@ -699,18 +699,21 @@ INT32 numfollowers = 0;
|
|||
|
||||
static void readfollower(MYFILE *f)
|
||||
{
|
||||
|
||||
|
||||
if (numfollowers > MAXSKINS)
|
||||
{
|
||||
CONS_Printf("Error: Too many followers, cannot add anymore.\n");
|
||||
{
|
||||
deh_warning("Error: Too many followers, cannot add anymore.\n");
|
||||
return;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
char *s = Z_Malloc(MAXLINELEN, PU_STATIC, NULL);
|
||||
char *word, *word2;
|
||||
char *word, *word2, *dname = malloc(SKINNAMESIZE+1);
|
||||
char *tmp;
|
||||
|
||||
CONS_Printf("Adding follower, please bear with me...\n");
|
||||
|
||||
boolean nameset;
|
||||
INT32 fallbackstate = 0;
|
||||
|
||||
CONS_Printf("Adding follower...\n");
|
||||
|
||||
do
|
||||
{
|
||||
|
@ -732,14 +735,20 @@ static void readfollower(MYFILE *f)
|
|||
break;
|
||||
|
||||
word2 = strtok(NULL, " = ");
|
||||
if (word2)
|
||||
strupr(word2);
|
||||
else
|
||||
|
||||
if (!word2)
|
||||
break;
|
||||
|
||||
if (word2[strlen(word2)-1] == '\n')
|
||||
word2[strlen(word2)-1] = '\0';
|
||||
|
||||
if (fastcmp(word, "ATANGLE"))
|
||||
if (fastcmp(word, "NAME"))
|
||||
{
|
||||
DEH_WriteUndoline(word, va("%s", followers[numfollowers].name), UNDO_NONE);
|
||||
strcpy(followers[numfollowers].name, word2);
|
||||
nameset = true;
|
||||
}
|
||||
else if (fastcmp(word, "ATANGLE"))
|
||||
{
|
||||
DEH_WriteUndoline(word, va("%d", followers[numfollowers].atangle), UNDO_NONE);
|
||||
followers[numfollowers].atangle = (INT32)atoi(word2);
|
||||
|
@ -749,15 +758,105 @@ static void readfollower(MYFILE *f)
|
|||
DEH_WriteUndoline(word, va("%d", followers[numfollowers].zoffs), UNDO_NONE);
|
||||
followers[numfollowers].zoffs = (INT32)atoi(word2);
|
||||
}
|
||||
else if (fastcmp(word, "IDLESTATE"))
|
||||
{
|
||||
if (word2)
|
||||
strupr(word2);
|
||||
DEH_WriteUndoline(word, va("%d", followers[numfollowers].idlestate), UNDO_NONE);
|
||||
followers[numfollowers].idlestate = get_number(word2);
|
||||
fallbackstate = followers[numfollowers].idlestate;
|
||||
}
|
||||
else if (fastcmp(word, "FOLLOWSTATE"))
|
||||
{
|
||||
if (word2)
|
||||
strupr(word2);
|
||||
DEH_WriteUndoline(word, va("%d", followers[numfollowers].followstate), UNDO_NONE);
|
||||
followers[numfollowers].followstate = get_number(word2);
|
||||
}
|
||||
else if (fastcmp(word, "HURTSTATE"))
|
||||
{
|
||||
if (word2)
|
||||
strupr(word2);
|
||||
DEH_WriteUndoline(word, va("%d", followers[numfollowers].hurtstate), UNDO_NONE);
|
||||
followers[numfollowers].hurtstate = get_number(word2);
|
||||
}
|
||||
else if (fastcmp(word, "LOSESTATE"))
|
||||
{
|
||||
if (word2)
|
||||
strupr(word2);
|
||||
DEH_WriteUndoline(word, va("%d", followers[numfollowers].losestate), UNDO_NONE);
|
||||
followers[numfollowers].losestate = get_number(word2);
|
||||
}
|
||||
else if (fastcmp(word, "WINSTATE"))
|
||||
{
|
||||
if (word2)
|
||||
strupr(word2);
|
||||
DEH_WriteUndoline(word, va("%d", followers[numfollowers].winstate), UNDO_NONE);
|
||||
followers[numfollowers].winstate = get_number(word2);
|
||||
}
|
||||
else
|
||||
deh_warning("Follower %d: unknown word '%s'", numfollowers, word);
|
||||
}
|
||||
} while (!myfeof(f)); // finish when the line is empty
|
||||
|
||||
CONS_Printf("We are done adding the follower.\n");
|
||||
numfollowers++;
|
||||
Z_Free(s);
|
||||
}
|
||||
|
||||
if (!nameset) // well this is problematic.
|
||||
{
|
||||
strcpy(followers[numfollowers].name, va("Follower%d", numfollowers)); // this is lazy, so what
|
||||
}
|
||||
|
||||
// set skin name (this is just the follower's name in lowercases):
|
||||
// but before we do, let's... actually check if another follower isn't doing the same shit...
|
||||
|
||||
char testname[SKINNAMESIZE];
|
||||
strcpy(testname, followers[numfollowers].name);
|
||||
|
||||
// lower testname for skin checks...
|
||||
strlwr(testname);
|
||||
INT32 res = R_FollowerAvailable(testname);
|
||||
if (res > -1) // yikes, someone else has stolen our name already
|
||||
{
|
||||
deh_warning("There was already a follower with the same name. (%s)", testname);
|
||||
INT32 startlen = strlen(testname);
|
||||
char cpy[2];
|
||||
sprintf(cpy, "%d", numfollowers);
|
||||
memcpy(&testname[startlen], cpy, 2);
|
||||
// in that case, we'll be very lazy and copy numfollowers to the end of our skin name.
|
||||
}
|
||||
|
||||
strcpy(followers[numfollowers].skinname, testname);
|
||||
|
||||
// get ready to print the name...
|
||||
strcpy(dname, followers[numfollowers].skinname);
|
||||
|
||||
// check for atangle and zoffs. But don't error if they aren't set, just give them logical values.
|
||||
if (!followers[numfollowers].atangle && followers[numfollowers].atangle != 0)
|
||||
followers[numfollowers].atangle = 300;
|
||||
|
||||
if ((!followers[numfollowers].zoffs || followers[numfollowers].zoffs < 0) && followers[numfollowers].zoffs != 0) // yikes, no offset or negative offset
|
||||
followers[numfollowers].zoffs = 64;
|
||||
|
||||
|
||||
// also check if we forgot states :V
|
||||
#define NOSTATE(field, field2) \
|
||||
if (!followers[numfollowers].field) \
|
||||
{ \
|
||||
followers[numfollowers].field = fallbackstate ? fallbackstate : S_INVISIBLE; \
|
||||
if (!fallbackstate) \
|
||||
deh_warning("Follower %s is missing state definition for %s, no idlestate fallback was found", dname, field2); \
|
||||
} \
|
||||
|
||||
NOSTATE(idlestate, "idlestate");
|
||||
NOSTATE(followstate, "followstate");
|
||||
NOSTATE(hurtstate, "hurtstate");
|
||||
NOSTATE(losestate, "losestate");
|
||||
NOSTATE(winstate, "winstate");
|
||||
#undef NOSTATE
|
||||
|
||||
CONS_Printf("Added follower '%s'\n", dname);
|
||||
numfollowers++; // add 1 follower
|
||||
free(dname); // free name memory
|
||||
Z_Free(s);
|
||||
}
|
||||
|
||||
static void readthing(MYFILE *f, INT32 num)
|
||||
{
|
||||
|
@ -3508,6 +3607,13 @@ static void DEH_LoadDehackedFile(MYFILE *f, UINT16 wad)
|
|||
// This is not a major mod.
|
||||
continue;
|
||||
}
|
||||
else if (fastcmp(word, "FOLLOWER"))
|
||||
{
|
||||
readfollower(f); // at the same time this will be our only way to ADD followers for now. Yikes.
|
||||
DEH_WriteUndoline(word, "", UNDO_HEADER);
|
||||
// This is not a major mod either.
|
||||
continue; // continue so that we don't error.
|
||||
}
|
||||
word2 = strtok(NULL, " ");
|
||||
if (fastcmp(word, "CHARACTER"))
|
||||
{
|
||||
|
@ -3549,11 +3655,6 @@ static void DEH_LoadDehackedFile(MYFILE *f, UINT16 wad)
|
|||
DEH_WriteUndoline(word, word2, UNDO_HEADER);
|
||||
// This is not a major mod.
|
||||
}
|
||||
else if (fastcmp(word, "FOLLOWER"))
|
||||
{
|
||||
readfollower(f); // at the same time this will be our only way to ADD followers for now. Yikes.
|
||||
DEH_WriteUndoline(word, word2, UNDO_HEADER);
|
||||
}
|
||||
else if (fastcmp(word, "THING") || fastcmp(word, "MOBJ") || fastcmp(word, "OBJECT"))
|
||||
{
|
||||
if (i == 0 && word2[0] != '0') // If word2 isn't a number
|
||||
|
|
|
@ -140,7 +140,7 @@
|
|||
extern FILE *logstream;
|
||||
#endif
|
||||
|
||||
#define DEVELOP // Disable this for release builds to remove excessive cheat commands and enable MD5 checking and stuff, all in one go. :3
|
||||
//#define DEVELOP // Disable this for release builds to remove excessive cheat commands and enable MD5 checking and stuff, all in one go. :3
|
||||
#ifdef DEVELOP
|
||||
#define VERSION 0 // Game version
|
||||
#define SUBVERSION 0 // more precise version number
|
||||
|
|
163
src/m_menu.c
163
src/m_menu.c
|
@ -184,6 +184,7 @@ INT16 startmap; // Mario, NiGHTS, or just a plain old normal game?
|
|||
|
||||
static INT16 itemOn = 1; // menu item skull is on, Hack by Tails 09-18-2002
|
||||
static INT16 skullAnimCounter = 10; // skull animation counter
|
||||
static tic_t followertimer = 0; // Used for smooth follower floating
|
||||
|
||||
static UINT8 setupcontrolplayer;
|
||||
static INT32 (*setupcontrols)[2]; // pointer to the gamecontrols of the player being edited
|
||||
|
@ -973,6 +974,7 @@ static menuitem_t MP_PlayerSetupMenu[] =
|
|||
{
|
||||
{IT_KEYHANDLER | IT_STRING, NULL, "Name", M_HandleSetupMultiPlayer, 0},
|
||||
{IT_KEYHANDLER | IT_STRING, NULL, "Character", M_HandleSetupMultiPlayer, 16}, // Tails 01-18-2001
|
||||
{IT_KEYHANDLER | IT_STRING, NULL, "Follower", M_HandleSetupMultiPlayer, 26},
|
||||
{IT_KEYHANDLER | IT_STRING, NULL, "Color", M_HandleSetupMultiPlayer, 152},
|
||||
};
|
||||
|
||||
|
@ -3139,6 +3141,8 @@ void M_Ticker(void)
|
|||
if (--skullAnimCounter <= 0)
|
||||
skullAnimCounter = 8;
|
||||
|
||||
followertimer++;
|
||||
|
||||
//added : 30-01-98 : test mode for five seconds
|
||||
if (vidm_testingmode > 0)
|
||||
{
|
||||
|
@ -8027,9 +8031,15 @@ static void M_HandleConnectIP(INT32 choice)
|
|||
// ========================
|
||||
// Tails 03-02-2002
|
||||
|
||||
// used for skin display on player setup menu
|
||||
static INT32 multi_tics;
|
||||
static state_t *multi_state;
|
||||
|
||||
// used for follower display on player setup menu
|
||||
static INT32 follower_tics;
|
||||
static INT32 follower_frame; // used for FF_ANIMATE garbo
|
||||
static state_t *follower_state;
|
||||
|
||||
// this is set before entering the MultiPlayer setup menu,
|
||||
// for either player 1 or 2
|
||||
static char setupm_name[MAXPLAYERNAME+1];
|
||||
|
@ -8037,8 +8047,10 @@ static player_t *setupm_player;
|
|||
static consvar_t *setupm_cvskin;
|
||||
static consvar_t *setupm_cvcolor;
|
||||
static consvar_t *setupm_cvname;
|
||||
static consvar_t *setupm_cvfollower;
|
||||
static INT32 setupm_fakeskin;
|
||||
static INT32 setupm_fakecolor;
|
||||
static INT32 setupm_fakefollower; // -1 is for none, our followers start at 0
|
||||
|
||||
static void M_DrawSetupMultiPlayerMenu(void)
|
||||
{
|
||||
|
@ -8087,11 +8099,31 @@ static void M_DrawSetupMultiPlayerMenu(void)
|
|||
'\x1D' | highlightflags, false); // right arrow
|
||||
}
|
||||
|
||||
// draw follower string
|
||||
char *fname = malloc(SKINNAMESIZE+1);
|
||||
|
||||
if (setupm_fakefollower == -1)
|
||||
strcpy(fname, "None");
|
||||
else
|
||||
strcpy(fname, followers[setupm_fakefollower].name);
|
||||
|
||||
st = V_StringWidth(fname, 0);
|
||||
V_DrawString(BASEVIDWIDTH - mx - st, my + 26,
|
||||
((MP_PlayerSetupMenu[2].status & IT_TYPE) == IT_SPACE ? V_TRANSLUCENT : 0)|highlightflags|V_ALLOWLOWERCASE,
|
||||
fname);
|
||||
if (itemOn == 2)
|
||||
{
|
||||
V_DrawCharacter(BASEVIDWIDTH - mx - 10 - st - (skullAnimCounter/5), my + 26,
|
||||
'\x1C' | highlightflags, false); // left arrow
|
||||
V_DrawCharacter(BASEVIDWIDTH - mx + 2 + (skullAnimCounter/5), my + 26,
|
||||
'\x1D' | highlightflags, false); // right arrow
|
||||
}
|
||||
|
||||
// draw the name of the color you have chosen
|
||||
// Just so people don't go thinking that "Default" is Green.
|
||||
st = V_StringWidth(KartColor_Names[setupm_fakecolor], 0);
|
||||
V_DrawString(BASEVIDWIDTH - mx - st, my + 152, highlightflags|V_ALLOWLOWERCASE, KartColor_Names[setupm_fakecolor]); // SRB2kart
|
||||
if (itemOn == 2)
|
||||
if (itemOn == 3)
|
||||
{
|
||||
V_DrawCharacter(BASEVIDWIDTH - mx - 10 - st - (skullAnimCounter/5), my + 152,
|
||||
'\x1C' | highlightflags, false); // left arrow
|
||||
|
@ -8262,9 +8294,84 @@ static void M_DrawSetupMultiPlayerMenu(void)
|
|||
|
||||
Z_Free(colormap);
|
||||
}
|
||||
|
||||
// draw their follower if there is one
|
||||
if (setupm_fakefollower > -1 && setupm_fakefollower < numfollowers)
|
||||
{
|
||||
// animate the follower
|
||||
|
||||
if (--follower_tics <= 0)
|
||||
{
|
||||
|
||||
// FF_ANIMATE; cycle through FRAMES and get back afterwards. This will be prominent amongst followers hence why it's being supported here.
|
||||
if (follower_state->frame & FF_ANIMATE)
|
||||
{
|
||||
follower_frame++;
|
||||
follower_tics = follower_state->var2;
|
||||
if (follower_frame > (follower_state->frame & FF_FRAMEMASK) + follower_state->var1) // that's how it works, right?
|
||||
follower_frame = follower_state->frame & FF_FRAMEMASK;
|
||||
}
|
||||
else
|
||||
{
|
||||
st = follower_state->nextstate;
|
||||
if (st != S_NULL)
|
||||
follower_state = &states[st];
|
||||
follower_tics = follower_state->tics;
|
||||
if (follower_tics == -1)
|
||||
follower_tics = 15; // er, what?
|
||||
// get spritedef:
|
||||
follower_frame = follower_state->frame & FF_FRAMEMASK;
|
||||
}
|
||||
}
|
||||
sprdef = &sprites[follower_state->sprite];
|
||||
|
||||
// draw the follower
|
||||
|
||||
if (follower_frame >= sprdef->numframes)
|
||||
follower_frame = 0; // frame doesn't exist, we went beyond it... what?
|
||||
sprframe = &sprdef->spriteframes[follower_frame];
|
||||
patch = W_CachePatchNum(sprframe->lumppat[1], PU_CACHE);
|
||||
if (sprframe->flip & 1) // Only for first sprite
|
||||
flags |= V_FLIP; // This sprite is left/right flipped!
|
||||
|
||||
// draw player sprite
|
||||
if (setupm_fakecolor) // inverse should never happen
|
||||
{
|
||||
|
||||
// smooth floating, totally not stolen from rocket sneakers.
|
||||
const fixed_t pi = (22<<FRACBITS) / 7; // loose approximation, this doesn't need to be incredibly precise
|
||||
fixed_t sine = 8 * FINESINE((((4*pi*(TICRATE)) * followertimer)>>ANGLETOFINESHIFT) & FINEMASK);
|
||||
|
||||
UINT8 *colormap = R_GetTranslationColormap(-1, setupm_fakecolor, 0);
|
||||
V_DrawMappedPatch(mx+65, my+90+(sine/FRACUNIT), flags, patch, colormap);
|
||||
Z_Free(colormap);
|
||||
}
|
||||
}
|
||||
|
||||
#undef charw
|
||||
}
|
||||
|
||||
// follower state update. This is its own function so that it's at least somewhat clean
|
||||
static void M_GetFollowerState(void)
|
||||
{
|
||||
|
||||
if (setupm_fakefollower == -1 || setupm_fakefollower > numfollowers-1) // yikes, there's none!
|
||||
return;
|
||||
// ^ we don't actually need to set anything since it won't be displayed anyway.
|
||||
|
||||
//followertimer = 0; // reset timer. not like it'll overflow anytime soon but whatever.
|
||||
|
||||
// set follower state
|
||||
follower_state = &states[followers[setupm_fakefollower].followstate];
|
||||
|
||||
if (follower_state->frame & FF_ANIMATE)
|
||||
follower_tics = follower_state->var2; // support for FF_ANIMATE
|
||||
else
|
||||
follower_tics = follower_state->tics;
|
||||
|
||||
follower_frame = follower_state->frame & FF_FRAMEMASK;
|
||||
}
|
||||
|
||||
// Handle 1P/2P MP Setup
|
||||
static void M_HandleSetupMultiPlayer(INT32 choice)
|
||||
{
|
||||
|
@ -8289,7 +8396,13 @@ static void M_HandleSetupMultiPlayer(INT32 choice)
|
|||
S_StartSound(NULL,sfx_menu1); // Tails
|
||||
setupm_fakeskin--;
|
||||
}
|
||||
else if (itemOn == 2) // player color
|
||||
else if (itemOn == 2) // follower
|
||||
{
|
||||
S_StartSound(NULL,sfx_menu1);
|
||||
setupm_fakefollower--;
|
||||
M_GetFollowerState(); // update follower state
|
||||
}
|
||||
else if (itemOn == 3) // player color
|
||||
{
|
||||
S_StartSound(NULL,sfx_menu1); // Tails
|
||||
setupm_fakecolor--;
|
||||
|
@ -8301,8 +8414,15 @@ static void M_HandleSetupMultiPlayer(INT32 choice)
|
|||
{
|
||||
S_StartSound(NULL,sfx_menu1); // Tails
|
||||
setupm_fakeskin++;
|
||||
M_GetFollowerState(); // update follower state
|
||||
}
|
||||
else if (itemOn == 2) // player color
|
||||
else if (itemOn == 2) // follower
|
||||
{
|
||||
S_StartSound(NULL,sfx_menu1);
|
||||
setupm_fakefollower++;
|
||||
M_GetFollowerState();
|
||||
}
|
||||
else if (itemOn == 3) // player color
|
||||
{
|
||||
S_StartSound(NULL,sfx_menu1); // Tails
|
||||
setupm_fakecolor++;
|
||||
|
@ -8322,7 +8442,12 @@ static void M_HandleSetupMultiPlayer(INT32 choice)
|
|||
setupm_name[l-1] =0;
|
||||
}
|
||||
}
|
||||
else if (itemOn == 2)
|
||||
else if (itemOn == 2) // follower
|
||||
{
|
||||
S_StartSound(NULL,sfx_menu1);
|
||||
setupm_fakefollower = -1;
|
||||
}
|
||||
else if (itemOn == 3)
|
||||
{
|
||||
UINT8 col = skins[setupm_fakeskin].prefcolor;
|
||||
if (setupm_fakecolor != col)
|
||||
|
@ -8360,6 +8485,18 @@ static void M_HandleSetupMultiPlayer(INT32 choice)
|
|||
if (setupm_fakeskin > numskins-1)
|
||||
setupm_fakeskin = 0;
|
||||
|
||||
// check followers:
|
||||
if (setupm_fakefollower < -1)
|
||||
{
|
||||
setupm_fakefollower = numfollowers-1;
|
||||
M_GetFollowerState(); // update follower state
|
||||
}
|
||||
if (setupm_fakefollower > numfollowers-1)
|
||||
{
|
||||
setupm_fakefollower = -1;
|
||||
M_GetFollowerState(); // update follower state
|
||||
}
|
||||
|
||||
// check color
|
||||
if (setupm_fakecolor < 1)
|
||||
setupm_fakecolor = MAXSKINCOLORS-1;
|
||||
|
@ -8382,6 +8519,7 @@ static void M_SetupMultiPlayer(INT32 choice)
|
|||
|
||||
multi_state = &states[mobjinfo[MT_PLAYER].seestate];
|
||||
multi_tics = multi_state->tics;
|
||||
|
||||
strcpy(setupm_name, cv_playername.string);
|
||||
|
||||
// set for player 1
|
||||
|
@ -8389,6 +8527,10 @@ static void M_SetupMultiPlayer(INT32 choice)
|
|||
setupm_cvskin = &cv_skin;
|
||||
setupm_cvcolor = &cv_playercolor;
|
||||
setupm_cvname = &cv_playername;
|
||||
setupm_cvfollower = &cv_follower;
|
||||
|
||||
setupm_fakefollower = atoi(setupm_cvfollower->string); // update fake follower value
|
||||
M_GetFollowerState(); // update follower state
|
||||
|
||||
// For whatever reason this doesn't work right if you just use ->value
|
||||
setupm_fakeskin = R_SkinAvailable(setupm_cvskin->string);
|
||||
|
@ -8420,6 +8562,10 @@ static void M_SetupMultiPlayer2(INT32 choice)
|
|||
setupm_cvskin = &cv_skin2;
|
||||
setupm_cvcolor = &cv_playercolor2;
|
||||
setupm_cvname = &cv_playername2;
|
||||
setupm_cvfollower = &cv_follower;
|
||||
|
||||
setupm_fakefollower = atoi(setupm_cvfollower->string); // update fake follower value
|
||||
M_GetFollowerState(); // update follower state
|
||||
|
||||
// For whatever reason this doesn't work right if you just use ->value
|
||||
setupm_fakeskin = R_SkinAvailable(setupm_cvskin->string);
|
||||
|
@ -8451,6 +8597,10 @@ static void M_SetupMultiPlayer3(INT32 choice)
|
|||
setupm_cvskin = &cv_skin3;
|
||||
setupm_cvcolor = &cv_playercolor3;
|
||||
setupm_cvname = &cv_playername3;
|
||||
setupm_cvfollower = &cv_follower;
|
||||
|
||||
setupm_fakefollower = atoi(setupm_cvfollower->string); // update fake follower value
|
||||
M_GetFollowerState(); // update follower state
|
||||
|
||||
// For whatever reason this doesn't work right if you just use ->value
|
||||
setupm_fakeskin = R_SkinAvailable(setupm_cvskin->string);
|
||||
|
@ -8482,6 +8632,10 @@ static void M_SetupMultiPlayer4(INT32 choice)
|
|||
setupm_cvskin = &cv_skin4;
|
||||
setupm_cvcolor = &cv_playercolor4;
|
||||
setupm_cvname = &cv_playername4;
|
||||
setupm_cvfollower = &cv_follower;
|
||||
|
||||
setupm_fakefollower = atoi(setupm_cvfollower->string); // update fake follower value
|
||||
M_GetFollowerState(); // update follower state
|
||||
|
||||
// For whatever reason this doesn't work right if you just use ->value
|
||||
setupm_fakeskin = R_SkinAvailable(setupm_cvskin->string);
|
||||
|
@ -8514,6 +8668,7 @@ static boolean M_QuitMultiPlayerMenu(void)
|
|||
// you know what? always putting these in the buffer won't hurt anything.
|
||||
COM_BufAddText (va("%s \"%s\"\n",setupm_cvskin->name,skins[setupm_fakeskin].name));
|
||||
COM_BufAddText (va("%s %d\n",setupm_cvcolor->name,setupm_fakecolor));
|
||||
COM_BufAddText (va("%s %d\n",setupm_cvfollower->name,setupm_fakefollower));
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -2637,6 +2637,19 @@ INT32 R_SkinAvailable(const char *name)
|
|||
return -1;
|
||||
}
|
||||
|
||||
// same thing but for followers:
|
||||
INT32 R_FollowerAvailable(const char *name)
|
||||
{
|
||||
INT32 i;
|
||||
|
||||
for (i = 0; i < numfollowers; i++)
|
||||
{
|
||||
if (stricmp(followers[i].skinname,name)==0)
|
||||
return i;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
// network code calls this when a 'skin change' is received
|
||||
boolean SetPlayerSkin(INT32 playernum, const char *skinname)
|
||||
{
|
||||
|
@ -2662,13 +2675,38 @@ boolean SetPlayerSkin(INT32 playernum, const char *skinname)
|
|||
return false;
|
||||
}
|
||||
|
||||
// Again, same thing but for followers;
|
||||
boolean SetPlayerFollower(INT32 playernum, const char *skinname)
|
||||
{
|
||||
INT32 i;
|
||||
player_t *player = &players[playernum];
|
||||
|
||||
for (i = 0; i < numfollowers; i++)
|
||||
{
|
||||
// search in the skin list
|
||||
if (stricmp(followers[i].skinname, skinname) == 0)
|
||||
{
|
||||
SetFollower(playernum, i);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
if (P_IsLocalPlayer(player))
|
||||
CONS_Alert(CONS_WARNING, M_GetText("Follower '%s' not found.\n"), skinname);
|
||||
else if(server || IsPlayerAdmin(consoleplayer))
|
||||
CONS_Alert(CONS_WARNING, M_GetText("Player %d (%s) follower '%s' not found\n"), playernum, player_names[playernum], skinname);
|
||||
|
||||
SetFollower(playernum, -1); // reminder that -1 is nothing
|
||||
return false;
|
||||
}
|
||||
|
||||
// Same as SetPlayerSkin, but uses the skin #.
|
||||
// network code calls this when a 'skin change' is received
|
||||
void SetPlayerSkinByNum(INT32 playernum, INT32 skinnum)
|
||||
{
|
||||
player_t *player = &players[playernum];
|
||||
skin_t *skin = &skins[skinnum];
|
||||
|
||||
CONS_Printf("skin\n");
|
||||
if (skinnum >= 0 && skinnum < numskins) // Make sure it exists!
|
||||
{
|
||||
player->skin = skinnum;
|
||||
|
@ -2727,6 +2765,30 @@ void SetPlayerSkinByNum(INT32 playernum, INT32 skinnum)
|
|||
SetPlayerSkinByNum(playernum, 0); // not found put the sonic skin
|
||||
}
|
||||
|
||||
// you get the drill, now we do the same for followers:
|
||||
void SetFollower(INT32 playernum, INT32 skinnum)
|
||||
{
|
||||
player_t *player = &players[playernum];
|
||||
|
||||
if (skinnum >= -1 && skinnum <= numfollowers) // Make sure it exists!
|
||||
{
|
||||
player->followerskin = skinnum;
|
||||
CONS_Printf("Updated player follower num\n");
|
||||
/*
|
||||
We don't actually set anything there, becasuse we need to be sure that a proper player->mo is available to spawn the follower.
|
||||
Moreover, the follower will self-handle itself the rest of the time, hence, its skinnum stored to the player is all we need right now.
|
||||
*/
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
if (P_IsLocalPlayer(player))
|
||||
CONS_Alert(CONS_WARNING, M_GetText("Follower %d not found\n"), skinnum);
|
||||
else if(server || IsPlayerAdmin(consoleplayer))
|
||||
CONS_Alert(CONS_WARNING, "Player %d (%s) follower %d not found\n", playernum, player_names[playernum], skinnum);
|
||||
SetFollower(playernum, -1); // Not found, then set -1 (nothing) as our follower.
|
||||
}
|
||||
|
||||
//
|
||||
// Add skins from a pwad, each skin preceded by 'S_SKIN' marker
|
||||
//
|
||||
|
|
|
@ -122,21 +122,22 @@ typedef struct
|
|||
//
|
||||
typedef struct follower_s
|
||||
{
|
||||
char name[SKINNAMESIZE+1]; // Name. This is used for the menus. We'll just follow the same rules as skins for this.
|
||||
|
||||
char skinname[SKINNAMESIZE+1]; // Skin Name. This is what to refer to when asking the commands anything.
|
||||
char name[SKINNAMESIZE+1]; // Name. This is used for the menus. We'll just follow the same rules as skins for this.
|
||||
|
||||
// some position shenanigans:
|
||||
INT32 atangle; // angle the object will be at around the player. The object itself will always face the same direction as the player.
|
||||
INT32 zoffs; // Z offset relative to the player's height. Cannot be negative.
|
||||
|
||||
|
||||
// from there on out, everything is STATES to allow customization
|
||||
// these are only set once when the action is performed and are then free to animate however they want.
|
||||
|
||||
|
||||
INT32 idlestate; // state when the player is at a standstill
|
||||
INT32 followstate; // state when the player is moving
|
||||
INT32 hurtstate; // state when the player is being hurt
|
||||
INT32 winstate; // state when the player has won
|
||||
INT32 losestate; // state when the player has lost
|
||||
|
||||
|
||||
} follower_t;
|
||||
|
||||
// -----------
|
||||
|
@ -225,6 +226,10 @@ void SetPlayerSkinByNum(INT32 playernum,INT32 skinnum); // Tails 03-16-2002
|
|||
INT32 R_SkinAvailable(const char *name);
|
||||
void R_AddSkins(UINT16 wadnum);
|
||||
|
||||
INT32 R_FollowerAvailable(const char *name);
|
||||
boolean SetPlayerFollower(INT32 playernum,const char *skinname);
|
||||
void SetFollower(INT32 playernum,INT32 skinnum);
|
||||
|
||||
#ifdef DELFILE
|
||||
void R_DelSkins(UINT16 wadnum);
|
||||
#endif
|
||||
|
|
Loading…
Reference in a new issue