Merge r_things.c/h

Includes r_skins, obviously, but also a little bit of m_cond to make availabilities better for kart's purposes
This commit is contained in:
Sally Coolatta 2020-08-08 19:08:19 -04:00
parent 4b5c7d7510
commit 3f1d58754e
5 changed files with 431 additions and 1391 deletions

View file

@ -20,8 +20,8 @@
// [required] <optional>
typedef enum
{
UC_PLAYTIME, // PLAYTIME [tics]
UC_MATCHESPLAYED, // SRB2Kart: MATCHESPLAYED [x played]
UC_PLAYTIME, // PLAYTIME [tics]
UC_MATCHESPLAYED, // SRB2Kart: MATCHESPLAYED [x played]
UC_POWERLEVEL, // SRB2Kart: POWERLEVEL [power level to reach] [gametype, "0" for race, "1" for battle]
UC_GAMECLEAR, // GAMECLEAR <x times>
UC_ALLEMERALDS, // ALLEMERALDS <x times>
@ -60,11 +60,11 @@ typedef struct
#define ET_GLOBAL 0 // Emblem with a position in space
#define ET_MAP 1 // Beat the map
#define ET_TIME 2 // Get the time
//#define ET_DEVTIME 3 // Time, but
//#define ET_DEVTIME 3 // Time, but the value is tied to a Time Trial demo, not pre-defined
// Global emblem flags
// (N/A to Kart yet)
//#define GE_NIGHTSPULL 1
//#define GE_OH 1
// Map emblem flags
#define ME_ENCORE 1
@ -109,21 +109,23 @@ typedef struct
#define SECRET_NONE 0 // Does nil. Use with levels locked by UnlockRequired
#define SECRET_HEADER 1 // Does nothing on its own, just serves as a header for the menu
#define SECRET_LEVELSELECT 2 // Selectable level select
#define SECRET_SKIN 2 // Allow this character to be selected
#define SECRET_WARP 3 // Selectable warp
#define SECRET_TIMEATTACK 4 // Enables Time Attack on the main menu
#define SECRET_BREAKTHECAPSULES 5 // Enables Break the Capsules on the main menu
#define SECRET_SOUNDTEST 6 // Sound Test
#define SECRET_CREDITS 7 // Enables Credits
#define SECRET_LEVELSELECT 4 // Selectable level select
#define SECRET_ITEMFINDER 8 // Enables Item Finder/Emblem Radar
#define SECRET_EMBLEMHINTS 9 // Enables Emblem Hints
#define SECRET_TIMEATTACK 5 // Enables Time Attack on the main menu
#define SECRET_BREAKTHECAPSULES 6 // Enables Break the Capsules on the main menu
#define SECRET_SOUNDTEST 7 // Sound Test
#define SECRET_CREDITS 8 // Enables Credits
#define SECRET_ENCORE 10 // Enables Encore mode cvar
#define SECRET_HARDSPEED 11 // Enables Hard gamespeed
#define SECRET_HELLATTACK 12 // Map Hell in record attack
#define SECRET_ITEMFINDER 9 // Enables Item Finder/Emblem Radar
#define SECRET_EMBLEMHINTS 10 // Enables Emblem Hints
#define SECRET_PANDORA 13 // Enables Pandora's Box
#define SECRET_ENCORE 11 // Enables Encore mode cvar
#define SECRET_HARDSPEED 12 // Enables Hard gamespeed
#define SECRET_HELLATTACK 13 // Map Hell in record attack
#define SECRET_PANDORA 14 // Enables Pandora's Box
// If you have more secrets than these variables allow in your game,
// you seriously need to get a life.
@ -174,8 +176,6 @@ const char *M_GetExtraEmblemPatch(extraemblem_t *em, boolean big);
// They stop checking upon reaching the target number so they
// should be (theoretically?) slightly faster.
UINT8 M_GotEnoughEmblems(INT32 number);
//UINT8 M_GotHighEnoughScore(INT32 tscore);
UINT8 M_GotLowEnoughTime(INT32 tictime);
//UINT8 M_GotHighEnoughRings(INT32 trings);
#define M_Achieved(a) ((a) >= MAXCONDITIONSETS || conditionSets[a].achieved)

View file

@ -46,6 +46,11 @@ skin_t skins[MAXSKINS];
CV_PossibleValue_t skin_cons_t[MAXSKINS+1];
#endif
CV_PossibleValue_t Forceskin_cons_t[MAXSKINS+2];
// SRB2Kart followers
follower_t followers[MAXSKINS];
//
// P_GetSkinSprite2
// For non-super players, tries each sprite2's immediate predecessor until it finds one with a number of frames or ends up at standing.
@ -125,36 +130,12 @@ static void Sk_SetDefaultValue(skin_t *skin)
skin->supercolor = SKINCOLOR_SUPERGOLD1;
skin->prefoppositecolor = 0; // use tables
skin->normalspeed = 36<<FRACBITS;
skin->runspeed = 28<<FRACBITS;
skin->thrustfactor = 5;
skin->accelstart = 96;
skin->acceleration = 40;
skin->kartspeed = 5;
skin->kartweight = 5;
skin->ability = CA_NONE;
skin->ability2 = CA2_SPINDASH;
skin->jumpfactor = FRACUNIT;
skin->actionspd = 30<<FRACBITS;
skin->mindash = 15<<FRACBITS;
skin->maxdash = 70<<FRACBITS;
skin->radius = mobjinfo[MT_PLAYER].radius;
skin->height = mobjinfo[MT_PLAYER].height;
skin->spinheight = FixedMul(skin->height, 2*FRACUNIT/3);
skin->shieldscale = FRACUNIT;
skin->camerascale = FRACUNIT;
skin->thokitem = -1;
skin->spinitem = -1;
skin->revitem = -1;
skin->followitem = 0;
skin->highresscale = FRACUNIT;
skin->contspeed = 17;
skin->contangle = 0;
skin->availability = 0;
for (i = 0; i < sfx_skinsoundslot0; i++)
if (S_sfx[i].skinsound != -1)
@ -182,14 +163,18 @@ void R_InitSkins(void)
UINT32 R_GetSkinAvailabilities(void)
{
INT32 s;
UINT8 i;
UINT32 response = 0;
for (s = 0; s < MAXSKINS; s++)
for (i = 0; i < MAXUNLOCKABLES; s++)
{
if (skins[s].availability && unlockables[skins[s].availability - 1].unlocked)
if (unlockables[i].type == SECRET_SKIN && unlockables[i].unlocked)
{
UINT8 s = min(unlockables[i].variable, MAXSKINS);
response |= (1 << s);
}
}
return response;
}
@ -197,14 +182,70 @@ UINT32 R_GetSkinAvailabilities(void)
// warning don't use with an invalid skinnum other than -1 which always returns true
boolean R_SkinUsable(INT32 playernum, INT32 skinnum)
{
return ((skinnum == -1) // Simplifies things elsewhere, since there's already plenty of checks for less-than-0...
|| (!skins[skinnum].availability)
|| (((netgame || multiplayer) && playernum != -1) ? (players[playernum].availabilities & (1 << skinnum)) : (unlockables[skins[skinnum].availability - 1].unlocked))
|| (modeattacking) // If you have someone else's run you might as well take a look
|| (Playing() && (R_SkinAvailable(mapheaderinfo[gamemap-1]->forcecharacter) == skinnum)) // Force 1.
|| (netgame && (cv_forceskin.value == skinnum)) // Force 2.
|| (metalrecording && skinnum == 5) // Force 3.
);
boolean needsunlocked = false;
UINT8 i;
if (skinnum == -1)
{
// Simplifies things elsewhere, since there's already plenty of checks for less-than-0...
return true;
}
if (modeattacking)
{
// If you have someone else's run, you should be able to take a look
return true;
}
if (Playing() && (R_SkinAvailable(mapheaderinfo[gamemap-1]->forcecharacter) == skinnum))
{
// Being forced to play as this character by the level
return true;
}
if (netgame && (cv_forceskin.value == skinnum))
{
// Being forced to play as this character by the server
return true;
}
if (metalrecording)
{
// Recording a Metal Sonic race
const INT32 metalskin = R_SkinAvailable("metalsonic");
return (skinnum == metalskin);
}
// Determine if this character is supposed to be unlockable or not
for (i = 0; i < MAXUNLOCKABLES; i++)
{
if (unlockables[i].type == SECRET_SKIN && unlockables[i].variable == skinnum)
{
// i is now the unlockable index, we can use this later
needsunlocked = true;
break;
}
}
if (needsunlocked == true)
{
// You can use this character IF you have it unlocked.
if ((netgame || multiplayer) && playernum != -1)
{
// Use the netgame synchronized unlocks.
return (boolean)(!(players[playernum].availabilities & (1 << skinnum)));
}
else
{
// Use the unlockables table directly
return (boolean)(unlockables[i].unlocked);
}
}
else
{
// Didn't trip anything, so we can use this character.
return true;
}
}
// returns true if the skin name is found (loaded from pwad)
@ -249,50 +290,33 @@ void SetPlayerSkinByNum(INT32 playernum, INT32 skinnum)
player_t *player = &players[playernum];
skin_t *skin = &skins[skinnum];
UINT16 newcolor = 0;
UINT8 i;
if (skinnum >= 0 && skinnum < numskins && R_SkinUsable(playernum, skinnum)) // Make sure it exists!
{
player->skin = skinnum;
player->camerascale = skin->camerascale;
player->shieldscale = skin->shieldscale;
player->charability = (UINT8)skin->ability;
player->charability2 = (UINT8)skin->ability2;
player->charflags = (UINT32)skin->flags;
player->thokitem = skin->thokitem < 0 ? (UINT32)mobjinfo[MT_PLAYER].painchance : (UINT32)skin->thokitem;
player->spinitem = skin->spinitem < 0 ? (UINT32)mobjinfo[MT_PLAYER].damage : (UINT32)skin->spinitem;
player->revitem = skin->revitem < 0 ? (mobjtype_t)mobjinfo[MT_PLAYER].raisestate : (UINT32)skin->revitem;
player->followitem = skin->followitem;
if (((player->powers[pw_shield] & SH_NOSTACK) == SH_PINK) && (player->revitem == MT_LHRT || player->spinitem == MT_LHRT || player->thokitem == MT_LHRT)) // Healers can't keep their buff.
player->powers[pw_shield] &= SH_STACK;
player->kartspeed = skin->kartspeed;
player->kartweight = skin->kartweight;
player->actionspd = skin->actionspd;
player->mindash = skin->mindash;
player->maxdash = skin->maxdash;
player->normalspeed = skin->normalspeed;
player->runspeed = skin->runspeed;
player->thrustfactor = skin->thrustfactor;
player->accelstart = skin->accelstart;
player->acceleration = skin->acceleration;
player->jumpfactor = skin->jumpfactor;
player->height = skin->height;
player->spinheight = skin->spinheight;
if (!(cv_debug || devparm) && !(netgame || multiplayer || demoplayback))
#if 0
if (!(cv_debug || devparm) && !(netgame || multiplayer || demo.playback))
{
if (playernum == consoleplayer)
CV_StealthSetValue(&cv_playercolor, skin->prefcolor);
else if (playernum == secondarydisplayplayer)
CV_StealthSetValue(&cv_playercolor2, skin->prefcolor);
for (i = 0; i <= r_splitscreen; i++)
{
if (playernum == g_localplayers[i])
{
CV_StealthSetValue(&cv_playercolor[i], skin->prefcolor);
}
}
player->skincolor = newcolor = skin->prefcolor;
}
#endif
if (player->followmobj)
{
@ -302,22 +326,20 @@ void SetPlayerSkinByNum(INT32 playernum, INT32 skinnum)
if (player->mo)
{
fixed_t radius = FixedMul(skin->radius, player->mo->scale);
if ((player->powers[pw_carry] == CR_NIGHTSMODE) && (skin->sprites[SPR2_NFLY].numframes == 0)) // If you don't have a sprite for flying horizontally, use the default NiGHTS skin.
{
skin = &skins[DEFAULTNIGHTSSKIN];
player->followitem = skin->followitem;
if (!(cv_debug || devparm) && !(netgame || multiplayer || demoplayback))
newcolor = skin->prefcolor; // will be updated in thinker to flashing
}
player->mo->skin = skin;
if (newcolor)
player->mo->color = newcolor;
P_SetScale(player->mo, player->mo->scale);
player->mo->radius = radius;
if (newcolor)
{
player->mo->color = newcolor;
}
P_SetScale(player->mo, player->mo->scale);
P_SetPlayerMobjState(player->mo, player->mo->state-states); // Prevent visual errors when switching between skins with differing number of frames
}
// for replays: We have changed our skin mid-game; let the game know so it can do the same in the replay!
demo_extradata[playernum] |= DXD_SKIN;
return;
}
@ -325,7 +347,8 @@ void SetPlayerSkinByNum(INT32 playernum, INT32 skinnum)
CONS_Alert(CONS_WARNING, M_GetText("Requested skin %d not found\n"), skinnum);
else if(server || IsPlayerAdmin(consoleplayer))
CONS_Alert(CONS_WARNING, "Player %d (%s) skin %d not found\n", playernum, player_names[playernum], skinnum);
SetPlayerSkinByNum(playernum, 0); // not found put the sonic skin
SetPlayerSkinByNum(playernum, 0); // not found, put in the default skin
}
//
@ -434,36 +457,9 @@ static boolean R_ProcessPatchableFields(skin_t *skin, char *stoken, char *value)
#define FULLPROCESS(field) else if (!stricmp(stoken, #field)) skin->field = get_number(value);
// character type identification
FULLPROCESS(flags)
FULLPROCESS(ability)
FULLPROCESS(ability2)
FULLPROCESS(thokitem)
FULLPROCESS(spinitem)
FULLPROCESS(revitem)
FULLPROCESS(followitem)
#undef FULLPROCESS
#define GETFRACBITS(field) else if (!stricmp(stoken, #field)) skin->field = atoi(value)<<FRACBITS;
GETFRACBITS(normalspeed)
GETFRACBITS(runspeed)
GETFRACBITS(mindash)
GETFRACBITS(maxdash)
GETFRACBITS(actionspd)
GETFRACBITS(radius)
GETFRACBITS(height)
GETFRACBITS(spinheight)
#undef GETFRACBITS
#define GETINT(field) else if (!stricmp(stoken, #field)) skin->field = atoi(value);
GETINT(thrustfactor)
GETINT(accelstart)
GETINT(acceleration)
GETINT(contspeed)
GETINT(contangle)
#undef GETINT
#define GETSKINCOLOR(field) else if (!stricmp(stoken, #field)) skin->field = R_GetColorByName(value);
GETSKINCOLOR(prefcolor)
GETSKINCOLOR(prefoppositecolor)
@ -472,12 +468,21 @@ static boolean R_ProcessPatchableFields(skin_t *skin, char *stoken, char *value)
skin->supercolor = R_GetSuperColorByName(value);
#define GETFLOAT(field) else if (!stricmp(stoken, #field)) skin->field = FLOAT_TO_FIXED(atof(value));
GETFLOAT(jumpfactor)
GETFLOAT(highresscale)
GETFLOAT(shieldscale)
GETFLOAT(camerascale)
#undef GETFLOAT
#define GETKARTSTAT(field) \
else if (!stricmp(stoken, #field)) \
{ \
skin->field = atoi(value); \
if (skin->field < 1) skin->field = 1; \
if (skin->field > 9) skin->field = 9; \
}
GETKARTSTAT(kartspeed)
GETKARTSTAT(kartweight)
#undef GETKARTSTAT
#define GETFLAG(field) else if (!stricmp(stoken, #field)) { \
strupr(value); \
if (atoi(value) || value[0] == 'T' || value[0] == 'Y') \
@ -488,23 +493,8 @@ static boolean R_ProcessPatchableFields(skin_t *skin, char *stoken, char *value)
// parameters for individual character flags
// these are uppercase so they can be concatenated with SF_
// 1, true, yes are all valid values
GETFLAG(SUPER)
GETFLAG(NOSUPERSPIN)
GETFLAG(NOSPINDASHDUST)
GETFLAG(HIRES)
GETFLAG(NOSKID)
GETFLAG(NOSPEEDADJUST)
GETFLAG(RUNONWATER)
GETFLAG(NOJUMPSPIN)
GETFLAG(NOJUMPDAMAGE)
GETFLAG(STOMPDAMAGE)
GETFLAG(MARIODAMAGE)
GETFLAG(MACHINE)
GETFLAG(DASHMODE)
GETFLAG(FASTEDGE)
GETFLAG(MULTIABILITY)
GETFLAG(NONIGHTSROTATION)
GETFLAG(NONIGHTSSUPER)
#undef GETFLAG
else // let's check if it's a sound, otherwise error out
@ -557,7 +547,7 @@ void R_AddSkins(UINT16 wadnum)
char *value;
size_t size;
skin_t *skin;
boolean hudname, realname;
boolean realname;
//
// search for all skin markers in pwad
@ -587,7 +577,7 @@ void R_AddSkins(UINT16 wadnum)
skin = &skins[numskins];
Sk_SetDefaultValue(skin);
skin->wadnum = wadnum;
hudname = realname = false;
realname = false;
// parse
stoken = strtok (buf2, "\r\n= ");
while (stoken)
@ -640,34 +630,51 @@ void R_AddSkins(UINT16 wadnum)
else if (*value == '.') *value = '\x1E'; // turn . into katana dot.
}
}
if (!hudname)
{
HUDNAMEWRITE(skin->name);
strupr(skin->hudname);
SYMBOLCONVERT(skin->hudname)
}
}
else if (!stricmp(stoken, "realname"))
{ // Display name (eg. "Knuckles")
realname = true;
STRBUFCPY(skin->realname, value);
SYMBOLCONVERT(skin->realname)
if (!hudname)
HUDNAMEWRITE(skin->realname);
}
else if (!stricmp(stoken, "hudname"))
{ // Life icon name (eg. "K.T.E")
hudname = true;
HUDNAMEWRITE(value);
SYMBOLCONVERT(skin->hudname)
if (!realname)
STRBUFCPY(skin->realname, skin->hudname);
}
else if (!stricmp(stoken, "availability"))
else if (!stricmp(stoken, "rivals"))
{
skin->availability = atoi(value);
if (skin->availability >= MAXUNLOCKABLES)
skin->availability = 0;
size_t len = strlen(value);
size_t i;
char rivalname[SKINNAMESIZE] = "";
UINT8 pos = 0;
UINT8 numrivals = 0;
// Can't use strtok, because this function's already using it.
// Using it causes it to upset the saved pointer,
// corrupting the reading for the rest of the file.
// So instead we get to crawl through the value, character by character,
// and write it down as we go, until we hit a comma or the end of the string.
// Yaaay.
for (i = 0; i <= len; i++)
{
if (numrivals >= SKINRIVALS)
{
break;
}
if (value[i] == ',' || i == len)
{
STRBUFCPY(skin->rivals[numrivals], rivalname);
strlwr(skin->rivals[numrivals]);
numrivals++;
memset(rivalname, 0, sizeof (rivalname));
pos = 0;
continue;
}
rivalname[pos] = value[i];
pos++;
}
}
else if (!R_ProcessPatchableFields(skin, stoken, value))
CONS_Debug(DBG_SETUP, "R_AddSkins: Unknown keyword '%s' in S_SKIN lump #%d (WAD %s)\n", stoken, lump, wadfiles[wadnum]->filename);
@ -690,6 +697,10 @@ next_token:
skin_cons_t[numskins].strvalue = skin->name;
#endif
// Update the forceskin possiblevalues
Forceskin_cons_t[numskins+1].value = numskins;
Forceskin_cons_t[numskins+1].strvalue = skins[numskins].name;
#ifdef HWRENDER
if (rendermode == render_opengl)
HWR_AddPlayerModel(numskins);
@ -712,7 +723,7 @@ void R_PatchSkins(UINT16 wadnum)
char *value;
size_t size;
skin_t *skin;
boolean noskincomplain, realname, hudname;
boolean noskincomplain, realname;
//
// search for all skin patch markers in pwad
@ -736,7 +747,7 @@ void R_PatchSkins(UINT16 wadnum)
buf2[size] = '\0';
skin = NULL;
noskincomplain = realname = hudname = false;
noskincomplain = realname = false;
/*
Parse. Has more phases than the parser in R_AddSkins because it needs to have the patching name first (no default skin name is acceptible for patching, unlike skin creation)
@ -780,16 +791,45 @@ void R_PatchSkins(UINT16 wadnum)
realname = true;
STRBUFCPY(skin->realname, value);
SYMBOLCONVERT(skin->realname)
if (!hudname)
HUDNAMEWRITE(skin->realname);
}
else if (!stricmp(stoken, "hudname"))
{ // Life icon name (eg. "K.T.E")
hudname = true;
HUDNAMEWRITE(value);
SYMBOLCONVERT(skin->hudname)
if (!realname)
STRBUFCPY(skin->realname, skin->hudname);
else if (!stricmp(stoken, "rivals"))
{
size_t len = strlen(value);
size_t i;
char rivalname[SKINNAMESIZE] = "";
UINT8 pos = 0;
UINT8 numrivals = 0;
// Can't use strtok, because this function's already using it.
// Using it causes it to upset the saved pointer,
// corrupting the reading for the rest of the file.
// So instead we get to crawl through the value, character by character,
// and write it down as we go, until we hit a comma or the end of the string.
// Yaaay.
for (i = 0; i <= len; i++)
{
if (numrivals >= SKINRIVALS)
{
break;
}
if (value[i] == ',' || i == len)
{
STRBUFCPY(skin->rivals[numrivals], rivalname);
strlwr(skin->rivals[numrivals]);
numrivals++;
memset(rivalname, 0, sizeof (rivalname));
pos = 0;
continue;
}
rivalname[pos] = value[i];
pos++;
}
}
else if (!R_ProcessPatchableFields(skin, stoken, value))
CONS_Debug(DBG_SETUP, "R_PatchSkins: Unknown keyword '%s' in P_SKIN lump #%d (WAD %s)\n", stoken, lump, wadfiles[wadnum]->filename);
@ -824,3 +864,92 @@ next_token:
#undef HUDNAMEWRITE
#undef SYMBOLCONVERT
// SRB2Kart: Followers!
// TODO: put this stuff in its own file?
// same thing as R_SkinAvailable, 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;
}
// same thing as SetPlayerSkin, 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;
}
// SetPlayerSkinByNum, for followers
void SetFollower(INT32 playernum, INT32 skinnum)
{
player_t *player = &players[playernum];
mobj_t *bub;
mobj_t *tmp;
player->followerready = true; // we are ready to perform follower related actions in the player thinker, now.
if (skinnum >= -1 && skinnum <= numfollowers) // Make sure it exists!
{
/*
We don't spawn the follower here since it'll be easier to handle all of it in the Player thinker itself.
However, we will despawn it right here if there's any to make it easy for the player thinker to replace it or delete it.
*/
if (player->follower && skinnum != player->followerskin) // this is also called when we change colour so don't respawn the follower unless we changed skins
{
// Remove follower's possible hnext list (bubble)
bub = player->follower->hnext;
while (bub && !P_MobjWasRemoved(bub))
{
tmp = bub->hnext;
P_RemoveMobj(bub);
bub = tmp;
}
P_RemoveMobj(player->follower);
P_SetTarget(&player->follower, NULL);
}
player->followerskin = skinnum;
// for replays: We have changed our follower mid-game; let the game know so it can do the same in the replay!
demo_extradata[playernum] |= DXD_FOLLOWER;
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.
}

