mirror of
https://github.com/KartKrewDev/RingRacers.git
synced 2025-10-30 08:01:28 +00:00
Merge branch 'master' into item-scale-tweak
This commit is contained in:
commit
c4cb4f32c3
35 changed files with 1275 additions and 840 deletions
22
src/d_main.c
22
src/d_main.c
|
|
@ -615,16 +615,6 @@ static void D_Display(void)
|
|||
{
|
||||
F_WipeEndScreen();
|
||||
|
||||
// Funny.
|
||||
if (WipeStageTitle && st_overlay)
|
||||
{
|
||||
lt_ticker--;
|
||||
lt_lasttic = lt_ticker;
|
||||
ST_preLevelTitleCardDrawer();
|
||||
V_DrawFill(0, 0, BASEVIDWIDTH, BASEVIDHEIGHT, levelfadecol);
|
||||
F_WipeStartScreen();
|
||||
}
|
||||
|
||||
F_RunWipe(wipedefs[wipedefindex], gamestate != GS_TIMEATTACK && gamestate != GS_TITLESCREEN, "FADEMAP0", true, false);
|
||||
}
|
||||
|
||||
|
|
@ -1057,15 +1047,6 @@ static void IdentifyVersion(void)
|
|||
D_AddFile(startupiwads, va(pandf,srb2waddir,"patch.pk3"));
|
||||
#endif
|
||||
|
||||
#if 0
|
||||
// TODO: pk3 doesn't support music replacement IIRC
|
||||
// music barely benefits from the compression anyway
|
||||
// would be nice for the folders, though
|
||||
D_AddFile(startupiwads, va(pandf,srb2waddir,"sounds.pk3"));
|
||||
D_AddFile(startupiwads, va(pandf,srb2waddir,"music.pk3"));
|
||||
|
||||
#else
|
||||
|
||||
#if !defined (HAVE_SDL) || defined (HAVE_MIXER)
|
||||
|
||||
#define MUSICTEST(str) \
|
||||
|
|
@ -1078,12 +1059,11 @@ static void IdentifyVersion(void)
|
|||
I_Error("File "str" has been modified with non-music/sound lumps"); \
|
||||
}
|
||||
|
||||
MUSICTEST("sounds.wad")
|
||||
MUSICTEST("sounds.pk3")
|
||||
MUSICTEST("music.pk3")
|
||||
|
||||
#undef MUSICTEST
|
||||
|
||||
#endif
|
||||
#endif
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -1299,16 +1299,18 @@ void PT_FileFragment(void)
|
|||
filename = va("%s", file->filename);
|
||||
nameonly(filename);
|
||||
|
||||
if (!(strcmp(filename, "main.kart")
|
||||
&& strcmp(filename, "gfx.pk3")
|
||||
&& strcmp(filename, "textures.pk3")
|
||||
&& strcmp(filename, "chars.pk3")
|
||||
&& strcmp(filename, "maps.wad")
|
||||
&& strcmp(filename, "patch.pk3")
|
||||
&& strcmp(filename, "sounds.wad")
|
||||
&& strcmp(filename, "music.wad")
|
||||
))
|
||||
if (!strcmp(filename, "main.kart")
|
||||
|| !strcmp(filename, "gfx.pk3")
|
||||
|| !strcmp(filename, "textures.pk3")
|
||||
|| !strcmp(filename, "chars.pk3")
|
||||
|| !strcmp(filename, "maps.pk3")
|
||||
|| !strcmp(filename, "patch.pk3")
|
||||
|| !strcmp(filename, "sounds.pk3")
|
||||
|| !strcmp(filename, "music.pk3")
|
||||
)
|
||||
{
|
||||
I_Error("Tried to download \"%s\"", filename);
|
||||
}
|
||||
|
||||
filename = file->filename;
|
||||
|
||||
|
|
|
|||
|
|
@ -232,6 +232,9 @@ typedef enum
|
|||
khud_cardanimation, // Used to determine the position of some full-screen Battle Mode graphics
|
||||
khud_yougotem, // "You Got Em" gfx when hitting someone as a karma player via a method that gets you back in the game instantly
|
||||
|
||||
// Tricks
|
||||
khud_trickcool,
|
||||
|
||||
NUMKARTHUD
|
||||
} karthudtype_t;
|
||||
|
||||
|
|
@ -241,6 +244,7 @@ typedef enum
|
|||
// CONSTANTS FOR TRICK PANELS
|
||||
#define TRICKMOMZRAMP (30)
|
||||
#define TRICKLAG (9)
|
||||
#define TRICKDELAY (TICRATE/4)
|
||||
|
||||
#define TUMBLEBOUNCES 3
|
||||
|
||||
|
|
@ -450,9 +454,14 @@ typedef struct player_s
|
|||
UINT8 jawztargetdelay; // (0 to 5) - Delay for Jawz target switching, to make it less twitchy
|
||||
|
||||
UINT8 trickpanel; // Trick panel state
|
||||
UINT8 tricktime; // Increases while you're tricking. You can't input any trick until it's reached a certain threshold
|
||||
fixed_t trickmomx;
|
||||
fixed_t trickmomy;
|
||||
fixed_t trickmomz;
|
||||
fixed_t trickboostpower; // Save the rough speed multiplier. Used for upwards tricks.
|
||||
UINT8 trickboostdecay; // used to know how long you've waited
|
||||
UINT8 trickboost; // Trick boost. This one is weird and has variable speed. Dear god.
|
||||
|
||||
|
||||
UINT32 roundscore; // battle score this round
|
||||
UINT8 emeralds;
|
||||
|
|
|
|||
|
|
@ -420,7 +420,7 @@ typedef struct
|
|||
extern mapheader_t* mapheaderinfo[NUMMAPS];
|
||||
|
||||
// This could support more, but is that a good idea?
|
||||
// Keep in mind that it may encourage people making overly long cups just because they "can", and would be a waste of memory.
|
||||
// Keep in mind that it may encourage people making overly long cups just because they "can", and would be a waste of memory.
|
||||
#define MAXLEVELLIST 5
|
||||
|
||||
typedef struct cupheader_s
|
||||
|
|
|
|||
|
|
@ -143,7 +143,7 @@ extern INT32 lastwipetic;
|
|||
|
||||
// Don't know where else to place this constant
|
||||
// But this file seems appropriate
|
||||
#define PRELEVELTIME 24 // frames in tics
|
||||
#define PRELEVELTIME TICRATE // frames in tics
|
||||
|
||||
void F_WipeStartScreen(void);
|
||||
void F_WipeEndScreen(void);
|
||||
|
|
|
|||
|
|
@ -415,7 +415,7 @@ void F_WipeStageTitle(void)
|
|||
if ((WipeStageTitle) && G_IsTitleCardAvailable())
|
||||
{
|
||||
ST_runTitleCard();
|
||||
ST_drawWipeTitleCard();
|
||||
ST_drawTitleCard();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
21
src/g_demo.c
21
src/g_demo.c
|
|
@ -347,6 +347,7 @@ void G_ReadDemoExtraData(void)
|
|||
players[p].pflags &= ~(PF_KICKSTARTACCEL);
|
||||
if (extradata & 1)
|
||||
players[p].pflags |= PF_KICKSTARTACCEL;
|
||||
//CONS_Printf("weaponpref is %d for player %d\n", extradata, p);
|
||||
}
|
||||
|
||||
p = READUINT8(demo_p);
|
||||
|
|
@ -2656,7 +2657,7 @@ void G_DoPlayDemo(char *defdemoname)
|
|||
UINT32 randseed;
|
||||
char msg[1024];
|
||||
|
||||
boolean spectator;
|
||||
boolean spectator, kickstart;
|
||||
UINT8 slots[MAXPLAYERS], kartspeed[MAXPLAYERS], kartweight[MAXPLAYERS], numslots = 0;
|
||||
|
||||
#if defined(SKIPERRORS) && !defined(DEVELOP)
|
||||
|
|
@ -2925,16 +2926,8 @@ void G_DoPlayDemo(char *defdemoname)
|
|||
|
||||
while (p != 0xFF)
|
||||
{
|
||||
players[p].pflags &= ~PF_KICKSTARTACCEL;
|
||||
if (p & DEMO_KICKSTART)
|
||||
if ((spectator = (p & DEMO_SPECTATOR)))
|
||||
{
|
||||
players[p].pflags |= PF_KICKSTARTACCEL;
|
||||
p &= ~DEMO_KICKSTART;
|
||||
}
|
||||
spectator = false;
|
||||
if (p & DEMO_SPECTATOR)
|
||||
{
|
||||
spectator = true;
|
||||
p &= ~DEMO_SPECTATOR;
|
||||
|
||||
if (modeattacking)
|
||||
|
|
@ -2949,6 +2942,10 @@ void G_DoPlayDemo(char *defdemoname)
|
|||
return;
|
||||
}
|
||||
}
|
||||
|
||||
if ((kickstart = (p & DEMO_KICKSTART)))
|
||||
p &= ~DEMO_KICKSTART;
|
||||
|
||||
slots[numslots] = p; numslots++;
|
||||
|
||||
if (modeattacking && numslots > 1)
|
||||
|
|
@ -2968,6 +2965,10 @@ void G_DoPlayDemo(char *defdemoname)
|
|||
|
||||
playeringame[p] = true;
|
||||
players[p].spectator = spectator;
|
||||
if (kickstart)
|
||||
players[p].pflags |= PF_KICKSTARTACCEL;
|
||||
else
|
||||
players[p].pflags &= ~PF_KICKSTARTACCEL;
|
||||
|
||||
// Name
|
||||
M_Memcpy(player_names[p],demo_p,16);
|
||||
|
|
|
|||
41
src/g_game.c
41
src/g_game.c
|
|
@ -1139,7 +1139,7 @@ void G_BuildTiccmd(ticcmd_t *cmd, INT32 realtics, UINT8 ssplayer)
|
|||
|
||||
// Send leveltime when this tic was generated to the server for control lag calculations.
|
||||
// Only do this when in a level. Also do this after the hook, so that it can't overwrite this.
|
||||
cmd->latency = (leveltime & 0xFF);
|
||||
cmd->latency = (leveltime & 0xFF);
|
||||
}
|
||||
|
||||
if (cmd->forwardmove > MAXPLMOVE)
|
||||
|
|
@ -1301,7 +1301,7 @@ void G_StartTitleCard(void)
|
|||
ST_startTitleCard();
|
||||
|
||||
// start the title card
|
||||
WipeStageTitle = false; //(!titlemapinaction); -- temporary until titlecards are reworked
|
||||
WipeStageTitle = (!titlemapinaction);
|
||||
}
|
||||
|
||||
//
|
||||
|
|
@ -1310,26 +1310,27 @@ void G_StartTitleCard(void)
|
|||
void G_PreLevelTitleCard(void)
|
||||
{
|
||||
#ifndef NOWIPE
|
||||
tic_t strtime = I_GetTime();
|
||||
tic_t endtime = strtime + (PRELEVELTIME*NEWTICRATERATIO);
|
||||
tic_t nowtime = strtime;
|
||||
tic_t lasttime = strtime;
|
||||
while (nowtime < endtime)
|
||||
{
|
||||
// draw loop
|
||||
while (!((nowtime = I_GetTime()) - lasttime))
|
||||
I_Sleep();
|
||||
lasttime = nowtime;
|
||||
tic_t strtime = I_GetTime();
|
||||
tic_t endtime = strtime + (PRELEVELTIME*NEWTICRATERATIO);
|
||||
tic_t nowtime = strtime;
|
||||
tic_t lasttime = strtime;
|
||||
while (nowtime < endtime)
|
||||
{
|
||||
// draw loop
|
||||
ST_runTitleCard();
|
||||
ST_preLevelTitleCardDrawer();
|
||||
I_FinishUpdate(); // page flip or blit buffer
|
||||
NetKeepAlive(); // Prevent timeouts
|
||||
|
||||
ST_runTitleCard();
|
||||
ST_preLevelTitleCardDrawer();
|
||||
I_FinishUpdate(); // page flip or blit buffer
|
||||
if (moviemode)
|
||||
M_SaveFrame();
|
||||
if (takescreenshot) // Only take screenshots after drawing.
|
||||
M_DoScreenShot();
|
||||
|
||||
if (moviemode)
|
||||
M_SaveFrame();
|
||||
if (takescreenshot) // Only take screenshots after drawing.
|
||||
M_DoScreenShot();
|
||||
}
|
||||
while (!((nowtime = I_GetTime()) - lasttime))
|
||||
I_Sleep();
|
||||
lasttime = nowtime;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -73,6 +73,8 @@
|
|||
patch_t *pinggfx[5]; // small ping graphic
|
||||
patch_t *mping[5]; // smaller ping graphic
|
||||
|
||||
patch_t *tc_font[2][LT_FONTSIZE]; // Special font stuff for titlecard
|
||||
|
||||
patch_t *framecounter;
|
||||
patch_t *frameslash; // framerate stuff. Used in screen.c
|
||||
|
||||
|
|
@ -178,7 +180,8 @@ static void Got_Saycmd(UINT8 **p, INT32 playernum);
|
|||
|
||||
void HU_LoadGraphics(void)
|
||||
{
|
||||
INT32 i;
|
||||
char buffer[9];
|
||||
INT32 i, j;
|
||||
|
||||
if (dedicated)
|
||||
return;
|
||||
|
|
@ -191,6 +194,27 @@ void HU_LoadGraphics(void)
|
|||
emblemicon = HU_CachePatch("EMBLICON");
|
||||
songcreditbg = HU_CachePatch("K_SONGCR");
|
||||
|
||||
// Cache titlecard font
|
||||
j = LT_FONTSTART;
|
||||
for (i = 0; i < LT_FONTSIZE; i++, j++)
|
||||
{
|
||||
// cache the titlecard font
|
||||
|
||||
// Bottom layer
|
||||
sprintf(buffer, "GTOL%.3d", j);
|
||||
if (W_CheckNumForName(buffer) == LUMPERROR)
|
||||
tc_font[0][i] = NULL;
|
||||
else
|
||||
tc_font[0][i] = (patch_t *)W_CachePatchName(buffer, PU_HUDGFX);
|
||||
|
||||
// Top layer
|
||||
sprintf(buffer, "GTFN%.3d", j);
|
||||
if (W_CheckNumForName(buffer) == LUMPERROR)
|
||||
tc_font[1][i] = NULL;
|
||||
else
|
||||
tc_font[1][i] = (patch_t *)W_CachePatchName(buffer, PU_HUDGFX);
|
||||
}
|
||||
|
||||
// cache ping gfx:
|
||||
for (i = 0; i < 5; i++)
|
||||
{
|
||||
|
|
@ -704,7 +728,7 @@ static void Got_Saycmd(UINT8 **p, INT32 playernum)
|
|||
}
|
||||
else if (target == -1) // say team
|
||||
{
|
||||
if (players[playernum].ctfteam == 1)
|
||||
if (players[playernum].ctfteam == 1)
|
||||
{
|
||||
// red text
|
||||
cstart = textcolor = "\x85";
|
||||
|
|
|
|||
|
|
@ -39,6 +39,11 @@
|
|||
#define LT_FONTEND 'z' // the last font characters
|
||||
#define LT_FONTSIZE (LT_FONTEND - LT_FONTSTART + 1)
|
||||
|
||||
// Under regular circumstances, we'd use the built in font stuff, however this font is a bit messy because of how we're gonna draw shit.
|
||||
// tc_font[0][n] is used for the "bottom" layer
|
||||
// tc_font[1][n] is used for the "top" layer
|
||||
extern patch_t *tc_font[2][LT_FONTSIZE];
|
||||
|
||||
#define CRED_FONTSTART '!' // the first font character
|
||||
#define CRED_FONTEND 'Z' // the last font character
|
||||
#define CRED_FONTSIZE (CRED_FONTEND - CRED_FONTSTART + 1)
|
||||
|
|
|
|||
|
|
@ -748,6 +748,8 @@ char sprnames[NUMSPRITES + 1][5] =
|
|||
"SDDS", // Spindash dust
|
||||
"SDWN", // Spindash wind
|
||||
|
||||
"TRCK",
|
||||
|
||||
"FLBM",
|
||||
|
||||
// First person view sprites; this is a sprite so that it can be replaced by a specialized MD2 draw later
|
||||
|
|
|
|||
|
|
@ -1290,6 +1290,8 @@ typedef enum sprite
|
|||
SPR_SDDS, // Spindash dust
|
||||
SPR_SDWN, // Spindash wind
|
||||
|
||||
SPR_TRCK,
|
||||
|
||||
SPR_FLBM, // Finish line beam
|
||||
|
||||
// First person view sprites; this is a sprite so that it can be replaced by a specialized MD2 draw later
|
||||
|
|
|
|||
44
src/k_hud.c
44
src/k_hud.c
|
|
@ -162,6 +162,8 @@ static patch_t *kp_cpu;
|
|||
|
||||
static patch_t *kp_nametagstem;
|
||||
|
||||
static patch_t *kp_trickcool[2];
|
||||
|
||||
void K_LoadKartHUDGraphics(void)
|
||||
{
|
||||
INT32 i, j;
|
||||
|
|
@ -601,6 +603,9 @@ void K_LoadKartHUDGraphics(void)
|
|||
kp_cpu = (patch_t *) W_CachePatchName("K_CPU", PU_HUDGFX);
|
||||
|
||||
kp_nametagstem = (patch_t *) W_CachePatchName("K_NAMEST", PU_HUDGFX);
|
||||
|
||||
kp_trickcool[0] = W_CachePatchName("K_COOL1", PU_HUDGFX);
|
||||
kp_trickcool[1] = W_CachePatchName("K_COOL2", PU_HUDGFX);
|
||||
}
|
||||
|
||||
// For the item toggle menu
|
||||
|
|
@ -679,6 +684,9 @@ INT32 ITEM2_X, ITEM2_Y;
|
|||
INT32 LAPS2_X, LAPS2_Y;
|
||||
INT32 POSI2_X, POSI2_Y;
|
||||
|
||||
// trick "cool"
|
||||
INT32 TCOOL_X, TCOOL_Y;
|
||||
|
||||
|
||||
void K_AdjustXYWithSnap(INT32 *x, INT32 *y, UINT32 options, INT32 dupx, INT32 dupy)
|
||||
{
|
||||
|
|
@ -982,6 +990,10 @@ static void K_initKartHUD(void)
|
|||
WANT_X = BASEVIDWIDTH - 55; // 270
|
||||
WANT_Y = BASEVIDHEIGHT- 71; // 176
|
||||
|
||||
// trick COOL
|
||||
TCOOL_X = (BASEVIDWIDTH)/2;
|
||||
TCOOL_Y = (BASEVIDHEIGHT)/2 -10;
|
||||
|
||||
if (r_splitscreen) // Splitscreen
|
||||
{
|
||||
ITEM_X = 5;
|
||||
|
|
@ -1024,6 +1036,8 @@ static void K_initKartHUD(void)
|
|||
MINI_X = (3*BASEVIDWIDTH/4);
|
||||
MINI_Y = (3*BASEVIDHEIGHT/4);
|
||||
|
||||
TCOOL_X = (BASEVIDWIDTH)/4;
|
||||
|
||||
if (r_splitscreen > 2) // 4P-only
|
||||
{
|
||||
MINI_X = (BASEVIDWIDTH/2);
|
||||
|
|
@ -3951,6 +3965,32 @@ static void K_drawLapStartAnim(void)
|
|||
}
|
||||
}
|
||||
|
||||
// stretch for "COOOOOL" popup.
|
||||
// I can't be fucked to find out any math behind this so have a table lmao
|
||||
static fixed_t stretch[6][2] = {
|
||||
{FRACUNIT/4, FRACUNIT*4},
|
||||
{FRACUNIT/2, FRACUNIT*2},
|
||||
{FRACUNIT, FRACUNIT},
|
||||
{FRACUNIT*4, FRACUNIT/2},
|
||||
{FRACUNIT*8, FRACUNIT/4},
|
||||
{FRACUNIT*4, FRACUNIT/2},
|
||||
};
|
||||
|
||||
static void K_drawTrickCool(void)
|
||||
{
|
||||
|
||||
tic_t timer = TICRATE - stplyr->karthud[khud_trickcool];
|
||||
|
||||
if (timer <= 6)
|
||||
{
|
||||
V_DrawStretchyFixedPatch(TCOOL_X<<FRACBITS, TCOOL_Y<<FRACBITS, stretch[timer-1][0], stretch[timer-1][1], V_HUDTRANS|V_SPLITSCREEN, kp_trickcool[splitscreen ? 1 : 0], NULL);
|
||||
}
|
||||
else if (leveltime & 1)
|
||||
{
|
||||
V_DrawFixedPatch(TCOOL_X<<FRACBITS, (TCOOL_Y<<FRACBITS) - (timer-10)*FRACUNIT/2, FRACUNIT, V_HUDTRANS|V_SPLITSCREEN, kp_trickcool[splitscreen ? 1 : 0], NULL);
|
||||
}
|
||||
}
|
||||
|
||||
void K_drawKartFreePlay(void)
|
||||
{
|
||||
// no splitscreen support because it's not FREE PLAY if you have more than one player in-game
|
||||
|
|
@ -4323,6 +4363,10 @@ void K_drawKartHUD(void)
|
|||
K_drawLapStartAnim();
|
||||
}
|
||||
|
||||
// trick panel cool trick
|
||||
if (stplyr->karthud[khud_trickcool])
|
||||
K_drawTrickCool();
|
||||
|
||||
if (modeattacking || freecam) // everything after here is MP and debug only
|
||||
return;
|
||||
|
||||
|
|
|
|||
177
src/k_kart.c
177
src/k_kart.c
|
|
@ -2771,6 +2771,11 @@ static void K_GetKartBoostPower(player_t *player)
|
|||
}
|
||||
}
|
||||
|
||||
if (player->trickboost) // Trick pannel up-boost
|
||||
{
|
||||
ADDBOOST(player->trickboostpower, 5*FRACUNIT, 0); // <trickboostpower>% speed, 500% accel, 0% handling
|
||||
}
|
||||
|
||||
if (player->ringboost) // Ring Boost
|
||||
{
|
||||
ADDBOOST(FRACUNIT/5, 4*FRACUNIT, 0); // + 20% top speed, + 400% acceleration, +0% handling
|
||||
|
|
@ -5093,7 +5098,10 @@ void K_DoPogoSpring(mobj_t *mo, fixed_t vertispeed, UINT8 sound)
|
|||
thrust = FixedMul(thrust, 9*FRACUNIT/8);
|
||||
}
|
||||
|
||||
mo->player->trickmomx = mo->player->trickmomy = mo->player->trickmomz = 0; // Reset post-hitlag momentums.
|
||||
mo->player->trickmomx = mo->player->trickmomy = mo->player->trickmomz = mo->player->tricktime = 0; // Reset post-hitlag momentums and timer
|
||||
// Setup the boost for potential upwards trick, at worse, make it your regular max speed. (boost = curr speed*1.25)
|
||||
mo->player->trickboostpower = max(FixedDiv(mo->player->speed, K_GetKartSpeed(mo->player, false)) - FRACUNIT, 0)*125/100;
|
||||
//CONS_Printf("Got boost: %d%\n", mo->player->trickboostpower*100 / FRACUNIT);
|
||||
}
|
||||
|
||||
mo->momz = FixedMul(thrust, vscale);
|
||||
|
|
@ -6324,6 +6332,9 @@ void K_KartPlayerHUDUpdate(player_t *player)
|
|||
if (player->karthud[khud_tauntvoices])
|
||||
player->karthud[khud_tauntvoices]--;
|
||||
|
||||
if (player->karthud[khud_trickcool])
|
||||
player->karthud[khud_trickcool]--;
|
||||
|
||||
if (!(player->pflags & PF_FAULT))
|
||||
player->karthud[khud_fault] = 0;
|
||||
else if (player->karthud[khud_fault] > 0 && player->karthud[khud_fault] < 2*TICRATE)
|
||||
|
|
@ -6517,7 +6528,7 @@ void K_KartPlayerThink(player_t *player, ticcmd_t *cmd)
|
|||
// Speed lines
|
||||
if (player->sneakertimer || player->ringboost
|
||||
|| player->driftboost || player->startboost
|
||||
|| player->eggmanexplode)
|
||||
|| player->eggmanexplode || player->trickboost)
|
||||
{
|
||||
if (player->invincibilitytimer)
|
||||
K_SpawnInvincibilitySpeedLines(player->mo);
|
||||
|
|
@ -6532,7 +6543,7 @@ void K_KartPlayerThink(player_t *player, ticcmd_t *cmd)
|
|||
ghost->extravalue1 = player->numboosts+1;
|
||||
ghost->extravalue2 = (leveltime % ghost->extravalue1);
|
||||
ghost->fuse = ghost->extravalue1;
|
||||
ghost->frame |= FF_FULLBRIGHT;
|
||||
ghost->renderflags |= RF_FULLBRIGHT;
|
||||
ghost->colorized = true;
|
||||
//ghost->color = player->skincolor;
|
||||
//ghost->momx = (3*player->mo->momx)/4;
|
||||
|
|
@ -6758,6 +6769,9 @@ void K_KartPlayerThink(player_t *player, ticcmd_t *cmd)
|
|||
}
|
||||
}
|
||||
|
||||
if (player->trickboost)
|
||||
player->trickboost--;
|
||||
|
||||
if (player->flamedash)
|
||||
player->flamedash--;
|
||||
|
||||
|
|
@ -7501,9 +7515,9 @@ INT16 K_GetKartTurnValue(player_t *player, INT16 turnvalue)
|
|||
return 0;
|
||||
}
|
||||
|
||||
if (player->trickpanel != 0)
|
||||
if (player->trickpanel != 0 && player->trickpanel < 4)
|
||||
{
|
||||
// No turning during trick panel
|
||||
// No turning during trick panel unless you did the upwards trick (4)
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
@ -8362,6 +8376,86 @@ void K_AdjustPlayerFriction(player_t *player)
|
|||
}
|
||||
}
|
||||
|
||||
//
|
||||
// K_trickPanelTimingVisual
|
||||
// Spawns the timing visual for trick panels depending on the given player's momz.
|
||||
// If the player has tricked and is not in hitlag, this will send the half circles flying out.
|
||||
// if you tumble, they'll fall off instead.
|
||||
//
|
||||
|
||||
#define RADIUSSCALING 6
|
||||
#define MINRADIUS 12
|
||||
|
||||
static void K_trickPanelTimingVisual(player_t *player, fixed_t momz)
|
||||
{
|
||||
|
||||
fixed_t pos, tx, ty, tz;
|
||||
mobj_t *flame;
|
||||
|
||||
angle_t hang = R_PointToAnglePlayer(player, player->mo->x, player->mo->y) + ANG1*90; // horizontal angle
|
||||
angle_t vang = -FixedAngle(momz)*12 + (ANG1*45); // vertical angle dependant on momz, we want it to line up at 45 degrees at the perfect frame to trick at
|
||||
fixed_t dist = FixedMul(max(MINRADIUS<<FRACBITS, abs(momz)*RADIUSSCALING), player->mo->scale); // distance.
|
||||
|
||||
UINT8 i;
|
||||
|
||||
// Do you like trig? cool, me neither.
|
||||
for (i=0; i < 2; i++)
|
||||
{
|
||||
pos = FixedMul(dist, FINESINE(vang>>ANGLETOFINESHIFT));
|
||||
tx = player->mo->x + FixedMul(pos, FINECOSINE(hang>>ANGLETOFINESHIFT));
|
||||
ty = player->mo->y + FixedMul(pos, FINESINE(hang>>ANGLETOFINESHIFT));
|
||||
tz = player->mo->z + player->mo->height/2 + FixedMul(dist, FINECOSINE(vang>>ANGLETOFINESHIFT));
|
||||
|
||||
// All coordinates set, spawn our fire, now.
|
||||
flame = P_SpawnMobj(tx, ty, tz, MT_THOK);
|
||||
|
||||
P_SetScale(flame, player->mo->scale);
|
||||
|
||||
// Visuals
|
||||
flame->sprite = SPR_TRCK;
|
||||
flame->frame = i|FF_FULLBRIGHT;
|
||||
|
||||
if (player->trickpanel <= 1 && !player->tumbleBounces)
|
||||
flame->tics = 2;
|
||||
else
|
||||
{
|
||||
flame->tics = TICRATE;
|
||||
|
||||
if (player->trickpanel > 1) // we tricked
|
||||
{
|
||||
// Send the thing outwards via ghetto maths which involves redoing the whole 3d sphere again, witht the "vertical" angle shifted by 90 degrees.
|
||||
// There's probably a simplier way to do this the way I want to but this works.
|
||||
pos = FixedMul(48*player->mo->scale, FINESINE((vang +ANG1*90)>>ANGLETOFINESHIFT));
|
||||
tx = player->mo->x + FixedMul(pos, FINECOSINE(hang>>ANGLETOFINESHIFT));
|
||||
ty = player->mo->y + FixedMul(pos, FINESINE(hang>>ANGLETOFINESHIFT));
|
||||
tz = player->mo->z + player->mo->height/2 + FixedMul(48*player->mo->scale, FINECOSINE((vang +ANG1*90)>>ANGLETOFINESHIFT));
|
||||
|
||||
flame->momx = tx -player->mo->x;
|
||||
flame->momy = ty -player->mo->y;
|
||||
flame->momz = tz -(player->mo->z+player->mo->height/2);
|
||||
}
|
||||
else // we failed the trick, drop the half circles, it'll be funny I promise.
|
||||
{
|
||||
flame->flags &= ~MF_NOGRAVITY;
|
||||
P_SetObjectMomZ(flame, 4<<FRACBITS, false);
|
||||
P_InstaThrust(flame, R_PointToAngle2(player->mo->x, player->mo->y, flame->x, flame->y), 8*mapobjectscale);
|
||||
flame->momx += player->mo->momx;
|
||||
flame->momy += player->mo->momy;
|
||||
flame->momz += player->mo->momz;
|
||||
}
|
||||
}
|
||||
|
||||
// make sure this is only drawn for our local player
|
||||
flame->renderflags |= (RF_DONTDRAW & ~K_GetPlayerDontDrawFlag(player));
|
||||
|
||||
vang += FixedAngle(180<<FRACBITS); // Avoid overflow warnings...
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
#undef RADIUSSCALING
|
||||
#undef MINRADIUS
|
||||
|
||||
//
|
||||
// K_MoveKartPlayer
|
||||
//
|
||||
|
|
@ -9025,6 +9119,43 @@ void K_MoveKartPlayer(player_t *player, boolean onground)
|
|||
fixed_t basespeed = P_AproxDistance(player->mo->momx, player->mo->momy); // at WORSE, keep your normal speed when tricking.
|
||||
fixed_t speed = FixedMul(speedmult, P_AproxDistance(player->mo->momx, player->mo->momy));
|
||||
|
||||
K_trickPanelTimingVisual(player, momz);
|
||||
|
||||
// streaks:
|
||||
if (momz*P_MobjFlip(player->mo) > 0) // only spawn those while you're going upwards relative to your current gravity
|
||||
{
|
||||
// these are all admittedly arbitrary numbers...
|
||||
INT32 n;
|
||||
INT32 maxlines = max(1, (momz/FRACUNIT)/16);
|
||||
INT32 frequency = max(1, 5-(momz/FRACUNIT)/4);
|
||||
fixed_t sx, sy, sz;
|
||||
mobj_t *spdl;
|
||||
|
||||
if (!(leveltime % frequency))
|
||||
{
|
||||
for (n=0; n < maxlines; n++)
|
||||
{
|
||||
sx = player->mo->x + P_RandomRange(-24, 24)*player->mo->scale;
|
||||
sy = player->mo->y + P_RandomRange(-24, 24)*player->mo->scale;
|
||||
sz = player->mo->z + P_RandomRange(0, 48)*player->mo->scale;
|
||||
|
||||
spdl = P_SpawnMobj(sx, sy, sz, MT_FASTLINE);
|
||||
P_SetTarget(&spdl->target, player->mo);
|
||||
spdl->angle = R_PointToAngle2(spdl->x, spdl->y, player->mo->x, player->mo->y);
|
||||
spdl->rollangle = -ANG1*90*P_MobjFlip(player->mo); // angle them downwards relative to the player's gravity...
|
||||
spdl->spriteyscale = player->trickboostpower+FRACUNIT;
|
||||
spdl->momx = player->mo->momx;
|
||||
spdl->momy = player->mo->momy;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
// We'll never need to go above that.
|
||||
if (player->tricktime <= TRICKDELAY)
|
||||
player->tricktime++;
|
||||
|
||||
// debug shit
|
||||
//CONS_Printf("%d\n", player->mo->momz / mapobjectscale);
|
||||
if (momz < -10*FRACUNIT) // :youfuckedup:
|
||||
|
|
@ -9034,11 +9165,22 @@ void K_MoveKartPlayer(player_t *player, boolean onground)
|
|||
player->pflags &= ~PF_TUMBLESOUND;
|
||||
player->tumbleHeight = 30; // Base tumble bounce height
|
||||
player->trickpanel = 0;
|
||||
K_trickPanelTimingVisual(player, momz); // fail trick visual
|
||||
P_SetPlayerMobjState(player->mo, S_KART_SPINOUT);
|
||||
}
|
||||
|
||||
else if (!(player->pflags & PF_TRICKDELAY)) // don't allow tricking at the same frame you tumble obv
|
||||
{
|
||||
|
||||
// "COOL" timing n shit.
|
||||
if (cmd->turning || player->throwdir)
|
||||
{
|
||||
if (abs(momz) < FRACUNIT*99) // Let's use that as baseline for PERFECT trick.
|
||||
{
|
||||
player->karthud[khud_trickcool] = TICRATE;
|
||||
}
|
||||
}
|
||||
|
||||
// Uses cmd->turning over steering intentionally.
|
||||
if (cmd->turning > 0)
|
||||
{
|
||||
|
|
@ -9052,6 +9194,7 @@ void K_MoveKartPlayer(player_t *player, boolean onground)
|
|||
|
||||
player->trickpanel = 2;
|
||||
player->mo->hitlag = TRICKLAG;
|
||||
K_trickPanelTimingVisual(player, momz);
|
||||
}
|
||||
else if (cmd->turning < 0)
|
||||
{
|
||||
|
|
@ -9065,6 +9208,7 @@ void K_MoveKartPlayer(player_t *player, boolean onground)
|
|||
|
||||
player->trickpanel = 3;
|
||||
player->mo->hitlag = TRICKLAG;
|
||||
K_trickPanelTimingVisual(player, momz);
|
||||
}
|
||||
else if (player->throwdir == 1)
|
||||
{
|
||||
|
|
@ -9083,6 +9227,7 @@ void K_MoveKartPlayer(player_t *player, boolean onground)
|
|||
|
||||
player->trickpanel = 2;
|
||||
player->mo->hitlag = TRICKLAG;
|
||||
K_trickPanelTimingVisual(player, momz);
|
||||
}
|
||||
else if (player->throwdir == -1)
|
||||
{
|
||||
|
|
@ -9096,6 +9241,12 @@ void K_MoveKartPlayer(player_t *player, boolean onground)
|
|||
relative = false;
|
||||
}
|
||||
|
||||
// Calculate speed boost decay:
|
||||
// Base speed boost duration is 35 tics.
|
||||
// At most, lose 3/4th of your boost.
|
||||
player->trickboostdecay = min(TICRATE*3/4, abs(momz/FRACUNIT));
|
||||
//CONS_Printf("decay: %d\n", player->trickboostdecay);
|
||||
|
||||
P_SetObjectMomZ(player->mo, 48*FRACUNIT, relative);
|
||||
|
||||
player->trickmomx = player->mo->momx;
|
||||
|
|
@ -9104,8 +9255,9 @@ void K_MoveKartPlayer(player_t *player, boolean onground)
|
|||
P_InstaThrust(player->mo, 0, 0); // Sike, you have no speed :)
|
||||
player->mo->momz = 0;
|
||||
|
||||
player->trickpanel = 3;
|
||||
player->trickpanel = 4;
|
||||
player->mo->hitlag = TRICKLAG;
|
||||
K_trickPanelTimingVisual(player, momz);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -9120,8 +9272,19 @@ void K_MoveKartPlayer(player_t *player, boolean onground)
|
|||
|
||||
}
|
||||
|
||||
else if (player->trickpanel == 4 && P_IsObjectOnGround(player->mo)) // Upwards trick landed!
|
||||
{
|
||||
//CONS_Printf("apply boost\n");
|
||||
S_StartSound(player->mo, sfx_s23c);
|
||||
K_SpawnDashDustRelease(player);
|
||||
player->trickboost = TICRATE - player->trickboostdecay;
|
||||
|
||||
player->trickpanel = player->trickboostdecay = 0;
|
||||
}
|
||||
|
||||
// Wait until we let go off the control stick to remove the delay
|
||||
if ((player->pflags & PF_TRICKDELAY) && !player->throwdir && !cmd->turning)
|
||||
// buttons must be neutral after the initial trick delay. This prevents weirdness where slight nudges after blast off would send you flying.
|
||||
if ((player->pflags & PF_TRICKDELAY) && !player->throwdir && !cmd->turning && (player->tricktime >= TRICKDELAY))
|
||||
{
|
||||
player->pflags &= ~PF_TRICKDELAY;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -2098,6 +2098,16 @@ static int lib_rPointToAngle(lua_State *L)
|
|||
return 1;
|
||||
}
|
||||
|
||||
static int lib_rPointToAnglePlayer(lua_State *L)
|
||||
{
|
||||
player_t *player = *((player_t **)luaL_checkudata(L, 1, META_PLAYER));
|
||||
fixed_t x = luaL_checkfixed(L, 2);
|
||||
fixed_t y = luaL_checkfixed(L, 3);
|
||||
//HUDSAFE
|
||||
lua_pushangle(L, R_PointToAnglePlayer(player, x, y));
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int lib_rPointToAngle2(lua_State *L)
|
||||
{
|
||||
fixed_t px2 = luaL_checkfixed(L, 1);
|
||||
|
|
@ -3874,6 +3884,7 @@ static luaL_Reg lib[] = {
|
|||
|
||||
// r_defs
|
||||
{"R_PointToAngle",lib_rPointToAngle},
|
||||
{"R_PointToAnglePlayer", lib_rPointToAnglePlayer},
|
||||
{"R_PointToAngle2",lib_rPointToAngle2},
|
||||
{"R_PointToDist",lib_rPointToDist},
|
||||
{"R_PointToDist2",lib_rPointToDist2},
|
||||
|
|
|
|||
|
|
@ -946,6 +946,24 @@ static int libd_drawString(lua_State *L)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int libd_drawTitleCardString(lua_State *L)
|
||||
{
|
||||
|
||||
fixed_t x = luaL_checkinteger(L, 1);
|
||||
fixed_t y = luaL_checkinteger(L, 2);
|
||||
const char *str = luaL_checkstring(L, 3);
|
||||
INT32 flags = luaL_optinteger(L, 4, V_ALLOWLOWERCASE);
|
||||
boolean rightalign = lua_optboolean(L, 5);
|
||||
INT32 timer = luaL_optinteger(L, 6, 0);
|
||||
INT32 threshold = luaL_optinteger(L, 7, 0);
|
||||
|
||||
flags &= ~V_PARAMMASK; // Don't let crashes happen.
|
||||
|
||||
HUDONLY
|
||||
V_DrawTitleCardString(x, y, str, flags, rightalign, timer, threshold);
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int libd_drawKartString(lua_State *L)
|
||||
{
|
||||
fixed_t x = luaL_checkinteger(L, 1);
|
||||
|
|
@ -960,6 +978,15 @@ static int libd_drawKartString(lua_State *L)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static int libd_titleCardStringWidth(lua_State *L)
|
||||
{
|
||||
const char *str = luaL_checkstring(L, 1);
|
||||
HUDONLY
|
||||
|
||||
lua_pushinteger(L, V_TitleCardStringWidth(str));
|
||||
return 1;
|
||||
}
|
||||
|
||||
static int libd_stringWidth(lua_State *L)
|
||||
{
|
||||
const char *str = luaL_checkstring(L, 1);
|
||||
|
|
@ -1163,9 +1190,11 @@ static luaL_Reg lib_draw[] = {
|
|||
{"drawFill", libd_drawFill},
|
||||
{"fadeScreen", libd_fadeScreen},
|
||||
{"drawString", libd_drawString},
|
||||
{"drawTitleCardString", libd_drawTitleCardString},
|
||||
{"drawKartString", libd_drawKartString},
|
||||
// misc
|
||||
{"stringWidth", libd_stringWidth},
|
||||
{"titleCardStringWidth", libd_titleCardStringWidth},
|
||||
// m_random
|
||||
{"RandomFixed",libd_RandomFixed},
|
||||
{"RandomByte",libd_RandomByte},
|
||||
|
|
|
|||
|
|
@ -354,12 +354,20 @@ static int player_get(lua_State *L)
|
|||
lua_pushinteger(L, plr->glanceDir);
|
||||
else if (fastcmp(field,"trickpanel"))
|
||||
lua_pushinteger(L, plr->trickpanel);
|
||||
else if (fastcmp(field,"tricktime"))
|
||||
lua_pushinteger(L, plr->tricktime);
|
||||
else if (fastcmp(field,"trickmomx"))
|
||||
lua_pushfixed(L, plr->trickmomx);
|
||||
else if (fastcmp(field,"trickmomy"))
|
||||
lua_pushfixed(L, plr->trickmomy);
|
||||
else if (fastcmp(field,"trickmomz"))
|
||||
lua_pushfixed(L, plr->trickmomz);
|
||||
else if (fastcmp(field,"trickboostpower"))
|
||||
lua_pushfixed(L, plr->trickboostpower);
|
||||
else if (fastcmp(field,"trickboostdecay"))
|
||||
lua_pushinteger(L, plr->trickboostdecay);
|
||||
else if (fastcmp(field,"trickboost"))
|
||||
lua_pushinteger(L, plr->trickboost);
|
||||
else if (fastcmp(field,"roundscore"))
|
||||
plr->roundscore = luaL_checkinteger(L, 3);
|
||||
else if (fastcmp(field,"emeralds"))
|
||||
|
|
@ -697,12 +705,20 @@ static int player_set(lua_State *L)
|
|||
plr->glanceDir = luaL_checkinteger(L, 3);
|
||||
else if (fastcmp(field,"trickpanel"))
|
||||
plr->trickpanel = luaL_checkinteger(L, 3);
|
||||
else if (fastcmp(field,"tricktime"))
|
||||
plr->tricktime = luaL_checkinteger(L, 3);
|
||||
else if (fastcmp(field,"trickmomx"))
|
||||
plr->trickmomx = luaL_checkfixed(L, 3);
|
||||
else if (fastcmp(field,"trickmomy"))
|
||||
plr->trickmomy = luaL_checkfixed(L, 3);
|
||||
else if (fastcmp(field,"trickmomz"))
|
||||
plr->trickmomz = luaL_checkfixed(L, 3);
|
||||
else if (fastcmp(field,"trickboostpower"))
|
||||
plr->trickboostpower = luaL_checkfixed(L, 3);
|
||||
else if (fastcmp(field,"trickboostdecay"))
|
||||
plr->trickboostdecay = luaL_checkinteger(L, 3);
|
||||
else if (fastcmp(field,"trickboost"))
|
||||
plr->trickboost = luaL_checkinteger(L, 3);
|
||||
else if (fastcmp(field,"roundscore"))
|
||||
lua_pushinteger(L, plr->roundscore);
|
||||
else if (fastcmp(field,"emeralds"))
|
||||
|
|
|
|||
|
|
@ -11044,7 +11044,7 @@ void A_FadeOverlay(mobj_t *actor)
|
|||
return;
|
||||
|
||||
fade = P_SpawnGhostMobj(actor);
|
||||
fade->frame = actor->frame;
|
||||
fade->renderflags = actor->renderflags;
|
||||
|
||||
if (!(locvar1 & 1))
|
||||
{
|
||||
|
|
|
|||
41
src/p_mobj.c
41
src/p_mobj.c
|
|
@ -1109,7 +1109,7 @@ fixed_t P_GetMobjGravity(mobj_t *mo)
|
|||
gravityadd = (4*gravityadd)/3;
|
||||
}
|
||||
|
||||
if (mo->player->trickpanel == 2 || mo->player->trickpanel == 3)
|
||||
if (mo->player->trickpanel >= 2)
|
||||
{
|
||||
gravityadd = (5*gravityadd)/2;
|
||||
}
|
||||
|
|
@ -8492,17 +8492,29 @@ void P_MobjThinker(mobj_t *mobj)
|
|||
|
||||
if (mobj->type == MT_GHOST && mobj->fuse > 0) // Not guaranteed to be MF_SCENERY or not MF_SCENERY!
|
||||
{
|
||||
if (mobj->flags2 & MF2_BOSSNOTRAP) // "fast" flag
|
||||
if (mobj->extravalue1 > 0) // Sonic Advance 2 mode
|
||||
{
|
||||
if ((signed)((mobj->renderflags & RF_TRANSMASK) >> RF_TRANSSHIFT) < (NUMTRANSMAPS-1) - (2*mobj->fuse)/3)
|
||||
// fade out when nearing the end of fuse...
|
||||
mobj->renderflags = (mobj->renderflags & ~RF_TRANSMASK) | (((NUMTRANSMAPS-1) - (2*mobj->fuse)/3) << RF_TRANSSHIFT);
|
||||
if (mobj->extravalue2 >= 2)
|
||||
{
|
||||
if (mobj->extravalue2 == 2) // I don't know why the normal logic doesn't work for this.
|
||||
mobj->renderflags ^= RF_DONTDRAW;
|
||||
else
|
||||
{
|
||||
if (mobj->fuse == mobj->extravalue2)
|
||||
mobj->renderflags &= ~RF_DONTDRAW;
|
||||
else
|
||||
mobj->renderflags |= RF_DONTDRAW;
|
||||
}
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if ((signed)((mobj->renderflags & RF_TRANSMASK) >> RF_TRANSSHIFT) < (NUMTRANSMAPS-1) - mobj->fuse / 2)
|
||||
INT32 dur = (mobj->flags2 & MF2_BOSSNOTRAP)
|
||||
? (2*mobj->fuse)/3
|
||||
: mobj->fuse/2;
|
||||
if (((mobj->renderflags & RF_TRANSMASK) >> RF_TRANSSHIFT) < ((NUMTRANSMAPS-1) - dur))
|
||||
// fade out when nearing the end of fuse...
|
||||
mobj->renderflags = (mobj->frame & ~RF_TRANSMASK) | (((NUMTRANSMAPS-1) - mobj->fuse / 2) << RF_TRANSSHIFT);
|
||||
mobj->renderflags = (mobj->renderflags & ~RF_TRANSMASK) | (((NUMTRANSMAPS-1) - dur) << RF_TRANSSHIFT);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -8830,21 +8842,6 @@ void P_SceneryThinker(mobj_t *mobj)
|
|||
}
|
||||
}
|
||||
|
||||
// Sonic Advance 2 flashing afterimages
|
||||
if (mobj->type == MT_GHOST && mobj->fuse > 0
|
||||
&& mobj->extravalue1 > 0 && mobj->extravalue2 >= 2)
|
||||
{
|
||||
if (mobj->extravalue2 == 2) // I don't know why the normal logic doesn't work for this.
|
||||
mobj->renderflags ^= RF_DONTDRAW;
|
||||
else
|
||||
{
|
||||
if (mobj->fuse == mobj->extravalue2)
|
||||
mobj->renderflags &= ~RF_DONTDRAW;
|
||||
else
|
||||
mobj->renderflags |= RF_DONTDRAW;
|
||||
}
|
||||
}
|
||||
|
||||
// momentum movement
|
||||
if (mobj->momx || mobj->momy)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -305,9 +305,13 @@ static void P_NetArchivePlayers(void)
|
|||
WRITEUINT8(save_p, players[i].jawztargetdelay);
|
||||
|
||||
WRITEUINT8(save_p, players[i].trickpanel);
|
||||
WRITEUINT8(save_p, players[i].tricktime);
|
||||
WRITEUINT32(save_p, players[i].trickmomx);
|
||||
WRITEUINT32(save_p, players[i].trickmomy);
|
||||
WRITEUINT32(save_p, players[i].trickmomz);
|
||||
WRITEUINT32(save_p, players[i].trickboostpower);
|
||||
WRITEUINT8(save_p, players[i].trickboostdecay);
|
||||
WRITEUINT8(save_p, players[i].trickboost);
|
||||
|
||||
WRITEUINT32(save_p, players[i].roundscore);
|
||||
WRITEUINT8(save_p, players[i].emeralds);
|
||||
|
|
@ -557,9 +561,13 @@ static void P_NetUnArchivePlayers(void)
|
|||
players[i].jawztargetdelay = READUINT8(save_p);
|
||||
|
||||
players[i].trickpanel = READUINT8(save_p);
|
||||
players[i].tricktime = READUINT8(save_p);
|
||||
players[i].trickmomx = READUINT32(save_p);
|
||||
players[i].trickmomy = READUINT32(save_p);
|
||||
players[i].trickmomz = READUINT32(save_p);
|
||||
players[i].trickboostpower = READUINT32(save_p);
|
||||
players[i].trickboostdecay = READUINT8(save_p);
|
||||
players[i].trickboost = READUINT8(save_p);
|
||||
|
||||
players[i].roundscore = READUINT32(save_p);
|
||||
players[i].emeralds = READUINT8(save_p);
|
||||
|
|
|
|||
|
|
@ -659,9 +659,7 @@ flatfound:
|
|||
levelflat->u.flat.baselumpnum = LUMPERROR;
|
||||
}
|
||||
|
||||
#ifndef ZDEBUG
|
||||
CONS_Debug(DBG_SETUP, "flat #%03d: %s\n", atoi(sizeu1(numlevelflats)), levelflat->name);
|
||||
#endif
|
||||
|
||||
return ( numlevelflats++ );
|
||||
}
|
||||
|
|
@ -3981,8 +3979,8 @@ boolean P_LoadLevel(boolean fromnetsave, boolean reloadinggamestate)
|
|||
|
||||
F_RunWipe(wipedefs[wipe_level_toblack], false, ((levelfadecol == 0) ? "FADEMAP1" : "FADEMAP0"), false, false);
|
||||
}
|
||||
if (!titlemapinaction)
|
||||
wipegamestate = GS_LEVEL;
|
||||
/*if (!titlemapinaction)
|
||||
wipegamestate = GS_LEVEL;*/
|
||||
|
||||
// Close text prompt before freeing the old level
|
||||
F_EndTextPrompt(false, true);
|
||||
|
|
|
|||
|
|
@ -2040,7 +2040,7 @@ void P_MovePlayer(player_t *player)
|
|||
{
|
||||
player->drawangle += ANGLE_22h;
|
||||
}
|
||||
else if (player->trickpanel == 3)
|
||||
else if (player->trickpanel >= 3)
|
||||
{
|
||||
player->drawangle -= ANGLE_22h;
|
||||
}
|
||||
|
|
|
|||
41
src/r_main.c
41
src/r_main.c
|
|
@ -318,18 +318,35 @@ INT32 R_PointOnSegSide(fixed_t x, fixed_t y, seg_t *line)
|
|||
|
||||
angle_t R_PointToAngle(fixed_t x, fixed_t y)
|
||||
{
|
||||
return (y -= viewy, (x -= viewx) || y) ?
|
||||
x >= 0 ?
|
||||
y >= 0 ?
|
||||
(x > y) ? tantoangle[SlopeDiv(y,x)] : // octant 0
|
||||
ANGLE_90-tantoangle[SlopeDiv(x,y)] : // octant 1
|
||||
x > (y = -y) ? 0-tantoangle[SlopeDiv(y,x)] : // octant 8
|
||||
ANGLE_270+tantoangle[SlopeDiv(x,y)] : // octant 7
|
||||
y >= 0 ? (x = -x) > y ? ANGLE_180-tantoangle[SlopeDiv(y,x)] : // octant 3
|
||||
ANGLE_90 + tantoangle[SlopeDiv(x,y)] : // octant 2
|
||||
(x = -x) > (y = -y) ? ANGLE_180+tantoangle[SlopeDiv(y,x)] : // octant 4
|
||||
ANGLE_270-tantoangle[SlopeDiv(x,y)] : // octant 5
|
||||
0;
|
||||
return R_PointToAngle2(viewx, viewy, x, y);
|
||||
}
|
||||
|
||||
// Similar to R_PointToAngle, but requires an additional player_t argument.
|
||||
// If this player is a local displayplayer, this will base off the calculations off of their camera instead, otherwise use viewx/viewy as usual.
|
||||
// Yes this is kinda ghetto.
|
||||
angle_t R_PointToAnglePlayer(player_t *player, fixed_t x, fixed_t y)
|
||||
{
|
||||
fixed_t refx = viewx, refy = viewy;
|
||||
camera_t *cam = NULL;
|
||||
UINT8 i;
|
||||
|
||||
for (i = 0; i < r_splitscreen; i++)
|
||||
{
|
||||
if (player == &players[displayplayers[i]])
|
||||
{
|
||||
cam = &camera[i];
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// use whatever cam we found's coordinates.
|
||||
if (cam != NULL)
|
||||
{
|
||||
refx = cam->x;
|
||||
refy = cam->y;
|
||||
}
|
||||
|
||||
return R_PointToAngle2(refx, refy, x, y);
|
||||
}
|
||||
|
||||
// This version uses 64-bit variables to avoid overflows with large values.
|
||||
|
|
|
|||
|
|
@ -63,6 +63,7 @@ extern lighttable_t *zlight[LIGHTLEVELS][MAXLIGHTZ];
|
|||
INT32 R_PointOnSide(fixed_t x, fixed_t y, node_t *node);
|
||||
INT32 R_PointOnSegSide(fixed_t x, fixed_t y, seg_t *line);
|
||||
angle_t R_PointToAngle(fixed_t x, fixed_t y);
|
||||
angle_t R_PointToAnglePlayer(player_t *player, fixed_t x, fixed_t y);
|
||||
angle_t R_PointToAngle64(INT64 x, INT64 y);
|
||||
angle_t R_PointToAngle2(fixed_t px2, fixed_t py2, fixed_t px1, fixed_t py1);
|
||||
angle_t R_PointToAngleEx(INT32 x2, INT32 y2, INT32 x1, INT32 y1);
|
||||
|
|
|
|||
|
|
@ -1611,9 +1611,7 @@ INT32 R_CheckTextureNumForName(const char *name)
|
|||
Z_Realloc(tidcache, tidcachelen * sizeof(*tidcache), PU_STATIC, &tidcache);
|
||||
strncpy(tidcache[tidcachelen-1].name, name, 8);
|
||||
tidcache[tidcachelen-1].name[8] = '\0';
|
||||
#ifndef ZDEBUG
|
||||
CONS_Debug(DBG_SETUP, "texture #%s: %s\n", sizeu1(tidcachelen), tidcache[tidcachelen-1].name);
|
||||
#endif
|
||||
tidcache[tidcachelen-1].id = i;
|
||||
return i;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -484,9 +484,7 @@ void R_AddSpriteDefs(UINT16 wadnum)
|
|||
#endif
|
||||
// if a new sprite was added (not just replaced)
|
||||
addsprites++;
|
||||
#ifndef ZDEBUG
|
||||
CONS_Debug(DBG_SETUP, "sprite %s set in pwad %d\n", sprnames[i], wadnum);
|
||||
#endif
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
684
src/s_sound.c
684
src/s_sound.c
|
|
@ -35,7 +35,7 @@
|
|||
// 3D Sound Interface
|
||||
#include "hardware/hw3sound.h"
|
||||
#else
|
||||
static INT32 S_AdjustSoundParams(const mobj_t *listener, const mobj_t *source, INT32 *vol, INT32 *sep, INT32 *pitch, sfxinfo_t *sfxinfo);
|
||||
static boolean S_AdjustSoundParams(const mobj_t *listener, const mobj_t *source, INT32 *vol, INT32 *sep, INT32 *pitch, sfxinfo_t *sfxinfo);
|
||||
#endif
|
||||
|
||||
CV_PossibleValue_t soundvolume_cons_t[] = {{0, "MIN"}, {MAX_VOLUME, "MAX"}, {0, NULL}};
|
||||
|
|
@ -183,8 +183,6 @@ static INT32 S_getChannel(const void *origin, sfxinfo_t *sfxinfo)
|
|||
// channel number to use
|
||||
INT32 cnum;
|
||||
|
||||
channel_t *c;
|
||||
|
||||
// Find an open channel
|
||||
for (cnum = 0; cnum < numofchannels; cnum++)
|
||||
{
|
||||
|
|
@ -196,7 +194,6 @@ static INT32 S_getChannel(const void *origin, sfxinfo_t *sfxinfo)
|
|||
else if (sfxinfo == channels[cnum].sfxinfo && (sfxinfo->pitch & SF_NOMULTIPLESOUND))
|
||||
{
|
||||
return -1;
|
||||
break;
|
||||
}
|
||||
else if (sfxinfo == channels[cnum].sfxinfo && sfxinfo->singularity == true)
|
||||
{
|
||||
|
|
@ -240,12 +237,6 @@ static INT32 S_getChannel(const void *origin, sfxinfo_t *sfxinfo)
|
|||
}
|
||||
}
|
||||
|
||||
c = &channels[cnum];
|
||||
|
||||
// channel is decided to be cnum.
|
||||
c->sfxinfo = sfxinfo;
|
||||
c->origin = origin;
|
||||
|
||||
return cnum;
|
||||
}
|
||||
|
||||
|
|
@ -501,24 +492,37 @@ void S_StartCaption(sfxenum_t sfx_id, INT32 cnum, UINT16 lifespan)
|
|||
closedcaptions[set].b = 2; // bob
|
||||
}
|
||||
|
||||
static INT32 S_ScaleVolumeWithSplitscreen(INT32 volume)
|
||||
{
|
||||
fixed_t root = INT32_MAX;
|
||||
|
||||
if (r_splitscreen == 0)
|
||||
{
|
||||
return volume;
|
||||
}
|
||||
|
||||
root = FixedSqrt((r_splitscreen + 1) * (FRACUNIT/3));
|
||||
|
||||
return FixedDiv(
|
||||
volume * FRACUNIT,
|
||||
root
|
||||
) / FRACUNIT;
|
||||
}
|
||||
|
||||
void S_StartSoundAtVolume(const void *origin_p, sfxenum_t sfx_id, INT32 volume)
|
||||
{
|
||||
const INT32 initial_volume = volume;
|
||||
INT32 sep, pitch, priority, cnum;
|
||||
const sfxenum_t actual_id = sfx_id;
|
||||
sfxinfo_t *sfx;
|
||||
const boolean reverse = (stereoreverse.value ^ encoremode);
|
||||
const mobj_t *origin = (const mobj_t *)origin_p;
|
||||
const sfxenum_t actual_id = sfx_id;
|
||||
const boolean reverse = (stereoreverse.value ^ encoremode);
|
||||
const INT32 initial_volume = (origin ? S_ScaleVolumeWithSplitscreen(volume) : volume);
|
||||
|
||||
listener_t listener = {0,0,0,0};
|
||||
listener_t listener2 = {0,0,0,0};
|
||||
listener_t listener3 = {0,0,0,0};
|
||||
listener_t listener4 = {0,0,0,0};
|
||||
sfxinfo_t *sfx;
|
||||
INT32 sep, pitch, priority, cnum;
|
||||
boolean anyListeners = false;
|
||||
INT32 i;
|
||||
|
||||
mobj_t *listenmobj = democam.soundmobj ? : players[displayplayers[0]].mo;
|
||||
mobj_t *listenmobj2 = NULL;
|
||||
mobj_t *listenmobj3 = NULL;
|
||||
mobj_t *listenmobj4 = NULL;
|
||||
listener_t listener[MAXSPLITSCREENPLAYERS];
|
||||
mobj_t *listenmobj[MAXSPLITSCREENPLAYERS];
|
||||
|
||||
if (S_SoundDisabled() || !sound_started)
|
||||
return;
|
||||
|
|
@ -527,27 +531,30 @@ void S_StartSoundAtVolume(const void *origin_p, sfxenum_t sfx_id, INT32 volume)
|
|||
if (sfx_id == sfx_None)
|
||||
return;
|
||||
|
||||
if (players[displayplayers[0]].awayviewtics)
|
||||
listenmobj = players[displayplayers[0]].awayviewmobj;
|
||||
|
||||
if (r_splitscreen)
|
||||
for (i = 0; i <= r_splitscreen; i++)
|
||||
{
|
||||
listenmobj2 = players[displayplayers[1]].mo;
|
||||
if (players[displayplayers[1]].awayviewtics)
|
||||
listenmobj2 = players[displayplayers[1]].awayviewmobj;
|
||||
player_t *player = &players[displayplayers[i]];
|
||||
|
||||
if (r_splitscreen > 1)
|
||||
memset(&listener[i], 0, sizeof (listener[i]));
|
||||
listenmobj[i] = NULL;
|
||||
|
||||
if (!player)
|
||||
{
|
||||
listenmobj3 = players[displayplayers[2]].mo;
|
||||
if (players[displayplayers[2]].awayviewtics)
|
||||
listenmobj3 = players[displayplayers[2]].awayviewmobj;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (r_splitscreen > 2)
|
||||
{
|
||||
listenmobj4 = players[displayplayers[3]].mo;
|
||||
if (players[displayplayers[3]].awayviewtics)
|
||||
listenmobj4 = players[displayplayers[3]].awayviewmobj;
|
||||
}
|
||||
if (i == 0 && democam.soundmobj)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (player->awayviewtics)
|
||||
{
|
||||
listenmobj[i] = player->awayviewmobj;
|
||||
}
|
||||
else
|
||||
{
|
||||
listenmobj[i] = player->mo;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -559,75 +566,37 @@ void S_StartSoundAtVolume(const void *origin_p, sfxenum_t sfx_id, INT32 volume)
|
|||
};
|
||||
#endif
|
||||
|
||||
if (camera[0].chase && !players[displayplayers[0]].awayviewtics)
|
||||
for (i = 0; i <= r_splitscreen; i++)
|
||||
{
|
||||
listener.x = camera[0].x;
|
||||
listener.y = camera[0].y;
|
||||
listener.z = camera[0].z;
|
||||
listener.angle = camera[0].angle;
|
||||
player_t *player = &players[displayplayers[i]];
|
||||
|
||||
if (!player)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (camera[i].chase && !player->awayviewtics)
|
||||
{
|
||||
listener[i].x = camera[i].x;
|
||||
listener[i].y = camera[i].y;
|
||||
listener[i].z = camera[i].z;
|
||||
listener[i].angle = camera[i].angle;
|
||||
anyListeners = true;
|
||||
}
|
||||
else if (listenmobj[i])
|
||||
{
|
||||
listener[i].x = listenmobj[i]->x;
|
||||
listener[i].y = listenmobj[i]->y;
|
||||
listener[i].z = listenmobj[i]->z;
|
||||
listener[i].angle = listenmobj[i]->angle;
|
||||
anyListeners = true;
|
||||
}
|
||||
}
|
||||
else if (listenmobj)
|
||||
|
||||
if (origin && anyListeners == false)
|
||||
{
|
||||
listener.x = listenmobj->x;
|
||||
listener.y = listenmobj->y;
|
||||
listener.z = listenmobj->z;
|
||||
listener.angle = listenmobj->angle;
|
||||
}
|
||||
else if (origin)
|
||||
// If a mobj is trying to make a noise, and no one is around to hear it, does it make a sound?
|
||||
return;
|
||||
|
||||
if (listenmobj2)
|
||||
{
|
||||
if (camera[1].chase && !players[displayplayers[1]].awayviewtics)
|
||||
{
|
||||
listener2.x = camera[1].x;
|
||||
listener2.y = camera[1].y;
|
||||
listener2.z = camera[1].z;
|
||||
listener2.angle = camera[1].angle;
|
||||
}
|
||||
else
|
||||
{
|
||||
listener2.x = listenmobj2->x;
|
||||
listener2.y = listenmobj2->y;
|
||||
listener2.z = listenmobj2->z;
|
||||
listener2.angle = listenmobj2->angle;
|
||||
}
|
||||
}
|
||||
|
||||
if (listenmobj3)
|
||||
{
|
||||
if (camera[2].chase && !players[displayplayers[2]].awayviewtics)
|
||||
{
|
||||
listener3.x = camera[2].x;
|
||||
listener3.y = camera[2].y;
|
||||
listener3.z = camera[2].z;
|
||||
listener3.angle = camera[2].angle;
|
||||
}
|
||||
else
|
||||
{
|
||||
listener3.x = listenmobj3->x;
|
||||
listener3.y = listenmobj3->y;
|
||||
listener3.z = listenmobj3->z;
|
||||
listener3.angle = listenmobj3->angle;
|
||||
}
|
||||
}
|
||||
|
||||
if (listenmobj4)
|
||||
{
|
||||
if (camera[3].chase && !players[displayplayers[3]].awayviewtics)
|
||||
{
|
||||
listener4.x = camera[3].x;
|
||||
listener4.y = camera[3].y;
|
||||
listener4.z = camera[3].z;
|
||||
listener4.angle = camera[3].angle;
|
||||
}
|
||||
else
|
||||
{
|
||||
listener4.x = listenmobj4->x;
|
||||
listener4.y = listenmobj4->y;
|
||||
listener4.z = listenmobj4->z;
|
||||
listener4.angle = listenmobj4->angle;
|
||||
}
|
||||
}
|
||||
|
||||
// check for bogus sound #
|
||||
|
|
@ -647,36 +616,40 @@ void S_StartSoundAtVolume(const void *origin_p, sfxenum_t sfx_id, INT32 volume)
|
|||
pitch = NORM_PITCH;
|
||||
priority = NORM_PRIORITY;
|
||||
|
||||
if (r_splitscreen && origin)
|
||||
volume = FixedDiv(volume<<FRACBITS, FixedSqrt((r_splitscreen+1)<<FRACBITS))>>FRACBITS;
|
||||
|
||||
if (r_splitscreen && listenmobj2) // Copy the sound for the split player
|
||||
for (i = r_splitscreen; i >= 0; i--)
|
||||
{
|
||||
// Check to see if it is audible, and if not, modify the params
|
||||
if (origin && origin != listenmobj2)
|
||||
// Copy the sound for the splitscreen players!
|
||||
if (listenmobj[i] == NULL && i != 0)
|
||||
{
|
||||
INT32 rc;
|
||||
rc = S_AdjustSoundParams(listenmobj2, origin, &volume, &sep, &pitch, sfx);
|
||||
continue;
|
||||
}
|
||||
|
||||
// Check to see if it is audible, and if not, modify the params
|
||||
if (origin && origin != listenmobj[i])
|
||||
{
|
||||
boolean rc = S_AdjustSoundParams(listenmobj[i], origin, &volume, &sep, &pitch, sfx);
|
||||
|
||||
if (!rc)
|
||||
goto dontplay; // Maybe the other player can hear it...
|
||||
{
|
||||
continue; // Maybe the other player can hear it...
|
||||
}
|
||||
|
||||
if (origin->x == listener2.x && origin->y == listener2.y)
|
||||
if (origin->x == listener[i].x && origin->y == listener[i].y)
|
||||
{
|
||||
sep = NORM_SEP;
|
||||
}
|
||||
}
|
||||
else if (!origin)
|
||||
// Do not play origin-less sounds for the second player.
|
||||
else if (i > 0 && !origin)
|
||||
{
|
||||
// Do not play origin-less sounds for the splitscreen players.
|
||||
// The first player will be able to hear it just fine,
|
||||
// we really don't want it playing twice.
|
||||
goto dontplay;
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
sep = NORM_SEP;
|
||||
|
||||
// try to find a channel
|
||||
cnum = S_getChannel(origin, sfx);
|
||||
|
||||
if (cnum < 0)
|
||||
return; // If there's no free channels, it's not gonna be free for player 1, either.
|
||||
}
|
||||
|
||||
// This is supposed to handle the loading/caching.
|
||||
// For some odd reason, the caching is done nearly
|
||||
|
|
@ -685,191 +658,43 @@ void S_StartSoundAtVolume(const void *origin_p, sfxenum_t sfx_id, INT32 volume)
|
|||
// cache data if necessary
|
||||
// NOTE: set sfx->data NULL sfx->lump -1 to force a reload
|
||||
if (!sfx->data)
|
||||
sfx->data = I_GetSfx(sfx);
|
||||
|
||||
// increase the usefulness
|
||||
if (sfx->usefulness++ < 0)
|
||||
sfx->usefulness = -1;
|
||||
|
||||
// Avoid channel reverse if surround
|
||||
if (reverse
|
||||
#ifdef SURROUND
|
||||
&& sep != SURROUND_SEP
|
||||
#endif
|
||||
)
|
||||
sep = (~sep) & 255;
|
||||
|
||||
// Assigns the handle to one of the channels in the
|
||||
// mix/output buffer.
|
||||
channels[cnum].handle = I_StartSound(sfx_id, volume, sep, pitch, priority, cnum);
|
||||
}
|
||||
|
||||
dontplay:
|
||||
|
||||
if (r_splitscreen > 1 && listenmobj3) // Copy the sound for the third player
|
||||
{
|
||||
// Check to see if it is audible, and if not, modify the params
|
||||
if (origin && origin != listenmobj3)
|
||||
{
|
||||
INT32 rc;
|
||||
rc = S_AdjustSoundParams(listenmobj3, origin, &volume, &sep, &pitch, sfx);
|
||||
|
||||
if (!rc)
|
||||
goto dontplay3; // Maybe the other player can hear it...
|
||||
|
||||
if (origin->x == listener3.x && origin->y == listener3.y)
|
||||
sep = NORM_SEP;
|
||||
}
|
||||
else if (!origin)
|
||||
// Do not play origin-less sounds for the second player.
|
||||
// The first player will be able to hear it just fine,
|
||||
// we really don't want it playing twice.
|
||||
goto dontplay3;
|
||||
else
|
||||
sep = NORM_SEP;
|
||||
|
||||
// try to find a channel
|
||||
cnum = S_getChannel(origin, sfx);
|
||||
|
||||
if (cnum < 0)
|
||||
return; // If there's no free channels, it's not gonna be free for player 1, either.
|
||||
|
||||
// This is supposed to handle the loading/caching.
|
||||
// For some odd reason, the caching is done nearly
|
||||
// each time the sound is needed?
|
||||
|
||||
// cache data if necessary
|
||||
// NOTE: set sfx->data NULL sfx->lump -1 to force a reload
|
||||
if (!sfx->data)
|
||||
sfx->data = I_GetSfx(sfx);
|
||||
}
|
||||
|
||||
// increase the usefulness
|
||||
if (sfx->usefulness++ < 0)
|
||||
sfx->usefulness = -1;
|
||||
|
||||
// Avoid channel reverse if surround
|
||||
if (reverse
|
||||
#ifdef SURROUND
|
||||
&& sep != SURROUND_SEP
|
||||
#endif
|
||||
)
|
||||
sep = (~sep) & 255;
|
||||
|
||||
// Assigns the handle to one of the channels in the
|
||||
// mix/output buffer.
|
||||
channels[cnum].handle = I_StartSound(sfx_id, volume, sep, pitch, priority, cnum);
|
||||
}
|
||||
|
||||
dontplay3:
|
||||
|
||||
if (r_splitscreen > 2 && listenmobj4) // Copy the sound for the split player
|
||||
{
|
||||
// Check to see if it is audible, and if not, modify the params
|
||||
if (origin && origin != listenmobj4)
|
||||
{
|
||||
INT32 rc;
|
||||
rc = S_AdjustSoundParams(listenmobj4, origin, &volume, &sep, &pitch, sfx);
|
||||
|
||||
if (!rc)
|
||||
goto dontplay4; // Maybe the other player can hear it...
|
||||
|
||||
if (origin->x == listener4.x && origin->y == listener4.y)
|
||||
sep = NORM_SEP;
|
||||
}
|
||||
else if (!origin)
|
||||
// Do not play origin-less sounds for the second player.
|
||||
// The first player will be able to hear it just fine,
|
||||
// we really don't want it playing twice.
|
||||
goto dontplay4;
|
||||
else
|
||||
sep = NORM_SEP;
|
||||
|
||||
// try to find a channel
|
||||
cnum = S_getChannel(origin, sfx);
|
||||
|
||||
if (cnum < 0)
|
||||
return; // If there's no free channels, it's not gonna be free for player 1, either.
|
||||
|
||||
// This is supposed to handle the loading/caching.
|
||||
// For some odd reason, the caching is done nearly
|
||||
// each time the sound is needed?
|
||||
|
||||
// cache data if necessary
|
||||
// NOTE: set sfx->data NULL sfx->lump -1 to force a reload
|
||||
if (!sfx->data)
|
||||
sfx->data = I_GetSfx(sfx);
|
||||
|
||||
// increase the usefulness
|
||||
if (sfx->usefulness++ < 0)
|
||||
sfx->usefulness = -1;
|
||||
}
|
||||
|
||||
// Avoid channel reverse if surround
|
||||
if (reverse
|
||||
#ifdef SURROUND
|
||||
&& sep != SURROUND_SEP
|
||||
#endif
|
||||
)
|
||||
)
|
||||
{
|
||||
sep = (~sep) & 255;
|
||||
}
|
||||
|
||||
// Handle closed caption input.
|
||||
S_StartCaption(actual_id, cnum, MAXCAPTIONTICS);
|
||||
|
||||
// Assigns the handle to one of the channels in the
|
||||
// mix/output buffer.
|
||||
// At this point it is determined that a sound can and should be played, so find a free channel to play it on
|
||||
cnum = S_getChannel(origin, sfx);
|
||||
|
||||
if (cnum < 0)
|
||||
{
|
||||
return; // If there's no free channels, there won't be any for anymore players either
|
||||
}
|
||||
|
||||
// Now that we know we are going to play a sound, fill out this info
|
||||
channels[cnum].sfxinfo = sfx;
|
||||
channels[cnum].origin = origin;
|
||||
channels[cnum].volume = initial_volume;
|
||||
channels[cnum].handle = I_StartSound(sfx_id, volume, sep, pitch, priority, cnum);
|
||||
}
|
||||
|
||||
dontplay4:
|
||||
|
||||
// Check to see if it is audible, and if not, modify the params
|
||||
if (origin && origin != listenmobj)
|
||||
{
|
||||
INT32 rc;
|
||||
rc = S_AdjustSoundParams(listenmobj, origin, &volume, &sep, &pitch, sfx);
|
||||
|
||||
if (!rc)
|
||||
return;
|
||||
|
||||
if (origin->x == listener.x && origin->y == listener.y)
|
||||
sep = NORM_SEP;
|
||||
}
|
||||
else
|
||||
sep = NORM_SEP;
|
||||
|
||||
// try to find a channel
|
||||
cnum = S_getChannel(origin, sfx);
|
||||
|
||||
if (cnum < 0)
|
||||
return;
|
||||
|
||||
// This is supposed to handle the loading/caching.
|
||||
// For some odd reason, the caching is done nearly
|
||||
// each time the sound is needed?
|
||||
|
||||
// cache data if necessary
|
||||
// NOTE: set sfx->data NULL sfx->lump -1 to force a reload
|
||||
if (!sfx->data)
|
||||
sfx->data = I_GetSfx(sfx);
|
||||
|
||||
// increase the usefulness
|
||||
if (sfx->usefulness++ < 0)
|
||||
sfx->usefulness = -1;
|
||||
|
||||
// Avoid channel reverse if surround
|
||||
if (reverse
|
||||
#ifdef SURROUND
|
||||
&& sep != SURROUND_SEP
|
||||
#endif
|
||||
)
|
||||
sep = (~sep) & 255;
|
||||
|
||||
// Handle closed caption input.
|
||||
S_StartCaption(actual_id, cnum, MAXCAPTIONTICS);
|
||||
|
||||
// Assigns the handle to one of the channels in the
|
||||
// mix/output buffer.
|
||||
channels[cnum].volume = initial_volume;
|
||||
channels[cnum].handle = I_StartSound(sfx_id, volume, sep, pitch, priority, cnum);
|
||||
}
|
||||
|
||||
void S_StartSound(const void *origin, sfxenum_t sfx_id)
|
||||
|
|
@ -920,23 +745,13 @@ static INT32 actualdigmusicvolume;
|
|||
|
||||
void S_UpdateSounds(void)
|
||||
{
|
||||
INT32 audible, cnum, volume, sep, pitch;
|
||||
INT32 cnum, volume, sep, pitch;
|
||||
boolean audible = false;
|
||||
channel_t *c;
|
||||
INT32 i;
|
||||
|
||||
listener_t listener;
|
||||
listener_t listener2;
|
||||
listener_t listener3;
|
||||
listener_t listener4;
|
||||
|
||||
mobj_t *listenmobj = democam.soundmobj ? : players[displayplayers[0]].mo;
|
||||
mobj_t *listenmobj2 = NULL;
|
||||
mobj_t *listenmobj3 = NULL;
|
||||
mobj_t *listenmobj4 = NULL;
|
||||
|
||||
memset(&listener, 0, sizeof(listener_t));
|
||||
memset(&listener2, 0, sizeof(listener_t));
|
||||
memset(&listener3, 0, sizeof(listener_t));
|
||||
memset(&listener4, 0, sizeof(listener_t));
|
||||
listener_t listener[MAXSPLITSCREENPLAYERS];
|
||||
mobj_t *listenmobj[MAXSPLITSCREENPLAYERS];
|
||||
|
||||
// Update sound/music volumes, if changed manually at console
|
||||
if (actualsfxvolume != cv_soundvolume.value * USER_VOLUME_SCALE)
|
||||
|
|
@ -949,7 +764,7 @@ void S_UpdateSounds(void)
|
|||
{
|
||||
#ifndef NOMUMBLE
|
||||
// Stop Mumble cutting out. I'm sick of it.
|
||||
I_UpdateMumble(NULL, listener);
|
||||
I_UpdateMumble(NULL, listener[0]);
|
||||
#endif
|
||||
|
||||
goto notinlevel;
|
||||
|
|
@ -958,47 +773,35 @@ void S_UpdateSounds(void)
|
|||
if (dedicated || sound_disabled)
|
||||
return;
|
||||
|
||||
if (players[displayplayers[0]].awayviewtics)
|
||||
listenmobj = players[displayplayers[0]].awayviewmobj;
|
||||
|
||||
if (r_splitscreen)
|
||||
for (i = 0; i <= r_splitscreen; i++)
|
||||
{
|
||||
listenmobj2 = players[displayplayers[1]].mo;
|
||||
if (players[displayplayers[1]].awayviewtics)
|
||||
listenmobj2 = players[displayplayers[1]].awayviewmobj;
|
||||
player_t *player = &players[displayplayers[i]];
|
||||
|
||||
if (r_splitscreen > 1)
|
||||
memset(&listener[i], 0, sizeof (listener[i]));
|
||||
listenmobj[i] = NULL;
|
||||
|
||||
if (!player)
|
||||
{
|
||||
listenmobj3 = players[displayplayers[2]].mo;
|
||||
if (players[displayplayers[2]].awayviewtics)
|
||||
listenmobj3 = players[displayplayers[2]].awayviewmobj;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (r_splitscreen > 2)
|
||||
{
|
||||
listenmobj4 = players[displayplayers[3]].mo;
|
||||
if (players[displayplayers[3]].awayviewtics)
|
||||
listenmobj4 = players[displayplayers[3]].awayviewmobj;
|
||||
}
|
||||
if (i == 0 && democam.soundmobj)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (player->awayviewtics)
|
||||
{
|
||||
listenmobj[i] = player->awayviewmobj;
|
||||
}
|
||||
else
|
||||
{
|
||||
listenmobj[i] = player->mo;
|
||||
}
|
||||
}
|
||||
|
||||
if (camera[0].chase && !players[displayplayers[0]].awayviewtics)
|
||||
{
|
||||
listener.x = camera[0].x;
|
||||
listener.y = camera[0].y;
|
||||
listener.z = camera[0].z;
|
||||
listener.angle = camera[0].angle;
|
||||
}
|
||||
else if (listenmobj)
|
||||
{
|
||||
listener.x = listenmobj->x;
|
||||
listener.y = listenmobj->y;
|
||||
listener.z = listenmobj->z;
|
||||
listener.angle = listenmobj->angle;
|
||||
}
|
||||
|
||||
#ifndef NOMUMBLE
|
||||
I_UpdateMumble(players[consoleplayer].mo, listener);
|
||||
I_UpdateMumble(players[consoleplayer].mo, listener[0]);
|
||||
#endif
|
||||
|
||||
#ifdef HW3SOUND
|
||||
|
|
@ -1009,57 +812,28 @@ void S_UpdateSounds(void)
|
|||
}
|
||||
#endif
|
||||
|
||||
if (listenmobj2)
|
||||
for (i = 0; i <= r_splitscreen; i++)
|
||||
{
|
||||
if (camera[1].chase && !players[displayplayers[1]].awayviewtics)
|
||||
{
|
||||
listener2.x = camera[1].x;
|
||||
listener2.y = camera[1].y;
|
||||
listener2.z = camera[1].z;
|
||||
listener2.angle = camera[1].angle;
|
||||
}
|
||||
else
|
||||
{
|
||||
listener2.x = listenmobj2->x;
|
||||
listener2.y = listenmobj2->y;
|
||||
listener2.z = listenmobj2->z;
|
||||
listener2.angle = listenmobj2->angle;
|
||||
}
|
||||
}
|
||||
player_t *player = &players[displayplayers[i]];
|
||||
|
||||
if (listenmobj3)
|
||||
{
|
||||
if (camera[2].chase && !players[displayplayers[2]].awayviewtics)
|
||||
if (!player)
|
||||
{
|
||||
listener3.x = camera[2].x;
|
||||
listener3.y = camera[2].y;
|
||||
listener3.z = camera[2].z;
|
||||
listener3.angle = camera[2].angle;
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
listener3.x = listenmobj3->x;
|
||||
listener3.y = listenmobj3->y;
|
||||
listener3.z = listenmobj3->z;
|
||||
listener3.angle = listenmobj3->angle;
|
||||
}
|
||||
}
|
||||
|
||||
if (listenmobj4)
|
||||
{
|
||||
if (camera[3].chase && !players[displayplayers[3]].awayviewtics)
|
||||
if (camera[i].chase && !player->awayviewtics)
|
||||
{
|
||||
listener4.x = camera[3].x;
|
||||
listener4.y = camera[3].y;
|
||||
listener4.z = camera[3].z;
|
||||
listener4.angle = camera[3].angle;
|
||||
listener[i].x = camera[i].x;
|
||||
listener[i].y = camera[i].y;
|
||||
listener[i].z = camera[i].z;
|
||||
listener[i].angle = camera[i].angle;
|
||||
}
|
||||
else
|
||||
else if (listenmobj[i])
|
||||
{
|
||||
listener4.x = listenmobj4->x;
|
||||
listener4.y = listenmobj4->y;
|
||||
listener4.z = listenmobj4->z;
|
||||
listener4.angle = listenmobj4->angle;
|
||||
listener[i].x = listenmobj[i]->x;
|
||||
listener[i].y = listenmobj[i]->y;
|
||||
listener[i].z = listenmobj[i]->z;
|
||||
listener[i].angle = listenmobj[i]->angle;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -1076,83 +850,53 @@ void S_UpdateSounds(void)
|
|||
pitch = NORM_PITCH;
|
||||
sep = NORM_SEP;
|
||||
|
||||
if (r_splitscreen && c->origin)
|
||||
volume = FixedDiv(volume<<FRACBITS, FixedSqrt((r_splitscreen+1)<<FRACBITS))>>FRACBITS;
|
||||
|
||||
// check non-local sounds for distance clipping
|
||||
// or modify their params
|
||||
if (c->origin && ((c->origin != players[displayplayers[0]].mo)
|
||||
|| (r_splitscreen && c->origin != players[displayplayers[1]].mo)
|
||||
|| (r_splitscreen > 1 && c->origin != players[displayplayers[2]].mo)
|
||||
|| (r_splitscreen > 2 && c->origin != players[displayplayers[3]].mo)))
|
||||
if (c->origin)
|
||||
{
|
||||
// Whomever is closer gets the sound, but only in splitscreen.
|
||||
if (r_splitscreen)
|
||||
boolean itsUs = false;
|
||||
|
||||
for (i = 0; i <= r_splitscreen; i++)
|
||||
{
|
||||
if (c->origin == players[displayplayers[i]].mo)
|
||||
{
|
||||
itsUs = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (itsUs == false)
|
||||
{
|
||||
const mobj_t *soundmobj = c->origin;
|
||||
fixed_t recdist = -1;
|
||||
INT32 i, p = -1;
|
||||
fixed_t recdist = INT32_MAX;
|
||||
UINT8 p = 0;
|
||||
|
||||
for (i = 0; i <= r_splitscreen; i++)
|
||||
{
|
||||
fixed_t thisdist = -1;
|
||||
fixed_t thisdist = INT32_MAX;
|
||||
|
||||
if (i == 0 && listenmobj)
|
||||
thisdist = P_AproxDistance(listener.x-soundmobj->x, listener.y-soundmobj->y);
|
||||
else if (i == 1 && listenmobj2)
|
||||
thisdist = P_AproxDistance(listener2.x-soundmobj->x, listener2.y-soundmobj->y);
|
||||
else if (i == 2 && listenmobj3)
|
||||
thisdist = P_AproxDistance(listener3.x-soundmobj->x, listener3.y-soundmobj->y);
|
||||
else if (i == 3 && listenmobj4)
|
||||
thisdist = P_AproxDistance(listener4.x-soundmobj->x, listener4.y-soundmobj->y);
|
||||
else
|
||||
if (!listenmobj[i])
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (recdist == -1 || (thisdist != -1 && thisdist < recdist))
|
||||
thisdist = P_AproxDistance(listener[i].x - soundmobj->x, listener[i].y - soundmobj->y);
|
||||
|
||||
if (thisdist < recdist)
|
||||
{
|
||||
recdist = thisdist;
|
||||
p = i;
|
||||
}
|
||||
}
|
||||
|
||||
if (p != -1)
|
||||
if (listenmobj[p])
|
||||
{
|
||||
if (p == 1)
|
||||
{
|
||||
// Player 2 gets the sound
|
||||
audible = S_AdjustSoundParams(listenmobj2, c->origin, &volume, &sep, &pitch,
|
||||
c->sfxinfo);
|
||||
}
|
||||
else if (p == 2)
|
||||
{
|
||||
// Player 3 gets the sound
|
||||
audible = S_AdjustSoundParams(listenmobj3, c->origin, &volume, &sep, &pitch,
|
||||
c->sfxinfo);
|
||||
}
|
||||
else if (p == 3)
|
||||
{
|
||||
// Player 4 gets the sound
|
||||
audible = S_AdjustSoundParams(listenmobj4, c->origin, &volume, &sep, &pitch,
|
||||
c->sfxinfo);
|
||||
}
|
||||
else
|
||||
{
|
||||
// Player 1 gets the sound
|
||||
audible = S_AdjustSoundParams(listenmobj, c->origin, &volume, &sep, &pitch,
|
||||
c->sfxinfo);
|
||||
}
|
||||
|
||||
if (audible)
|
||||
I_UpdateSoundParams(c->handle, volume, sep, pitch);
|
||||
else
|
||||
S_StopChannel(cnum);
|
||||
audible = S_AdjustSoundParams(
|
||||
listenmobj[p], c->origin,
|
||||
&volume, &sep, &pitch,
|
||||
c->sfxinfo
|
||||
);
|
||||
}
|
||||
}
|
||||
else if (listenmobj && !r_splitscreen)
|
||||
{
|
||||
// In the case of a single player, he or she always should get updated sound.
|
||||
audible = S_AdjustSoundParams(listenmobj, c->origin, &volume, &sep, &pitch,
|
||||
c->sfxinfo);
|
||||
|
||||
if (audible)
|
||||
I_UpdateSoundParams(c->handle, volume, sep, pitch);
|
||||
|
|
@ -1273,54 +1017,39 @@ fixed_t S_CalculateSoundDistance(fixed_t sx1, fixed_t sy1, fixed_t sz1, fixed_t
|
|||
// If the sound is not audible, returns a 0.
|
||||
// Otherwise, modifies parameters and returns 1.
|
||||
//
|
||||
INT32 S_AdjustSoundParams(const mobj_t *listener, const mobj_t *source, INT32 *vol, INT32 *sep, INT32 *pitch,
|
||||
boolean S_AdjustSoundParams(const mobj_t *listener, const mobj_t *source, INT32 *vol, INT32 *sep, INT32 *pitch,
|
||||
sfxinfo_t *sfxinfo)
|
||||
{
|
||||
const boolean reverse = (stereoreverse.value ^ encoremode);
|
||||
|
||||
fixed_t approx_dist;
|
||||
angle_t angle;
|
||||
|
||||
listener_t listensource;
|
||||
|
||||
const boolean reverse = (stereoreverse.value ^ encoremode);
|
||||
INT32 i;
|
||||
|
||||
(void)pitch;
|
||||
|
||||
if (!listener)
|
||||
return false;
|
||||
|
||||
if (listener == players[displayplayers[0]].mo && camera[0].chase)
|
||||
// Init listensource with default listener
|
||||
listensource.x = listener->x;
|
||||
listensource.y = listener->y;
|
||||
listensource.z = listener->z;
|
||||
listensource.angle = listener->angle;
|
||||
|
||||
for (i = 0; i <= r_splitscreen; i++)
|
||||
{
|
||||
listensource.x = camera[0].x;
|
||||
listensource.y = camera[0].y;
|
||||
listensource.z = camera[0].z;
|
||||
listensource.angle = camera[0].angle;
|
||||
}
|
||||
else if (r_splitscreen && listener == players[displayplayers[1]].mo && camera[1].chase)
|
||||
{
|
||||
listensource.x = camera[1].x;
|
||||
listensource.y = camera[1].y;
|
||||
listensource.z = camera[1].z;
|
||||
listensource.angle = camera[1].angle;
|
||||
}
|
||||
else if (r_splitscreen > 1 && listener == players[displayplayers[2]].mo && camera[2].chase)
|
||||
{
|
||||
listensource.x = camera[2].x;
|
||||
listensource.y = camera[2].y;
|
||||
listensource.z = camera[2].z;
|
||||
listensource.angle = camera[2].angle;
|
||||
}
|
||||
else if (r_splitscreen > 2 && listener == players[displayplayers[3]].mo && camera[3].chase)
|
||||
{
|
||||
listensource.x = camera[3].x;
|
||||
listensource.y = camera[3].y;
|
||||
listensource.z = camera[3].z;
|
||||
listensource.angle = camera[3].angle;
|
||||
}
|
||||
else
|
||||
{
|
||||
listensource.x = listener->x;
|
||||
listensource.y = listener->y;
|
||||
listensource.z = listener->z;
|
||||
listensource.angle = listener->angle;
|
||||
// If listener is a chasecam player, use the camera instead
|
||||
if (listener == players[displayplayers[i]].mo && camera[i].chase)
|
||||
{
|
||||
listensource.x = camera[i].x;
|
||||
listensource.y = camera[i].y;
|
||||
listensource.z = camera[i].z;
|
||||
listensource.angle = camera[i].angle;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (sfxinfo->pitch & SF_OUTSIDESOUND) // Rain special case
|
||||
|
|
@ -1370,7 +1099,7 @@ INT32 S_AdjustSoundParams(const mobj_t *listener, const mobj_t *source, INT32 *v
|
|||
approx_dist = FixedDiv(approx_dist,2*FRACUNIT);
|
||||
|
||||
if (approx_dist > S_CLIPPING_DIST)
|
||||
return 0;
|
||||
return false;
|
||||
|
||||
// angle of source to listener
|
||||
angle = R_PointToAngle2(listensource.x, listensource.y, source->x, source->y);
|
||||
|
|
@ -1405,9 +1134,6 @@ INT32 S_AdjustSoundParams(const mobj_t *listener, const mobj_t *source, INT32 *v
|
|||
*vol = FixedMul(*vol * FRACUNIT / 255, n) / S_ATTENUATOR;
|
||||
}
|
||||
|
||||
if (r_splitscreen)
|
||||
*vol = FixedDiv((*vol)<<FRACBITS, FixedSqrt((r_splitscreen+1)<<FRACBITS))>>FRACBITS;
|
||||
|
||||
return (*vol > 0);
|
||||
}
|
||||
|
||||
|
|
|
|||
71
src/sounds.c
71
src/sounds.c
|
|
@ -837,6 +837,77 @@ sfxinfo_t S_sfx[NUMSFX] =
|
|||
{"kc6d", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"kc6e", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
|
||||
// Mean Bean Machine sounds
|
||||
{"mbs41", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs42", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs43", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs44", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs45", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs46", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs47", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs48", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs49", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs4a", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs4b", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs4c", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs4d", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs4e", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs4f", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs50", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs51", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs52", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs53", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs54", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs55", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs56", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs57", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs58", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs59", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs5a", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs5b", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs5c", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs5d", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs5e", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs5f", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs60", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs61", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs62", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs63", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs64", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs67", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs68", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs69", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs6a", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs6b", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs6d", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs6e", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs70", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs71", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbs72", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv81", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv82", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv83", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv84", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv85", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv86", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv87", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv88", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv89", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv8a", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv8b", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv8c", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv8d", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv8e", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv8f", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv90", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv91", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv92", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv93", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv94", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv95", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv96", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
{"mbv97", false, 64, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""},
|
||||
|
||||
// SRB2kart
|
||||
{"slip", false, 96, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""}, // Spinout
|
||||
{"screec", false, 48, 0, -1, NULL, 0, -1, -1, LUMPERROR, ""}, // Tight turning screech
|
||||
|
|
|
|||
71
src/sounds.h
71
src/sounds.h
|
|
@ -901,6 +901,77 @@ typedef enum
|
|||
sfx_kc6d,
|
||||
sfx_kc6e,
|
||||
|
||||
// Mean Bean Machine sounds
|
||||
sfx_mbs41,
|
||||
sfx_mbs42,
|
||||
sfx_mbs43,
|
||||
sfx_mbs44,
|
||||
sfx_mbs45,
|
||||
sfx_mbs46,
|
||||
sfx_mbs47,
|
||||
sfx_mbs48,
|
||||
sfx_mbs49,
|
||||
sfx_mbs4a,
|
||||
sfx_mbs4b,
|
||||
sfx_mbs4c,
|
||||
sfx_mbs4d,
|
||||
sfx_mbs4e,
|
||||
sfx_mbs4f,
|
||||
sfx_mbs50,
|
||||
sfx_mbs51,
|
||||
sfx_mbs52,
|
||||
sfx_mbs53,
|
||||
sfx_mbs54,
|
||||
sfx_mbs55,
|
||||
sfx_mbs56,
|
||||
sfx_mbs57,
|
||||
sfx_mbs58,
|
||||
sfx_mbs59,
|
||||
sfx_mbs5a,
|
||||
sfx_mbs5b,
|
||||
sfx_mbs5c,
|
||||
sfx_mbs5d,
|
||||
sfx_mbs5e,
|
||||
sfx_mbs5f,
|
||||
sfx_mbs60,
|
||||
sfx_mbs61,
|
||||
sfx_mbs62,
|
||||
sfx_mbs63,
|
||||
sfx_mbs64,
|
||||
sfx_mbs67,
|
||||
sfx_mbs68,
|
||||
sfx_mbs69,
|
||||
sfx_mbs6a,
|
||||
sfx_mbs6b,
|
||||
sfx_mbs6d,
|
||||
sfx_mbs6e,
|
||||
sfx_mbs70,
|
||||
sfx_mbs71,
|
||||
sfx_mbs72,
|
||||
sfx_mbv81,
|
||||
sfx_mbv82,
|
||||
sfx_mbv83,
|
||||
sfx_mbv84,
|
||||
sfx_mbv85,
|
||||
sfx_mbv86,
|
||||
sfx_mbv87,
|
||||
sfx_mbv88,
|
||||
sfx_mbv89,
|
||||
sfx_mbv8a,
|
||||
sfx_mbv8b,
|
||||
sfx_mbv8c,
|
||||
sfx_mbv8d,
|
||||
sfx_mbv8e,
|
||||
sfx_mbv8f,
|
||||
sfx_mbv90,
|
||||
sfx_mbv91,
|
||||
sfx_mbv92,
|
||||
sfx_mbv93,
|
||||
sfx_mbv94,
|
||||
sfx_mbv95,
|
||||
sfx_mbv96,
|
||||
sfx_mbv97,
|
||||
|
||||
// SRB2kart
|
||||
sfx_slip,
|
||||
sfx_screec,
|
||||
|
|
|
|||
440
src/st_stuff.c
440
src/st_stuff.c
|
|
@ -31,6 +31,7 @@
|
|||
#include "m_misc.h" // moviemode
|
||||
#include "m_anigif.h" // cv_gif_downscale
|
||||
#include "p_setup.h" // NiGHTS grading
|
||||
#include "k_grandprix.h" // we need to know grandprix status for titlecards
|
||||
|
||||
//random index
|
||||
#include "m_random.h"
|
||||
|
|
@ -622,23 +623,97 @@ static void ST_drawDebugInfo(void)
|
|||
V_DrawRightAlignedString(320, height, V_MONOSPACE, va("Heap used: %7sKB", sizeu1(Z_TagsUsage(0, INT32_MAX)>>10)));
|
||||
}
|
||||
|
||||
static patch_t *lt_patches[3];
|
||||
static INT32 lt_scroll = 0;
|
||||
static INT32 lt_mom = 0;
|
||||
static INT32 lt_zigzag = 0;
|
||||
|
||||
tic_t lt_ticker = 0, lt_lasttic = 0;
|
||||
tic_t lt_exitticker = 0, lt_endtime = 0;
|
||||
|
||||
// SRB2KART: HUD shit for new titlecards:
|
||||
static patch_t *tcchev1;
|
||||
static patch_t *tcchev2;
|
||||
|
||||
static patch_t *tcol1;
|
||||
static patch_t *tcol2;
|
||||
|
||||
static patch_t *tcroundbar;
|
||||
static patch_t *tcround;
|
||||
|
||||
static patch_t *tccircletop;
|
||||
static patch_t *tccirclebottom;
|
||||
static patch_t *tccirclebg;
|
||||
|
||||
static patch_t *tcbanner;
|
||||
static patch_t *tcbanner2;
|
||||
|
||||
static patch_t *tcroundnum[10];
|
||||
static patch_t *tcactnum[10];
|
||||
static patch_t *tcact;
|
||||
|
||||
// some coordinates define to make my life easier....
|
||||
#define FINAL_ROUNDX (24)
|
||||
#define FINAL_EGGY (160)
|
||||
#define FINAL_ROUNDY (16)
|
||||
#define FINAL_BANNERY (160)
|
||||
|
||||
INT32 chev1x, chev1y, chev2x, chev2y, chevtflag;
|
||||
INT32 roundx, roundy;
|
||||
INT32 bannerx, bannery;
|
||||
|
||||
INT32 roundnumx, roundnumy;
|
||||
INT32 eggx1, eggx2, eggy1, eggy2;
|
||||
|
||||
// These are all arbitrary values found by trial and error trying to align the hud lmao.
|
||||
// But they'll work.
|
||||
#define BASE_CHEV1X (252)
|
||||
#define BASE_CHEV1Y (60)
|
||||
#define BASE_CHEV2X (65)
|
||||
#define BASE_CHEV2Y (135)
|
||||
|
||||
#define TTANIMTHRESHOLD (TICRATE)
|
||||
#define TTANIMSTART (TTANIMTHRESHOLD-16)
|
||||
#define TTANIMENDTHRESHOLD (TICRATE*3)
|
||||
#define TTANIMEND (TICRATE*4)
|
||||
|
||||
//
|
||||
// Load the graphics for the title card.
|
||||
// Don't let LJ see this
|
||||
//
|
||||
static void ST_cacheLevelTitle(void)
|
||||
{
|
||||
lt_patches[0] = (patch_t *)W_CachePatchName("LTACTBLU", PU_HUDGFX);
|
||||
lt_patches[1] = (patch_t *)W_CachePatchName("LTZIGZAG", PU_HUDGFX);
|
||||
lt_patches[2] = (patch_t *)W_CachePatchName("LTZZTEXT", PU_HUDGFX);
|
||||
UINT8 i;
|
||||
char buf[9];
|
||||
|
||||
// SRB2KART
|
||||
tcchev1 = (patch_t *)W_CachePatchName("TCCHEV1W", PU_HUDGFX);
|
||||
tcchev2 = (patch_t *)W_CachePatchName("TCCHEV2W", PU_HUDGFX);
|
||||
|
||||
tcol1 = (patch_t *)W_CachePatchName("TCCHOL1", PU_HUDGFX);
|
||||
tcol2 = (patch_t *)W_CachePatchName("TCCHOL2", PU_HUDGFX);
|
||||
|
||||
tcroundbar = (patch_t *)W_CachePatchName("TCBB0", PU_HUDGFX);
|
||||
tcround = (patch_t *)W_CachePatchName("TCROUND", PU_HUDGFX);
|
||||
|
||||
tccircletop = (patch_t *)W_CachePatchName("TCSN1", PU_HUDGFX);
|
||||
tccirclebottom =(patch_t *)W_CachePatchName("TCSN2", PU_HUDGFX);
|
||||
tccirclebg = (patch_t *)W_CachePatchName("TCEG3", PU_HUDGFX);
|
||||
|
||||
tcbanner = (patch_t *)W_CachePatchName("TCBSKA0", PU_HUDGFX);
|
||||
tcbanner2 = (patch_t *)W_CachePatchName("TCBC0", PU_HUDGFX);
|
||||
|
||||
tcact = (patch_t *)W_CachePatchName("TT_ACT", PU_HUDGFX);
|
||||
|
||||
// Cache round #
|
||||
for (i=1; i < 11; i++)
|
||||
{
|
||||
sprintf(buf, "TT_RND%d", i);
|
||||
tcroundnum[i-1] = (patch_t *)W_CachePatchName(buf, PU_HUDGFX);
|
||||
}
|
||||
|
||||
// Cache act #
|
||||
for (i=0; i < 10; i++)
|
||||
{
|
||||
sprintf(buf, "TT_ACT%d", i);
|
||||
tcactnum[i] = (patch_t *)W_CachePatchName(buf, PU_HUDGFX);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//
|
||||
|
|
@ -649,12 +724,28 @@ void ST_startTitleCard(void)
|
|||
// cache every HUD patch used
|
||||
ST_cacheLevelTitle();
|
||||
|
||||
// Set most elements to start off-screen, ST_runTitleCard will have them slide in afterwards
|
||||
chev1x = BASE_CHEV1X +350; // start off-screen
|
||||
chev1y = BASE_CHEV1Y;
|
||||
chev2x = BASE_CHEV2X -350; // start off-screen
|
||||
chev2y = BASE_CHEV2Y;
|
||||
chevtflag = 0;
|
||||
|
||||
roundx = -999;
|
||||
roundy = -999;
|
||||
|
||||
roundnumx = -999;
|
||||
roundnumy = -999;
|
||||
eggx1 = -999;
|
||||
eggx2 = -999;
|
||||
eggy1 = -999;
|
||||
eggy2 = -999;
|
||||
|
||||
bannery = 300;
|
||||
|
||||
// initialize HUD variables
|
||||
lt_ticker = lt_exitticker = lt_lasttic = 0;
|
||||
lt_endtime = 2*TICRATE + (10*NEWTICRATERATIO);
|
||||
lt_scroll = BASEVIDWIDTH * FRACUNIT;
|
||||
lt_zigzag = -((lt_patches[1])->width * FRACUNIT);
|
||||
lt_mom = 0;
|
||||
lt_endtime = 4*TICRATE; // + (10*NEWTICRATERATIO);
|
||||
}
|
||||
|
||||
//
|
||||
|
|
@ -679,6 +770,8 @@ void ST_preDrawTitleCard(void)
|
|||
void ST_runTitleCard(void)
|
||||
{
|
||||
boolean run = !(paused || P_AutoPause());
|
||||
INT32 auxticker;
|
||||
boolean gp = (grandprixinfo.gp && grandprixinfo.roundnum); // check whether we're in grandprix
|
||||
|
||||
if (!G_IsTitleCardAvailable())
|
||||
return;
|
||||
|
|
@ -690,35 +783,137 @@ void ST_runTitleCard(void)
|
|||
{
|
||||
// tick
|
||||
lt_ticker++;
|
||||
|
||||
// SRB2KART
|
||||
// side Zig-Zag positions...
|
||||
|
||||
// TITLECARD START
|
||||
if (lt_ticker < TTANIMSTART)
|
||||
{
|
||||
chev1x = max(BASE_CHEV1X, (BASE_CHEV1X +350) - (INT32)(lt_ticker)*50);
|
||||
chev2x = min(BASE_CHEV2X, (BASE_CHEV2X -350) + (INT32)(lt_ticker)*50);
|
||||
}
|
||||
|
||||
// OPEN ZIG-ZAGS 1 SECOND IN
|
||||
if (lt_ticker > TTANIMTHRESHOLD)
|
||||
{
|
||||
auxticker = (INT32)(lt_ticker) - TTANIMTHRESHOLD;
|
||||
|
||||
chev1x = min(320, BASE_CHEV1X + auxticker*16);
|
||||
chev1y = max(0, BASE_CHEV1Y - auxticker*16);
|
||||
|
||||
chev2x = max(0, BASE_CHEV2X - auxticker*16);
|
||||
chev2y = min(200, BASE_CHEV2Y + auxticker*16);
|
||||
|
||||
// translucent fade after opening up.
|
||||
chevtflag = min(5, ((auxticker)/5)) << V_ALPHASHIFT;
|
||||
|
||||
|
||||
// OPEN ZIG-ZAG: END OF ANIMATION (they leave the screen borders)
|
||||
if (lt_ticker > TTANIMENDTHRESHOLD)
|
||||
{
|
||||
auxticker = (INT32)lt_ticker - TTANIMENDTHRESHOLD;
|
||||
|
||||
chev1x += auxticker*16;
|
||||
chev1y -= auxticker*16;
|
||||
|
||||
chev2x -= auxticker*16;
|
||||
chev2y += auxticker*16;
|
||||
}
|
||||
}
|
||||
|
||||
// ROUND BAR + EGG
|
||||
|
||||
eggy1 = FINAL_EGGY; // Make sure to reset that each call so that Y position doesn't go bonkers
|
||||
|
||||
// SLIDE BAR IN, SLIDE "ROUND" DOWNWARDS
|
||||
if (lt_ticker <= TTANIMTHRESHOLD)
|
||||
{
|
||||
INT32 interptimer = (INT32)lt_ticker - TTANIMSTART;
|
||||
// INT32 because tic_t is unsigned and we want this to be potentially negative
|
||||
|
||||
if (interptimer >= 0)
|
||||
{
|
||||
INT32 interpdiff = ((TTANIMTHRESHOLD-TTANIMSTART) - interptimer);
|
||||
interpdiff *= interpdiff; // interpdiff^2
|
||||
|
||||
roundx = FINAL_ROUNDX - interpdiff;
|
||||
roundy = FINAL_ROUNDY - interpdiff;
|
||||
eggy1 = FINAL_EGGY + interpdiff;
|
||||
|
||||
}
|
||||
}
|
||||
// SLIDE BAR OUT, SLIDE "ROUND" DOWNWARDS FASTER
|
||||
else if (lt_ticker >= TTANIMENDTHRESHOLD)
|
||||
{
|
||||
auxticker = (INT32)lt_ticker - TTANIMENDTHRESHOLD;
|
||||
|
||||
roundx = FINAL_ROUNDX - auxticker*24;
|
||||
roundy = FINAL_ROUNDY + auxticker*48;
|
||||
eggy1 = FINAL_EGGY + auxticker*48;
|
||||
}
|
||||
|
||||
// follow the round bar.
|
||||
eggx1 = roundx + tcroundbar->width/2;
|
||||
|
||||
// initially, both halves are on the same coordinates.
|
||||
eggx2 = eggx1;
|
||||
eggy2 = eggy1;
|
||||
// same for the background (duh)
|
||||
roundnumx = eggx1;
|
||||
roundnumy = eggy1;
|
||||
|
||||
// split both halves of the egg, but only do that in grand prix!
|
||||
if (gp && lt_ticker > TTANIMTHRESHOLD + TICRATE/2)
|
||||
{
|
||||
auxticker = (INT32)lt_ticker - (TTANIMTHRESHOLD + TICRATE/2);
|
||||
|
||||
eggx1 -= auxticker*12;
|
||||
eggy1 -= auxticker*12;
|
||||
|
||||
eggx2 += auxticker*12;
|
||||
eggy2 += auxticker*12;
|
||||
|
||||
}
|
||||
|
||||
|
||||
// SCROLLING BOTTOM BANNER
|
||||
|
||||
// SLIDE BANNER UPWARDS WITH A FUNNY BOUNCE (this requires trig :death:)
|
||||
if (lt_ticker < TTANIMTHRESHOLD)
|
||||
{
|
||||
INT32 costimer = (INT32)lt_ticker - TTANIMSTART;
|
||||
// INT32 because tic_t is unsigned and we want this to be potentially negative
|
||||
|
||||
if (costimer > 0)
|
||||
{
|
||||
// For this animation, we're going to do a tiny bit of stupid trigonometry.
|
||||
// Admittedly all of this is going to look like magic numbers, and honestly? They are.
|
||||
|
||||
// start at angle 355 (where y = ~230 with our params)
|
||||
// and go to angle 131 (where y = ~160 with our params)
|
||||
|
||||
UINT8 basey = 190;
|
||||
UINT8 amplitude = 45;
|
||||
fixed_t ang = (355 - costimer*14)*FRACUNIT;
|
||||
|
||||
bannery = basey + (amplitude * FINECOSINE(FixedAngle(ang)>>ANGLETOFINESHIFT)) / FRACUNIT;
|
||||
}
|
||||
}
|
||||
// SLIDE BANNER DOWNWARDS OUT OF THE SCREEN AT THE END
|
||||
else if (lt_ticker >= TTANIMENDTHRESHOLD)
|
||||
{
|
||||
auxticker = (INT32)lt_ticker - TTANIMENDTHRESHOLD;
|
||||
bannery = FINAL_BANNERY + auxticker*16;
|
||||
}
|
||||
|
||||
// No matter the circumstances, scroll the banner...
|
||||
bannerx = -(lt_ticker%(tcbanner->width));
|
||||
|
||||
|
||||
// used for hud slidein
|
||||
if (lt_ticker >= lt_endtime)
|
||||
lt_exitticker++;
|
||||
|
||||
// scroll to screen (level title)
|
||||
if (!lt_exitticker)
|
||||
{
|
||||
if (abs(lt_scroll) > FRACUNIT)
|
||||
lt_scroll -= (lt_scroll>>2);
|
||||
else
|
||||
lt_scroll = 0;
|
||||
}
|
||||
// scroll away from screen (level title)
|
||||
else
|
||||
{
|
||||
lt_mom -= FRACUNIT*6;
|
||||
lt_scroll += lt_mom;
|
||||
}
|
||||
|
||||
// scroll to screen (zigzag)
|
||||
if (!lt_exitticker)
|
||||
{
|
||||
if (abs(lt_zigzag) > FRACUNIT)
|
||||
lt_zigzag -= (lt_zigzag>>2);
|
||||
else
|
||||
lt_zigzag = 0;
|
||||
}
|
||||
// scroll away from screen (zigzag)
|
||||
else
|
||||
lt_zigzag += lt_mom;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -729,25 +924,17 @@ void ST_runTitleCard(void)
|
|||
void ST_drawTitleCard(void)
|
||||
{
|
||||
char *lvlttl = mapheaderinfo[gamemap-1]->lvlttl;
|
||||
char *subttl = mapheaderinfo[gamemap-1]->subttl;
|
||||
char *zonttl = mapheaderinfo[gamemap-1]->zonttl; // SRB2kart
|
||||
UINT8 actnum = mapheaderinfo[gamemap-1]->actnum;
|
||||
INT32 lvlttlxpos, ttlnumxpos, zonexpos;
|
||||
INT32 subttlxpos = BASEVIDWIDTH/2;
|
||||
INT32 ttlscroll = FixedInt(lt_scroll);
|
||||
#ifdef TITLEPATCHES
|
||||
INT32 zzticker;
|
||||
patch_t *actpat, *zigzag, *zztext;
|
||||
UINT8 colornum;
|
||||
const UINT8 *colormap;
|
||||
boolean gp = (grandprixinfo.gp && grandprixinfo.roundnum);
|
||||
|
||||
if (players[g_localplayers[0]].skincolor)
|
||||
colornum = players[g_localplayers[0]].skincolor;
|
||||
else
|
||||
colornum = cv_playercolor[0].value;
|
||||
INT32 acttimer;
|
||||
fixed_t actscale;
|
||||
angle_t fakeangle;
|
||||
|
||||
colormap = R_GetTranslationColormap(TC_DEFAULT, colornum, GTC_CACHE);
|
||||
#endif
|
||||
INT32 bx = bannerx; // We need to make a copy of that otherwise pausing will cause problems.
|
||||
|
||||
UINT8 i;
|
||||
|
||||
if (!G_IsTitleCardAvailable())
|
||||
return;
|
||||
|
|
@ -761,95 +948,118 @@ void ST_drawTitleCard(void)
|
|||
if ((lt_ticker-lt_lasttic) > 1)
|
||||
lt_ticker = lt_lasttic+1;
|
||||
|
||||
ST_cacheLevelTitle();
|
||||
// Avoid HOMs while drawing the start of the titlecard
|
||||
if (lt_ticker < TTANIMSTART)
|
||||
V_DrawFill(0, 0, BASEVIDWIDTH, BASEVIDHEIGHT, levelfadecol);
|
||||
|
||||
#ifdef TITLEPATCHES
|
||||
actpat = lt_patches[0];
|
||||
zigzag = lt_patches[1];
|
||||
zztext = lt_patches[2];
|
||||
#endif
|
||||
// Background zig-zags
|
||||
V_DrawFixedPatch((chev1x)*FRACUNIT, (chev1y)*FRACUNIT, FRACUNIT, chevtflag, tcchev1, NULL);
|
||||
V_DrawFixedPatch((chev2x)*FRACUNIT, (chev2y)*FRACUNIT, FRACUNIT, chevtflag, tcchev2, NULL);
|
||||
|
||||
lvlttlxpos = ((BASEVIDWIDTH/2) - (V_LevelNameWidth(lvlttl)/2));
|
||||
|
||||
if (actnum > 0)
|
||||
lvlttlxpos -= V_LevelNameWidth(va("%d", actnum));
|
||||
// Draw ROUND bar, scroll it downwards.
|
||||
V_DrawFixedPatch(roundx*FRACUNIT, ((-32) + (lt_ticker%32))*FRACUNIT, FRACUNIT, V_SNAPTOTOP|V_SNAPTOLEFT, tcroundbar, NULL);
|
||||
// Draw ROUND text
|
||||
if (gp)
|
||||
V_DrawFixedPatch((roundx+10)*FRACUNIT, roundy*FRACUNIT, FRACUNIT, V_SNAPTOTOP|V_SNAPTOLEFT, tcround, NULL);
|
||||
|
||||
zonexpos = ttlnumxpos = lvlttlxpos + V_LevelNameWidth(lvlttl);
|
||||
if (zonttl[0])
|
||||
zonexpos -= V_LevelNameWidth(zonttl); // SRB2kart
|
||||
else
|
||||
zonexpos -= V_LevelNameWidth(M_GetText("Zone"));
|
||||
// round num background
|
||||
V_DrawFixedPatch(roundnumx*FRACUNIT, roundnumy*FRACUNIT, FRACUNIT, V_SNAPTOBOTTOM|V_SNAPTOLEFT, tccirclebg, NULL);
|
||||
|
||||
ttlnumxpos++;
|
||||
|
||||
if (lvlttlxpos < 0)
|
||||
lvlttlxpos = 0;
|
||||
|
||||
#ifdef TITLEPATCHES
|
||||
if (!splitscreen || (splitscreen && stplyr == &players[displayplayers[0]]))
|
||||
// Scrolling banner, we'll draw 3 of those back to back.
|
||||
for (i=0; i < 3; i++)
|
||||
{
|
||||
zzticker = lt_ticker;
|
||||
V_DrawMappedPatch(FixedInt(lt_zigzag), (-zzticker) % zigzag->height, V_SNAPTOTOP|V_SNAPTOLEFT, zigzag, colormap);
|
||||
V_DrawMappedPatch(FixedInt(lt_zigzag), (zigzag->height-zzticker) % zigzag->height, V_SNAPTOTOP|V_SNAPTOLEFT, zigzag, colormap);
|
||||
V_DrawMappedPatch(FixedInt(lt_zigzag), (-zigzag->height+zzticker) % zztext->height, V_SNAPTOTOP|V_SNAPTOLEFT, zztext, colormap);
|
||||
V_DrawMappedPatch(FixedInt(lt_zigzag), (zzticker) % zztext->height, V_SNAPTOTOP|V_SNAPTOLEFT, zztext, colormap);
|
||||
V_DrawFixedPatch((bannerx + bx)*FRACUNIT, (bannery)*FRACUNIT, FRACUNIT, V_SNAPTOBOTTOM|V_SNAPTOLEFT, tcbanner, NULL);
|
||||
bx += tcbanner->width;
|
||||
}
|
||||
#endif
|
||||
|
||||
if (actnum)
|
||||
// If possible, draw round number
|
||||
if (gp && grandprixinfo.roundnum > 0 && grandprixinfo.roundnum < 11) // Check boundaries JUST IN CASE.
|
||||
V_DrawFixedPatch(roundnumx*FRACUNIT, roundnumy*FRACUNIT, FRACUNIT, V_SNAPTOBOTTOM|V_SNAPTOLEFT, tcroundnum[grandprixinfo.roundnum-1], NULL);
|
||||
|
||||
// Draw both halves of the egg
|
||||
V_DrawFixedPatch(eggx1*FRACUNIT, eggy1*FRACUNIT, FRACUNIT, V_SNAPTOBOTTOM|V_SNAPTOLEFT, tccircletop, NULL);
|
||||
V_DrawFixedPatch(eggx2*FRACUNIT, eggy2*FRACUNIT, FRACUNIT, V_SNAPTOBOTTOM|V_SNAPTOLEFT, tccirclebottom, NULL);
|
||||
|
||||
// Now the level name.
|
||||
V_DrawTitleCardString((actnum) ? 265 : 280, 60, lvlttl, V_SNAPTORIGHT, true, lt_ticker, TTANIMENDTHRESHOLD);
|
||||
|
||||
if (!(mapheaderinfo[gamemap-1]->levelflags & LF_NOZONE))
|
||||
V_DrawTitleCardString((actnum) ? 265 : 280, 60+32, strlen(zonttl) ? zonttl : "ZONE", V_SNAPTORIGHT, true, lt_ticker - strlen(lvlttl), TTANIMENDTHRESHOLD);
|
||||
|
||||
// the act has a similar graphic animation, but we'll handle it here since it's only like 2 graphics lmfao.
|
||||
if (actnum && actnum < 10)
|
||||
{
|
||||
#ifdef TITLEPATCHES
|
||||
if (!splitscreen)
|
||||
|
||||
// compute delay before the act should appear.
|
||||
acttimer = lt_ticker - strlen(lvlttl);
|
||||
if (!(mapheaderinfo[gamemap-1]->levelflags & LF_NOZONE))
|
||||
acttimer -= strlen((strlen(zonttl)) ? (zonttl) : ("ZONE"));
|
||||
|
||||
actscale = 0;
|
||||
fakeangle = 0;
|
||||
|
||||
if (acttimer >= 0)
|
||||
{
|
||||
if (actnum > 9) // slightly offset the act diamond for two-digit act numbers
|
||||
V_DrawMappedPatch(ttlnumxpos + (V_LevelNameWidth(va("%d", actnum))/4) + ttlscroll, 104 - ttlscroll, 0, actpat, colormap);
|
||||
else
|
||||
V_DrawMappedPatch(ttlnumxpos + ttlscroll, 104 - ttlscroll, 0, actpat, colormap);
|
||||
}
|
||||
#endif
|
||||
V_DrawLevelTitle(ttlnumxpos + ttlscroll, 104, 0, va("%d", actnum));
|
||||
}
|
||||
|
||||
V_DrawLevelTitle(lvlttlxpos - ttlscroll, 80, 0, lvlttl);
|
||||
if (zonttl[0])
|
||||
V_DrawLevelTitle(zonexpos + ttlscroll, 104, 0, zonttl);
|
||||
else if (!(mapheaderinfo[gamemap-1]->levelflags & LF_NOZONE))
|
||||
V_DrawLevelTitle(zonexpos + ttlscroll, 104, 0, M_GetText("Zone"));
|
||||
V_DrawCenteredString(subttlxpos - ttlscroll, 135, 0|V_ALLOWLOWERCASE, subttl);
|
||||
if (acttimer < TTANIMENDTHRESHOLD) // spin in
|
||||
{
|
||||
fakeangle = min(360 + 90, acttimer*41) * ANG1;
|
||||
actscale = FINESINE(fakeangle>>ANGLETOFINESHIFT);
|
||||
}
|
||||
else // spin out
|
||||
{
|
||||
// Make letters disappear...
|
||||
acttimer -= TTANIMENDTHRESHOLD;
|
||||
|
||||
fakeangle = max(0, (360+90) - acttimer*41)*ANG1;
|
||||
actscale = FINESINE(fakeangle>>ANGLETOFINESHIFT);
|
||||
}
|
||||
|
||||
if (actscale)
|
||||
{
|
||||
// draw the top:
|
||||
V_DrawStretchyFixedPatch(286*FRACUNIT, 76*FRACUNIT, abs(actscale), FRACUNIT, V_SNAPTORIGHT|(actscale < 0 ? V_FLIP : 0), tcact, NULL);
|
||||
V_DrawStretchyFixedPatch(286*FRACUNIT, 123*FRACUNIT, abs(actscale), FRACUNIT, V_SNAPTORIGHT|(actscale < 0 ? V_FLIP : 0), tcactnum[actnum], NULL);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
lt_lasttic = lt_ticker;
|
||||
|
||||
luahook:
|
||||
LUAh_TitleCardHUD(stplyr);
|
||||
|
||||
}
|
||||
|
||||
// Clear defined coordinates, we don't need them anymore
|
||||
#undef FINAL_ROUNDX
|
||||
#undef FINAL_EGGY
|
||||
#undef FINAL_ROUNDY
|
||||
#undef FINAL_BANNERY
|
||||
|
||||
#undef BASE_CHEV1X
|
||||
#undef BASE_CHEV1Y
|
||||
#undef BASE_CHEV2X
|
||||
#undef BASE_CHEV2Y
|
||||
|
||||
#undef TTANIMTHRESHOLD
|
||||
#undef TTANIMSTART
|
||||
#undef TTANIMENDTHRESHOLD
|
||||
#undef TTANIMEND
|
||||
|
||||
//
|
||||
// Drawer for G_PreLevelTitleCard.
|
||||
//
|
||||
void ST_preLevelTitleCardDrawer(void)
|
||||
{
|
||||
V_DrawFill(0, 0, BASEVIDWIDTH, BASEVIDHEIGHT, levelfadecol);
|
||||
ST_drawWipeTitleCard();
|
||||
|
||||
ST_drawTitleCard();
|
||||
I_OsPolling();
|
||||
I_UpdateNoBlit();
|
||||
}
|
||||
|
||||
//
|
||||
// Draw the title card while on a wipe.
|
||||
// Also used in G_PreLevelTitleCard.
|
||||
//
|
||||
void ST_drawWipeTitleCard(void)
|
||||
{
|
||||
UINT8 i;
|
||||
|
||||
for (i = 0; i <= r_splitscreen; i++)
|
||||
{
|
||||
stplyr = &players[displayplayers[i]];
|
||||
ST_preDrawTitleCard();
|
||||
ST_drawTitleCard();
|
||||
}
|
||||
}
|
||||
|
||||
//
|
||||
// Draw the status bar overlay, customisable: the user chooses which
|
||||
// kind of information to overlay
|
||||
|
|
|
|||
|
|
@ -64,7 +64,6 @@ void ST_runTitleCard(void);
|
|||
void ST_drawTitleCard(void);
|
||||
void ST_preDrawTitleCard(void);
|
||||
void ST_preLevelTitleCardDrawer(void);
|
||||
void ST_drawWipeTitleCard(void);
|
||||
|
||||
extern tic_t lt_ticker, lt_lasttic;
|
||||
extern tic_t lt_exitticker, lt_endtime;
|
||||
|
|
|
|||
143
src/v_video.c
143
src/v_video.c
|
|
@ -1676,6 +1676,149 @@ void V_DrawChatCharacter(INT32 x, INT32 y, INT32 c, boolean lowercaseallowed, UI
|
|||
V_DrawFixedPatch(x*FRACUNIT, y*FRACUNIT, FRACUNIT/2, flags, fontv[HU_FONT].font[c], colormap);
|
||||
}
|
||||
|
||||
// V_TitleCardStringWidth
|
||||
// Get the string's width using the titlecard font.
|
||||
INT32 V_TitleCardStringWidth(const char *str)
|
||||
{
|
||||
INT32 xoffs = 0;
|
||||
const char *ch = str;
|
||||
char c;
|
||||
patch_t *pp;
|
||||
|
||||
for (;;ch++)
|
||||
{
|
||||
if (!*ch)
|
||||
break;
|
||||
|
||||
if (*ch == '\n')
|
||||
{
|
||||
xoffs = 0;
|
||||
continue;
|
||||
}
|
||||
|
||||
c = *ch;
|
||||
c = toupper(c);
|
||||
c -= LT_FONTSTART;
|
||||
|
||||
// check if character exists, if not, it's a space.
|
||||
if (c < 0 || c >= LT_FONTSIZE || !tc_font[0][(INT32)c])
|
||||
{
|
||||
xoffs += 10;
|
||||
continue;
|
||||
}
|
||||
|
||||
pp = tc_font[1][(INT32)c];
|
||||
|
||||
xoffs += pp->width-5;
|
||||
}
|
||||
|
||||
return xoffs;
|
||||
}
|
||||
|
||||
// V_DrawTitleCardScreen.
|
||||
// see v_video.h's prototype for more information.
|
||||
//
|
||||
void V_DrawTitleCardString(INT32 x, INT32 y, const char *str, INT32 flags, boolean alignright, INT32 timer, INT32 threshold)
|
||||
{
|
||||
|
||||
INT32 xoffs = 0;
|
||||
INT32 yoffs = 0;
|
||||
INT32 i = 0;
|
||||
|
||||
// per-letter variables
|
||||
fixed_t scalex;
|
||||
fixed_t offs;
|
||||
INT32 let_time;
|
||||
INT32 flipflag;
|
||||
angle_t fakeang;
|
||||
|
||||
const char *ch = str;
|
||||
char c;
|
||||
patch_t *pp;
|
||||
patch_t *ol;
|
||||
|
||||
x -= 2; // Account for patch width...
|
||||
|
||||
if (alignright)
|
||||
x -= V_TitleCardStringWidth(str);
|
||||
|
||||
|
||||
for (;;ch++, i++)
|
||||
{
|
||||
|
||||
scalex = FRACUNIT;
|
||||
offs = 0;
|
||||
let_time = timer - i;
|
||||
flipflag = 0;
|
||||
|
||||
if (!*ch)
|
||||
break;
|
||||
|
||||
if (*ch == '\n')
|
||||
{
|
||||
xoffs = x;
|
||||
yoffs += 32;
|
||||
|
||||
continue;
|
||||
}
|
||||
|
||||
c = *ch;
|
||||
|
||||
c = toupper(c);
|
||||
c -= LT_FONTSTART;
|
||||
|
||||
// check if character exists, if not, it's a space.
|
||||
if (c < 0 || c >= LT_FONTSIZE || !tc_font[1][(INT32)c])
|
||||
{
|
||||
xoffs += 10;
|
||||
continue;
|
||||
}
|
||||
|
||||
ol = tc_font[0][(INT32)c];
|
||||
pp = tc_font[1][(INT32)c];
|
||||
|
||||
if (timer)
|
||||
{
|
||||
|
||||
// make letters appear
|
||||
if (!threshold || let_time < threshold)
|
||||
{
|
||||
if (let_time <= 0)
|
||||
return; // No reason to continue drawing, none of the next letters will be drawn either.
|
||||
|
||||
// otherwise; scalex must start at 0
|
||||
// let's have each letter do 4 spins (360*4 + 90 = 1530 "degrees")
|
||||
fakeang = min(360 + 90, let_time*41) * ANG1;
|
||||
scalex = FINESINE(fakeang>>ANGLETOFINESHIFT);
|
||||
}
|
||||
else if (let_time > threshold)
|
||||
{
|
||||
// Make letters disappear...
|
||||
let_time -= threshold;
|
||||
|
||||
fakeang = max(0, (360+90) - let_time*41)*ANG1;
|
||||
scalex = FINESINE(fakeang>>ANGLETOFINESHIFT);
|
||||
}
|
||||
|
||||
// Because of how our patches are offset, we need to counter the displacement caused by changing the scale with an offset of our own.
|
||||
offs = ((FRACUNIT-scalex)*pp->width)/2;
|
||||
}
|
||||
|
||||
// And now, we just need to draw the stuff.
|
||||
flipflag = (scalex < 0) ? V_FLIP : 0;
|
||||
|
||||
if (scalex && ol && pp)
|
||||
{
|
||||
//CONS_Printf("%d\n", (INT32)c);
|
||||
V_DrawStretchyFixedPatch((x + xoffs)*FRACUNIT + offs, (y+yoffs)*FRACUNIT, abs(scalex), FRACUNIT, flags|flipflag, ol, NULL);
|
||||
V_DrawStretchyFixedPatch((x + xoffs)*FRACUNIT + offs, (y+yoffs)*FRACUNIT, abs(scalex), FRACUNIT, flags|flipflag, pp, NULL);
|
||||
}
|
||||
|
||||
xoffs += pp->width -5;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// Precompile a wordwrapped string to any given width.
|
||||
// This is a muuuch better method than V_WORDWRAP.
|
||||
char *V_WordWrap(INT32 x, INT32 w, INT32 option, const char *string)
|
||||
|
|
|
|||
|
|
@ -262,6 +262,16 @@ void V_DrawRightAlignedThinString(INT32 x, INT32 y, INT32 option, const char *st
|
|||
#define V_DrawThinStringAtFixed( x,y,option,string ) \
|
||||
V__DrawOneScaleString (x,y,FRACUNIT,option,TINY_FONT,string)
|
||||
|
||||
// Draws a titlecard font string.
|
||||
// timer: when the letters start appearing (leave to 0 to disable)
|
||||
// threshold: when the letters start disappearing (leave to 0 to disable) (both are INT32 in case you supply negative values...)
|
||||
// NOTE: This function ignores most conventional string flags (V_RETURN8, V_ALLOWLOWERCASE ...)
|
||||
// NOTE: This font only works with uppercase letters.
|
||||
void V_DrawTitleCardString(INT32 x, INT32 y, const char *str, INT32 flags, boolean alignright, INT32 timer, INT32 threshold);
|
||||
|
||||
// returns thr width of a string drawn using the above function.
|
||||
INT32 V_TitleCardStringWidth(const char *str);
|
||||
|
||||
// Draw tall nums, used for menu, HUD, intermission
|
||||
void V_DrawTallNum(INT32 x, INT32 y, INT32 flags, INT32 num);
|
||||
void V_DrawPaddedTallNum(INT32 x, INT32 y, INT32 flags, INT32 num, INT32 digits);
|
||||
|
|
|
|||
145
src/z_zone.c
145
src/z_zone.c
|
|
@ -47,10 +47,6 @@ static boolean Z_calloc = false;
|
|||
|
||||
#define ZONEID 0xa441d13d
|
||||
|
||||
#ifdef ZDEBUG
|
||||
//#define ZDEBUG2
|
||||
#endif
|
||||
|
||||
struct memblock_s;
|
||||
|
||||
typedef struct
|
||||
|
|
@ -76,10 +72,8 @@ typedef struct memblock_s
|
|||
size_t size; // including the header and blocks
|
||||
size_t realsize; // size of real data only
|
||||
|
||||
#ifdef ZDEBUG
|
||||
const char *ownerfile;
|
||||
INT32 ownerline;
|
||||
#endif
|
||||
|
||||
struct memblock_s *next, *prev;
|
||||
} ATTRPACK memblock_t;
|
||||
|
|
@ -91,9 +85,7 @@ static memblock_t head;
|
|||
// Function prototypes
|
||||
//
|
||||
static void Command_Memfree_f(void);
|
||||
#ifdef ZDEBUG
|
||||
static void Command_Memdump_f(void);
|
||||
#endif
|
||||
|
||||
// --------------------------
|
||||
// Zone memory initialisation
|
||||
|
|
@ -117,10 +109,7 @@ void Z_Init(void)
|
|||
|
||||
// Note: This allocates memory. Watch out.
|
||||
COM_AddCommand("memfree", Command_Memfree_f);
|
||||
|
||||
#ifdef ZDEBUG
|
||||
COM_AddCommand("memdump", Command_Memdump_f);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -137,12 +126,8 @@ void Z_Init(void)
|
|||
* \return A pointer to the memblock_t for the given memory.
|
||||
* \sa Z_Free, Z_ReallocAlign
|
||||
*/
|
||||
#ifdef ZDEBUG
|
||||
#define Ptr2Memblock(s, f) Ptr2Memblock2(s, f, __FILE__, __LINE__)
|
||||
static memblock_t *Ptr2Memblock2(void *ptr, const char* func, const char *file, INT32 line)
|
||||
#else
|
||||
static memblock_t *Ptr2Memblock(void *ptr, const char* func)
|
||||
#endif
|
||||
{
|
||||
memhdr_t *hdr;
|
||||
memblock_t *block;
|
||||
|
|
@ -150,8 +135,8 @@ static memblock_t *Ptr2Memblock(void *ptr, const char* func)
|
|||
if (ptr == NULL)
|
||||
return NULL;
|
||||
|
||||
#ifdef ZDEBUG2
|
||||
CONS_Printf("%s %s:%d\n", func, file, line);
|
||||
#ifdef ZDEBUG
|
||||
CONS_Debug(DBG_MEMORY, "%s %s:%d\n", func, file, line);
|
||||
#endif
|
||||
|
||||
hdr = (memhdr_t *)((UINT8 *)ptr - sizeof *hdr);
|
||||
|
|
@ -163,20 +148,12 @@ static memblock_t *Ptr2Memblock(void *ptr, const char* func)
|
|||
#ifdef VALGRIND_MEMPOOL_EXISTS
|
||||
if (!VALGRIND_MEMPOOL_EXISTS(hdr->block))
|
||||
{
|
||||
#ifdef ZDEBUG
|
||||
I_Error("%s: bad memblock from %s:%d", func, file, line);
|
||||
#else
|
||||
I_Error("%s: bad memblock", func);
|
||||
#endif
|
||||
}
|
||||
#endif
|
||||
if (hdr->id != ZONEID)
|
||||
{
|
||||
#ifdef ZDEBUG
|
||||
I_Error("%s: wrong id from %s:%d", func, file, line);
|
||||
#else
|
||||
I_Error("%s: wrong id", func);
|
||||
#endif
|
||||
}
|
||||
block = hdr->block;
|
||||
#ifdef VALGRIND_MAKE_MEM_NOACCESS
|
||||
|
|
@ -192,31 +169,24 @@ static memblock_t *Ptr2Memblock(void *ptr, const char* func)
|
|||
* assumed to have been allocated with Z_Malloc/Z_Calloc.
|
||||
* \sa Z_FreeTags
|
||||
*/
|
||||
#ifdef ZDEBUG
|
||||
void Z_Free2(void *ptr, const char *file, INT32 line)
|
||||
#else
|
||||
void Z_Free(void *ptr)
|
||||
#endif
|
||||
{
|
||||
memblock_t *block;
|
||||
|
||||
if (ptr == NULL)
|
||||
return;
|
||||
|
||||
#ifdef ZDEBUG2
|
||||
/*
|
||||
// Sal: There's a print exactly like this just below?
|
||||
#ifdef ZDEBUG
|
||||
CONS_Debug(DBG_MEMORY, "Z_Free %s:%d\n", file, line);
|
||||
#endif
|
||||
*/
|
||||
|
||||
#ifdef ZDEBUG
|
||||
block = Ptr2Memblock2(ptr, "Z_Free", file, line);
|
||||
#else
|
||||
block = Ptr2Memblock(ptr, "Z_Free");
|
||||
#endif
|
||||
|
||||
#ifdef ZDEBUG
|
||||
// Write every Z_Free call to a debug file.
|
||||
CONS_Debug(DBG_MEMORY, "Z_Free at %s:%d\n", file, line);
|
||||
#endif
|
||||
|
||||
// anything that isn't by lua gets passed to lua just in case.
|
||||
if (block->tag != PU_LUA)
|
||||
|
|
@ -280,12 +250,8 @@ static void *xm(size_t size)
|
|||
* \note You can pass Z_Malloc() a NULL user if the tag is less than PU_PURGELEVEL.
|
||||
* \sa Z_CallocAlign, Z_ReallocAlign
|
||||
*/
|
||||
#ifdef ZDEBUG
|
||||
void *Z_Malloc2(size_t size, INT32 tag, void *user, INT32 alignbits,
|
||||
const char *file, INT32 line)
|
||||
#else
|
||||
void *Z_MallocAlign(size_t size, INT32 tag, void *user, INT32 alignbits)
|
||||
#endif
|
||||
{
|
||||
size_t extrabytes = (1<<alignbits) - 1;
|
||||
size_t padsize = 0;
|
||||
|
|
@ -295,7 +261,7 @@ void *Z_MallocAlign(size_t size, INT32 tag, void *user, INT32 alignbits)
|
|||
void *given;
|
||||
size_t blocksize = extrabytes + sizeof *hdr + size;
|
||||
|
||||
#ifdef ZDEBUG2
|
||||
#ifdef ZDEBUG
|
||||
CONS_Debug(DBG_MEMORY, "Z_Malloc %s:%d\n", file, line);
|
||||
#endif
|
||||
|
||||
|
|
@ -329,10 +295,8 @@ void *Z_MallocAlign(size_t size, INT32 tag, void *user, INT32 alignbits)
|
|||
block->hdr = hdr;
|
||||
block->tag = tag;
|
||||
block->user = NULL;
|
||||
#ifdef ZDEBUG
|
||||
block->ownerline = line;
|
||||
block->ownerfile = file;
|
||||
#endif
|
||||
block->size = blocksize;
|
||||
block->realsize = size;
|
||||
|
||||
|
|
@ -375,20 +339,12 @@ void *Z_MallocAlign(size_t size, INT32 tag, void *user, INT32 alignbits)
|
|||
* \note You can pass Z_Calloc() a NULL user if the tag is less than PU_PURGELEVEL.
|
||||
* \sa Z_MallocAlign, Z_ReallocAlign
|
||||
*/
|
||||
#ifdef ZDEBUG
|
||||
void *Z_Calloc2(size_t size, INT32 tag, void *user, INT32 alignbits, const char *file, INT32 line)
|
||||
#else
|
||||
void *Z_CallocAlign(size_t size, INT32 tag, void *user, INT32 alignbits)
|
||||
#endif
|
||||
{
|
||||
#ifdef VALGRIND_MEMPOOL_ALLOC
|
||||
Z_calloc = true;
|
||||
#endif
|
||||
#ifdef ZDEBUG
|
||||
return memset(Z_Malloc2 (size, tag, user, alignbits, file, line), 0, size);
|
||||
#else
|
||||
return memset(Z_MallocAlign(size, tag, user, alignbits ), 0, size);
|
||||
#endif
|
||||
}
|
||||
|
||||
/** The Z_ReallocAlign function.
|
||||
|
|
@ -407,17 +363,13 @@ void *Z_CallocAlign(size_t size, INT32 tag, void *user, INT32 alignbits)
|
|||
* \note You can pass Z_Realloc() a NULL user if the tag is less than PU_PURGELEVEL.
|
||||
* \sa Z_MallocAlign, Z_CallocAlign
|
||||
*/
|
||||
#ifdef ZDEBUG
|
||||
void *Z_Realloc2(void *ptr, size_t size, INT32 tag, void *user, INT32 alignbits, const char *file, INT32 line)
|
||||
#else
|
||||
void *Z_ReallocAlign(void *ptr, size_t size, INT32 tag, void *user, INT32 alignbits)
|
||||
#endif
|
||||
{
|
||||
void *rez;
|
||||
memblock_t *block;
|
||||
size_t copysize;
|
||||
|
||||
#ifdef ZDEBUG2
|
||||
#ifdef ZDEBUG
|
||||
CONS_Debug(DBG_MEMORY, "Z_Realloc %s:%d\n", file, line);
|
||||
#endif
|
||||
|
||||
|
|
@ -429,29 +381,17 @@ void *Z_ReallocAlign(void *ptr, size_t size, INT32 tag, void *user, INT32 alignb
|
|||
|
||||
if (!ptr)
|
||||
{
|
||||
#ifdef ZDEBUG
|
||||
return Z_Calloc2(size, tag, user, alignbits, file , line);
|
||||
#else
|
||||
return Z_CallocAlign(size, tag, user, alignbits);
|
||||
#endif
|
||||
}
|
||||
|
||||
#ifdef ZDEBUG
|
||||
block = Ptr2Memblock2(ptr, "Z_Realloc", file, line);
|
||||
#else
|
||||
block = Ptr2Memblock(ptr, "Z_Realloc");
|
||||
#endif
|
||||
|
||||
if (block == NULL)
|
||||
return NULL;
|
||||
|
||||
#ifdef ZDEBUG
|
||||
// Write every Z_Realloc call to a debug file.
|
||||
DEBFILE(va("Z_Realloc at %s:%d\n", file, line));
|
||||
rez = Z_Malloc2(size, tag, user, alignbits, file, line);
|
||||
#else
|
||||
rez = Z_MallocAlign(size, tag, user, alignbits);
|
||||
#endif
|
||||
|
||||
if (size < block->realsize)
|
||||
copysize = size;
|
||||
|
|
@ -460,11 +400,7 @@ void *Z_ReallocAlign(void *ptr, size_t size, INT32 tag, void *user, INT32 alignb
|
|||
|
||||
M_Memcpy(rez, ptr, copysize);
|
||||
|
||||
#ifdef ZDEBUG
|
||||
Z_Free2(ptr, file, line);
|
||||
#else
|
||||
Z_Free(ptr);
|
||||
#endif
|
||||
|
||||
// Need to set the user in case the old block had the same one, in
|
||||
// which case the Z_Free will just have NULLed it out.
|
||||
|
|
@ -569,7 +505,7 @@ void Z_CheckHeap(INT32 i)
|
|||
blocknumon++;
|
||||
hdr = block->hdr;
|
||||
given = (UINT8 *)hdr + sizeof *hdr;
|
||||
#ifdef ZDEBUG2
|
||||
#ifdef ZDEBUG
|
||||
CONS_Debug(DBG_MEMORY, "block %u owned by %s:%d\n",
|
||||
blocknumon, block->ownerfile, block->ownerline);
|
||||
#endif
|
||||
|
|
@ -577,51 +513,35 @@ void Z_CheckHeap(INT32 i)
|
|||
if (!VALGRIND_MEMPOOL_EXISTS(block))
|
||||
{
|
||||
I_Error("Z_CheckHeap %d: block %u"
|
||||
#ifdef ZDEBUG
|
||||
"(owned by %s:%d)"
|
||||
#endif
|
||||
" should not exist", i, blocknumon
|
||||
#ifdef ZDEBUG
|
||||
, block->ownerfile, block->ownerline
|
||||
#endif
|
||||
);
|
||||
" should not exist", i, blocknumon,
|
||||
block->ownerfile, block->ownerline
|
||||
);
|
||||
}
|
||||
#endif
|
||||
if (block->user != NULL && *(block->user) != given)
|
||||
{
|
||||
I_Error("Z_CheckHeap %d: block %u"
|
||||
#ifdef ZDEBUG
|
||||
"(owned by %s:%d)"
|
||||
#endif
|
||||
" doesn't have a proper user", i, blocknumon
|
||||
#ifdef ZDEBUG
|
||||
, block->ownerfile, block->ownerline
|
||||
#endif
|
||||
);
|
||||
" doesn't have a proper user", i, blocknumon,
|
||||
block->ownerfile, block->ownerline
|
||||
);
|
||||
}
|
||||
if (block->next->prev != block)
|
||||
{
|
||||
I_Error("Z_CheckHeap %d: block %u"
|
||||
#ifdef ZDEBUG
|
||||
"(owned by %s:%d)"
|
||||
#endif
|
||||
" lacks proper backlink", i, blocknumon
|
||||
#ifdef ZDEBUG
|
||||
, block->ownerfile, block->ownerline
|
||||
#endif
|
||||
);
|
||||
" lacks proper backlink", i, blocknumon,
|
||||
block->ownerfile, block->ownerline
|
||||
);
|
||||
}
|
||||
if (block->prev->next != block)
|
||||
{
|
||||
I_Error("Z_CheckHeap %d: block %u"
|
||||
#ifdef ZDEBUG
|
||||
"(owned by %s:%d)"
|
||||
#endif
|
||||
" lacks proper forward link", i, blocknumon
|
||||
#ifdef ZDEBUG
|
||||
, block->ownerfile, block->ownerline
|
||||
#endif
|
||||
);
|
||||
" lacks proper forward link", i, blocknumon,
|
||||
block->ownerfile, block->ownerline
|
||||
);
|
||||
}
|
||||
#ifdef VALGRIND_MAKE_MEM_DEFINED
|
||||
VALGRIND_MAKE_MEM_DEFINED(hdr, sizeof *hdr);
|
||||
|
|
@ -629,27 +549,19 @@ void Z_CheckHeap(INT32 i)
|
|||
if (hdr->block != block)
|
||||
{
|
||||
I_Error("Z_CheckHeap %d: block %u"
|
||||
#ifdef ZDEBUG
|
||||
"(owned by %s:%d)"
|
||||
#endif
|
||||
" doesn't have linkback from allocated memory",
|
||||
i, blocknumon
|
||||
#ifdef ZDEBUG
|
||||
, block->ownerfile, block->ownerline
|
||||
#endif
|
||||
);
|
||||
i, blocknumon,
|
||||
block->ownerfile, block->ownerline
|
||||
);
|
||||
}
|
||||
if (hdr->id != ZONEID)
|
||||
{
|
||||
I_Error("Z_CheckHeap %d: block %u"
|
||||
#ifdef ZDEBUG
|
||||
"(owned by %s:%d)"
|
||||
#endif
|
||||
" have the wrong ID", i, blocknumon
|
||||
#ifdef ZDEBUG
|
||||
, block->ownerfile, block->ownerline
|
||||
#endif
|
||||
);
|
||||
" have the wrong ID", i, blocknumon,
|
||||
block->ownerfile, block->ownerline
|
||||
);
|
||||
}
|
||||
#ifdef VALGRIND_MAKE_MEM_NOACCESS
|
||||
VALGRIND_MAKE_MEM_NOACCESS(hdr, sizeof *hdr);
|
||||
|
|
@ -828,11 +740,9 @@ static void Command_Memfree_f(void)
|
|||
CONS_Printf(M_GetText("Available physical memory: %7u KB\n"), freebytes>>10);
|
||||
}
|
||||
|
||||
#ifdef ZDEBUG
|
||||
/** The function called by the "memdump" console command.
|
||||
* Prints zone memory debugging information (i.e. tag, size, location in code allocated).
|
||||
* Can be all memory allocated in game, or between a set of tags (if -min/-max args used).
|
||||
* This command is available only if ZDEBUG is enabled.
|
||||
*/
|
||||
static void Command_Memdump_f(void)
|
||||
{
|
||||
|
|
@ -853,7 +763,6 @@ static void Command_Memdump_f(void)
|
|||
CONS_Printf("[%3d] %s (%s) bytes @ %s:%d\n", block->tag, sizeu1(block->size), sizeu2(block->realsize), filename ? filename + 1 : block->ownerfile, block->ownerline);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/** Creates a copy of a string.
|
||||
*
|
||||
|
|
|
|||
12
src/z_zone.h
12
src/z_zone.h
|
|
@ -79,12 +79,8 @@ void Z_Init(void);
|
|||
//
|
||||
// Zone memory allocation
|
||||
//
|
||||
// enable ZDEBUG to get the file + line the functions were called from
|
||||
// for ZZ_Alloc, see doomdef.h
|
||||
//
|
||||
|
||||
// Z_Free and alloc with alignment
|
||||
#ifdef ZDEBUG
|
||||
#define Z_Free(p) Z_Free2(p, __FILE__, __LINE__)
|
||||
#define Z_MallocAlign(s,t,u,a) Z_Malloc2(s, t, u, a, __FILE__, __LINE__)
|
||||
#define Z_CallocAlign(s,t,u,a) Z_Calloc2(s, t, u, a, __FILE__, __LINE__)
|
||||
|
|
@ -93,12 +89,6 @@ void Z_Free2(void *ptr, const char *file, INT32 line);
|
|||
void *Z_Malloc2(size_t size, INT32 tag, void *user, INT32 alignbits, const char *file, INT32 line) FUNCALLOC(1);
|
||||
void *Z_Calloc2(size_t size, INT32 tag, void *user, INT32 alignbits, const char *file, INT32 line) FUNCALLOC(1);
|
||||
void *Z_Realloc2(void *ptr, size_t size, INT32 tag, void *user, INT32 alignbits, const char *file, INT32 line) FUNCALLOC(2);
|
||||
#else
|
||||
void Z_Free(void *ptr);
|
||||
void *Z_MallocAlign(size_t size, INT32 tag, void *user, INT32 alignbits) FUNCALLOC(1);
|
||||
void *Z_CallocAlign(size_t size, INT32 tag, void *user, INT32 alignbits) FUNCALLOC(1);
|
||||
void *Z_ReallocAlign(void *ptr, size_t size, INT32 tag, void *user, INT32 alignbits) FUNCALLOC(2);
|
||||
#endif
|
||||
|
||||
// Alloc with no alignment
|
||||
#define Z_Malloc(s,t,u) Z_MallocAlign(s, t, u, 0)
|
||||
|
|
@ -106,7 +96,7 @@ void *Z_ReallocAlign(void *ptr, size_t size, INT32 tag, void *user, INT32 alignb
|
|||
#define Z_Realloc(p,s,t,u) Z_ReallocAlign(p, s, t, u, 0)
|
||||
|
||||
// Free all memory by tag
|
||||
// these don't give line numbers for ZDEBUG currently though
|
||||
// these don't give line numbers currently though
|
||||
// (perhaps this should be changed in future?)
|
||||
#define Z_FreeTag(tagnum) Z_FreeTags(tagnum, tagnum)
|
||||
void Z_FreeTags(INT32 lowtag, INT32 hightag);
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue