Merge branch 'smiling_on_the_inside' into 'master'

Smiles! (and some tweaks to Super)

See merge request !119
This commit is contained in:
toaster 2017-10-11 10:40:11 -04:00
commit e298e35ada
22 changed files with 608 additions and 93 deletions

View File

@ -544,6 +544,7 @@ static inline void resynch_write_player(resynch_pak *rsp, const size_t i)
rsp->thokitem = (UINT32)LONG(players[i].thokitem); //mobjtype_t
rsp->spinitem = (UINT32)LONG(players[i].spinitem); //mobjtype_t
rsp->revitem = (UINT32)LONG(players[i].revitem); //mobjtype_t
rsp->followitem = (UINT32)LONG(players[i].followitem); //mobjtype_t
rsp->actionspd = (fixed_t)LONG(players[i].actionspd);
rsp->mindash = (fixed_t)LONG(players[i].mindash);
rsp->maxdash = (fixed_t)LONG(players[i].maxdash);
@ -673,6 +674,7 @@ static void resynch_read_player(resynch_pak *rsp)
players[i].thokitem = (UINT32)LONG(rsp->thokitem); //mobjtype_t
players[i].spinitem = (UINT32)LONG(rsp->spinitem); //mobjtype_t
players[i].revitem = (UINT32)LONG(rsp->revitem); //mobjtype_t
players[i].followitem = (UINT32)LONG(rsp->followitem); //mobjtype_t
players[i].actionspd = (fixed_t)LONG(rsp->actionspd);
players[i].mindash = (fixed_t)LONG(rsp->mindash);
players[i].maxdash = (fixed_t)LONG(rsp->maxdash);

View File

@ -189,6 +189,7 @@ typedef struct
UINT32 thokitem; // mobjtype_t
UINT32 spinitem; // mobjtype_t
UINT32 revitem; // mobjtype_t
UINT32 followitem; // mobjtype_t
fixed_t actionspd;
fixed_t mindash;
fixed_t maxdash;

View File

@ -369,6 +369,8 @@ typedef struct player_s
mobjtype_t thokitem; // Object # to spawn for the thok
mobjtype_t spinitem; // Object # to spawn for spindash/spinning
mobjtype_t revitem; // Object # to spawn for spindash/spinning
mobjtype_t followitem; // Object # to spawn for Smiles
mobj_t *followmobj; // Smiles all around
fixed_t actionspd; // Speed of thok/glide/fly
fixed_t mindash; // Minimum spindash speed

View File

