- Fixed: Do not interpolate from an actor's despawned position to its spawned position when it

respawns.
- Use doubles instead of floats, as appropriate, in PIT_FindFloorCeiling().
- Fixed: The second call to P_FindFloorCeiling() in A_RestoreSpecialPosition and P_NightmareRespawn()
  must only consider 3D floors and midtexes.

SVN r3545 (trunk)
This commit is contained in:
Randy Heit 2012-04-08 21:12:14 +00:00
parent 9451b7c1d3
commit 837126ae57
5 changed files with 87 additions and 65 deletions

View file

@ -385,7 +385,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialPosition)
} }
} }
// Redo floor/ceiling check, in case of 3D floors // Redo floor/ceiling check, in case of 3D floors
P_FindFloorCeiling(self, FFCF_SAMESECTOR); P_FindFloorCeiling(self, FFCF_SAMESECTOR | FFCF_ONLY3DFLOORS);
if (self->z < self->floorz) if (self->z < self->floorz)
{ // Do not reappear under the floor, even if that's where we were for the { // Do not reappear under the floor, even if that's where we were for the
// initial spawn. // initial spawn.
@ -395,6 +395,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_RestoreSpecialPosition)
{ // Do the same for the ceiling. { // Do the same for the ceiling.
self->z = self->ceilingz - self->height; self->z = self->ceilingz - self->height;
} }
// Do not interpolate from the position the actor was at when it was
// picked up, in case that is different from where it is now.
self->PrevX = self->x;
self->PrevY = self->y;
self->PrevZ = self->z;
} }
int AInventory::StaticLastMessageTic; int AInventory::StaticLastMessageTic;

View file

@ -259,7 +259,7 @@ struct FLineOpening
bool abovemidtex; bool abovemidtex;
}; };
void P_LineOpening (FLineOpening &open, AActor *thing, const line_t *linedef, fixed_t x, fixed_t y, fixed_t refx=FIXED_MIN, fixed_t refy=0); void P_LineOpening (FLineOpening &open, AActor *thing, const line_t *linedef, fixed_t x, fixed_t y, fixed_t refx=FIXED_MIN, fixed_t refy=0, bool only3d=false);
class FBoundingBox; class FBoundingBox;
struct polyblock_t; struct polyblock_t;
@ -436,7 +436,8 @@ bool P_UsePuzzleItem (AActor *actor, int itemType);
enum enum
{ {
FFCF_ONLYSPAWNPOS = 1, FFCF_ONLYSPAWNPOS = 1,
FFCF_SAMESECTOR = 2 FFCF_SAMESECTOR = 2,
FFCF_ONLY3DFLOORS = 4, // includes 3D midtexes
}; };
void P_FindFloorCeiling (AActor *actor, int flags=0); void P_FindFloorCeiling (AActor *actor, int flags=0);

View file

