Commit 54f0d0c1 by ShaderWraith

IN PROGRESS: porting eternity slopes from srb2cb

parent c9753836
......@@ -432,6 +432,7 @@ OBJS:=$(i_main_o) \
$(OBJDIR)/m_misc.o \
$(OBJDIR)/m_random.o \
$(OBJDIR)/m_queue.o \
$(OBJDIR)/m_vector.o \
$(OBJDIR)/info.o \
$(OBJDIR)/p_ceilng.o \
$(OBJDIR)/p_enemy.o \
......@@ -450,6 +451,7 @@ OBJS:=$(i_main_o) \
$(OBJDIR)/p_telept.o \
$(OBJDIR)/p_tick.o \
$(OBJDIR)/p_user.o \
$(OBJDIR)/p_slopes.o \
$(OBJDIR)/tables.o \
$(OBJDIR)/r_bsp.o \
$(OBJDIR)/r_data.o \
......
......@@ -436,6 +436,14 @@ extern const char *compdate, *comptime, *comprevision;
/// Fun experimental slope stuff!
//#define SLOPENESS
/// Kalaron/Eternity Engine slope code (SRB2CB ported)
/// Depends on NEED_FIXED_VECTORS? for a few functions.
/// However, uses own vector types for math.
#define ESLOPE
/// Fixed and float point types
//#define NEED_FIXED_VECTOR
/// Delete file while the game is running.
/// \note EXTREMELY buggy, tends to crash game.
//#define DELFILE
......
......@@ -357,6 +357,29 @@ FUNCMATH FUNCINLINE static ATTRINLINE fixed_t FixedRound(fixed_t x)
return INT32_MAX;
}
/*!
\brief convert a fixed_t number into double floating number
*/
#define FIXED_TO_DOUBLE(f) ((double)((f) / FRACUNIT))
/*!
\brief convert a double floating number into fixed_t number
*/
#define DOUBLE_TO_FIXED(f) ((fixed_t)((f) * FRACUNIT))
/*!
\brief convert a integer into fixed_t number
*/
#define INT_TO_FIXED(x) ((int)((x) * FRACUNIT))
/*!
\brief convert a fixed_t number into integer
*/
#define FIXED_TO_INT(x) (((int)(x)) / (FRACUNIT))
static inline int DivScale32 (fixed_t a, fixed_t b) { return (fixed_t)(((INT64)a << 32) / b); }
#ifdef NEED_FIXED_VECTOR
typedef struct
......
This diff is collapsed. Click to expand it.
// Emacs style mode select -*- C++ -*-
//-----------------------------------------------------------------------------
//
// Copyright(C) 2004 Stephen McGranahan
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
//
//--------------------------------------------------------------------------
//
// DESCRIPTION:
// Vectors
// SoM created 05/18/09
//
//-----------------------------------------------------------------------------
#ifndef M_VECTOR_H__
#define M_VECTOR_H__
#ifdef ESLOPE
#include "m_fixed.h"
#include "tables.h"
#define TWOPI M_PI*2.0
#define HALFPI M_PI*0.5
#define QUARTERPI M_PI*0.25
#define EPSILON 0.000001f
#define OMEGA 10000000.0f
typedef struct
{
fixed_t x, y, z;
} v3fixed_t;
typedef struct
{
fixed_t x, y;
} v2fixed_t;
typedef struct
{
float x, y, z;
} v3float_t;
typedef struct
{
float yaw, pitch, roll;
} angles3d_t;
typedef struct
{
double x, y, z;
} v3double_t;
typedef struct
{
float x, y;
} v2float_t;
v3fixed_t *M_MakeVec3(const v3fixed_t *point1, const v3fixed_t *point2, v3fixed_t *a_o);
v3float_t *M_MakeVec3f(const v3float_t *point1, const v3float_t *point2, v3float_t *a_o);
void M_TranslateVec3(v3fixed_t *vec);
void M_TranslateVec3f(v3float_t *vec);
void M_AddVec3(v3fixed_t *dest, const v3fixed_t *v1, const v3fixed_t *v2);
void M_AddVec3f(v3float_t *dest, const v3float_t *v1, const v3float_t *v2);
void M_SubVec3(v3fixed_t *dest, const v3fixed_t *v1, const v3fixed_t *v2);
void M_SubVec3f(v3float_t *dest, const v3float_t *v1, const v3float_t *v2);
fixed_t M_DotVec3(const v3fixed_t *v1, const v3fixed_t *v2);
float M_DotVec3f(const v3float_t *v1, const v3float_t *v2);
#ifdef SESLOPE
v3double_t *M_MakeVec3d(const v3double_t *point1, const v3double_t *point2, v3double_t *a_o);
double M_DotVec3d(const v3double_t *v1, const v3double_t *v2);
void M_TranslateVec3d(v3double_t *vec);
#endif
void M_CrossProduct3(v3fixed_t *dest, const v3fixed_t *v1, const v3fixed_t *v2);
void M_CrossProduct3f(v3float_t *dest, const v3float_t *v1, const v3float_t *v2);
fixed_t FV_Magnitude(const v3fixed_t *a_normal);
float FV_Magnitudef(const v3float_t *a_normal);
fixed_t FV_NormalizeO(const v3fixed_t *a_normal, v3fixed_t *a_o);
float FV_NormalizeOf(const v3float_t *a_normal, v3float_t *a_o);
fixed_t FV_Normalize(v3fixed_t *a_normal);
fixed_t FV_Normalizef(v3float_t *a_normal);
void FV_Normal(const v3fixed_t *a_triangle, v3fixed_t *a_normal);
void FV_Normalf(const v3float_t *a_triangle, v3float_t *a_normal);
v3fixed_t *M_LoadVec(v3fixed_t *vec, fixed_t x, fixed_t y, fixed_t z);
v3fixed_t *M_CopyVec(v3fixed_t *a_o, const v3fixed_t *a_i);
v3float_t *M_LoadVecf(v3float_t *vec, float x, float y, float z);
v3float_t *M_CopyVecf(v3float_t *a_o, const v3float_t *a_i);
v3fixed_t *FV_Midpoint(const v3fixed_t *a_1, const v3fixed_t *a_2, v3fixed_t *a_o);
fixed_t FV_Distance(const v3fixed_t *p1, const v3fixed_t *p2);
v3float_t *FV_Midpointf(const v3float_t *a_1, const v3float_t *a_2, v3float_t *a_o);
angle_t FV_AngleBetweenVectors(const v3fixed_t *Vector1, const v3fixed_t *Vector2);
float FV_AngleBetweenVectorsf(const v3float_t *Vector1, const v3float_t *Vector2);
float FV_Distancef(const v3float_t *p1, const v3float_t *p2);
// Kalaron: something crazy, vector physics
float M_VectorYaw(v3float_t v);
float M_VectorPitch(v3float_t v);
angles3d_t *M_VectorAlignTo(float Pitch, float Yaw, float Roll, v3float_t v, byte AngleAxis, float Rate);
#endif
// EOF
#endif // #ifdef ESLOPE
......@@ -28,6 +28,10 @@
#include "hardware/hw3sound.h"
#endif
#ifdef ESLOPE
#include "p_slopes.h"
#endif
#ifdef HAVE_BLUA
boolean LUA_CallAction(const char *action, mobj_t *actor);
#endif
......@@ -5614,8 +5618,17 @@ void A_MixUp(mobj_t *actor)
P_SetThingPosition(players[i].mo);
#ifdef ESLOPE
players[i].mo->floorz = (players[i].mo->subsector->sector->f_slope ?
P_GetZAt(players[i].mo->subsector->sector->f_slope, players[i].mo->x, players[i].mo->y) :
players[i].mo->subsector->sector->floorheight);
players[i].mo->ceilingz = (players[i].mo->subsector->sector->c_slope ?
P_GetZAt(players[i].mo->subsector->sector->c_slope, players[i].mo->x, players[i].mo->y) :
players[i].mo->subsector->sector->ceilingheight);
#else
players[i].mo->floorz = players[i].mo->subsector->sector->floorheight;
players[i].mo->ceilingz = players[i].mo->subsector->sector->ceilingheight;
#endif
P_CheckPosition(players[i].mo, players[i].mo->x, players[i].mo->y);
}
......
......@@ -19,6 +19,9 @@
#include "z_zone.h"
#include "g_game.h"
#include "r_main.h"
#ifdef ESLOPE
#include "p_slopes.h"
#endif
// ==========================================================================
// FLOORS
......@@ -1174,12 +1177,18 @@ void T_SpikeSector(levelspecthink_t *spikes)
if (affectsec == spikes->sector) // Applied to an actual sector
{
fixed_t affectpoint = affectsec->floorheight;
#ifdef ESLOPE
if (affectsec->f_slope)
affectpoint = P_GetZAt(affectsec->f_slope, thing->x, thing->y);
#endif
if (affectsec->flags & SF_FLIPSPECIAL_FLOOR)
{
if (!(thing->eflags & MFE_VERTICALFLIP) && thing->momz > 0)
continue;
if (thing->z == affectsec->floorheight)
if (thing->z == affectpoint)
dothepain = true;
}
......
......@@ -50,6 +50,15 @@
// above this, a height difference is considered as a 'dropoff'
#define MAXSTEPMOVE (24*FRACUNIT)
#ifdef ESLOPE
// [RH] Minimum floorplane.c value for walking
// The lower the value, the steeper the slope is
#define SECPLANESTEEPSLOPE 46000
// ESLOPE stuff - a slope of 4 or lower is so level, treat it as flat
#define LEVELSLOPE 4
#define STEEPSLOPE 65
#endif
#define USERANGE (64*FRACUNIT)
#define MELEERANGE (64*FRACUNIT)
#define MISSILERANGE (32*64*FRACUNIT)
......@@ -135,6 +144,12 @@ boolean P_IsObjectOnGroundIn(mobj_t *mo, sector_t *sec);
boolean P_InSpaceSector(mobj_t *mo);
boolean P_InQuicksand(mobj_t *mo);
#ifdef ESLOPE
boolean P_IsObjectOnSlope(mobj_t *mo, boolean ceiling);
boolean P_SlopeGreaterThan(mobj_t *mo, boolean ceiling, int value);
boolean P_SlopeLessThan(mobj_t *mo, boolean ceiling, int value);
#endif
void P_SetObjectMomZ(mobj_t *mo, fixed_t value, boolean relative);
void P_RestoreMusic(player_t *player);
void P_SpawnShieldOrb(player_t *player);
......
......@@ -31,6 +31,9 @@
#include "i_video.h"
#include "lua_hook.h"
#include "b_bot.h"
#ifdef ESLOPE
#include "p_slopes.h"
#endif
// protos.
static CV_PossibleValue_t viewheight_cons_t[] = {{16, "MIN"}, {56, "MAX"}, {0, NULL}};
......@@ -700,15 +703,75 @@ boolean P_InsideANonSolidFFloor(mobj_t *mobj, ffloor_t *rover)
|| ((rover->flags & FF_BLOCKOTHERS) && !mobj->player)))
return false;
if (mobj->z > *rover->topheight)
fixed_t topheight = *rover->topheight;
fixed_t bottomheight = *rover->bottomheight;
/*#ifdef ESLOPE
if (rover->t_slope)
topheight = P_GetZAt(rover->t_slope, mobj->x, mobj->y);
if (rover->b_slope)
bottomheight = P_GetZAt(rover->b_slope, mobj->x, mobj->y);
#endif*/
if (mobj->z > topheight)
return false;
if (mobj->z + mobj->height < *rover->bottomheight)
if (mobj->z + mobj->height < bottomheight)
return false;
return true;
}
fixed_t P_GetMobjZAtSecF(mobj_t *mobj, sector_t *sector) // SRB2CBTODO: This needs to be over all the code
{
I_Assert(mobj != NULL);
#ifdef ESLOPE
if (sector->f_slope)
return P_GetZAt(sector->f_slope, mobj->x, mobj->y);
else
#endif
return sector->floorheight;
}
fixed_t P_GetMobjZAtF(mobj_t *mobj) // SRB2CBTODO: This needs to be over all the code
{
I_Assert(mobj != NULL);
sector_t *sector;
sector = R_PointInSubsector(mobj->x, mobj->y)->sector;
#ifdef ESLOPE
if (sector->f_slope)
return P_GetZAt(sector->f_slope, mobj->x, mobj->y);
else
#endif
return sector->floorheight;
}
fixed_t P_GetMobjZAtSecC(mobj_t *mobj, sector_t *sector) // SRB2CBTODO: This needs to be over all the code
{
I_Assert(mobj != NULL);
#ifdef ESLOPE
if (sector->c_slope)
return P_GetZAt(sector->c_slope, mobj->x, mobj->y);
else
#endif
return sector->ceilingheight;
}
fixed_t P_GetMobjZAtC(mobj_t *mobj) // SRB2CBTODO: This needs to be over all the code
{
I_Assert(mobj != NULL);
sector_t *sector;
sector = R_PointInSubsector(mobj->x, mobj->y)->sector;
#ifdef ESLOPE
if (sector->c_slope)
return P_GetZAt(sector->c_slope, mobj->x, mobj->y);
else
#endif
return sector->ceilingheight;
}
static void P_PlayerFlip(mobj_t *mo)
{
if (!mo->player)
......@@ -2455,6 +2518,11 @@ void P_MobjCheckWater(mobj_t *mobj)
// Default if no water exists.
mobj->watertop = mobj->waterbottom = mobj->subsector->sector->floorheight - 1000*FRACUNIT;
#ifdef ESLOPE // Set the correct waterbottom/top to be below the lowest point of the slope
if (mobj->subsector->sector->f_slope)
mobj->watertop = mobj->waterbottom = mobj->subsector->sector->f_slope->lowz - 1000*FRACUNIT;
#endif
// Reset water state.
mobj->eflags &= ~(MFE_UNDERWATER|MFE_TOUCHWATER|MFE_GOOWATER);
......@@ -2465,34 +2533,45 @@ void P_MobjCheckWater(mobj_t *mobj)
|| ((rover->flags & FF_BLOCKOTHERS) && !mobj->player)))
continue;
fixed_t topheight = *rover->topheight;
fixed_t bottomheight = *rover->bottomheight;
/*#ifdef ESLOPE
if (rover->t_slope)
topheight = P_GetZAt(rover->t_slope, mobj->x, mobj->y);
if (rover->b_slope)
bottomheight = P_GetZAt(rover->b_slope, mobj->x, mobj->y);
#endif*/
if (mobj->eflags & MFE_VERTICALFLIP)
{
if (*rover->topheight < (thingtop - FixedMul(mobj->info->height/2, mobj->scale))
|| *rover->bottomheight > thingtop)
if (topheight < (thingtop - FixedMul(mobj->info->height/2, mobj->scale))
|| bottomheight > thingtop)
continue;
}
else
{
if (*rover->topheight < mobj->z
|| *rover->bottomheight > (mobj->z + FixedMul(mobj->info->height/2, mobj->scale)))
if (topheight < mobj->z
|| bottomheight > (mobj->z + FixedMul(mobj->info->height/2, mobj->scale)))
continue;
}
// Set the watertop and waterbottom
mobj->watertop = *rover->topheight;
mobj->waterbottom = *rover->bottomheight;
mobj->watertop = topheight;
mobj->waterbottom = bottomheight;
// Just touching the water?
if (((mobj->eflags & MFE_VERTICALFLIP) && thingtop - FixedMul(mobj->info->height, mobj->scale) < *rover->bottomheight)
|| (!(mobj->eflags & MFE_VERTICALFLIP) && mobj->z + FixedMul(mobj->info->height, mobj->scale) > *rover->topheight))
if (((mobj->eflags & MFE_VERTICALFLIP) && thingtop - FixedMul(mobj->info->height, mobj->scale) < bottomheight)
|| (!(mobj->eflags & MFE_VERTICALFLIP) && mobj->z + FixedMul(mobj->info->height, mobj->scale) > topheight))
{
mobj->eflags |= MFE_TOUCHWATER;
if (rover->flags & FF_GOOWATER && !(mobj->flags & MF_NOGRAVITY))
mobj->eflags |= MFE_GOOWATER;
}
// Actually in the water?
if (((mobj->eflags & MFE_VERTICALFLIP) && thingtop - FixedMul(mobj->info->height/2, mobj->scale) > *rover->bottomheight)
|| (!(mobj->eflags & MFE_VERTICALFLIP) && mobj->z + FixedMul(mobj->info->height/2, mobj->scale) < *rover->topheight))
if (((mobj->eflags & MFE_VERTICALFLIP) && thingtop - FixedMul(mobj->info->height/2, mobj->scale) > bottomheight)
|| (!(mobj->eflags & MFE_VERTICALFLIP) && mobj->z + FixedMul(mobj->info->height/2, mobj->scale) < topheight))
{
mobj->eflags |= MFE_UNDERWATER;
if (rover->flags & FF_GOOWATER && !(mobj->flags & MF_NOGRAVITY))
......
......@@ -28,6 +28,11 @@
// Needs precompiled tables/data structures.
#include "info.h"
// For slope code, we need v3float_t
#ifdef ESLOPE
#include "m_vector.h"
#endif
//
// NOTES: mobj_t
//
......@@ -349,6 +354,11 @@ typedef struct mobj_s
INT32 cusval;
INT32 cvmem;
#ifdef ESLOPE
angle_t pitchangle;
v3float_t vector;
#endif
// WARNING: New fields must be added separately to savegame and Lua.
} mobj_t;
......
This diff is collapsed. Click to expand it.
// Emacs style mode select -*- C++ -*-
//-----------------------------------------------------------------------------
//
// Copyright(C) 2004 Stephen McGranahan
//
// This program is free software; you can redistribute it and/or modify
// it under the terms of the GNU General Public License as published by
// the Free Software Foundation; either version 2 of the License, or
// (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
//
//--------------------------------------------------------------------------
//
// DESCRIPTION:
// Slopes
// SoM created 05/10/09
//
//-----------------------------------------------------------------------------
#ifndef P_SLOPES_H__
#define P_SLOPES_H__
#ifdef ESLOPE
// P_MakeLineNormal
// Calculates a 2D normal for the given line and stores it in the line
void P_MakeLineNormal(line_t *line);
// P_SpawnSlope_Line
// Creates one or more slopes based on the given line type and front/back
// sectors.
void P_SpawnSlope_Line(int linenum);
// Loads just map objects that make slopes,
// terrain affecting objects have to be spawned first
void P_SetSlopesFromVertexHeights(lumpnum_t lumpnum);
typedef enum
{
THING_SlopeFloorPointLine = 9500,
THING_SlopeCeilingPointLine = 9501,
THING_SetFloorSlope = 9502,
THING_SetCeilingSlope = 9503,
THING_CopyFloorPlane = 9510,
THING_CopyCeilingPlane = 9511,
THING_VavoomFloor=1500,
THING_VavoomCeiling=1501,
THING_VertexFloorZ=1504,
THING_VertexCeilingZ=1505,
} slopething_e;
//
// P_CopySectorSlope
//
// Searches through tagged sectors and copies
//
void P_CopySectorSlope(line_t *line);
// Returns the height of the sloped plane at (x, y) as a fixed_t
fixed_t P_GetZAt(pslope_t *slope, fixed_t x, fixed_t y);
// Returns the height of the sloped plane at (x, y) as a float
float P_GetZAtf(pslope_t *slope, float x, float y);
// Returns the distance of the given point from the given origin and normal.
float P_DistFromPlanef(const v3float_t *point, const v3float_t *pori,
const v3float_t *pnormal);
#endif
// EOF
#endif // #ifdef ESLOPE
......@@ -33,6 +33,9 @@
#include "m_misc.h"
#include "m_cond.h" //unlock triggers
#include "lua_hook.h" // LUAh_LinedefExecute
#ifdef ESLOPE
#include "p_slopes.h"
#endif
#ifdef HW3SOUND
#include "hardware/hw3sound.h"
......@@ -4579,16 +4582,27 @@ static void P_RunSpecialSectorCheck(player_t *player, sector_t *sector)
return;
}
fixed_t f_affectpoint = sector->floorheight;
fixed_t c_affectpoint = sector->ceilingheight;
#ifdef ESLOPE
if (sector->f_slope)
f_affectpoint = P_GetZAt(sector->f_slope, player->mo->x, player->mo->y);
if (sector->c_slope)
c_affectpoint = P_GetZAt(sector->c_slope, player->mo->x, player->mo->y);
#endif
// Only go further if on the ground
if ((sector->flags & SF_FLIPSPECIAL_FLOOR) && !(sector->flags & SF_FLIPSPECIAL_CEILING) && player->mo->z != sector->floorheight)
if ((sector->flags & SF_FLIPSPECIAL_FLOOR) && !(sector->flags & SF_FLIPSPECIAL_CEILING) && player->mo->z != f_affectpoint)
return;
if ((sector->flags & SF_FLIPSPECIAL_CEILING) && !(sector->flags & SF_FLIPSPECIAL_FLOOR) && player->mo->z + player->mo->height != sector->ceilingheight)
if ((sector->flags & SF_FLIPSPECIAL_CEILING) && !(sector->flags & SF_FLIPSPECIAL_FLOOR) && player->mo->z + player->mo->height != c_affectpoint)
return;
if ((sector->flags & SF_FLIPSPECIAL_BOTH)
&& player->mo->z != sector->floorheight
&& player->mo->z + player->mo->height != sector->ceilingheight)
&& player->mo->z != f_affectpoint
&& player->mo->z + player->mo->height != c_affectpoint)
return;
P_ProcessSpecialSector(player, sector, NULL);
......@@ -4749,6 +4763,9 @@ void P_UpdateSpecials(void)
// POINT LIMIT
P_CheckPointLimit();
// Kalaron: ...We...have dynamic slopes *YESSSS*
P_SpawnDeferredSpecials();
// ANIMATE TEXTURES
for (anim = anims; anim < lastanim; anim++)
{
......@@ -6500,6 +6517,63 @@ void P_SpawnSpecials(INT32 fromnetsave)
P_RunLevelLoadExecutors();
}
#ifdef ESLOPE
//
// P_SpawnDeferredSpecials
//
// SoM: Specials that copy slopes, ect., need to be collected in a separate
// pass
// NOTE: SRB2CBTODO: A new function, P_SpawnDeferredSpecials is needed if objects
// are to be needed in this function, because this function currently needs to be
// done before 'things' are loaded, because slopes are part of this function,
// and slope height adjustments are needed for spawning objects
void P_SpawnDeferredSpecials(void)
{
size_t i;
line_t *line;
for(i = 0; i < numlines; i++)
{
line = lines + i;
switch(line->special)
{
// Slopes, Eternity engine
/*{ 386, "Slope_FrontsectorFloor" },
{ 387, "Slope_FrontsectorCeiling" },
{ 388, "Slope_FrontsectorFloorAndCeiling" },
{ 389, "Slope_BacksectorFloor" },
{ 390, "Slope_BacksectorCeiling" },
{ 391, "Slope_BacksectorFloorAndCeiling" },
{ 392, "Slope_BackFloorAndFrontCeiling" },
{ 393, "Slope_BackCeilingAndFrontFloor" },
{ 394, "Slope_FrontFloorToTaggedSlope" },
{ 395, "Slope_FrontCeilingToTaggedSlope" },
{ 396, "Slope_FrontFloorAndCeilingToTaggedSlope" },*/
// SoM 05/10/09: Slopes // SRB2CBTODO:!
case 386:
case 387:
case 388:
case 389:
case 390:
case 391:
case 392:
case 393:
P_SpawnSlope_Line(i);
break;
// SoM: Copy slopes
case 394:
case 395:
case 396:
P_CopySectorSlope(line);
break;
}
}
}
#endif
/** Adds 3Dfloors as appropriate based on a common control linedef.
*
* \param line Control linedef to use.
......@@ -7399,8 +7473,12 @@ void T_Pusher(pusher_t *p)
|| GETSECSPECIAL(referrer->special, 3) == 3)
foundfloor = true;
}
else if (!(GETSECSPECIAL(sec->special, 3) == 2
|| GETSECSPECIAL(sec->special, 3) == 3))
else if (
#ifdef ESLOPE
(!sec->f_slope) &&
#endif
(!(GETSECSPECIAL(sec->special, 3) == 2
|| GETSECSPECIAL(sec->special, 3) == 3)))
return;
if (p->roverpusher && foundfloor == false) // Not even a 3d floor has the PUSH_MASK.
......
......@@ -36,6 +36,11 @@ void P_SpawnSpecials(INT32 fromnetsave);
// every tic
void P_UpdateSpecials(void);
#ifdef ESLOPE
void P_SpawnDeferredSpecials(void);
#endif
sector_t *P_PlayerTouchingSectorSpecial(player_t *player, INT32 section, INT32 number);
void P_PlayerInSpecialSector(player_t *player);
void P_ProcessSpecialSector(player_t *player, sector_t *sector, sector_t *roversector);
......
......@@ -1201,6 +1201,87 @@ boolean P_IsObjectOnGround(mobj_t *mo)
return false;
}
#ifdef ESLOPE
//
// P_IsObjectOnSlope
//
// Returns true if the player is
// on a slope. Takes reverse
// gravity into account.
//
boolean P_IsObjectOnSlope(mobj_t *mo, boolean ceiling)
{
if (ceiling && (mo->eflags & MFE_VERTICALFLIP))
{
if ((mo->z + mo->height >= mo->ceilingz) && mo->subsector->sector->c_slope) // SRB2CBTODO: allow being on underside of mobj too?
return true;
}
else
{
if (mo->z <= mo->floorz && mo->subsector->sector->f_slope)
return true;
}
return false;
}
//
// P_SlopeGreaterThan
//
// Returns true if the object is on a slope
// that has an angle greater than the value
//
boolean P_SlopeGreaterThan(mobj_t *mo, boolean ceiling, int value)
{
if (ceiling && (mo->eflags & MFE_VERTICALFLIP))
{
if ((mo->z + mo->height >= mo->ceilingz) && mo->subsector->sector->c_slope)
{
if (value < mo->subsector->sector->c_slope->zangle)
return true;
}
}
else
{
if (mo->z <= mo->floorz && mo->subsector->sector->f_slope)
{