A thorough reimplementation of Nojumpspin for the SPR2_ age.

* SF_NOJUMPSPIN - Player's height is full whilst jumping, SPR2_JUMP defaults to SPR2_SPNG instead of SPR2_SPIN, and the player goes into fall frames if they start moving downwards or use their ability.
* PA_JUMP - for jumping (upwards in the case of SF_NOJUMPSPIN.
* SF_NOJUMPDAMAGE - Ala rosy.wad, don't damage enemies, etc when jumping into them.
* SF_STOMPDAMAGE - Just for fun. Ala in Mario, always damage enemies when you land on top of them (your gravity reference, not theirs).
* SF_MARIODAMAGE - SF_NOJUMPDAMAGE|SF_STOMPDAMAGE is reasonably accurate to the Mario games, and might as well be surfaced as such.

Also, a minor change:

* Instead of not spawning the revitem if your SPR2_ is SPR2_DASH, don't spawn it if it's set to 0. This requires the player.dta I uploaded a couple days ago to behave as it was previously.
* Don't get stuck in spindash frames if your maxdash is 0, and don't flash rolling frames if you're on goop.
This commit is contained in:
toasterbabe 2016-07-10 18:41:38 +01:00
parent d8d8333719
commit 8431f64300
6 changed files with 64 additions and 30 deletions

View file

@ -39,6 +39,10 @@ typedef enum
SF_NOSKID = 1<<4, // No skid particles etc SF_NOSKID = 1<<4, // No skid particles etc
SF_NOSPEEDADJUST = 1<<5, // Skin-specific version of disablespeedadjust SF_NOSPEEDADJUST = 1<<5, // Skin-specific version of disablespeedadjust
SF_RUNONWATER = 1<<6, // Run on top of water FOFs? SF_RUNONWATER = 1<<6, // Run on top of water FOFs?
SF_NOJUMPSPIN = 1<<7, // SPR2_JUMP defaults to SPR2_SPRG instead of SPR2_SPIN, falling states used, and player height is full when jumping?
SF_NOJUMPDAMAGE = 1<<8, // Don't damage enemies, etc whilst jumping?
SF_STOMPDAMAGE = 1<<9, // Always damage enemies, etc by landing on them, no matter your vunerability?
SF_MARIODAMAGE = SF_NOJUMPDAMAGE|SF_STOMPDAMAGE, // The Mario method of being able to damage enemies, etc.
} skinflags_t; } skinflags_t;
//Primary and secondary skin abilities //Primary and secondary skin abilities
@ -166,6 +170,7 @@ typedef enum
PA_RUN, PA_RUN,
PA_PAIN, PA_PAIN,
PA_ROLL, PA_ROLL,
PA_JUMP,
PA_SPRING, PA_SPRING,
PA_FALL, PA_FALL,
PA_ABILITY, PA_ABILITY,

View file

