Drone de-coupling implementation

* Visual elements and hitbox work as expected with scaling and OBJECTFLIP
This commit is contained in:
mazmazz 2018-08-10 22:11:48 -04:00
parent 32c17b1454
commit 7c0186bc97

View file

@ -7827,78 +7827,102 @@ void P_MobjThinker(mobj_t *mobj)
} }
break; break;
case MT_NIGHTSDRONE: case MT_NIGHTSDRONE:
// GOAL mode?
if (mobj->state >= &states[S_NIGHTSDRONE_SPARKLING1] && mobj->state <= &states[S_NIGHTSDRONE_SPARKLING16])
{ {
INT32 i; mobj_t *goalpost = NULL;
boolean bonustime = false; mobj_t *sparkle = NULL;
mobj_t *droneman = NULL;
for (i = 0; i < MAXPLAYERS; i++) if (mobj->target && mobj->target->type == MT_NIGHTSDRONE_GOAL)
if (playeringame[i] && players[i].bonustime && players[i].powers[pw_carry] == CR_NIGHTSMODE)
{
bonustime = true;
break;
}
if (!bonustime)
{ {
CONS_Debug(DBG_NIGHTSBASIC, "Removing goal post\n"); goalpost = mobj->target;
P_RemoveMobj(mobj->target); if (goalpost->target && goalpost->target->type == MT_NIGHTSDRONE_SPARKLING)
P_SetTarget(&mobj->target, NULL); sparkle = goalpost->target;
if (goalpost->tracer && goalpost->tracer->type == MT_NIGHTSDRONE_MAN)
mobj->flags &= ~MF_NOGRAVITY; droneman = goalpost->tracer;
mobj->flags2 |= MF2_DONTDRAW;
//P_SetMobjState(mobj, S_NIGHTSDRONE);
} }
}
// Invisible/bouncing mode.
else
{
INT32 i;
boolean bonustime = false;
// Bouncy bouncy! // GOAL mode?
mobj->angle += ANG10; if (sparkle->state >= &states[S_NIGHTSDRONE_SPARKLING1] && sparkle->state <= &states[S_NIGHTSDRONE_SPARKLING16])
if (mobj->flags2 & MF2_DONTDRAW)
mobj->momz = 0;
else if (mobj->z <= mobj->floorz)
mobj->momz = 5*FRACUNIT;
for (i = 0; i < MAXPLAYERS; i++)
if (playeringame[i] && players[i].bonustime && players[i].powers[pw_carry] == CR_NIGHTSMODE)
{
bonustime = true;
break;
}
if (bonustime)
{ {
mobj->z = mobj->floorz + mobj->height; INT32 i;
mobj->angle = mobj->momz = 0; boolean bonustime = false;
if (mobj->spawnpoint)
mobj->z += (mobj->spawnpoint->options >> ZSHIFT)<<FRACBITS;
CONS_Debug(DBG_NIGHTSBASIC, "Adding goal post\n");
P_SetTarget(&mobj->target, P_SpawnMobjFromMobj(mobj, 0, 0, FRACUNIT, MT_NIGHTSDRONE_GOAL));
mobj->flags2 &= ~MF2_DONTDRAW;
mobj->flags |= MF_NOGRAVITY;
P_SetMobjState(mobj, S_NIGHTSDRONE_SPARKLING1);
}
else if (!G_IsSpecialStage(gamemap))
{
for (i = 0; i < MAXPLAYERS; i++) for (i = 0; i < MAXPLAYERS; i++)
if (playeringame[i] && players[i].powers[pw_carry] != CR_NIGHTSMODE) if (playeringame[i] && players[i].bonustime && players[i].powers[pw_carry] == CR_NIGHTSMODE)
{ {
bonustime = true; // variable reuse bonustime = true;
break;
}
if (!bonustime)
{
CONS_Debug(DBG_NIGHTSBASIC, "Removing goal post\n");
if (goalpost && goalpost->state != &states[S_INVISIBLE])
P_SetMobjState(goalpost, S_INVISIBLE);
if (sparkle && sparkle->state != &states[S_INVISIBLE])
P_SetMobjState(sparkle, S_INVISIBLE);
}
}
// Invisible/bouncing mode.
else
{
INT32 i;
boolean bonustime = false;
// Bouncy bouncy!
droneman->angle += ANG10;
if (droneman->flags2 & MF2_DONTDRAW)
droneman->momz = 0;
else if (!(droneman->flags2 & MF2_OBJECTFLIP)
&& droneman->z <= droneman->floorz)
droneman->momz = FixedMul(5*FRACUNIT, droneman->scale);
else if ((droneman->flags2 & MF2_OBJECTFLIP)
&& droneman->z >= droneman->ceilingz - droneman->height)
droneman->momz = FixedMul(-5*FRACUNIT, droneman->scale);
for (i = 0; i < MAXPLAYERS; i++)
if (playeringame[i] && players[i].bonustime && players[i].powers[pw_carry] == CR_NIGHTSMODE)
{
bonustime = true;
break; break;
} }
if (bonustime) if (bonustime)
mobj->flags2 &= ~MF2_DONTDRAW; {
else CONS_Debug(DBG_NIGHTSBASIC, "Adding goal post\n");
mobj->flags2 |= MF2_DONTDRAW; if (droneman && droneman->state != &states[S_INVISIBLE])
P_SetMobjState(droneman, S_INVISIBLE);
if (goalpost && goalpost->state == &states[S_INVISIBLE])
P_SetMobjState(goalpost, mobjinfo[goalpost->type].meleestate);
if (sparkle && sparkle->state == &states[S_INVISIBLE])
P_SetMobjState(sparkle, mobjinfo[sparkle->type].meleestate);
}
else if (!G_IsSpecialStage(gamemap))
{
for (i = 0; i < MAXPLAYERS; i++)
if (playeringame[i] && players[i].powers[pw_carry] != CR_NIGHTSMODE)
{
bonustime = true; // variable reuse
break;
}
if (bonustime)
{
// show droneman if at least one player is non-nights
if (goalpost && goalpost->state != &states[S_INVISIBLE])
P_SetMobjState(goalpost, S_INVISIBLE);
if (sparkle && sparkle->state != &states[S_INVISIBLE])
P_SetMobjState(sparkle, S_INVISIBLE);
if (droneman && droneman->state == &states[S_INVISIBLE])
P_SetMobjState(droneman, mobjinfo[droneman->type].meleestate);
}
else
{
// else, hide it
if (droneman && droneman->state != &states[S_INVISIBLE])
P_SetMobjState(droneman, S_INVISIBLE);
}
}
} }
} }
break; break;
@ -10516,6 +10540,23 @@ ML_EFFECT4 : Don't clip inside the ground
case MT_NIGHTSDRONE: case MT_NIGHTSDRONE:
if (mthing->angle > 0) if (mthing->angle > 0)
mobj->health = mthing->angle; mobj->health = mthing->angle;
if (mthing->options & MTF_OBJECTFLIP)
{
mobj->eflags |= MFE_VERTICALFLIP;
mobj->flags2 |= MF2_OBJECTFLIP;
}
// spawn visual components
{
mobj_t *goalpost = P_SpawnMobjFromMobj(mobj, 0, 0, 0, MT_NIGHTSDRONE_GOAL);
mobj_t *sparkle = P_SpawnMobjFromMobj(mobj, 0, 0, 0, MT_NIGHTSDRONE_SPARKLING);
mobj_t *droneman = P_SpawnMobjFromMobj(mobj, 0, 0, 0, MT_NIGHTSDRONE_MAN);
P_SetTarget(&mobj->target, goalpost);
P_SetTarget(&goalpost->target, sparkle);
P_SetTarget(&goalpost->tracer, droneman);
}
break; break;
case MT_HIVEELEMENTAL: case MT_HIVEELEMENTAL:
if (mthing->extrainfo) if (mthing->extrainfo)