@ -1804,6 +1804,7 @@ static actionpointer_t actionpointers[] =
{{A_FlickyHeightCheck}, "A_FLICKYHEIGHTCHECK"},
{{A_FlickyFlutter}, "A_FLICKYFLUTTER"},
{{A_FlameParticle}, "A_FLAMEPARTICLE"},
{{A_FadeOverlay}, "A_FADEOVERLAY"},
{{NULL}, "NONE"},
@ -2831,6 +2832,11 @@ static void readmaincfg(MYFILE *f)
bootmap = (INT16)value;
//titlechanged = true;
}
else if (fastcmp(word, "STARTCHAR"))
{
startchar = (INT16)value;
char_on = -1;
}
else
deh_warning("Maincfg: unknown word '%s'", word);
}
@ -3460,15 +3466,12 @@ static const char *const STATE_LIST[] = { // array length left dynamic for sanit
"S_PLAY_MELEE_LANDING",
// SF_SUPER
"S_PLAY_SUPERTRANS1",
"S_PLAY_SUPERTRANS2",
"S_PLAY_SUPERTRANS3",
"S_PLAY_SUPERTRANS4",
"S_PLAY_SUPERTRANS5",
"S_PLAY_SUPERTRANS6",
"S_PLAY_SUPERTRANS7",
"S_PLAY_SUPERTRANS8",
"S_PLAY_SUPERTRANS9", // This has special significance in the code. If you add more frames, search for it and make the appropriate changes.
"S_PLAY_SUPER_TRANS1",
"S_PLAY_SUPER_TRANS2",
"S_PLAY_SUPER_TRANS3",
"S_PLAY_SUPER_TRANS4",
"S_PLAY_SUPER_TRANS5",
"S_PLAY_SUPER_TRANS6", // This has special significance in the code. If you add more frames, search for it and make the appropriate changes.
// technically the player goes here but it's an infinite tic state
"S_OBJPLACE_DUMMY",
@ -3484,15 +3487,12 @@ static const char *const STATE_LIST[] = { // array length left dynamic for sanit
"S_PLAY_SIGN",
// NiGHTS character (uses player sprite)
"S_PLAY_NIGHTS_TRANS",
"S_PLAY_NIGHTS_TRANS1",
"S_PLAY_NIGHTS_TRANS2",
"S_PLAY_NIGHTS_TRANS3",
"S_PLAY_NIGHTS_TRANS4",
"S_PLAY_NIGHTS_TRANS5",
"S_PLAY_NIGHTS_TRANS6",
"S_PLAY_NIGHTS_TRANS7",
"S_PLAY_NIGHTS_TRANS8",
"S_PLAY_NIGHTS_TRANS9",
"S_PLAY_NIGHTS_STAND",
"S_PLAY_NIGHTS_FLOAT",
@ -3527,6 +3527,20 @@ static const char *const STATE_LIST[] = { // array length left dynamic for sanit
"S_PLAY_NIGHTS_FLYC",
"S_PLAY_NIGHTS_DRILLC",
// c:
"S_TAILSOVERLAY_STAND",
"S_TAILSOVERLAY_0DEGREES",
"S_TAILSOVERLAY_PLUS30DEGREES",
"S_TAILSOVERLAY_PLUS60DEGREES",
"S_TAILSOVERLAY_MINUS30DEGREES",
"S_TAILSOVERLAY_MINUS60DEGREES",
"S_TAILSOVERLAY_RUN",
"S_TAILSOVERLAY_FLY",
"S_TAILSOVERLAY_TIRE",
"S_TAILSOVERLAY_PAIN",
"S_TAILSOVERLAY_GASP",
"S_TAILSOVERLAY_EDGE",
// Blue Crawla
"S_POSS_STND",
"S_POSS_RUN1",
@ -5881,6 +5895,7 @@ static const char *const MOBJTYPE_LIST[] = { // array length left dynamic for s
"MT_THOK", // Thok! mobj
"MT_PLAYER",
"MT_TAILSOVERLAY", // c:
// Enemies
"MT_BLUECRAWLA",

View File

@ -2144,6 +2144,7 @@ void G_PlayerReborn(INT32 player)
UINT32 thokitem;
UINT32 spinitem;
UINT32 revitem;
UINT32 followitem;
fixed_t actionspd;
fixed_t mindash;
fixed_t maxdash;
@ -2215,6 +2216,7 @@ void G_PlayerReborn(INT32 player)
thokitem = players[player].thokitem;
spinitem = players[player].spinitem;
revitem = players[player].revitem;
followitem = players[player].followitem;
actionspd = players[player].actionspd;
mindash = players[player].mindash;
maxdash = players[player].maxdash;
@ -2252,6 +2254,7 @@ void G_PlayerReborn(INT32 player)
p->thokitem = thokitem;
p->spinitem = spinitem;
p->revitem = revitem;
p->followitem = followitem;
p->actionspd = actionspd;
p->mindash = mindash;
p->maxdash = maxdash;

View File

@ -1180,7 +1180,7 @@ void HU_Erase(void)
// IN-LEVEL MULTIPLAYER RANKINGS
//======================================================================
#define supercheckdef ((players[tab[i].num].powers[pw_super] && players[tab[i].num].mo && (players[tab[i].num].mo->state < &states[S_PLAY_SUPER_TRANS] || players[tab[i].num].mo->state > &states[S_PLAY_SUPER_TRANS9])) || (players[tab[i].num].powers[pw_carry] == CR_NIGHTSMODE && skins[players[tab[i].num].skin].flags & SF_SUPER))
#define supercheckdef ((players[tab[i].num].powers[pw_super] && players[tab[i].num].mo && (players[tab[i].num].mo->state < &states[S_PLAY_SUPER_TRANS1] || players[tab[i].num].mo->state >= &states[S_PLAY_SUPER_TRANS6])) || (players[tab[i].num].powers[pw_carry] == CR_NIGHTSMODE && skins[players[tab[i].num].skin].flags & SF_SUPER))
#define greycheckdef ((players[tab[i].num].mo && players[tab[i].num].mo->health <= 0) || players[tab[i].num].spectator)
//

View File

@ -479,6 +479,19 @@ char spr2names[NUMPLAYERSPRITES][5] =
"DRLB",
"DRLC",
"TAL0",
"TAL1",
"TAL2",
"TAL3",
"TAL4",
"TAL5",
"TAL6",
"TAL7",
"TAL8",
"TAL9",
"TALA",
"TALB",
"SIGN",
"LIFE"
};
@ -562,8 +575,21 @@ playersprite_t spr2defaults[NUMPLAYERSPRITES] = {
SPR2_NGTB, // SPR2_DRLB,
SPR2_NGTC, // SPR2_DRLC,
0, // SPR2_TAL0,
SPR2_TAL0, // SPR2_TAL1,
SPR2_TAL1, // SPR2_TAL2,
SPR2_TAL2, // SPR2_TAL3,
SPR2_TAL1, // SPR2_TAL4,
SPR2_TAL4, // SPR2_TAL5,
SPR2_TAL0, // SPR2_TAL6,
SPR2_TAL3, // SPR2_TAL7,
SPR2_TAL7, // SPR2_TAL8,
SPR2_TAL0, // SPR2_TAL9,
SPR2_TAL9, // SPR2_TALA,
SPR2_TAL0, // SPR2_TALB,
0, // SPR2_SIGN,
0, // SPR2_LIFE
0, // SPR2_LIFE,
};
// Doesn't work with g++, needs actionf_p1 (don't modify this comment)
@ -644,15 +670,12 @@ state_t states[NUMSTATES] =
{SPR_PLAY, SPR2_MLEL, 35, {NULL}, 0, 0, S_PLAY_WALK}, // S_PLAY_MELEE_LANDING
// SF_SUPER
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER, 4, {NULL}, 0, 0, S_PLAY_SUPER_TRANS2}, // S_PLAY_SUPER_TRANS
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER, 4, {NULL}, 0, 0, S_PLAY_SUPER_TRANS3}, // S_PLAY_SUPER_TRANS2
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 4, {NULL}, 0, 0, S_PLAY_SUPER_TRANS4}, // S_PLAY_SUPER_TRANS3
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 3, {NULL}, 0, 0, S_PLAY_SUPER_TRANS5}, // S_PLAY_SUPER_TRANS4
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 3, {NULL}, 0, 0, S_PLAY_SUPER_TRANS6}, // S_PLAY_SUPER_TRANS5
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 3, {NULL}, 0, 0, S_PLAY_SUPER_TRANS7}, // S_PLAY_SUPER_TRANS6
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 3, {NULL}, 0, 0, S_PLAY_SUPER_TRANS8}, // S_PLAY_SUPER_TRANS7
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 3, {NULL}, 0, 0, S_PLAY_SUPER_TRANS9}, // S_PLAY_SUPER_TRANS8
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 16, {NULL}, 0, 0, S_PLAY_WALK}, // S_PLAY_SUPER_TRANS9
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER, 3, {NULL}, 0, 0, S_PLAY_SUPER_TRANS2}, // S_PLAY_SUPER_TRANS1
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER, 3, {NULL}, 0, 0, S_PLAY_SUPER_TRANS3}, // S_PLAY_SUPER_TRANS2
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 2, {NULL}, 0, 0, S_PLAY_SUPER_TRANS4}, // S_PLAY_SUPER_TRANS3
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 2, {NULL}, 0, 0, S_PLAY_SUPER_TRANS5}, // S_PLAY_SUPER_TRANS4
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 2, {NULL}, 0, 0, S_PLAY_SUPER_TRANS6}, // S_PLAY_SUPER_TRANS5
{SPR_PLAY, SPR2_TRNS|FF_SPR2SUPER|FF_FULLBRIGHT, 20, {A_FadeOverlay}, 0, 0, S_PLAY_FALL}, // S_PLAY_SUPER_TRANS6
{SPR_NULL, 0, -1, {NULL}, 0, 0, S_OBJPLACE_DUMMY}, //S_OBJPLACE_DUMMY
@ -667,15 +690,12 @@ state_t states[NUMSTATES] =
{SPR_PLAY, SPR2_SIGN, 1, {NULL}, 0, 24, S_PLAY_SIGN}, // S_PLAY_SIGN
// NiGHTS Player, transforming
{SPR_PLAY, SPR2_TRNS, 4, {A_Scream}, 0, 0, S_PLAY_NIGHTS_TRANS2}, // S_PLAY_NIGHTS_TRANS
{SPR_PLAY, SPR2_TRNS, 4, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS3}, // S_PLAY_NIGHTS_TRANS2
{SPR_PLAY, SPR2_TRNS|FF_FULLBRIGHT, 4, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS4}, // S_PLAY_NIGHTS_TRANS3
{SPR_PLAY, SPR2_TRNS, 3, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS5}, // S_PLAY_NIGHTS_TRANS4
{SPR_PLAY, SPR2_TRNS, 3, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS6}, // S_PLAY_NIGHTS_TRANS5
{SPR_PLAY, SPR2_TRNS, 3, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS7}, // S_PLAY_NIGHTS_TRANS6
{SPR_PLAY, SPR2_TRNS, 3, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS8}, // S_PLAY_NIGHTS_TRANS7
{SPR_PLAY, SPR2_TRNS, 3, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS9}, // S_PLAY_NIGHTS_TRANS8
{SPR_PLAY, SPR2_TRNS, 16, {NULL}, 0, 0, S_PLAY_NIGHTS_FLOAT}, // S_PLAY_NIGHTS_TRANS9
{SPR_PLAY, SPR2_TRNS, 3, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS2}, // S_PLAY_NIGHTS_TRANS1
{SPR_PLAY, SPR2_TRNS, 3, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS3}, // S_PLAY_NIGHTS_TRANS2
{SPR_PLAY, SPR2_TRNS|FF_FULLBRIGHT, 2, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS4}, // S_PLAY_NIGHTS_TRANS3
{SPR_PLAY, SPR2_TRNS|FF_FULLBRIGHT, 2, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS5}, // S_PLAY_NIGHTS_TRANS4
{SPR_PLAY, SPR2_TRNS|FF_FULLBRIGHT, 2, {NULL}, 0, 0, S_PLAY_NIGHTS_TRANS6}, // S_PLAY_NIGHTS_TRANS5
{SPR_PLAY, SPR2_TRNS|FF_FULLBRIGHT, 25, {A_FadeOverlay}, 4, 0, S_PLAY_NIGHTS_FLOAT}, // S_PLAY_NIGHTS_TRANS5
// NiGHTS Player, stand, float, pain, pull and attack
{SPR_PLAY, SPR2_NSTD, 7, {NULL}, 0, 0, S_PLAY_NIGHTS_STAND}, // S_PLAY_NIGHTS_STAND
@ -712,6 +732,20 @@ state_t states[NUMSTATES] =
{SPR_PLAY, SPR2_NGTC, 2, {NULL}, 0, 0, S_PLAY_NIGHTS_FLYC}, // S_PLAY_NIGHTS_FLYC
{SPR_PLAY, SPR2_DRLC, 2, {NULL}, 0, 0, S_PLAY_NIGHTS_DRILLC}, // S_PLAY_NIGHTS_DRILLC
// c:
{SPR_PLAY, SPR2_TAL0|FF_SPR2MIDSTART, 5, {NULL}, 0, 0, S_TAILSOVERLAY_STAND}, // S_TAILSOVERLAY_STAND
{SPR_PLAY, SPR2_TAL1|FF_SPR2MIDSTART, 35, {NULL}, 0, 0, S_TAILSOVERLAY_0DEGREES}, // S_TAILSOVERLAY_0DEGREES
{SPR_PLAY, SPR2_TAL2|FF_SPR2MIDSTART, 35, {NULL}, 0, 0, S_TAILSOVERLAY_PLUS30DEGREES}, // S_TAILSOVERLAY_PLUS30DEGREES
{SPR_PLAY, SPR2_TAL3|FF_SPR2MIDSTART, 35, {NULL}, 0, 0, S_TAILSOVERLAY_PLUS60DEGREES}, // S_TAILSOVERLAY_PLUS60DEGREES
{SPR_PLAY, SPR2_TAL4|FF_SPR2MIDSTART, 35, {NULL}, 0, 0, S_TAILSOVERLAY_MINUS30DEGREES}, // S_TAILSOVERLAY_MINUS30DEGREES
{SPR_PLAY, SPR2_TAL5|FF_SPR2MIDSTART, 35, {NULL}, 0, 0, S_TAILSOVERLAY_MINUS60DEGREES}, // S_TAILSOVERLAY_MINUS60DEGREES
{SPR_PLAY, SPR2_TAL6|FF_SPR2MIDSTART, 35, {NULL}, 0, 0, S_TAILSOVERLAY_RUN}, // S_TAILSOVERLAY_RUN
{SPR_PLAY, SPR2_TAL7|FF_SPR2MIDSTART, 4, {NULL}, 0, 0, S_TAILSOVERLAY_FLY}, // S_TAILSOVERLAY_FLY
{SPR_PLAY, SPR2_TAL8|FF_SPR2MIDSTART, 4, {NULL}, 0, 0, S_TAILSOVERLAY_TIRE}, // S_TAILSOVERLAY_TIRE
{SPR_PLAY, SPR2_TAL9|FF_SPR2MIDSTART, 35, {NULL}, 0, 0, S_TAILSOVERLAY_PAIN}, // S_TAILSOVERLAY_PAIN
{SPR_PLAY, SPR2_TALA|FF_SPR2MIDSTART, 35, {NULL}, 0, 0, S_TAILSOVERLAY_GASP}, // S_TAILSOVERLAY_GASP
{SPR_PLAY, SPR2_TALB , 35, {NULL}, 0, 0, S_TAILSOVERLAY_EDGE}, // S_TAILSOVERLAY_EDGE
// Blue Crawla
{SPR_POSS, 0, 5, {A_Look}, 0, 0, S_POSS_STND}, // S_POSS_STND
{SPR_POSS, 0, 3, {A_Chase}, 0, 0, S_POSS_RUN2}, // S_POSS_RUN1
@ -3235,6 +3269,33 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
(statenum_t)MT_NULL // raisestate
},
{ // MT_TAILSOVERLAY
-1, // doomednum
S_INVISIBLE, // spawnstate
1000, // spawnhealth
S_NULL, // seestate
sfx_None, // seesound
8, // reactiontime
sfx_None, // attacksound
S_NULL, // painstate
0, // painchance
sfx_None, // painsound
S_NULL, // meleestate
S_NULL, // missilestate
S_NULL, // deathstate
S_NULL, // xdeathstate
sfx_None, // deathsound
8, // speed
16*FRACUNIT, // radius
48*FRACUNIT, // height
2, // display offset
16, // mass
0, // damage
sfx_None, // activesound
MF_NOBLOCKMAP|MF_NOCLIP|MF_NOCLIPHEIGHT|MF_NOGRAVITY|MF_SCENERY, // flags
S_NULL // raisestate
},
{ // MT_BLUECRAWLA
100, // doomednum
S_POSS_STND, // spawnstate
@ -11703,7 +11764,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
SH_ELEMENTAL, // speed
64*FRACUNIT, // radius
64*FRACUNIT, // height
2, // display offset
4, // display offset
16, // mass
0, // damage
sfx_None, // activesound
@ -11730,7 +11791,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
SH_ATTRACT, // speed
64*FRACUNIT, // radius
64*FRACUNIT, // height
2, // display offset
4, // display offset
16, // mass
0, // damage
sfx_None, // activesound
@ -11757,7 +11818,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
SH_FORCE, // speed
64*FRACUNIT, // radius
64*FRACUNIT, // height
2, // display offset
4, // display offset
16, // mass
0, // damage
sfx_None, // activesound
@ -11784,7 +11845,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
SH_ARMAGEDDON, // speed
64*FRACUNIT, // radius
64*FRACUNIT, // height
2, // display offset
4, // display offset
16, // mass
0, // damage
sfx_None, // activesound
@ -11811,7 +11872,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
SH_WHIRLWIND, // speed
64*FRACUNIT, // radius
64*FRACUNIT, // height
2, // display offset
4, // display offset
16, // mass
0, // damage
sfx_None, // activesound
@ -11838,7 +11899,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
SH_PITY, // speed
64*FRACUNIT, // radius
64*FRACUNIT, // height
2, // display offset
4, // display offset
16, // mass
0, // damage
sfx_None, // activesound
@ -11865,7 +11926,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
SH_FLAMEAURA, // speed
64*FRACUNIT, // radius
64*FRACUNIT, // height
-2, // display offset
-4, // display offset
16, // mass
0, // damage
sfx_None, // activesound
@ -11892,7 +11953,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
SH_BUBBLEWRAP, // speed
64*FRACUNIT, // radius
64*FRACUNIT, // height
2, // display offset
4, // display offset
16, // mass
0, // damage
sfx_None, // activesound
@ -11919,7 +11980,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
SH_THUNDERCOIN, // speed
64*FRACUNIT, // radius
64*FRACUNIT, // height
-2, // display offset
-4, // display offset
16, // mass
0, // damage
sfx_None, // activesound
@ -14957,7 +15018,7 @@ mobjinfo_t mobjinfo[NUMMOBJTYPES] =
0, // speed
16*FRACUNIT, // radius
48*FRACUNIT, // height
0, // display offset
1, // display offset
1000, // mass
8, // damage
sfx_None, // activesound

View File

@ -216,6 +216,7 @@ void A_FlickyCheck();
void A_FlickyHeightCheck();
void A_FlickyFlutter();
void A_FlameParticle();
void A_FadeOverlay();
// ratio of states to sprites to mobj types is roughly 6 : 1 : 1
#define NUMMOBJFREESLOTS 256
@ -685,6 +686,20 @@ typedef enum playersprite
SPR2_DRLB,
SPR2_DRLC,
// c:
SPR2_TAL0,
SPR2_TAL1,
SPR2_TAL2,
SPR2_TAL3,
SPR2_TAL4,
SPR2_TAL5,
SPR2_TAL6,
SPR2_TAL7,
SPR2_TAL8,
SPR2_TAL9,
SPR2_TALA,
SPR2_TALB,
SPR2_SIGN, // end sign head
SPR2_LIFE, // life monitor icon
@ -763,15 +778,12 @@ typedef enum state
S_PLAY_MELEE_LANDING,
// SF_SUPER
S_PLAY_SUPER_TRANS,
S_PLAY_SUPER_TRANS1,
S_PLAY_SUPER_TRANS2,
S_PLAY_SUPER_TRANS3,
S_PLAY_SUPER_TRANS4,
S_PLAY_SUPER_TRANS5,
S_PLAY_SUPER_TRANS6,
S_PLAY_SUPER_TRANS7,
S_PLAY_SUPER_TRANS8,
S_PLAY_SUPER_TRANS9,
// technically the player goes here but it's an infinite tic state
S_OBJPLACE_DUMMY,
@ -787,15 +799,12 @@ typedef enum state
S_PLAY_SIGN,
// NiGHTS character (uses player sprite)
S_PLAY_NIGHTS_TRANS,
S_PLAY_NIGHTS_TRANS1,
S_PLAY_NIGHTS_TRANS2,
S_PLAY_NIGHTS_TRANS3,
S_PLAY_NIGHTS_TRANS4,
S_PLAY_NIGHTS_TRANS5,
S_PLAY_NIGHTS_TRANS6,
S_PLAY_NIGHTS_TRANS7,
S_PLAY_NIGHTS_TRANS8,
S_PLAY_NIGHTS_TRANS9,
S_PLAY_NIGHTS_STAND,
S_PLAY_NIGHTS_FLOAT,
@ -830,6 +839,20 @@ typedef enum state
S_PLAY_NIGHTS_FLYC,
S_PLAY_NIGHTS_DRILLC,
// c:
S_TAILSOVERLAY_STAND,
S_TAILSOVERLAY_0DEGREES,
S_TAILSOVERLAY_PLUS30DEGREES,
S_TAILSOVERLAY_PLUS60DEGREES,
S_TAILSOVERLAY_MINUS30DEGREES,
S_TAILSOVERLAY_MINUS60DEGREES,
S_TAILSOVERLAY_RUN,
S_TAILSOVERLAY_FLY,
S_TAILSOVERLAY_TIRE,
S_TAILSOVERLAY_PAIN,
S_TAILSOVERLAY_GASP,
S_TAILSOVERLAY_EDGE,
// Blue Crawla
S_POSS_STND,
S_POSS_RUN1,
@ -3206,6 +3229,7 @@ typedef enum mobj_type
MT_THOK, // Thok! mobj
MT_PLAYER,
MT_TAILSOVERLAY, // c:
// Enemies
MT_BLUECRAWLA,

View File

@ -47,6 +47,7 @@ enum hook {
hook_ShieldSpecial,
hook_MobjMoveBlocked,
hook_MapThingSpawn,
hook_FollowMobj,
hook_MAX // last hook
};
@ -85,5 +86,6 @@ boolean LUAh_HurtMsg(player_t *player, mobj_t *inflictor, mobj_t *source, UINT8
#define LUAh_ShieldSpecial(player) LUAh_PlayerHook(player, hook_ShieldSpecial) // Hook for shield abilities
#define LUAh_MobjMoveBlocked(mo) LUAh_MobjHook(mo, hook_MobjMoveBlocked) // Hook for P_XYMovement (when movement is blocked)
boolean LUAh_MapThingSpawn(mobj_t *mo, mapthing_t *mthing); // Hook for P_SpawnMapThing by mobj type
boolean LUAh_FollowMobj(player_t *player, mobj_t *mo); // Hook for P_PlayerAfterThink Smiles mobj-following
#endif

View File

@ -58,6 +58,7 @@ const char *const hookNames[hook_MAX+1] = {
"ShieldSpecial",
"MobjMoveBlocked",
"MapThingSpawn",
"FollowMobj",
NULL
};
@ -197,6 +198,7 @@ static int lib_addHook(lua_State *L)
case hook_SpinSpecial:
case hook_JumpSpinSpecial:
case hook_PlayerSpawn:
case hook_FollowMobj:
lastp = &playerhooks;
break;
case hook_LinedefExecute:
@ -1138,4 +1140,42 @@ boolean LUAh_MapThingSpawn(mobj_t *mo, mapthing_t *mthing)
return hooked;
}
// Hook for P_PlayerAfterThink Smiles mobj-following
boolean LUAh_FollowMobj(player_t *player, mobj_t *mobj)
{
hook_p hookp;
boolean hooked = false;
if (!gL || !(hooksAvailable[hook_FollowMobj/8] & (1<<(hook_FollowMobj%8))))
return 0;
lua_settop(gL, 0);
for (hookp = playerhooks; hookp; hookp = hookp->next)
if (hookp->type == hook_FollowMobj)
{
if (lua_gettop(gL) == 0)
{
LUA_PushUserdata(gL, player, META_PLAYER);
LUA_PushUserdata(gL, mobj, META_MOBJ);
}
lua_pushfstring(gL, FMT_HOOKID, hookp->id);
lua_gettable(gL, LUA_REGISTRYINDEX);
lua_pushvalue(gL, -3);
lua_pushvalue(gL, -3);
if (lua_pcall(gL, 2, 1, 0)) {
if (!hookp->error || cv_debug & DBG_LUA)
CONS_Alert(CONS_WARNING,"%s\n",lua_tostring(gL, -1));
lua_pop(gL, 1);
hookp->error = true;
continue;
}
if (lua_toboolean(gL, -1))
hooked = true;
lua_pop(gL, 1);
}
lua_settop(gL, 0);
return hooked;
}
#endif

View File

@ -174,6 +174,10 @@ static int player_get(lua_State *L)
lua_pushinteger(L, plr->spinitem);
else if (fastcmp(field,"revitem"))
lua_pushinteger(L, plr->revitem);
else if (fastcmp(field,"followitem"))
lua_pushinteger(L, plr->followitem);
else if (fastcmp(field,"followmobj"))
LUA_PushUserdata(L, plr->followmobj, META_MOBJ);
else if (fastcmp(field,"actionspd"))
lua_pushfixed(L, plr->actionspd);
else if (fastcmp(field,"mindash"))
@ -441,6 +445,10 @@ static int player_set(lua_State *L)
plr->spinitem = luaL_checkinteger(L, 3);
else if (fastcmp(field,"revitem"))
plr->revitem = luaL_checkinteger(L, 3);
else if (fastcmp(field,"followitem"))
plr->followitem = luaL_checkinteger(L, 3);
else if (fastcmp(field,"followmobj"))
plr->followmobj = *((mobj_t **)luaL_checkudata(L, 3, META_MOBJ));
else if (fastcmp(field,"actionspd"))
plr->actionspd = (INT32)luaL_checkinteger(L, 3);
else if (fastcmp(field,"mindash"))

View File

@ -35,6 +35,7 @@ enum skin {
skin_thokitem,
skin_spinitem,
skin_revitem,
skin_followitem,
skin_actionspd,
skin_mindash,
skin_maxdash,
@ -73,6 +74,7 @@ static const char *const skin_opt[] = {
"thokitem",
"spinitem",
"revitem",
"followitem",
"actionspd",
"mindash",
"maxdash",
@ -162,6 +164,9 @@ static int skin_get(lua_State *L)
case skin_revitem:
lua_pushinteger(L, skin->revitem);
break;
case skin_followitem:
lua_pushinteger(L, skin->followitem);
break;
case skin_actionspd:
lua_pushfixed(L, skin->actionspd);
break;

View File

@ -149,7 +149,7 @@ description_t description[32] =
{false, "???", "", "", 0, 0},
{false, "???", "", "", 0, 0}
};
static INT16 char_on = 0;
INT16 char_on = -1, startchar = 1;
static char *char_notes = NULL;
static fixed_t char_scroll = 0;
@ -6738,7 +6738,15 @@ static void M_SetupChoosePlayer(INT32 choice)
SP_PlayerDef.prevMenu = currentMenu;
M_SetupNextMenu(&SP_PlayerDef);
if (!allowed)
{
char_on = firstvalid;
if (startchar > 0 && startchar < 32)
{
INT16 workchar = startchar;
while (workchar--)
char_on = description[char_on].next;
}
}
char_scroll = 0; // finish scrolling the menu
Z_Free(char_notes);
char_notes = V_WordWrap(0, 21*8, V_ALLOWLOWERCASE, description[char_on].notes);

View File

@ -232,6 +232,7 @@ extern CV_PossibleValue_t gametype_cons_t[];
extern INT16 startmap;
extern INT32 ultimate_selectable;
extern INT16 char_on, startchar;
#define MAXSAVEGAMES 31 //note: last save game is "no save"
#define NOSAVESLOT 0 //slot where Play Without Saving appears

View File

@ -244,6 +244,7 @@ void A_FlickyCheck(mobj_t *actor);
void A_FlickyHeightCheck(mobj_t *actor);
void A_FlickyFlutter(mobj_t *actor);
void A_FlameParticle(mobj_t *actor);
void A_FadeOverlay(mobj_t *actor);
//
// ENEMY THINKING
@ -10492,3 +10493,39 @@ void A_FlameParticle(mobj_t *actor)
type);
P_SetObjectMomZ(particle, locvar1<<FRACBITS, false);
}
// Function: A_FadeOverlay
//
// Description: Makes a pretty overlay (primarily for super/NiGHTS transformation).
//
// var1 = bit 1 = don't halt momentum, bit 2 = don't make fast, bit 3 = don't set tracer
// var2 = unused
//
void A_FadeOverlay(mobj_t *actor)
{
mobj_t *fade;
INT32 locvar1 = var1;
//INT32 locvar2 = var2;
#ifdef HAVE_BLUA
if (LUA_CallAction("A_FadeOverlay", actor))
return;
#endif
if (!(locvar1 & 1))
actor->momx = actor->momy = actor->momz = 0;
fade = P_SpawnGhostMobj(actor);
fade->frame = actor->frame;
if (!(locvar1 & 2))
{
fade->fuse = 15;
fade->flags2 |= MF2_BOSSNOTRAP;
}
else
fade->fuse = 20;
if (!(locvar1 & 4))
P_SetTarget(&actor->tracer, fade);
}