@ -7120,6 +7120,10 @@ struct {
{"SF_NOSKID",SF_NOSKID}, {"SF_NOSKID",SF_NOSKID},
{"SF_NOSPEEDADJUST",SF_NOSPEEDADJUST}, {"SF_NOSPEEDADJUST",SF_NOSPEEDADJUST},
{"SF_RUNONWATER",SF_RUNONWATER}, {"SF_RUNONWATER",SF_RUNONWATER},
{"SF_NOJUMPSPIN",SF_NOJUMPSPIN},
{"SF_NOJUMPDAMAGE",SF_NOJUMPDAMAGE},
{"SF_STOMPDAMAGE",SF_STOMPDAMAGE},
{"SF_MARIODAMAGE",SF_MARIODAMAGE},
// Character abilities! // Character abilities!
// Primary // Primary
@ -7189,6 +7193,7 @@ struct {
{"PA_RUN",PA_RUN}, {"PA_RUN",PA_RUN},
{"PA_PAIN",PA_PAIN}, {"PA_PAIN",PA_PAIN},
{"PA_ROLL",PA_ROLL}, {"PA_ROLL",PA_ROLL},
{"PA_JUMP",PA_JUMP},
{"PA_SPRING",PA_SPRING}, {"PA_SPRING",PA_SPRING},
{"PA_FALL",PA_FALL}, {"PA_FALL",PA_FALL},
{"PA_ABILITY",PA_ABILITY}, {"PA_ABILITY",PA_ABILITY},

View file

@ -300,7 +300,9 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck)
} }
if (((player->pflags & PF_NIGHTSMODE) && (player->pflags & PF_DRILLING)) if (((player->pflags & PF_NIGHTSMODE) && (player->pflags & PF_DRILLING))
|| (player->pflags & (PF_JUMPED|PF_SPINNING|PF_GLIDING)) || ((player->pflags & PF_JUMPED) && !(player->charflags & SF_NOJUMPDAMAGE))
|| (player->pflags & (PF_SPINNING|PF_GLIDING))
|| ((player->charflags & SF_STOMPDAMAGE) && (P_MobjFlip(toucher)*(toucher->z - (special->z + special->height/2)) > 0) && (P_MobjFlip(toucher)*toucher->momz < 0))
|| player->powers[pw_invulnerability] || player->powers[pw_super]) // Do you possess the ability to subdue the object? || player->powers[pw_invulnerability] || player->powers[pw_super]) // Do you possess the ability to subdue the object?
{ {
if (P_MobjFlip(toucher)*toucher->momz < 0) if (P_MobjFlip(toucher)*toucher->momz < 0)
@ -343,7 +345,9 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck)
P_DamageMobj(toucher, special, special, 1, 0); P_DamageMobj(toucher, special, special, 1, 0);
} }
else if (((player->pflags & PF_NIGHTSMODE) && (player->pflags & PF_DRILLING)) else if (((player->pflags & PF_NIGHTSMODE) && (player->pflags & PF_DRILLING))
|| (player->pflags & (PF_JUMPED|PF_SPINNING|PF_GLIDING)) || ((player->pflags & PF_JUMPED) && !(player->charflags & SF_NOJUMPDAMAGE))
|| (player->pflags & (PF_SPINNING|PF_GLIDING))
|| ((player->charflags & SF_STOMPDAMAGE) && (P_MobjFlip(toucher)*(toucher->z - (special->z + special->height/2)) > 0) && (P_MobjFlip(toucher)*toucher->momz < 0))
|| player->powers[pw_invulnerability] || player->powers[pw_super]) // Do you possess the ability to subdue the object? || player->powers[pw_invulnerability] || player->powers[pw_super]) // Do you possess the ability to subdue the object?
{ {
if (P_MobjFlip(toucher)*toucher->momz < 0) if (P_MobjFlip(toucher)*toucher->momz < 0)
@ -1298,7 +1302,10 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck)
S_StartSound(toucher, special->info->painsound); S_StartSound(toucher, special->info->painsound);
return; return;
} }
else if (((player->pflags & PF_NIGHTSMODE) && (player->pflags & PF_DRILLING)) || (player->pflags & (PF_JUMPED|PF_SPINNING|PF_GLIDING)) else if (((player->pflags & PF_NIGHTSMODE) && (player->pflags & PF_DRILLING))
|| ((player->pflags & PF_JUMPED) && !(player->charflags & SF_NOJUMPDAMAGE))
|| ((player->charflags & SF_STOMPDAMAGE) && (P_MobjFlip(toucher)*(toucher->z - (special->z + special->height/2)) > 0) && (P_MobjFlip(toucher)*toucher->momz < 0))
|| (player->pflags & (PF_SPINNING|PF_GLIDING))
|| player->powers[pw_invulnerability] || player->powers[pw_super]) // Do you possess the ability to subdue the object? || player->powers[pw_invulnerability] || player->powers[pw_super]) // Do you possess the ability to subdue the object?
{ {
// Shatter the shield! // Shatter the shield!

View file

@ -938,7 +938,9 @@ static boolean PIT_CheckThing(mobj_t *thing)
&& thing->z + thing->height + FixedMul(FRACUNIT, thing->scale) >= tmthing->z) && thing->z + thing->height + FixedMul(FRACUNIT, thing->scale) >= tmthing->z)
{ {
if (thing->flags & MF_MONITOR if (thing->flags & MF_MONITOR
&& tmthing->player->pflags & (PF_JUMPED|PF_SPINNING|PF_GLIDING)) && (tmthing->player->pflags & (PF_SPINNING|PF_GLIDING)
|| ((tmthing->player->pflags & PF_JUMPED) && !(tmthing->player->charflags & SF_NOJUMPDAMAGE))
|| ((tmthing->player->charflags & SF_STOMPDAMAGE) && (P_MobjFlip(tmthing)*(tmthing->z - (thing->z + thing->height/2)) > 0) && (P_MobjFlip(tmthing)*tmthing->momz < 0))))
{ {
SINT8 flipval = P_MobjFlip(thing); // Save this value in case monitor gets removed. SINT8 flipval = P_MobjFlip(thing); // Save this value in case monitor gets removed.
fixed_t *momz = &tmthing->momz; // tmthing gets changed by P_DamageMobj, so we need a new pointer?! X_x;; fixed_t *momz = &tmthing->momz; // tmthing gets changed by P_DamageMobj, so we need a new pointer?! X_x;;
@ -960,7 +962,10 @@ static boolean PIT_CheckThing(mobj_t *thing)
} }
// Monitors are not treated as solid to players who are jumping, spinning or gliding, // Monitors are not treated as solid to players who are jumping, spinning or gliding,
// unless it's a CTF team monitor and you're on the wrong team // unless it's a CTF team monitor and you're on the wrong team
else if (thing->flags & MF_MONITOR && tmthing->player && tmthing->player->pflags & (PF_JUMPED|PF_SPINNING|PF_GLIDING) else if (thing->flags & MF_MONITOR && tmthing->player
&& (tmthing->player->pflags & (PF_SPINNING|PF_GLIDING)
|| ((tmthing->player->pflags & PF_JUMPED) && !(tmthing->player->charflags & SF_NOJUMPDAMAGE))
|| ((tmthing->player->charflags & SF_STOMPDAMAGE) && (P_MobjFlip(tmthing)*(tmthing->z - (thing->z + thing->height/2)) > 0) && (P_MobjFlip(tmthing)*tmthing->momz < 0)))
&& !((thing->type == MT_REDRINGBOX && tmthing->player->ctfteam != 1) || (thing->type == MT_BLUERINGBOX && tmthing->player->ctfteam != 2))) && !((thing->type == MT_REDRINGBOX && tmthing->player->ctfteam != 1) || (thing->type == MT_BLUERINGBOX && tmthing->player->ctfteam != 2)))
; ;
// z checking at last // z checking at last

View file

@ -238,11 +238,13 @@ boolean P_SetPlayerMobjState(mobj_t *mobj, statenum_t state)
break; break;
case S_PLAY_SPIN: case S_PLAY_SPIN:
case S_PLAY_DASH: case S_PLAY_DASH:
case S_PLAY_JUMP:
case S_PLAY_SUPER_SPIN: case S_PLAY_SUPER_SPIN:
case S_PLAY_SUPER_JUMP:
player->panim = PA_ROLL; player->panim = PA_ROLL;
break; break;
case S_PLAY_JUMP:
case S_PLAY_SUPER_JUMP:
player->panim = PA_JUMP;
break;
case S_PLAY_SPRING: case S_PLAY_SPRING:
case S_PLAY_SUPER_SPRING: case S_PLAY_SUPER_SPRING:
player->panim = PA_SPRING; player->panim = PA_SPRING;
@ -286,7 +288,7 @@ boolean P_SetPlayerMobjState(mobj_t *mobj, statenum_t state)
if (!(disableSpeedAdjust || player->charflags & SF_NOSPEEDADJUST)) if (!(disableSpeedAdjust || player->charflags & SF_NOSPEEDADJUST))
{ {
fixed_t speed = FixedDiv(player->speed, mobj->scale); fixed_t speed = FixedDiv(player->speed, mobj->scale);
if (player->panim == PA_ROLL) if (player->panim == PA_ROLL || player->panim == PA_JUMP)
{ {
if (speed > 16<<FRACBITS) if (speed > 16<<FRACBITS)
mobj->tics = 1; mobj->tics = 1;
@ -329,12 +331,13 @@ boolean P_SetPlayerMobjState(mobj_t *mobj, statenum_t state)
// Player animations // Player animations
if (st->sprite == SPR_PLAY) if (st->sprite == SPR_PLAY)
{ {
skin_t *skin = ((skin_t *)mobj->skin);
boolean noalt = false; boolean noalt = false;
UINT8 spr2 = st->frame & FF_FRAMEMASK; UINT8 spr2 = st->frame & FF_FRAMEMASK;
UINT16 frame = (mobj->frame & FF_FRAMEMASK)+1; UINT16 frame = (mobj->frame & FF_FRAMEMASK)+1;
mobj->anim_duration = (UINT16)st->var2; // only used if FF_ANIMATE is set mobj->anim_duration = (UINT16)st->var2; // only used if FF_ANIMATE is set
while (((skin_t *)mobj->skin)->sprites[spr2].numframes <= 0 while (skin->sprites[spr2].numframes <= 0
&& spr2 != SPR2_STND) && spr2 != SPR2_STND)
{ {
switch(spr2) switch(spr2)
@ -352,7 +355,7 @@ boolean P_SetPlayerMobjState(mobj_t *mobj, statenum_t state)
spr2 = SPR2_SPNG; spr2 = SPR2_SPNG;
break; break;
case SPR2_JUMP: case SPR2_JUMP:
spr2 = SPR2_SPIN; spr2 = (skin->flags & SF_NOJUMPSPIN) ? SPR2_SPNG : SPR2_SPIN;
break; break;
case SPR2_SPNG: // spring case SPR2_SPNG: // spring
spr2 = SPR2_FALL; spr2 = SPR2_FALL;

View file

@ -3727,9 +3727,6 @@ void P_DoJump(player_t *player, boolean soundandstate)
if (!player->spectator) if (!player->spectator)
S_StartSound(player->mo, sfx_jump); // Play jump sound! S_StartSound(player->mo, sfx_jump); // Play jump sound!
if (!(player->charability2 == CA2_SPINDASH))
P_SetPlayerMobjState(player->mo, S_PLAY_SPRING);
else
P_SetPlayerMobjState(player->mo, S_PLAY_JUMP); P_SetPlayerMobjState(player->mo, S_PLAY_JUMP);
} }
} }
@ -3780,7 +3777,7 @@ static void P_DoSpinDash(player_t *player, ticcmd_t *cmd)
S_StartSound(player->mo, sfx_spndsh); // Make the rev sound! S_StartSound(player->mo, sfx_spndsh); // Make the rev sound!
// Now spawn the color thok circle. // Now spawn the color thok circle.
if (player->mo->sprite2 != SPR2_DASH) if (player->revitem)
{ {
P_SpawnSpinMobj(player, player->revitem); P_SpawnSpinMobj(player, player->revitem);
if (demorecording) if (demorecording)
@ -3827,19 +3824,29 @@ static void P_DoSpinDash(player_t *player, ticcmd_t *cmd)
} }
// Catapult the player from a spindash rev! // Catapult the player from a spindash rev!
if (onground && !(player->pflags & PF_USEDOWN) && player->dashspeed && (player->pflags & PF_STARTDASH) && (player->pflags & PF_SPINNING)) if (onground && !(player->pflags & PF_USEDOWN) && (player->pflags & PF_STARTDASH) && (player->pflags & PF_SPINNING))
{ {
player->pflags &= ~PF_STARTDASH;
if (player->powers[pw_ingoop]) if (player->powers[pw_ingoop])
player->dashspeed = 0; player->dashspeed = 0;
player->pflags &= ~PF_STARTDASH;
if (!((gametype == GT_RACE || gametype == GT_COMPETITION) && leveltime < 4*TICRATE)) if (!((gametype == GT_RACE || gametype == GT_COMPETITION) && leveltime < 4*TICRATE))
{
if (player->dashspeed)
{ {
P_SetPlayerMobjState(player->mo, S_PLAY_SPIN); P_SetPlayerMobjState(player->mo, S_PLAY_SPIN);
P_InstaThrust(player->mo, player->mo->angle, player->dashspeed); // catapult forward ho!! P_InstaThrust(player->mo, player->mo->angle, player->dashspeed); // catapult forward ho!!
}
else
{
P_SetPlayerMobjState(player->mo, S_PLAY_STND);
player->pflags &= ~PF_SPINNING;
}
if (!player->spectator) if (!player->spectator)
S_StartSound(player->mo, sfx_zoom); S_StartSound(player->mo, sfx_zoom);
} }
player->dashspeed = 0; player->dashspeed = 0;
} }
@ -6524,8 +6531,10 @@ static void P_MovePlayer(player_t *player)
P_SetPlayerMobjState(player->mo, S_PLAY_WALK); P_SetPlayerMobjState(player->mo, S_PLAY_WALK);
} }
// If Springing, but travelling DOWNWARD, change back! // If Springing (or nojumpspinning), but travelling DOWNWARD, change back! (nojumpspin also turns to fall once PF_THOKKED is added.)
if (player->panim == PA_SPRING && P_MobjFlip(player->mo)*player->mo->momz < 0) if ((player->panim == PA_SPRING && P_MobjFlip(player->mo)*player->mo->momz < 0)
|| ((((player->charflags & SF_NOJUMPSPIN) && (player->pflags & PF_JUMPED) && player->panim == PA_JUMP))
&& (P_MobjFlip(player->mo)*player->mo->momz < 0 || player->pflags & PF_THOKKED)))
P_SetPlayerMobjState(player->mo, S_PLAY_FALL); P_SetPlayerMobjState(player->mo, S_PLAY_FALL);
// If Springing but on the ground, change back! // If Springing but on the ground, change back!
else if (onground && (player->panim == PA_SPRING || player->panim == PA_FALL || player->panim == PA_RIDE) && !player->mo->momz) else if (onground && (player->panim == PA_SPRING || player->panim == PA_FALL || player->panim == PA_RIDE) && !player->mo->momz)
@ -6844,7 +6853,7 @@ static void P_MovePlayer(player_t *player)
#endif #endif
} }
// Otherwise, face the direction you're travelling. // Otherwise, face the direction you're travelling.
else if (player->panim == PA_WALK || player->panim == PA_RUN || player->panim == PA_ROLL else if (player->panim == PA_WALK || player->panim == PA_RUN || player->panim == PA_ROLL || player->panim == PA_JUMP
|| (player->mo->state-states == S_PLAY_FLY || player->mo->state-states == S_PLAY_FLY_TIRED)) || (player->mo->state-states == S_PLAY_FLY || player->mo->state-states == S_PLAY_FLY_TIRED))
player->mo->angle = R_PointToAngle2(0, 0, player->rmomx, player->rmomy); player->mo->angle = R_PointToAngle2(0, 0, player->rmomx, player->rmomy);
@ -6893,7 +6902,7 @@ static void P_MovePlayer(player_t *player)
if (player->skin == 0 && player->powers[pw_super] && player->speed > FixedMul(5<<FRACBITS, player->mo->scale) if (player->skin == 0 && player->powers[pw_super] && player->speed > FixedMul(5<<FRACBITS, player->mo->scale)
&& P_MobjFlip(player->mo)*player->mo->momz <= 0) && P_MobjFlip(player->mo)*player->mo->momz <= 0)
{ {
if (player->panim == PA_ROLL || player->mo->state-states == S_PLAY_PAIN || player->panim == PA_WALK) if (player->panim == PA_ROLL || player->panim == PA_JUMP || player->mo->state-states == S_PLAY_PAIN || player->panim == PA_WALK)
P_SetPlayerMobjState(player->mo, S_PLAY_SUPER_FLOAT); P_SetPlayerMobjState(player->mo, S_PLAY_SUPER_FLOAT);
player->mo->momz = 0; player->mo->momz = 0;
@ -6980,7 +6989,7 @@ static void P_MovePlayer(player_t *player)
// Less height while spinning. Good for spinning under things...? // Less height while spinning. Good for spinning under things...?
if ((player->mo->state == &states[player->mo->info->painstate] || player->mo->state == &states[S_PLAY_SUPER_PAIN]) if ((player->mo->state == &states[player->mo->info->painstate] || player->mo->state == &states[S_PLAY_SUPER_PAIN])
|| (player->charability2 == CA2_SPINDASH && (player->pflags & (PF_SPINNING|PF_JUMPED))) || (!(player->charflags & SF_NOJUMPSPIN) && (player->pflags & (PF_SPINNING|PF_JUMPED)))
|| player->powers[pw_tailsfly] || player->pflags & PF_GLIDING || player->powers[pw_tailsfly] || player->pflags & PF_GLIDING
|| (player->charability == CA_FLY && player->mo->state-states == S_PLAY_FLY_TIRED)) || (player->charability == CA_FLY && player->mo->state-states == S_PLAY_FLY_TIRED))
player->mo->height = P_GetPlayerSpinHeight(player); player->mo->height = P_GetPlayerSpinHeight(player);
@ -7274,7 +7283,7 @@ static void P_DoRopeHang(player_t *player)
player->pflags &= ~PF_ROPEHANG; player->pflags &= ~PF_ROPEHANG;
if (!(player->pflags & PF_SLIDING) && (player->pflags & PF_JUMPED) if (!(player->pflags & PF_SLIDING) && (player->pflags & PF_JUMPED)
&& !(player->panim == PA_ROLL) && player->charability2 == CA2_SPINDASH) && !(player->panim == PA_JUMP))
P_SetPlayerMobjState(player->mo, S_PLAY_JUMP); P_SetPlayerMobjState(player->mo, S_PLAY_JUMP);
return; return;
} }
@ -7391,7 +7400,7 @@ static void P_DoRopeHang(player_t *player)
player->pflags &= ~PF_ROPEHANG; player->pflags &= ~PF_ROPEHANG;
if (!(player->pflags & PF_SLIDING) && (player->pflags & PF_JUMPED) if (!(player->pflags & PF_SLIDING) && (player->pflags & PF_JUMPED)
&& !(player->panim == PA_ROLL) && player->charability2 == CA2_SPINDASH) && !(player->panim == PA_JUMP))
P_SetPlayerMobjState(player->mo, S_PLAY_JUMP); P_SetPlayerMobjState(player->mo, S_PLAY_JUMP);
} }
@ -8733,7 +8742,7 @@ void P_PlayerThink(player_t *player)
if (player->panim != PA_ABILITY) if (player->panim != PA_ABILITY)
P_SetPlayerMobjState(player->mo, S_PLAY_GLIDE); P_SetPlayerMobjState(player->mo, S_PLAY_GLIDE);
} }
else if ((player->pflags & PF_JUMPED) && !player->powers[pw_super] && player->panim != PA_ROLL && player->charability2 == CA2_SPINDASH) else if ((player->pflags & PF_JUMPED) && !player->powers[pw_super] && player->panim != PA_JUMP && !(player->charflags & SF_NOJUMPSPIN))
P_SetPlayerMobjState(player->mo, S_PLAY_JUMP); P_SetPlayerMobjState(player->mo, S_PLAY_JUMP);
if (player->flashcount) if (player->flashcount)
@ -8977,7 +8986,7 @@ void P_PlayerThink(player_t *player)
else else
{ {
P_DoZoomTube(player); P_DoZoomTube(player);
if (!(player->panim == PA_ROLL) && player->charability2 == CA2_SPINDASH) if (!(player->panim == PA_ROLL))
P_SetPlayerMobjState(player->mo, S_PLAY_SPIN); P_SetPlayerMobjState(player->mo, S_PLAY_SPIN);
} }
player->rmomx = player->rmomy = 0; // no actual momentum from your controls player->rmomx = player->rmomy = 0; // no actual momentum from your controls
@ -9361,9 +9370,9 @@ void P_PlayerAfterThink(player_t *player)
else if (player->pflags & PF_SLIDING) else if (player->pflags & PF_SLIDING)
P_SetPlayerMobjState(player->mo, player->mo->info->painstate); P_SetPlayerMobjState(player->mo, player->mo->info->painstate);
else if (player->pflags & PF_JUMPED else if (player->pflags & PF_JUMPED
&& ((!player->powers[pw_super] && player->panim != PA_ROLL) && ((!player->powers[pw_super] && player->panim != PA_JUMP)
|| player->mo->state == &states[player->mo->info->painstate]) || player->mo->state == &states[player->mo->info->painstate])
&& player->charability2 == CA2_SPINDASH) && !(player->charflags & SF_NOJUMPSPIN))
P_SetPlayerMobjState(player->mo, S_PLAY_JUMP); P_SetPlayerMobjState(player->mo, S_PLAY_JUMP);
if (player->pflags & PF_CARRIED && player->mo->tracer) if (player->pflags & PF_CARRIED && player->mo->tracer)