@ -83,9 +83,11 @@ msecnode_t* sector_list = NULL; // phares 3/16/98
// //
// PIT_FindFloorCeiling // PIT_FindFloorCeiling
// //
// only3d set means to only check against 3D floors and midtexes.
//
//========================================================================== //==========================================================================
static bool PIT_FindFloorCeiling (line_t *ld, const FBoundingBox &box, FCheckPosition &tmf) static bool PIT_FindFloorCeiling (line_t *ld, const FBoundingBox &box, FCheckPosition &tmf, bool only3d)
{ {
if (box.Right() <= ld->bbox[BOXLEFT] if (box.Right() <= ld->bbox[BOXLEFT]
|| box.Left() >= ld->bbox[BOXRIGHT] || box.Left() >= ld->bbox[BOXRIGHT]
@ -113,28 +115,28 @@ static bool PIT_FindFloorCeiling (line_t *ld, const FBoundingBox &box, FCheckPos
(ld->backsector->ceilingplane.a | ld->backsector->ceilingplane.b)) == 0) (ld->backsector->ceilingplane.a | ld->backsector->ceilingplane.b)) == 0)
&& ld->backsector->e->XFloor.ffloors.Size()==0 && ld->frontsector->e->XFloor.ffloors.Size()==0) && ld->backsector->e->XFloor.ffloors.Size()==0 && ld->frontsector->e->XFloor.ffloors.Size()==0)
{ {
P_LineOpening (open, tmf.thing, ld, sx=tmf.x, sy=tmf.y, tmf.x, tmf.y); P_LineOpening (open, tmf.thing, ld, sx=tmf.x, sy=tmf.y, tmf.x, tmf.y, only3d);
} }
else else
{ // Find the point on the line closest to the actor's center, and use { // Find the point on the line closest to the actor's center, and use
// that to calculate openings // that to calculate openings
float dx = (float)ld->dx; double dx = ld->dx;
float dy = (float)ld->dy; double dy = ld->dy;
fixed_t r = (fixed_t)(((float)(tmf.x - ld->v1->x) * dx + fixed_t r = xs_CRoundToInt(((double)(tmf.x - ld->v1->x) * dx +
(float)(tmf.y - ld->v1->y) * dy) / (double)(tmf.y - ld->v1->y) * dy) /
(dx*dx + dy*dy) * 16777216.f); (dx*dx + dy*dy) * 16777216.f);
if (r <= 0) if (r <= 0)
{ {
P_LineOpening (open, tmf.thing, ld, sx=ld->v1->x, sy=ld->v1->y, tmf.x, tmf.y); P_LineOpening (open, tmf.thing, ld, sx=ld->v1->x, sy=ld->v1->y, tmf.x, tmf.y, only3d);
} }
else if (r >= (1<<24)) else if (r >= (1<<24))
{ {
P_LineOpening (open, tmf.thing, ld, sx=ld->v2->x, sy=ld->v2->y, tmf.thing->x, tmf.thing->y); P_LineOpening (open, tmf.thing, ld, sx=ld->v2->x, sy=ld->v2->y, tmf.thing->x, tmf.thing->y, only3d);
} }
else else
{ {
P_LineOpening (open, tmf.thing, ld, sx=ld->v1->x + MulScale24 (r, ld->dx), P_LineOpening (open, tmf.thing, ld, sx=ld->v1->x + MulScale24 (r, ld->dx),
sy=ld->v1->y + MulScale24 (r, ld->dy), tmf.x, tmf.y); sy=ld->v1->y + MulScale24 (r, ld->dy), tmf.x, tmf.y, only3d);
} }
} }
@ -264,7 +266,7 @@ void P_FindFloorCeiling (AActor *actor, int flags)
while ((ld = it.Next())) while ((ld = it.Next()))
{ {
PIT_FindFloorCeiling(ld, box, tmf); PIT_FindFloorCeiling(ld, box, tmf, !!(flags & FFCF_ONLY3DFLOORS));
} }
if (tmf.touchmidtex) tmf.dropoffz = tmf.floorz; if (tmf.touchmidtex) tmf.dropoffz = tmf.floorz;
@ -340,7 +342,7 @@ bool P_TeleportMove (AActor *thing, fixed_t x, fixed_t y, fixed_t z, bool telefr
thing->z = z; thing->z = z;
while ((ld = it.Next())) while ((ld = it.Next()))
{ {
PIT_FindFloorCeiling(ld, box, tmf); PIT_FindFloorCeiling(ld, box, tmf, false);
} }
thing->z = savedz; thing->z = savedz;

View file

@ -135,13 +135,14 @@ fixed_t P_InterceptVector (const divline_t *v2, const divline_t *v1)
// //
// Sets opentop and openbottom to the window // Sets opentop and openbottom to the window
// through a two sided line. // through a two sided line.
// OPTIMIZE: keep this precalculated
// //
//========================================================================== //==========================================================================
void P_LineOpening (FLineOpening &open, AActor *actor, const line_t *linedef, void P_LineOpening (FLineOpening &open, AActor *actor, const line_t *linedef,
fixed_t x, fixed_t y, fixed_t refx, fixed_t refy) fixed_t x, fixed_t y, fixed_t refx, fixed_t refy, bool only3d)
{ {
if (!only3d)
{
sector_t *front, *back; sector_t *front, *back;
fixed_t fc, ff, bc, bf; fixed_t fc, ff, bc, bf;
@ -202,6 +203,17 @@ void P_LineOpening (FLineOpening &open, AActor *actor, const line_t *linedef,
open.floorpic = back->GetTexture(sector_t::floor); open.floorpic = back->GetTexture(sector_t::floor);
open.lowfloor = ff; open.lowfloor = ff;
} }
}
else
{ // Dummy stuff to have some sort of opening for the 3D checks to modify
open.topsec = NULL;
open.ceilingpic.SetInvalid();
open.top = FIXED_MAX;
open.bottomsec = NULL;
open.floorpic.SetInvalid();
open.bottom = FIXED_MIN;
open.lowfloor = FIXED_MAX;
}
// Check 3D floors // Check 3D floors
if (actor != NULL) if (actor != NULL)

View file

@ -2487,7 +2487,7 @@ void P_NightmareRespawn (AActor *mobj)
} }
// If there are 3D floors, we need to find floor/ceiling again. // If there are 3D floors, we need to find floor/ceiling again.
P_FindFloorCeiling(mo, FFCF_SAMESECTOR); P_FindFloorCeiling(mo, FFCF_SAMESECTOR | FFCF_ONLY3DFLOORS);
if (z == ONFLOORZ) if (z == ONFLOORZ)
{ {
@ -2530,6 +2530,8 @@ void P_NightmareRespawn (AActor *mobj)
mo->skillrespawncount = mobj->skillrespawncount; mo->skillrespawncount = mobj->skillrespawncount;
mo->PrevZ = z; // Do not interpolate Z position if we changed it since spawning.
// spawn a teleport fog at old spot because of removal of the body? // spawn a teleport fog at old spot because of removal of the body?
mo = Spawn ("TeleportFog", mobj->x, mobj->y, mobj->z, ALLOW_REPLACE); mo = Spawn ("TeleportFog", mobj->x, mobj->y, mobj->z, ALLOW_REPLACE);
if (mo != NULL) if (mo != NULL)