View File

@ -1751,6 +1751,7 @@ static mobj_t *SearchMarioNode(msecnode_t *node)
{
case MT_NULL:
case MT_UNKNOWN:
case MT_TAILSOVERLAY:
case MT_THOK:
case MT_GHOST:
case MT_OVERLAY:

View File

@ -322,7 +322,9 @@ boolean P_SetPlayerMobjState(mobj_t *mobj, statenum_t state)
mobj->tics = st->tics;
// Adjust the player's animation speed to match their velocity.
if (player->panim == PA_EDGE && (player->charflags & SF_FASTEDGE))
if (state == S_PLAY_STND && player->powers[pw_super] && skins[player->skin].sprites[SPR2_WAIT|FF_SPR2SUPER].numframes == 0) // if no super wait, don't wait at all
mobj->tics = -1;
else if (player->panim == PA_EDGE && (player->charflags & SF_FASTEDGE))
mobj->tics = 2;
else if (!(disableSpeedAdjust || player->charflags & SF_NOSPEEDADJUST))
{
@ -6646,10 +6648,21 @@ void P_MobjThinker(mobj_t *mobj)
}
}
if ((mobj->type == MT_GHOST || mobj->type == MT_THOK) && mobj->fuse > 0 // Not guaranteed to be MF_SCENERY or not MF_SCENERY!
&& (signed)(mobj->frame >> FF_TRANSSHIFT) < (NUMTRANSMAPS-1) - mobj->fuse / 2)
// fade out when nearing the end of fuse...
mobj->frame = (mobj->frame & ~FF_TRANSMASK) | (((NUMTRANSMAPS-1) - mobj->fuse / 2) << FF_TRANSSHIFT);
if ((mobj->type == MT_GHOST || mobj->type == MT_THOK) && mobj->fuse > 0) // Not guaranteed to be MF_SCENERY or not MF_SCENERY!
{
if (mobj->flags2 & MF2_BOSSNOTRAP) // "fast" flag
{
if ((signed)((mobj->frame & FF_TRANSMASK) >> FF_TRANSSHIFT) < (NUMTRANSMAPS-1) - (2*mobj->fuse)/3)
// fade out when nearing the end of fuse...
mobj->frame = (mobj->frame & ~FF_TRANSMASK) | (((NUMTRANSMAPS-1) - (2*mobj->fuse)/3) << FF_TRANSSHIFT);
}
else
{
if ((signed)((mobj->frame & FF_TRANSMASK) >> FF_TRANSSHIFT) < (NUMTRANSMAPS-1) - mobj->fuse / 2)
// fade out when nearing the end of fuse...
mobj->frame = (mobj->frame & ~FF_TRANSMASK) | (((NUMTRANSMAPS-1) - mobj->fuse / 2) << FF_TRANSSHIFT);
}
}
if (mobj->flags2 & MF2_MACEROTATE)
{

View File

@ -56,6 +56,7 @@ typedef enum
AWAYVIEW = 0x08,
FIRSTAXIS = 0x10,
SECONDAXIS = 0x20,
FOLLOW = 0x40,
} player_saveflags;
//
@ -220,6 +221,9 @@ static void P_NetArchivePlayers(void)
if (players[i].axis2)
flags |= SECONDAXIS;
if (players[i].followmobj)
flags |= FOLLOW;
WRITEINT16(save_p, players[i].lastsidehit);
WRITEINT16(save_p, players[i].lastlinehit);
@ -245,6 +249,9 @@ static void P_NetArchivePlayers(void)
if (flags & AWAYVIEW)
WRITEUINT32(save_p, players[i].awayviewmobj->mobjnum);
if (flags & FOLLOW)
WRITEUINT32(save_p, players[i].followmobj->mobjnum);
WRITEFIXED(save_p, players[i].camerascale);
WRITEFIXED(save_p, players[i].shieldscale);
@ -254,6 +261,7 @@ static void P_NetArchivePlayers(void)
WRITEUINT32(save_p, (UINT32)players[i].thokitem);
WRITEUINT32(save_p, (UINT32)players[i].spinitem);
WRITEUINT32(save_p, (UINT32)players[i].revitem);
WRITEUINT32(save_p, (UINT32)players[i].followitem);
WRITEFIXED(save_p, players[i].actionspd);
WRITEFIXED(save_p, players[i].mindash);
WRITEFIXED(save_p, players[i].maxdash);
@ -413,6 +421,9 @@ static void P_NetUnArchivePlayers(void)
if (flags & AWAYVIEW)
players[i].awayviewmobj = (mobj_t *)(size_t)READUINT32(save_p);
if (flags & FOLLOW)
players[i].followmobj = (mobj_t *)(size_t)READUINT32(save_p);
players[i].viewheight = cv_viewheight.value<<FRACBITS;
players[i].camerascale = READFIXED(save_p);
@ -425,6 +436,7 @@ static void P_NetUnArchivePlayers(void)
players[i].thokitem = (mobjtype_t)READUINT32(save_p);
players[i].spinitem = (mobjtype_t)READUINT32(save_p);
players[i].revitem = (mobjtype_t)READUINT32(save_p);
players[i].followitem = (mobjtype_t)READUINT32(save_p);
players[i].actionspd = READFIXED(save_p);
players[i].mindash = READFIXED(save_p);
players[i].maxdash = READFIXED(save_p);
@ -3060,6 +3072,13 @@ static void P_RelinkPointers(void)
if (!P_SetTarget(&mobj->player->awayviewmobj, P_FindNewPosition(temp)))
CONS_Debug(DBG_GAMELOGIC, "awayviewmobj not found on %d\n", mobj->type);
}
if (mobj->player && mobj->player->followmobj)
{
temp = (UINT32)(size_t)mobj->player->followmobj;
mobj->player->followmobj = NULL;
if (!P_SetTarget(&mobj->player->followmobj, P_FindNewPosition(temp)))
CONS_Debug(DBG_GAMELOGIC, "followmobj not found on %d\n", mobj->type);
}
}
}
}