View file

@ -22,10 +22,12 @@
/// Defaults
#define SKINNAMESIZE 16
#define SKINRIVALS 3
// should be all lowercase!! S_SKIN processing does a strlwr
#define DEFAULTSKIN "sonic"
#define DEFAULTSKIN "eggman"
#define DEFAULTSKIN2 "tails" // secondary player
#define DEFAULTNIGHTSSKIN 0
#define DEFAULTSKIN3 "sonic" // third player
#define DEFAULTSKIN4 "knuckles" // fourth player
/// The skin_t struct
typedef struct
@ -35,33 +37,11 @@ typedef struct
skinflags_t flags;
char realname[SKINNAMESIZE+1]; // Display name for level completion.
char hudname[SKINNAMESIZE+1]; // HUD name to display (officially exactly 5 characters long)
UINT8 ability; // ability definition
UINT8 ability2; // secondary ability definition
INT32 thokitem;
INT32 spinitem;
INT32 revitem;
UINT8 kartspeed;
UINT8 kartweight;
INT32 followitem;
fixed_t actionspd;
fixed_t mindash;
fixed_t maxdash;
fixed_t normalspeed; // Normal ground
fixed_t runspeed; // Speed that you break into your run animation
UINT8 thrustfactor; // Thrust = thrustfactor * acceleration
UINT8 accelstart; // Acceleration if speed = 0
UINT8 acceleration; // Acceleration
fixed_t jumpfactor; // multiple of standard jump height
fixed_t radius; // Bounding box changes.
fixed_t height;
fixed_t spinheight;
fixed_t shieldscale; // no change to bounding box, but helps set the shield's sprite size
fixed_t camerascale;
// Definable color translation table
UINT8 starttranscolor;
@ -70,8 +50,6 @@ typedef struct
UINT16 prefoppositecolor; // if 0 use tables instead
fixed_t highresscale; // scale of highres, default is 0.5
UINT8 contspeed; // continue screen animation speed
UINT8 contangle; // initial angle on continue screen
// specific sounds per skin
sfxenum_t soundsid[NUMSKINSOUNDS]; // sound # in S_sfx table
@ -80,13 +58,15 @@ typedef struct
spritedef_t sprites[NUMPLAYERSPRITES*2];
spriteinfo_t sprinfo[NUMPLAYERSPRITES*2];
UINT8 availability; // lock?
char rivals[SKINRIVALS][SKINNAMESIZE+1]; // Your top 3 rivals for GP mode. Uses names so that you can reference skins that aren't added
} skin_t;
/// Externs
extern INT32 numskins;
extern skin_t skins[MAXSKINS];
extern CV_PossibleValue_t Forceskin_cons_t[];
/// Function prototypes
void R_InitSkins(void);
@ -100,4 +80,51 @@ void R_AddSkins(UINT16 wadnum);
UINT8 P_GetSkinSprite2(skin_t *skin, UINT8 spr2, player_t *player);
// SRB2Kart Followers
//
// We'll define these here because they're really just a mobj that'll follow some rules behind a player
//
typedef struct follower_s
{
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.
UINT8 defaultcolor; // default color for menus.
fixed_t scale; // Scale relative to the player's.
fixed_t bubblescale; // Bubble scale relative to the player scale. If not set, no bubble will spawn (default)
// 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 dist; // distance relative to the player. (In a circle)
INT32 height; // height of the follower, this is mostly important for Z flipping.
INT32 zoffs; // Z offset relative to the player's height. Cannot be negative.
// movement options
INT32 horzlag; // Lag for X/Y displacement. Default is 2. Must be > 0 because we divide by this number.
INT32 vertlag; // not Vert from Neptunia lagging, this is for Z displacement lag Default is 6. Must be > 0 because we divide by this number.
INT32 bobamp; // Bob amplitude. Default is 4.
INT32 bobspeed; // Arbitrary modifier for bobbing speed, default is TICRATE*2 (70).
// 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
INT32 hitconfirmstate; // state for hit confirm
INT32 hitconfirmtime; // time to keep the above playing for
} follower_t;
extern INT32 numfollowers;
extern follower_t followers[MAXSKINS]; // again, use the same rules as skins, no reason not to.
INT32 R_FollowerAvailable(const char *name);
boolean SetPlayerFollower(INT32 playernum,const char *skinname);
void SetFollower(INT32 playernum,INT32 skinnum);
#endif //__R_SKINS__