View File

@ -591,6 +591,7 @@ static void P_DeNightserizePlayer(player_t *player)
player->mo->flags &= ~MF_NOGRAVITY;
player->mo->skin = &skins[player->skin];
player->followitem = skins[player->skin].followitem;
player->mo->color = player->skincolor;
// Restore aiming angle
@ -665,14 +666,16 @@ void P_NightserizePlayer(player_t *player, INT32 nighttime)
if (skins[player->skin].sprites[SPR2_NGT0].numframes == 0) // If you don't have a sprite for flying horizontally, use the default NiGHTS skin.
{
player->mo->skin = &skins[DEFAULTNIGHTSSKIN];
player->mo->color = skins[DEFAULTNIGHTSSKIN].prefcolor;
if (!(cv_debug || devparm) && !(netgame || multiplayer || demoplayback))
player->mo->color = skins[DEFAULTNIGHTSSKIN].prefcolor;
player->followitem = skins[DEFAULTNIGHTSSKIN].followitem;
}
player->nightstime = player->startedtime = nighttime*TICRATE;
player->bonustime = false;
P_RestoreMusic(player);
P_SetPlayerMobjState(player->mo, S_PLAY_NIGHTS_TRANS);
P_SetPlayerMobjState(player->mo, S_PLAY_NIGHTS_TRANS1);
if (gametype == GT_RACE || gametype == GT_COMPETITION)
{
@ -999,10 +1002,10 @@ void P_DoSuperTransformation(player_t *player, boolean giverings)
S_StartSound(NULL, sfx_supert); //let all players hear it -mattw_cfi
// Transformation animation
P_SetPlayerMobjState(player->mo, S_PLAY_SUPER_TRANS);
P_SetPlayerMobjState(player->mo, S_PLAY_SUPER_TRANS1);
player->mo->momx = player->mo->momy = player->mo->momz = 0;
player->pflags &= ~(PF_JUMPED|PF_NOJUMPDAMAGE);
player->pflags |= PF_NOJUMPDAMAGE; // just to avoid recurling but still allow thok
if (giverings)
player->rings = 50;
@ -1551,9 +1554,7 @@ void P_SwitchShield(player_t *player, UINT16 shieldtype)
//
mobj_t *P_SpawnGhostMobj(mobj_t *mobj)
{
mobj_t *ghost;
ghost = P_SpawnMobj(mobj->x, mobj->y, mobj->z, MT_GHOST);
mobj_t *ghost = P_SpawnMobj(mobj->x, mobj->y, mobj->z, MT_GHOST);
P_SetScale(ghost, mobj->scale);
ghost->destscale = mobj->scale;
@ -1579,6 +1580,14 @@ mobj_t *P_SpawnGhostMobj(mobj_t *mobj)
if (mobj->flags2 & MF2_OBJECTFLIP)
ghost->flags |= MF2_OBJECTFLIP;
if (mobj->player && mobj->player->followmobj)
{
mobj_t *ghost2 = P_SpawnGhostMobj(mobj->player->followmobj);
P_SetTarget(&ghost2->tracer, ghost);
P_SetTarget(&ghost->tracer, ghost2);
ghost2->flags2 |= MF2_LINKDRAW;
}
return ghost;
}
@ -3648,9 +3657,8 @@ static void P_DoSuperStuff(player_t *player)
{
mobj_t *spark;
ticcmd_t *cmd = &player->cmd;
if (player->mo->state >= &states[S_PLAY_SUPER_TRANS]
&& (player->mo->state < &states[S_PLAY_SUPER_TRANS9]
|| (player->mo->state == &states[S_PLAY_SUPER_TRANS9] && player->mo->tics > 1))) // needed to prevent one-frame old colour...
if (player->mo->state >= &states[S_PLAY_SUPER_TRANS1]
&& player->mo->state < &states[S_PLAY_SUPER_TRANS6])
return; // don't do anything right now, we're in the middle of transforming!
if (player->powers[pw_carry] == CR_NIGHTSMODE)
@ -3687,14 +3695,19 @@ static void P_DoSuperStuff(player_t *player)
return;
}
player->mo->color = (player->pflags & PF_GODMODE && cv_debug == 0)
? (SKINCOLOR_SUPERSILVER1 + 5*(((signed)leveltime >> 1) % 7)) // A wholesome easter egg.
: skins[player->skin].supercolor + abs( ( (player->powers[pw_super] >> 1) % 9) - 4); // This is where super flashing is handled.
G_GhostAddColor(GHC_SUPER);
if (player->mo->state == &states[S_PLAY_SUPER_TRANS6]) // stop here for now
return;
// Deplete one ring every second while super
if ((leveltime % TICRATE == 0) && !(player->exiting))
player->rings--;
player->mo->color = (player->pflags & PF_GODMODE && cv_debug == 0)
? (SKINCOLOR_SUPERSILVER1 + 5*((leveltime >> 1) % 7)) // A wholesome easter egg.
: skins[player->skin].supercolor + (unsigned)abs( ( (signed)(leveltime >> 1) % 9) - 4); // This is where super flashing is handled.
if ((cmd->forwardmove != 0 || cmd->sidemove != 0 || player->powers[pw_carry])
&& !(leveltime % TICRATE) && (player->mo->momx || player->mo->momy))
{
@ -3703,8 +3716,6 @@ static void P_DoSuperStuff(player_t *player)
P_SetScale(spark, player->mo->scale);
}
G_GhostAddColor(GHC_SUPER);
// Ran out of rings while super!
if (player->rings <= 0 || player->exiting)
{
@ -6081,14 +6092,14 @@ static void P_NiGHTSMovement(player_t *player)
&& (players[i].capsule && players[i].capsule->reactiontime))
capsule = true;
if (!capsule
&& !(player->mo->state >= &states[S_PLAY_NIGHTS_TRANS]
&& player->mo->state <= &states[S_PLAY_NIGHTS_TRANS9])
&& !(player->mo->state >= &states[S_PLAY_NIGHTS_TRANS1]
&& player->mo->state <= &states[S_PLAY_NIGHTS_TRANS6])
&& !player->exiting)
player->nightstime--;
}
else if (gametype != GT_RACE && gametype != GT_COMPETITION
&& !(player->mo->state >= &states[S_PLAY_NIGHTS_TRANS]
&& player->mo->state <= &states[S_PLAY_NIGHTS_TRANS9])
&& !(player->mo->state >= &states[S_PLAY_NIGHTS_TRANS1]
&& player->mo->state <= &states[S_PLAY_NIGHTS_TRANS6])
&& !(player->capsule && player->capsule->reactiontime)
&& !player->exiting)
player->nightstime--;
@ -6227,8 +6238,8 @@ static void P_NiGHTSMovement(player_t *player)
return;
}
if (player->mo->state >= &states[S_PLAY_NIGHTS_TRANS]
&& player->mo->state <= &states[S_PLAY_NIGHTS_TRANS9])
if (player->mo->state >= &states[S_PLAY_NIGHTS_TRANS1]
&& player->mo->state <= &states[S_PLAY_NIGHTS_TRANS6])
{
player->mo->momx = player->mo->momy = player->mo->momz = 0;
return;
@ -6832,7 +6843,7 @@ static void P_MovePlayer(player_t *player)
fixed_t runspd;
if (player->mo->state >= &states[S_PLAY_SUPER_TRANS] && player->mo->state <= &states[S_PLAY_SUPER_TRANS9])
if (player->mo->state >= &states[S_PLAY_SUPER_TRANS1] && player->mo->state <= &states[S_PLAY_SUPER_TRANS6])
{
player->mo->momx = player->mo->momy = player->mo->momz = 0;
return;
@ -6901,12 +6912,12 @@ static void P_MovePlayer(player_t *player)
else if (maptol & TOL_NIGHTS)
{
if ((player->powers[pw_carry] == CR_NIGHTSMODE)
&& !(player->mo->state >= &states[S_PLAY_NIGHTS_TRANS]
&& player->mo->state <= &states[S_PLAY_NIGHTS_TRANS6] // NOT 9 - it's 6 when the player turns their supercolor.
&& !(player->exiting)))
&& (player->exiting
|| !(player->mo->state >= &states[S_PLAY_NIGHTS_TRANS1]
&& player->mo->state < &states[S_PLAY_NIGHTS_TRANS6])))
{
skin_t *skin = ((skin_t *)(player->mo->skin));
player->mo->color = (skin->flags & SF_SUPER) ? skin->supercolor + (unsigned)abs(((signed)(leveltime >> 1) % 9) - 4) : player->mo->color; // This is where super flashing is handled.
player->mo->color = (skin->flags & SF_SUPER) ? skin->supercolor + abs((((player->startedtime - player->nightstime) >> 1) % 9) - 4) : player->mo->color; // This is where super flashing is handled.
}
if (!player->capsule && !player->bonustime)
@ -9725,7 +9736,8 @@ void P_PlayerThink(player_t *player)
ticmiss++;
P_DoRopeHang(player);
P_SetPlayerMobjState(player->mo, S_PLAY_RIDE);
if (player->mo->state-states != S_PLAY_RIDE)
P_SetPlayerMobjState(player->mo, S_PLAY_RIDE);
P_DoJumpStuff(player, &player->cmd);
}
else //if (player->powers[pw_carry] == CR_ZOOMTUBE)
@ -9896,10 +9908,17 @@ void P_PlayerThink(player_t *player)
{
mobj_t *gmobj = P_SpawnGhostMobj(player->mo);
gmobj->fuse = 2;
if (gmobj->tracer)
gmobj->tracer->fuse = 2;
if (leveltime & 1)
{
gmobj->frame &= ~FF_TRANSMASK;
gmobj->frame |= tr_trans70<<FF_TRANSSHIFT;
if (gmobj->tracer)
{
gmobj->tracer->frame &= ~FF_TRANSMASK;
gmobj->tracer->frame |= tr_trans70<<FF_TRANSSHIFT;
}
}
// Hide the mobj from our sights if we're the displayplayer and chasecam is off,
@ -9973,7 +9992,9 @@ void P_PlayerThink(player_t *player)
player->powers[pw_nocontrol] = 0;
//pw_super acts as a timer now
if (player->powers[pw_super])
if (player->powers[pw_super]
&& (player->mo->state < &states[S_PLAY_SUPER_TRANS1]
|| player->mo->state > &states[S_PLAY_SUPER_TRANS6]))
player->powers[pw_super]++;
if (player->powers[pw_carry] == CR_BRAKGOOP)
@ -10165,6 +10186,11 @@ void P_PlayerAfterThink(player_t *player)
if (thiscam && thiscam->chase)
P_MoveChaseCamera(player, thiscam, false);
}
if (player->followmobj)
{
P_RemoveMobj(player->followmobj);
player->followmobj = NULL;
}
return;
}
@ -10343,7 +10369,10 @@ void P_PlayerAfterThink(player_t *player)
player->powers[pw_carry] = CR_NONE;
if (player->powers[pw_carry] != CR_NONE)
P_SetPlayerMobjState(player->mo, S_PLAY_RIDE);
{
if (player->mo->state-states != S_PLAY_RIDE)
P_SetPlayerMobjState(player->mo, S_PLAY_RIDE);
}
else
P_SetTarget(&player->mo->tracer, NULL);
@ -10362,7 +10391,8 @@ void P_PlayerAfterThink(player_t *player)
player->mo->z = player->mo->tracer->z - FixedDiv(player->mo->height, 3*FRACUNIT/2);
player->mo->momx = player->mo->momy = player->mo->momz = 0;
P_SetThingPosition(player->mo);
P_SetPlayerMobjState(player->mo, S_PLAY_RIDE);
if (player->mo->state-states != S_PLAY_RIDE)
P_SetPlayerMobjState(player->mo, S_PLAY_RIDE);
// Controllable missile
if (player->mo->tracer->type == MT_BLACKEGGMAN_MISSILE)
@ -10456,4 +10486,224 @@ void P_PlayerAfterThink(player_t *player)
if (P_IsObjectOnGround(player->mo))
player->mo->pmomz = 0;
if (player->followmobj && (player->spectator || player->mo->health <= 0 || player->followmobj->type != player->followitem))
{
P_RemoveMobj(player->followmobj);
player->followmobj = NULL;
}
if (!player->spectator && player->mo->health && player->followitem)
{
if (!player->followmobj || P_MobjWasRemoved(player->followmobj))
{
player->followmobj = P_SpawnMobjFromMobj(player->mo, 0, 0, 0, player->followitem);
P_SetTarget(&player->followmobj->tracer, player->mo);
player->followmobj->flags2 |= MF2_LINKDRAW;
}
if (player->followmobj)
{
#ifdef HAVE_BLUA
if (LUAh_FollowMobj(player, player->followmobj) || P_MobjWasRemoved(player->followmobj))
{;}
else
#endif
{
switch (player->followmobj->type)
{
case MT_TAILSOVERLAY: // c:
{
// init...
boolean smilesonground = P_IsObjectOnGround(player->mo);
angle_t horizangle = player->drawangle;
fixed_t zoffs = 0;
fixed_t backwards = -1*FRACUNIT;
boolean doroll = (player->panim == PA_ROLL || player->panim == PA_JUMP);
angle_t rollangle;
boolean panimchange;
INT32 ticnum = 0;
statenum_t chosenstate;
if (!player->followmobj->skin)
{
player->followmobj->skin = player->mo->skin;
P_SetMobjState(player->followmobj, S_TAILSOVERLAY_STAND);
player->followmobj->movecount = -1;
}
panimchange = (player->followmobj->movecount != (INT32)player->panim);
// initial position...
if (doroll)
{
fixed_t testval, zdist;
if (player->speed < FRACUNIT)
testval = FRACUNIT;
else
{
testval = (FixedMul(player->speed, FINECOSINE((horizangle - R_PointToAngle2(0, 0, player->rmomx, player->rmomy)) >> ANGLETOFINESHIFT)));
if (testval < FRACUNIT)
testval = FRACUNIT;
}
if (smilesonground && !player->mo->reactiontime)
zdist = (player->mo->z - player->followmobj->threshold);
else
zdist = player->mo->momz;
rollangle = R_PointToAngle2(0, 0, testval, -P_MobjFlip(player->mo)*zdist);
zoffs = 3*FRACUNIT + 12*FINESINE(rollangle >> ANGLETOFINESHIFT);
backwards = -12*FINECOSINE(rollangle >> ANGLETOFINESHIFT);
}
else if (player->panim == PA_RUN)
backwards = -5*FRACUNIT;
else if (player->panim == PA_SPRING)
{
zoffs += 4*FRACUNIT;
backwards /= 2;
}
else if (player->panim == PA_PAIN)
backwards /= 16;
else if (player->mo->state-states == S_PLAY_GASP)
{
backwards /= 16;
zoffs += 12*FRACUNIT;
}
else if (player->mo->state-states == S_PLAY_EDGE)
{
backwards /= 16;
zoffs = 3*FRACUNIT;
}
else if (player->panim == PA_ABILITY2)
{
zoffs = -7*FRACUNIT;
backwards = -9*FRACUNIT;
}
else if (player->mo->sprite2 == SPR2_FLY || player->mo->sprite2 == SPR2_TIRE)
backwards = -5*FRACUNIT;
// sprite...
if (doroll)
{
statenum_t add = ((rollangle > ANGLE_180) ? 2 : 0);
if (add)
rollangle = InvAngle(rollangle);
rollangle += ANG15; // modify the thresholds to be nice clean numbers
if (rollangle > ANG60)
chosenstate = S_TAILSOVERLAY_PLUS60DEGREES + add;
else if (rollangle > ANG30)
chosenstate = S_TAILSOVERLAY_PLUS30DEGREES + add;
else
chosenstate = S_TAILSOVERLAY_0DEGREES;
}
else if (player->panim == PA_SPRING)
chosenstate = S_TAILSOVERLAY_MINUS60DEGREES;
else if (player->panim == PA_FALL || player->mo->state-states == S_PLAY_RIDE)
chosenstate = S_TAILSOVERLAY_PLUS60DEGREES;
else if (player->panim == PA_PAIN)
chosenstate = S_TAILSOVERLAY_PAIN;
else if (player->mo->state-states == S_PLAY_GASP)
chosenstate = S_TAILSOVERLAY_GASP;
else if (player->mo->state-states == S_PLAY_EDGE)
chosenstate = S_TAILSOVERLAY_EDGE;
else if (player->panim == PA_RUN)
chosenstate = S_TAILSOVERLAY_RUN;
else if (player->panim == PA_WALK)
{
if (!smilesonground)
chosenstate = S_TAILSOVERLAY_PLUS30DEGREES;
else if (player->speed >= FixedMul(player->runspeed/2, player->mo->scale))
chosenstate = S_TAILSOVERLAY_0DEGREES;
else
chosenstate = S_TAILSOVERLAY_MINUS30DEGREES;
}
else if (player->mo->sprite2 == SPR2_FLY)
chosenstate = S_TAILSOVERLAY_FLY;
else if (player->mo->sprite2 == SPR2_TIRE)
chosenstate = S_TAILSOVERLAY_TIRE;
else if (player->panim == PA_ABILITY2)
chosenstate = S_TAILSOVERLAY_PLUS30DEGREES;
else if (player->panim == PA_IDLE)
chosenstate = S_TAILSOVERLAY_STAND;
else
chosenstate = S_INVISIBLE;
// state...
if (panimchange)
{
player->followmobj->sprite2 = -1;
P_SetMobjState(player->followmobj, chosenstate);
}
else
{
if (player->followmobj->state != states+chosenstate)
{
if (states[chosenstate].sprite == SPR_PLAY)
player->followmobj->sprite2 = P_GetSkinSprite2(((skin_t *)player->followmobj->skin), (states[chosenstate].frame & FF_FRAMEMASK), player);
P_SetMobjState(player->followmobj, chosenstate);
}
}
if (player->fly1 != 0 && player->powers[pw_tailsfly] != 0 && !smilesonground)
P_SetMobjState(player->followmobj, chosenstate);
// animation...
if (player->panim == PA_SPRING || player->panim == PA_FALL || player->mo->state-states == S_PLAY_RIDE)
{
if (FixedDiv(abs(player->mo->momz), player->mo->scale) < 20<<FRACBITS)
ticnum = 2;
else
ticnum = 1;
}
else if (player->panim == PA_PAIN)
ticnum = 2;
else if (player->mo->state-states == S_PLAY_GASP)
player->followmobj->tics = -1;
else if (player->mo->sprite2 == SPR2_TIRE)
ticnum = 4;
else if (player->panim != PA_IDLE)
ticnum = player->mo->tics;
if (ticnum && player->followmobj->tics > ticnum)
player->followmobj->tics = ticnum;
// final handling...
player->followmobj->color = player->mo->color;
player->followmobj->threshold = player->mo->z;
player->followmobj->movecount = player->panim;
player->followmobj->angle = horizangle;
player->followmobj->scale = player->mo->scale;
P_SetScale(player->followmobj, player->mo->scale);
player->followmobj->destscale = player->mo->destscale;
player->followmobj->radius = player->mo->radius;
player->followmobj->height = player->mo->height;
zoffs = FixedMul(zoffs, player->followmobj->scale);
if (player->mo->eflags & MFE_VERTICALFLIP)
{
player->followmobj->eflags |= MFE_VERTICALFLIP;
player->followmobj->flags2 |= MF2_OBJECTFLIP;
zoffs = player->mo->height - player->followmobj->height - zoffs;
}
else
{
player->followmobj->eflags &= ~MFE_VERTICALFLIP;
player->followmobj->flags2 &= ~MF2_OBJECTFLIP;
}
P_UnsetThingPosition(player->followmobj);
player->followmobj->x = player->mo->x + P_ReturnThrustX(player->followmobj, player->followmobj->angle, FixedMul(backwards, player->followmobj->scale));
player->followmobj->y = player->mo->y + P_ReturnThrustY(player->followmobj, player->followmobj->angle, FixedMul(backwards, player->followmobj->scale));
player->followmobj->z = player->mo->z + zoffs;
P_SetThingPosition(player->followmobj);
}
break;
default:
var1 = 1;
var2 = 0;
A_CapeChase(player->followmobj);
break;
}
}
}
}
}