File diff suppressed because it is too large Load diff

View file

@ -53,20 +53,12 @@ void R_DrawFlippedMaskedColumn(column_t *column);
// SPRITE RENDERING
// ----------------
<<<<<<< HEAD
fixed_t R_GetShadowZ(mobj_t *thing, pslope_t **shadowslope);
#ifdef DELFILE
void R_DelSpriteDefs(UINT16 wadnum);
#endif
=======
// Constant arrays used for psprite clipping
// and initializing clipping.
extern INT16 negonearray[MAXVIDWIDTH];
extern INT16 screenheightarray[MAXVIDWIDTH];
fixed_t R_GetShadowZ(mobj_t *thing, pslope_t **shadowslope);
>>>>>>> srb2/next
//SoM: 6/5/2000: Light sprites correctly!
void R_AddSprites(sector_t *sec, INT32 lightlevel);
@ -74,19 +66,7 @@ void R_InitSprites(void);
void R_ClearSprites(void);
void R_ClipSprites(drawseg_t* dsstart, portal_t* portal);
<<<<<<< HEAD
// -----------
// SKINS STUFF
// -----------
#define SKINNAMESIZE 16
// should be all lowercase!! S_SKIN processing does a strlwr
#define DEFAULTSKIN "sonic"
#define DEFAULTSKIN2 "tails" // secondary player
#define DEFAULTSKIN3 "knuckles" // third player
#define DEFAULTSKIN4 "eggman" // fourth player
=======
boolean R_ThingVisible (mobj_t *thing);
>>>>>>> srb2/next
boolean R_ThingVisibleWithinDist (mobj_t *thing,
fixed_t draw_dist,
@ -104,37 +84,6 @@ boolean R_PrecipThingVisible (precipmobj_t *precipthing,
*/
typedef struct
{
<<<<<<< HEAD
char name[SKINNAMESIZE+1]; // INT16 descriptive name of the skin
spritedef_t spritedef;
UINT16 wadnum;
char sprite[4]; // Sprite name, if seperated from S_SKIN.
skinflags_t flags;
char realname[SKINNAMESIZE+1]; // Display name for level completion.
char hudname[SKINNAMESIZE+1]; // HUD name to display (officially exactly 5 characters long)
char facerank[9], facewant[9], facemmap[9]; // Arbitrarily named patch lumps
// SRB2kart
UINT8 kartspeed;
UINT8 kartweight;
//
// Definable color translation table
UINT8 starttranscolor;
UINT8 prefcolor;
fixed_t highresscale; // scale of highres, default is 0.5
// specific sounds per skin
sfxenum_t soundsid[NUMSKINSOUNDS]; // sound # in S_sfx table
} skin_t;
extern CV_PossibleValue_t Forceskin_cons_t[];
// -----------
// NOT SKINS STUFF !
// -----------
=======
size_t drawsegs[2];
size_t vissprites[2];
fixed_t viewx, viewy, viewz; /**< View z stored at the time of the BSP traversal for the view/portal. Masked sorting/drawing needs it. */
@ -155,7 +104,6 @@ void R_DrawMasked(maskcount_t* masks, UINT8 nummasks);
#define VISSPRITESPERCHUNK (1 << VISSPRITECHUNKBITS)
#define VISSPRITEINDEXMASK (VISSPRITESPERCHUNK - 1)
>>>>>>> srb2/next
typedef enum
{
// actual cuts
@ -164,20 +112,12 @@ typedef enum
SC_BOTTOM = 1<<1,
// other flags
SC_PRECIP = 1<<2,
<<<<<<< HEAD
//SC_LINKDRAW = 1<<3, -- 2.2 compat
SC_LINKDRAW = 1<<3,
SC_FULLBRIGHT = 1<<4,
SC_SEMIBRIGHT = 1<<5,
SC_VFLIP = 1<<6,
SC_ISSCALED = 1<<7,
SC_SHADOW = 1<<8,
=======
SC_LINKDRAW = 1<<3,
SC_FULLBRIGHT = 1<<4,
SC_VFLIP = 1<<5,
SC_ISSCALED = 1<<6,
SC_SHADOW = 1<<7,
>>>>>>> srb2/next
// masks
SC_CUTMASK = SC_TOP|SC_BOTTOM,
SC_FLAGMASK = ~SC_CUTMASK
@ -203,13 +143,8 @@ typedef struct vissprite_s
fixed_t pz, pzt; // physical bottom/top for sorting with 3D floors
fixed_t startfrac; // horizontal position of x1
<<<<<<< HEAD
fixed_t scale, sortscale; // sortscale only differs from scale for flat sprites
fixed_t scalestep; // only for flat sprites, 0 otherwise
=======
fixed_t scale, sortscale; // sortscale only differs from scale for paper sprites and MF2_LINKDRAW
fixed_t scalestep; // only for paper sprites, 0 otherwise
>>>>>>> srb2/next
fixed_t paperoffset, paperdistance; // for paper sprites, offset/dist relative to the angle
fixed_t xiscale; // negative if flipped
@ -268,21 +203,6 @@ typedef struct drawnode_s
struct drawnode_s *prev;
} drawnode_t;
<<<<<<< HEAD
extern INT32 numskins;
extern skin_t skins[MAXSKINS];
boolean SetPlayerSkin(INT32 playernum,const char *skinname);
void SetPlayerSkinByNum(INT32 playernum,INT32 skinnum); // Tails 03-16-2002
INT32 R_SkinAvailable(const char *name);
void R_AddSkins(UINT16 wadnum);
#ifdef DELFILE
void R_DelSkins(UINT16 wadnum);
#endif
=======
>>>>>>> srb2/next
void R_InitDrawNodes(void);
// -----------------------