View File

@ -1385,12 +1385,12 @@ static void R_ProjectSprite(mobj_t *thing)
// specific translucency
if (!cv_translucency.value)
; // no translucency
else if (oldthing->flags2 & MF2_SHADOW) // actually only the player should use this (temporary invisibility)
else if (oldthing->flags2 & MF2_SHADOW || thing->flags2 & MF2_SHADOW) // actually only the player should use this (temporary invisibility)
vis->transmap = transtables + ((tr_trans80-1)<<FF_TRANSSHIFT); // because now the translucency is set through FF_TRANSMASK
else if (oldthing->frame & FF_TRANSMASK)
vis->transmap = transtables + (oldthing->frame & FF_TRANSMASK) - 0x10000;
if ((oldthing->frame & FF_FULLBRIGHT) || (oldthing->flags2 & MF2_SHADOW))
if (oldthing->frame & FF_FULLBRIGHT || oldthing->flags2 & MF2_SHADOW || thing->flags2 & MF2_SHADOW)
vis->cut |= SC_FULLBRIGHT;
if (vis->cut & SC_FULLBRIGHT
@ -2438,7 +2438,7 @@ UINT8 P_GetSkinSprite2(skin_t *skin, UINT8 spr2, player_t *player)
while (!(skin->sprites[spr2].numframes)
&& spr2 != SPR2_STND
&& ++i != 32) // recursion limiter
&& ++i < 32) // recursion limiter
{
if (spr2 & FF_SPR2SUPER)
{
@ -2525,6 +2525,7 @@ static void Sk_SetDefaultValue(skin_t *skin)
skin->thokitem = -1;
skin->spinitem = -1;
skin->revitem = -1;
skin->followitem = 0;
skin->highresscale = FRACUNIT;
@ -2638,6 +2639,7 @@ void SetPlayerSkinByNum(INT32 playernum, INT32 skinnum)
player->thokitem = skin->thokitem < 0 ? (UINT32)mobjinfo[MT_PLAYER].painchance : (UINT32)skin->thokitem;
player->spinitem = skin->spinitem < 0 ? (UINT32)mobjinfo[MT_PLAYER].damage : (UINT32)skin->spinitem;
player->revitem = skin->revitem < 0 ? (mobjtype_t)mobjinfo[MT_PLAYER].raisestate : (UINT32)skin->revitem;
player->followitem = skin->followitem;
player->actionspd = skin->actionspd;
player->mindash = skin->mindash;
@ -2663,13 +2665,21 @@ void SetPlayerSkinByNum(INT32 playernum, INT32 skinnum)
player->skincolor = newcolor = skin->prefcolor;
}
if (player->followmobj)
{
P_RemoveMobj(player->followmobj);
player->followmobj = NULL;
}
if (player->mo)
{
fixed_t radius = FixedMul(skin->radius, player->mo->scale);
if ((player->powers[pw_carry] == CR_NIGHTSMODE) && (skin->sprites[SPR2_NGT0].numframes == 0)) // If you don't have a sprite for flying horizontally, use the default NiGHTS skin.
{
skin = &skins[DEFAULTNIGHTSSKIN];
newcolor = skin->prefcolor; // will be updated in thinker to flashing
player->followitem = skin->followitem;
if (!(cv_debug || devparm) && !(netgame || multiplayer || demoplayback))
newcolor = skin->prefcolor; // will be updated in thinker to flashing
}
player->mo->skin = skin;
if (newcolor)
@ -2803,6 +2813,7 @@ static boolean R_ProcessPatchableFields(skin_t *skin, char *stoken, char *value)
FULLPROCESS(thokitem)
FULLPROCESS(spinitem)
FULLPROCESS(revitem)
FULLPROCESS(followitem)
#undef FULLPROCESS
#define GETFRACBITS(field) else if (!stricmp(stoken, #field)) skin->field = atoi(value)<<FRACBITS;

View File

@ -82,6 +82,7 @@ typedef struct
INT32 thokitem;
INT32 spinitem;
INT32 revitem;
INT32 followitem;
fixed_t actionspd;
fixed_t mindash;
fixed_t maxdash;

View File

@ -700,10 +700,21 @@ static void ST_drawLives(void)
// skincolor face/super
UINT8 *colormap = R_GetTranslationColormap(stplyr->skin, stplyr->mo->color, GTC_CACHE);
patch_t *face = faceprefix[stplyr->skin];
if ((stplyr->powers[pw_super] && (stplyr->mo->state < &states[S_PLAY_SUPER_TRANS] || stplyr->mo->state > &states[S_PLAY_SUPER_TRANS9])) || (stplyr->powers[pw_carry] == CR_NIGHTSMODE && skins[stplyr->skin].flags & SF_SUPER))
if (stplyr->powers[pw_super])
face = superprefix[stplyr->skin];
V_DrawSmallMappedPatch(hudinfo[HUD_LIVESPIC].x, hudinfo[HUD_LIVESPIC].y + (v_splitflag ? -12 : 0),
V_SNAPTOLEFT|V_SNAPTOBOTTOM|V_HUDTRANS|v_splitflag,face, colormap);
if (cv_translucenthud.value == 10 && stplyr->powers[pw_super] == 1 && stplyr->mo->tracer)
{
INT32 v_supertrans = (stplyr->mo->tracer->frame & FF_TRANSMASK) >> FF_TRANSSHIFT;
if (v_supertrans < 10)
{
v_supertrans <<= V_ALPHASHIFT;
colormap = R_GetTranslationColormap(stplyr->skin, stplyr->mo->tracer->color, GTC_CACHE);
V_DrawSmallMappedPatch(hudinfo[HUD_LIVESPIC].x, hudinfo[HUD_LIVESPIC].y + (v_splitflag ? -12 : 0),
V_SNAPTOLEFT|V_SNAPTOBOTTOM|v_supertrans|v_splitflag,face, colormap);
}
}
}
else if (stplyr->skincolor)
{