mirror of
https://github.com/ZDoom/gzdoom-gles.git
synced 2025-01-18 14:41:40 +00:00
Merge branch 'floatcvt'
This commit is contained in:
commit
1a5a00a76e
314 changed files with 14459 additions and 13379 deletions
|
@ -164,7 +164,7 @@ if( MSVC )
|
|||
string(REPLACE " /GR" " " CMAKE_CXX_FLAGS ${CMAKE_CXX_FLAGS} )
|
||||
else()
|
||||
set( REL_LINKER_FLAGS "" )
|
||||
set( ALL_C_FLAGS "" )
|
||||
set( ALL_C_FLAGS "-ffp-contract=off" )
|
||||
set( REL_C_FLAGS "" )
|
||||
set( DEB_C_FLAGS "" )
|
||||
|
||||
|
|
|
@ -1159,6 +1159,22 @@ add_executable( zdoom WIN32 MACOSX_BUNDLE
|
|||
g_shared/sbar_mugshot.cpp
|
||||
g_shared/shared_hud.cpp
|
||||
g_shared/shared_sbar.cpp
|
||||
math/asin.c
|
||||
math/atan.c
|
||||
math/const.c
|
||||
math/cosh.c
|
||||
math/exp.c
|
||||
math/isnan.c
|
||||
math/log.c
|
||||
math/log10.c
|
||||
math/mtherr.c
|
||||
math/polevl.c
|
||||
math/sin.c
|
||||
math/sinh.c
|
||||
math/sqrt.c
|
||||
math/tan.c
|
||||
math/tanh.c
|
||||
math/fastsin.cpp
|
||||
resourcefiles/ancientzip.cpp
|
||||
resourcefiles/file_7z.cpp
|
||||
resourcefiles/file_grp.cpp
|
||||
|
@ -1355,6 +1371,7 @@ source_group("Games\\Hexen Game" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR
|
|||
source_group("Games\\Raven Shared" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/g_raven/.+")
|
||||
source_group("Games\\Strife Game" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/g_strife/.+")
|
||||
source_group("Intermission" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/intermission/.+")
|
||||
source_group("Math" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/math/.+")
|
||||
source_group("Menu" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/menu/.+")
|
||||
source_group("Render Core\\Render Headers" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/r_.+\\.h$")
|
||||
source_group("Render Core\\Render Sources" REGULAR_EXPRESSION "^${CMAKE_CURRENT_SOURCE_DIR}/r_.+\\.cpp$")
|
||||
|
|
513
src/actor.h
513
src/actor.h
|
@ -25,6 +25,7 @@
|
|||
|
||||
// Basics.
|
||||
#include "tables.h"
|
||||
#include "templates.h"
|
||||
|
||||
// We need the thinker_t stuff.
|
||||
#include "dthinker.h"
|
||||
|
@ -414,24 +415,12 @@ enum ActorRenderFlag
|
|||
RF_FORCEXYBILLBOARD = 0x20000, // [BB] OpenGL only: draw with xy axis billboard, i.e. unanchored (overrides gl_billboard_mode setting)
|
||||
};
|
||||
|
||||
#define TRANSLUC25 (FRACUNIT/4)
|
||||
#define TRANSLUC33 (FRACUNIT/3)
|
||||
#define TRANSLUC50 (FRACUNIT/2)
|
||||
#define TRANSLUC66 ((FRACUNIT*2)/3)
|
||||
#define TRANSLUC75 ((FRACUNIT*3)/4)
|
||||
|
||||
// <wingdi.h> also #defines OPAQUE
|
||||
#ifndef OPAQUE
|
||||
#define OPAQUE (FRACUNIT)
|
||||
#endif
|
||||
|
||||
// This translucency value produces the closest match to Heretic's TINTTAB.
|
||||
// ~40% of the value of the overlaid image shows through.
|
||||
#define HR_SHADOW (0x6800)
|
||||
|
||||
const double HR_SHADOW = (0x6800 / 65536.);
|
||||
// Hexen's TINTTAB is the same as Heretic's, just reversed.
|
||||
#define HX_SHADOW (0x9800)
|
||||
#define HX_ALTSHADOW (0x6800)
|
||||
const double HX_SHADOW = (0x9800 / 65536.);
|
||||
const double HX_ALTSHADOW = (0x6800 / 65536.);
|
||||
|
||||
// This could easily be a bool but then it'd be much harder to find later. ;)
|
||||
enum replace_t
|
||||
|
@ -533,6 +522,10 @@ enum EThingSpecialActivationType
|
|||
THINGSPEC_Switch = 1<<10, // The thing is alternatively activated and deactivated when triggered
|
||||
};
|
||||
|
||||
#define ONFLOORZ FIXED_MIN
|
||||
#define ONCEILINGZ FIXED_MAX
|
||||
#define FLOATRANDZ (FIXED_MAX-1)
|
||||
|
||||
|
||||
class FDecalBase;
|
||||
class AInventory;
|
||||
|
@ -568,9 +561,7 @@ public:
|
|||
int Amount;
|
||||
};
|
||||
|
||||
fixed_t P_AproxDistance (fixed_t dx, fixed_t dy); // since we cannot include p_local here...
|
||||
angle_t R_PointToAngle2 (fixed_t x1, fixed_t y1, fixed_t x2, fixed_t y2); // same reason here with r_defs.h
|
||||
|
||||
const double MinVel = EQUAL_EPSILON;
|
||||
|
||||
// Map Object definition.
|
||||
class AActor : public DThinker
|
||||
|
@ -586,7 +577,7 @@ public:
|
|||
|
||||
void Serialize (FArchive &arc);
|
||||
|
||||
static AActor *StaticSpawn (PClassActor *type, fixed_t x, fixed_t y, fixed_t z, replace_t allowreplacement, bool SpawningMapThing = false);
|
||||
static AActor *StaticSpawn (PClassActor *type, const DVector3 &pos, replace_t allowreplacement, bool SpawningMapThing = false);
|
||||
|
||||
inline AActor *GetDefault () const
|
||||
{
|
||||
|
@ -596,11 +587,11 @@ public:
|
|||
DDropItem *GetDropItems() const;
|
||||
|
||||
// Return true if the monster should use a missile attack, false for melee
|
||||
bool SuggestMissileAttack (fixed_t dist);
|
||||
bool SuggestMissileAttack (double dist);
|
||||
|
||||
// Adjusts the angle for deflection/reflection of incoming missiles
|
||||
// Returns true if the missile should be allowed to explode anyway
|
||||
bool AdjustReflectionAngle (AActor *thing, angle_t &angle);
|
||||
bool AdjustReflectionAngle (AActor *thing, DAngle &angle);
|
||||
|
||||
// Returns true if this actor is within melee range of its target
|
||||
bool CheckMeleeRange();
|
||||
|
@ -644,7 +635,7 @@ public:
|
|||
|
||||
// Called when an actor is to be reflected by a disc of repulsion.
|
||||
// Returns true to continue normal blast processing.
|
||||
virtual bool SpecialBlastHandling (AActor *source, fixed_t strength);
|
||||
virtual bool SpecialBlastHandling (AActor *source, double strength);
|
||||
|
||||
// Called by RoughBlockCheck
|
||||
bool IsOkayToAttack (AActor *target);
|
||||
|
@ -743,18 +734,18 @@ public:
|
|||
|
||||
inline bool IsNoClip2() const;
|
||||
void CheckPortalTransition(bool islinked);
|
||||
fixedvec3 GetPortalTransition(fixed_t byoffset, sector_t **pSec = NULL);
|
||||
DVector3 GetPortalTransition(double byoffset, sector_t **pSec = NULL);
|
||||
|
||||
// What species am I?
|
||||
virtual FName GetSpecies();
|
||||
|
||||
fixed_t GetBobOffset(fixed_t ticfrac=0) const
|
||||
double GetBobOffset(double ticfrac = 0) const
|
||||
{
|
||||
if (!(flags2 & MF2_FLOATBOB))
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
return finesine[MulScale22(((FloatBobPhase + level.maptime) << FRACBITS) + ticfrac, FINEANGLES) & FINEMASK] * 8;
|
||||
if (!(flags2 & MF2_FLOATBOB))
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
return BobSin(FloatBobPhase + level.maptime + ticfrac);
|
||||
}
|
||||
|
||||
// Enter the crash state
|
||||
|
@ -763,7 +754,7 @@ public:
|
|||
// Return starting health adjusted by skill level
|
||||
int SpawnHealth() const;
|
||||
int GetGibHealth() const;
|
||||
fixed_t GetCameraHeight() const;
|
||||
double GetCameraHeight() const;
|
||||
|
||||
inline bool isMissile(bool precise=true)
|
||||
{
|
||||
|
@ -782,9 +773,9 @@ public:
|
|||
}
|
||||
|
||||
// These also set CF_INTERPVIEW for players.
|
||||
void SetPitch(int p, bool interpolate, bool forceclamp = false);
|
||||
void SetAngle(angle_t ang, bool interpolate);
|
||||
void SetRoll(angle_t roll, bool interpolate);
|
||||
void SetPitch(DAngle p, bool interpolate, bool forceclamp = false);
|
||||
void SetAngle(DAngle ang, bool interpolate);
|
||||
void SetRoll(DAngle roll, bool interpolate);
|
||||
|
||||
PClassActor *GetBloodType(int type = 0) const
|
||||
{
|
||||
|
@ -813,142 +804,137 @@ public:
|
|||
return bloodcls;
|
||||
}
|
||||
|
||||
fixed_t AproxDistance(fixed_t otherx, fixed_t othery)
|
||||
double Distance2D(AActor *other, bool absolute = false)
|
||||
{
|
||||
return P_AproxDistance(X() - otherx, Y() - othery);
|
||||
DVector2 otherpos = absolute ? other->Pos() : other->PosRelative(this);
|
||||
return (Pos().XY() - otherpos).Length();
|
||||
}
|
||||
|
||||
fixed_t AngleTo(fixed_t otherx, fixed_t othery)
|
||||
double Distance2D(double x, double y) const
|
||||
{
|
||||
return R_PointToAngle2(X(), Y(), otherx, othery);
|
||||
return DVector2(X() - x, Y() - y).Length();
|
||||
}
|
||||
|
||||
fixed_t AngleTo(fixedvec2 other)
|
||||
double Distance2D(AActor *other, double xadd, double yadd, bool absolute = false)
|
||||
{
|
||||
return R_PointToAngle2(X(), Y(), other.x, other.y);
|
||||
DVector3 otherpos = absolute ? other->Pos() : other->PosRelative(this);
|
||||
return DVector2(X() - otherpos.X + xadd, Y() - otherpos.Y + yadd).Length();
|
||||
}
|
||||
|
||||
// 'absolute' is reserved for a linked portal implementation which needs
|
||||
// to distinguish between portal-aware and portal-unaware distance calculation.
|
||||
fixed_t AproxDistance(AActor *other, bool absolute = false)
|
||||
{
|
||||
fixedvec3 otherpos = absolute ? other->Pos() : other->PosRelative(this);
|
||||
return P_AproxDistance(X() - otherpos.x, Y() - otherpos.y);
|
||||
}
|
||||
|
||||
fixed_t AproxDistance(AActor *other, fixed_t xadd, fixed_t yadd, bool absolute = false)
|
||||
{
|
||||
fixedvec3 otherpos = absolute ? other->Pos() : other->PosRelative(this);
|
||||
return P_AproxDistance(X() - otherpos.x + xadd, Y() - otherpos.y + yadd);
|
||||
}
|
||||
|
||||
fixed_t AproxDistance3D(AActor *other, bool absolute = false)
|
||||
{
|
||||
return P_AproxDistance(AproxDistance(other), Z() - other->Z());
|
||||
}
|
||||
|
||||
// more precise, but slower version, being used in a few places
|
||||
fixed_t Distance2D(AActor *other, bool absolute = false)
|
||||
{
|
||||
fixedvec3 otherpos = absolute ? other->Pos() : other->PosRelative(this);
|
||||
return xs_RoundToInt(DVector2(X() - otherpos.x, Y() - otherpos.y).Length());
|
||||
}
|
||||
|
||||
// a full 3D version of the above
|
||||
fixed_t Distance3D(AActor *other, bool absolute = false)
|
||||
double Distance3D(AActor *other, bool absolute = false)
|
||||
{
|
||||
fixedvec3 otherpos = absolute ? other->Pos() : other->PosRelative(this);
|
||||
return xs_RoundToInt(DVector3(X() - otherpos.x, Y() - otherpos.y, Z() - otherpos.z).Length());
|
||||
DVector3 otherpos = absolute ? other->Pos() : other->PosRelative(this);
|
||||
return (Pos() - otherpos).Length();
|
||||
}
|
||||
|
||||
angle_t AngleTo(AActor *other, bool absolute = false)
|
||||
DAngle AngleTo(AActor *other, bool absolute = false)
|
||||
{
|
||||
fixedvec3 otherpos = absolute ? other->Pos() : other->PosRelative(this);
|
||||
return R_PointToAngle2(X(), Y(), otherpos.x, otherpos.y);
|
||||
DVector2 otherpos = absolute ? other->Pos() : other->PosRelative(this);
|
||||
return VecToAngle(otherpos - Pos().XY());
|
||||
}
|
||||
|
||||
angle_t AngleTo(AActor *other, fixed_t oxofs, fixed_t oyofs, bool absolute = false) const
|
||||
DAngle AngleTo(AActor *other, double oxofs, double oyofs, bool absolute = false) const
|
||||
{
|
||||
return R_PointToAngle2(X(), Y(), other->X() + oxofs, other->Y() + oyofs);
|
||||
DVector2 otherpos = absolute ? other->Pos() : other->PosRelative(this);
|
||||
return VecToAngle(otherpos - Pos() + DVector2(oxofs, oyofs));
|
||||
}
|
||||
|
||||
fixedvec2 Vec2To(AActor *other) const
|
||||
DVector2 Vec2To(AActor *other) const
|
||||
{
|
||||
fixedvec3 otherpos = other->PosRelative(this);
|
||||
fixedvec2 ret = { otherpos.x - X(), otherpos.y - Y() };
|
||||
return ret;
|
||||
return other->PosRelative(this) - Pos();
|
||||
}
|
||||
|
||||
fixedvec3 Vec3To(AActor *other) const
|
||||
DVector3 Vec3To(AActor *other) const
|
||||
{
|
||||
fixedvec3 otherpos = other->PosRelative(this);
|
||||
fixedvec3 ret = { otherpos.x - X(), otherpos.y - Y(), otherpos.z - Z() };
|
||||
return ret;
|
||||
return other->PosRelative(this) - Pos();
|
||||
}
|
||||
|
||||
fixedvec2 Vec2Offset(fixed_t dx, fixed_t dy, bool absolute = false)
|
||||
DVector2 Vec2Offset(double dx, double dy, bool absolute = false)
|
||||
{
|
||||
if (absolute)
|
||||
{
|
||||
fixedvec2 ret = { X() + dx, Y() + dy };
|
||||
return ret;
|
||||
}
|
||||
else return P_GetOffsetPosition(X(), Y(), dx, dy);
|
||||
}
|
||||
|
||||
|
||||
fixedvec2 Vec2Angle(fixed_t length, angle_t angle, bool absolute = false)
|
||||
{
|
||||
if (absolute)
|
||||
{
|
||||
fixedvec2 ret = { X() + FixedMul(length, finecosine[angle >> ANGLETOFINESHIFT]),
|
||||
Y() + FixedMul(length, finesine[angle >> ANGLETOFINESHIFT]) };
|
||||
return ret;
|
||||
}
|
||||
else return P_GetOffsetPosition(X(), Y(), FixedMul(length, finecosine[angle >> ANGLETOFINESHIFT]), FixedMul(length, finesine[angle >> ANGLETOFINESHIFT]));
|
||||
}
|
||||
|
||||
fixedvec3 Vec3Offset(fixed_t dx, fixed_t dy, fixed_t dz, bool absolute = false)
|
||||
{
|
||||
if (absolute)
|
||||
{
|
||||
fixedvec3 ret = { X() + dx, Y() + dy, Z() + dz };
|
||||
return ret;
|
||||
return { X() + dx, Y() + dy };
|
||||
}
|
||||
else
|
||||
{
|
||||
fixedvec2 op = P_GetOffsetPosition(X(), Y(), dx, dy);
|
||||
fixedvec3 pos = { op.x, op.y, Z() + dz };
|
||||
return pos;
|
||||
return P_GetOffsetPosition(X(), Y(), dx, dy);
|
||||
}
|
||||
}
|
||||
|
||||
fixedvec3 Vec3Angle(fixed_t length, angle_t angle, fixed_t dz, bool absolute = false)
|
||||
|
||||
DVector3 Vec2OffsetZ(double dx, double dy, double atz, bool absolute = false)
|
||||
{
|
||||
if (absolute)
|
||||
{
|
||||
fixedvec3 ret = { X() + FixedMul(length, finecosine[angle >> ANGLETOFINESHIFT]),
|
||||
Y() + FixedMul(length, finesine[angle >> ANGLETOFINESHIFT]), Z() + dz };
|
||||
return ret;
|
||||
return{ X() + dx, Y() + dy, atz };
|
||||
}
|
||||
else
|
||||
{
|
||||
fixedvec2 op = P_GetOffsetPosition(X(), Y(), FixedMul(length, finecosine[angle >> ANGLETOFINESHIFT]), FixedMul(length, finesine[angle >> ANGLETOFINESHIFT]));
|
||||
fixedvec3 pos = { op.x, op.y, Z() + dz };
|
||||
return pos;
|
||||
DVector2 v = P_GetOffsetPosition(X(), Y(), dx, dy);
|
||||
return DVector3(v, atz);
|
||||
}
|
||||
}
|
||||
|
||||
DVector2 Vec2Angle(double length, DAngle angle, bool absolute = false)
|
||||
{
|
||||
if (absolute)
|
||||
{
|
||||
return{ X() + length * angle.Cos(), Y() + length * angle.Sin() };
|
||||
}
|
||||
else
|
||||
{
|
||||
return P_GetOffsetPosition(X(), Y(), length*angle.Cos(), length*angle.Sin());
|
||||
}
|
||||
}
|
||||
|
||||
DVector3 Vec3Offset(double dx, double dy, double dz, bool absolute = false)
|
||||
{
|
||||
if (absolute)
|
||||
{
|
||||
return { X() + dx, Y() + dy, Z() + dz };
|
||||
}
|
||||
else
|
||||
{
|
||||
DVector2 v = P_GetOffsetPosition(X(), Y(), dx, dy);
|
||||
return DVector3(v, Z() + dz);
|
||||
}
|
||||
}
|
||||
|
||||
DVector3 Vec3Offset(const DVector3 &ofs, bool absolute = false)
|
||||
{
|
||||
return Vec3Offset(ofs.X, ofs.Y, ofs.Z, absolute);
|
||||
}
|
||||
|
||||
DVector3 Vec3Angle(double length, DAngle angle, double dz, bool absolute = false)
|
||||
{
|
||||
if (absolute)
|
||||
{
|
||||
return{ X() + length * angle.Cos(), Y() + length * angle.Sin(), Z() + dz };
|
||||
}
|
||||
else
|
||||
{
|
||||
DVector2 v = P_GetOffsetPosition(X(), Y(), length*angle.Cos(), length*angle.Sin());
|
||||
return DVector3(v, Z() + dz);
|
||||
}
|
||||
}
|
||||
|
||||
double AccuracyFactor()
|
||||
{
|
||||
return 1. / (1 << (accuracy * 5 / 100));
|
||||
}
|
||||
|
||||
void ClearInterpolation();
|
||||
|
||||
void Move(fixed_t dx, fixed_t dy, fixed_t dz)
|
||||
void Move(const DVector3 &vel)
|
||||
{
|
||||
SetOrigin(X() + dx, Y() + dy, Z() + dz, true);
|
||||
SetOrigin(Pos() + vel, true);
|
||||
}
|
||||
|
||||
void SetOrigin(const fixedvec3 & npos, bool moving)
|
||||
virtual void SetOrigin(double x, double y, double z, bool moving);
|
||||
void SetOrigin(const DVector3 & npos, bool moving)
|
||||
{
|
||||
SetOrigin(npos.x, npos.y, npos.z, moving);
|
||||
SetOrigin(npos.X, npos.Y, npos.Z, moving);
|
||||
}
|
||||
|
||||
inline void SetFriendPlayer(player_t *player);
|
||||
|
@ -960,7 +946,7 @@ public:
|
|||
|
||||
bool CanSeek(AActor *target) const;
|
||||
|
||||
fixed_t GetGravity() const;
|
||||
double GetGravity() const;
|
||||
bool IsSentient() const;
|
||||
const char *GetTag(const char *def = NULL) const;
|
||||
void SetTag(const char *def);
|
||||
|
@ -971,36 +957,39 @@ public:
|
|||
// info for drawing
|
||||
// NOTE: The first member variable *must* be snext.
|
||||
AActor *snext, **sprev; // links in sector (if needed)
|
||||
fixedvec3 __pos; // double underscores so that it won't get used by accident. Access to this should be exclusively through the designated access functions.
|
||||
DVector3 __Pos; // double underscores so that it won't get used by accident. Access to this should be exclusively through the designated access functions.
|
||||
|
||||
DRotator Angles;
|
||||
DVector3 Vel;
|
||||
double Speed;
|
||||
double FloatSpeed;
|
||||
|
||||
angle_t angle;
|
||||
WORD sprite; // used to find patch_t and flip value
|
||||
BYTE frame; // sprite frame to draw
|
||||
fixed_t scaleX, scaleY; // Scaling values; FRACUNIT is normal size
|
||||
DVector2 Scale; // Scaling values; 1 is normal size
|
||||
FRenderStyle RenderStyle; // Style to draw this actor with
|
||||
ActorRenderFlags renderflags; // Different rendering flags
|
||||
FTextureID picnum; // Draw this instead of sprite if valid
|
||||
DWORD effects; // [RH] see p_effect.h
|
||||
fixed_t alpha;
|
||||
double Alpha; // Since P_CheckSight makes an alpha check this can't be a float. It has to be a double.
|
||||
DWORD fillcolor; // Color to draw when STYLE_Shaded
|
||||
|
||||
// interaction info
|
||||
fixed_t pitch;
|
||||
angle_t roll; // This was fixed_t before, which is probably wrong
|
||||
FBlockNode *BlockNode; // links in blocks (if needed)
|
||||
struct sector_t *Sector;
|
||||
subsector_t * subsector;
|
||||
fixed_t floorz, ceilingz; // closest together of contacted secs
|
||||
fixed_t dropoffz; // killough 11/98: the lowest floor over all contacted Sectors.
|
||||
double floorz, ceilingz; // closest together of contacted secs
|
||||
double dropoffz; // killough 11/98: the lowest floor over all contacted Sectors.
|
||||
|
||||
struct sector_t *floorsector;
|
||||
FTextureID floorpic; // contacted sec floorpic
|
||||
int floorterrain;
|
||||
struct sector_t *ceilingsector;
|
||||
FTextureID ceilingpic; // contacted sec ceilingpic
|
||||
fixed_t radius, height; // for movement checking
|
||||
fixed_t projectilepassheight; // height for clipping projectile movement against this actor
|
||||
fixedvec3 vel;
|
||||
double radius, Height; // for movement checking
|
||||
|
||||
double projectilepassheight; // height for clipping projectile movement against this actor
|
||||
|
||||
SDWORD tics; // state tic counter
|
||||
FState *state;
|
||||
VMFunction *Damage; // For missiles and monster railgun
|
||||
|
@ -1018,6 +1007,9 @@ public:
|
|||
|
||||
int special1; // Special info
|
||||
int special2; // Special info
|
||||
double specialf1; // With floats we cannot use the int versions for storing position or angle data without reverting to fixed point (which we do not want.)
|
||||
double specialf2;
|
||||
|
||||
int weaponspecial; // Special info for weapons.
|
||||
int health;
|
||||
BYTE movedir; // 0-7
|
||||
|
@ -1035,7 +1027,7 @@ public:
|
|||
// no matter what (even if shot)
|
||||
player_t *player; // only valid if type of APlayerPawn
|
||||
TObjPtr<AActor> LastLookActor; // Actor last looked for (if TIDtoHate != 0)
|
||||
fixed_t SpawnPoint[3]; // For nightmare respawn
|
||||
DVector3 SpawnPoint; // For nightmare respawn
|
||||
WORD SpawnAngle;
|
||||
int StartHealth;
|
||||
BYTE WeaveIndexXY; // Separated from special2 because it's used by globally accessible functions.
|
||||
|
@ -1045,7 +1037,8 @@ public:
|
|||
FNameNoInit Species; // For monster families
|
||||
TObjPtr<AActor> tracer; // Thing being chased/attacked for tracers
|
||||
TObjPtr<AActor> master; // Thing which spawned this one (prevents mutual attacks)
|
||||
fixed_t floorclip; // value to use for floor clipping
|
||||
double Floorclip; // value to use for floor clipping
|
||||
|
||||
int tid; // thing identifier
|
||||
int special; // special
|
||||
int args[5]; // special arguments
|
||||
|
@ -1060,18 +1053,18 @@ public:
|
|||
SBYTE LastLookPlayerNumber;// Player number last looked for (if TIDtoHate == 0)
|
||||
ActorBounceFlags BounceFlags; // which bouncing type?
|
||||
DWORD SpawnFlags; // Increased to DWORD because of Doom 64
|
||||
fixed_t meleerange; // specifies how far a melee attack reaches.
|
||||
fixed_t meleethreshold; // Distance below which a monster doesn't try to shoot missiles anynore
|
||||
double meleerange; // specifies how far a melee attack reaches.
|
||||
double meleethreshold; // Distance below which a monster doesn't try to shoot missiles anynore
|
||||
// but instead tries to come closer for a melee attack.
|
||||
// This is not the same as meleerange
|
||||
fixed_t maxtargetrange; // any target farther away cannot be attacked
|
||||
fixed_t bouncefactor; // Strife's grenades use 50%, Hexen's Flechettes 70.
|
||||
fixed_t wallbouncefactor; // The bounce factor for walls can be different.
|
||||
double maxtargetrange; // any target farther away cannot be attacked
|
||||
double bouncefactor; // Strife's grenades use 50%, Hexen's Flechettes 70.
|
||||
double wallbouncefactor; // The bounce factor for walls can be different.
|
||||
int bouncecount; // Strife's grenades only bounce twice before exploding
|
||||
fixed_t gravity; // [GRB] Gravity factor
|
||||
fixed_t Friction;
|
||||
double Gravity; // [GRB] Gravity factor
|
||||
double Friction;
|
||||
int FastChaseStrafeCount;
|
||||
fixed_t pushfactor;
|
||||
double pushfactor;
|
||||
int lastpush;
|
||||
int activationtype; // How the thing behaves when activated with USESPECIAL or BUMPSPECIAL
|
||||
int lastbump; // Last time the actor was bumped, used to control BUMPSPECIAL
|
||||
|
@ -1115,16 +1108,16 @@ public:
|
|||
FSoundIDNoInit WallBounceSound;
|
||||
FSoundIDNoInit CrushPainSound;
|
||||
|
||||
fixed_t Speed;
|
||||
fixed_t FloatSpeed;
|
||||
fixed_t MaxDropOffHeight, MaxStepHeight;
|
||||
double MaxDropOffHeight;
|
||||
double MaxStepHeight;
|
||||
|
||||
SDWORD Mass;
|
||||
SWORD PainChance;
|
||||
int PainThreshold;
|
||||
FNameNoInit DamageType;
|
||||
FNameNoInit DamageTypeReceived;
|
||||
fixed_t DamageFactor;
|
||||
fixed_t DamageMultiply;
|
||||
double DamageFactor;
|
||||
double DamageMultiply;
|
||||
|
||||
FNameNoInit PainType;
|
||||
FNameNoInit DeathType;
|
||||
|
@ -1147,8 +1140,8 @@ public:
|
|||
FDecalBase *DecalGenerator;
|
||||
|
||||
// [RH] Used to interpolate the view to get >35 FPS
|
||||
fixed_t PrevX, PrevY, PrevZ;
|
||||
angle_t PrevAngle;
|
||||
DVector3 Prev;
|
||||
DRotator PrevAngles;
|
||||
int PrevPortalGroup;
|
||||
|
||||
// ThingIDs
|
||||
|
@ -1156,6 +1149,7 @@ public:
|
|||
void AddToHash ();
|
||||
void RemoveFromHash ();
|
||||
|
||||
|
||||
private:
|
||||
static AActor *TIDHash[128];
|
||||
static inline int TIDHASH (int key) { return key & 127; }
|
||||
|
@ -1170,11 +1164,10 @@ public:
|
|||
void LinkToWorld (bool spawningmapthing=false, sector_t *sector = NULL);
|
||||
void UnlinkFromWorld ();
|
||||
void AdjustFloorClip ();
|
||||
void SetOrigin (fixed_t x, fixed_t y, fixed_t z, bool moving = false);
|
||||
bool InStateSequence(FState * newstate, FState * basestate);
|
||||
int GetTics(FState * newstate);
|
||||
bool SetState (FState *newstate, bool nofunction=false);
|
||||
virtual bool UpdateWaterLevel (fixed_t oldz, bool splash=true);
|
||||
virtual bool UpdateWaterLevel (bool splash=true);
|
||||
bool isFast();
|
||||
bool isSlow();
|
||||
void SetIdle(bool nofunction=false);
|
||||
|
@ -1200,90 +1193,168 @@ public:
|
|||
|
||||
bool HasSpecialDeathStates () const;
|
||||
|
||||
fixed_t X() const
|
||||
double X() const
|
||||
{
|
||||
return __pos.x;
|
||||
return __Pos.X;
|
||||
}
|
||||
fixed_t Y() const
|
||||
double Y() const
|
||||
{
|
||||
return __pos.y;
|
||||
return __Pos.Y;
|
||||
}
|
||||
fixed_t Z() const
|
||||
double Z() const
|
||||
{
|
||||
return __pos.z;
|
||||
return __Pos.Z;
|
||||
}
|
||||
fixedvec3 Pos() const
|
||||
DVector3 Pos() const
|
||||
{
|
||||
return __pos;
|
||||
return __Pos;
|
||||
}
|
||||
// Note: Never compare z directly with a plane height if you want to know if the actor is *on* the plane. Some very minor inaccuracies may creep in. Always use these inline functions!
|
||||
// Comparing with floorz is ok because those values come from the same calculations.
|
||||
bool isAbove(double checkz) const
|
||||
{
|
||||
return Z() > checkz + EQUAL_EPSILON;
|
||||
}
|
||||
bool isBelow(double checkz) const
|
||||
{
|
||||
return Z() < checkz - EQUAL_EPSILON;
|
||||
}
|
||||
bool isAtZ(double checkz) const
|
||||
{
|
||||
return fabs(Z() - checkz) < EQUAL_EPSILON;
|
||||
}
|
||||
|
||||
fixedvec3 PosRelative(int grp) const;
|
||||
fixedvec3 PosRelative(const AActor *other) const;
|
||||
fixedvec3 PosRelative(sector_t *sec) const;
|
||||
fixedvec3 PosRelative(line_t *line) const;
|
||||
DVector3 PosRelative(int grp) const;
|
||||
DVector3 PosRelative(const AActor *other) const;
|
||||
DVector3 PosRelative(sector_t *sec) const;
|
||||
DVector3 PosRelative(line_t *line) const;
|
||||
|
||||
fixed_t SoundX() const
|
||||
FVector3 SoundPos() const
|
||||
{
|
||||
return X();
|
||||
// the sound system switches y and z axes so this function must, too.
|
||||
// fixme: This still needs portal handling
|
||||
return{ float(X()), float(Z()), float(Y()) };
|
||||
}
|
||||
fixed_t SoundY() const
|
||||
DVector3 InterpolatedPosition(double ticFrac) const
|
||||
{
|
||||
return Y();
|
||||
return Prev + (ticFrac * (Pos() - Prev));
|
||||
}
|
||||
fixed_t SoundZ() const
|
||||
DVector3 PosPlusZ(double zadd) const
|
||||
{
|
||||
return Z();
|
||||
return { X(), Y(), Z() + zadd };
|
||||
}
|
||||
fixedvec3 InterpolatedPosition(fixed_t ticFrac) const
|
||||
DVector3 PosAtZ(double zadd) const
|
||||
{
|
||||
fixedvec3 ret;
|
||||
|
||||
ret.x = PrevX + FixedMul (ticFrac, X() - PrevX);
|
||||
ret.y = PrevY + FixedMul (ticFrac, Y() - PrevY);
|
||||
ret.z = PrevZ + FixedMul (ticFrac, Z() - PrevZ);
|
||||
return ret;
|
||||
return{ X(), Y(), zadd };
|
||||
}
|
||||
fixedvec3 PosPlusZ(fixed_t zadd) const
|
||||
double Top() const
|
||||
{
|
||||
fixedvec3 ret = { X(), Y(), Z() + zadd };
|
||||
return ret;
|
||||
return Z() + Height;
|
||||
}
|
||||
fixed_t Top() const
|
||||
double Center() const
|
||||
{
|
||||
return Z() + height;
|
||||
return Z() + Height/2;
|
||||
}
|
||||
void SetZ(fixed_t newz, bool moving = true)
|
||||
void SetZ(double newz, bool moving = true)
|
||||
{
|
||||
__pos.z = newz;
|
||||
__Pos.Z = newz;
|
||||
}
|
||||
void AddZ(fixed_t newz, bool moving = true)
|
||||
void AddZ(double newz, bool moving = true)
|
||||
{
|
||||
__pos.z += newz;
|
||||
__Pos.Z += newz;
|
||||
if (!moving) Prev.Z = Z();
|
||||
}
|
||||
|
||||
// These are not for general use as they do not link the actor into the world!
|
||||
void SetXY(fixed_t xx, fixed_t yy)
|
||||
void SetXY(const DVector2 &npos)
|
||||
{
|
||||
__pos.x = xx;
|
||||
__pos.y = yy;
|
||||
__Pos.X = npos.X;
|
||||
__Pos.Y = npos.Y;
|
||||
}
|
||||
void SetXYZ(fixed_t xx, fixed_t yy, fixed_t zz)
|
||||
void SetXYZ(double xx, double yy, double zz)
|
||||
{
|
||||
__pos.x = xx;
|
||||
__pos.y = yy;
|
||||
__pos.z = zz;
|
||||
__Pos = { xx,yy,zz };
|
||||
}
|
||||
void SetXY(const fixedvec2 &npos)
|
||||
void SetXYZ(const DVector3 &npos)
|
||||
{
|
||||
__pos.x = npos.x;
|
||||
__pos.y = npos.y;
|
||||
__Pos = npos;
|
||||
}
|
||||
void SetXYZ(const fixedvec3 &npos)
|
||||
|
||||
double VelXYToSpeed() const
|
||||
{
|
||||
__pos.x = npos.x;
|
||||
__pos.y = npos.y;
|
||||
__pos.z = npos.z;
|
||||
return DVector2(Vel.X, Vel.Y).Length();
|
||||
}
|
||||
|
||||
double VelToSpeed() const
|
||||
{
|
||||
return Vel.Length();
|
||||
}
|
||||
|
||||
void AngleFromVel()
|
||||
{
|
||||
Angles.Yaw = VecToAngle(Vel.X, Vel.Y);
|
||||
}
|
||||
|
||||
void VelFromAngle()
|
||||
{
|
||||
Vel.X = Speed * Angles.Yaw.Cos();
|
||||
Vel.Y = Speed * Angles.Yaw.Sin();
|
||||
}
|
||||
|
||||
void VelFromAngle(double speed)
|
||||
{
|
||||
Vel.X = speed * Angles.Yaw.Cos();
|
||||
Vel.Y = speed * Angles.Yaw.Sin();
|
||||
}
|
||||
|
||||
void VelFromAngle(DAngle angle, double speed)
|
||||
{
|
||||
Vel.X = speed * angle.Cos();
|
||||
Vel.Y = speed * angle.Sin();
|
||||
}
|
||||
|
||||
void Thrust()
|
||||
{
|
||||
Vel.X += Speed * Angles.Yaw.Cos();
|
||||
Vel.Y += Speed * Angles.Yaw.Sin();
|
||||
}
|
||||
|
||||
void Thrust(double speed)
|
||||
{
|
||||
Vel.X += speed * Angles.Yaw.Cos();
|
||||
Vel.Y += speed * Angles.Yaw.Sin();
|
||||
}
|
||||
|
||||
void Thrust(DAngle angle, double speed)
|
||||
{
|
||||
Vel.X += speed * angle.Cos();
|
||||
Vel.Y += speed * angle.Sin();
|
||||
}
|
||||
|
||||
void Vel3DFromAngle(DAngle angle, DAngle pitch, double speed)
|
||||
{
|
||||
double cospitch = pitch.Cos();
|
||||
Vel.X = speed * cospitch * angle.Cos();
|
||||
Vel.Y = speed * cospitch * angle.Sin();
|
||||
Vel.Z = speed * -pitch.Sin();
|
||||
}
|
||||
|
||||
void Vel3DFromAngle(DAngle pitch, double speed)
|
||||
{
|
||||
double cospitch = pitch.Cos();
|
||||
Vel.X = speed * cospitch * Angles.Yaw.Cos();
|
||||
Vel.Y = speed * cospitch * Angles.Yaw.Sin();
|
||||
Vel.Z = speed * -pitch.Sin();
|
||||
}
|
||||
|
||||
// This is used by many vertical velocity calculations.
|
||||
// Better have it in one place, if something needs to be changed about the formula.
|
||||
double DistanceBySpeed(AActor *dest, double speed)
|
||||
{
|
||||
return MAX(1., Distance2D(dest) / speed);
|
||||
}
|
||||
|
||||
int ApplyDamageFactor(FName damagetype, int damage) const;
|
||||
|
||||
};
|
||||
|
||||
class FActorIterator
|
||||
|
@ -1352,56 +1423,46 @@ public:
|
|||
bool P_IsTIDUsed(int tid);
|
||||
int P_FindUniqueTID(int start_tid, int limit);
|
||||
|
||||
inline AActor *Spawn (PClassActor *type, fixed_t x, fixed_t y, fixed_t z, replace_t allowreplacement)
|
||||
PClassActor *ClassForSpawn(FName classname);
|
||||
|
||||
inline AActor *Spawn(PClassActor *type)
|
||||
{
|
||||
return AActor::StaticSpawn (type, x, y, z, allowreplacement);
|
||||
}
|
||||
inline AActor *Spawn (PClassActor *type, const fixedvec3 &pos, replace_t allowreplacement)
|
||||
{
|
||||
return AActor::StaticSpawn (type, pos.x, pos.y, pos.z, allowreplacement);
|
||||
return AActor::StaticSpawn(type, DVector3(0, 0, 0), NO_REPLACE);
|
||||
}
|
||||
|
||||
AActor *Spawn (const char *type, fixed_t x, fixed_t y, fixed_t z, replace_t allowreplacement);
|
||||
AActor *Spawn (FName classname, fixed_t x, fixed_t y, fixed_t z, replace_t allowreplacement);
|
||||
|
||||
inline AActor *Spawn (const char *type, const fixedvec3 &pos, replace_t allowreplacement)
|
||||
inline AActor *Spawn(PClassActor *type, const DVector3 &pos, replace_t allowreplacement)
|
||||
{
|
||||
return Spawn (type, pos.x, pos.y, pos.z, allowreplacement);
|
||||
return AActor::StaticSpawn(type, pos, allowreplacement);
|
||||
}
|
||||
|
||||
inline AActor *Spawn (FName classname, const fixedvec3 &pos, replace_t allowreplacement)
|
||||
inline AActor *Spawn(FName type)
|
||||
{
|
||||
return Spawn (classname, pos.x, pos.y, pos.z, allowreplacement);
|
||||
return AActor::StaticSpawn(ClassForSpawn(type), DVector3(0, 0, 0), NO_REPLACE);
|
||||
}
|
||||
|
||||
|
||||
template<class T>
|
||||
inline T *Spawn (fixed_t x, fixed_t y, fixed_t z, replace_t allowreplacement)
|
||||
inline AActor *Spawn(FName type, const DVector3 &pos, replace_t allowreplacement)
|
||||
{
|
||||
return static_cast<T *>(AActor::StaticSpawn (RUNTIME_TEMPLATE_CLASS(T), x, y, z, allowreplacement));
|
||||
return AActor::StaticSpawn(ClassForSpawn(type), pos, allowreplacement);
|
||||
}
|
||||
|
||||
template<class T>
|
||||
inline T *Spawn (const fixedvec3 &pos, replace_t allowreplacement)
|
||||
template<class T> inline T *Spawn(const DVector3 &pos, replace_t allowreplacement)
|
||||
{
|
||||
return static_cast<T *>(AActor::StaticSpawn (RUNTIME_TEMPLATE_CLASS(T), pos.x, pos.y, pos.z, allowreplacement));
|
||||
return static_cast<T *>(AActor::StaticSpawn(RUNTIME_TEMPLATE_CLASS(T), pos, allowreplacement));
|
||||
}
|
||||
|
||||
inline fixedvec2 Vec2Angle(fixed_t length, angle_t angle)
|
||||
template<class T> inline T *Spawn() // for inventory items we do not need coordinates and replacement info.
|
||||
{
|
||||
fixedvec2 ret = { FixedMul(length, finecosine[angle >> ANGLETOFINESHIFT]),
|
||||
FixedMul(length, finesine[angle >> ANGLETOFINESHIFT]) };
|
||||
return ret;
|
||||
return static_cast<T *>(AActor::StaticSpawn(RUNTIME_TEMPLATE_CLASS(T), DVector3(0, 0, 0), NO_REPLACE));
|
||||
}
|
||||
|
||||
void PrintMiscActorInfo(AActor * query);
|
||||
AActor *P_LinePickActor(AActor *t1, angle_t angle, fixed_t distance, int pitch, ActorFlags actorMask, DWORD wallMask);
|
||||
AActor *P_LinePickActor(AActor *t1, DAngle angle, double distance, DAngle pitch, ActorFlags actorMask, DWORD wallMask);
|
||||
|
||||
// If we want to make P_AimLineAttack capable of handling arbitrary portals, it needs to pass a lot more info than just the linetarget actor.
|
||||
struct FTranslatedLineTarget
|
||||
{
|
||||
AActor *linetarget;
|
||||
angle_t angleFromSource;
|
||||
DAngle angleFromSource;
|
||||
bool unlinked; // found by a trace that went through an unlinked portal.
|
||||
};
|
||||
|
||||
|
|
516
src/am_map.cpp
516
src/am_map.cpp
File diff suppressed because it is too large
Load diff
|
@ -33,7 +33,7 @@ DBot::DBot ()
|
|||
void DBot::Clear ()
|
||||
{
|
||||
player = NULL;
|
||||
angle = 0;
|
||||
Angle = 0.;
|
||||
dest = NULL;
|
||||
prev = NULL;
|
||||
enemy = NULL;
|
||||
|
@ -52,27 +52,15 @@ void DBot::Clear ()
|
|||
sleft = false;
|
||||
allround = false;
|
||||
increase = false;
|
||||
oldx = 0;
|
||||
oldy = 0;
|
||||
old = { 0, 0 };
|
||||
}
|
||||
|
||||
void DBot::Serialize (FArchive &arc)
|
||||
{
|
||||
Super::Serialize (arc);
|
||||
|
||||
if (SaveVersion < 4515)
|
||||
{
|
||||
angle_t savedyaw;
|
||||
int savedpitch;
|
||||
arc << savedyaw
|
||||
<< savedpitch;
|
||||
}
|
||||
else
|
||||
{
|
||||
arc << player;
|
||||
}
|
||||
|
||||
arc << angle
|
||||
arc << player
|
||||
<< Angle
|
||||
<< dest
|
||||
<< prev
|
||||
<< enemy
|
||||
|
@ -91,8 +79,7 @@ void DBot::Serialize (FArchive &arc)
|
|||
<< sleft
|
||||
<< allround
|
||||
<< increase
|
||||
<< oldx
|
||||
<< oldy;
|
||||
<< old;
|
||||
}
|
||||
|
||||
void DBot::Tick ()
|
||||
|
@ -269,7 +256,7 @@ void InitBotStuff()
|
|||
AWeapon *w = (AWeapon*)GetDefaultByType(cls);
|
||||
if (w != NULL)
|
||||
{
|
||||
w->MoveCombatDist = botinits[i].movecombatdist;
|
||||
w->MoveCombatDist = botinits[i].movecombatdist/65536.;
|
||||
w->WeaponFlags |= botinits[i].weaponflags;
|
||||
w->ProjectileType = PClass::FindActor(botinits[i].projectile);
|
||||
}
|
||||
|
|
38
src/b_bot.h
38
src/b_bot.h
|
@ -31,18 +31,18 @@
|
|||
|
||||
#define BOTFILENAME "bots.cfg"
|
||||
|
||||
#define MAX_TRAVERSE_DIST 100000000 //10 meters, used within b_func.c
|
||||
#define AVOID_DIST 45000000 //Try avoid incoming missiles once they reached this close
|
||||
#define SAFE_SELF_MISDIST (140*FRACUNIT) //Distance from self to target where it's safe to pull a rocket.
|
||||
#define FRIEND_DIST 15000000 //To friend.
|
||||
#define DARK_DIST 5000000 //Distance that bot can see enemies in the dark from.
|
||||
#define MAX_TRAVERSE_DIST (100000000/65536.) //10 meters, used within b_func.c
|
||||
#define AVOID_DIST (45000000/65536.) //Try avoid incoming missiles once they reached this close
|
||||
#define SAFE_SELF_MISDIST (140.) //Distance from self to target where it's safe to pull a rocket.
|
||||
#define FRIEND_DIST (15000000/65536.) //To friend.
|
||||
#define DARK_DIST (5000000/65536.) //Distance that bot can see enemies in the dark from.
|
||||
#define WHATS_DARK 50 //light value thats classed as dark.
|
||||
#define MAX_MONSTER_TARGET_DIST 50000000 //Too high can slow down the performance, see P_mobj.c
|
||||
#define ENEMY_SCAN_FOV (120*ANGLE_1)
|
||||
#define MAX_MONSTER_TARGET_DIST (50000000/65536.) //Too high can slow down the performance, see P_mobj.c
|
||||
#define ENEMY_SCAN_FOV (120.)
|
||||
#define THINGTRYTICK 1000
|
||||
#define MAXMOVEHEIGHT (32*FRACUNIT) //MAXSTEPMOVE but with jumping counted in.
|
||||
#define GETINCOMBAT 35000000 //Max distance to item. if it's due to be icked up in a combat situation.
|
||||
#define SHOOTFOV (60*ANGLE_1)
|
||||
#define MAXMOVEHEIGHT (32) //MAXSTEPMOVE but with jumping counted in.
|
||||
#define GETINCOMBAT (35000000/65536.) //Max distance to item. if it's due to be icked up in a combat situation.
|
||||
#define SHOOTFOV (60.)
|
||||
#define AFTERTICS (2*TICRATE) //Seconds that bot will be alert on an recent enemy. Ie not looking the other way
|
||||
#define MAXROAM (4*TICRATE) //When this time is elapsed the bot will roam after something else.
|
||||
//monster mod
|
||||
|
@ -103,12 +103,13 @@ public:
|
|||
void StartTravel ();
|
||||
void FinishTravel ();
|
||||
bool IsLeader (player_t *player);
|
||||
void SetBodyAt (fixed_t x, fixed_t y, fixed_t z, int hostnum);
|
||||
fixed_t FakeFire (AActor *source, AActor *dest, ticcmd_t *cmd);
|
||||
bool SafeCheckPosition (AActor *actor, fixed_t x, fixed_t y, FCheckPosition &tm);
|
||||
void SetBodyAt (const DVector3 &pos, int hostnum);
|
||||
double FakeFire (AActor *source, AActor *dest, ticcmd_t *cmd);
|
||||
bool SafeCheckPosition (AActor *actor, double x, double y, FCheckPosition &tm);
|
||||
void BotTick(AActor *mo);
|
||||
|
||||
//(b_move.cpp)
|
||||
bool CleanAhead (AActor *thing, fixed_t x, fixed_t y, ticcmd_t *cmd);
|
||||
bool CleanAhead (AActor *thing, double x, double y, ticcmd_t *cmd);
|
||||
bool IsDangerous (sector_t *sec);
|
||||
|
||||
TArray<FString> getspawned; //Array of bots (their names) which should be spawned when starting a game.
|
||||
|
@ -149,10 +150,10 @@ public:
|
|||
void WhatToGet (AActor *item);
|
||||
|
||||
//(b_func.cpp)
|
||||
bool Check_LOS (AActor *to, angle_t vangle);
|
||||
bool Check_LOS (AActor *to, DAngle vangle);
|
||||
|
||||
player_t *player;
|
||||
angle_t angle; // The wanted angle that the bot try to get every tic.
|
||||
DAngle Angle; // The wanted angle that the bot try to get every tic.
|
||||
// (used to get a smooth view movement)
|
||||
TObjPtr<AActor> dest; // Move Destination.
|
||||
TObjPtr<AActor> prev; // Previous move destination.
|
||||
|
@ -183,8 +184,7 @@ public:
|
|||
bool allround;
|
||||
bool increase;
|
||||
|
||||
fixed_t oldx;
|
||||
fixed_t oldy;
|
||||
DVector2 old;
|
||||
|
||||
private:
|
||||
//(b_think.cpp)
|
||||
|
@ -197,7 +197,7 @@ private:
|
|||
void Dofire (ticcmd_t *cmd);
|
||||
AActor *Choose_Mate ();
|
||||
AActor *Find_enemy ();
|
||||
angle_t FireRox (AActor *enemy, ticcmd_t *cmd);
|
||||
DAngle FireRox (AActor *enemy, ticcmd_t *cmd);
|
||||
|
||||
//(b_move.cpp)
|
||||
void Roam (ticcmd_t *cmd);
|
||||
|
|
187
src/b_func.cpp
187
src/b_func.cpp
|
@ -36,30 +36,30 @@ bool DBot::Reachable (AActor *rtarget)
|
|||
|
||||
if ((rtarget->Sector->ceilingplane.ZatPoint (rtarget) -
|
||||
rtarget->Sector->floorplane.ZatPoint (rtarget))
|
||||
< player->mo->height) //Where rtarget is, player->mo can't be.
|
||||
< player->mo->Height) //Where rtarget is, player->mo can't be.
|
||||
return false;
|
||||
|
||||
sector_t *last_s = player->mo->Sector;
|
||||
fixed_t last_z = last_s->floorplane.ZatPoint (player->mo);
|
||||
fixed_t estimated_dist = player->mo->AproxDistance(rtarget);
|
||||
double last_z = last_s->floorplane.ZatPoint (player->mo);
|
||||
double estimated_dist = player->mo->Distance2D(rtarget);
|
||||
bool reachable = true;
|
||||
|
||||
FPathTraverse it(player->mo->X()+player->mo->vel.x, player->mo->Y()+player->mo->vel.y, rtarget->X(), rtarget->Y(), PT_ADDLINES|PT_ADDTHINGS);
|
||||
FPathTraverse it(player->mo->X()+player->mo->Vel.X, player->mo->Y()+player->mo->Vel.Y, rtarget->X(), rtarget->Y(), PT_ADDLINES|PT_ADDTHINGS);
|
||||
intercept_t *in;
|
||||
while ((in = it.Next()))
|
||||
{
|
||||
fixed_t hitx, hity;
|
||||
fixed_t frac;
|
||||
double hitx, hity;
|
||||
double frac;
|
||||
line_t *line;
|
||||
AActor *thing;
|
||||
fixed_t dist;
|
||||
double dist;
|
||||
sector_t *s;
|
||||
|
||||
frac = in->frac - FixedDiv (4*FRACUNIT, MAX_TRAVERSE_DIST);
|
||||
dist = FixedMul (frac, MAX_TRAVERSE_DIST);
|
||||
frac = in->frac - 4 /MAX_TRAVERSE_DIST;
|
||||
dist = frac * MAX_TRAVERSE_DIST;
|
||||
|
||||
hitx = it.Trace().x + FixedMul (player->mo->vel.x, frac);
|
||||
hity = it.Trace().y + FixedMul (player->mo->vel.y, frac);
|
||||
hitx = it.Trace().x + player->mo->Vel.X * frac;
|
||||
hity = it.Trace().y + player->mo->Vel.Y * frac;
|
||||
|
||||
if (in->isaline)
|
||||
{
|
||||
|
@ -73,13 +73,13 @@ bool DBot::Reachable (AActor *rtarget)
|
|||
{
|
||||
//Determine if going to use backsector/frontsector.
|
||||
s = (line->backsector == last_s) ? line->frontsector : line->backsector;
|
||||
fixed_t ceilingheight = s->ceilingplane.ZatPoint (hitx, hity);
|
||||
fixed_t floorheight = s->floorplane.ZatPoint (hitx, hity);
|
||||
double ceilingheight = s->ceilingplane.ZatPoint (hitx, hity);
|
||||
double floorheight = s->floorplane.ZatPoint (hitx, hity);
|
||||
|
||||
if (!bglobal.IsDangerous (s) && //Any nukage/lava?
|
||||
(floorheight <= (last_z+MAXMOVEHEIGHT)
|
||||
&& ((ceilingheight == floorheight && line->special)
|
||||
|| (ceilingheight - floorheight) >= player->mo->height))) //Does it fit?
|
||||
|| (ceilingheight - floorheight) >= player->mo->Height))) //Does it fit?
|
||||
{
|
||||
last_z = floorheight;
|
||||
last_s = s;
|
||||
|
@ -118,16 +118,16 @@ bool DBot::Reachable (AActor *rtarget)
|
|||
//if these conditions are true, the function returns true.
|
||||
//GOOD TO KNOW is that the player's view angle
|
||||
//in doom is 90 degrees infront.
|
||||
bool DBot::Check_LOS (AActor *to, angle_t vangle)
|
||||
bool DBot::Check_LOS (AActor *to, DAngle vangle)
|
||||
{
|
||||
if (!P_CheckSight (player->mo, to, SF_SEEPASTBLOCKEVERYTHING))
|
||||
return false; // out of sight
|
||||
if (vangle == ANGLE_MAX)
|
||||
if (vangle >= 360.)
|
||||
return true;
|
||||
if (vangle == 0)
|
||||
return false; //Looker seems to be blind.
|
||||
|
||||
return absangle(player->mo->AngleTo(to) - player->mo->angle) <= vangle/2;
|
||||
return absangle(player->mo->AngleTo(to), player->mo->Angles.Yaw) <= (vangle/2);
|
||||
}
|
||||
|
||||
//-------------------------------------
|
||||
|
@ -140,9 +140,10 @@ void DBot::Dofire (ticcmd_t *cmd)
|
|||
bool no_fire; //used to prevent bot from pumping rockets into nearby walls.
|
||||
int aiming_penalty=0; //For shooting at shading target, if screen is red, MAKEME: When screen red.
|
||||
int aiming_value; //The final aiming value.
|
||||
fixed_t dist;
|
||||
angle_t an;
|
||||
int m;
|
||||
double Dist;
|
||||
DAngle an;
|
||||
DAngle m;
|
||||
double fm;
|
||||
|
||||
if (!enemy || !(enemy->flags & MF_SHOOTABLE) || enemy->health <= 0)
|
||||
return;
|
||||
|
@ -170,7 +171,7 @@ void DBot::Dofire (ticcmd_t *cmd)
|
|||
|
||||
no_fire = true;
|
||||
//Distance to enemy.
|
||||
dist = player->mo->AproxDistance(enemy, player->mo->vel.x - enemy->vel.x, player->mo->vel.y - enemy->vel.y);
|
||||
Dist = player->mo->Distance2D(enemy, player->mo->Vel.X - enemy->Vel.X, player->mo->Vel.Y - enemy->Vel.Y);
|
||||
|
||||
//FIRE EACH TYPE OF WEAPON DIFFERENT: Here should all the different weapons go.
|
||||
if (player->ReadyWeapon->WeaponFlags & WIF_MELEEWEAPON)
|
||||
|
@ -192,7 +193,7 @@ void DBot::Dofire (ticcmd_t *cmd)
|
|||
else
|
||||
{
|
||||
//*4 is for atmosphere, the chainsaws sounding and all..
|
||||
no_fire = (dist > (MELEERANGE*4));
|
||||
no_fire = (Dist > MELEERANGE*4);
|
||||
}
|
||||
}
|
||||
else if (player->ReadyWeapon->WeaponFlags & WIF_BOT_BFG)
|
||||
|
@ -208,11 +209,11 @@ void DBot::Dofire (ticcmd_t *cmd)
|
|||
{
|
||||
//Special rules for RL
|
||||
an = FireRox (enemy, cmd);
|
||||
if(an)
|
||||
if(an != 0)
|
||||
{
|
||||
angle = an;
|
||||
Angle = an;
|
||||
//have to be somewhat precise. to avoid suicide.
|
||||
if (absangle(angle - player->mo->angle) < 12*ANGLE_1)
|
||||
if (absangle(an, player->mo->Angles.Yaw) < 12.)
|
||||
{
|
||||
t_rocket = 9;
|
||||
no_fire = false;
|
||||
|
@ -221,17 +222,17 @@ void DBot::Dofire (ticcmd_t *cmd)
|
|||
}
|
||||
// prediction aiming
|
||||
shootmissile:
|
||||
dist = player->mo->AproxDistance (enemy);
|
||||
m = dist / GetDefaultByType (player->ReadyWeapon->ProjectileType)->Speed;
|
||||
bglobal.SetBodyAt (enemy->X() + enemy->vel.x*m*2, enemy->Y() + enemy->vel.y*m*2, enemy->Z(), 1);
|
||||
angle = player->mo->AngleTo(bglobal.body1);
|
||||
Dist = player->mo->Distance2D(enemy);
|
||||
fm = Dist / GetDefaultByType (player->ReadyWeapon->ProjectileType)->Speed;
|
||||
bglobal.SetBodyAt(enemy->Pos() + enemy->Vel.XY() * fm * 2, 1);
|
||||
Angle = player->mo->AngleTo(bglobal.body1);
|
||||
if (Check_LOS (enemy, SHOOTFOV))
|
||||
no_fire = false;
|
||||
}
|
||||
else
|
||||
{
|
||||
//Other weapons, mostly instant hit stuff.
|
||||
angle = player->mo->AngleTo(enemy);
|
||||
Angle = player->mo->AngleTo(enemy);
|
||||
aiming_penalty = 0;
|
||||
if (enemy->flags & MF_SHADOW)
|
||||
aiming_penalty += (pr_botdofire()%25)+10;
|
||||
|
@ -244,17 +245,17 @@ shootmissile:
|
|||
aiming_value = 1;
|
||||
m = ((SHOOTFOV/2)-(aiming_value*SHOOTFOV/200)); //Higher skill is more accurate
|
||||
if (m <= 0)
|
||||
m = 1; //Prevents lock.
|
||||
m = 1.; //Prevents lock.
|
||||
|
||||
if (m)
|
||||
if (m != 0)
|
||||
{
|
||||
if (increase)
|
||||
angle += m;
|
||||
Angle += m;
|
||||
else
|
||||
angle -= m;
|
||||
Angle -= m;
|
||||
}
|
||||
|
||||
if (absangle(angle - player->mo->angle) < 4*ANGLE_1)
|
||||
if (absangle(Angle, player->mo->Angles.Yaw) < 4.)
|
||||
{
|
||||
increase = !increase;
|
||||
}
|
||||
|
@ -283,13 +284,55 @@ bool FCajunMaster::IsLeader (player_t *player)
|
|||
return false;
|
||||
}
|
||||
|
||||
extern int BotWTG;
|
||||
|
||||
void FCajunMaster::BotTick(AActor *mo)
|
||||
{
|
||||
BotSupportCycles.Clock();
|
||||
bglobal.m_Thinking = true;
|
||||
for (int i = 0; i < MAXPLAYERS; i++)
|
||||
{
|
||||
if (!playeringame[i] || players[i].Bot == NULL)
|
||||
continue;
|
||||
|
||||
if (mo->flags3 & MF3_ISMONSTER)
|
||||
{
|
||||
if (mo->health > 0
|
||||
&& !players[i].Bot->enemy
|
||||
&& mo->player ? !mo->IsTeammate(players[i].mo) : true
|
||||
&& mo->Distance2D(players[i].mo) < MAX_MONSTER_TARGET_DIST
|
||||
&& P_CheckSight(players[i].mo, mo, SF_SEEPASTBLOCKEVERYTHING))
|
||||
{ //Probably a monster, so go kill it.
|
||||
players[i].Bot->enemy = mo;
|
||||
}
|
||||
}
|
||||
else if (mo->flags & MF_SPECIAL)
|
||||
{ //Item pickup time
|
||||
//clock (BotWTG);
|
||||
players[i].Bot->WhatToGet(mo);
|
||||
//unclock (BotWTG);
|
||||
BotWTG++;
|
||||
}
|
||||
else if (mo->flags & MF_MISSILE)
|
||||
{
|
||||
if (!players[i].Bot->missile && (mo->flags3 & MF3_WARNBOT))
|
||||
{ //warn for incoming missiles.
|
||||
if (mo->target != players[i].mo && players[i].Bot->Check_LOS(mo, 90.))
|
||||
players[i].Bot->missile = mo;
|
||||
}
|
||||
}
|
||||
}
|
||||
bglobal.m_Thinking = false;
|
||||
BotSupportCycles.Unclock();
|
||||
}
|
||||
|
||||
//This function is called every
|
||||
//tick (for each bot) to set
|
||||
//the mate (teammate coop mate).
|
||||
AActor *DBot::Choose_Mate ()
|
||||
{
|
||||
int count;
|
||||
fixed_t closest_dist, test;
|
||||
double closest_dist, test;
|
||||
AActor *target;
|
||||
AActor *observer;
|
||||
|
||||
|
@ -310,7 +353,7 @@ AActor *DBot::Choose_Mate ()
|
|||
last_mate = NULL;
|
||||
|
||||
target = NULL;
|
||||
closest_dist = FIXED_MAX;
|
||||
closest_dist = FLT_MAX;
|
||||
if (bot_observer)
|
||||
observer = players[consoleplayer].mo;
|
||||
else
|
||||
|
@ -332,7 +375,7 @@ AActor *DBot::Choose_Mate ()
|
|||
{
|
||||
if (P_CheckSight (player->mo, client->mo, SF_IGNOREVISIBILITY))
|
||||
{
|
||||
test = client->mo->AproxDistance(player->mo);
|
||||
test = client->mo->Distance2D(player->mo);
|
||||
|
||||
if (test < closest_dist)
|
||||
{
|
||||
|
@ -366,9 +409,9 @@ AActor *DBot::Choose_Mate ()
|
|||
AActor *DBot::Find_enemy ()
|
||||
{
|
||||
int count;
|
||||
fixed_t closest_dist, temp; //To target.
|
||||
double closest_dist, temp; //To target.
|
||||
AActor *target;
|
||||
angle_t vangle;
|
||||
DAngle vangle;
|
||||
AActor *observer;
|
||||
|
||||
if (!deathmatch)
|
||||
|
@ -378,13 +421,13 @@ AActor *DBot::Find_enemy ()
|
|||
|
||||
//Note: It's hard to ambush a bot who is not alone
|
||||
if (allround || mate)
|
||||
vangle = ANGLE_MAX;
|
||||
vangle = 360.;
|
||||
else
|
||||
vangle = ENEMY_SCAN_FOV;
|
||||
allround = false;
|
||||
|
||||
target = NULL;
|
||||
closest_dist = FIXED_MAX;
|
||||
closest_dist = FLT_MAX;
|
||||
if (bot_observer)
|
||||
observer = players[consoleplayer].mo;
|
||||
else
|
||||
|
@ -402,7 +445,7 @@ AActor *DBot::Find_enemy ()
|
|||
if (Check_LOS (client->mo, vangle)) //Here's a strange one, when bot is standing still, the P_CheckSight within Check_LOS almost always returns false. tought it should be the same checksight as below but.. (below works) something must be fuckin wierd screded up.
|
||||
//if(P_CheckSight(player->mo, players[count].mo))
|
||||
{
|
||||
temp = client->mo->AproxDistance(player->mo);
|
||||
temp = client->mo->Distance2D(player->mo);
|
||||
|
||||
//Too dark?
|
||||
if (temp > DARK_DIST &&
|
||||
|
@ -425,28 +468,28 @@ AActor *DBot::Find_enemy ()
|
|||
|
||||
|
||||
//Creates a temporary mobj (invisible) at the given location.
|
||||
void FCajunMaster::SetBodyAt (fixed_t x, fixed_t y, fixed_t z, int hostnum)
|
||||
void FCajunMaster::SetBodyAt (const DVector3 &pos, int hostnum)
|
||||
{
|
||||
if (hostnum == 1)
|
||||
{
|
||||
if (body1)
|
||||
{
|
||||
body1->SetOrigin (x, y, z, false);
|
||||
body1->SetOrigin (pos, false);
|
||||
}
|
||||
else
|
||||
{
|
||||
body1 = Spawn ("CajunBodyNode", x, y, z, NO_REPLACE);
|
||||
body1 = Spawn ("CajunBodyNode", pos, NO_REPLACE);
|
||||
}
|
||||
}
|
||||
else if (hostnum == 2)
|
||||
{
|
||||
if (body2)
|
||||
{
|
||||
body2->SetOrigin (x, y, z, false);
|
||||
body2->SetOrigin (pos, false);
|
||||
}
|
||||
else
|
||||
{
|
||||
body2 = Spawn ("CajunBodyNode", x, y, z, NO_REPLACE);
|
||||
body2 = Spawn ("CajunBodyNode", pos, NO_REPLACE);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -461,27 +504,21 @@ void FCajunMaster::SetBodyAt (fixed_t x, fixed_t y, fixed_t z, int hostnum)
|
|||
|
||||
|
||||
//Emulates missile travel. Returns distance travelled.
|
||||
fixed_t FCajunMaster::FakeFire (AActor *source, AActor *dest, ticcmd_t *cmd)
|
||||
double FCajunMaster::FakeFire (AActor *source, AActor *dest, ticcmd_t *cmd)
|
||||
{
|
||||
AActor *th = Spawn ("CajunTrace", source->PosPlusZ(4*8*FRACUNIT), NO_REPLACE);
|
||||
AActor *th = Spawn ("CajunTrace", source->PosPlusZ(4*8.), NO_REPLACE);
|
||||
|
||||
th->target = source; // where it came from
|
||||
|
||||
float speed = (float)th->Speed;
|
||||
|
||||
fixedvec3 fixvel = source->Vec3To(dest);
|
||||
DVector3 velocity(fixvel.x, fixvel.y, fixvel.z);
|
||||
velocity.MakeUnit();
|
||||
th->vel.x = FLOAT2FIXED(velocity[0] * speed);
|
||||
th->vel.y = FLOAT2FIXED(velocity[1] * speed);
|
||||
th->vel.z = FLOAT2FIXED(velocity[2] * speed);
|
||||
th->Vel = source->Vec3To(dest).Resized(th->Speed);
|
||||
|
||||
fixed_t dist = 0;
|
||||
double dist = 0;
|
||||
|
||||
while (dist < SAFE_SELF_MISDIST)
|
||||
{
|
||||
dist += th->Speed;
|
||||
th->Move(th->vel.x, th->vel.y, th->vel.z);
|
||||
th->Move(th->Vel);
|
||||
if (!CleanAhead (th, th->X(), th->Y(), cmd))
|
||||
break;
|
||||
}
|
||||
|
@ -489,27 +526,23 @@ fixed_t FCajunMaster::FakeFire (AActor *source, AActor *dest, ticcmd_t *cmd)
|
|||
return dist;
|
||||
}
|
||||
|
||||
angle_t DBot::FireRox (AActor *enemy, ticcmd_t *cmd)
|
||||
DAngle DBot::FireRox (AActor *enemy, ticcmd_t *cmd)
|
||||
{
|
||||
fixed_t dist;
|
||||
angle_t ang;
|
||||
double dist;
|
||||
AActor *actor;
|
||||
int m;
|
||||
double m;
|
||||
|
||||
bglobal.SetBodyAt (player->mo->X() + FixedMul(player->mo->vel.x, 5*FRACUNIT),
|
||||
player->mo->Y() + FixedMul(player->mo->vel.y, 5*FRACUNIT),
|
||||
player->mo->Z() + (player->mo->height / 2), 2);
|
||||
bglobal.SetBodyAt(player->mo->PosPlusZ(player->mo->Height / 2) + player->mo->Vel.XY() * 5, 2);
|
||||
|
||||
actor = bglobal.body2;
|
||||
|
||||
dist = actor->AproxDistance (enemy);
|
||||
dist = actor->Distance2D (enemy);
|
||||
if (dist < SAFE_SELF_MISDIST)
|
||||
return 0;
|
||||
return 0.;
|
||||
//Predict.
|
||||
m = (((dist+1)/FRACUNIT) / GetDefaultByName("Rocket")->Speed);
|
||||
m = ((dist+1) / GetDefaultByName("Rocket")->Speed);
|
||||
|
||||
bglobal.SetBodyAt (enemy->X() + FixedMul(enemy->vel.x, (m+2*FRACUNIT)),
|
||||
enemy->Y() + FixedMul(enemy->vel.y, (m+2*FRACUNIT)), ONFLOORZ, 1);
|
||||
bglobal.SetBodyAt(DVector3((enemy->Pos() + enemy->Vel * (m + 2)), ONFLOORZ), 1);
|
||||
|
||||
//try the predicted location
|
||||
if (P_CheckSight (actor, bglobal.body1, SF_IGNOREVISIBILITY)) //See the predicted location, so give a test missile
|
||||
|
@ -519,8 +552,7 @@ angle_t DBot::FireRox (AActor *enemy, ticcmd_t *cmd)
|
|||
{
|
||||
if (bglobal.FakeFire (actor, bglobal.body1, cmd) >= SAFE_SELF_MISDIST)
|
||||
{
|
||||
ang = actor->AngleTo(bglobal.body1);
|
||||
return ang;
|
||||
return actor->AngleTo(bglobal.body1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -529,21 +561,20 @@ angle_t DBot::FireRox (AActor *enemy, ticcmd_t *cmd)
|
|||
{
|
||||
if (bglobal.FakeFire (player->mo, enemy, cmd) >= SAFE_SELF_MISDIST)
|
||||
{
|
||||
ang = player->mo->AngleTo(enemy);
|
||||
return ang;
|
||||
return player->mo->AngleTo(enemy);
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
return 0.;
|
||||
}
|
||||
|
||||
// [RH] We absolutely do not want to pick things up here. The bot code is
|
||||
// executed apart from all the other simulation code, so we don't want it
|
||||
// creating side-effects during gameplay.
|
||||
bool FCajunMaster::SafeCheckPosition (AActor *actor, fixed_t x, fixed_t y, FCheckPosition &tm)
|
||||
bool FCajunMaster::SafeCheckPosition (AActor *actor, double x, double y, FCheckPosition &tm)
|
||||
{
|
||||
ActorFlags savedFlags = actor->flags;
|
||||
actor->flags &= ~MF_PICKUP;
|
||||
bool res = P_CheckPosition (actor, x, y, tm);
|
||||
bool res = P_CheckPosition (actor, DVector2(x, y), tm);
|
||||
actor->flags = savedFlags;
|
||||
return res;
|
||||
}
|
||||
|
|
|
@ -21,6 +21,7 @@
|
|||
#include "d_player.h"
|
||||
#include "p_spec.h"
|
||||
#include "p_checkposition.h"
|
||||
#include "math/cmath.h"
|
||||
|
||||
static FRandom pr_botopendoor ("BotOpenDoor");
|
||||
static FRandom pr_bottrywalk ("BotTryWalk");
|
||||
|
@ -34,21 +35,21 @@ extern dirtype_t diags[4];
|
|||
//which can be a weapon/enemy/item whatever.
|
||||
void DBot::Roam (ticcmd_t *cmd)
|
||||
{
|
||||
int delta;
|
||||
|
||||
if (Reachable(dest))
|
||||
{ // Straight towards it.
|
||||
angle = player->mo->AngleTo(dest);
|
||||
Angle = player->mo->AngleTo(dest);
|
||||
}
|
||||
else if (player->mo->movedir < 8) // turn towards movement direction if not there yet
|
||||
{
|
||||
angle &= (angle_t)(7<<29);
|
||||
delta = angle - (player->mo->movedir << 29);
|
||||
// no point doing this with floating point angles...
|
||||
unsigned angle = Angle.BAMs() & (unsigned)(7 << 29);
|
||||
int delta = angle - (player->mo->movedir << 29);
|
||||
|
||||
if (delta > 0)
|
||||
angle -= ANG45;
|
||||
Angle -= 45;
|
||||
else if (delta < 0)
|
||||
angle += ANG45;
|
||||
Angle += 45;
|
||||
}
|
||||
|
||||
// chase towards destination.
|
||||
|
@ -60,7 +61,7 @@ void DBot::Roam (ticcmd_t *cmd)
|
|||
|
||||
bool DBot::Move (ticcmd_t *cmd)
|
||||
{
|
||||
fixed_t tryx, tryy;
|
||||
double tryx, tryy;
|
||||
bool try_ok;
|
||||
int good;
|
||||
|
||||
|
@ -147,18 +148,18 @@ void DBot::NewChaseDir (ticcmd_t *cmd)
|
|||
olddir = (dirtype_t)player->mo->movedir;
|
||||
turnaround = opposite[olddir];
|
||||
|
||||
fixedvec2 delta = player->mo->Vec2To(dest);
|
||||
DVector2 delta = player->mo->Vec2To(dest);
|
||||
|
||||
if (delta.x > 10*FRACUNIT)
|
||||
if (delta.X > 10)
|
||||
d[1] = DI_EAST;
|
||||
else if (delta.x < -10*FRACUNIT)
|
||||
else if (delta.X < -10)
|
||||
d[1] = DI_WEST;
|
||||
else
|
||||
d[1] = DI_NODIR;
|
||||
|
||||
if (delta.y < -10*FRACUNIT)
|
||||
if (delta.Y < -10)
|
||||
d[2] = DI_SOUTH;
|
||||
else if (delta.y > 10*FRACUNIT)
|
||||
else if (delta.Y > 10)
|
||||
d[2] = DI_NORTH;
|
||||
else
|
||||
d[2] = DI_NODIR;
|
||||
|
@ -166,19 +167,19 @@ void DBot::NewChaseDir (ticcmd_t *cmd)
|
|||
// try direct route
|
||||
if (d[1] != DI_NODIR && d[2] != DI_NODIR)
|
||||
{
|
||||
player->mo->movedir = diags[((delta.y<0)<<1)+(delta.x>0)];
|
||||
player->mo->movedir = diags[((delta.Y < 0) << 1) + (delta.X > 0)];
|
||||
if (player->mo->movedir != turnaround && TryWalk(cmd))
|
||||
return;
|
||||
}
|
||||
|
||||
// try other directions
|
||||
if (pr_botnewchasedir() > 200
|
||||
|| abs(delta.y)>abs(delta.x))
|
||||
{
|
||||
tdir=d[1];
|
||||
d[1]=d[2];
|
||||
d[2]=(dirtype_t)tdir;
|
||||
}
|
||||
if (pr_botnewchasedir() > 200
|
||||
|| fabs(delta.Y) > fabs(delta.X))
|
||||
{
|
||||
tdir = d[1];
|
||||
d[1] = d[2];
|
||||
d[2] = (dirtype_t)tdir;
|
||||
}
|
||||
|
||||
if (d[1]==turnaround)
|
||||
d[1]=DI_NODIR;
|
||||
|
@ -259,7 +260,7 @@ void DBot::NewChaseDir (ticcmd_t *cmd)
|
|||
// This is also a traverse function for
|
||||
// bots pre-rocket fire (preventing suicide)
|
||||
//
|
||||
bool FCajunMaster::CleanAhead (AActor *thing, fixed_t x, fixed_t y, ticcmd_t *cmd)
|
||||
bool FCajunMaster::CleanAhead (AActor *thing, double x, double y, ticcmd_t *cmd)
|
||||
{
|
||||
FCheckPosition tm;
|
||||
|
||||
|
@ -268,30 +269,30 @@ bool FCajunMaster::CleanAhead (AActor *thing, fixed_t x, fixed_t y, ticcmd_t *cm
|
|||
|
||||
if (!(thing->flags & MF_NOCLIP) )
|
||||
{
|
||||
fixed_t maxstep = thing->MaxStepHeight;
|
||||
if (tm.ceilingz - tm.floorz < thing->height)
|
||||
if (tm.ceilingz - tm.floorz < thing->Height)
|
||||
return false; // doesn't fit
|
||||
|
||||
double maxmove = MAXMOVEHEIGHT;
|
||||
if (!(thing->flags&MF_MISSILE))
|
||||
{
|
||||
if(tm.floorz > (thing->Sector->floorplane.ZatPoint (x, y)+MAXMOVEHEIGHT)) //Too high wall
|
||||
if(tm.floorz > (thing->Sector->floorplane.ZatPoint(x, y)+maxmove)) //Too high wall
|
||||
return false;
|
||||
|
||||
//Jumpable
|
||||
if(tm.floorz>(thing->Sector->floorplane.ZatPoint (x, y)+thing->MaxStepHeight))
|
||||
if(tm.floorz > (thing->Sector->floorplane.ZatPoint(x, y)+thing->MaxStepHeight))
|
||||
cmd->ucmd.buttons |= BT_JUMP;
|
||||
|
||||
|
||||
if ( !(thing->flags & MF_TELEPORT) &&
|
||||
tm.ceilingz - thing->Z() < thing->height)
|
||||
tm.ceilingz < thing->Top())
|
||||
return false; // mobj must lower itself to fit
|
||||
|
||||
// jump out of water
|
||||
// if((thing->eflags & (MF_UNDERWATER|MF_TOUCHWATER))==(MF_UNDERWATER|MF_TOUCHWATER))
|
||||
// maxstep=37*FRACUNIT;
|
||||
// maxstep=37;
|
||||
|
||||
if ( !(thing->flags & MF_TELEPORT) &&
|
||||
(tm.floorz - thing->Z() > maxstep ) )
|
||||
(tm.floorz - thing->Z() > thing->MaxStepHeight) )
|
||||
return false; // too big a step up
|
||||
|
||||
|
||||
|
@ -304,13 +305,13 @@ bool FCajunMaster::CleanAhead (AActor *thing, fixed_t x, fixed_t y, ticcmd_t *cm
|
|||
return true;
|
||||
}
|
||||
|
||||
#define OKAYRANGE (5*ANGLE_1) //counts *2, when angle is in range, turning is not executed.
|
||||
#define MAXTURN (15*ANGLE_1) //Max degrees turned in one tic. Lower is smother but may cause the bot not getting where it should = crash
|
||||
#define OKAYRANGE (5) //counts *2, when angle is in range, turning is not executed.
|
||||
#define MAXTURN (15) //Max degrees turned in one tic. Lower is smother but may cause the bot not getting where it should = crash
|
||||
#define TURNSENS 3 //Higher is smoother but slower turn.
|
||||
|
||||
void DBot::TurnToAng ()
|
||||
{
|
||||
int maxturn = MAXTURN;
|
||||
double maxturn = MAXTURN;
|
||||
|
||||
if (player->ReadyWeapon != NULL)
|
||||
{
|
||||
|
@ -326,20 +327,20 @@ void DBot::TurnToAng ()
|
|||
if(enemy)
|
||||
if(!dest) //happens when running after item in combat situations, or normal, prevents weak turns
|
||||
if(player->ReadyWeapon->ProjectileType == NULL && !(player->ReadyWeapon->WeaponFlags & WIF_MELEEWEAPON))
|
||||
if(Check_LOS(enemy, SHOOTFOV+5*ANGLE_1))
|
||||
if(Check_LOS(enemy, SHOOTFOV+5))
|
||||
maxturn = 3;
|
||||
}
|
||||
|
||||
int distance = angle - player->mo->angle;
|
||||
DAngle distance = deltaangle(player->mo->Angles.Yaw, Angle);
|
||||
|
||||
if (abs (distance) < OKAYRANGE && !enemy)
|
||||
if (fabs (distance) < OKAYRANGE && !enemy)
|
||||
return;
|
||||
|
||||
distance /= TURNSENS;
|
||||
if (abs (distance) > maxturn)
|
||||
if (fabs (distance) > maxturn)
|
||||
distance = distance < 0 ? -maxturn : maxturn;
|
||||
|
||||
player->mo->angle += distance;
|
||||
player->mo->Angles.Yaw += distance;
|
||||
}
|
||||
|
||||
void DBot::Pitch (AActor *target)
|
||||
|
@ -348,8 +349,8 @@ void DBot::Pitch (AActor *target)
|
|||
double diff;
|
||||
|
||||
diff = target->Z() - player->mo->Z();
|
||||
aim = atan(diff / (double)player->mo->AproxDistance(target));
|
||||
player->mo->pitch = -(int)(aim * ANGLE_180/M_PI);
|
||||
aim = g_atan(diff / player->mo->Distance2D(target));
|
||||
player->mo->Angles.Pitch = DAngle::ToDegrees(aim);
|
||||
}
|
||||
|
||||
//Checks if a sector is dangerous.
|
||||
|
|
|
@ -20,6 +20,7 @@
|
|||
#include "d_net.h"
|
||||
#include "d_event.h"
|
||||
#include "d_player.h"
|
||||
#include "vectors.h"
|
||||
|
||||
static FRandom pr_botmove ("BotMove");
|
||||
|
||||
|
@ -39,20 +40,21 @@ void DBot::Think ()
|
|||
if (teamplay || !deathmatch)
|
||||
mate = Choose_Mate ();
|
||||
|
||||
angle_t oldyaw = player->mo->angle;
|
||||
int oldpitch = player->mo->pitch;
|
||||
AActor *actor = player->mo;
|
||||
DAngle oldyaw = actor->Angles.Yaw;
|
||||
DAngle oldpitch = actor->Angles.Pitch;
|
||||
|
||||
Set_enemy ();
|
||||
ThinkForMove (cmd);
|
||||
TurnToAng ();
|
||||
|
||||
cmd->ucmd.yaw = (short)((player->mo->angle - oldyaw) >> 16) / ticdup;
|
||||
cmd->ucmd.pitch = (short)((oldpitch - player->mo->pitch) >> 16);
|
||||
cmd->ucmd.yaw = (short)((actor->Angles.Yaw - oldyaw).Degrees * (65536 / 360.f)) / ticdup;
|
||||
cmd->ucmd.pitch = (short)((oldpitch - actor->Angles.Pitch).Degrees * (65536 / 360.f));
|
||||
if (cmd->ucmd.pitch == -32768)
|
||||
cmd->ucmd.pitch = -32767;
|
||||
cmd->ucmd.pitch /= ticdup;
|
||||
player->mo->angle = oldyaw + (cmd->ucmd.yaw << 16) * ticdup;
|
||||
player->mo->pitch = oldpitch - (cmd->ucmd.pitch << 16) * ticdup;
|
||||
actor->Angles.Yaw = oldyaw + DAngle(cmd->ucmd.yaw * ticdup * (360 / 65536.f));
|
||||
actor->Angles.Pitch = oldpitch - DAngle(cmd->ucmd.pitch * ticdup * (360 / 65536.f));
|
||||
}
|
||||
|
||||
if (t_active) t_active--;
|
||||
|
@ -73,38 +75,41 @@ void DBot::Think ()
|
|||
}
|
||||
}
|
||||
|
||||
#define THINKDISTSQ (50000.*50000./(65536.*65536.))
|
||||
//how the bot moves.
|
||||
//MAIN movement function.
|
||||
void DBot::ThinkForMove (ticcmd_t *cmd)
|
||||
{
|
||||
fixed_t dist;
|
||||
double dist;
|
||||
bool stuck;
|
||||
int r;
|
||||
|
||||
stuck = false;
|
||||
dist = dest ? player->mo->AproxDistance(dest) : 0;
|
||||
dist = dest ? player->mo->Distance2D(dest) : 0;
|
||||
|
||||
if (missile &&
|
||||
((!missile->vel.x || !missile->vel.y) || !Check_LOS(missile, SHOOTFOV*3/2)))
|
||||
(!missile->Vel.X || !missile->Vel.Y || !Check_LOS(missile, SHOOTFOV*3/2)))
|
||||
{
|
||||
sleft = !sleft;
|
||||
missile = NULL; //Probably ended its travel.
|
||||
}
|
||||
|
||||
if (player->mo->pitch > 0)
|
||||
player->mo->pitch -= 80;
|
||||
else if (player->mo->pitch <= -60)
|
||||
player->mo->pitch += 80;
|
||||
#if 0 // this has always been broken and without any reference it cannot be fixed.
|
||||
if (player->mo->Angles.Pitch > 0)
|
||||
player->mo->Angles.Pitch -= 80;
|
||||
else if (player->mo->Angles.Pitch <= -60)
|
||||
player->mo->Angles.Pitch += 80;
|
||||
#endif
|
||||
|
||||
//HOW TO MOVE:
|
||||
if (missile && (player->mo->AproxDistance(missile)<AVOID_DIST)) //try avoid missile got from P_Mobj.c thinking part.
|
||||
if (missile && (player->mo->Distance2D(missile)<AVOID_DIST)) //try avoid missile got from P_Mobj.c thinking part.
|
||||
{
|
||||
Pitch (missile);
|
||||
angle = player->mo->AngleTo(missile);
|
||||
Angle = player->mo->AngleTo(missile);
|
||||
cmd->ucmd.sidemove = sleft ? -SIDERUN : SIDERUN;
|
||||
cmd->ucmd.forwardmove = -FORWARDRUN; //Back IS best.
|
||||
|
||||
if ((player->mo->AproxDistance(oldx, oldy)<50000)
|
||||
if ((player->mo->Pos() - old).LengthSquared() < THINKDISTSQ
|
||||
&& t_strafe<=0)
|
||||
{
|
||||
t_strafe = 5;
|
||||
|
@ -157,7 +162,7 @@ void DBot::ThinkForMove (ticcmd_t *cmd)
|
|||
t_fight = AFTERTICS;
|
||||
|
||||
if (t_strafe <= 0 &&
|
||||
(player->mo->AproxDistance(oldx, oldy)<50000
|
||||
((player->mo->Pos() - old).LengthSquared() < THINKDISTSQ
|
||||
|| ((pr_botmove()%30)==10))
|
||||
)
|
||||
{
|
||||
|
@ -166,10 +171,10 @@ void DBot::ThinkForMove (ticcmd_t *cmd)
|
|||
sleft = !sleft;
|
||||
}
|
||||
|
||||
angle = player->mo->AngleTo(enemy);
|
||||
Angle = player->mo->AngleTo(enemy);
|
||||
|
||||
if (player->ReadyWeapon == NULL ||
|
||||
player->mo->AproxDistance(enemy) >
|
||||
player->mo->Distance2D(enemy) >
|
||||
player->ReadyWeapon->MoveCombatDist)
|
||||
{
|
||||
// If a monster, use lower speed (just for cooler apperance while strafing down doomed monster)
|
||||
|
@ -194,7 +199,7 @@ void DBot::ThinkForMove (ticcmd_t *cmd)
|
|||
}
|
||||
else if (mate && !enemy && (!dest || dest==mate)) //Follow mate move.
|
||||
{
|
||||
fixed_t matedist;
|
||||
double matedist;
|
||||
|
||||
Pitch (mate);
|
||||
|
||||
|
@ -207,9 +212,9 @@ void DBot::ThinkForMove (ticcmd_t *cmd)
|
|||
goto roam;
|
||||
}
|
||||
|
||||
angle = player->mo->AngleTo(mate);
|
||||
Angle = player->mo->AngleTo(mate);
|
||||
|
||||
matedist = player->mo->AproxDistance(mate);
|
||||
matedist = player->mo->Distance2D(mate);
|
||||
if (matedist > (FRIEND_DIST*2))
|
||||
cmd->ucmd.forwardmove = FORWARDRUN;
|
||||
else if (matedist > FRIEND_DIST)
|
||||
|
@ -242,7 +247,7 @@ void DBot::ThinkForMove (ticcmd_t *cmd)
|
|||
(pr_botmove()%100)>skill.isp) && player->ReadyWeapon != NULL && !(player->ReadyWeapon->WeaponFlags & WIF_WIMPY_WEAPON))
|
||||
dest = enemy;//Dont let enemy kill the bot by supressive fire. So charge enemy.
|
||||
else //hide while t_fight, but keep view at enemy.
|
||||
angle = player->mo->AngleTo(enemy);
|
||||
Angle = player->mo->AngleTo(enemy);
|
||||
} //Just a monster, so kill it.
|
||||
else
|
||||
dest = enemy;
|
||||
|
@ -304,8 +309,7 @@ void DBot::ThinkForMove (ticcmd_t *cmd)
|
|||
if (t_fight<(AFTERTICS/2))
|
||||
player->mo->flags |= MF_DROPOFF;
|
||||
|
||||
oldx = player->mo->X();
|
||||
oldy = player->mo->Y();
|
||||
old = player->mo->Pos();
|
||||
}
|
||||
|
||||
//BOT_WhatToGet
|
||||
|
|
100
src/basictypes.h
100
src/basictypes.h
|
@ -1,16 +1,6 @@
|
|||
#ifndef __BASICTYPES_H
|
||||
#define __BASICTYPES_H
|
||||
|
||||
#ifdef _MSC_VER
|
||||
typedef __int8 SBYTE;
|
||||
typedef unsigned __int8 BYTE;
|
||||
typedef __int16 SWORD;
|
||||
typedef unsigned __int16 WORD;
|
||||
typedef __int32 SDWORD;
|
||||
typedef unsigned __int32 uint32;
|
||||
typedef __int64 SQWORD;
|
||||
typedef unsigned __int64 QWORD;
|
||||
#else
|
||||
#include <stdint.h>
|
||||
|
||||
typedef int8_t SBYTE;
|
||||
|
@ -21,11 +11,6 @@ typedef int32_t SDWORD;
|
|||
typedef uint32_t uint32;
|
||||
typedef int64_t SQWORD;
|
||||
typedef uint64_t QWORD;
|
||||
#endif
|
||||
|
||||
typedef SDWORD int32;
|
||||
typedef float real32;
|
||||
typedef double real64;
|
||||
|
||||
// windef.h, included by windows.h, has its own incompatible definition
|
||||
// of DWORD as a long. In files that mix Doom and Windows code, you
|
||||
|
@ -73,7 +58,7 @@ union QWORD_UNION
|
|||
};
|
||||
|
||||
//
|
||||
// Fixed point, 32bit as 16.16.
|
||||
// fixed point, 32bit as 16.16.
|
||||
//
|
||||
#define FRACBITS 16
|
||||
#define FRACUNIT (1<<FRACBITS)
|
||||
|
@ -81,89 +66,6 @@ union QWORD_UNION
|
|||
typedef SDWORD fixed_t;
|
||||
typedef DWORD dsfixed_t; // fixedpt used by span drawer
|
||||
|
||||
struct fixedvec2
|
||||
{
|
||||
fixed_t x, y;
|
||||
|
||||
fixedvec2 &operator +=(const fixedvec2 &other)
|
||||
{
|
||||
x += other.x;
|
||||
y += other.y;
|
||||
return *this;
|
||||
}
|
||||
};
|
||||
|
||||
struct fixedvec3
|
||||
{
|
||||
fixed_t x, y, z;
|
||||
|
||||
fixedvec3 &operator +=(const fixedvec3 &other)
|
||||
{
|
||||
x += other.x;
|
||||
y += other.y;
|
||||
z += other.z;
|
||||
return *this;
|
||||
}
|
||||
|
||||
fixedvec3 &operator +=(const fixedvec2 &other)
|
||||
{
|
||||
x += other.x;
|
||||
y += other.y;
|
||||
return *this;
|
||||
}
|
||||
|
||||
fixedvec3 &operator -=(const fixedvec2 &other)
|
||||
{
|
||||
x -= other.x;
|
||||
y -= other.y;
|
||||
return *this;
|
||||
}
|
||||
|
||||
fixedvec3 &operator -=(const fixedvec3 &other)
|
||||
{
|
||||
x -= other.x;
|
||||
y -= other.y;
|
||||
z -= other.z;
|
||||
return *this;
|
||||
}
|
||||
|
||||
operator fixedvec2()
|
||||
{
|
||||
return { x, y };
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
inline fixedvec2 operator +(const fixedvec2 &v1, const fixedvec2 &v2)
|
||||
{
|
||||
return { v1.x + v2.x, v1.y + v2.y };
|
||||
}
|
||||
|
||||
inline fixedvec2 operator -(const fixedvec2 &v1, const fixedvec2 &v2)
|
||||
{
|
||||
return { v1.x - v2.x, v1.y - v2.y };
|
||||
}
|
||||
|
||||
inline fixedvec3 operator +(const fixedvec3 &v1, const fixedvec3 &v2)
|
||||
{
|
||||
return { v1.x + v2.x, v1.y + v2.y, v1.z + v2.z };
|
||||
}
|
||||
|
||||
inline fixedvec3 operator +(const fixedvec3 &v1, const fixedvec2 &v2)
|
||||
{
|
||||
return { v1.x + v2.x, v1.y + v2.y, v1.z };
|
||||
}
|
||||
|
||||
inline fixedvec3 operator -(const fixedvec3 &v1, const fixedvec2 &v2)
|
||||
{
|
||||
return{ v1.x - v2.x, v1.y - v2.y, v1.z };
|
||||
}
|
||||
|
||||
inline fixedvec3 operator -(const fixedvec3 &v1, const fixedvec3 &v2)
|
||||
{
|
||||
return{ v1.x - v2.x, v1.y - v2.y, v1.z - v2.z };
|
||||
}
|
||||
|
||||
#define FIXED_MAX (signed)(0x7fffffff)
|
||||
#define FIXED_MIN (signed)(0x80000000)
|
||||
|
||||
|
|
|
@ -875,7 +875,7 @@ CCMD(linetarget)
|
|||
FTranslatedLineTarget t;
|
||||
|
||||
if (CheckCheatmode () || players[consoleplayer].mo == NULL) return;
|
||||
P_AimLineAttack(players[consoleplayer].mo,players[consoleplayer].mo->angle,MISSILERANGE, &t, 0);
|
||||
P_AimLineAttack(players[consoleplayer].mo,players[consoleplayer].mo->Angles.Yaw, MISSILERANGE, &t, 0.);
|
||||
if (t.linetarget)
|
||||
{
|
||||
Printf("Target=%s, Health=%d, Spawnhealth=%d\n",
|
||||
|
@ -892,8 +892,8 @@ CCMD(info)
|
|||
FTranslatedLineTarget t;
|
||||
|
||||
if (CheckCheatmode () || players[consoleplayer].mo == NULL) return;
|
||||
P_AimLineAttack(players[consoleplayer].mo,players[consoleplayer].mo->angle,MISSILERANGE,
|
||||
&t, 0, ALF_CHECKNONSHOOTABLE|ALF_FORCENOSMART);
|
||||
P_AimLineAttack(players[consoleplayer].mo,players[consoleplayer].mo->Angles.Yaw, MISSILERANGE,
|
||||
&t, 0., ALF_CHECKNONSHOOTABLE|ALF_FORCENOSMART);
|
||||
if (t.linetarget)
|
||||
{
|
||||
Printf("Target=%s, Health=%d, Spawnhealth=%d\n",
|
||||
|
@ -943,9 +943,8 @@ static void PrintFilteredActorList(const ActorTypeChecker IsActorType, const cha
|
|||
{
|
||||
if ((FilterClass == NULL || mo->IsA(FilterClass)) && IsActorType(mo))
|
||||
{
|
||||
Printf ("%s at (%d,%d,%d)\n",
|
||||
mo->GetClass()->TypeName.GetChars(),
|
||||
mo->X() >> FRACBITS, mo->Y() >> FRACBITS, mo->Z() >> FRACBITS);
|
||||
Printf ("%s at (%f,%f,%f)\n",
|
||||
mo->GetClass()->TypeName.GetChars(), mo->X(), mo->Y(), mo->Z());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1087,7 +1086,7 @@ CCMD(currentpos)
|
|||
if(mo)
|
||||
{
|
||||
Printf("Current player position: (%1.3f,%1.3f,%1.3f), angle: %1.3f, floorheight: %1.3f, sector:%d, lightlevel: %d\n",
|
||||
FIXED2DBL(mo->X()), FIXED2DBL(mo->Y()), FIXED2DBL(mo->Z()), ANGLE2DBL(mo->angle), FIXED2DBL(mo->floorz), mo->Sector->sectornum, mo->Sector->lightlevel);
|
||||
mo->X(), mo->Y(), mo->Z(), mo->Angles.Yaw.Normalized360().Degrees, mo->floorz, mo->Sector->sectornum, mo->Sector->lightlevel);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1245,9 +1244,9 @@ CCMD(angleconvtest)
|
|||
Printf("Testing degrees to angle conversion:\n");
|
||||
for (double ang = -5 * 180.; ang < 5 * 180.; ang += 45.)
|
||||
{
|
||||
angle_t ang1 = FLOAT2ANGLE(ang);
|
||||
angle_t ang2 = (angle_t)(ang * (ANGLE_90 / 90.));
|
||||
angle_t ang3 = (angle_t)(int)(ang * (ANGLE_90 / 90.));
|
||||
unsigned ang1 = DAngle(ang).BAMs();
|
||||
unsigned ang2 = (unsigned)(ang * (0x40000000 / 90.));
|
||||
unsigned ang3 = (unsigned)(int)(ang * (0x40000000 / 90.));
|
||||
Printf("Angle = %.5f: xs_RoundToInt = %08x, unsigned cast = %08x, signed cast = %08x\n",
|
||||
ang, ang1, ang2, ang3);
|
||||
}
|
||||
|
|
|
@ -732,15 +732,15 @@ static void C_DrawNotifyText ()
|
|||
if (!show_messages && NotifyStrings[i].PrintLevel != 128)
|
||||
continue;
|
||||
|
||||
fixed_t alpha;
|
||||
double alpha;
|
||||
|
||||
if (j < NOTIFYFADETIME)
|
||||
{
|
||||
alpha = OPAQUE * j / NOTIFYFADETIME;
|
||||
alpha = 1. * j / NOTIFYFADETIME;
|
||||
}
|
||||
else
|
||||
{
|
||||
alpha = OPAQUE;
|
||||
alpha = 1;
|
||||
}
|
||||
|
||||
if (NotifyStrings[i].PrintLevel >= PRINTLEVELS)
|
||||
|
@ -752,23 +752,23 @@ static void C_DrawNotifyText ()
|
|||
{
|
||||
if (!center)
|
||||
screen->DrawText (SmallFont, color, 0, line, NotifyStrings[i].Text,
|
||||
DTA_CleanNoMove, true, DTA_Alpha, alpha, TAG_DONE);
|
||||
DTA_CleanNoMove, true, DTA_AlphaF, alpha, TAG_DONE);
|
||||
else
|
||||
screen->DrawText (SmallFont, color, (SCREENWIDTH -
|
||||
SmallFont->StringWidth (NotifyStrings[i].Text)*CleanXfac)/2,
|
||||
line, NotifyStrings[i].Text, DTA_CleanNoMove, true,
|
||||
DTA_Alpha, alpha, TAG_DONE);
|
||||
DTA_AlphaF, alpha, TAG_DONE);
|
||||
}
|
||||
else if (con_scaletext == 0)
|
||||
{
|
||||
if (!center)
|
||||
screen->DrawText (SmallFont, color, 0, line, NotifyStrings[i].Text,
|
||||
DTA_Alpha, alpha, TAG_DONE);
|
||||
DTA_AlphaF, alpha, TAG_DONE);
|
||||
else
|
||||
screen->DrawText (SmallFont, color, (SCREENWIDTH -
|
||||
SmallFont->StringWidth (NotifyStrings[i].Text))/2,
|
||||
line, NotifyStrings[i].Text,
|
||||
DTA_Alpha, alpha, TAG_DONE);
|
||||
DTA_AlphaF, alpha, TAG_DONE);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -777,7 +777,7 @@ static void C_DrawNotifyText ()
|
|||
DTA_VirtualWidth, screen->GetWidth() / 2,
|
||||
DTA_VirtualHeight, screen->GetHeight() / 2,
|
||||
DTA_KeepRatio, true,
|
||||
DTA_Alpha, alpha, TAG_DONE);
|
||||
DTA_AlphaF, alpha, TAG_DONE);
|
||||
else
|
||||
screen->DrawText (SmallFont, color, (screen->GetWidth() / 2 -
|
||||
SmallFont->StringWidth (NotifyStrings[i].Text))/2,
|
||||
|
@ -785,7 +785,7 @@ static void C_DrawNotifyText ()
|
|||
DTA_VirtualWidth, screen->GetWidth() / 2,
|
||||
DTA_VirtualHeight, screen->GetHeight() / 2,
|
||||
DTA_KeepRatio, true,
|
||||
DTA_Alpha, alpha, TAG_DONE);
|
||||
DTA_AlphaF, alpha, TAG_DONE);
|
||||
}
|
||||
line += lineadv;
|
||||
canskip = false;
|
||||
|
@ -865,7 +865,7 @@ void C_DrawConsole (bool hw2d)
|
|||
DTA_DestWidth, screen->GetWidth(),
|
||||
DTA_DestHeight, screen->GetHeight(),
|
||||
DTA_ColorOverlay, conshade,
|
||||
DTA_Alpha, (hw2d && gamestate != GS_FULLCONSOLE) ? FLOAT2FIXED(con_alpha) : FRACUNIT,
|
||||
DTA_AlphaF, (hw2d && gamestate != GS_FULLCONSOLE) ? (double)con_alpha : 1.,
|
||||
DTA_Masked, false,
|
||||
TAG_DONE);
|
||||
if (conline && visheight < screen->GetHeight())
|
||||
|
|
|
@ -290,7 +290,7 @@ void ParseCompatibility()
|
|||
sc.MustGetNumber();
|
||||
CompatParams.Push(sc.Number);
|
||||
sc.MustGetFloat();
|
||||
CompatParams.Push(FLOAT2FIXED(sc.Float));
|
||||
CompatParams.Push(int(sc.Float*65536.));
|
||||
}
|
||||
else if (sc.Compare("setwallyscale"))
|
||||
{
|
||||
|
@ -303,7 +303,7 @@ void ParseCompatibility()
|
|||
sc.MustGetString();
|
||||
CompatParams.Push(sc.MustMatchString(WallTiers));
|
||||
sc.MustGetFloat();
|
||||
CompatParams.Push(FLOAT2FIXED(sc.Float));
|
||||
CompatParams.Push(int(sc.Float*65536.));
|
||||
}
|
||||
else if (sc.Compare("setthingz"))
|
||||
{
|
||||
|
@ -312,7 +312,7 @@ void ParseCompatibility()
|
|||
sc.MustGetNumber();
|
||||
CompatParams.Push(sc.Number);
|
||||
sc.MustGetFloat();
|
||||
CompatParams.Push(FLOAT2FIXED(sc.Float));
|
||||
CompatParams.Push(int(sc.Float*256)); // do not use full fixed here so that it can eventually handle larger levels
|
||||
}
|
||||
else if (sc.Compare("setsectortag"))
|
||||
{
|
||||
|
@ -522,7 +522,7 @@ void SetCompatibilityParams()
|
|||
{
|
||||
sector_t *sec = §ors[CompatParams[i+1]];
|
||||
sec->floorplane.ChangeHeight(CompatParams[i+2]);
|
||||
sec->ChangePlaneTexZ(sector_t::floor, CompatParams[i+2]);
|
||||
sec->ChangePlaneTexZ(sector_t::floor, CompatParams[i+2] / 65536.);
|
||||
}
|
||||
i += 3;
|
||||
break;
|
||||
|
@ -534,7 +534,7 @@ void SetCompatibilityParams()
|
|||
side_t *side = lines[CompatParams[i+1]].sidedef[CompatParams[i+2]];
|
||||
if (side != NULL)
|
||||
{
|
||||
side->SetTextureYScale(CompatParams[i+3], CompatParams[i+4]);
|
||||
side->SetTextureYScale(CompatParams[i+3], CompatParams[i+4] / 65536.);
|
||||
}
|
||||
}
|
||||
i += 5;
|
||||
|
@ -545,7 +545,7 @@ void SetCompatibilityParams()
|
|||
// When this is called, the things haven't been spawned yet so we can alter the position inside the MapThings array.
|
||||
if ((unsigned)CompatParams[i+1] < MapThingsConverted.Size())
|
||||
{
|
||||
MapThingsConverted[CompatParams[i+1]].z = CompatParams[i+2];
|
||||
MapThingsConverted[CompatParams[i+1]].pos.Z = CompatParams[i+2]/256.;
|
||||
}
|
||||
i += 3;
|
||||
break;
|
||||
|
|
|
@ -215,7 +215,7 @@ DehInfo deh =
|
|||
2, // .KFAAC
|
||||
"PLAY", // Name of player sprite
|
||||
255, // Rocket explosion style, 255=use cvar
|
||||
FRACUNIT*2/3, // Rocket explosion alpha
|
||||
2./3., // Rocket explosion alpha
|
||||
false, // .NoAutofreeze
|
||||
40, // BFG cells per shot
|
||||
};
|
||||
|
@ -353,6 +353,11 @@ static bool ReadChars (char **stuff, int size);
|
|||
static char *igets (void);
|
||||
static int GetLine (void);
|
||||
|
||||
inline double DEHToDouble(int acsval)
|
||||
{
|
||||
return acsval / 65536.;
|
||||
}
|
||||
|
||||
static void PushTouchedActor(PClassActor *cls)
|
||||
{
|
||||
for(unsigned i = 0; i < TouchedActors.Size(); i++)
|
||||
|
@ -647,7 +652,7 @@ static int CreateMushroomFunc(VMFunctionBuilder &buildit, int value1, int value2
|
|||
}
|
||||
else
|
||||
{
|
||||
buildit.Emit(OP_PARAM, 0, REGT_FLOAT | REGT_KONST, buildit.GetConstantFloat(FIXED2DBL(value1)));
|
||||
buildit.Emit(OP_PARAM, 0, REGT_FLOAT | REGT_KONST, buildit.GetConstantFloat(DEHToDouble(value1)));
|
||||
}
|
||||
// hrange
|
||||
if (value2 == 0)
|
||||
|
@ -656,7 +661,7 @@ static int CreateMushroomFunc(VMFunctionBuilder &buildit, int value1, int value2
|
|||
}
|
||||
else
|
||||
{
|
||||
buildit.Emit(OP_PARAM, 0, REGT_FLOAT | REGT_KONST, buildit.GetConstantFloat(FIXED2DBL(value2)));
|
||||
buildit.Emit(OP_PARAM, 0, REGT_FLOAT | REGT_KONST, buildit.GetConstantFloat(DEHToDouble(value2)));
|
||||
}
|
||||
return 5;
|
||||
}
|
||||
|
@ -896,14 +901,14 @@ static int PatchThing (int thingy)
|
|||
}
|
||||
else if (linelen == 12 && stricmp (Line1, "Translucency") == 0)
|
||||
{
|
||||
info->alpha = val;
|
||||
info->Alpha = DEHToDouble(val);
|
||||
info->RenderStyle = STYLE_Translucent;
|
||||
hadTranslucency = true;
|
||||
hadStyle = true;
|
||||
}
|
||||
else if (linelen == 6 && stricmp (Line1, "Height") == 0)
|
||||
{
|
||||
info->height = val;
|
||||
info->Height = DEHToDouble(val);
|
||||
info->projectilepassheight = 0; // needs to be disabled
|
||||
hadHeight = true;
|
||||
}
|
||||
|
@ -915,20 +920,20 @@ static int PatchThing (int thingy)
|
|||
{
|
||||
if (stricmp (Line1, "Speed") == 0)
|
||||
{
|
||||
info->Speed = val;
|
||||
info->Speed = val; // handle fixed point later.
|
||||
}
|
||||
else if (stricmp (Line1, "Width") == 0)
|
||||
{
|
||||
info->radius = val;
|
||||
info->radius = DEHToDouble(val);
|
||||
}
|
||||
else if (stricmp (Line1, "Alpha") == 0)
|
||||
{
|
||||
info->alpha = (fixed_t)(atof (Line2) * FRACUNIT);
|
||||
info->Alpha = atof (Line2);
|
||||
hadTranslucency = true;
|
||||
}
|
||||
else if (stricmp (Line1, "Scale") == 0)
|
||||
{
|
||||
info->scaleY = info->scaleX = clamp<fixed_t> (FLOAT2FIXED(atof (Line2)), 1, 256*FRACUNIT);
|
||||
info->Scale.Y = info->Scale.X = clamp(atof (Line2), 1./65536, 256.);
|
||||
}
|
||||
else if (stricmp (Line1, "Decal") == 0)
|
||||
{
|
||||
|
@ -1141,14 +1146,12 @@ static int PatchThing (int thingy)
|
|||
}
|
||||
|
||||
// MBF bounce factors depend on flag combos:
|
||||
enum
|
||||
{
|
||||
MBF_BOUNCE_NOGRAVITY = FRACUNIT, // With NOGRAVITY: full momentum
|
||||
MBF_BOUNCE_FLOATDROPOFF = (FRACUNIT * 85) / 100,// With FLOAT and DROPOFF: 85%
|
||||
MBF_BOUNCE_FLOAT = (FRACUNIT * 70) / 100,// With FLOAT alone: 70%
|
||||
MBF_BOUNCE_DEFAULT = (FRACUNIT * 45) / 100,// Without the above flags: 45%
|
||||
MBF_BOUNCE_WALL = (FRACUNIT * 50) / 100,// Bouncing off walls: 50%
|
||||
};
|
||||
const double MBF_BOUNCE_NOGRAVITY = 1; // With NOGRAVITY: full momentum
|
||||
const double MBF_BOUNCE_FLOATDROPOFF = 0.85; // With FLOAT and DROPOFF: 85%
|
||||
const double MBF_BOUNCE_FLOAT = 0.7; // With FLOAT alone: 70%
|
||||
const double MBF_BOUNCE_DEFAULT = 0.45; // Without the above flags: 45%
|
||||
const double MBF_BOUNCE_WALL = 0.5; // Bouncing off walls: 50%
|
||||
|
||||
info->bouncefactor = ((value[0] & MF_NOGRAVITY) ? MBF_BOUNCE_NOGRAVITY
|
||||
: (value[0] & MF_FLOAT) ? (value[0] & MF_DROPOFF) ? MBF_BOUNCE_FLOATDROPOFF
|
||||
: MBF_BOUNCE_FLOAT : MBF_BOUNCE_DEFAULT);
|
||||
|
@ -1215,7 +1218,7 @@ static int PatchThing (int thingy)
|
|||
}
|
||||
if (value[1] & 0x00000001)
|
||||
{
|
||||
info->gravity = FRACUNIT/4;
|
||||
info->Gravity = 1./4;
|
||||
value[1] &= ~0x00000001;
|
||||
}
|
||||
info->flags2 = ActorFlags2::FromInt (value[1]);
|
||||
|
@ -1226,11 +1229,11 @@ static int PatchThing (int thingy)
|
|||
{
|
||||
hadTranslucency = true;
|
||||
if (value[2] & 1)
|
||||
info->alpha = TRANSLUC25;
|
||||
info->Alpha = 0.25;
|
||||
else if (value[2] & 2)
|
||||
info->alpha = TRANSLUC50;
|
||||
info->Alpha = 0.5;
|
||||
else if (value[2] & 4)
|
||||
info->alpha = TRANSLUC75;
|
||||
info->Alpha = 0.75;
|
||||
info->RenderStyle = STYLE_Translucent;
|
||||
}
|
||||
if (value[2] & 8)
|
||||
|
@ -1257,7 +1260,7 @@ static int PatchThing (int thingy)
|
|||
!hadHeight &&
|
||||
thingy <= (int)OrgHeights.Size() && thingy > 0)
|
||||
{
|
||||
info->height = OrgHeights[thingy - 1] * FRACUNIT;
|
||||
info->Height = OrgHeights[thingy - 1];
|
||||
info->projectilepassheight = 0;
|
||||
}
|
||||
// If the thing's shadow changed, change its fuzziness if not already specified
|
||||
|
@ -1268,7 +1271,7 @@ static int PatchThing (int thingy)
|
|||
if (!hadStyle)
|
||||
info->RenderStyle = STYLE_OptFuzzy;
|
||||
if (!hadTranslucency)
|
||||
info->alpha = FRACUNIT/5;
|
||||
info->Alpha = 0.5;
|
||||
}
|
||||
else
|
||||
{ // changed from shadow
|
||||
|
@ -1276,11 +1279,11 @@ static int PatchThing (int thingy)
|
|||
info->RenderStyle = STYLE_Normal;
|
||||
}
|
||||
}
|
||||
// If this thing's speed is really low (i.e. meant to be a monster),
|
||||
// bump it up, because all speeds are fixed point now.
|
||||
if (abs(info->Speed) < 256)
|
||||
// Speed could be either an int of fixed value, depending on its use
|
||||
// If this value is very large it needs to be rescaled.
|
||||
if (fabs(info->Speed) >= 256)
|
||||
{
|
||||
info->Speed <<= FRACBITS;
|
||||
info->Speed /= 65536;
|
||||
}
|
||||
|
||||
if (info->flags & MF_SPECIAL)
|
||||
|
@ -1853,7 +1856,7 @@ static int PatchMisc (int dummy)
|
|||
}
|
||||
else if (stricmp (Line1, "Rocket Explosion Alpha") == 0)
|
||||
{
|
||||
deh.ExplosionAlpha = (fixed_t)(atof (Line2) * FRACUNIT);
|
||||
deh.ExplosionAlpha = atof (Line2);
|
||||
}
|
||||
else if (stricmp (Line1, "Monsters Infight") == 0)
|
||||
{
|
||||
|
@ -1940,13 +1943,13 @@ static int PatchMisc (int dummy)
|
|||
if (armor!=NULL)
|
||||
{
|
||||
armor->SaveAmount = 100 * deh.GreenAC;
|
||||
armor->SavePercent = deh.GreenAC == 1 ? FRACUNIT/3 : FRACUNIT/2;
|
||||
armor->SavePercent = deh.GreenAC == 1 ? 0.33335 : 0.5;
|
||||
}
|
||||
armor = static_cast<ABasicArmorPickup *> (GetDefaultByName ("BlueArmor"));
|
||||
if (armor!=NULL)
|
||||
{
|
||||
armor->SaveAmount = 100 * deh.BlueAC;
|
||||
armor->SavePercent = deh.BlueAC == 1 ? FRACUNIT/3 : FRACUNIT/2;
|
||||
armor->SavePercent = deh.BlueAC == 1 ? 0.33335 : 0.5;
|
||||
}
|
||||
|
||||
ABasicArmorBonus *barmor;
|
||||
|
|
|
@ -2203,7 +2203,7 @@ void Net_DoCommand (int type, BYTE **stream, int player)
|
|||
x = ReadWord (stream);
|
||||
y = ReadWord (stream);
|
||||
z = ReadWord (stream);
|
||||
P_TeleportMove (players[player].mo, x * 65536, y * 65536, z * 65536, true);
|
||||
P_TeleportMove (players[player].mo, DVector3(x, y, z), true);
|
||||
}
|
||||
break;
|
||||
|
||||
|
@ -2321,7 +2321,7 @@ void Net_DoCommand (int type, BYTE **stream, int player)
|
|||
else
|
||||
{
|
||||
const AActor *def = GetDefaultByType (typeinfo);
|
||||
fixedvec3 spawnpos = source->Vec3Angle(def->radius * 2 + source->radius, source->angle, 8 * FRACUNIT);
|
||||
DVector3 spawnpos = source->Vec3Angle(def->radius * 2 + source->radius, source->Angles.Yaw, 8.);
|
||||
|
||||
AActor *spawned = Spawn (typeinfo, spawnpos, ALLOW_REPLACE);
|
||||
if (spawned != NULL)
|
||||
|
@ -2348,7 +2348,7 @@ void Net_DoCommand (int type, BYTE **stream, int player)
|
|||
}
|
||||
if (type >= DEM_SUMMON2 && type <= DEM_SUMMONFOE2)
|
||||
{
|
||||
spawned->angle = source->angle - (ANGLE_1 * angle);
|
||||
spawned->Angles.Yaw = source->Angles.Yaw - angle;
|
||||
spawned->tid = tid;
|
||||
spawned->special = special;
|
||||
for(i = 0; i < 5; i++) {
|
||||
|
@ -2366,19 +2366,15 @@ void Net_DoCommand (int type, BYTE **stream, int player)
|
|||
{
|
||||
FTraceResults trace;
|
||||
|
||||
angle_t ang = players[player].mo->angle >> ANGLETOFINESHIFT;
|
||||
angle_t pitch = (angle_t)(players[player].mo->pitch) >> ANGLETOFINESHIFT;
|
||||
fixed_t vx = FixedMul (finecosine[pitch], finecosine[ang]);
|
||||
fixed_t vy = FixedMul (finecosine[pitch], finesine[ang]);
|
||||
fixed_t vz = -finesine[pitch];
|
||||
DAngle ang = players[player].mo->Angles.Yaw;
|
||||
DAngle pitch = players[player].mo->Angles.Pitch;
|
||||
double c = pitch.Cos();
|
||||
DVector3 vec(c * ang.Cos(), c * ang.Sin(), -pitch.Sin());
|
||||
|
||||
s = ReadString (stream);
|
||||
|
||||
if (Trace (players[player].mo->X(), players[player].mo->Y(),
|
||||
players[player].mo->Top() - (players[player].mo->height>>2),
|
||||
players[player].mo->Sector,
|
||||
vx, vy, vz, 172*FRACUNIT, 0, ML_BLOCKEVERYTHING, players[player].mo,
|
||||
trace, TRACE_NoSky))
|
||||
if (Trace (players[player].mo->PosPlusZ(players[player].mo->Height/2), players[player].mo->Sector,
|
||||
vec, 172., 0, ML_BLOCKEVERYTHING, players[player].mo, trace, TRACE_NoSky))
|
||||
{
|
||||
if (trace.HitType == TRACE_HitWall)
|
||||
{
|
||||
|
@ -2656,8 +2652,8 @@ void Net_DoCommand (int type, BYTE **stream, int player)
|
|||
break;
|
||||
|
||||
case DEM_SETPITCHLIMIT:
|
||||
players[player].MinPitch = ReadByte(stream) * -ANGLE_1; // up
|
||||
players[player].MaxPitch = ReadByte(stream) * ANGLE_1; // down
|
||||
players[player].MinPitch = -(double)ReadByte(stream); // up
|
||||
players[player].MaxPitch = (double)ReadByte(stream); // down
|
||||
break;
|
||||
|
||||
case DEM_ADVANCEINTER:
|
||||
|
|
|
@ -878,33 +878,6 @@ void D_ReadUserInfoStrings (int pnum, BYTE **stream, bool update)
|
|||
*stream += strlen (*((char **)stream)) + 1;
|
||||
}
|
||||
|
||||
void ReadCompatibleUserInfo(FArchive &arc, userinfo_t &info)
|
||||
{
|
||||
char netname[MAXPLAYERNAME + 1];
|
||||
BYTE team;
|
||||
int aimdist, color, colorset, skin, gender;
|
||||
bool neverswitch;
|
||||
//fixed_t movebob, stillbob; These were never serialized!
|
||||
//int playerclass; "
|
||||
|
||||
info.Reset();
|
||||
|
||||
arc.Read(&netname, sizeof(netname));
|
||||
arc << team << aimdist << color << skin << gender << neverswitch << colorset;
|
||||
|
||||
*static_cast<FStringCVar *>(info[NAME_Name]) = netname;
|
||||
*static_cast<FIntCVar *>(info[NAME_Team]) = team;
|
||||
*static_cast<FFloatCVar *>(info[NAME_Autoaim]) = ANGLE2FLOAT(aimdist);
|
||||
*static_cast<FIntCVar *>(info[NAME_Skin]) = skin;
|
||||
*static_cast<FIntCVar *>(info[NAME_Gender]) = gender;
|
||||
*static_cast<FBoolCVar *>(info[NAME_NeverSwitchOnPickup]) = neverswitch;
|
||||
*static_cast<FIntCVar *>(info[NAME_ColorSet]) = colorset;
|
||||
|
||||
UCVarValue val;
|
||||
val.Int = color;
|
||||
static_cast<FColorCVar *>(info[NAME_Color])->SetGenericRep(val, CVAR_Int);
|
||||
}
|
||||
|
||||
void WriteUserInfo(FArchive &arc, userinfo_t &info)
|
||||
{
|
||||
TMapIterator<FName, FBaseCVar *> it(info);
|
||||
|
@ -945,12 +918,6 @@ void ReadUserInfo(FArchive &arc, userinfo_t &info, FString &skin)
|
|||
char *str = NULL;
|
||||
UCVarValue val;
|
||||
|
||||
if (SaveVersion < 4253)
|
||||
{
|
||||
ReadCompatibleUserInfo(arc, info);
|
||||
return;
|
||||
}
|
||||
|
||||
info.Reset();
|
||||
skin = NULL;
|
||||
for (arc << name; name != NAME_None; arc << name)
|
||||
|
|
|
@ -89,7 +89,7 @@ public:
|
|||
FString Slot[10];
|
||||
FName InvulMode;
|
||||
FName HealingRadiusType;
|
||||
fixed_t HexenArmor[5];
|
||||
double HexenArmor[5];
|
||||
BYTE ColorRangeStart; // Skin color range
|
||||
BYTE ColorRangeEnd;
|
||||
FPlayerColorSetMap ColorSets;
|
||||
|
@ -114,7 +114,7 @@ public:
|
|||
virtual void PlayIdle ();
|
||||
virtual void PlayRunning ();
|
||||
virtual void ThrowPoisonBag ();
|
||||
virtual void TweakSpeeds (int &forwardmove, int &sidemove);
|
||||
virtual void TweakSpeeds (double &forwardmove, double &sidemove);
|
||||
virtual void MorphPlayerThink ();
|
||||
virtual void ActivateMorphWeapon ();
|
||||
AWeapon *PickNewWeapon (PClassAmmo *ammotype);
|
||||
|
@ -149,25 +149,25 @@ public:
|
|||
TObjPtr<AInventory> InvSel; // selected inventory item
|
||||
|
||||
// [GRB] Player class properties
|
||||
fixed_t JumpZ;
|
||||
fixed_t GruntSpeed;
|
||||
fixed_t FallingScreamMinSpeed, FallingScreamMaxSpeed;
|
||||
fixed_t ViewHeight;
|
||||
fixed_t ForwardMove1, ForwardMove2;
|
||||
fixed_t SideMove1, SideMove2;
|
||||
double JumpZ;
|
||||
double GruntSpeed;
|
||||
double FallingScreamMinSpeed, FallingScreamMaxSpeed;
|
||||
double ViewHeight;
|
||||
double ForwardMove1, ForwardMove2;
|
||||
double SideMove1, SideMove2;
|
||||
FTextureID ScoreIcon;
|
||||
int SpawnMask;
|
||||
FNameNoInit MorphWeapon;
|
||||
fixed_t AttackZOffset; // attack height, relative to player center
|
||||
fixed_t UseRange; // [NS] Distance at which player can +use
|
||||
fixed_t AirCapacity; // Multiplier for air supply underwater.
|
||||
double AttackZOffset; // attack height, relative to player center
|
||||
double UseRange; // [NS] Distance at which player can +use
|
||||
double AirCapacity; // Multiplier for air supply underwater.
|
||||
PClassActor *FlechetteType;
|
||||
|
||||
|
||||
// [CW] Fades for when you are being damaged.
|
||||
PalEntry DamageFade;
|
||||
|
||||
bool UpdateWaterLevel (fixed_t oldz, bool splash);
|
||||
bool UpdateWaterLevel (bool splash);
|
||||
bool ResetAirSupply (bool playgasp = true);
|
||||
|
||||
int GetMaxHealth() const;
|
||||
|
@ -292,7 +292,7 @@ struct userinfo_t : TMap<FName,FBaseCVar *>
|
|||
{
|
||||
~userinfo_t();
|
||||
|
||||
int GetAimDist() const
|
||||
double GetAimDist() const
|
||||
{
|
||||
if (dmflags2 & DF2_NOAUTOAIM)
|
||||
{
|
||||
|
@ -302,11 +302,11 @@ struct userinfo_t : TMap<FName,FBaseCVar *>
|
|||
float aim = *static_cast<FFloatCVar *>(*CheckKey(NAME_Autoaim));
|
||||
if (aim > 35 || aim < 0)
|
||||
{
|
||||
return ANGLE_1*35;
|
||||
return 35.;
|
||||
}
|
||||
else
|
||||
{
|
||||
return xs_RoundToInt(fabs(aim * ANGLE_1));
|
||||
return aim;
|
||||
}
|
||||
}
|
||||
const char *GetName() const
|
||||
|
@ -329,13 +329,13 @@ struct userinfo_t : TMap<FName,FBaseCVar *>
|
|||
{
|
||||
return *static_cast<FBoolCVar *>(*CheckKey(NAME_NeverSwitchOnPickup));
|
||||
}
|
||||
fixed_t GetMoveBob() const
|
||||
double GetMoveBob() const
|
||||
{
|
||||
return FLOAT2FIXED(*static_cast<FFloatCVar *>(*CheckKey(NAME_MoveBob)));
|
||||
return *static_cast<FFloatCVar *>(*CheckKey(NAME_MoveBob));
|
||||
}
|
||||
fixed_t GetStillBob() const
|
||||
double GetStillBob() const
|
||||
{
|
||||
return FLOAT2FIXED(*static_cast<FFloatCVar *>(*CheckKey(NAME_StillBob)));
|
||||
return *static_cast<FFloatCVar *>(*CheckKey(NAME_StillBob));
|
||||
}
|
||||
int GetPlayerClassNum() const
|
||||
{
|
||||
|
@ -402,16 +402,16 @@ public:
|
|||
|
||||
float DesiredFOV; // desired field of vision
|
||||
float FOV; // current field of vision
|
||||
fixed_t viewz; // focal origin above r.z
|
||||
fixed_t viewheight; // base height above floor for viewz
|
||||
fixed_t deltaviewheight; // squat speed.
|
||||
fixed_t bob; // bounded/scaled total velocity
|
||||
double viewz; // focal origin above r.z
|
||||
double viewheight; // base height above floor for viewz
|
||||
double deltaviewheight; // squat speed.
|
||||
double bob; // bounded/scaled total velocity
|
||||
|
||||
// killough 10/98: used for realistic bobbing (i.e. not simply overall speed)
|
||||
// mo->vel.x and mo->vel.y represent true velocity experienced by player.
|
||||
// mo->velx and mo->vely represent true velocity experienced by player.
|
||||
// This only represents the thrust that the player applies himself.
|
||||
// This avoids anomalies with such things as Boom ice and conveyors.
|
||||
fixedvec2 vel;
|
||||
DVector2 Vel;
|
||||
|
||||
bool centering;
|
||||
BYTE turnticks;
|
||||
|
@ -488,30 +488,30 @@ public:
|
|||
|
||||
FString LogText; // [RH] Log for Strife
|
||||
|
||||
int MinPitch; // Viewpitch limits (negative is up, positive is down)
|
||||
int MaxPitch;
|
||||
DAngle MinPitch; // Viewpitch limits (negative is up, positive is down)
|
||||
DAngle MaxPitch;
|
||||
|
||||
fixed_t crouchfactor;
|
||||
fixed_t crouchoffset;
|
||||
fixed_t crouchviewdelta;
|
||||
double crouchfactor;
|
||||
double crouchoffset;
|
||||
double crouchviewdelta;
|
||||
|
||||
FWeaponSlots weapons;
|
||||
|
||||
// [CW] I moved these here for multiplayer conversation support.
|
||||
TObjPtr<AActor> ConversationNPC, ConversationPC;
|
||||
angle_t ConversationNPCAngle;
|
||||
DAngle ConversationNPCAngle;
|
||||
bool ConversationFaceTalker;
|
||||
|
||||
fixed_t GetDeltaViewHeight() const
|
||||
double GetDeltaViewHeight() const
|
||||
{
|
||||
return (mo->ViewHeight + crouchviewdelta - viewheight) >> 3;
|
||||
return (mo->ViewHeight + crouchviewdelta - viewheight) / 8;
|
||||
}
|
||||
|
||||
void Uncrouch()
|
||||
{
|
||||
if (crouchfactor != FRACUNIT)
|
||||
if (crouchfactor != 1)
|
||||
{
|
||||
crouchfactor = FRACUNIT;
|
||||
crouchfactor = 1;
|
||||
crouchoffset = 0;
|
||||
crouchdir = 0;
|
||||
crouching = 0;
|
||||
|
@ -533,7 +533,7 @@ extern player_t players[MAXPLAYERS];
|
|||
|
||||
FArchive &operator<< (FArchive &arc, player_t *&p);
|
||||
|
||||
void P_CheckPlayerSprite(AActor *mo, int &spritenum, fixed_t &scalex, fixed_t &scaley);
|
||||
void P_CheckPlayerSprite(AActor *mo, int &spritenum, DVector2 &scale);
|
||||
|
||||
inline void AActor::SetFriendPlayer(player_t *player)
|
||||
{
|
||||
|
@ -556,7 +556,7 @@ inline bool AActor::IsNoClip2() const
|
|||
return false;
|
||||
}
|
||||
|
||||
#define CROUCHSPEED (FRACUNIT/12)
|
||||
#define CROUCHSPEED (1./12)
|
||||
|
||||
bool P_IsPlayerTotallyFrozen(const player_t *player);
|
||||
|
||||
|
|
|
@ -50,9 +50,6 @@
|
|||
#define NETD_ID BIGE_ID('N','E','T','D')
|
||||
#define WEAP_ID BIGE_ID('W','E','A','P')
|
||||
|
||||
#define ANGLE2SHORT(x) ((((x)/360) & 65535)
|
||||
#define SHORT2ANGLE(x) ((x)*360)
|
||||
|
||||
|
||||
struct zdemoheader_s {
|
||||
BYTE demovermajor;
|
||||
|
|
|
@ -52,7 +52,7 @@
|
|||
|
||||
FDecalLib DecalLibrary;
|
||||
|
||||
static fixed_t ReadScale (FScanner &sc);
|
||||
static double ReadScale (FScanner &sc);
|
||||
static TArray<BYTE> DecalTranslations;
|
||||
|
||||
// A decal group holds multiple decals and returns one randomly
|
||||
|
@ -148,7 +148,7 @@ public:
|
|||
|
||||
int TimeToStartDecay;
|
||||
int TimeToEndDecay;
|
||||
fixed_t StartTrans;
|
||||
double StartTrans;
|
||||
private:
|
||||
DDecalFader () {}
|
||||
};
|
||||
|
@ -186,7 +186,7 @@ struct FDecalStretcherAnim : public FDecalAnimator
|
|||
|
||||
int StretchStart;
|
||||
int StretchTime;
|
||||
fixed_t GoalX, GoalY;
|
||||
double GoalX, GoalY;
|
||||
};
|
||||
|
||||
class DDecalStretcher : public DDecalThinker
|
||||
|
@ -199,10 +199,10 @@ public:
|
|||
|
||||
int TimeToStart;
|
||||
int TimeToStop;
|
||||
fixed_t GoalX;
|
||||
fixed_t StartX;
|
||||
fixed_t GoalY;
|
||||
fixed_t StartY;
|
||||
double GoalX;
|
||||
double StartX;
|
||||
double GoalY;
|
||||
double StartY;
|
||||
bool bStretchX;
|
||||
bool bStretchY;
|
||||
bool bStarted;
|
||||
|
@ -217,7 +217,7 @@ struct FDecalSliderAnim : public FDecalAnimator
|
|||
|
||||
int SlideStart;
|
||||
int SlideTime;
|
||||
fixed_t /*DistX,*/ DistY;
|
||||
double /*DistX,*/ DistY;
|
||||
};
|
||||
|
||||
class DDecalSlider : public DDecalThinker
|
||||
|
@ -230,10 +230,10 @@ public:
|
|||
|
||||
int TimeToStart;
|
||||
int TimeToStop;
|
||||
/* fixed_t DistX; */
|
||||
fixed_t DistY;
|
||||
fixed_t StartX;
|
||||
fixed_t StartY;
|
||||
/* double DistX; */
|
||||
double DistY;
|
||||
double StartX;
|
||||
double StartY;
|
||||
bool bStarted;
|
||||
private:
|
||||
DDecalSlider () {}
|
||||
|
@ -453,10 +453,10 @@ void FDecalLib::ParseDecal (FScanner &sc)
|
|||
|
||||
memset ((void *)&newdecal, 0, sizeof(newdecal));
|
||||
newdecal.PicNum.SetInvalid();
|
||||
newdecal.ScaleX = newdecal.ScaleY = FRACUNIT;
|
||||
newdecal.ScaleX = newdecal.ScaleY = 1.;
|
||||
newdecal.RenderFlags = RF_WALLSPRITE;
|
||||
newdecal.RenderStyle = STYLE_Normal;
|
||||
newdecal.Alpha = 0x8000;
|
||||
newdecal.Alpha = 1.;
|
||||
|
||||
for (;;)
|
||||
{
|
||||
|
@ -492,13 +492,13 @@ void FDecalLib::ParseDecal (FScanner &sc)
|
|||
|
||||
case DECAL_ADD:
|
||||
sc.MustGetFloat ();
|
||||
newdecal.Alpha = (WORD)(32768.f * sc.Float);
|
||||
newdecal.Alpha = sc.Float;
|
||||
newdecal.RenderStyle = STYLE_Add;
|
||||
break;
|
||||
|
||||
case DECAL_TRANSLUCENT:
|
||||
sc.MustGetFloat ();
|
||||
newdecal.Alpha = (WORD)(32768.f * sc.Float);
|
||||
newdecal.Alpha = sc.Float;
|
||||
newdecal.RenderStyle = STYLE_Translucent;
|
||||
break;
|
||||
|
||||
|
@ -681,7 +681,7 @@ void FDecalLib::ParseFader (FScanner &sc)
|
|||
void FDecalLib::ParseStretcher (FScanner &sc)
|
||||
{
|
||||
FString stretcherName;
|
||||
fixed_t goalX = -1, goalY = -1;
|
||||
double goalX = -1, goalY = -1;
|
||||
int startTime = 0, takeTime = 0;
|
||||
|
||||
sc.MustGetString ();
|
||||
|
@ -732,7 +732,7 @@ void FDecalLib::ParseStretcher (FScanner &sc)
|
|||
void FDecalLib::ParseSlider (FScanner &sc)
|
||||
{
|
||||
FString sliderName;
|
||||
fixed_t distX = 0, distY = 0;
|
||||
double distX = 0, distY = 0;
|
||||
int startTime = 0, takeTime = 0;
|
||||
|
||||
sc.MustGetString ();
|
||||
|
@ -773,7 +773,7 @@ void FDecalLib::ParseSlider (FScanner &sc)
|
|||
else if (sc.Compare ("DistY"))
|
||||
{
|
||||
sc.MustGetFloat ();
|
||||
distY = (fixed_t)(sc.Float * FRACUNIT);
|
||||
distY = sc.Float;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -1046,7 +1046,7 @@ void FDecalTemplate::ApplyToDecal (DBaseDecal *decal, side_t *wall) const
|
|||
decal->ScaleX = ScaleX;
|
||||
decal->ScaleY = ScaleY;
|
||||
decal->PicNum = PicNum;
|
||||
decal->Alpha = Alpha << 1;
|
||||
decal->Alpha = Alpha;
|
||||
decal->RenderStyle = RenderStyle;
|
||||
decal->RenderFlags = (RenderFlags & ~(DECAL_RandomFlipX|DECAL_RandomFlipY)) |
|
||||
(decal->RenderFlags & (RF_RELMASK|RF_CLIPMASK|RF_INVISIBLE|RF_ONESIDED));
|
||||
|
@ -1184,7 +1184,7 @@ void DDecalFader::Tick ()
|
|||
|
||||
int distanceToEnd = TimeToEndDecay - level.maptime;
|
||||
int fadeDistance = TimeToEndDecay - TimeToStartDecay;
|
||||
TheDecal->Alpha = Scale (StartTrans, distanceToEnd, fadeDistance);
|
||||
TheDecal->Alpha = StartTrans * distanceToEnd / fadeDistance;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1278,11 +1278,11 @@ void DDecalStretcher::Tick ()
|
|||
int maxDistance = TimeToStop - TimeToStart;
|
||||
if (bStretchX)
|
||||
{
|
||||
TheDecal->ScaleX = StartX + Scale (GoalX - StartX, distance, maxDistance);
|
||||
TheDecal->ScaleX = StartX + (GoalX - StartX) * distance / maxDistance;
|
||||
}
|
||||
if (bStretchY)
|
||||
{
|
||||
TheDecal->ScaleY = StartY + Scale (GoalY - StartY, distance, maxDistance);
|
||||
TheDecal->ScaleY = StartY + (GoalY - StartY) * distance / maxDistance;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1339,8 +1339,8 @@ void DDecalSlider::Tick ()
|
|||
|
||||
int distance = level.maptime - TimeToStart;
|
||||
int maxDistance = TimeToStop - TimeToStart;
|
||||
/*TheDecal->LeftDistance = StartX + Scale (DistX, distance, maxDistance);*/
|
||||
TheDecal->Z = StartY + Scale (DistY, distance, maxDistance);
|
||||
/*TheDecal->LeftDistance = StartX + DistX * distance / maxDistance);*/
|
||||
TheDecal->Z = StartY + DistY * distance / maxDistance;
|
||||
}
|
||||
|
||||
DThinker *FDecalCombinerAnim::CreateThinker (DBaseDecal *actor, side_t *wall) const
|
||||
|
@ -1428,8 +1428,8 @@ DThinker *FDecalColorerAnim::CreateThinker (DBaseDecal *actor, side_t *wall) con
|
|||
return Colorer;
|
||||
}
|
||||
|
||||
static fixed_t ReadScale (FScanner &sc)
|
||||
static double ReadScale (FScanner &sc)
|
||||
{
|
||||
sc.MustGetFloat ();
|
||||
return fixed_t(clamp (sc.Float * FRACUNIT, 256.0, 256.0*FRACUNIT));
|
||||
return clamp (sc.Float, 1/256.0, 256.0);
|
||||
}
|
||||
|
|
|
@ -74,13 +74,13 @@ public:
|
|||
const FDecalTemplate *GetDecal () const;
|
||||
void ReplaceDecalRef (FDecalBase *from, FDecalBase *to);
|
||||
|
||||
fixed_t ScaleX, ScaleY;
|
||||
double ScaleX, ScaleY;
|
||||
DWORD ShadeColor;
|
||||
DWORD Translation;
|
||||
FRenderStyle RenderStyle;
|
||||
FTextureID PicNum;
|
||||
WORD RenderFlags;
|
||||
WORD Alpha; // same as (actor->alpha >> 1)
|
||||
double Alpha; // same as actor->alpha
|
||||
const FDecalAnimator *Animator;
|
||||
const FDecalBase *LowerDecal;
|
||||
|
||||
|
|
250
src/dobjtype.cpp
250
src/dobjtype.cpp
|
@ -80,8 +80,6 @@ PName *TypeName;
|
|||
PSound *TypeSound;
|
||||
PColor *TypeColor;
|
||||
PStatePointer *TypeState;
|
||||
PFixed *TypeFixed;
|
||||
PAngle *TypeAngle;
|
||||
|
||||
// PRIVATE DATA DEFINITIONS ------------------------------------------------
|
||||
|
||||
|
@ -663,9 +661,7 @@ void PType::StaticInit()
|
|||
RUNTIME_CLASS(PPrototype)->TypeTableType = RUNTIME_CLASS(PPrototype);
|
||||
RUNTIME_CLASS(PClass)->TypeTableType = RUNTIME_CLASS(PClass);
|
||||
RUNTIME_CLASS(PStatePointer)->TypeTableType = RUNTIME_CLASS(PStatePointer);
|
||||
RUNTIME_CLASS(PFixed)->TypeTableType = RUNTIME_CLASS(PFixed);
|
||||
RUNTIME_CLASS(PAngle)->TypeTableType = RUNTIME_CLASS(PAngle);
|
||||
|
||||
|
||||
// Create types and add them type the type table.
|
||||
TypeTable.AddType(TypeError = new PErrorType);
|
||||
TypeTable.AddType(TypeVoid = new PVoidType);
|
||||
|
@ -683,8 +679,6 @@ void PType::StaticInit()
|
|||
TypeTable.AddType(TypeSound = new PSound);
|
||||
TypeTable.AddType(TypeColor = new PColor);
|
||||
TypeTable.AddType(TypeState = new PStatePointer);
|
||||
TypeTable.AddType(TypeFixed = new PFixed);
|
||||
TypeTable.AddType(TypeAngle = new PAngle);
|
||||
|
||||
GlobalSymbols.AddSymbol(new PSymbolType(NAME_sByte, TypeSInt8));
|
||||
GlobalSymbols.AddSymbol(new PSymbolType(NAME_Byte, TypeUInt8));
|
||||
|
@ -702,8 +696,6 @@ void PType::StaticInit()
|
|||
GlobalSymbols.AddSymbol(new PSymbolType(NAME_Sound, TypeSound));
|
||||
GlobalSymbols.AddSymbol(new PSymbolType(NAME_Color, TypeColor));
|
||||
GlobalSymbols.AddSymbol(new PSymbolType(NAME_State, TypeState));
|
||||
GlobalSymbols.AddSymbol(new PSymbolType(NAME_Fixed, TypeFixed));
|
||||
GlobalSymbols.AddSymbol(new PSymbolType(NAME_Angle, TypeAngle));
|
||||
}
|
||||
|
||||
|
||||
|
@ -1694,242 +1686,6 @@ PColor::PColor()
|
|||
assert(sizeof(PalEntry) == __alignof(PalEntry));
|
||||
}
|
||||
|
||||
/* PFixed *****************************************************************/
|
||||
|
||||
IMPLEMENT_CLASS(PFixed)
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PFixed Default Constructor
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
PFixed::PFixed()
|
||||
: PFloat(sizeof(fixed_t))
|
||||
{
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PFixed :: WriteValue
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
void PFixed::WriteValue(FArchive &ar, const void *addr) const
|
||||
{
|
||||
ar.WriteByte(VAL_Fixed);
|
||||
ar << *(fixed_t *)addr;
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PFixed :: ReadValue
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
bool PFixed::ReadValue(FArchive &ar, void *addr) const
|
||||
{
|
||||
BYTE tag;
|
||||
ar << tag;
|
||||
if (tag == VAL_Fixed)
|
||||
{
|
||||
ar << *(fixed_t *)addr;
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
double val;
|
||||
if (ReadValueDbl(ar, &val, tag))
|
||||
{
|
||||
*(fixed_t *)addr = FLOAT2FIXED(val);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PFixed :: SetValue
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
void PFixed::SetValue(void *addr, int val)
|
||||
{
|
||||
assert(((intptr_t)addr & (Align - 1)) == 0 && "unaligned address");
|
||||
*(fixed_t *)addr = val << FRACBITS;
|
||||
}
|
||||
|
||||
void PFixed::SetValue(void *addr, double val)
|
||||
{
|
||||
assert(((intptr_t)addr & (Align - 1)) == 0 && "unaligned address");
|
||||
*(fixed_t *)addr = FLOAT2FIXED(val);
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PFixed :: GetValueInt
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
int PFixed::GetValueInt(void *addr) const
|
||||
{
|
||||
assert(((intptr_t)addr & (Align - 1)) == 0 && "unaligned address");
|
||||
return *(fixed_t *)addr >> FRACBITS;
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PFixed :: GetValueFloat
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
double PFixed::GetValueFloat(void *addr) const
|
||||
{
|
||||
assert(((intptr_t)addr & (Align - 1)) == 0 && "unaligned address");
|
||||
return FIXED2DBL(*(fixed_t *)addr);
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PFixed :: GetStoreOp
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
int PFixed::GetStoreOp() const
|
||||
{
|
||||
return OP_SX;
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PFixed :: GetLoadOp
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
int PFixed::GetLoadOp() const
|
||||
{
|
||||
return OP_LX;
|
||||
}
|
||||
|
||||
/* PAngle *****************************************************************/
|
||||
|
||||
IMPLEMENT_CLASS(PAngle)
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PAngle Default Constructor
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
PAngle::PAngle()
|
||||
: PFloat(sizeof(angle_t))
|
||||
{
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PAngle :: WriteValue
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
void PAngle::WriteValue(FArchive &ar, const void *addr) const
|
||||
{
|
||||
ar.WriteByte(VAL_BAM);
|
||||
ar.WriteInt32(*(angle_t *)addr);
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PAngle :: ReadValue
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
bool PAngle::ReadValue(FArchive &ar, void *addr) const
|
||||
{
|
||||
BYTE tag;
|
||||
ar << tag;
|
||||
if (tag == VAL_BAM)
|
||||
{
|
||||
ar << *(angle_t *)addr;
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
double val;
|
||||
if (ReadValueDbl(ar, &val, tag))
|
||||
{
|
||||
*(angle_t *)addr = FLOAT2ANGLE(val);
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PAngle :: SetValue
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
void PAngle::SetValue(void *addr, int val)
|
||||
{
|
||||
assert(((intptr_t)addr & (Align - 1)) == 0 && "unaligned address");
|
||||
*(angle_t *)addr = Scale(val, ANGLE_90, 90);
|
||||
}
|
||||
|
||||
void PAngle::SetValue(void *addr, double val)
|
||||
{
|
||||
assert(((intptr_t)addr & (Align - 1)) == 0 && "unaligned address");
|
||||
*(angle_t *)addr = (angle_t)(val * ANGLE_90 / 90);
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PAngle :: GetValueInt
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
int PAngle::GetValueInt(void *addr) const
|
||||
{
|
||||
assert(((intptr_t)addr & (Align - 1)) == 0 && "unaligned address");
|
||||
return *(angle_t *)addr / ANGLE_1;
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PAngle :: GetValueFloat
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
double PAngle::GetValueFloat(void *addr) const
|
||||
{
|
||||
assert(((intptr_t)addr & (Align - 1)) == 0 && "unaligned address");
|
||||
return (double)(*(angle_t *)addr) / ANGLE_1;
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PAngle :: GetStoreOp
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
int PAngle::GetStoreOp() const
|
||||
{
|
||||
return OP_SANG;
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
//
|
||||
// PAngle :: GetLoadOp
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
int PAngle::GetLoadOp() const
|
||||
{
|
||||
return OP_LANG;
|
||||
}
|
||||
|
||||
/* PStatePointer **********************************************************/
|
||||
|
||||
IMPLEMENT_CLASS(PStatePointer)
|
||||
|
@ -3537,8 +3293,8 @@ PField *PClass::AddField(FName name, PType *type, DWORD flags)
|
|||
PField *field = Super::AddField(name, type, flags);
|
||||
if (field != NULL)
|
||||
{
|
||||
Defaults = (BYTE *)M_Realloc(Defaults, Size);
|
||||
memset(Defaults + oldsize, 0, Size - oldsize);
|
||||
Defaults = (BYTE *)M_Realloc(Defaults, Size);
|
||||
memset(Defaults + oldsize, 0, Size - oldsize);
|
||||
// If this is a native class, then we must not initialize and
|
||||
// destroy any of its members. We do, however, initialize the
|
||||
// default instance since it's not a normal instance of the class.
|
||||
|
|
|
@ -456,43 +456,6 @@ public:
|
|||
PColor();
|
||||
};
|
||||
|
||||
// Variations of floating point types ---------------------------------------
|
||||
// These get converted to floats when they're loaded from memory.
|
||||
|
||||
class PFixed : public PFloat
|
||||
{
|
||||
DECLARE_CLASS(PFixed, PFloat);
|
||||
public:
|
||||
PFixed();
|
||||
|
||||
void WriteValue(FArchive &ar, const void *addr) const override;
|
||||
bool ReadValue(FArchive &ar, void *addr) const override;
|
||||
|
||||
virtual void SetValue(void *addr, int val);
|
||||
virtual void SetValue(void *addr, double val);
|
||||
virtual int GetValueInt(void *addr) const;
|
||||
virtual double GetValueFloat(void *addr) const;
|
||||
virtual int GetStoreOp() const;
|
||||
virtual int GetLoadOp() const;
|
||||
};
|
||||
|
||||
class PAngle : public PFloat
|
||||
{
|
||||
DECLARE_CLASS(PAngle, PFloat);
|
||||
public:
|
||||
PAngle();
|
||||
|
||||
void WriteValue(FArchive &ar, const void *addr) const override;
|
||||
bool ReadValue(FArchive &ar, void *addr) const override;
|
||||
|
||||
virtual void SetValue(void *addr, int val);
|
||||
virtual void SetValue(void *addr, double val);
|
||||
virtual int GetValueInt(void *addr) const;
|
||||
virtual double GetValueFloat(void *addr) const;
|
||||
virtual int GetStoreOp() const;
|
||||
virtual int GetLoadOp() const;
|
||||
};
|
||||
|
||||
// Pointers -----------------------------------------------------------------
|
||||
|
||||
class PStatePointer : public PBasicType
|
||||
|
@ -878,8 +841,6 @@ extern PName *TypeName;
|
|||
extern PSound *TypeSound;
|
||||
extern PColor *TypeColor;
|
||||
extern PStatePointer *TypeState;
|
||||
extern PFixed *TypeFixed;
|
||||
extern PAngle *TypeAngle;
|
||||
|
||||
// A constant value ---------------------------------------------------------
|
||||
|
||||
|
|
|
@ -26,6 +26,7 @@
|
|||
|
||||
// The most basic types we use, portability.
|
||||
#include "doomtype.h"
|
||||
#include "vectors.h"
|
||||
|
||||
// Some global defines, that configure the game.
|
||||
#include "doomdef.h"
|
||||
|
@ -345,9 +346,7 @@ struct FDoomEdEntry;
|
|||
struct FMapThing
|
||||
{
|
||||
int thingid;
|
||||
fixed_t x;
|
||||
fixed_t y;
|
||||
fixed_t z;
|
||||
DVector3 pos;
|
||||
short angle;
|
||||
WORD SkillFilter;
|
||||
WORD ClassFilter;
|
||||
|
@ -357,11 +356,10 @@ struct FMapThing
|
|||
int special;
|
||||
int args[5];
|
||||
int Conversation;
|
||||
fixed_t gravity;
|
||||
fixed_t alpha;
|
||||
double Gravity;
|
||||
double Alpha;
|
||||
DWORD fillcolor;
|
||||
fixed_t scaleX;
|
||||
fixed_t scaleY;
|
||||
DVector2 Scale;
|
||||
int health;
|
||||
int score;
|
||||
short pitch;
|
||||
|
@ -428,12 +426,12 @@ enum EMapThingFlags
|
|||
// A simplified mapthing for player starts
|
||||
struct FPlayerStart
|
||||
{
|
||||
fixed_t x, y, z;
|
||||
DVector3 pos;
|
||||
short angle, type;
|
||||
|
||||
FPlayerStart() { }
|
||||
FPlayerStart(const FMapThing *mthing, int pnum)
|
||||
: x(mthing->x), y(mthing->y), z(mthing->z),
|
||||
: pos(mthing->pos),
|
||||
angle(mthing->angle),
|
||||
type(pnum)
|
||||
{ }
|
||||
|
|
|
@ -340,7 +340,7 @@ enum : unsigned int
|
|||
COMPATF2_BADANGLES = 1 << 0, // It is impossible to face directly NSEW.
|
||||
COMPATF2_FLOORMOVE = 1 << 1, // Use the same floor motion behavior as Doom.
|
||||
COMPATF2_SOUNDCUTOFF = 1 << 2, // Cut off sounds when an actor vanishes instead of making it owner-less
|
||||
COMPATF2_POINTONLINE = 1 << 3, // Use original but buggy P_PointOnLineSide() and P_PointOnDivlineSide()
|
||||
COMPATF2_POINTONLINE = 1 << 3, // Use original but buggy P_PointOnLineSide() and P_PointOnDivlineSideCompat()
|
||||
COMPATF2_MULTIEXIT = 1 << 4, // Level exit can be triggered multiple times (required by Daedalus's travel tubes, thanks to a faulty script)
|
||||
};
|
||||
|
||||
|
@ -365,11 +365,11 @@ enum
|
|||
// linedefs. More friction can create mud, sludge,
|
||||
// magnetized floors, etc. Less friction can create ice.
|
||||
|
||||
#define MORE_FRICTION_VELOCITY 15000 // mud factor based on velocity
|
||||
#define ORIG_FRICTION 0xE800 // original value
|
||||
#define ORIG_FRICTION_FACTOR 2048 // original value
|
||||
#define FRICTION_LOW 0xf900
|
||||
#define FRICTION_FLY 0xeb00
|
||||
#define MORE_FRICTION_VELOCITY (15000/65536.) // mud factor based on velocity
|
||||
#define ORIG_FRICTION (0xE800/65536.) // original value
|
||||
#define ORIG_FRICTION_FACTOR (2048/65536.) // original value
|
||||
#define FRICTION_LOW (0xf900/65536.)
|
||||
#define FRICTION_FLY (0xeb00/65536.)
|
||||
|
||||
|
||||
#define BLINKTHRESHOLD (4*32)
|
||||
|
|
|
@ -233,7 +233,7 @@ struct DehInfo
|
|||
int KFAAC;
|
||||
char PlayerSprite[5];
|
||||
BYTE ExplosionStyle;
|
||||
fixed_t ExplosionAlpha;
|
||||
double ExplosionAlpha;
|
||||
int NoAutofreeze;
|
||||
int BFGCells;
|
||||
};
|
||||
|
|
|
@ -44,7 +44,6 @@
|
|||
#include "tarray.h"
|
||||
#include "name.h"
|
||||
#include "zstring.h"
|
||||
#include "vectors.h"
|
||||
|
||||
class PClassActor;
|
||||
typedef TMap<int, PClassActor *> FClassMap;
|
||||
|
@ -252,10 +251,13 @@ enum ESSType
|
|||
SS_BGRA
|
||||
};
|
||||
|
||||
#ifndef M_PI
|
||||
#define M_PI 3.14159265358979323846 // matches value in gcc v2 math.h
|
||||
// always use our own definition for consistency.
|
||||
#ifdef M_PI
|
||||
#undef M_PI
|
||||
#endif
|
||||
|
||||
const double M_PI = 3.14159265358979323846; // matches value in gcc v2 math.h
|
||||
|
||||
template <typename T, size_t N>
|
||||
char ( &_ArraySizeHelper( T (&array)[N] ))[N];
|
||||
|
||||
|
|
|
@ -133,7 +133,7 @@ DMovingCeiling::DMovingCeiling (sector_t *sector)
|
|||
interpolation = sector->SetInterpolation(sector_t::CeilingMove, true);
|
||||
}
|
||||
|
||||
bool DMover::MoveAttached(int crush, fixed_t move, int floorOrCeiling, bool resetfailed)
|
||||
bool DMover::MoveAttached(int crush, double move, int floorOrCeiling, bool resetfailed)
|
||||
{
|
||||
if (!P_Scroll3dMidtex(m_Sector, crush, move, !!floorOrCeiling) && resetfailed)
|
||||
{
|
||||
|
@ -155,20 +155,20 @@ bool DMover::MoveAttached(int crush, fixed_t move, int floorOrCeiling, bool rese
|
|||
// (Use -1 to prevent it from trying to crush)
|
||||
// dest is the desired d value for the plane
|
||||
//
|
||||
DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
||||
DMover::EResult DMover::MovePlane (double speed, double dest, int crush,
|
||||
int floorOrCeiling, int direction, bool hexencrush)
|
||||
{
|
||||
bool flag;
|
||||
fixed_t lastpos;
|
||||
fixed_t movedest;
|
||||
fixed_t move;
|
||||
//fixed_t destheight; //jff 02/04/98 used to keep floors/ceilings
|
||||
double lastpos;
|
||||
double movedest;
|
||||
double move;
|
||||
//double destheight; //jff 02/04/98 used to keep floors/ceilings
|
||||
// from moving thru each other
|
||||
switch (floorOrCeiling)
|
||||
{
|
||||
case 0:
|
||||
// FLOOR
|
||||
lastpos = m_Sector->floorplane.d;
|
||||
lastpos = m_Sector->floorplane.fD();
|
||||
switch (direction)
|
||||
{
|
||||
case -1:
|
||||
|
@ -180,11 +180,11 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
|
||||
if (!MoveAttached(crush, move, 0, true)) return crushed;
|
||||
|
||||
m_Sector->floorplane.d = dest;
|
||||
m_Sector->floorplane.setD(dest);
|
||||
flag = P_ChangeSector (m_Sector, crush, move, 0, false);
|
||||
if (flag)
|
||||
{
|
||||
m_Sector->floorplane.d = lastpos;
|
||||
m_Sector->floorplane.setD(lastpos);
|
||||
P_ChangeSector (m_Sector, crush, -move, 0, true);
|
||||
MoveAttached(crush, -move, 0, false);
|
||||
}
|
||||
|
@ -199,12 +199,12 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
{
|
||||
if (!MoveAttached(crush, -speed, 0, true)) return crushed;
|
||||
|
||||
m_Sector->floorplane.d = movedest;
|
||||
m_Sector->floorplane.setD(movedest);
|
||||
|
||||
flag = P_ChangeSector (m_Sector, crush, -speed, 0, false);
|
||||
if (flag)
|
||||
{
|
||||
m_Sector->floorplane.d = lastpos;
|
||||
m_Sector->floorplane.setD(lastpos);
|
||||
P_ChangeSector (m_Sector, crush, speed, 0, true);
|
||||
MoveAttached(crush, speed, 0, false);
|
||||
return crushed;
|
||||
|
@ -222,11 +222,10 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
// jff 02/04/98 keep floor from moving thru ceilings
|
||||
// [RH] not so easy with arbitrary planes
|
||||
//destheight = (dest < m_Sector->ceilingheight) ? dest : m_Sector->ceilingheight;
|
||||
if ((m_Sector->ceilingplane.a | m_Sector->ceilingplane.b |
|
||||
m_Sector->floorplane.a | m_Sector->floorplane.b) == 0 &&
|
||||
(!(i_compatflags2 & COMPATF2_FLOORMOVE) && -dest > m_Sector->ceilingplane.d))
|
||||
if (!m_Sector->ceilingplane.isSlope() && !m_Sector->floorplane.isSlope() &&
|
||||
(!(i_compatflags2 & COMPATF2_FLOORMOVE) && -dest > m_Sector->ceilingplane.fD()))
|
||||
{
|
||||
dest = -m_Sector->ceilingplane.d;
|
||||
dest = -m_Sector->ceilingplane.fD();
|
||||
}
|
||||
|
||||
movedest = m_Sector->floorplane.GetChangedHeight (speed);
|
||||
|
@ -237,12 +236,12 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
|
||||
if (!MoveAttached(crush, move, 0, true)) return crushed;
|
||||
|
||||
m_Sector->floorplane.d = dest;
|
||||
m_Sector->floorplane.setD(dest);
|
||||
|
||||
flag = P_ChangeSector (m_Sector, crush, move, 0, false);
|
||||
if (flag)
|
||||
{
|
||||
m_Sector->floorplane.d = lastpos;
|
||||
m_Sector->floorplane.setD(lastpos);
|
||||
P_ChangeSector (m_Sector, crush, -move, 0, true);
|
||||
MoveAttached(crush, -move, 0, false);
|
||||
}
|
||||
|
@ -257,7 +256,7 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
{
|
||||
if (!MoveAttached(crush, speed, 0, true)) return crushed;
|
||||
|
||||
m_Sector->floorplane.d = movedest;
|
||||
m_Sector->floorplane.setD(movedest);
|
||||
|
||||
// COULD GET CRUSHED
|
||||
flag = P_ChangeSector (m_Sector, crush, speed, 0, false);
|
||||
|
@ -269,7 +268,7 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
m_Sector->AdjustFloorClip ();
|
||||
return crushed;
|
||||
}
|
||||
m_Sector->floorplane.d = lastpos;
|
||||
m_Sector->floorplane.setD(lastpos);
|
||||
P_ChangeSector (m_Sector, crush, -speed, 0, true);
|
||||
MoveAttached(crush, -speed, 0, false);
|
||||
return crushed;
|
||||
|
@ -283,7 +282,7 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
|
||||
case 1:
|
||||
// CEILING
|
||||
lastpos = m_Sector->ceilingplane.d;
|
||||
lastpos = m_Sector->ceilingplane.fD();
|
||||
switch (direction)
|
||||
{
|
||||
case -1:
|
||||
|
@ -291,11 +290,10 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
// jff 02/04/98 keep ceiling from moving thru floors
|
||||
// [RH] not so easy with arbitrary planes
|
||||
//destheight = (dest > m_Sector->floorheight) ? dest : m_Sector->floorheight;
|
||||
if ((m_Sector->ceilingplane.a | m_Sector->ceilingplane.b |
|
||||
m_Sector->floorplane.a | m_Sector->floorplane.b) == 0 &&
|
||||
(!(i_compatflags2 & COMPATF2_FLOORMOVE) && dest < -m_Sector->floorplane.d))
|
||||
if (!m_Sector->ceilingplane.isSlope() && !m_Sector->floorplane.isSlope() &&
|
||||
(!(i_compatflags2 & COMPATF2_FLOORMOVE) && dest < -m_Sector->floorplane.fD()))
|
||||
{
|
||||
dest = -m_Sector->floorplane.d;
|
||||
dest = -m_Sector->floorplane.fD();
|
||||
}
|
||||
movedest = m_Sector->ceilingplane.GetChangedHeight (-speed);
|
||||
if (movedest <= dest)
|
||||
|
@ -304,12 +302,12 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
|
||||
if (!MoveAttached(crush, move, 1, true)) return crushed;
|
||||
|
||||
m_Sector->ceilingplane.d = dest;
|
||||
m_Sector->ceilingplane.setD(dest);
|
||||
flag = P_ChangeSector (m_Sector, crush, move, 1, false);
|
||||
|
||||
if (flag)
|
||||
{
|
||||
m_Sector->ceilingplane.d = lastpos;
|
||||
m_Sector->ceilingplane.setD(lastpos);
|
||||
P_ChangeSector (m_Sector, crush, -move, 1, true);
|
||||
MoveAttached(crush, -move, 1, false);
|
||||
}
|
||||
|
@ -323,7 +321,7 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
{
|
||||
if (!MoveAttached(crush, -speed, 1, true)) return crushed;
|
||||
|
||||
m_Sector->ceilingplane.d = movedest;
|
||||
m_Sector->ceilingplane.setD(movedest);
|
||||
|
||||
// COULD GET CRUSHED
|
||||
flag = P_ChangeSector (m_Sector, crush, -speed, 1, false);
|
||||
|
@ -334,7 +332,7 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
m_Sector->ChangePlaneTexZ(sector_t::ceiling, m_Sector->ceilingplane.HeightDiff (lastpos));
|
||||
return crushed;
|
||||
}
|
||||
m_Sector->ceilingplane.d = lastpos;
|
||||
m_Sector->ceilingplane.setD(lastpos);
|
||||
P_ChangeSector (m_Sector, crush, speed, 1, true);
|
||||
MoveAttached(crush, speed, 1, false);
|
||||
return crushed;
|
||||
|
@ -352,12 +350,12 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
|
||||
if (!MoveAttached(crush, move, 1, true)) return crushed;
|
||||
|
||||
m_Sector->ceilingplane.d = dest;
|
||||
m_Sector->ceilingplane.setD(dest);
|
||||
|
||||
flag = P_ChangeSector (m_Sector, crush, move, 1, false);
|
||||
if (flag)
|
||||
{
|
||||
m_Sector->ceilingplane.d = lastpos;
|
||||
m_Sector->ceilingplane.setD(lastpos);
|
||||
P_ChangeSector (m_Sector, crush, move, 1, true);
|
||||
MoveAttached(crush, move, 1, false);
|
||||
}
|
||||
|
@ -371,12 +369,12 @@ DMover::EResult DMover::MovePlane (fixed_t speed, fixed_t dest, int crush,
|
|||
{
|
||||
if (!MoveAttached(crush, speed, 1, true)) return crushed;
|
||||
|
||||
m_Sector->ceilingplane.d = movedest;
|
||||
m_Sector->ceilingplane.setD(movedest);
|
||||
|
||||
flag = P_ChangeSector (m_Sector, crush, speed, 1, false);
|
||||
if (flag)
|
||||
{
|
||||
m_Sector->ceilingplane.d = lastpos;
|
||||
m_Sector->ceilingplane.setD(lastpos);
|
||||
P_ChangeSector (m_Sector, crush, -speed, 1, true);
|
||||
MoveAttached(crush, -speed, 1, false);
|
||||
return crushed;
|
||||
|
|
|
@ -30,26 +30,26 @@ protected:
|
|||
enum EResult { ok, crushed, pastdest };
|
||||
TObjPtr<DInterpolation> interpolation;
|
||||
private:
|
||||
bool MoveAttached(int crush, fixed_t move, int floorOrCeiling, bool resetfailed);
|
||||
EResult MovePlane (fixed_t speed, fixed_t dest, int crush, int floorOrCeiling, int direction, bool hexencrush);
|
||||
bool MoveAttached(int crush, double move, int floorOrCeiling, bool resetfailed);
|
||||
EResult MovePlane (double speed, double dest, int crush, int floorOrCeiling, int direction, bool hexencrush);
|
||||
protected:
|
||||
DMover ();
|
||||
void Serialize (FArchive &arc);
|
||||
void Destroy();
|
||||
void StopInterpolation(bool force = false);
|
||||
inline EResult MoveFloor (fixed_t speed, fixed_t dest, int crush, int direction, bool hexencrush)
|
||||
inline EResult MoveFloor (double speed, double dest, int crush, int direction, bool hexencrush)
|
||||
{
|
||||
return MovePlane (speed, dest, crush, 0, direction, hexencrush);
|
||||
}
|
||||
inline EResult MoveFloor (fixed_t speed, fixed_t dest, int direction)
|
||||
inline EResult MoveFloor (double speed, double dest, int direction)
|
||||
{
|
||||
return MovePlane (speed, dest, -1, 0, direction, false);
|
||||
}
|
||||
inline EResult MoveCeiling (fixed_t speed, fixed_t dest, int crush, int direction, bool hexencrush)
|
||||
inline EResult MoveCeiling (double speed, double dest, int crush, int direction, bool hexencrush)
|
||||
{
|
||||
return MovePlane (speed, dest, crush, 1, direction, hexencrush);
|
||||
}
|
||||
inline EResult MoveCeiling (fixed_t speed, fixed_t dest, int direction)
|
||||
inline EResult MoveCeiling (double speed, double dest, int direction)
|
||||
{
|
||||
return MovePlane (speed, dest, -1, 1, direction, false);
|
||||
}
|
||||
|
|
|
@ -92,7 +92,7 @@ struct EDMapthing
|
|||
int recordnum;
|
||||
int tid;
|
||||
int type;
|
||||
fixed_t height;
|
||||
double height;
|
||||
int args[5];
|
||||
WORD skillfilter;
|
||||
DWORD flags;
|
||||
|
@ -105,7 +105,7 @@ struct EDLinedef
|
|||
int tag;
|
||||
int id;
|
||||
int args[5];
|
||||
fixed_t alpha;
|
||||
double alpha;
|
||||
DWORD flags;
|
||||
DWORD activation;
|
||||
};
|
||||
|
@ -140,10 +140,10 @@ struct EDSector
|
|||
bool colorSet;
|
||||
|
||||
// colormaptop//bottom cannot be used because ZDoom has no corresponding properties.
|
||||
|
||||
FTransform planexform[2];
|
||||
double xoffs[2], yoffs[2];
|
||||
DAngle angle[2];
|
||||
DWORD portalflags[2];
|
||||
fixed_t overlayalpha[2];
|
||||
double Overlayalpha[2];
|
||||
};
|
||||
|
||||
static FString EDMap;
|
||||
|
@ -158,7 +158,7 @@ static void parseLinedef(FScanner &sc)
|
|||
bool argsset = false;
|
||||
|
||||
memset(&ld, 0, sizeof(ld));
|
||||
ld.alpha = FRACUNIT;
|
||||
ld.alpha = 1.;
|
||||
|
||||
sc.MustGetStringName("{");
|
||||
while (!sc.CheckString("}"))
|
||||
|
@ -216,7 +216,7 @@ static void parseLinedef(FScanner &sc)
|
|||
{
|
||||
sc.CheckString("=");
|
||||
sc.MustGetFloat();
|
||||
ld.alpha = FLOAT2FIXED(sc.Float);
|
||||
ld.alpha = sc.Float;
|
||||
}
|
||||
else if (sc.Compare("extflags"))
|
||||
{
|
||||
|
@ -275,7 +275,7 @@ static void parseSector(FScanner &sc)
|
|||
EDSector sec;
|
||||
|
||||
memset(&sec, 0, sizeof(sec));
|
||||
sec.overlayalpha[sector_t::floor] = sec.overlayalpha[sector_t::ceiling] = FRACUNIT;
|
||||
sec.Overlayalpha[sector_t::floor] = sec.Overlayalpha[sector_t::ceiling] = 1.;
|
||||
sec.floorterrain = sec.ceilingterrain = -1;
|
||||
|
||||
sc.MustGetStringName("{");
|
||||
|
@ -398,19 +398,19 @@ static void parseSector(FScanner &sc)
|
|||
{
|
||||
sc.CheckString("=");
|
||||
sc.MustGetFloat();
|
||||
sec.planexform[sector_t::floor].angle = FLOAT2ANGLE(sc.Float);
|
||||
sec.angle[sector_t::floor] = sc.Float;
|
||||
}
|
||||
else if (sc.Compare("flooroffsetx"))
|
||||
{
|
||||
sc.CheckString("=");
|
||||
sc.MustGetFloat();
|
||||
sec.planexform[sector_t::floor].xoffs = FLOAT2FIXED(sc.Float);
|
||||
sec.xoffs[sector_t::floor] = sc.Float;
|
||||
}
|
||||
else if (sc.Compare("flooroffsety"))
|
||||
{
|
||||
sc.CheckString("=");
|
||||
sc.MustGetFloat();
|
||||
sec.planexform[sector_t::floor].yoffs = FLOAT2FIXED(sc.Float);
|
||||
sec.yoffs[sector_t::floor] = sc.Float;
|
||||
}
|
||||
else if (sc.Compare("ceilingterrain"))
|
||||
{
|
||||
|
@ -422,19 +422,19 @@ static void parseSector(FScanner &sc)
|
|||
{
|
||||
sc.CheckString("=");
|
||||
sc.MustGetFloat();
|
||||
sec.planexform[sector_t::ceiling].angle = FLOAT2ANGLE(sc.Float);
|
||||
sec.angle[sector_t::ceiling] = sc.Float;
|
||||
}
|
||||
else if (sc.Compare("ceilingoffsetx"))
|
||||
{
|
||||
sc.CheckString("=");
|
||||
sc.MustGetFloat();
|
||||
sec.planexform[sector_t::ceiling].xoffs = FLOAT2FIXED(sc.Float);
|
||||
sec.xoffs[sector_t::ceiling] = sc.Float;
|
||||
}
|
||||
else if (sc.Compare("ceilingoffsety"))
|
||||
{
|
||||
sc.CheckString("=");
|
||||
sc.MustGetFloat();
|
||||
sec.planexform[sector_t::ceiling].yoffs = FLOAT2FIXED(sc.Float);
|
||||
sec.yoffs[sector_t::ceiling] = sc.Float;
|
||||
}
|
||||
else if (sc.Compare("colormaptop") || sc.Compare("colormapbottom"))
|
||||
{
|
||||
|
@ -464,14 +464,14 @@ static void parseSector(FScanner &sc)
|
|||
sc.MustGetNumber();
|
||||
if (sc.CheckString("%")) sc.Float = sc.Number / 100.f;
|
||||
else sc.Float = sc.Number / 255.f;
|
||||
sec.overlayalpha[sector_t::floor] = FLOAT2FIXED(sc.Float);
|
||||
sec.Overlayalpha[sector_t::floor] = sc.Float;
|
||||
}
|
||||
else if (sc.Compare("ceiling"))
|
||||
{
|
||||
sc.MustGetFloat();
|
||||
if (sc.CheckString("%")) sc.Float = sc.Number / 100.f;
|
||||
else sc.Float = sc.Number / 255.f;
|
||||
sec.overlayalpha[sector_t::floor] = FLOAT2FIXED(sc.Float);
|
||||
sec.Overlayalpha[sector_t::floor] = sc.Float;
|
||||
}
|
||||
}
|
||||
else if (sc.Compare("portalflags"))
|
||||
|
@ -585,7 +585,7 @@ static void parseMapthing(FScanner &sc)
|
|||
{
|
||||
sc.CheckString("=");
|
||||
sc.MustGetFloat(); // no idea if Eternity allows fractional numbers. Better be safe and do it anyway.
|
||||
mt.height = FLOAT2FIXED(sc.Float);
|
||||
mt.height = sc.Float;
|
||||
}
|
||||
else if (sc.Compare("options"))
|
||||
{
|
||||
|
@ -682,7 +682,7 @@ void ProcessEDMapthing(FMapThing *mt, int recordnum)
|
|||
mt->thingid = emt->tid;
|
||||
mt->EdNum = emt->type;
|
||||
mt->info = DoomEdMap.CheckKey(mt->EdNum);
|
||||
mt->z = emt->height;
|
||||
mt->pos.Z = emt->height;
|
||||
memcpy(mt->args, emt->args, sizeof(mt->args));
|
||||
mt->SkillFilter = emt->skillfilter;
|
||||
mt->flags = emt->flags;
|
||||
|
@ -703,7 +703,7 @@ void ProcessEDLinedef(line_t *ld, int recordnum)
|
|||
ld->special = eld->special;
|
||||
ld->activation = eld->activation;
|
||||
ld->flags = (ld->flags&~fmask) | eld->flags;
|
||||
ld->Alpha = eld->alpha;
|
||||
ld->setAlpha(eld->alpha);
|
||||
memcpy(ld->args, eld->args, sizeof(ld->args));
|
||||
tagManager.AddLineID(int(ld - lines), eld->tag);
|
||||
}
|
||||
|
@ -742,10 +742,10 @@ void ProcessEDSector(sector_t *sec, int recordnum)
|
|||
const DWORD pflagmask = PLANEF_DISABLED | PLANEF_NORENDER | PLANEF_NOPASS | PLANEF_BLOCKSOUND | PLANEF_ADDITIVE;
|
||||
for (int i = 0; i < 2; i++)
|
||||
{
|
||||
sec->planes[i].xform.xoffs = esec->planexform[i].xoffs;
|
||||
sec->planes[i].xform.yoffs = esec->planexform[i].yoffs;
|
||||
sec->planes[i].xform.angle = esec->planexform[i].angle;
|
||||
sec->planes[i].alpha = esec->overlayalpha[i];
|
||||
sec->SetXOffset(i, esec->xoffs[i]);
|
||||
sec->SetYOffset(i, esec->yoffs[i]);
|
||||
sec->SetAngle(i, esec->angle[i]);
|
||||
sec->SetAlpha(i, esec->Overlayalpha[i]);
|
||||
sec->planes[i].Flags = (sec->planes[i].Flags & ~pflagmask) | esec->portalflags[i];
|
||||
}
|
||||
}
|
||||
|
|
|
@ -269,12 +269,13 @@ bool wipe_doBurn (int ticks)
|
|||
}
|
||||
|
||||
// Draw the screen
|
||||
fixed_t xstep, ystep, firex, firey;
|
||||
int xstep, ystep, firex, firey;
|
||||
int x, y;
|
||||
BYTE *to, *fromold, *fromnew;
|
||||
const int SHIFT = 16;
|
||||
|
||||
xstep = (FIREWIDTH * FRACUNIT) / SCREENWIDTH;
|
||||
ystep = (FIREHEIGHT * FRACUNIT) / SCREENHEIGHT;
|
||||
xstep = (FIREWIDTH << SHIFT) / SCREENWIDTH;
|
||||
ystep = (FIREHEIGHT << SHIFT) / SCREENHEIGHT;
|
||||
to = screen->GetBuffer();
|
||||
fromold = (BYTE *)wipe_scr_start;
|
||||
fromnew = (BYTE *)wipe_scr_end;
|
||||
|
@ -285,7 +286,7 @@ bool wipe_doBurn (int ticks)
|
|||
{
|
||||
int fglevel;
|
||||
|
||||
fglevel = burnarray[(firex>>FRACBITS)+(firey>>FRACBITS)*FIREWIDTH] / 2;
|
||||
fglevel = burnarray[(firex>>SHIFT)+(firey>>SHIFT)*FIREWIDTH] / 2;
|
||||
if (fglevel >= 63)
|
||||
{
|
||||
to[x] = fromnew[x];
|
||||
|
@ -340,7 +341,7 @@ bool wipe_doFade (int ticks)
|
|||
else
|
||||
{
|
||||
int x, y;
|
||||
fixed_t bglevel = 64 - fade;
|
||||
int bglevel = 64 - fade;
|
||||
DWORD *fg2rgb = Col2RGB8[fade];
|
||||
DWORD *bg2rgb = Col2RGB8[bglevel];
|
||||
BYTE *fromnew = (BYTE *)wipe_scr_end;
|
||||
|
|
|
@ -1562,3 +1562,21 @@ FArchive &operator<< (FArchive &arc, side_t *&side)
|
|||
{
|
||||
return arc.SerializePointer (sides, (BYTE **)&side, sizeof(*sides));
|
||||
}
|
||||
|
||||
FArchive &operator<<(FArchive &arc, DAngle &ang)
|
||||
{
|
||||
arc << ang.Degrees;
|
||||
return arc;
|
||||
}
|
||||
|
||||
FArchive &operator<<(FArchive &arc, DVector3 &vec)
|
||||
{
|
||||
arc << vec.X << vec.Y << vec.Z;
|
||||
return arc;
|
||||
}
|
||||
|
||||
FArchive &operator<<(FArchive &arc, DVector2 &vec)
|
||||
{
|
||||
arc << vec.X << vec.Y;
|
||||
return arc;
|
||||
}
|
||||
|
|
|
@ -331,6 +331,10 @@ FArchive &operator<< (FArchive &arc, line_t *&line);
|
|||
FArchive &operator<< (FArchive &arc, vertex_t *&vert);
|
||||
FArchive &operator<< (FArchive &arc, side_t *&side);
|
||||
|
||||
FArchive &operator<<(FArchive &arc, DAngle &ang);
|
||||
FArchive &operator<<(FArchive &arc, DVector3 &vec);
|
||||
FArchive &operator<<(FArchive &arc, DVector2 &vec);
|
||||
|
||||
|
||||
|
||||
template<typename T, typename TT>
|
||||
|
|
|
@ -46,7 +46,7 @@ public:
|
|||
return *this;
|
||||
}
|
||||
|
||||
FileReaderBase &operator>> (fixed_t &v)
|
||||
FileReaderBase &operator>> (int &v)
|
||||
{
|
||||
Read (&v, 4);
|
||||
v = LittleLong(v);
|
||||
|
@ -171,7 +171,7 @@ public:
|
|||
return *this;
|
||||
}
|
||||
|
||||
FileReaderZ &operator>> (fixed_t &v)
|
||||
FileReaderZ &operator>> (int &v)
|
||||
{
|
||||
Read (&v, 4);
|
||||
v = LittleLong(v);
|
||||
|
@ -233,7 +233,7 @@ public:
|
|||
return *this;
|
||||
}
|
||||
|
||||
FileReaderBZ2 &operator>> (fixed_t &v)
|
||||
FileReaderBZ2 &operator>> (int &v)
|
||||
{
|
||||
Read (&v, 4);
|
||||
v = LittleLong(v);
|
||||
|
@ -297,7 +297,7 @@ public:
|
|||
return *this;
|
||||
}
|
||||
|
||||
FileReaderLZMA &operator>> (fixed_t &v)
|
||||
FileReaderLZMA &operator>> (int &v)
|
||||
{
|
||||
Read (&v, 4);
|
||||
v = LittleLong(v);
|
||||
|
|
|
@ -165,7 +165,7 @@ void FS_EmulateCmd(char * string)
|
|||
else if (sc.Compare("viewheight"))
|
||||
{
|
||||
sc.MustGetFloat();
|
||||
fixed_t playerviewheight = (fixed_t)(sc.Float*FRACUNIT);
|
||||
double playerviewheight = sc.Float;
|
||||
for(int i=0;i<MAXPLAYERS;i++)
|
||||
{
|
||||
// No, this is not correct. But this is the way Legacy WADs expect it to be handled!
|
||||
|
|
|
@ -115,7 +115,7 @@ void DHUDPicManager::DoDraw (int linenum, int x, int y, int hudheight, float tra
|
|||
{
|
||||
FTexture * tex = TexMan[piclist[i].texturenum];
|
||||
if (tex) screen->DrawTexture(tex, piclist[i].xpos, piclist[i].ypos, DTA_320x200, true,
|
||||
DTA_Alpha, (fixed_t)(translucent*basetrans*FRACUNIT), TAG_DONE);
|
||||
DTA_AlphaF, translucent*basetrans, TAG_DONE);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -68,13 +68,11 @@
|
|||
#include "farchive.h"
|
||||
#include "p_setup.h"
|
||||
#include "p_spec.h"
|
||||
#include "r_utility.h"
|
||||
#include "math/cmath.h"
|
||||
|
||||
static FRandom pr_script("FScript");
|
||||
|
||||
|
||||
#define AngleToFixed(x) ((((double) x) / ((double) ANG45/45)) * FRACUNIT)
|
||||
#define FixedToAngle(x) ((((double) x) / FRACUNIT) * ANG45/45)
|
||||
|
||||
// functions. FParser::SF_ means Script Function not, well.. heh, me
|
||||
|
||||
/////////// actually running a function /////////////
|
||||
|
@ -860,43 +858,43 @@ void FParser::SF_Player(void)
|
|||
|
||||
void FParser::SF_Spawn(void)
|
||||
{
|
||||
int x, y, z;
|
||||
DVector3 pos;
|
||||
PClassActor *pclass;
|
||||
angle_t angle = 0;
|
||||
DAngle angle = 0.;
|
||||
|
||||
if (CheckArgs(3))
|
||||
{
|
||||
if (!(pclass=T_GetMobjType(t_argv[0]))) return;
|
||||
|
||||
x = fixedvalue(t_argv[1]);
|
||||
y = fixedvalue(t_argv[2]);
|
||||
pos.X = floatvalue(t_argv[1]);
|
||||
pos.Y = floatvalue(t_argv[2]);
|
||||
|
||||
if(t_argc >= 5)
|
||||
{
|
||||
z = fixedvalue(t_argv[4]);
|
||||
pos.Z = floatvalue(t_argv[4]);
|
||||
// [Graf Zahl] added option of spawning with a relative z coordinate
|
||||
if(t_argc > 5)
|
||||
{
|
||||
if (intvalue(t_argv[5])) z+=P_PointInSector(x, y)->floorplane.ZatPoint(x,y);
|
||||
if (intvalue(t_argv[5])) pos.Z += P_PointInSector(pos)->floorplane.ZatPoint(pos);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
// Legacy compatibility is more important than correctness.
|
||||
z = ONFLOORZ;// (GetDefaultByType(PClass)->flags & MF_SPAWNCEILING) ? ONCEILINGZ : ONFLOORZ;
|
||||
pos.Z = ONFLOORZ;// (GetDefaultByType(PClass)->flags & MF_SPAWNCEILING) ? ONCEILINGZ : ONFLOORZ;
|
||||
}
|
||||
|
||||
if(t_argc >= 4)
|
||||
{
|
||||
angle = intvalue(t_argv[3]) * (SQWORD)ANG45 / 45;
|
||||
angle = floatvalue(t_argv[3]);
|
||||
}
|
||||
|
||||
t_return.type = svt_mobj;
|
||||
t_return.value.mobj = Spawn(pclass, x, y, z, ALLOW_REPLACE);
|
||||
t_return.value.mobj = Spawn(pclass, pos, ALLOW_REPLACE);
|
||||
|
||||
if (t_return.value.mobj)
|
||||
{
|
||||
t_return.value.mobj->angle = angle;
|
||||
t_return.value.mobj->Angles.Yaw = angle;
|
||||
|
||||
if (!DFraggleThinker::ActiveThinker->nocheckposition)
|
||||
{
|
||||
|
@ -981,8 +979,7 @@ void FParser::SF_ObjX(void)
|
|||
mo = Script->trigger;
|
||||
}
|
||||
|
||||
t_return.type = svt_fixed; // haleyjd: SoM's fixed-point fix
|
||||
t_return.value.f = mo ? mo->X() : 0; // null ptr check
|
||||
t_return.setDouble(mo ? mo->X() : 0.);
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
|
@ -1004,8 +1001,7 @@ void FParser::SF_ObjY(void)
|
|||
mo = Script->trigger;
|
||||
}
|
||||
|
||||
t_return.type = svt_fixed; // haleyjd
|
||||
t_return.value.f = mo ? mo->Y() : 0; // null ptr check
|
||||
t_return.setDouble(mo ? mo->Y() : 0.);
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
|
@ -1027,8 +1023,7 @@ void FParser::SF_ObjZ(void)
|
|||
mo = Script->trigger;
|
||||
}
|
||||
|
||||
t_return.type = svt_fixed; // haleyjd
|
||||
t_return.value.f = mo ? mo->Z() : 0; // null ptr check
|
||||
t_return.setDouble(mo ? mo->Z() : 0.);
|
||||
}
|
||||
|
||||
|
||||
|
@ -1051,8 +1046,7 @@ void FParser::SF_ObjAngle(void)
|
|||
mo = Script->trigger;
|
||||
}
|
||||
|
||||
t_return.type = svt_fixed; // haleyjd: fixed-point -- SoM again :)
|
||||
t_return.value.f = mo ? (fixed_t)AngleToFixed(mo->angle) : 0; // null ptr check
|
||||
t_return.setDouble(mo ? mo->Angles.Yaw.Degrees : 0.);
|
||||
}
|
||||
|
||||
|
||||
|
@ -1256,10 +1250,9 @@ void FParser::SF_PushThing(void)
|
|||
AActor * mo = actorvalue(t_argv[0]);
|
||||
if(!mo) return;
|
||||
|
||||
angle_t angle = (angle_t)FixedToAngle(fixedvalue(t_argv[1]));
|
||||
fixed_t force = fixedvalue(t_argv[2]);
|
||||
|
||||
P_ThrustMobj(mo, angle, force);
|
||||
DAngle angle = floatvalue(t_argv[1]);
|
||||
double force = floatvalue(t_argv[2]);
|
||||
mo->Thrust(angle, force);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1333,11 +1326,10 @@ void FParser::SF_MobjMomx(void)
|
|||
if(t_argc > 1)
|
||||
{
|
||||
if(mo)
|
||||
mo->vel.x = fixedvalue(t_argv[1]);
|
||||
mo->Vel.X = floatvalue(t_argv[1]);
|
||||
}
|
||||
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = mo ? mo->vel.x : 0;
|
||||
t_return.setDouble(mo ? mo->Vel.X : 0.);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1356,12 +1348,11 @@ void FParser::SF_MobjMomy(void)
|
|||
mo = actorvalue(t_argv[0]);
|
||||
if(t_argc > 1)
|
||||
{
|
||||
if(mo)
|
||||
mo->vel.y = fixedvalue(t_argv[1]);
|
||||
if(mo)
|
||||
mo->Vel.Y = floatvalue(t_argv[1]);
|
||||
}
|
||||
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = mo ? mo->vel.y : 0;
|
||||
t_return.setDouble(mo ? mo->Vel.Y : 0.);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1378,14 +1369,13 @@ void FParser::SF_MobjMomz(void)
|
|||
if (CheckArgs(1))
|
||||
{
|
||||
mo = actorvalue(t_argv[0]);
|
||||
if(t_argc > 1)
|
||||
if (t_argc > 1)
|
||||
{
|
||||
if(mo)
|
||||
mo->vel.z = fixedvalue(t_argv[1]);
|
||||
if (mo)
|
||||
mo->Vel.Z = floatvalue(t_argv[1]);
|
||||
}
|
||||
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = mo ? mo->vel.z : 0;
|
||||
|
||||
t_return.setDouble(mo ? mo->Vel.Z : 0.);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1402,15 +1392,12 @@ void FParser::SF_PointToAngle(void)
|
|||
{
|
||||
if (CheckArgs(4))
|
||||
{
|
||||
fixed_t x1 = fixedvalue(t_argv[0]);
|
||||
fixed_t y1 = fixedvalue(t_argv[1]);
|
||||
fixed_t x2 = fixedvalue(t_argv[2]);
|
||||
fixed_t y2 = fixedvalue(t_argv[3]);
|
||||
double x1 = floatvalue(t_argv[0]);
|
||||
double y1 = floatvalue(t_argv[1]);
|
||||
double x2 = floatvalue(t_argv[2]);
|
||||
double y2 = floatvalue(t_argv[3]);
|
||||
|
||||
angle_t angle = R_PointToAngle2(x1, y1, x2, y2);
|
||||
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = (fixed_t)AngleToFixed(angle);
|
||||
t_return.setDouble(DVector2(x2 - x1, y2 - y1).Angle().Normalized360().Degrees);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1428,9 +1415,7 @@ void FParser::SF_PointToDist(void)
|
|||
// Doing this in floating point is actually faster with modern computers!
|
||||
double x = floatvalue(t_argv[2]) - floatvalue(t_argv[0]);
|
||||
double y = floatvalue(t_argv[3]) - floatvalue(t_argv[1]);
|
||||
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(sqrt(x*x+y*y));
|
||||
t_return.setDouble(g_sqrt(x*x+y*y));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1447,7 +1432,7 @@ void FParser::SF_PointToDist(void)
|
|||
|
||||
void FParser::SF_SetCamera(void)
|
||||
{
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
player_t * player;
|
||||
AActor * newcamera;
|
||||
|
||||
|
@ -1463,21 +1448,16 @@ void FParser::SF_SetCamera(void)
|
|||
return; // nullptr check
|
||||
}
|
||||
|
||||
angle = t_argc < 2 ? newcamera->angle : (fixed_t)FixedToAngle(fixedvalue(t_argv[1]));
|
||||
angle = t_argc < 2 ? newcamera->Angles.Yaw : floatvalue(t_argv[1]);
|
||||
|
||||
newcamera->special1=newcamera->angle;
|
||||
newcamera->special2=newcamera->Z();
|
||||
newcamera->SetZ(t_argc < 3 ? (newcamera->Z() + (41 << FRACBITS)) : (intvalue(t_argv[2]) << FRACBITS));
|
||||
newcamera->angle = angle;
|
||||
if(t_argc < 4) newcamera->pitch = 0;
|
||||
else
|
||||
{
|
||||
fixed_t pitch = fixedvalue(t_argv[3]);
|
||||
if (pitch < -50 * FRACUNIT) pitch = -50 * FRACUNIT;
|
||||
if (pitch > 50 * FRACUNIT) pitch = 50 * FRACUNIT;
|
||||
newcamera->pitch = xs_CRoundToUInt((pitch / 65536.0f)*(ANGLE_45 / 45.0f)*(20.0f / 32.0f));
|
||||
}
|
||||
newcamera->specialf1 = newcamera->Angles.Yaw.Degrees;
|
||||
newcamera->specialf2 = newcamera->Z();
|
||||
newcamera->SetZ(t_argc < 3 ? newcamera->Z() + 41 : floatvalue(t_argv[2]));
|
||||
newcamera->Angles.Yaw = angle;
|
||||
if (t_argc < 4) newcamera->Angles.Pitch = 0.;
|
||||
else newcamera->Angles.Pitch = clamp(floatvalue(t_argv[3]), -50., 50.) * (20. / 32.);
|
||||
player->camera=newcamera;
|
||||
R_ResetViewInterpolation();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1497,8 +1477,8 @@ void FParser::SF_ClearCamera(void)
|
|||
if (cam)
|
||||
{
|
||||
player->camera=player->mo;
|
||||
cam->angle=cam->special1;
|
||||
cam->SetZ(cam->special2);
|
||||
cam->Angles.Yaw = cam->specialf1;
|
||||
cam->SetZ(cam->specialf2);
|
||||
}
|
||||
|
||||
}
|
||||
|
@ -1557,16 +1537,13 @@ void FParser::SF_StartSectorSound(void)
|
|||
|
||||
/************* Sector functions ***************/
|
||||
|
||||
//DMover::EResult P_MoveFloor (sector_t * m_Sector, fixed_t speed, fixed_t dest, int crush, int direction, int flags=0);
|
||||
//DMover::EResult P_MoveCeiling (sector_t * m_Sector, fixed_t speed, fixed_t dest, int crush, int direction, int flags=0);
|
||||
|
||||
class DFloorChanger : public DFloor
|
||||
{
|
||||
public:
|
||||
DFloorChanger(sector_t * sec)
|
||||
: DFloor(sec) {}
|
||||
|
||||
bool Move(fixed_t speed, fixed_t dest, int crush, int direction)
|
||||
bool Move(double speed, double dest, int crush, int direction)
|
||||
{
|
||||
bool res = DMover::crushed != MoveFloor(speed, dest, crush, direction, false);
|
||||
Destroy();
|
||||
|
@ -1589,8 +1566,8 @@ void FParser::SF_FloorHeight(void)
|
|||
{
|
||||
int tagnum;
|
||||
int secnum;
|
||||
fixed_t dest;
|
||||
int returnval = 1; // haleyjd: SoM's fixes
|
||||
double dest;
|
||||
double returnval = 1; // haleyjd: SoM's fixes
|
||||
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
|
@ -1602,7 +1579,7 @@ void FParser::SF_FloorHeight(void)
|
|||
int crush = (t_argc >= 3) ? intvalue(t_argv[2]) : false;
|
||||
|
||||
i = -1;
|
||||
dest = fixedvalue(t_argv[1]);
|
||||
dest = floatvalue(t_argv[1]);
|
||||
|
||||
// set all sectors with tag
|
||||
|
||||
|
@ -1613,7 +1590,7 @@ void FParser::SF_FloorHeight(void)
|
|||
|
||||
DFloorChanger * f = new DFloorChanger(§ors[i]);
|
||||
if (!f->Move(
|
||||
abs(dest - sectors[i].CenterFloor()),
|
||||
fabs(dest - sectors[i].CenterFloor()),
|
||||
sectors[i].floorplane.PointToDist (sectors[i].centerspot, dest),
|
||||
crush? 10:-1,
|
||||
(dest > sectors[i].CenterFloor()) ? 1 : -1))
|
||||
|
@ -1630,13 +1607,11 @@ void FParser::SF_FloorHeight(void)
|
|||
script_error("sector not found with tagnum %i\n", tagnum);
|
||||
return;
|
||||
}
|
||||
returnval = sectors[secnum].CenterFloor() >> FRACBITS;
|
||||
returnval = sectors[secnum].CenterFloor();
|
||||
}
|
||||
|
||||
// return floor height
|
||||
|
||||
t_return.type = svt_int;
|
||||
t_return.value.i = returnval;
|
||||
t_return.setDouble(returnval);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1648,7 +1623,7 @@ void FParser::SF_FloorHeight(void)
|
|||
class DMoveFloor : public DFloor
|
||||
{
|
||||
public:
|
||||
DMoveFloor(sector_t * sec,int moveheight,int _m_Direction,int crush,int movespeed)
|
||||
DMoveFloor(sector_t * sec,double moveheight,int _m_Direction,int crush,double movespeed)
|
||||
: DFloor(sec)
|
||||
{
|
||||
m_Type = floorRaiseByValue;
|
||||
|
@ -1658,7 +1633,7 @@ public:
|
|||
m_FloorDestDist = moveheight;
|
||||
|
||||
// Do not interpolate instant movement floors.
|
||||
fixed_t movedist = abs(-sec->floorplane.d - moveheight);
|
||||
double movedist = fabs(-sec->floorplane.fD() - moveheight);
|
||||
if (m_Speed >= movedist)
|
||||
{
|
||||
StopInterpolation(true);
|
||||
|
@ -1680,13 +1655,14 @@ void FParser::SF_MoveFloor(void)
|
|||
{
|
||||
int secnum = -1;
|
||||
sector_t *sec;
|
||||
int tagnum, platspeed = 1, destheight, crush;
|
||||
int tagnum, crush;
|
||||
double platspeed = 1, destheight;
|
||||
|
||||
if (CheckArgs(2))
|
||||
{
|
||||
tagnum = intvalue(t_argv[0]);
|
||||
destheight = intvalue(t_argv[1]) * FRACUNIT;
|
||||
platspeed = t_argc > 2 ? fixedvalue(t_argv[2]) : FRACUNIT;
|
||||
destheight = intvalue(t_argv[1]);
|
||||
platspeed = t_argc > 2 ? floatvalue(t_argv[2]) : 1.;
|
||||
crush = (t_argc > 3 ? intvalue(t_argv[3]) : -1);
|
||||
|
||||
// move all sectors with tag
|
||||
|
@ -1698,8 +1674,8 @@ void FParser::SF_MoveFloor(void)
|
|||
// Don't start a second thinker on the same floor
|
||||
if (sec->floordata) continue;
|
||||
|
||||
new DMoveFloor(sec,sec->floorplane.PointToDist(sec->centerspot,destheight),
|
||||
destheight < sec->CenterFloor() ? -1:1,crush,platspeed);
|
||||
new DMoveFloor(sec, sec->floorplane.PointToDist(sec->centerspot, destheight),
|
||||
destheight < sec->CenterFloor() ? -1 : 1, crush, platspeed);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1716,7 +1692,7 @@ public:
|
|||
DCeilingChanger(sector_t * sec)
|
||||
: DCeiling(sec) {}
|
||||
|
||||
bool Move(fixed_t speed, fixed_t dest, int crush, int direction)
|
||||
bool Move(double speed, double dest, int crush, int direction)
|
||||
{
|
||||
bool res = DMover::crushed != MoveCeiling(speed, dest, crush, direction, false);
|
||||
Destroy();
|
||||
|
@ -1736,10 +1712,10 @@ public:
|
|||
// ceiling height of sector
|
||||
void FParser::SF_CeilingHeight(void)
|
||||
{
|
||||
fixed_t dest;
|
||||
double dest;
|
||||
int secnum;
|
||||
int tagnum;
|
||||
int returnval = 1;
|
||||
double returnval = 1;
|
||||
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
|
@ -1751,7 +1727,7 @@ void FParser::SF_CeilingHeight(void)
|
|||
int crush = (t_argc >= 3) ? intvalue(t_argv[2]) : false;
|
||||
|
||||
i = -1;
|
||||
dest = fixedvalue(t_argv[1]);
|
||||
dest = floatvalue(t_argv[1]);
|
||||
|
||||
// set all sectors with tag
|
||||
FSSectorTagIterator itr(tagnum);
|
||||
|
@ -1761,7 +1737,7 @@ void FParser::SF_CeilingHeight(void)
|
|||
|
||||
DCeilingChanger * c = new DCeilingChanger(§ors[i]);
|
||||
if (!c->Move(
|
||||
abs(dest - sectors[i].CenterCeiling()),
|
||||
fabs(dest - sectors[i].CenterCeiling()),
|
||||
sectors[i].ceilingplane.PointToDist (sectors[i].centerspot, dest),
|
||||
crush? 10:-1,
|
||||
(dest > sectors[i].CenterCeiling()) ? 1 : -1))
|
||||
|
@ -1778,12 +1754,11 @@ void FParser::SF_CeilingHeight(void)
|
|||
script_error("sector not found with tagnum %i\n", tagnum);
|
||||
return;
|
||||
}
|
||||
returnval = sectors[secnum].CenterCeiling() >> FRACBITS;
|
||||
returnval = sectors[secnum].CenterCeiling();
|
||||
}
|
||||
|
||||
// return ceiling height
|
||||
t_return.type = svt_int;
|
||||
t_return.value.i = returnval;
|
||||
t_return.setDouble(returnval);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1798,7 +1773,7 @@ class DMoveCeiling : public DCeiling
|
|||
{
|
||||
public:
|
||||
|
||||
DMoveCeiling(sector_t * sec,int tag,fixed_t destheight,fixed_t speed,int silent,int crush)
|
||||
DMoveCeiling(sector_t * sec,int tag,double destheight,double speed,int silent,int crush)
|
||||
: DCeiling(sec)
|
||||
{
|
||||
m_Crush = crush;
|
||||
|
@ -1807,10 +1782,10 @@ public:
|
|||
m_Type = DCeiling::ceilLowerByValue; // doesn't really matter as long as it's no special value
|
||||
m_Tag=tag;
|
||||
m_TopHeight=m_BottomHeight=sec->ceilingplane.PointToDist(sec->centerspot,destheight);
|
||||
m_Direction=destheight>sec->GetPlaneTexZ(sector_t::ceiling)? 1:-1;
|
||||
m_Direction=destheight>sec->GetPlaneTexZF(sector_t::ceiling)? 1:-1;
|
||||
|
||||
// Do not interpolate instant movement ceilings.
|
||||
fixed_t movedist = abs(sec->ceilingplane.d - m_BottomHeight);
|
||||
double movedist = fabs(sec->ceilingplane.fD() - m_BottomHeight);
|
||||
if (m_Speed >= movedist)
|
||||
{
|
||||
StopInterpolation (true);
|
||||
|
@ -1831,15 +1806,16 @@ void FParser::SF_MoveCeiling(void)
|
|||
{
|
||||
int secnum = -1;
|
||||
sector_t *sec;
|
||||
int tagnum, platspeed = 1, destheight;
|
||||
int tagnum;
|
||||
double platspeed = 1, destheight;
|
||||
int crush;
|
||||
int silent;
|
||||
|
||||
if (CheckArgs(2))
|
||||
{
|
||||
tagnum = intvalue(t_argv[0]);
|
||||
destheight = intvalue(t_argv[1]) * FRACUNIT;
|
||||
platspeed = /*FLOORSPEED **/ (t_argc > 2 ? fixedvalue(t_argv[2]) : FRACUNIT);
|
||||
destheight = intvalue(t_argv[1]);
|
||||
platspeed = /*FLOORSPEED **/ (t_argc > 2 ? floatvalue(t_argv[2]) : 1);
|
||||
crush=t_argc>3 ? intvalue(t_argv[3]):-1;
|
||||
silent=t_argc>4 ? intvalue(t_argv[4]):1;
|
||||
|
||||
|
@ -2190,7 +2166,7 @@ void FParser::SF_OpenDoor(void)
|
|||
if(t_argc > 2) speed = intvalue(t_argv[2]);
|
||||
else speed = 1; // 1= normal speed
|
||||
|
||||
EV_DoDoor(wait_time? DDoor::doorRaise:DDoor::doorOpen,NULL,NULL,sectag,2*FRACUNIT*clamp(speed,1,127),wait_time,0,0);
|
||||
EV_DoDoor(wait_time ? DDoor::doorRaise : DDoor::doorOpen, NULL, NULL, sectag, 2. * clamp(speed, 1, 127), wait_time, 0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2215,7 +2191,7 @@ void FParser::SF_CloseDoor(void)
|
|||
if(t_argc > 1) speed = intvalue(t_argv[1]);
|
||||
else speed = 1; // 1= normal speed
|
||||
|
||||
EV_DoDoor(DDoor::doorClose,NULL,NULL,sectag,2*FRACUNIT*clamp(speed,1,127),0,0,0);
|
||||
EV_DoDoor(DDoor::doorClose, NULL, NULL, sectag, 2.*clamp(speed, 1, 127), 0, 0, 0);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -2429,12 +2405,10 @@ void FParser::SF_SetLineTexture(void)
|
|||
|
||||
void FParser::SF_Max(void)
|
||||
{
|
||||
fixed_t n1, n2;
|
||||
|
||||
if (CheckArgs(2))
|
||||
{
|
||||
n1 = fixedvalue(t_argv[0]);
|
||||
n2 = fixedvalue(t_argv[1]);
|
||||
auto n1 = fixedvalue(t_argv[0]);
|
||||
auto n2 = fixedvalue(t_argv[1]);
|
||||
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = (n1 > n2) ? n1 : n2;
|
||||
|
@ -2450,12 +2424,10 @@ void FParser::SF_Max(void)
|
|||
|
||||
void FParser::SF_Min(void)
|
||||
{
|
||||
fixed_t n1, n2;
|
||||
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
n1 = fixedvalue(t_argv[0]);
|
||||
n2 = fixedvalue(t_argv[1]);
|
||||
auto n1 = fixedvalue(t_argv[0]);
|
||||
auto n2 = fixedvalue(t_argv[1]);
|
||||
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = (n1 < n2) ? n1 : n2;
|
||||
|
@ -2471,11 +2443,10 @@ void FParser::SF_Min(void)
|
|||
|
||||
void FParser::SF_Abs(void)
|
||||
{
|
||||
fixed_t n1;
|
||||
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
n1 = fixedvalue(t_argv[0]);
|
||||
auto n1 = fixedvalue(t_argv[0]);
|
||||
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = (n1 < 0) ? -n1 : n1;
|
||||
|
@ -2587,7 +2558,7 @@ static void FS_GiveInventory (AActor *actor, const char * type, int amount)
|
|||
AWeapon *savedPendingWeap = actor->player != NULL? actor->player->PendingWeapon : NULL;
|
||||
bool hadweap = actor->player != NULL ? actor->player->ReadyWeapon != NULL : true;
|
||||
|
||||
AInventory *item = static_cast<AInventory *>(Spawn (info, 0,0,0, NO_REPLACE));
|
||||
AInventory *item = static_cast<AInventory *>(Spawn (info));
|
||||
|
||||
// This shouldn't count for the item statistics!
|
||||
item->ClearCounters();
|
||||
|
@ -2795,7 +2766,7 @@ void FParser::SF_MaxPlayerAmmo()
|
|||
if(amount < 0) amount = 0;
|
||||
if (!iammo)
|
||||
{
|
||||
iammo = static_cast<AAmmo *>(Spawn (ammotype, 0, 0, 0, NO_REPLACE));
|
||||
iammo = static_cast<AAmmo *>(Spawn (ammotype));
|
||||
iammo->Amount = 0;
|
||||
iammo->AttachToOwner (players[playernum].mo);
|
||||
}
|
||||
|
@ -3067,166 +3038,57 @@ void FParser::SF_SetWeapon()
|
|||
//
|
||||
// movecamera(camera, targetobj, targetheight, movespeed, targetangle, anglespeed)
|
||||
//
|
||||
// This has been completely rewritten in a sane fashion, using actual vector math.
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
void FParser::SF_MoveCamera(void)
|
||||
{
|
||||
fixed_t x, y, z;
|
||||
fixed_t zdist, xydist, movespeed;
|
||||
fixed_t xstep, ystep, zstep, targetheight;
|
||||
angle_t anglespeed, anglestep, angledist, targetangle,
|
||||
mobjangle, bigangle, smallangle;
|
||||
|
||||
// I have to use floats for the math where angles are divided
|
||||
// by fixed values.
|
||||
double fangledist, fanglestep, fmovestep;
|
||||
int angledir;
|
||||
AActor* target;
|
||||
int moved;
|
||||
int quad1, quad2;
|
||||
AActor * cam;
|
||||
|
||||
angledir = moved = 0;
|
||||
|
||||
if (CheckArgs(6))
|
||||
{
|
||||
cam = actorvalue(t_argv[0]);
|
||||
|
||||
target = actorvalue(t_argv[1]);
|
||||
if(!cam || !target)
|
||||
AActor *cam = actorvalue(t_argv[0]);
|
||||
AActor *target = actorvalue(t_argv[1]);
|
||||
if(!cam || !target)
|
||||
{
|
||||
script_error("invalid target for camera\n"); return;
|
||||
}
|
||||
|
||||
targetheight = fixedvalue(t_argv[2]);
|
||||
movespeed = fixedvalue(t_argv[3]);
|
||||
targetangle = (angle_t)FixedToAngle(fixedvalue(t_argv[4]));
|
||||
anglespeed = (angle_t)FixedToAngle(fixedvalue(t_argv[5]));
|
||||
|
||||
// figure out how big one step will be
|
||||
fixedvec2 dist = cam->Vec2To(target);
|
||||
zdist = targetheight - cam->Z();
|
||||
|
||||
// Angle checking...
|
||||
// 90
|
||||
// Q1|Q0
|
||||
//180--+--0
|
||||
// Q2|Q3
|
||||
// 270
|
||||
quad1 = targetangle / ANG90;
|
||||
quad2 = cam->angle / ANG90;
|
||||
bigangle = targetangle > cam->angle ? targetangle : cam->angle;
|
||||
smallangle = targetangle < cam->angle ? targetangle : cam->angle;
|
||||
if((quad1 > quad2 && quad1 - 1 == quad2) || (quad2 > quad1 && quad2 - 1 == quad1) ||
|
||||
quad1 == quad2)
|
||||
|
||||
double targetheight = floatvalue(t_argv[2]);
|
||||
DVector3 campos = cam->Pos();
|
||||
DVector3 targpos = DVector3(target->Pos(), targetheight);
|
||||
if (campos != targpos)
|
||||
{
|
||||
angledist = bigangle - smallangle;
|
||||
angledir = targetangle > cam->angle ? 1 : -1;
|
||||
}
|
||||
else
|
||||
{
|
||||
angle_t diff180 = (bigangle + ANG180) - (smallangle + ANG180);
|
||||
|
||||
if(quad2 == 3 && quad1 == 0)
|
||||
DVector3 movement = targpos - campos;
|
||||
double movelen = movement.Length();
|
||||
double movespeed = floatvalue(t_argv[3]);
|
||||
DVector3 movepos;
|
||||
bool finished = (movespeed >= movelen);
|
||||
if (finished) movepos = targpos;
|
||||
else movepos = campos + movement.Resized(movespeed);
|
||||
|
||||
DAngle targetangle = floatvalue(t_argv[4]);
|
||||
DAngle anglespeed = floatvalue(t_argv[5]);
|
||||
DAngle diffangle = deltaangle(cam->Angles.Yaw, targetangle);
|
||||
|
||||
if (movespeed > 0 && anglespeed == 0.)
|
||||
{
|
||||
angledist = diff180;
|
||||
angledir = 1;
|
||||
}
|
||||
else if(quad1 == 3 && quad2 == 0)
|
||||
{
|
||||
angledist = diff180;
|
||||
angledir = -1;
|
||||
if (!finished) targetangle = diffangle * movespeed / movelen;
|
||||
}
|
||||
else
|
||||
{
|
||||
angledist = bigangle - smallangle;
|
||||
if(angledist > ANG180)
|
||||
{
|
||||
angledist = diff180;
|
||||
angledir = targetangle > cam->angle ? -1 : 1;
|
||||
}
|
||||
else
|
||||
angledir = targetangle > cam->angle ? 1 : -1;
|
||||
targetangle = cam->Angles.Yaw + anglespeed;
|
||||
}
|
||||
}
|
||||
|
||||
// set step variables based on distance and speed
|
||||
mobjangle = cam->AngleTo(target);
|
||||
xydist = cam->Distance2D(target);
|
||||
|
||||
xstep = FixedMul(finecosine[mobjangle >> ANGLETOFINESHIFT], movespeed);
|
||||
ystep = FixedMul(finesine[mobjangle >> ANGLETOFINESHIFT], movespeed);
|
||||
|
||||
if(xydist && movespeed)
|
||||
zstep = FixedDiv(zdist, FixedDiv(xydist, movespeed));
|
||||
else
|
||||
zstep = zdist > 0 ? movespeed : -movespeed;
|
||||
|
||||
if(xydist && movespeed && !anglespeed)
|
||||
{
|
||||
fangledist = ((double)angledist / (ANG45/45));
|
||||
fmovestep = ((double)FixedDiv(xydist, movespeed) / FRACUNIT);
|
||||
if(fmovestep)
|
||||
fanglestep = fangledist / fmovestep;
|
||||
else
|
||||
fanglestep = 360;
|
||||
|
||||
anglestep =(angle_t) (fanglestep * (ANG45/45));
|
||||
}
|
||||
else
|
||||
anglestep = anglespeed;
|
||||
|
||||
if(abs(xstep) >= (abs(dist.x) - 1))
|
||||
x = cam->X() + dist.x;
|
||||
else
|
||||
{
|
||||
x = cam->X() + xstep;
|
||||
moved = 1;
|
||||
}
|
||||
|
||||
if(abs(ystep) >= (abs(dist.y) - 1))
|
||||
y = cam->Y() + dist.y;
|
||||
else
|
||||
{
|
||||
y = cam->Y() + ystep;
|
||||
moved = 1;
|
||||
}
|
||||
|
||||
if(abs(zstep) >= (abs(zdist) - 1))
|
||||
z = targetheight;
|
||||
else
|
||||
{
|
||||
z = cam->Z() + zstep;
|
||||
moved = 1;
|
||||
}
|
||||
|
||||
if(anglestep >= angledist)
|
||||
cam->angle = targetangle;
|
||||
else
|
||||
{
|
||||
if(angledir == 1)
|
||||
{
|
||||
cam->angle += anglestep;
|
||||
moved = 1;
|
||||
}
|
||||
else if(angledir == -1)
|
||||
{
|
||||
cam->angle -= anglestep;
|
||||
moved = 1;
|
||||
}
|
||||
}
|
||||
|
||||
cam->radius=8;
|
||||
cam->height=8;
|
||||
if ((x != cam->X() || y != cam->Y()) && !P_TryMove(cam, x, y, true))
|
||||
{
|
||||
Printf("Illegal camera move to (%f, %f)\n", x/65536.f, y/65536.f);
|
||||
return;
|
||||
cam->radius = 1 / 8192.;
|
||||
cam->Height = 1 / 8192.;
|
||||
cam->SetOrigin(movepos, true);
|
||||
t_return.value.i = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
t_return.value.i = 0;
|
||||
}
|
||||
cam->SetZ(z);
|
||||
|
||||
t_return.type = svt_int;
|
||||
t_return.value.i = moved;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3348,7 +3210,7 @@ void FParser::SF_FixedValue(void)
|
|||
|
||||
void FParser::SF_SpawnExplosion()
|
||||
{
|
||||
fixed_t x, y, z;
|
||||
DVector3 pos;
|
||||
AActor* spawn;
|
||||
PClassActor * pclass;
|
||||
|
||||
|
@ -3356,14 +3218,14 @@ void FParser::SF_SpawnExplosion()
|
|||
{
|
||||
if (!(pclass=T_GetMobjType(t_argv[0]))) return;
|
||||
|
||||
x = fixedvalue(t_argv[1]);
|
||||
y = fixedvalue(t_argv[2]);
|
||||
pos.X = floatvalue(t_argv[1]);
|
||||
pos.Y = floatvalue(t_argv[2]);
|
||||
if(t_argc > 3)
|
||||
z = fixedvalue(t_argv[3]);
|
||||
pos.Z = floatvalue(t_argv[3]);
|
||||
else
|
||||
z = P_PointInSector(x, y)->floorplane.ZatPoint(x,y);
|
||||
pos.Z = P_PointInSector(pos)->floorplane.ZatPoint(pos);
|
||||
|
||||
spawn = Spawn (pclass, x, y, z, ALLOW_REPLACE);
|
||||
spawn = Spawn (pclass, pos, ALLOW_REPLACE);
|
||||
t_return.type = svt_int;
|
||||
t_return.value.i=0;
|
||||
if (spawn)
|
||||
|
@ -3417,9 +3279,9 @@ void FParser::SF_SetObjPosition()
|
|||
if (!mobj) return;
|
||||
|
||||
mobj->SetOrigin(
|
||||
fixedvalue(t_argv[1]),
|
||||
(t_argc >= 3)? fixedvalue(t_argv[2]) : mobj->Y(),
|
||||
(t_argc >= 4)? fixedvalue(t_argv[3]) : mobj->Z(), false);
|
||||
floatvalue(t_argv[1]),
|
||||
(t_argc >= 3)? floatvalue(t_argv[2]) : mobj->Y(),
|
||||
(t_argc >= 4)? floatvalue(t_argv[3]) : mobj->Z(), false);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3750,7 +3612,7 @@ void FParser::SF_Resurrect()
|
|||
return;
|
||||
|
||||
mo->SetState(state);
|
||||
mo->height = mo->GetDefault()->height;
|
||||
mo->Height = mo->GetDefault()->Height;
|
||||
mo->radius = mo->GetDefault()->radius;
|
||||
mo->flags = mo->GetDefault()->flags;
|
||||
mo->flags2 = mo->GetDefault()->flags2;
|
||||
|
@ -3771,14 +3633,15 @@ void FParser::SF_Resurrect()
|
|||
void FParser::SF_LineAttack()
|
||||
{
|
||||
AActor *mo;
|
||||
int damage, angle, slope;
|
||||
int damage;
|
||||
DAngle angle, slope;
|
||||
|
||||
if (CheckArgs(3))
|
||||
{
|
||||
mo = actorvalue(t_argv[0]);
|
||||
damage = intvalue(t_argv[2]);
|
||||
|
||||
angle = (intvalue(t_argv[1]) * (ANG45 / 45));
|
||||
angle = floatvalue(t_argv[1]);
|
||||
slope = P_AimLineAttack(mo, angle, MISSILERANGE);
|
||||
|
||||
P_LineAttack(mo, angle, MISSILERANGE, slope, damage, NAME_Hitscan, NAME_BulletPuff);
|
||||
|
@ -3828,8 +3691,7 @@ void FParser::SF_Sin()
|
|||
{
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(sin(floatvalue(t_argv[0])));
|
||||
t_return.setDouble(g_sin(floatvalue(t_argv[0])));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3838,8 +3700,7 @@ void FParser::SF_ASin()
|
|||
{
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(asin(floatvalue(t_argv[0])));
|
||||
t_return.setDouble(g_asin(floatvalue(t_argv[0])));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3848,8 +3709,7 @@ void FParser::SF_Cos()
|
|||
{
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(cos(floatvalue(t_argv[0])));
|
||||
t_return.setDouble(g_cos(floatvalue(t_argv[0])));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3858,8 +3718,7 @@ void FParser::SF_ACos()
|
|||
{
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(acos(floatvalue(t_argv[0])));
|
||||
t_return.setDouble(g_acos(floatvalue(t_argv[0])));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3868,8 +3727,7 @@ void FParser::SF_Tan()
|
|||
{
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(tan(floatvalue(t_argv[0])));
|
||||
t_return.setDouble(g_tan(floatvalue(t_argv[0])));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3878,8 +3736,7 @@ void FParser::SF_ATan()
|
|||
{
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(atan(floatvalue(t_argv[0])));
|
||||
t_return.setDouble(g_atan(floatvalue(t_argv[0])));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3888,8 +3745,7 @@ void FParser::SF_Exp()
|
|||
{
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(exp(floatvalue(t_argv[0])));
|
||||
t_return.setDouble(g_exp(floatvalue(t_argv[0])));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3897,8 +3753,7 @@ void FParser::SF_Log()
|
|||
{
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(log(floatvalue(t_argv[0])));
|
||||
t_return.setDouble(g_log(floatvalue(t_argv[0])));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3907,8 +3762,7 @@ void FParser::SF_Sqrt()
|
|||
{
|
||||
if (CheckArgs(1))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(sqrt(floatvalue(t_argv[0])));
|
||||
t_return.setDouble(g_sqrt(floatvalue(t_argv[0])));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3918,7 +3772,7 @@ void FParser::SF_Floor()
|
|||
if (CheckArgs(1))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = fixedvalue(t_argv[0]) & 0xffFF0000;
|
||||
t_return.value.f = fixedvalue(t_argv[0]) & 0xffff0000;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -3927,8 +3781,7 @@ void FParser::SF_Pow()
|
|||
{
|
||||
if (CheckArgs(2))
|
||||
{
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = FLOAT2FIXED(pow(floatvalue(t_argv[0]), floatvalue(t_argv[1])));
|
||||
t_return.setDouble(pow(floatvalue(t_argv[0]), floatvalue(t_argv[1])));
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -4008,10 +3861,9 @@ void FParser::SF_SetCorona(void)
|
|||
return;
|
||||
}
|
||||
|
||||
int num = t_argv[0].value.i; // which corona we want to modify
|
||||
int what = t_argv[1].value.i; // what we want to modify (type, color, offset,...)
|
||||
int ival = t_argv[2].value.i; // the value of what we modify
|
||||
double fval = ((double) t_argv[2].value.f / FRACUNIT);
|
||||
int num = intvalue(t_argv[0]); // which corona we want to modify
|
||||
int what = intvalue(t_argv[1]); // what we want to modify (type, color, offset,...)
|
||||
double val = floatvalue(t_argv[2]); // the value of what we modify
|
||||
|
||||
/*
|
||||
switch (what)
|
||||
|
@ -4042,7 +3894,7 @@ void FParser::SF_SetCorona(void)
|
|||
break;
|
||||
case 6:
|
||||
lspr[num].dynamic_radius = fval;
|
||||
lspr[num].dynamic_sqrradius = sqrt(lspr[num].dynamic_radius);
|
||||
lspr[num].dynamic_sqrradius = g_sqrt(lspr[num].dynamic_radius);
|
||||
break;
|
||||
default:
|
||||
CONS_Printf("Error in setcorona\n");
|
||||
|
@ -4108,11 +3960,9 @@ void FParser::SF_MobjRadius(void)
|
|||
if(t_argc > 1)
|
||||
{
|
||||
if(mo)
|
||||
mo->radius = fixedvalue(t_argv[1]);
|
||||
mo->radius = floatvalue(t_argv[1]);
|
||||
}
|
||||
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = mo ? mo->radius : 0;
|
||||
t_return.setDouble(mo ? mo->radius : 0.);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -4133,11 +3983,9 @@ void FParser::SF_MobjHeight(void)
|
|||
if(t_argc > 1)
|
||||
{
|
||||
if(mo)
|
||||
mo->height = fixedvalue(t_argv[1]);
|
||||
mo->Height = floatvalue(t_argv[1]);
|
||||
}
|
||||
|
||||
t_return.type = svt_fixed;
|
||||
t_return.value.f = mo ? mo->height : 0;
|
||||
t_return.setDouble(mo ? mo->Height : 0.);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -4260,33 +4108,34 @@ void FParser::SF_SpawnShot2(void)
|
|||
{
|
||||
AActor *source = NULL;
|
||||
PClassActor * pclass;
|
||||
int z=0;
|
||||
|
||||
double z = 0;
|
||||
|
||||
// t_argv[0] = type to spawn
|
||||
// t_argv[1] = source mobj, optional, -1 to default
|
||||
// shoots at source's angle
|
||||
|
||||
|
||||
if (CheckArgs(2))
|
||||
{
|
||||
if(t_argv[1].type == svt_int && t_argv[1].value.i < 0)
|
||||
if (t_argv[1].type == svt_int && t_argv[1].value.i < 0)
|
||||
source = Script->trigger;
|
||||
else
|
||||
source = actorvalue(t_argv[1]);
|
||||
|
||||
if (t_argc>2) z=fixedvalue(t_argv[2]);
|
||||
|
||||
if(!source) return;
|
||||
|
||||
if (!(pclass=T_GetMobjType(t_argv[0]))) return;
|
||||
|
||||
if (t_argc > 2) z = floatvalue(t_argv[2]);
|
||||
|
||||
if (!source) return;
|
||||
|
||||
if (!(pclass = T_GetMobjType(t_argv[0]))) return;
|
||||
|
||||
t_return.type = svt_mobj;
|
||||
|
||||
AActor *mo = Spawn (pclass, source->PosPlusZ(z), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
AActor *mo = Spawn(pclass, source->PosPlusZ(z), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
S_Sound (mo, CHAN_VOICE, mo->SeeSound, 1, ATTN_NORM);
|
||||
S_Sound(mo, CHAN_VOICE, mo->SeeSound, 1, ATTN_NORM);
|
||||
mo->target = source;
|
||||
P_ThrustMobj(mo, mo->angle = source->angle, mo->Speed);
|
||||
mo->Angles.Yaw = source->Angles.Yaw;
|
||||
mo->Thrust();
|
||||
if (!P_CheckMissileSpawn(mo, source->radius)) mo = NULL;
|
||||
}
|
||||
t_return.value.mobj = mo;
|
||||
|
|
|
@ -360,8 +360,7 @@ void FParser::OPmultiply(svalue_t &result,int start, int n, int stop)
|
|||
// haleyjd: 8-17
|
||||
if(left.type == svt_fixed || right.type == svt_fixed)
|
||||
{
|
||||
result.type = svt_fixed;
|
||||
result.value.f = FixedMul(fixedvalue(left), fixedvalue(right));
|
||||
result.setDouble(floatvalue(left) * floatvalue(right));
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -385,21 +384,20 @@ void FParser::OPdivide(svalue_t &result, int start, int n, int stop)
|
|||
// haleyjd: 8-17
|
||||
if(left.type == svt_fixed || right.type == svt_fixed)
|
||||
{
|
||||
fixed_t fr;
|
||||
auto fr = floatvalue(right);
|
||||
|
||||
if((fr = fixedvalue(right)) == 0)
|
||||
if(fr == 0)
|
||||
script_error("divide by zero\n");
|
||||
else
|
||||
{
|
||||
result.type = svt_fixed;
|
||||
result.value.f = FixedDiv(fixedvalue(left), fr);
|
||||
result.setDouble(floatvalue(left) / fr);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
int ir;
|
||||
auto ir = intvalue(right);
|
||||
|
||||
if(!(ir = intvalue(right)))
|
||||
if(!ir)
|
||||
script_error("divide by zero\n");
|
||||
else
|
||||
{
|
||||
|
@ -509,8 +507,7 @@ void FParser::OPincrement(svalue_t &result, int start, int n, int stop)
|
|||
}
|
||||
else
|
||||
{
|
||||
result.value.f = fixedvalue(result) + FRACUNIT;
|
||||
result.type = svt_fixed;
|
||||
result.setDouble(floatvalue(result)+1);
|
||||
var->SetValue (result);
|
||||
}
|
||||
}
|
||||
|
@ -535,8 +532,7 @@ void FParser::OPincrement(svalue_t &result, int start, int n, int stop)
|
|||
}
|
||||
else
|
||||
{
|
||||
newvalue.type = svt_fixed;
|
||||
newvalue.value.f = fixedvalue(result) + FRACUNIT;
|
||||
newvalue.setDouble(floatvalue(result)+1);
|
||||
var->SetValue (newvalue);
|
||||
}
|
||||
}
|
||||
|
@ -574,7 +570,7 @@ void FParser::OPdecrement(svalue_t &result, int start, int n, int stop)
|
|||
}
|
||||
else
|
||||
{
|
||||
result.value.f = fixedvalue(result) - FRACUNIT;
|
||||
result.setDouble(floatvalue(result)-1);
|
||||
result.type = svt_fixed;
|
||||
var->SetValue (result);
|
||||
}
|
||||
|
@ -600,8 +596,7 @@ void FParser::OPdecrement(svalue_t &result, int start, int n, int stop)
|
|||
}
|
||||
else
|
||||
{
|
||||
newvalue.type = svt_fixed;
|
||||
newvalue.value.f = fixedvalue(result) - FRACUNIT;
|
||||
newvalue.setDouble(floatvalue(result)-1);
|
||||
var->SetValue (newvalue);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -567,8 +567,7 @@ void FParser::SimpleEvaluate(svalue_t &returnvar, int n)
|
|||
case number:
|
||||
if(strchr(Tokens[n], '.'))
|
||||
{
|
||||
returnvar.type = svt_fixed;
|
||||
returnvar.value.f = (fixed_t)(atof(Tokens[n]) * FRACUNIT);
|
||||
returnvar.setDouble(atof(Tokens[n]));
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
@ -82,15 +82,17 @@ enum
|
|||
//
|
||||
//
|
||||
//==========================================================================
|
||||
typedef int fsfix;
|
||||
|
||||
struct svalue_t
|
||||
{
|
||||
int type;
|
||||
|
||||
FString string;
|
||||
union
|
||||
{
|
||||
int i;
|
||||
fixed_t f; // haleyjd: 8-17
|
||||
fsfix f; // haleyjd: 8-17
|
||||
AActor *mobj;
|
||||
} value;
|
||||
|
||||
|
@ -106,10 +108,28 @@ struct svalue_t
|
|||
string = other.string;
|
||||
value = other.value;
|
||||
}
|
||||
|
||||
void setInt(int ip)
|
||||
{
|
||||
value.i = ip;
|
||||
type = svt_int;
|
||||
}
|
||||
|
||||
void setFixed(fsfix fp)
|
||||
{
|
||||
value.f = fp;
|
||||
type = svt_fixed;
|
||||
}
|
||||
|
||||
void setDouble(double dp)
|
||||
{
|
||||
value.f = fsfix(dp/65536);
|
||||
type = svt_fixed;
|
||||
}
|
||||
};
|
||||
|
||||
int intvalue(const svalue_t & v);
|
||||
fixed_t fixedvalue(const svalue_t & v);
|
||||
fsfix fixedvalue(const svalue_t & v);
|
||||
double floatvalue(const svalue_t & v);
|
||||
const char *stringvalue(const svalue_t & v);
|
||||
AActor *actorvalue(const svalue_t &svalue);
|
||||
|
@ -153,7 +173,7 @@ public:
|
|||
union value_t
|
||||
{
|
||||
SDWORD i;
|
||||
fixed_t fixed; // haleyjd: fixed-point
|
||||
fsfix fixed; // haleyjd: fixed-point
|
||||
|
||||
// the following are only used in the global script so we don't need to bother with them
|
||||
// when serializing variables.
|
||||
|
|
|
@ -66,7 +66,7 @@
|
|||
int intvalue(const svalue_t &v)
|
||||
{
|
||||
return (v.type == svt_string ? atoi(v.string) :
|
||||
v.type == svt_fixed ? (int)(v.value.f / FRACUNIT) :
|
||||
v.type == svt_fixed ? (int)(v.value.f / 65536.) :
|
||||
v.type == svt_mobj ? -1 : v.value.i );
|
||||
}
|
||||
|
||||
|
@ -76,11 +76,11 @@ int intvalue(const svalue_t &v)
|
|||
//
|
||||
//==========================================================================
|
||||
|
||||
fixed_t fixedvalue(const svalue_t &v)
|
||||
fsfix fixedvalue(const svalue_t &v)
|
||||
{
|
||||
return (v.type == svt_fixed ? v.value.f :
|
||||
v.type == svt_string ? (fixed_t)(atof(v.string) * FRACUNIT) :
|
||||
v.type == svt_mobj ? -1*FRACUNIT : v.value.i * FRACUNIT );
|
||||
v.type == svt_string ? (fsfix)(atof(v.string) * 65536.) :
|
||||
v.type == svt_mobj ? -65536 : v.value.i * 65536 );
|
||||
}
|
||||
|
||||
//==========================================================================
|
||||
|
@ -93,7 +93,7 @@ double floatvalue(const svalue_t &v)
|
|||
{
|
||||
return
|
||||
v.type == svt_string ? atof(v.string) :
|
||||
v.type == svt_fixed ? FIXED2DBL(v.value.f) :
|
||||
v.type == svt_fixed ? v.value.f * 65536. :
|
||||
v.type == svt_mobj ? -1. : (double)v.value.i;
|
||||
}
|
||||
|
||||
|
@ -118,7 +118,7 @@ const char *stringvalue(const svalue_t & v)
|
|||
|
||||
case svt_fixed:
|
||||
{
|
||||
double val = ((double)v.value.f) / FRACUNIT;
|
||||
double val = v.value.f / 65536.;
|
||||
mysnprintf(buffer, countof(buffer), "%g", val);
|
||||
return buffer;
|
||||
}
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
// PIT_VileCheck
|
||||
// Detect a corpse that could be raised.
|
||||
//
|
||||
void A_Fire(AActor *self, int height);
|
||||
void A_Fire(AActor *self, double height);
|
||||
|
||||
|
||||
//
|
||||
|
@ -50,13 +50,13 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireCrackle)
|
|||
DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Fire)
|
||||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
PARAM_FIXED_OPT(height) { height = 0; }
|
||||
PARAM_FLOAT_OPT(height) { height = 0; }
|
||||
|
||||
A_Fire(self, height);
|
||||
return 0;
|
||||
}
|
||||
|
||||
void A_Fire(AActor *self, int height)
|
||||
void A_Fire(AActor *self, double height)
|
||||
{
|
||||
AActor *dest;
|
||||
|
||||
|
@ -68,7 +68,7 @@ void A_Fire(AActor *self, int height)
|
|||
if (!P_CheckSight (self->target, dest, 0) )
|
||||
return;
|
||||
|
||||
fixedvec3 newpos = dest->Vec3Angle(24 * FRACUNIT, dest->angle, height);
|
||||
DVector3 newpos = dest->Vec3Angle(24., dest->Angles.Yaw, height);
|
||||
self->SetOrigin(newpos, true);
|
||||
}
|
||||
|
||||
|
@ -116,7 +116,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_VileAttack)
|
|||
PARAM_INT_OPT (dmg) { dmg = 20; }
|
||||
PARAM_INT_OPT (blastdmg) { blastdmg = 70; }
|
||||
PARAM_INT_OPT (blastrad) { blastrad = 70; }
|
||||
PARAM_FIXED_OPT (thrust) { thrust = FRACUNIT; }
|
||||
PARAM_FLOAT_OPT (thrust) { thrust = 1; }
|
||||
PARAM_NAME_OPT (dmgtype) { dmgtype = NAME_Fire; }
|
||||
PARAM_INT_OPT (flags) { flags = 0; }
|
||||
|
||||
|
@ -147,14 +147,14 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_VileAttack)
|
|||
if (fire != NULL)
|
||||
{
|
||||
// move the fire between the vile and the player
|
||||
fixedvec3 pos = target->Vec3Angle(-24 * FRACUNIT, self->angle, 0);
|
||||
DVector3 pos = target->Vec3Angle(-24., self->Angles.Yaw, 0);
|
||||
fire->SetOrigin (pos, true);
|
||||
|
||||
P_RadiusAttack (fire, self, blastdmg, blastrad, dmgtype, 0);
|
||||
}
|
||||
if (!(target->flags7 & MF7_DONTTHRUST))
|
||||
{
|
||||
target->vel.z = Scale(thrust, 1000, target->Mass);
|
||||
target->Vel.Z = thrust * 1000 / MAX(1, target->Mass);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -31,13 +31,13 @@ DEFINE_ACTION_FUNCTION(AActor, A_BrainPain)
|
|||
return 0;
|
||||
}
|
||||
|
||||
static void BrainishExplosion (fixed_t x, fixed_t y, fixed_t z)
|
||||
static void BrainishExplosion (const DVector3 &pos)
|
||||
{
|
||||
AActor *boom = Spawn("Rocket", x, y, z, NO_REPLACE);
|
||||
AActor *boom = Spawn("Rocket", pos, NO_REPLACE);
|
||||
if (boom != NULL)
|
||||
{
|
||||
boom->DeathSound = "misc/brainexplode";
|
||||
boom->vel.z = pr_brainscream() << 9;
|
||||
boom->Vel.Z = pr_brainscream() /128.;
|
||||
|
||||
PClassActor *cls = PClass::FindActor("BossBrain");
|
||||
if (cls != NULL)
|
||||
|
@ -57,12 +57,11 @@ static void BrainishExplosion (fixed_t x, fixed_t y, fixed_t z)
|
|||
DEFINE_ACTION_FUNCTION(AActor, A_BrainScream)
|
||||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
fixed_t x;
|
||||
|
||||
for (x = self->X() - 196*FRACUNIT; x < self->X() + 320*FRACUNIT; x += 8*FRACUNIT)
|
||||
|
||||
for (double x = -196; x < +320; x += 8)
|
||||
{
|
||||
BrainishExplosion (x, self->Y() - 320*FRACUNIT,
|
||||
128 + (pr_brainscream() << (FRACBITS + 1)));
|
||||
// (1 / 512.) is actually what the original value of 128 did, even though it probably meant 128 map units.
|
||||
BrainishExplosion(self->Vec2OffsetZ(x, -320, (1 / 512.) + pr_brainexplode() * 2));
|
||||
}
|
||||
S_Sound (self, CHAN_VOICE, "brain/death", 1, ATTN_NONE);
|
||||
return 0;
|
||||
|
@ -71,9 +70,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_BrainScream)
|
|||
DEFINE_ACTION_FUNCTION(AActor, A_BrainExplode)
|
||||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
fixed_t x = self->X() + pr_brainexplode.Random2()*2048;
|
||||
fixed_t z = 128 + pr_brainexplode()*2*FRACUNIT;
|
||||
BrainishExplosion (x, self->Y(), z);
|
||||
double x = pr_brainexplode.Random2() / 32.;
|
||||
DVector3 pos = self->Vec2OffsetZ(x, 0, 1 / 512. + pr_brainexplode() * 2);
|
||||
BrainishExplosion(pos);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -144,17 +143,17 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BrainSpit)
|
|||
spit->master = self;
|
||||
// [RH] Do this correctly for any trajectory. Doom would divide by 0
|
||||
// if the target had the same y coordinate as the spitter.
|
||||
if ((spit->vel.x | spit->vel.y) == 0)
|
||||
if (spit->Vel.X == 0 && spit->Vel.Y == 0)
|
||||
{
|
||||
spit->special2 = 0;
|
||||
}
|
||||
else if (abs(spit->vel.y) > abs(spit->vel.x))
|
||||
else if (fabs(spit->Vel.X) > fabs(spit->Vel.Y))
|
||||
{
|
||||
spit->special2 = (targ->Y() - self->Y()) / spit->vel.y;
|
||||
spit->special2 = int((targ->Y() - self->Y()) / spit->Vel.Y);
|
||||
}
|
||||
else
|
||||
{
|
||||
spit->special2 = (targ->X() - self->X()) / spit->vel.x;
|
||||
spit->special2 = int((targ->X() - self->X()) / spit->Vel.X);
|
||||
}
|
||||
// [GZ] Calculates when the projectile will have reached destination
|
||||
spit->special2 += level.maptime;
|
||||
|
|
|
@ -47,7 +47,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BarrelDestroy)
|
|||
|
||||
if (dmflags2 & DF2_BARRELS_RESPAWN)
|
||||
{
|
||||
self->height = self->GetDefault()->height;
|
||||
self->Height = self->GetDefault()->Height;
|
||||
self->renderflags |= RF_INVISIBLE;
|
||||
self->flags &= ~MF_SOLID;
|
||||
}
|
||||
|
|
|
@ -30,9 +30,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_Punch)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
int pitch;
|
||||
DAngle pitch;
|
||||
FTranslatedLineTarget t;
|
||||
|
||||
if (self->player != NULL)
|
||||
|
@ -50,9 +50,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Punch)
|
|||
if (self->FindInventory<APowerStrength>())
|
||||
damage *= 10;
|
||||
|
||||
angle = self->angle;
|
||||
|
||||
angle += pr_punch.Random2() << 18;
|
||||
angle = self->Angles.Yaw + pr_punch.Random2() * (5.625 / 256);
|
||||
pitch = P_AimLineAttack (self, angle, MELEERANGE);
|
||||
|
||||
P_LineAttack (self, angle, MELEERANGE, pitch, damage, NAME_Melee, NAME_BulletPuff, LAF_ISMELEEATTACK, &t);
|
||||
|
@ -61,7 +59,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Punch)
|
|||
if (t.linetarget)
|
||||
{
|
||||
S_Sound (self, CHAN_WEAPON, "*fist", 1, ATTN_NORM);
|
||||
self->angle = t.angleFromSource;
|
||||
self->Angles.Yaw = t.angleFromSource;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -124,15 +122,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Saw)
|
|||
PARAM_INT_OPT (damage) { damage = 2; }
|
||||
PARAM_CLASS_OPT (pufftype, AActor) { pufftype = NULL; }
|
||||
PARAM_INT_OPT (flags) { flags = 0; }
|
||||
PARAM_FIXED_OPT (range) { range = 0; }
|
||||
PARAM_ANGLE_OPT(spread_xy) { spread_xy = 33554432; /*angle_t(2.8125 * (ANGLE_90 / 90.0));*/ } // The floating point expression does not get optimized away.
|
||||
PARAM_ANGLE_OPT (spread_z) { spread_z = 0; }
|
||||
PARAM_FIXED_OPT (lifesteal) { lifesteal = 0; }
|
||||
PARAM_FLOAT_OPT (range) { range = 0; }
|
||||
PARAM_ANGLE_OPT (spread_xy) { spread_xy = 2.8125; }
|
||||
PARAM_ANGLE_OPT (spread_z) { spread_z = 0.; }
|
||||
PARAM_FLOAT_OPT (lifesteal) { lifesteal = 0; }
|
||||
PARAM_INT_OPT (lifestealmax) { lifestealmax = 0; }
|
||||
PARAM_CLASS_OPT (armorbonustype, ABasicArmorBonus) { armorbonustype = NULL; }
|
||||
|
||||
angle_t angle;
|
||||
angle_t slope;
|
||||
DAngle angle;
|
||||
DAngle slope;
|
||||
player_t *player;
|
||||
FTranslatedLineTarget t;
|
||||
int actualdamage;
|
||||
|
@ -155,12 +153,12 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Saw)
|
|||
damage *= (pr_saw()%10+1);
|
||||
}
|
||||
if (range == 0)
|
||||
{ // use meleerange + 1 so the puff doesn't skip the flash (i.e. plays all states)
|
||||
range = MELEERANGE+1;
|
||||
{
|
||||
range = SAWRANGE;
|
||||
}
|
||||
|
||||
angle = self->angle + (pr_saw.Random2() * (spread_xy / 255));
|
||||
slope = P_AimLineAttack (self, angle, range, &t) + (pr_saw.Random2() * (spread_z / 255));
|
||||
angle = self->Angles.Yaw + spread_xy * (pr_saw.Random2() / 255.);
|
||||
slope = P_AimLineAttack (self, angle, range, &t) + spread_z * (pr_saw.Random2() / 255.);
|
||||
|
||||
AWeapon *weapon = self->player->ReadyWeapon;
|
||||
if ((weapon != NULL) && !(flags & SF_NOUSEAMMO) && !(!t.linetarget && (flags & SF_NOUSEAMMOMISS)) && !(weapon->WeaponFlags & WIF_DEHAMMO) && ACTION_CALL_FROM_WEAPON())
|
||||
|
@ -209,8 +207,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Saw)
|
|||
if (armorbonustype != NULL)
|
||||
{
|
||||
assert(armorbonustype->IsDescendantOf (RUNTIME_CLASS(ABasicArmorBonus)));
|
||||
ABasicArmorBonus *armorbonus = static_cast<ABasicArmorBonus *>(Spawn(armorbonustype, 0,0,0, NO_REPLACE));
|
||||
armorbonus->SaveAmount *= (actualdamage * lifesteal) >> FRACBITS;
|
||||
ABasicArmorBonus *armorbonus = static_cast<ABasicArmorBonus *>(Spawn(armorbonustype));
|
||||
armorbonus->SaveAmount = int(armorbonus->SaveAmount * actualdamage * lifesteal);
|
||||
armorbonus->MaxSaveAmount = lifestealmax <= 0 ? armorbonus->MaxSaveAmount : lifestealmax;
|
||||
armorbonus->flags |= MF_DROPPED;
|
||||
armorbonus->ClearCounters();
|
||||
|
@ -224,7 +222,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Saw)
|
|||
|
||||
else
|
||||
{
|
||||
P_GiveBody (self, (actualdamage * lifesteal) >> FRACBITS, lifestealmax);
|
||||
P_GiveBody (self, int(actualdamage * lifesteal), lifestealmax);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -233,20 +231,21 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Saw)
|
|||
// turn to face target
|
||||
if (!(flags & SF_NOTURN))
|
||||
{
|
||||
angle = t.angleFromSource;
|
||||
if (angle - self->angle > ANG180)
|
||||
DAngle anglediff = deltaangle(self->Angles.Yaw, t.angleFromSource);
|
||||
|
||||
if (anglediff < 0.0)
|
||||
{
|
||||
if (angle - self->angle < (angle_t)(-ANG90 / 20))
|
||||
self->angle = angle + ANG90 / 21;
|
||||
if (anglediff < -4.5)
|
||||
self->Angles.Yaw = angle + 90.0 / 21;
|
||||
else
|
||||
self->angle -= ANG90 / 20;
|
||||
self->Angles.Yaw -= 4.5;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (angle - self->angle > ANG90 / 20)
|
||||
self->angle = angle - ANG90 / 21;
|
||||
if (anglediff > 4.5)
|
||||
self->Angles.Yaw = angle - 90.0 / 21;
|
||||
else
|
||||
self->angle += ANG90 / 20;
|
||||
self->Angles.Yaw += 4.5;
|
||||
}
|
||||
}
|
||||
if (!(flags & SF_NOPULLIN))
|
||||
|
@ -280,7 +279,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireShotgun)
|
|||
}
|
||||
player->mo->PlayAttacking2 ();
|
||||
|
||||
angle_t pitch = P_BulletSlope (self);
|
||||
DAngle pitch = P_BulletSlope (self);
|
||||
|
||||
for (i = 0; i < 7; i++)
|
||||
{
|
||||
|
@ -297,7 +296,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireShotgun2)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int i;
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
player_t *player;
|
||||
|
||||
|
@ -318,13 +317,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireShotgun2)
|
|||
player->mo->PlayAttacking2 ();
|
||||
|
||||
|
||||
angle_t pitch = P_BulletSlope (self);
|
||||
DAngle pitch = P_BulletSlope (self);
|
||||
|
||||
for (i=0 ; i<20 ; i++)
|
||||
{
|
||||
damage = 5*(pr_fireshotgun2()%3+1);
|
||||
angle = self->angle;
|
||||
angle += pr_fireshotgun2.Random2() << 19;
|
||||
angle = self->Angles.Yaw + pr_fireshotgun2.Random2() * (11.25 / 256);
|
||||
|
||||
// Doom adjusts the bullet slope by shifting a random number [-255,255]
|
||||
// left 5 places. At 2048 units away, this means the vertical position
|
||||
|
@ -335,7 +333,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireShotgun2)
|
|||
P_LineAttack (self,
|
||||
angle,
|
||||
PLAYERMISSILERANGE,
|
||||
pitch + (pr_fireshotgun2.Random2() * 332063), damage,
|
||||
pitch + pr_fireshotgun2.Random2() * (7.097 / 256), damage,
|
||||
NAME_Hitscan, NAME_BulletPuff);
|
||||
}
|
||||
return 0;
|
||||
|
@ -507,10 +505,10 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FireSTGrenade)
|
|||
}
|
||||
|
||||
// Temporarily raise the pitch to send the grenade slightly upwards
|
||||
fixed_t SavedPlayerPitch = self->pitch;
|
||||
self->pitch -= (1152 << FRACBITS);
|
||||
DAngle SavedPlayerPitch = self->Angles.Pitch;
|
||||
self->Angles.Pitch -= 6.328125; //(1152 << F RACBITS);
|
||||
P_SpawnPlayerMissile(self, grenade);
|
||||
self->pitch = SavedPlayerPitch;
|
||||
self->Angles.Pitch = SavedPlayerPitch;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -572,7 +570,11 @@ static void FireRailgun(AActor *self, int offset_xy, bool fromweapon)
|
|||
|
||||
damage = deathmatch ? 100 : 150;
|
||||
|
||||
P_RailAttack (self, damage, offset_xy);
|
||||
FRailParams p;
|
||||
p.source = self;
|
||||
p.damage = damage;
|
||||
p.offset_xy = offset_xy;
|
||||
P_RailAttack (&p);
|
||||
}
|
||||
|
||||
|
||||
|
@ -625,7 +627,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireBFG)
|
|||
return 0;
|
||||
}
|
||||
|
||||
P_SpawnPlayerMissile (self, 0, 0, 0, PClass::FindActor("BFGBall"), self->angle, NULL, NULL, !!(dmflags2 & DF2_NO_FREEAIMBFG));
|
||||
P_SpawnPlayerMissile (self, 0, 0, 0, PClass::FindActor("BFGBall"), self->Angles.Yaw, NULL, NULL, !!(dmflags2 & DF2_NO_FREEAIMBFG));
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -638,25 +640,25 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BFGSpray)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
PARAM_CLASS_OPT (spraytype, AActor) { spraytype = NULL; }
|
||||
PARAM_INT_OPT (numrays) { numrays = 40; }
|
||||
PARAM_INT_OPT (damagecnt) { damagecnt = 15; }
|
||||
PARAM_ANGLE_OPT (angle) { angle = ANGLE_90; }
|
||||
PARAM_FIXED_OPT (distance) { distance = 16*64*FRACUNIT; }
|
||||
PARAM_ANGLE_OPT (vrange) { vrange = 32*ANGLE_1; }
|
||||
PARAM_INT_OPT (numrays) { numrays = 0; }
|
||||
PARAM_INT_OPT (damagecnt) { damagecnt = 0; }
|
||||
PARAM_ANGLE_OPT (angle) { angle = 0.; }
|
||||
PARAM_FLOAT_OPT (distance) { distance = 0; }
|
||||
PARAM_ANGLE_OPT (vrange) { vrange = 0.; }
|
||||
PARAM_INT_OPT (defdamage) { defdamage = 0; }
|
||||
|
||||
int i;
|
||||
int j;
|
||||
int damage;
|
||||
angle_t an;
|
||||
DAngle an;
|
||||
FTranslatedLineTarget t;
|
||||
|
||||
if (spraytype == NULL) spraytype = PClass::FindActor("BFGExtra");
|
||||
if (numrays <= 0) numrays = 40;
|
||||
if (damagecnt <= 0) damagecnt = 15;
|
||||
if (angle == 0) angle = ANG90;
|
||||
if (distance <= 0) distance = 16 * 64 * FRACUNIT;
|
||||
if (vrange == 0) vrange = ANGLE_1 * 32;
|
||||
if (angle == 0) angle = 90.;
|
||||
if (distance <= 0) distance = 16 * 64;
|
||||
if (vrange == 0) vrange = 32.;
|
||||
|
||||
// [RH] Don't crash if no target
|
||||
if (!self->target)
|
||||
|
@ -665,14 +667,14 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BFGSpray)
|
|||
// offset angles from its attack angle
|
||||
for (i = 0; i < numrays; i++)
|
||||
{
|
||||
an = self->angle - angle / 2 + angle / numrays*i;
|
||||
an = self->Angles.Yaw - angle / 2 + angle / numrays*i;
|
||||
|
||||
// self->target is the originator (player) of the missile
|
||||
P_AimLineAttack(self->target, an, distance, &t, vrange);
|
||||
|
||||
if (t.linetarget != NULL)
|
||||
{
|
||||
AActor *spray = Spawn(spraytype, t.linetarget->PosPlusZ(t.linetarget->height >> 2), ALLOW_REPLACE);
|
||||
AActor *spray = Spawn(spraytype, t.linetarget->PosPlusZ(t.linetarget->Height / 4), ALLOW_REPLACE);
|
||||
|
||||
int dmgFlags = 0;
|
||||
FName dmgType = NAME_BFGSplash;
|
||||
|
@ -702,7 +704,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_BFGSpray)
|
|||
damage = defdamage;
|
||||
}
|
||||
|
||||
int newdam = P_DamageMobj(t.linetarget, self->target, self->target, damage, dmgType, dmgFlags|DMG_USEANGLE, t.angleFromSource);
|
||||
int newdam = P_DamageMobj(t.linetarget, self->target, self->target, damage, dmgType, dmgFlags|DMG_USEANGLE, t.angleFromSource.Degrees);
|
||||
P_TraceBleed(newdam > 0 ? newdam : damage, &t, self);
|
||||
}
|
||||
}
|
||||
|
@ -755,16 +757,16 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireOldBFG)
|
|||
self->player->extralight = 2;
|
||||
|
||||
// Save values temporarily
|
||||
angle_t SavedPlayerAngle = self->angle;
|
||||
fixed_t SavedPlayerPitch = self->pitch;
|
||||
DAngle SavedPlayerAngle = self->Angles.Yaw;
|
||||
DAngle SavedPlayerPitch = self->Angles.Pitch;
|
||||
for (int i = 0; i < 2; i++) // Spawn two plasma balls in sequence
|
||||
{
|
||||
self->angle += ((pr_oldbfg()&127) - 64) * (ANG90/768);
|
||||
self->pitch += ((pr_oldbfg()&127) - 64) * (ANG90/640);
|
||||
self->Angles.Yaw += ((pr_oldbfg()&127) - 64) * (90./768);
|
||||
self->Angles.Pitch += ((pr_oldbfg()&127) - 64) * (90./640);
|
||||
mo = P_SpawnPlayerMissile (self, plasma[i]);
|
||||
// Restore saved values
|
||||
self->angle = SavedPlayerAngle;
|
||||
self->pitch = SavedPlayerPitch;
|
||||
self->Angles.Yaw = SavedPlayerAngle;
|
||||
self->Angles.Pitch = SavedPlayerPitch;
|
||||
}
|
||||
if (doesautoaim && weapon != NULL)
|
||||
{ // Restore autoaim setting
|
||||
|
|
|
@ -15,7 +15,7 @@
|
|||
// firing three missiles in three different directions?
|
||||
// Doesn't look like it.
|
||||
//
|
||||
#define FATSPREAD (ANG90/8)
|
||||
#define FATSPREAD (90./8)
|
||||
|
||||
DEFINE_ACTION_FUNCTION(AActor, A_FatRaise)
|
||||
{
|
||||
|
@ -32,7 +32,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack1)
|
|||
PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; }
|
||||
|
||||
AActor *missile;
|
||||
angle_t an;
|
||||
|
||||
if (!self->target)
|
||||
return 0;
|
||||
|
@ -41,16 +40,14 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack1)
|
|||
|
||||
A_FaceTarget (self);
|
||||
// Change direction to ...
|
||||
self->angle += FATSPREAD;
|
||||
self->Angles.Yaw += FATSPREAD;
|
||||
P_SpawnMissile (self, self->target, spawntype);
|
||||
|
||||
missile = P_SpawnMissile (self, self->target, spawntype);
|
||||
if (missile != NULL)
|
||||
{
|
||||
missile->angle += FATSPREAD;
|
||||
an = missile->angle >> ANGLETOFINESHIFT;
|
||||
missile->vel.x = FixedMul (missile->Speed, finecosine[an]);
|
||||
missile->vel.y = FixedMul (missile->Speed, finesine[an]);
|
||||
missile->Angles.Yaw += FATSPREAD;
|
||||
missile->VelFromAngle();
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -61,7 +58,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack2)
|
|||
PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; }
|
||||
|
||||
AActor *missile;
|
||||
angle_t an;
|
||||
|
||||
if (!self->target)
|
||||
return 0;
|
||||
|
@ -70,16 +66,14 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack2)
|
|||
|
||||
A_FaceTarget (self);
|
||||
// Now here choose opposite deviation.
|
||||
self->angle -= FATSPREAD;
|
||||
self->Angles.Yaw -= FATSPREAD;
|
||||
P_SpawnMissile (self, self->target, spawntype);
|
||||
|
||||
missile = P_SpawnMissile (self, self->target, spawntype);
|
||||
if (missile != NULL)
|
||||
{
|
||||
missile->angle -= FATSPREAD*2;
|
||||
an = missile->angle >> ANGLETOFINESHIFT;
|
||||
missile->vel.x = FixedMul (missile->Speed, finecosine[an]);
|
||||
missile->vel.y = FixedMul (missile->Speed, finesine[an]);
|
||||
missile->Angles.Yaw -= FATSPREAD*2;
|
||||
missile->VelFromAngle();
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -90,7 +84,6 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack3)
|
|||
PARAM_CLASS_OPT(spawntype, AActor) { spawntype = NULL; }
|
||||
|
||||
AActor *missile;
|
||||
angle_t an;
|
||||
|
||||
if (!self->target)
|
||||
return 0;
|
||||
|
@ -102,19 +95,15 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_FatAttack3)
|
|||
missile = P_SpawnMissile (self, self->target, spawntype);
|
||||
if (missile != NULL)
|
||||
{
|
||||
missile->angle -= FATSPREAD/2;
|
||||
an = missile->angle >> ANGLETOFINESHIFT;
|
||||
missile->vel.x = FixedMul (missile->Speed, finecosine[an]);
|
||||
missile->vel.y = FixedMul (missile->Speed, finesine[an]);
|
||||
missile->Angles.Yaw -= FATSPREAD/2;
|
||||
missile->VelFromAngle();
|
||||
}
|
||||
|
||||
missile = P_SpawnMissile (self, self->target, spawntype);
|
||||
if (missile != NULL)
|
||||
{
|
||||
missile->angle += FATSPREAD/2;
|
||||
an = missile->angle >> ANGLETOFINESHIFT;
|
||||
missile->vel.x = FixedMul (missile->Speed, finecosine[an]);
|
||||
missile->vel.y = FixedMul (missile->Speed, finesine[an]);
|
||||
missile->Angles.Yaw += FATSPREAD/2;
|
||||
missile->VelFromAngle();
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -137,8 +126,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Mushroom)
|
|||
PARAM_CLASS_OPT (spawntype, AActor) { spawntype = NULL; }
|
||||
PARAM_INT_OPT (n) { n = 0; }
|
||||
PARAM_INT_OPT (flags) { flags = 0; }
|
||||
PARAM_FIXED_OPT (vrange) { vrange = 4*FRACUNIT; }
|
||||
PARAM_FIXED_OPT (hrange) { hrange = FRACUNIT/2; }
|
||||
PARAM_FLOAT_OPT (vrange) { vrange = 4; }
|
||||
PARAM_FLOAT_OPT (hrange) { hrange = 0.5; }
|
||||
|
||||
int i, j;
|
||||
|
||||
|
@ -152,20 +141,20 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Mushroom)
|
|||
}
|
||||
|
||||
P_RadiusAttack (self, self->target, 128, 128, self->DamageType, (flags & MSF_DontHurt) ? 0 : RADF_HURTSOURCE);
|
||||
P_CheckSplash(self, 128<<FRACBITS);
|
||||
P_CheckSplash(self, 128.);
|
||||
|
||||
// Now launch mushroom cloud
|
||||
AActor *target = Spawn("Mapspot", self->Pos(), NO_REPLACE); // We need something to aim at.
|
||||
AActor *master = (flags & MSF_DontHurt) ? (AActor*)(self->target) : self;
|
||||
target->height = self->height;
|
||||
target->Height = self->Height;
|
||||
for (i = -n; i <= n; i += 8)
|
||||
{
|
||||
for (j = -n; j <= n; j += 8)
|
||||
{
|
||||
AActor *mo;
|
||||
target->SetXYZ(
|
||||
self->X() + (i << FRACBITS), // Aim in many directions from source
|
||||
self->Y() + (j << FRACBITS),
|
||||
self->X() + i, // Aim in many directions from source
|
||||
self->Y() + j,
|
||||
self->Z() + (P_AproxDistance(i,j) * vrange)); // Aim up fairly high
|
||||
if ((flags & MSF_Classic) || // Flag explicitely set, or no flags and compat options
|
||||
(flags == 0 && (self->state->DefineFlags & SDF_DEHACKED) && (i_compatflags & COMPATF_MUSHROOM)))
|
||||
|
@ -178,9 +167,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_Mushroom)
|
|||
}
|
||||
if (mo != NULL)
|
||||
{ // Slow it down a bit
|
||||
mo->vel.x = FixedMul(mo->vel.x, hrange);
|
||||
mo->vel.y = FixedMul(mo->vel.y, hrange);
|
||||
mo->vel.z = FixedMul(mo->vel.z, hrange);
|
||||
mo->Vel *= hrange;
|
||||
mo->flags &= ~MF_NOGRAVITY; // Make debris fall under gravity
|
||||
}
|
||||
}
|
||||
|
|
|
@ -35,7 +35,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_KeenDie)
|
|||
}
|
||||
}
|
||||
|
||||
EV_DoDoor (DDoor::doorOpen, NULL, NULL, doortag, 2*FRACUNIT, 0, 0, 0);
|
||||
EV_DoDoor (DDoor::doorOpen, NULL, NULL, doortag, 2., 0, 0, 0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -19,12 +19,9 @@
|
|||
// Fly at the player like a missile.
|
||||
//
|
||||
|
||||
void A_SkullAttack(AActor *self, fixed_t speed)
|
||||
void A_SkullAttack(AActor *self, double speed)
|
||||
{
|
||||
AActor *dest;
|
||||
angle_t an;
|
||||
int dist;
|
||||
|
||||
if (!self->target)
|
||||
return;
|
||||
|
||||
|
@ -33,21 +30,14 @@ void A_SkullAttack(AActor *self, fixed_t speed)
|
|||
|
||||
S_Sound (self, CHAN_VOICE, self->AttackSound, 1, ATTN_NORM);
|
||||
A_FaceTarget (self);
|
||||
an = self->angle >> ANGLETOFINESHIFT;
|
||||
self->vel.x = FixedMul (speed, finecosine[an]);
|
||||
self->vel.y = FixedMul (speed, finesine[an]);
|
||||
dist = self->AproxDistance (dest);
|
||||
dist = dist / speed;
|
||||
|
||||
if (dist < 1)
|
||||
dist = 1;
|
||||
self->vel.z = (dest->Z() + (dest->height>>1) - self->Z()) / dist;
|
||||
self->VelFromAngle(speed);
|
||||
self->Vel.Z = (dest->Center() - self->Z()) / self->DistanceBySpeed(dest, speed);
|
||||
}
|
||||
|
||||
DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_SkullAttack)
|
||||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
PARAM_FIXED_OPT(speed) { speed = SKULLSPEED; }
|
||||
PARAM_FLOAT_OPT(speed) { speed = SKULLSPEED; }
|
||||
|
||||
if (speed <= 0)
|
||||
speed = SKULLSPEED;
|
||||
|
|
|
@ -10,8 +10,6 @@
|
|||
#include "doomstat.h"
|
||||
*/
|
||||
|
||||
DECLARE_ACTION(A_SkullAttack)
|
||||
|
||||
enum PA_Flags
|
||||
{
|
||||
PAF_NOSKULLATTACK = 1,
|
||||
|
@ -23,21 +21,21 @@ enum PA_Flags
|
|||
// A_PainShootSkull
|
||||
// Spawn a lost soul and launch it at the target
|
||||
//
|
||||
void A_PainShootSkull (AActor *self, angle_t angle, PClassActor *spawntype, int flags = 0, int limit = -1)
|
||||
void A_PainShootSkull (AActor *self, DAngle Angle, PClassActor *spawntype, int flags = 0, int limit = -1)
|
||||
{
|
||||
AActor *other;
|
||||
int prestep;
|
||||
double prestep;
|
||||
|
||||
if (spawntype == NULL) spawntype = PClass::FindActor("LostSoul");
|
||||
assert(spawntype != NULL);
|
||||
if (self->DamageType == NAME_Massacre) return;
|
||||
|
||||
// [RH] check to make sure it's not too close to the ceiling
|
||||
if (self->Top() + 8*FRACUNIT > self->ceilingz)
|
||||
if (self->Top() + 8 > self->ceilingz)
|
||||
{
|
||||
if (self->flags & MF_FLOAT)
|
||||
{
|
||||
self->vel.z -= 2*FRACUNIT;
|
||||
self->Vel.Z -= 2;
|
||||
self->flags |= MF_INFLOAT;
|
||||
self->flags4 |= MF4_VFRICTION;
|
||||
}
|
||||
|
@ -64,14 +62,13 @@ void A_PainShootSkull (AActor *self, angle_t angle, PClassActor *spawntype, int
|
|||
}
|
||||
|
||||
// okay, there's room for another one
|
||||
prestep = 4*FRACUNIT +
|
||||
3*(self->radius + GetDefaultByType(spawntype)->radius)/2;
|
||||
prestep = 4 + (self->radius + GetDefaultByType(spawntype)->radius) * 1.5;
|
||||
|
||||
// NOTE: The following code contains some advance work for line-to-line portals which is currenty inactive.
|
||||
|
||||
fixedvec2 dist = Vec2Angle(prestep, angle);
|
||||
fixedvec3 pos = self->Vec3Offset(dist.x, dist.y, 8 * FRACUNIT, true);
|
||||
fixedvec3 src = self->Pos();
|
||||
DVector2 dist = Angle.ToVector(prestep);
|
||||
DVector3 pos = self->Vec3Offset(dist.X, dist.Y, 8., true);
|
||||
DVector3 src = self->Pos();
|
||||
|
||||
for (int i = 0; i < 2; i++)
|
||||
{
|
||||
|
@ -79,7 +76,7 @@ void A_PainShootSkull (AActor *self, angle_t angle, PClassActor *spawntype, int
|
|||
// wall or an impassible line, or a "monsters can't cross" line.// |
|
||||
// If it is, then we don't allow the spawn. // V
|
||||
|
||||
FBoundingBox box(MIN(src.x, pos.x), MIN(src.y, pos.y), MAX(src.x, pos.x), MAX(src.y, pos.y));
|
||||
FBoundingBox box(MIN(src.X, pos.X), MIN(src.Y, pos.Y), MAX(src.X, pos.X), MAX(src.Y, pos.Y));
|
||||
FBlockLinesIterator it(box);
|
||||
line_t *ld;
|
||||
bool inportal = false;
|
||||
|
@ -88,8 +85,8 @@ void A_PainShootSkull (AActor *self, angle_t angle, PClassActor *spawntype, int
|
|||
{
|
||||
if (ld->isLinePortal() && i == 0)
|
||||
{
|
||||
if (P_PointOnLineSidePrecise(src.x, src.y, ld) == 0 &&
|
||||
P_PointOnLineSidePrecise(pos.x, pos.y, ld) == 1)
|
||||
if (P_PointOnLineSidePrecise(src, ld) == 0 &&
|
||||
P_PointOnLineSidePrecise(pos, ld) == 1)
|
||||
{
|
||||
// crossed a portal line from front to back, we need to repeat the check on the other side as well.
|
||||
inportal = true;
|
||||
|
@ -98,12 +95,9 @@ void A_PainShootSkull (AActor *self, angle_t angle, PClassActor *spawntype, int
|
|||
else if (!(ld->flags & ML_TWOSIDED) ||
|
||||
(ld->flags & (ML_BLOCKING | ML_BLOCKMONSTERS | ML_BLOCKEVERYTHING)))
|
||||
{
|
||||
if (!(box.Left() > ld->bbox[BOXRIGHT] ||
|
||||
box.Right() < ld->bbox[BOXLEFT] ||
|
||||
box.Top() < ld->bbox[BOXBOTTOM] ||
|
||||
box.Bottom() > ld->bbox[BOXTOP]))
|
||||
if (box.inRange(ld))
|
||||
{
|
||||
if (P_PointOnLineSidePrecise(src.x, src.y, ld) != P_PointOnLineSidePrecise(pos.x, pos.y, ld))
|
||||
if (P_PointOnLineSidePrecise(src, ld) != P_PointOnLineSidePrecise(pos, ld))
|
||||
return; // line blocks trajectory // ^
|
||||
}
|
||||
}
|
||||
|
@ -111,20 +105,19 @@ void A_PainShootSkull (AActor *self, angle_t angle, PClassActor *spawntype, int
|
|||
if (!inportal) break;
|
||||
|
||||
// recalculate position and redo the check on the other side of the portal
|
||||
pos = self->Vec3Offset(dist.x, dist.y, 8 * FRACUNIT);
|
||||
src.x = pos.x - dist.x;
|
||||
src.y = pos.y - dist.y;
|
||||
pos = self->Vec3Offset(dist.X, dist.Y, 8.);
|
||||
src.X = pos.X - dist.X;
|
||||
src.Y = pos.Y - dist.Y;
|
||||
|
||||
}
|
||||
|
||||
other = Spawn (spawntype, pos.x, pos.y, pos.z, ALLOW_REPLACE);
|
||||
other = Spawn (spawntype, pos, ALLOW_REPLACE);
|
||||
|
||||
// Check to see if the new Lost Soul's z value is above the
|
||||
// ceiling of its new sector, or below the floor. If so, kill it.
|
||||
|
||||
if ((other->Top() >
|
||||
(other->Sector->HighestCeilingAt(other))) ||
|
||||
(other->Z() < other->Sector->LowestFloorAt(other)))
|
||||
if (other->Top() > other->Sector->HighestCeilingAt(other) ||
|
||||
other->Z() < other->Sector->LowestFloorAt(other))
|
||||
{
|
||||
// kill it immediately
|
||||
P_DamageMobj (other, self, self, TELEFRAG_DAMAGE, NAME_None);// ^
|
||||
|
@ -160,13 +153,13 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PainAttack)
|
|||
return 0;
|
||||
|
||||
PARAM_CLASS_OPT (spawntype, AActor) { spawntype = NULL; }
|
||||
PARAM_ANGLE_OPT (angle) { angle = 0; }
|
||||
PARAM_ANGLE_OPT (angle) { angle = 0.; }
|
||||
PARAM_INT_OPT (flags) { flags = 0; }
|
||||
PARAM_INT_OPT (limit) { limit = -1; }
|
||||
|
||||
if (!(flags & PAF_AIMFACING))
|
||||
A_FaceTarget (self);
|
||||
A_PainShootSkull (self, self->angle+angle, spawntype, flags, limit);
|
||||
A_PainShootSkull (self, self->Angles.Yaw + angle, spawntype, flags, limit);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -179,8 +172,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DualPainAttack)
|
|||
return 0;
|
||||
|
||||
A_FaceTarget (self);
|
||||
A_PainShootSkull (self, self->angle + ANG45, spawntype);
|
||||
A_PainShootSkull (self, self->angle - ANG45, spawntype);
|
||||
A_PainShootSkull (self, self->Angles.Yaw + 45., spawntype);
|
||||
A_PainShootSkull (self, self->Angles.Yaw - 45., spawntype);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -194,8 +187,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PainDie)
|
|||
self->flags &= ~MF_FRIENDLY;
|
||||
}
|
||||
A_Unblock(self, true);
|
||||
A_PainShootSkull (self, self->angle + ANG90, spawntype);
|
||||
A_PainShootSkull (self, self->angle + ANG180, spawntype);
|
||||
A_PainShootSkull (self, self->angle + ANG270, spawntype);
|
||||
A_PainShootSkull (self, self->Angles.Yaw + 90, spawntype);
|
||||
A_PainShootSkull (self, self->Angles.Yaw + 180, spawntype);
|
||||
A_PainShootSkull (self, self->Angles.Yaw + 270, spawntype);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -22,19 +22,19 @@ DEFINE_ACTION_FUNCTION(AActor, A_PosAttack)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int angle;
|
||||
int damage;
|
||||
int slope;
|
||||
DAngle angle;
|
||||
DAngle slope;
|
||||
|
||||
if (!self->target)
|
||||
return 0;
|
||||
|
||||
A_FaceTarget (self);
|
||||
angle = self->angle;
|
||||
angle = self->Angles.Yaw;
|
||||
slope = P_AimLineAttack (self, angle, MISSILERANGE);
|
||||
|
||||
S_Sound (self, CHAN_WEAPON, "grunt/attack", 1, ATTN_NORM);
|
||||
angle += pr_posattack.Random2() << 20;
|
||||
angle += pr_posattack.Random2() * (22.5 / 256);
|
||||
damage = ((pr_posattack()%5)+1)*3;
|
||||
P_LineAttack (self, angle, MISSILERANGE, slope, damage, NAME_Hitscan, NAME_BulletPuff);
|
||||
return 0;
|
||||
|
@ -43,16 +43,16 @@ DEFINE_ACTION_FUNCTION(AActor, A_PosAttack)
|
|||
static void A_SPosAttack2 (AActor *self)
|
||||
{
|
||||
int i;
|
||||
int bangle;
|
||||
int slope;
|
||||
DAngle bangle;
|
||||
DAngle slope;
|
||||
|
||||
A_FaceTarget (self);
|
||||
bangle = self->angle;
|
||||
bangle = self->Angles.Yaw;
|
||||
slope = P_AimLineAttack (self, bangle, MISSILERANGE);
|
||||
|
||||
for (i=0 ; i<3 ; i++)
|
||||
{
|
||||
int angle = bangle + (pr_sposattack.Random2() << 20);
|
||||
DAngle angle = bangle + pr_sposattack.Random2() * (22.5 / 256);
|
||||
int damage = ((pr_sposattack()%5)+1)*3;
|
||||
P_LineAttack(self, angle, MISSILERANGE, slope, damage, NAME_Hitscan, NAME_BulletPuff);
|
||||
}
|
||||
|
@ -88,10 +88,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_CPosAttack)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int angle;
|
||||
int bangle;
|
||||
DAngle angle;
|
||||
DAngle bangle;
|
||||
int damage;
|
||||
int slope;
|
||||
DAngle slope;
|
||||
|
||||
if (!self->target)
|
||||
return 0;
|
||||
|
@ -104,10 +104,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_CPosAttack)
|
|||
|
||||
S_Sound (self, CHAN_WEAPON, self->AttackSound, 1, ATTN_NORM);
|
||||
A_FaceTarget (self);
|
||||
bangle = self->angle;
|
||||
bangle = self->Angles.Yaw;
|
||||
slope = P_AimLineAttack (self, bangle, MISSILERANGE);
|
||||
|
||||
angle = bangle + (pr_cposattack.Random2() << 20);
|
||||
angle = bangle + pr_cposattack.Random2() * (22.5 / 256);
|
||||
damage = ((pr_cposattack()%5)+1)*3;
|
||||
P_LineAttack (self, angle, MISSILERANGE, slope, damage, NAME_Hitscan, NAME_BulletPuff);
|
||||
return 0;
|
||||
|
|
|
@ -28,27 +28,26 @@ DEFINE_ACTION_FUNCTION(AActor, A_SkelMissile)
|
|||
return 0;
|
||||
|
||||
A_FaceTarget (self);
|
||||
self->AddZ(16*FRACUNIT);
|
||||
missile = P_SpawnMissile (self, self->target, PClass::FindActor("RevenantTracer"));
|
||||
self->AddZ(-16*FRACUNIT);
|
||||
self->AddZ(16.);
|
||||
missile = P_SpawnMissile(self, self->target, PClass::FindActor("RevenantTracer"));
|
||||
self->AddZ(-16.);
|
||||
|
||||
if (missile != NULL)
|
||||
{
|
||||
missile->SetOrigin(missile->Vec3Offset(missile->vel.x, missile->vel.y, 0), false);
|
||||
missile->SetOrigin(missile->Vec3Offset(missile->Vel.X, missile->Vel.Y, 0.), false);
|
||||
missile->tracer = self->target;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
#define TRACEANGLE (0xc000000)
|
||||
#define TRACEANGLE (16.875)
|
||||
|
||||
DEFINE_ACTION_FUNCTION(AActor, A_Tracer)
|
||||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t exact;
|
||||
fixed_t dist;
|
||||
fixed_t slope;
|
||||
double dist;
|
||||
double slope;
|
||||
AActor *dest;
|
||||
AActor *smoke;
|
||||
|
||||
|
@ -65,11 +64,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_Tracer)
|
|||
return 0;
|
||||
|
||||
// spawn a puff of smoke behind the rocket
|
||||
P_SpawnPuff (self, PClass::FindActor(NAME_BulletPuff), self->Pos(), self->angle, self->angle, 3);
|
||||
P_SpawnPuff (self, PClass::FindActor(NAME_BulletPuff), self->Pos(), self->Angles.Yaw, self->Angles.Yaw, 3);
|
||||
|
||||
smoke = Spawn ("RevenantTracerSmoke", self->Vec3Offset(-self->vel.x, -self->vel.y, 0), ALLOW_REPLACE);
|
||||
smoke = Spawn ("RevenantTracerSmoke", self->Vec3Offset(-self->Vel.X, -self->Vel.Y, 0.), ALLOW_REPLACE);
|
||||
|
||||
smoke->vel.z = FRACUNIT;
|
||||
smoke->Vel.Z = 1.;
|
||||
smoke->tics -= pr_tracer()&3;
|
||||
if (smoke->tics < 1)
|
||||
smoke->tics = 1;
|
||||
|
@ -81,49 +80,42 @@ DEFINE_ACTION_FUNCTION(AActor, A_Tracer)
|
|||
return 0;
|
||||
|
||||
// change angle
|
||||
exact = self->AngleTo(dest);
|
||||
DAngle exact = self->AngleTo(dest);
|
||||
DAngle diff = deltaangle(self->Angles.Yaw, exact);
|
||||
|
||||
if (exact != self->angle)
|
||||
if (diff < 0)
|
||||
{
|
||||
if (exact - self->angle > 0x80000000)
|
||||
{
|
||||
self->angle -= TRACEANGLE;
|
||||
if (exact - self->angle < 0x80000000)
|
||||
self->angle = exact;
|
||||
}
|
||||
else
|
||||
{
|
||||
self->angle += TRACEANGLE;
|
||||
if (exact - self->angle > 0x80000000)
|
||||
self->angle = exact;
|
||||
}
|
||||
self->Angles.Yaw -= TRACEANGLE;
|
||||
if (deltaangle(self->Angles.Yaw, exact) > 0)
|
||||
self->Angles.Yaw = exact;
|
||||
}
|
||||
|
||||
exact = self->angle>>ANGLETOFINESHIFT;
|
||||
self->vel.x = FixedMul (self->Speed, finecosine[exact]);
|
||||
self->vel.y = FixedMul (self->Speed, finesine[exact]);
|
||||
else if (diff > 0)
|
||||
{
|
||||
self->Angles.Yaw += TRACEANGLE;
|
||||
if (deltaangle(self->Angles.Yaw, exact) < 0.)
|
||||
self->Angles.Yaw = exact;
|
||||
}
|
||||
|
||||
self->VelFromAngle();
|
||||
|
||||
if (!(self->flags3 & (MF3_FLOORHUGGER|MF3_CEILINGHUGGER)))
|
||||
{
|
||||
// change slope
|
||||
dist = self->AproxDistance (dest) / self->Speed;
|
||||
dist = self->DistanceBySpeed(dest, self->Speed);
|
||||
|
||||
if (dist < 1)
|
||||
dist = 1;
|
||||
|
||||
if (dest->height >= 56*FRACUNIT)
|
||||
if (dest->Height >= 56.)
|
||||
{
|
||||
slope = (dest->Z()+40*FRACUNIT - self->Z()) / dist;
|
||||
slope = (dest->Z() + 40. - self->Z()) / dist;
|
||||
}
|
||||
else
|
||||
{
|
||||
slope = (dest->Z() + self->height*2/3 - self->Z()) / dist;
|
||||
slope = (dest->Z() + self->Height*(2./3) - self->Z()) / dist;
|
||||
}
|
||||
|
||||
if (slope < self->vel.z)
|
||||
self->vel.z -= FRACUNIT/8;
|
||||
if (slope < self->Vel.Z)
|
||||
self->Vel.Z -= 1. / 8;
|
||||
else
|
||||
self->vel.z += FRACUNIT/8;
|
||||
self->Vel.Z += 1. / 8;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -275,14 +275,14 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_Saw)
|
|||
A_FaceTarget (self);
|
||||
if (self->CheckMeleeRange ())
|
||||
{
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
FTranslatedLineTarget t;
|
||||
|
||||
damage *= (pr_m_saw()%10+1);
|
||||
angle = self->angle + (pr_m_saw.Random2() << 18);
|
||||
angle = self->Angles.Yaw + pr_m_saw.Random2() * (5.625 / 256);
|
||||
|
||||
P_LineAttack (self, angle, MELEERANGE+1,
|
||||
P_AimLineAttack (self, angle, MELEERANGE+1), damage,
|
||||
P_LineAttack (self, angle, SAWRANGE,
|
||||
P_AimLineAttack (self, angle, SAWRANGE), damage,
|
||||
NAME_Melee, pufftype, false, &t);
|
||||
|
||||
if (!t.linetarget)
|
||||
|
@ -294,19 +294,21 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_Saw)
|
|||
|
||||
// turn to face target
|
||||
angle = t.angleFromSource;
|
||||
if (angle - self->angle > ANG180)
|
||||
DAngle anglediff = deltaangle(self->Angles.Yaw, angle);
|
||||
|
||||
if (anglediff < 0.0)
|
||||
{
|
||||
if (angle - self->angle < (angle_t)(-ANG90/20))
|
||||
self->angle = angle + ANG90/21;
|
||||
if (anglediff < -4.5)
|
||||
self->Angles.Yaw = angle + 90.0 / 21;
|
||||
else
|
||||
self->angle -= ANG90/20;
|
||||
self->Angles.Yaw -= 4.5;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (angle - self->angle > ANG90/20)
|
||||
self->angle = angle - ANG90/21;
|
||||
if (anglediff > 4.5)
|
||||
self->Angles.Yaw = angle - 90.0 / 21;
|
||||
else
|
||||
self->angle += ANG90/20;
|
||||
self->Angles.Yaw += 4.5;
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -325,9 +327,9 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_Saw)
|
|||
|
||||
static void MarinePunch(AActor *self, int damagemul)
|
||||
{
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
int pitch;
|
||||
DAngle pitch;
|
||||
FTranslatedLineTarget t;
|
||||
|
||||
if (self->target == NULL)
|
||||
|
@ -336,7 +338,7 @@ static void MarinePunch(AActor *self, int damagemul)
|
|||
damage = ((pr_m_punch()%10+1) << 1) * damagemul;
|
||||
|
||||
A_FaceTarget (self);
|
||||
angle = self->angle + (pr_m_punch.Random2() << 18);
|
||||
angle = self->Angles.Yaw + pr_m_punch.Random2() * (5.625 / 256);
|
||||
pitch = P_AimLineAttack (self, angle, MELEERANGE);
|
||||
P_LineAttack (self, angle, MELEERANGE, pitch, damage, NAME_Melee, NAME_BulletPuff, true, &t);
|
||||
|
||||
|
@ -344,7 +346,7 @@ static void MarinePunch(AActor *self, int damagemul)
|
|||
if (t.linetarget)
|
||||
{
|
||||
S_Sound (self, CHAN_WEAPON, "*fist", 1, ATTN_NORM);
|
||||
self->angle = t.angleFromSource;
|
||||
self->Angles.Yaw = t.angleFromSource;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -363,17 +365,17 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_Punch)
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
void P_GunShot2 (AActor *mo, bool accurate, int pitch, PClassActor *pufftype)
|
||||
void P_GunShot2 (AActor *mo, bool accurate, DAngle pitch, PClassActor *pufftype)
|
||||
{
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
|
||||
damage = 5*(pr_m_gunshot()%3+1);
|
||||
angle = mo->angle;
|
||||
angle = mo->Angles.Yaw;
|
||||
|
||||
if (!accurate)
|
||||
{
|
||||
angle += pr_m_gunshot.Random2 () << 18;
|
||||
angle += pr_m_gunshot.Random2() * (5.625 / 256);
|
||||
}
|
||||
|
||||
P_LineAttack (mo, angle, MISSILERANGE, pitch, damage, NAME_Hitscan, pufftype);
|
||||
|
@ -395,7 +397,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_FirePistol)
|
|||
|
||||
S_Sound (self, CHAN_WEAPON, "weapons/pistol", 1, ATTN_NORM);
|
||||
A_FaceTarget (self);
|
||||
P_GunShot2 (self, accurate, P_AimLineAttack (self, self->angle, MISSILERANGE),
|
||||
P_GunShot2 (self, accurate, P_AimLineAttack (self, self->Angles.Yaw, MISSILERANGE),
|
||||
PClass::FindActor(NAME_BulletPuff));
|
||||
return 0;
|
||||
}
|
||||
|
@ -410,14 +412,14 @@ DEFINE_ACTION_FUNCTION(AActor, A_M_FireShotgun)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int pitch;
|
||||
DAngle pitch;
|
||||
|
||||
if (self->target == NULL)
|
||||
return 0;
|
||||
|
||||
S_Sound (self, CHAN_WEAPON, "weapons/shotgf", 1, ATTN_NORM);
|
||||
A_FaceTarget (self);
|
||||
pitch = P_AimLineAttack (self, self->angle, MISSILERANGE);
|
||||
pitch = P_AimLineAttack (self, self->Angles.Yaw, MISSILERANGE);
|
||||
for (int i = 0; i < 7; ++i)
|
||||
{
|
||||
P_GunShot2 (self, false, pitch, PClass::FindActor(NAME_BulletPuff));
|
||||
|
@ -457,21 +459,21 @@ DEFINE_ACTION_FUNCTION(AActor, A_M_FireShotgun2)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int pitch;
|
||||
DAngle pitch;
|
||||
|
||||
if (self->target == NULL)
|
||||
return 0;
|
||||
|
||||
S_Sound (self, CHAN_WEAPON, "weapons/sshotf", 1, ATTN_NORM);
|
||||
A_FaceTarget (self);
|
||||
pitch = P_AimLineAttack (self, self->angle, MISSILERANGE);
|
||||
pitch = P_AimLineAttack (self, self->Angles.Yaw, MISSILERANGE);
|
||||
for (int i = 0; i < 20; ++i)
|
||||
{
|
||||
int damage = 5*(pr_m_fireshotgun2()%3+1);
|
||||
angle_t angle = self->angle + (pr_m_fireshotgun2.Random2() << 19);
|
||||
DAngle angle = self->Angles.Yaw + pr_m_fireshotgun2.Random2() * (11.25 / 256);
|
||||
|
||||
P_LineAttack (self, angle, MISSILERANGE,
|
||||
pitch + (pr_m_fireshotgun2.Random2() * 332063), damage,
|
||||
pitch + pr_m_fireshotgun2.Random2() * (7.097 / 256), damage,
|
||||
NAME_Hitscan, NAME_BulletPuff);
|
||||
}
|
||||
self->special1 = level.maptime;
|
||||
|
@ -494,7 +496,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_M_FireCGun)
|
|||
|
||||
S_Sound (self, CHAN_WEAPON, "weapons/chngun", 1, ATTN_NORM);
|
||||
A_FaceTarget (self);
|
||||
P_GunShot2 (self, accurate, P_AimLineAttack (self, self->angle, MISSILERANGE),
|
||||
P_GunShot2 (self, accurate, P_AimLineAttack (self, self->Angles.Yaw, MISSILERANGE),
|
||||
PClass::FindActor(NAME_BulletPuff));
|
||||
return 0;
|
||||
}
|
||||
|
@ -647,13 +649,11 @@ void AScriptedMarine::SetSprite (PClassActor *source)
|
|||
{ // A valid actor class wasn't passed, so use the standard sprite
|
||||
SpriteOverride = sprite = GetClass()->OwnedStates[0].sprite;
|
||||
// Copy the standard scaling
|
||||
scaleX = GetDefault()->scaleX;
|
||||
scaleY = GetDefault()->scaleY;
|
||||
Scale = GetDefault()->Scale;
|
||||
}
|
||||
else
|
||||
{ // Use the same sprite and scaling the passed class spawns with
|
||||
SpriteOverride = sprite = GetDefaultByType (source)->SpawnState->sprite;
|
||||
scaleX = GetDefaultByType(source)->scaleX;
|
||||
scaleY = GetDefaultByType(source)->scaleY;
|
||||
Scale = GetDefaultByType(source)->Scale;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -197,9 +197,9 @@ short consistancy[MAXPLAYERS][BACKUPTICS];
|
|||
float normforwardmove[2] = {0x19, 0x32}; // [RH] For setting turbo from console
|
||||
float normsidemove[2] = {0x18, 0x28}; // [RH] Ditto
|
||||
|
||||
fixed_t forwardmove[2], sidemove[2];
|
||||
fixed_t angleturn[4] = {640, 1280, 320, 320}; // + slow turn
|
||||
fixed_t flyspeed[2] = {1*256, 3*256};
|
||||
int forwardmove[2], sidemove[2];
|
||||
int angleturn[4] = {640, 1280, 320, 320}; // + slow turn
|
||||
int flyspeed[2] = {1*256, 3*256};
|
||||
int lookspeed[2] = {450, 512};
|
||||
|
||||
#define SLOWTURNTICS 6
|
||||
|
@ -1182,8 +1182,7 @@ void G_Ticker ()
|
|||
}
|
||||
if (players[i].mo)
|
||||
{
|
||||
DWORD sum = rngsum + players[i].mo->X() + players[i].mo->Y() + players[i].mo->Z()
|
||||
+ players[i].mo->angle + players[i].mo->pitch;
|
||||
DWORD sum = rngsum + int((players[i].mo->X() + players[i].mo->Y() + players[i].mo->Z())*257) + players[i].mo->Angles.Yaw.BAMs() + players[i].mo->Angles.Pitch.BAMs();
|
||||
sum ^= players[i].health;
|
||||
consistancy[i][buf] = sum;
|
||||
}
|
||||
|
@ -1288,7 +1287,7 @@ void G_PlayerFinishLevel (int player, EFinishLevelType mode, int flags)
|
|||
p->mo->flags &= ~MF_SHADOW;
|
||||
}
|
||||
p->mo->RenderStyle = p->mo->GetDefault()->RenderStyle;
|
||||
p->mo->alpha = p->mo->GetDefault()->alpha;
|
||||
p->mo->Alpha = p->mo->GetDefault()->Alpha;
|
||||
p->extralight = 0; // cancel gun flashes
|
||||
p->fixedcolormap = NOFIXEDCOLORMAP; // cancel ir goggles
|
||||
p->fixedlightlevel = -1;
|
||||
|
@ -1423,33 +1422,30 @@ void G_PlayerReborn (int player)
|
|||
|
||||
bool G_CheckSpot (int playernum, FPlayerStart *mthing)
|
||||
{
|
||||
fixed_t x;
|
||||
fixed_t y;
|
||||
fixed_t z, oldz;
|
||||
DVector3 spot;
|
||||
double oldz;
|
||||
int i;
|
||||
|
||||
if (mthing->type == 0) return false;
|
||||
|
||||
x = mthing->x;
|
||||
y = mthing->y;
|
||||
z = mthing->z;
|
||||
spot = mthing->pos;
|
||||
|
||||
if (!(level.flags & LEVEL_USEPLAYERSTARTZ))
|
||||
{
|
||||
z = 0;
|
||||
spot.Z = 0;
|
||||
}
|
||||
z += P_PointInSector (x, y)->floorplane.ZatPoint (x, y);
|
||||
spot.Z += P_PointInSector (spot)->floorplane.ZatPoint (spot);
|
||||
|
||||
if (!players[playernum].mo)
|
||||
{ // first spawn of level, before corpses
|
||||
for (i = 0; i < playernum; i++)
|
||||
if (players[i].mo && players[i].mo->X() == x && players[i].mo->Y() == y)
|
||||
if (players[i].mo && players[i].mo->X() == spot.X && players[i].mo->Y() == spot.Y)
|
||||
return false;
|
||||
return true;
|
||||
}
|
||||
|
||||
oldz = players[playernum].mo->Z(); // [RH] Need to save corpse's z-height
|
||||
players[playernum].mo->SetZ(z); // [RH] Checks are now full 3-D
|
||||
players[playernum].mo->SetZ(spot.Z); // [RH] Checks are now full 3-D
|
||||
|
||||
// killough 4/2/98: fix bug where P_CheckPosition() uses a non-solid
|
||||
// corpse to detect collisions with other players in DM starts
|
||||
|
@ -1459,7 +1455,7 @@ bool G_CheckSpot (int playernum, FPlayerStart *mthing)
|
|||
// return false;
|
||||
|
||||
players[playernum].mo->flags |= MF_SOLID;
|
||||
i = P_CheckPosition(players[playernum].mo, x, y);
|
||||
i = P_CheckPosition(players[playernum].mo, spot);
|
||||
players[playernum].mo->flags &= ~MF_SOLID;
|
||||
players[playernum].mo->SetZ(oldz); // [RH] Restore corpse's height
|
||||
if (!i)
|
||||
|
@ -1476,10 +1472,10 @@ bool G_CheckSpot (int playernum, FPlayerStart *mthing)
|
|||
//
|
||||
|
||||
// [RH] Returns the distance of the closest player to the given mapthing
|
||||
static fixed_t PlayersRangeFromSpot (FPlayerStart *spot)
|
||||
static double PlayersRangeFromSpot (FPlayerStart *spot)
|
||||
{
|
||||
fixed_t closest = INT_MAX;
|
||||
fixed_t distance;
|
||||
double closest = INT_MAX;
|
||||
double distance;
|
||||
int i;
|
||||
|
||||
for (i = 0; i < MAXPLAYERS; i++)
|
||||
|
@ -1487,7 +1483,7 @@ static fixed_t PlayersRangeFromSpot (FPlayerStart *spot)
|
|||
if (!playeringame[i] || !players[i].mo || players[i].health <= 0)
|
||||
continue;
|
||||
|
||||
distance = players[i].mo->AproxDistance (spot->x, spot->y);
|
||||
distance = players[i].mo->Distance2D(spot->pos.X, spot->pos.Y);
|
||||
|
||||
if (distance < closest)
|
||||
closest = distance;
|
||||
|
@ -1499,13 +1495,13 @@ static fixed_t PlayersRangeFromSpot (FPlayerStart *spot)
|
|||
// [RH] Select the deathmatch spawn spot farthest from everyone.
|
||||
static FPlayerStart *SelectFarthestDeathmatchSpot (size_t selections)
|
||||
{
|
||||
fixed_t bestdistance = 0;
|
||||
double bestdistance = 0;
|
||||
FPlayerStart *bestspot = NULL;
|
||||
unsigned int i;
|
||||
|
||||
for (i = 0; i < selections; i++)
|
||||
{
|
||||
fixed_t distance = PlayersRangeFromSpot (&deathmatchstarts[i]);
|
||||
double distance = PlayersRangeFromSpot (&deathmatchstarts[i]);
|
||||
|
||||
if (distance > bestdistance)
|
||||
{
|
||||
|
@ -1645,8 +1641,8 @@ static void G_QueueBody (AActor *body)
|
|||
const AActor *const defaultActor = body->GetDefault();
|
||||
const FPlayerSkin &skin = skins[skinidx];
|
||||
|
||||
body->scaleX = Scale(body->scaleX, skin.ScaleX, defaultActor->scaleX);
|
||||
body->scaleY = Scale(body->scaleY, skin.ScaleY, defaultActor->scaleY);
|
||||
body->Scale.X *= skin.Scale.X / defaultActor->Scale.X;
|
||||
body->Scale.Y *= skin.Scale.Y / defaultActor->Scale.Y;
|
||||
}
|
||||
|
||||
bodyqueslot++;
|
||||
|
@ -1933,13 +1929,6 @@ void G_DoLoadGame ()
|
|||
BYTE *vars_p = (BYTE *)text;
|
||||
C_ReadCVars (&vars_p);
|
||||
delete[] text;
|
||||
if (SaveVersion <= 4509)
|
||||
{
|
||||
// account for the flag shuffling for making freelook a 3-state option
|
||||
INTBOOL flag = dmflags & DF_YES_FREELOOK;
|
||||
dmflags = dmflags & ~DF_YES_FREELOOK;
|
||||
if (flag) dmflags2 = dmflags2 | DF2_RESPAWN_SUPER;
|
||||
}
|
||||
}
|
||||
|
||||
// dearchive all the modifications
|
||||
|
|
|
@ -41,13 +41,13 @@ void AChickenPlayer::MorphPlayerThink ()
|
|||
{
|
||||
return;
|
||||
}
|
||||
if (!(vel.x | vel.y) && pr_chickenplayerthink () < 160)
|
||||
if (Vel.X == 0 && Vel.Y == 0 && pr_chickenplayerthink () < 160)
|
||||
{ // Twitch view angle
|
||||
angle += pr_chickenplayerthink.Random2 () << 19;
|
||||
Angles.Yaw += pr_chickenplayerthink.Random2() * (360. / 256. / 32.);
|
||||
}
|
||||
if ((Z() <= floorz) && (pr_chickenplayerthink() < 32))
|
||||
{ // Jump and noise
|
||||
vel.z += JumpZ;
|
||||
Vel.Z += JumpZ;
|
||||
|
||||
FState * painstate = FindState(NAME_Pain);
|
||||
if (painstate != NULL) SetState (painstate);
|
||||
|
@ -105,11 +105,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_Feathers)
|
|||
}
|
||||
for (i = 0; i < count; i++)
|
||||
{
|
||||
mo = Spawn("Feather", self->PosPlusZ(20*FRACUNIT), NO_REPLACE);
|
||||
mo = Spawn("Feather", self->PosPlusZ(20.), NO_REPLACE);
|
||||
mo->target = self;
|
||||
mo->vel.x = pr_feathers.Random2() << 8;
|
||||
mo->vel.y = pr_feathers.Random2() << 8;
|
||||
mo->vel.z = FRACUNIT + (pr_feathers() << 9);
|
||||
mo->Vel.X = pr_feathers.Random2() / 256.;
|
||||
mo->Vel.Y = pr_feathers.Random2() / 256.;
|
||||
mo->Vel.Z = 1. + pr_feathers() / 128.;
|
||||
mo->SetState (mo->SpawnState + (pr_feathers()&7));
|
||||
}
|
||||
return 0;
|
||||
|
@ -125,8 +125,7 @@ void P_UpdateBeak (AActor *self)
|
|||
{
|
||||
if (self->player != NULL)
|
||||
{
|
||||
self->player->psprites[ps_weapon].sy = WEAPONTOP +
|
||||
(self->player->chickenPeck << (FRACBITS-1));
|
||||
self->player->psprites[ps_weapon].sy = WEAPONTOP + self->player->chickenPeck / 2;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -172,9 +171,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_BeakAttackPL1)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
int slope;
|
||||
DAngle slope;
|
||||
player_t *player;
|
||||
FTranslatedLineTarget t;
|
||||
|
||||
|
@ -184,12 +183,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_BeakAttackPL1)
|
|||
}
|
||||
|
||||
damage = 1 + (pr_beakatkpl1()&3);
|
||||
angle = player->mo->angle;
|
||||
angle = player->mo->Angles.Yaw;
|
||||
slope = P_AimLineAttack (player->mo, angle, MELEERANGE);
|
||||
P_LineAttack (player->mo, angle, MELEERANGE, slope, damage, NAME_Melee, "BeakPuff", true, &t);
|
||||
if (t.linetarget)
|
||||
{
|
||||
player->mo->angle = t.angleFromSource;
|
||||
player->mo->Angles.Yaw = t.angleFromSource;
|
||||
}
|
||||
P_PlayPeck (player->mo);
|
||||
player->chickenPeck = 12;
|
||||
|
@ -207,9 +206,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_BeakAttackPL2)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
int slope;
|
||||
DAngle slope;
|
||||
player_t *player;
|
||||
FTranslatedLineTarget t;
|
||||
|
||||
|
@ -219,12 +218,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_BeakAttackPL2)
|
|||
}
|
||||
|
||||
damage = pr_beakatkpl2.HitDice (4);
|
||||
angle = player->mo->angle;
|
||||
angle = player->mo->Angles.Yaw;
|
||||
slope = P_AimLineAttack (player->mo, angle, MELEERANGE);
|
||||
P_LineAttack (player->mo, angle, MELEERANGE, slope, damage, NAME_Melee, "BeakPuff", true, &t);
|
||||
if (t.linetarget)
|
||||
{
|
||||
player->mo->angle = t.angleFromSource;
|
||||
player->mo->Angles.Yaw = t.angleFromSource;
|
||||
}
|
||||
P_PlayPeck (player->mo);
|
||||
player->chickenPeck = 12;
|
||||
|
|
|
@ -67,8 +67,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Srcr1Attack)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
AActor *mo;
|
||||
fixed_t vz;
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
|
||||
if (!self->target)
|
||||
{
|
||||
|
@ -86,17 +85,16 @@ DEFINE_ACTION_FUNCTION(AActor, A_Srcr1Attack)
|
|||
PClassActor *fx = PClass::FindActor("SorcererFX1");
|
||||
if (self->health > (self->SpawnHealth()/3)*2)
|
||||
{ // Spit one fireball
|
||||
P_SpawnMissileZ (self, self->Z() + 48*FRACUNIT, self->target, fx );
|
||||
P_SpawnMissileZ (self, self->Z() + 48, self->target, fx );
|
||||
}
|
||||
else
|
||||
{ // Spit three fireballs
|
||||
mo = P_SpawnMissileZ (self, self->Z() + 48*FRACUNIT, self->target, fx);
|
||||
mo = P_SpawnMissileZ (self, self->Z() + 48, self->target, fx);
|
||||
if (mo != NULL)
|
||||
{
|
||||
vz = mo->vel.z;
|
||||
angle = mo->angle;
|
||||
P_SpawnMissileAngleZ (self, self->Z() + 48*FRACUNIT, fx, angle-ANGLE_1*3, vz);
|
||||
P_SpawnMissileAngleZ (self, self->Z() + 48*FRACUNIT, fx, angle+ANGLE_1*3, vz);
|
||||
angle = mo->Angles.Yaw;
|
||||
P_SpawnMissileAngleZ(self, self->Z() + 48, fx, angle - 3, mo->Vel.Z);
|
||||
P_SpawnMissileAngleZ(self, self->Z() + 48, fx, angle + 3, mo->Vel.Z);
|
||||
}
|
||||
if (self->health < self->SpawnHealth()/3)
|
||||
{ // Maybe attack again
|
||||
|
@ -130,7 +128,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcererRise)
|
|||
mo = Spawn("Sorcerer2", self->Pos(), ALLOW_REPLACE);
|
||||
mo->Translation = self->Translation;
|
||||
mo->SetState (mo->FindState("Rise"));
|
||||
mo->angle = self->angle;
|
||||
mo->Angles.Yaw = self->Angles.Yaw;
|
||||
mo->CopyFriendliness (self, true);
|
||||
return 0;
|
||||
}
|
||||
|
@ -143,31 +141,27 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcererRise)
|
|||
|
||||
void P_DSparilTeleport (AActor *actor)
|
||||
{
|
||||
fixed_t prevX;
|
||||
fixed_t prevY;
|
||||
fixed_t prevZ;
|
||||
DVector3 prev;
|
||||
AActor *mo;
|
||||
AActor *spot;
|
||||
|
||||
DSpotState *state = DSpotState::GetSpotState();
|
||||
if (state == NULL) return;
|
||||
|
||||
spot = state->GetSpotWithMinMaxDistance(PClass::FindClass("BossSpot"), actor->X(), actor->Y(), 128*FRACUNIT, 0);
|
||||
spot = state->GetSpotWithMinMaxDistance(PClass::FindClass("BossSpot"), actor->X(), actor->Y(), 128, 0);
|
||||
if (spot == NULL) return;
|
||||
|
||||
prevX = actor->X();
|
||||
prevY = actor->Y();
|
||||
prevZ = actor->Z();
|
||||
prev = actor->Pos();
|
||||
if (P_TeleportMove (actor, spot->Pos(), false))
|
||||
{
|
||||
mo = Spawn("Sorcerer2Telefade", prevX, prevY, prevZ, ALLOW_REPLACE);
|
||||
mo = Spawn("Sorcerer2Telefade", prev, ALLOW_REPLACE);
|
||||
if (mo) mo->Translation = actor->Translation;
|
||||
S_Sound (mo, CHAN_BODY, "misc/teleport", 1, ATTN_NORM);
|
||||
actor->SetState (actor->FindState("Teleport"));
|
||||
S_Sound (actor, CHAN_BODY, "misc/teleport", 1, ATTN_NORM);
|
||||
actor->SetZ(actor->floorz, false);
|
||||
actor->angle = spot->angle;
|
||||
actor->vel.x = actor->vel.y = actor->vel.z = 0;
|
||||
actor->SetZ(actor->floorz);
|
||||
actor->Angles.Yaw = spot->Angles.Yaw;
|
||||
actor->Vel.Zero();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -230,8 +224,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_Srcr2Attack)
|
|||
PClassActor *fx = PClass::FindActor("Sorcerer2FX2");
|
||||
if (fx)
|
||||
{
|
||||
P_SpawnMissileAngle (self, fx, self->angle-ANG45, FRACUNIT/2);
|
||||
P_SpawnMissileAngle (self, fx, self->angle+ANG45, FRACUNIT/2);
|
||||
P_SpawnMissileAngle(self, fx, self->Angles.Yaw - 45, 0.5);
|
||||
P_SpawnMissileAngle(self, fx, self->Angles.Yaw + 45, 0.5);
|
||||
}
|
||||
}
|
||||
else
|
||||
|
@ -257,9 +251,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_BlueSpark)
|
|||
for (i = 0; i < 2; i++)
|
||||
{
|
||||
mo = Spawn("Sorcerer2FXSpark", self->Pos(), ALLOW_REPLACE);
|
||||
mo->vel.x = pr_bluespark.Random2() << 9;
|
||||
mo->vel.y = pr_bluespark.Random2() << 9;
|
||||
mo->vel.z = FRACUNIT + (pr_bluespark()<<8);
|
||||
mo->Vel.X = pr_bluespark.Random2() / 128.;
|
||||
mo->Vel.Y = pr_bluespark.Random2() / 128.;
|
||||
mo->Vel.Z = 1. + pr_bluespark() / 256.;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -279,7 +273,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_GenWizard)
|
|||
mo = Spawn("Wizard", self->Pos(), ALLOW_REPLACE);
|
||||
if (mo != NULL)
|
||||
{
|
||||
mo->AddZ(-mo->GetDefault()->height / 2, false);
|
||||
mo->AddZ(-mo->GetDefault()->Height / 2, false);
|
||||
if (!P_TestMobjLocation (mo))
|
||||
{ // Didn't fit
|
||||
mo->ClearCounters();
|
||||
|
@ -289,7 +283,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_GenWizard)
|
|||
{ // [RH] Make the new wizards inherit D'Sparil's target
|
||||
mo->CopyFriendliness (self->target, true);
|
||||
|
||||
self->vel.x = self->vel.y = self->vel.z = 0;
|
||||
self->Vel.Zero();
|
||||
self->SetState (self->FindState(NAME_Death));
|
||||
self->flags &= ~MF_MISSILE;
|
||||
mo->master = self->target;
|
||||
|
|
|
@ -49,12 +49,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_TimeBomb)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->AddZ(32*FRACUNIT, false);
|
||||
self->PrevZ = self->Z(); // no interpolation!
|
||||
self->AddZ(32, false);
|
||||
self->RenderStyle = STYLE_Add;
|
||||
self->alpha = FRACUNIT;
|
||||
self->Alpha = 1.;
|
||||
P_RadiusAttack (self, self->target, 128, 128, self->DamageType, RADF_HURTSOURCE);
|
||||
P_CheckSplash(self, 128<<FRACBITS);
|
||||
P_CheckSplash(self, 128);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -70,9 +69,8 @@ IMPLEMENT_CLASS (AArtiTimeBomb)
|
|||
|
||||
bool AArtiTimeBomb::Use (bool pickup)
|
||||
{
|
||||
angle_t angle = Owner->angle >> ANGLETOFINESHIFT;
|
||||
AActor *mo = Spawn("ActivatedTimeBomb",
|
||||
Owner->Vec3Angle(24*FRACUNIT, Owner->angle, - Owner->floorclip), ALLOW_REPLACE);
|
||||
Owner->Vec3Angle(24., Owner->Angles.Yaw, - Owner->Floorclip), ALLOW_REPLACE);
|
||||
mo->target = Owner;
|
||||
return true;
|
||||
}
|
||||
|
|
|
@ -28,7 +28,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ImpMsAttack)
|
|||
self->SetState (self->SeeState);
|
||||
return 0;
|
||||
}
|
||||
A_SkullAttack(self, 12 * FRACUNIT);
|
||||
A_SkullAttack(self, 12.);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -47,14 +47,14 @@ DEFINE_ACTION_FUNCTION(AActor, A_ImpExplode)
|
|||
self->flags &= ~MF_NOGRAVITY;
|
||||
|
||||
chunk = Spawn("HereticImpChunk1", self->Pos(), ALLOW_REPLACE);
|
||||
chunk->vel.x = pr_imp.Random2 () << 10;
|
||||
chunk->vel.y = pr_imp.Random2 () << 10;
|
||||
chunk->vel.z = 9*FRACUNIT;
|
||||
chunk->Vel.X = pr_imp.Random2() / 64.;
|
||||
chunk->Vel.Y = pr_imp.Random2() / 64.;
|
||||
chunk->Vel.Z = 9;
|
||||
|
||||
chunk = Spawn("HereticImpChunk2", self->Pos(), ALLOW_REPLACE);
|
||||
chunk->vel.x = pr_imp.Random2 () << 10;
|
||||
chunk->vel.y = pr_imp.Random2 () << 10;
|
||||
chunk->vel.z = 9*FRACUNIT;
|
||||
chunk->Vel.X = pr_imp.Random2() / 64.;
|
||||
chunk->Vel.Y = pr_imp.Random2() / 64.;
|
||||
chunk->Vel.Z = 9;
|
||||
if (self->special1 == 666)
|
||||
{ // Extreme death crash
|
||||
self->SetState (self->FindState("XCrash"));
|
||||
|
|
|
@ -59,11 +59,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_PodPain)
|
|||
}
|
||||
for (count = chance > 240 ? 2 : 1; count; count--)
|
||||
{
|
||||
goo = Spawn(gootype, self->PosPlusZ(48*FRACUNIT), ALLOW_REPLACE);
|
||||
goo = Spawn(gootype, self->PosPlusZ(48.), ALLOW_REPLACE);
|
||||
goo->target = self;
|
||||
goo->vel.x = pr_podpain.Random2() << 9;
|
||||
goo->vel.y = pr_podpain.Random2() << 9;
|
||||
goo->vel.z = FRACUNIT/2 + (pr_podpain() << 9);
|
||||
goo->Vel.X = pr_podpain.Random2() / 128.;
|
||||
goo->Vel.Y = pr_podpain.Random2() / 128.;
|
||||
goo->Vel.Z = 0.5 + pr_podpain() / 128.;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -104,23 +104,19 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_MakePod)
|
|||
PARAM_CLASS_OPT(podtype, AActor) { podtype = PClass::FindActor("Pod"); }
|
||||
|
||||
AActor *mo;
|
||||
fixed_t x;
|
||||
fixed_t y;
|
||||
|
||||
if (self->special1 == MAX_GEN_PODS)
|
||||
{ // Too many generated pods
|
||||
return 0;
|
||||
}
|
||||
x = self->X();
|
||||
y = self->Y();
|
||||
mo = Spawn(podtype, x, y, ONFLOORZ, ALLOW_REPLACE);
|
||||
if (!P_CheckPosition (mo, x, y))
|
||||
mo = Spawn(podtype, self->PosAtZ(ONFLOORZ), ALLOW_REPLACE);
|
||||
if (!P_CheckPosition (mo, mo->Pos()))
|
||||
{ // Didn't fit
|
||||
mo->Destroy ();
|
||||
return 0;
|
||||
}
|
||||
mo->SetState (mo->FindState("Grow"));
|
||||
P_ThrustMobj (mo, pr_makepod()<<24, (fixed_t)(4.5*FRACUNIT));
|
||||
mo->Thrust(pr_makepod() * (360. / 256), 4.5);
|
||||
S_Sound (mo, CHAN_BODY, self->AttackSound, 1, ATTN_IDLE);
|
||||
self->special1++; // Increment generated pod count
|
||||
mo->master = self; // Link the generator to the pod
|
||||
|
@ -139,7 +135,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_AccTeleGlitter)
|
|||
|
||||
if (++self->health > 35)
|
||||
{
|
||||
self->vel.z += self->vel.z/2;
|
||||
self->Vel.Z *= 1.5;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -172,19 +168,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_VolcanoBlast)
|
|||
int i;
|
||||
int count;
|
||||
AActor *blast;
|
||||
angle_t angle;
|
||||
|
||||
count = 1 + (pr_blast() % 3);
|
||||
for (i = 0; i < count; i++)
|
||||
{
|
||||
blast = Spawn("VolcanoBlast", self->PosPlusZ(44*FRACUNIT), ALLOW_REPLACE);
|
||||
blast = Spawn("VolcanoBlast", self->PosPlusZ(44.), ALLOW_REPLACE);
|
||||
blast->target = self;
|
||||
angle = pr_blast () << 24;
|
||||
blast->angle = angle;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
blast->vel.x = FixedMul (1*FRACUNIT, finecosine[angle]);
|
||||
blast->vel.y = FixedMul (1*FRACUNIT, finesine[angle]);
|
||||
blast->vel.z = (FRACUNIT*5/2) + (pr_blast() << 10);
|
||||
blast->Angles.Yaw = pr_blast() * (360 / 256.);
|
||||
blast->VelFromAngle(1.);
|
||||
blast->Vel.Z = 2.5 + pr_blast() / 64.;
|
||||
S_Sound (blast, CHAN_BODY, "world/volcano/shoot", 1, ATTN_NORM);
|
||||
P_CheckMissileSpawn (blast, self->radius);
|
||||
}
|
||||
|
@ -203,26 +195,22 @@ DEFINE_ACTION_FUNCTION(AActor, A_VolcBallImpact)
|
|||
|
||||
unsigned int i;
|
||||
AActor *tiny;
|
||||
angle_t angle;
|
||||
|
||||
if (self->Z() <= self->floorz)
|
||||
{
|
||||
self->flags |= MF_NOGRAVITY;
|
||||
self->gravity = FRACUNIT;
|
||||
self->AddZ(28*FRACUNIT);
|
||||
//self->vel.z = 3*FRACUNIT;
|
||||
self->Gravity = 1;
|
||||
self->AddZ(28);
|
||||
//self->Vel.Z = 3;
|
||||
}
|
||||
P_RadiusAttack (self, self->target, 25, 25, NAME_Fire, RADF_HURTSOURCE);
|
||||
for (i = 0; i < 4; i++)
|
||||
{
|
||||
tiny = Spawn("VolcanoTBlast", self->Pos(), ALLOW_REPLACE);
|
||||
tiny->target = self;
|
||||
angle = i*ANG90;
|
||||
tiny->angle = angle;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
tiny->vel.x = FixedMul (FRACUNIT*7/10, finecosine[angle]);
|
||||
tiny->vel.y = FixedMul (FRACUNIT*7/10, finesine[angle]);
|
||||
tiny->vel.z = FRACUNIT + (pr_volcimpact() << 9);
|
||||
tiny->Angles.Yaw = 90.*i;
|
||||
tiny->VelFromAngle(0.7);
|
||||
tiny->Vel.Z = 1. + pr_volcimpact() / 128.;
|
||||
P_CheckMissileSpawn (tiny, self->radius);
|
||||
}
|
||||
return 0;
|
||||
|
|
|
@ -63,8 +63,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_StaffAttack)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
int slope;
|
||||
DAngle angle;
|
||||
DAngle slope;
|
||||
player_t *player;
|
||||
FTranslatedLineTarget t;
|
||||
|
||||
|
@ -86,15 +86,14 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_StaffAttack)
|
|||
{
|
||||
puff = PClass::FindActor(NAME_BulletPuff); // just to be sure
|
||||
}
|
||||
angle = self->angle;
|
||||
angle += pr_sap.Random2() << 18;
|
||||
angle = self->Angles.Yaw + pr_sap.Random2() * (5.625 / 256);
|
||||
slope = P_AimLineAttack (self, angle, MELEERANGE);
|
||||
P_LineAttack (self, angle, MELEERANGE, slope, damage, NAME_Melee, puff, true, &t);
|
||||
if (t.linetarget)
|
||||
{
|
||||
//S_StartSound(player->mo, sfx_stfhit);
|
||||
// turn to face target
|
||||
self->angle = t.angleFromSource;
|
||||
self->Angles.Yaw = t.angleFromSource;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -110,7 +109,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL1)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
player_t *player;
|
||||
|
||||
|
@ -122,18 +121,18 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL1)
|
|||
AWeapon *weapon = player->ReadyWeapon;
|
||||
if (weapon != NULL)
|
||||
{
|
||||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
if (!weapon->DepleteAmmo(weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
angle_t pitch = P_BulletSlope(self);
|
||||
damage = 7+(pr_fgw()&7);
|
||||
angle = self->angle;
|
||||
DAngle pitch = P_BulletSlope(self);
|
||||
damage = 7 + (pr_fgw() & 7);
|
||||
angle = self->Angles.Yaw;
|
||||
if (player->refire)
|
||||
{
|
||||
angle += pr_fgw.Random2() << 18;
|
||||
angle += pr_fgw.Random2() * (5.625 / 256);
|
||||
}
|
||||
P_LineAttack (self, angle, PLAYERMISSILERANGE, pitch, damage, NAME_Hitscan, "GoldWandPuff1");
|
||||
S_Sound (self, CHAN_WEAPON, "weapons/wandhit", 1, ATTN_NORM);
|
||||
P_LineAttack(self, angle, PLAYERMISSILERANGE, pitch, damage, NAME_Hitscan, "GoldWandPuff1");
|
||||
S_Sound(self, CHAN_WEAPON, "weapons/wandhit", 1, ATTN_NORM);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -148,9 +147,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL2)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int i;
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
fixed_t vz;
|
||||
double vz;
|
||||
player_t *player;
|
||||
|
||||
if (NULL == (player = self->player))
|
||||
|
@ -164,17 +163,17 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireGoldWandPL2)
|
|||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
angle_t pitch = P_BulletSlope(self);
|
||||
vz = FixedMul (GetDefaultByName("GoldWandFX2")->Speed,
|
||||
finetangent[FINEANGLES/4-((signed)pitch>>ANGLETOFINESHIFT)]);
|
||||
P_SpawnMissileAngle (self, PClass::FindActor("GoldWandFX2"), self->angle-(ANG45/8), vz);
|
||||
P_SpawnMissileAngle (self, PClass::FindActor("GoldWandFX2"), self->angle+(ANG45/8), vz);
|
||||
angle = self->angle-(ANG45/8);
|
||||
DAngle pitch = P_BulletSlope(self);
|
||||
|
||||
vz = -GetDefaultByName("GoldWandFX2")->Speed * pitch.TanClamped();
|
||||
P_SpawnMissileAngle(self, PClass::FindActor("GoldWandFX2"), self->Angles.Yaw - (45. / 8), vz);
|
||||
P_SpawnMissileAngle(self, PClass::FindActor("GoldWandFX2"), self->Angles.Yaw + (45. / 8), vz);
|
||||
angle = self->Angles.Yaw - (45. / 8);
|
||||
for(i = 0; i < 5; i++)
|
||||
{
|
||||
damage = 1+(pr_fgw2()&7);
|
||||
P_LineAttack (self, angle, PLAYERMISSILERANGE, pitch, damage, NAME_Hitscan, "GoldWandPuff2");
|
||||
angle += ((ANG45/8)*2)/4;
|
||||
angle += ((45. / 8) * 2) / 4;
|
||||
}
|
||||
S_Sound (self, CHAN_WEAPON, "weapons/wandhit", 1, ATTN_NORM);
|
||||
return 0;
|
||||
|
@ -204,8 +203,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireCrossbowPL1)
|
|||
return 0;
|
||||
}
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX1"));
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX3"), self->angle-(ANG45/10));
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX3"), self->angle+(ANG45/10));
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX3"), self->Angles.Yaw - 4.5);
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX3"), self->Angles.Yaw + 4.5);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -233,10 +232,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireCrossbowPL2)
|
|||
return 0;
|
||||
}
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX2"));
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX2"), self->angle-(ANG45/10));
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX2"), self->angle+(ANG45/10));
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX3"), self->angle-(ANG45/5));
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX3"), self->angle+(ANG45/5));
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX2"), self->Angles.Yaw - 4.5);
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX2"), self->Angles.Yaw + 4.5);
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX3"), self->Angles.Yaw - 9.);
|
||||
P_SpawnPlayerMissile (self, PClass::FindActor("CrossbowFX3"), self->Angles.Yaw + 9.);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -250,11 +249,11 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_GauntletAttack)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle Angle;
|
||||
int damage;
|
||||
int slope;
|
||||
DAngle slope;
|
||||
int randVal;
|
||||
fixed_t dist;
|
||||
double dist;
|
||||
player_t *player;
|
||||
PClassActor *pufftype;
|
||||
FTranslatedLineTarget t;
|
||||
|
@ -273,25 +272,25 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_GauntletAttack)
|
|||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
player->psprites[ps_weapon].sx = ((pr_gatk()&3)-2) * FRACUNIT;
|
||||
player->psprites[ps_weapon].sy = WEAPONTOP + (pr_gatk()&3) * FRACUNIT;
|
||||
angle = self->angle;
|
||||
player->psprites[ps_weapon].sx = ((pr_gatk()&3)-2);
|
||||
player->psprites[ps_weapon].sy = WEAPONTOP + (pr_gatk()&3);
|
||||
Angle = self->Angles.Yaw;
|
||||
if (power)
|
||||
{
|
||||
damage = pr_gatk.HitDice (2);
|
||||
dist = 4*MELEERANGE;
|
||||
angle += pr_gatk.Random2() << 17;
|
||||
Angle += pr_gatk.Random2() * (2.8125 / 256);
|
||||
pufftype = PClass::FindActor("GauntletPuff2");
|
||||
}
|
||||
else
|
||||
{
|
||||
damage = pr_gatk.HitDice (2);
|
||||
dist = MELEERANGE+1;
|
||||
angle += pr_gatk.Random2() << 18;
|
||||
dist = SAWRANGE;
|
||||
Angle += pr_gatk.Random2() * (5.625 / 256);
|
||||
pufftype = PClass::FindActor("GauntletPuff1");
|
||||
}
|
||||
slope = P_AimLineAttack (self, angle, dist);
|
||||
P_LineAttack (self, angle, dist, slope, damage, NAME_Melee, pufftype, false, &t, &actualdamage);
|
||||
slope = P_AimLineAttack (self, Angle, dist);
|
||||
P_LineAttack (self, Angle, dist, slope, damage, NAME_Melee, pufftype, false, &t, &actualdamage);
|
||||
if (!t.linetarget)
|
||||
{
|
||||
if (pr_gatk() > 64)
|
||||
|
@ -324,20 +323,22 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_GauntletAttack)
|
|||
S_Sound (self, CHAN_AUTO, "weapons/gauntletshit", 1, ATTN_NORM);
|
||||
}
|
||||
// turn to face target
|
||||
angle = t.angleFromSource;
|
||||
if (angle-self->angle > ANG180)
|
||||
DAngle angle = t.angleFromSource;
|
||||
DAngle anglediff = deltaangle(self->Angles.Yaw, angle);
|
||||
|
||||
if (anglediff < 0.0)
|
||||
{
|
||||
if ((int)(angle-self->angle) < -ANG90/20)
|
||||
self->angle = angle+ANG90/21;
|
||||
if (anglediff < -4.5)
|
||||
self->Angles.Yaw = angle + 90.0 / 21;
|
||||
else
|
||||
self->angle -= ANG90/20;
|
||||
self->Angles.Yaw -= 4.5;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (angle-self->angle > ANG90/20)
|
||||
self->angle = angle-ANG90/21;
|
||||
if (anglediff > 4.5)
|
||||
self->Angles.Yaw = angle - 90.0 / 21;
|
||||
else
|
||||
self->angle += ANG90/20;
|
||||
self->Angles.Yaw += 4.5;
|
||||
}
|
||||
self->flags |= MF_JUSTATTACKED;
|
||||
return 0;
|
||||
|
@ -387,7 +388,6 @@ int AMaceFX4::DoSpecialDamage (AActor *target, int damage, FName damagetype)
|
|||
void FireMacePL1B (AActor *actor)
|
||||
{
|
||||
AActor *ball;
|
||||
angle_t angle;
|
||||
player_t *player;
|
||||
|
||||
if (NULL == (player = actor->player))
|
||||
|
@ -401,16 +401,13 @@ void FireMacePL1B (AActor *actor)
|
|||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
return;
|
||||
}
|
||||
ball = Spawn("MaceFX2", actor->PosPlusZ(28*FRACUNIT - actor->floorclip), ALLOW_REPLACE);
|
||||
ball->vel.z = 2*FRACUNIT+/*((player->lookdir)<<(FRACBITS-5))*/
|
||||
finetangent[FINEANGLES/4-(actor->pitch>>ANGLETOFINESHIFT)];
|
||||
angle = actor->angle;
|
||||
ball = Spawn("MaceFX2", actor->PosPlusZ(28 - actor->Floorclip), ALLOW_REPLACE);
|
||||
ball->Vel.Z = 2 - player->mo->Angles.Pitch.TanClamped();
|
||||
ball->target = actor;
|
||||
ball->angle = angle;
|
||||
ball->AddZ(2*finetangent[FINEANGLES/4-(actor->pitch>>ANGLETOFINESHIFT)]);
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
ball->vel.x = (actor->vel.x>>1) + FixedMul(ball->Speed, finecosine[angle]);
|
||||
ball->vel.y = (actor->vel.y>>1) + FixedMul(ball->Speed, finesine[angle]);
|
||||
ball->Angles.Yaw = actor->Angles.Yaw;
|
||||
ball->AddZ(ball->Vel.Z);
|
||||
ball->VelFromAngle();
|
||||
ball->Vel += actor->Vel.XY()/2;
|
||||
S_Sound (ball, CHAN_BODY, "weapons/maceshoot", 1, ATTN_NORM);
|
||||
P_CheckMissileSpawn (ball, actor->radius);
|
||||
}
|
||||
|
@ -435,19 +432,18 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMacePL1)
|
|||
|
||||
if (pr_maceatk() < 28)
|
||||
{
|
||||
FireMacePL1B (self);
|
||||
FireMacePL1B(self);
|
||||
return 0;
|
||||
}
|
||||
AWeapon *weapon = player->ReadyWeapon;
|
||||
if (weapon != NULL)
|
||||
{
|
||||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
if (!weapon->DepleteAmmo(weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
player->psprites[ps_weapon].sx = ((pr_maceatk()&3)-2)*FRACUNIT;
|
||||
player->psprites[ps_weapon].sy = WEAPONTOP+(pr_maceatk()&3)*FRACUNIT;
|
||||
ball = P_SpawnPlayerMissile (self, PClass::FindActor("MaceFX1"),
|
||||
self->angle+(((pr_maceatk()&7)-4)<<24));
|
||||
player->psprites[ps_weapon].sx = ((pr_maceatk() & 3) - 2);
|
||||
player->psprites[ps_weapon].sy = WEAPONTOP + (pr_maceatk() & 3);
|
||||
ball = P_SpawnPlayerMissile(self, PClass::FindActor("MaceFX1"), self->Angles.Yaw + (((pr_maceatk() & 7) - 4) * (360. / 256)));
|
||||
if (ball)
|
||||
{
|
||||
ball->special1 = 16; // tics till dropoff
|
||||
|
@ -476,21 +472,19 @@ DEFINE_ACTION_FUNCTION(AActor, A_MacePL1Check)
|
|||
}
|
||||
self->special1 = 0;
|
||||
self->flags &= ~MF_NOGRAVITY;
|
||||
self->gravity = FRACUNIT/8;
|
||||
self->Gravity = 1. / 8;;
|
||||
// [RH] Avoid some precision loss by scaling the velocity directly
|
||||
#if 0
|
||||
// This is the original code, for reference.
|
||||
angle_t angle = self->angle>>ANGLETOFINESHIFT;
|
||||
self->vel.x = FixedMul(7*FRACUNIT, finecosine[angle]);
|
||||
self->vel.y = FixedMul(7*FRACUNIT, finesine[angle]);
|
||||
a.ngle_t angle = self->angle>>ANGLETOF.INESHIFT;
|
||||
self->velx = F.ixedMul(7*F.RACUNIT, f.inecosine[angle]);
|
||||
self->vely = F.ixedMul(7*F.RACUNIT, f.inesine[angle]);
|
||||
#else
|
||||
double velscale = sqrt ((double)self->vel.x * (double)self->vel.x +
|
||||
(double)self->vel.y * (double)self->vel.y);
|
||||
velscale = 458752 / velscale;
|
||||
self->vel.x = (int)(self->vel.x * velscale);
|
||||
self->vel.y = (int)(self->vel.y * velscale);
|
||||
double velscale = 7 / self->Vel.XY().Length();
|
||||
self->Vel.X *= velscale;
|
||||
self->Vel.Y *= velscale;
|
||||
#endif
|
||||
self->vel.z -= self->vel.z >> 1;
|
||||
self->Vel.Z *= 0.5;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -507,16 +501,16 @@ DEFINE_ACTION_FUNCTION(AActor, A_MaceBallImpact)
|
|||
if ((self->health != MAGIC_JUNK) && (self->flags & MF_INBOUNCE))
|
||||
{ // Bounce
|
||||
self->health = MAGIC_JUNK;
|
||||
self->vel.z = (self->vel.z * 192) >> 8;
|
||||
self->Vel.Z *= 0.75;
|
||||
self->BounceFlags = BOUNCE_None;
|
||||
self->SetState (self->SpawnState);
|
||||
S_Sound (self, CHAN_BODY, "weapons/macebounce", 1, ATTN_NORM);
|
||||
}
|
||||
else
|
||||
{ // Explode
|
||||
self->vel.x = self->vel.y = self->vel.z = 0;
|
||||
self->Vel.Zero();
|
||||
self->flags |= MF_NOGRAVITY;
|
||||
self->gravity = FRACUNIT;
|
||||
self->Gravity = 1;
|
||||
S_Sound (self, CHAN_BODY, "weapons/macehit", 1, ATTN_NORM);
|
||||
}
|
||||
return 0;
|
||||
|
@ -533,7 +527,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_MaceBallImpact2)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
AActor *tiny;
|
||||
angle_t angle;
|
||||
|
||||
if ((self->Z() <= self->floorz) && P_HitFloor (self))
|
||||
{ // Landed in some sort of liquid
|
||||
|
@ -542,42 +535,36 @@ DEFINE_ACTION_FUNCTION(AActor, A_MaceBallImpact2)
|
|||
}
|
||||
if (self->flags & MF_INBOUNCE)
|
||||
{
|
||||
if (self->vel.z < 2*FRACUNIT)
|
||||
if (self->Vel.Z < 2)
|
||||
{
|
||||
goto boom;
|
||||
}
|
||||
|
||||
// Bounce
|
||||
self->vel.z = (self->vel.z * 192) >> 8;
|
||||
self->Vel.Z *= 0.75;
|
||||
self->SetState (self->SpawnState);
|
||||
|
||||
tiny = Spawn("MaceFX3", self->Pos(), ALLOW_REPLACE);
|
||||
angle = self->angle+ANG90;
|
||||
tiny->target = self->target;
|
||||
tiny->angle = angle;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
tiny->vel.x = (self->vel.x>>1) + FixedMul(self->vel.z-FRACUNIT, finecosine[angle]);
|
||||
tiny->vel.y = (self->vel.y>>1) + FixedMul(self->vel.z-FRACUNIT, finesine[angle]);
|
||||
tiny->vel.z = self->vel.z;
|
||||
tiny->Angles.Yaw = self->Angles.Yaw + 90.;
|
||||
tiny->VelFromAngle(self->Vel.Z - 1.);
|
||||
tiny->Vel += { self->Vel.X * .5, self->Vel.Y * .5, self->Vel.Z };
|
||||
P_CheckMissileSpawn (tiny, self->radius);
|
||||
|
||||
tiny = Spawn("MaceFX3", self->Pos(), ALLOW_REPLACE);
|
||||
angle = self->angle-ANG90;
|
||||
tiny->target = self->target;
|
||||
tiny->angle = angle;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
tiny->vel.x = (self->vel.x>>1) + FixedMul(self->vel.z-FRACUNIT, finecosine[angle]);
|
||||
tiny->vel.y = (self->vel.y>>1) + FixedMul(self->vel.z-FRACUNIT, finesine[angle]);
|
||||
tiny->vel.z = self->vel.z;
|
||||
tiny->Angles.Yaw = self->Angles.Yaw - 90.;
|
||||
tiny->VelFromAngle(self->Vel.Z - 1.);
|
||||
tiny->Vel += { self->Vel.X * .5, self->Vel.Y * .5, self->Vel.Z };
|
||||
P_CheckMissileSpawn (tiny, self->radius);
|
||||
}
|
||||
else
|
||||
{ // Explode
|
||||
boom:
|
||||
self->vel.x = self->vel.y = self->vel.z = 0;
|
||||
self->Vel.Zero();
|
||||
self->flags |= MF_NOGRAVITY;
|
||||
self->BounceFlags = BOUNCE_None;
|
||||
self->gravity = FRACUNIT;
|
||||
self->Gravity = 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -607,13 +594,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireMacePL2)
|
|||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
mo = P_SpawnPlayerMissile (self, 0,0,0, RUNTIME_CLASS(AMaceFX4), self->angle, &t);
|
||||
mo = P_SpawnPlayerMissile (self, 0,0,0, RUNTIME_CLASS(AMaceFX4), self->Angles.Yaw, &t);
|
||||
if (mo)
|
||||
{
|
||||
mo->vel.x += self->vel.x;
|
||||
mo->vel.y += self->vel.y;
|
||||
mo->vel.z = 2*FRACUNIT+
|
||||
clamp<fixed_t>(finetangent[FINEANGLES/4-(self->pitch>>ANGLETOFINESHIFT)], -5*FRACUNIT, 5*FRACUNIT);
|
||||
mo->Vel += self->Vel.XY();
|
||||
mo->Vel.Z = 2 - player->mo->Angles.Pitch.TanClamped();
|
||||
if (t.linetarget && !t.unlinked)
|
||||
{
|
||||
mo->tracer = t.linetarget;
|
||||
|
@ -635,7 +620,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DeathBallImpact)
|
|||
|
||||
int i;
|
||||
AActor *target;
|
||||
angle_t angle = 0;
|
||||
DAngle angle = 0.;
|
||||
bool newAngle;
|
||||
FTranslatedLineTarget t;
|
||||
|
||||
|
@ -646,7 +631,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_DeathBallImpact)
|
|||
}
|
||||
if (self->flags & MF_INBOUNCE)
|
||||
{
|
||||
if (self->vel.z < 2*FRACUNIT)
|
||||
if (self->Vel.Z < 2)
|
||||
{
|
||||
goto boom;
|
||||
}
|
||||
|
@ -668,10 +653,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_DeathBallImpact)
|
|||
}
|
||||
else
|
||||
{ // Find new target
|
||||
angle = 0;
|
||||
angle = 0.;
|
||||
for (i = 0; i < 16; i++)
|
||||
{
|
||||
P_AimLineAttack (self, angle, 10*64*FRACUNIT, &t, 0, ALF_NOFRIENDS|ALF_PORTALRESTRICT, NULL, self->target);
|
||||
P_AimLineAttack (self, angle, 640., &t, 0., ALF_NOFRIENDS|ALF_PORTALRESTRICT, NULL, self->target);
|
||||
if (t.linetarget && self->target != t.linetarget)
|
||||
{
|
||||
self->tracer = t.linetarget;
|
||||
|
@ -679,15 +664,13 @@ DEFINE_ACTION_FUNCTION(AActor, A_DeathBallImpact)
|
|||
newAngle = true;
|
||||
break;
|
||||
}
|
||||
angle += ANGLE_45/2;
|
||||
angle += 22.5;
|
||||
}
|
||||
}
|
||||
if (newAngle)
|
||||
{
|
||||
self->angle = angle;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
self->vel.x = FixedMul (self->Speed, finecosine[angle]);
|
||||
self->vel.y = FixedMul (self->Speed, finesine[angle]);
|
||||
self->Angles.Yaw = angle;
|
||||
self->VelFromAngle();
|
||||
}
|
||||
self->SetState (self->SpawnState);
|
||||
S_Sound (self, CHAN_BODY, "weapons/macestop", 1, ATTN_NORM);
|
||||
|
@ -695,9 +678,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_DeathBallImpact)
|
|||
else
|
||||
{ // Explode
|
||||
boom:
|
||||
self->vel.x = self->vel.y = self->vel.z = 0;
|
||||
self->Vel.Zero();
|
||||
self->flags |= MF_NOGRAVITY;
|
||||
self->gravity = FRACUNIT;
|
||||
self->Gravity = 1;
|
||||
S_Sound (self, CHAN_BODY, "weapons/maceexplode", 1, ATTN_NORM);
|
||||
}
|
||||
return 0;
|
||||
|
@ -737,7 +720,7 @@ void ABlasterFX1::Effect ()
|
|||
{
|
||||
if (pr_bfx1t() < 64)
|
||||
{
|
||||
Spawn("BlasterSmoke", X(), Y(), MAX<fixed_t> (Z() - 8 * FRACUNIT, floorz), ALLOW_REPLACE);
|
||||
Spawn("BlasterSmoke", PosAtZ(MAX(Z() - 8., floorz)), ALLOW_REPLACE);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -778,7 +761,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireBlasterPL1)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
player_t *player;
|
||||
|
||||
|
@ -793,12 +776,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireBlasterPL1)
|
|||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
angle_t pitch = P_BulletSlope(self);
|
||||
DAngle pitch = P_BulletSlope(self);
|
||||
damage = pr_fb1.HitDice (4);
|
||||
angle = self->angle;
|
||||
angle = self->Angles.Yaw;
|
||||
if (player->refire)
|
||||
{
|
||||
angle += pr_fb1.Random2() << 18;
|
||||
angle += pr_fb1.Random2() * (5.625 / 256);
|
||||
}
|
||||
P_LineAttack (self, angle, PLAYERMISSILERANGE, pitch, damage, NAME_Hitscan, "BlasterPuff");
|
||||
S_Sound (self, CHAN_WEAPON, "weapons/blastershoot", 1, ATTN_NORM);
|
||||
|
@ -816,18 +799,16 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpawnRippers)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
unsigned int i;
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
AActor *ripper;
|
||||
|
||||
for(i = 0; i < 8; i++)
|
||||
{
|
||||
ripper = Spawn<ARipper> (self->Pos(), ALLOW_REPLACE);
|
||||
angle = i*ANG45;
|
||||
angle = i*45.;
|
||||
ripper->target = self->target;
|
||||
ripper->angle = angle;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
ripper->vel.x = FixedMul (ripper->Speed, finecosine[angle]);
|
||||
ripper->vel.y = FixedMul (ripper->Speed, finesine[angle]);
|
||||
ripper->Angles.Yaw = angle;
|
||||
ripper->VelFromAngle();
|
||||
P_CheckMissileSpawn (ripper, self->radius);
|
||||
}
|
||||
return 0;
|
||||
|
@ -955,7 +936,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireSkullRodPL2)
|
|||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
P_SpawnPlayerMissile (self, 0,0,0, RUNTIME_CLASS(AHornRodFX2), self->angle, &t, &MissileActor);
|
||||
P_SpawnPlayerMissile (self, 0,0,0, RUNTIME_CLASS(AHornRodFX2), self->Angles.Yaw, &t, &MissileActor);
|
||||
// Use MissileActor instead of the return value from
|
||||
// P_SpawnPlayerMissile because we need to give info to the mobj
|
||||
// even if it exploded immediately.
|
||||
|
@ -1071,10 +1052,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_SkullRodStorm)
|
|||
{ // Fudge rain frequency
|
||||
return 0;
|
||||
}
|
||||
fixedvec2 pos = self->Vec2Offset(
|
||||
((pr_storm()&127) - 64) * FRACUNIT,
|
||||
((pr_storm()&127) - 64) * FRACUNIT);
|
||||
mo = Spawn<ARainPillar> (pos.x, pos.y, ONCEILINGZ, ALLOW_REPLACE);
|
||||
double xo = ((pr_storm() & 127) - 64);
|
||||
double yo = ((pr_storm() & 127) - 64);
|
||||
DVector3 pos = self->Vec2OffsetZ(xo, yo, ONCEILINGZ);
|
||||
mo = Spawn<ARainPillar> (pos, ALLOW_REPLACE);
|
||||
// We used bouncecount to store the 3D floor index in A_HideInCeiling
|
||||
if (!mo) return 0;
|
||||
if (mo->Sector->PortalGroup != self->Sector->PortalGroup)
|
||||
|
@ -1083,19 +1064,16 @@ DEFINE_ACTION_FUNCTION(AActor, A_SkullRodStorm)
|
|||
mo->Destroy();
|
||||
return 0;
|
||||
}
|
||||
fixed_t newz;
|
||||
if (self->bouncecount >= 0 && (unsigned)self->bouncecount < self->Sector->e->XFloor.ffloors.Size())
|
||||
newz = self->Sector->e->XFloor.ffloors[self->bouncecount]->bottom.plane->ZatPoint(mo);// - 40 * FRACUNIT;
|
||||
pos.Z = self->Sector->e->XFloor.ffloors[self->bouncecount]->bottom.plane->ZatPoint(mo);
|
||||
else
|
||||
newz = self->Sector->ceilingplane.ZatPoint(mo);
|
||||
int moceiling = P_Find3DFloor(NULL, pos.x, pos.y, newz, false, false, newz);
|
||||
if (moceiling >= 0)
|
||||
mo->SetZ(newz - mo->height, false);
|
||||
mo->Translation = multiplayer ?
|
||||
TRANSLATION(TRANSLATION_RainPillar,self->special2) : 0;
|
||||
pos.Z = self->Sector->ceilingplane.ZatPoint(mo);
|
||||
int moceiling = P_Find3DFloor(NULL, pos, false, false, pos.Z);
|
||||
if (moceiling >= 0) mo->SetZ(pos.Z - mo->Height);
|
||||
mo->Translation = multiplayer ? TRANSLATION(TRANSLATION_RainPillar,self->special2) : 0;
|
||||
mo->target = self->target;
|
||||
mo->vel.x = 1; // Force collision detection
|
||||
mo->vel.z = -mo->Speed;
|
||||
mo->Vel.X = MinVel; // Force collision detection
|
||||
mo->Vel.Z = -mo->Speed;
|
||||
mo->special2 = self->special2; // Transfer player number
|
||||
P_CheckMissileSpawn (mo, self->radius);
|
||||
if (self->special1 != -1 && !S_IsActorPlayingSomething (self, CHAN_BODY, -1))
|
||||
|
@ -1136,21 +1114,21 @@ DEFINE_ACTION_FUNCTION(AActor, A_HideInCeiling)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
// We use bouncecount to store the 3D floor index
|
||||
fixed_t foo;
|
||||
for (unsigned int i=0; i< self->Sector->e->XFloor.ffloors.Size(); i++)
|
||||
double foo;
|
||||
for (int i = self->Sector->e->XFloor.ffloors.Size() - 1; i >= 0; i--)
|
||||
{
|
||||
F3DFloor * rover = self->Sector->e->XFloor.ffloors[i];
|
||||
if(!(rover->flags & FF_SOLID) || !(rover->flags & FF_EXISTS)) continue;
|
||||
|
||||
if ((foo = rover->bottom.plane->ZatPoint(self)) >= (self->Top()))
|
||||
if (!(rover->flags & FF_SOLID) || !(rover->flags & FF_EXISTS)) continue;
|
||||
|
||||
if ((foo = rover->bottom.plane->ZatPoint(self)) >= self->Top())
|
||||
{
|
||||
self->SetZ(foo + 4*FRACUNIT, false);
|
||||
self->SetZ(foo + 4, false);
|
||||
self->bouncecount = i;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
self->bouncecount = -1;
|
||||
self->SetZ(self->ceilingz + 4*FRACUNIT, false);
|
||||
self->SetZ(self->ceilingz + 4, false);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1237,7 +1215,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL1)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
player_t *player;
|
||||
|
||||
if (NULL == (player = self->player))
|
||||
|
@ -1252,10 +1229,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL1)
|
|||
return 0;
|
||||
}
|
||||
P_SpawnPlayerMissile (self, RUNTIME_CLASS(APhoenixFX1));
|
||||
angle = self->angle + ANG180;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
self->vel.x += FixedMul (4*FRACUNIT, finecosine[angle]);
|
||||
self->vel.y += FixedMul (4*FRACUNIT, finesine[angle]);
|
||||
self->Thrust(self->Angles.Yaw + 180, 4);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1270,22 +1244,17 @@ DEFINE_ACTION_FUNCTION(AActor, A_PhoenixPuff)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
AActor *puff;
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
|
||||
//[RH] Heretic never sets the target for seeking
|
||||
//P_SeekerMissile (self, ANGLE_1*5, ANGLE_1*10);
|
||||
//P_SeekerMissile (self, 5, 10);
|
||||
puff = Spawn("PhoenixPuff", self->Pos(), ALLOW_REPLACE);
|
||||
angle = self->angle + ANG90;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
puff->vel.x = FixedMul (FRACUNIT*13/10, finecosine[angle]);
|
||||
puff->vel.y = FixedMul (FRACUNIT*13/10, finesine[angle]);
|
||||
puff->vel.z = 0;
|
||||
angle = self->Angles.Yaw + 90;
|
||||
puff->Vel = DVector3(angle.ToVector(1.3), 0);
|
||||
|
||||
puff = Spawn("PhoenixPuff", self->Pos(), ALLOW_REPLACE);
|
||||
angle = self->angle - ANG90;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
puff->vel.x = FixedMul (FRACUNIT*13/10, finecosine[angle]);
|
||||
puff->vel.y = FixedMul (FRACUNIT*13/10, finesine[angle]);
|
||||
puff->vel.z = 0;
|
||||
angle = self->Angles.Yaw - 90;
|
||||
puff->Vel = DVector3(angle.ToVector(1.3), 0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1323,9 +1292,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL2)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
AActor *mo;
|
||||
angle_t angle;
|
||||
|
||||
fixed_t slope;
|
||||
double slope;
|
||||
FSoundID soundid;
|
||||
player_t *player;
|
||||
APhoenixRod *flamethrower;
|
||||
|
@ -1345,20 +1313,19 @@ DEFINE_ACTION_FUNCTION(AActor, A_FirePhoenixPL2)
|
|||
S_StopSound (self, CHAN_WEAPON);
|
||||
return 0;
|
||||
}
|
||||
angle = self->angle;
|
||||
|
||||
fixed_t xo = (pr_fp2.Random2() << 9);
|
||||
fixed_t yo = (pr_fp2.Random2() << 9);
|
||||
fixedvec3 pos = self->Vec3Offset(xo, yo,
|
||||
26*FRACUNIT + finetangent[FINEANGLES/4-(self->pitch>>ANGLETOFINESHIFT)] - self->floorclip);
|
||||
slope = -self->Angles.Pitch.TanClamped();
|
||||
double xo = pr_fp2.Random2() / 128.;
|
||||
double yo = pr_fp2.Random2() / 128.;
|
||||
DVector3 pos = self->Vec3Offset(xo, yo, 26 + slope - self->Floorclip);
|
||||
|
||||
slope = finetangent[FINEANGLES/4-(self->pitch>>ANGLETOFINESHIFT)] + (FRACUNIT/10);
|
||||
slope += 0.1;
|
||||
mo = Spawn("PhoenixFX2", pos, ALLOW_REPLACE);
|
||||
mo->target = self;
|
||||
mo->angle = angle;
|
||||
mo->vel.x = self->vel.x + FixedMul (mo->Speed, finecosine[angle>>ANGLETOFINESHIFT]);
|
||||
mo->vel.y = self->vel.y + FixedMul (mo->Speed, finesine[angle>>ANGLETOFINESHIFT]);
|
||||
mo->vel.z = FixedMul (mo->Speed, slope);
|
||||
mo->Angles.Yaw = self->Angles.Yaw;
|
||||
mo->VelFromAngle();
|
||||
mo->Vel += self->Vel.XY();
|
||||
mo->Vel.Z = mo->Speed * slope;
|
||||
if (!player->refire || !S_IsActorPlayingSomething (self, CHAN_WEAPON, -1))
|
||||
{
|
||||
S_Sound (self, CHAN_WEAPON|CHAN_LOOP, soundid, 1, ATTN_NORM);
|
||||
|
@ -1403,7 +1370,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FlameEnd)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->vel.z += FRACUNIT*3/2;
|
||||
self->Vel.Z += 1.5;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -1417,7 +1384,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FloatPuff)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->vel.z += FRACUNIT*18/10;
|
||||
self->Vel.Z += 1.8;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -30,9 +30,9 @@ int AWhirlwind::DoSpecialDamage (AActor *target, int damage, FName damagetype)
|
|||
|
||||
if (!(target->flags7 & MF7_DONTTHRUST))
|
||||
{
|
||||
target->angle += pr_foo.Random2() << 20;
|
||||
target->vel.x += pr_foo.Random2() << 10;
|
||||
target->vel.y += pr_foo.Random2() << 10;
|
||||
target->Angles.Yaw += pr_foo.Random2() * (360 / 4096.);
|
||||
target->Vel.X += pr_foo.Random2() / 64.;
|
||||
target->Vel.Y += pr_foo.Random2() / 64.;
|
||||
}
|
||||
|
||||
if ((level.time & 16) && !(target->flags2 & MF2_BOSS) && !(target->flags7 & MF7_DONTTHRUST))
|
||||
|
@ -42,10 +42,10 @@ int AWhirlwind::DoSpecialDamage (AActor *target, int damage, FName damagetype)
|
|||
{
|
||||
randVal = 160;
|
||||
}
|
||||
target->vel.z += randVal << 11;
|
||||
if (target->vel.z > 12*FRACUNIT)
|
||||
target->Vel.Z += randVal / 32.;
|
||||
if (target->Vel.Z > 12)
|
||||
{
|
||||
target->vel.z = 12*FRACUNIT;
|
||||
target->Vel.Z = 12;
|
||||
}
|
||||
}
|
||||
if (!(level.time & 7))
|
||||
|
@ -73,7 +73,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_LichAttack)
|
|||
int randAttack;
|
||||
static const int atkResolve1[] = { 50, 150 };
|
||||
static const int atkResolve2[] = { 150, 200 };
|
||||
int dist;
|
||||
|
||||
// Ice ball (close 20% : far 60%)
|
||||
// Fire column (close 40% : far 20%)
|
||||
|
@ -93,7 +92,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LichAttack)
|
|||
P_TraceBleed (newdam > 0 ? newdam : damage, target, self);
|
||||
return 0;
|
||||
}
|
||||
dist = self->AproxDistance (target) > 8*64*FRACUNIT;
|
||||
int dist = self->Distance2D(target) > 8 * 64;
|
||||
randAttack = pr_atk ();
|
||||
if (randAttack < atkResolve1[dist])
|
||||
{ // Ice ball
|
||||
|
@ -114,10 +113,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_LichAttack)
|
|||
S_Sound (self, CHAN_BODY, "ironlich/attack1", 1, ATTN_NORM);
|
||||
}
|
||||
fire->target = baseFire->target;
|
||||
fire->angle = baseFire->angle;
|
||||
fire->vel.x = baseFire->vel.x;
|
||||
fire->vel.y = baseFire->vel.y;
|
||||
fire->vel.z = baseFire->vel.z;
|
||||
fire->Angles.Yaw = baseFire->Angles.Yaw;
|
||||
fire->Vel = baseFire->Vel;
|
||||
fire->Damage = NULL;
|
||||
fire->health = (i+1) * 2;
|
||||
P_CheckMissileSpawn (fire, self->radius);
|
||||
|
@ -129,7 +126,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LichAttack)
|
|||
mo = P_SpawnMissile (self, target, RUNTIME_CLASS(AWhirlwind));
|
||||
if (mo != NULL)
|
||||
{
|
||||
mo->AddZ(-32*FRACUNIT, false);
|
||||
mo->AddZ(-32);
|
||||
mo->tracer = target;
|
||||
mo->health = 20*TICRATE; // Duration
|
||||
S_Sound (self, CHAN_BODY, "ironlich/attack3", 1, ATTN_NORM);
|
||||
|
@ -151,21 +148,21 @@ DEFINE_ACTION_FUNCTION(AActor, A_WhirlwindSeek)
|
|||
self->health -= 3;
|
||||
if (self->health < 0)
|
||||
{
|
||||
self->vel.x = self->vel.y = self->vel.z = 0;
|
||||
self->SetState (self->FindState(NAME_Death));
|
||||
self->Vel.Zero();
|
||||
self->SetState(self->FindState(NAME_Death));
|
||||
self->flags &= ~MF_MISSILE;
|
||||
return 0;
|
||||
}
|
||||
if ((self->threshold -= 3) < 0)
|
||||
{
|
||||
self->threshold = 58 + (pr_seek() & 31);
|
||||
S_Sound (self, CHAN_BODY, "ironlich/attack3", 1, ATTN_NORM);
|
||||
S_Sound(self, CHAN_BODY, "ironlich/attack3", 1, ATTN_NORM);
|
||||
}
|
||||
if (self->tracer && self->tracer->flags&MF_SHADOW)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
P_SeekerMissile (self, ANGLE_1*10, ANGLE_1*30);
|
||||
P_SeekerMissile(self, 10, 30);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -180,19 +177,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_LichIceImpact)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
unsigned int i;
|
||||
angle_t angle;
|
||||
AActor *shard;
|
||||
|
||||
for (i = 0; i < 8; i++)
|
||||
{
|
||||
shard = Spawn("HeadFX2", self->Pos(), ALLOW_REPLACE);
|
||||
angle = i*ANG45;
|
||||
shard->target = self->target;
|
||||
shard->angle = angle;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
shard->vel.x = FixedMul (shard->Speed, finecosine[angle]);
|
||||
shard->vel.y = FixedMul (shard->Speed, finesine[angle]);
|
||||
shard->vel.z = -FRACUNIT*6/10;
|
||||
shard->Angles.Yaw = i*45.;
|
||||
shard->VelFromAngle();
|
||||
shard->Vel.Z = -.6;
|
||||
P_CheckMissileSpawn (shard, self->radius);
|
||||
}
|
||||
return 0;
|
||||
|
@ -209,7 +202,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LichFireGrow)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->health--;
|
||||
self->AddZ(9*FRACUNIT);
|
||||
self->AddZ(9.);
|
||||
if (self->health == 0)
|
||||
{
|
||||
self->Damage = self->GetDefault()->Damage;
|
||||
|
|
|
@ -25,12 +25,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_DripBlood)
|
|||
|
||||
AActor *mo;
|
||||
|
||||
fixed_t xo = (pr_dripblood.Random2() << 11);
|
||||
fixed_t yo = (pr_dripblood.Random2() << 11);
|
||||
mo = Spawn ("Blood", self->Vec3Offset(xo, yo, 0), ALLOW_REPLACE);
|
||||
mo->vel.x = pr_dripblood.Random2 () << 10;
|
||||
mo->vel.y = pr_dripblood.Random2 () << 10;
|
||||
mo->gravity = FRACUNIT/8;
|
||||
double xo = pr_dripblood.Random2() / 32.;
|
||||
double yo = pr_dripblood.Random2() / 32.;
|
||||
mo = Spawn ("Blood", self->Vec3Offset(xo, yo, 0.), ALLOW_REPLACE);
|
||||
mo->Vel.X = pr_dripblood.Random2 () / 64.;
|
||||
mo->Vel.Y = pr_dripblood.Random2() / 64.;
|
||||
mo->Gravity = 1./8;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -60,11 +60,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_KnightAttack)
|
|||
S_Sound (self, CHAN_BODY, self->AttackSound, 1, ATTN_NORM);
|
||||
if (self->flags & MF_SHADOW || pr_knightatk () < 40)
|
||||
{ // Red axe
|
||||
P_SpawnMissileZ (self, self->Z() + 36*FRACUNIT, self->target, PClass::FindActor("RedAxe"));
|
||||
P_SpawnMissileZ (self, self->Z() + 36, self->target, PClass::FindActor("RedAxe"));
|
||||
return 0;
|
||||
}
|
||||
// Green axe
|
||||
P_SpawnMissileZ (self, self->Z() + 36*FRACUNIT, self->target, PClass::FindActor("KnightAxe"));
|
||||
P_SpawnMissileZ (self, self->Z() + 36, self->target, PClass::FindActor("KnightAxe"));
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -53,7 +53,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WizAtk2)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
A_FaceTarget (self);
|
||||
self->alpha = HR_SHADOW;
|
||||
self->Alpha = HR_SHADOW;
|
||||
self->RenderStyle = STYLE_Translucent;
|
||||
self->flags3 |= MF3_GHOST;
|
||||
return 0;
|
||||
|
@ -88,8 +88,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_WizAtk3)
|
|||
mo = P_SpawnMissile (self, self->target, fx);
|
||||
if (mo != NULL)
|
||||
{
|
||||
P_SpawnMissileAngle(self, fx, mo->angle-(ANG45/8), mo->vel.z);
|
||||
P_SpawnMissileAngle(self, fx, mo->angle+(ANG45/8), mo->vel.z);
|
||||
P_SpawnMissileAngle(self, fx, mo->Angles.Yaw - 45. / 8, mo->Vel.Z);
|
||||
P_SpawnMissileAngle(self, fx, mo->Angles.Yaw + 45. / 8, mo->Vel.Z);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -39,7 +39,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BatSpawn)
|
|||
|
||||
AActor *mo;
|
||||
int delta;
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
|
||||
// Countdown until next spawn
|
||||
if (self->special1-- > 0) return 0;
|
||||
|
@ -47,7 +47,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_BatSpawn)
|
|||
|
||||
delta = self->args[1];
|
||||
if (delta==0) delta=1;
|
||||
angle = self->angle + (((pr_batspawn()%delta)-(delta>>1))<<24);
|
||||
|
||||
angle = self->Angles.Yaw + (((pr_batspawn() % delta) - (delta >> 1)) * (360 / 256.));
|
||||
|
||||
mo = P_SpawnMissileAngle (self, PClass::FindActor("Bat"), angle, 0);
|
||||
if (mo)
|
||||
{
|
||||
|
@ -64,7 +66,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BatMove)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t newangle;
|
||||
DAngle newangle;
|
||||
|
||||
if (self->special2 < 0)
|
||||
{
|
||||
|
@ -74,17 +76,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_BatMove)
|
|||
|
||||
if (pr_batmove()<128)
|
||||
{
|
||||
newangle = self->angle + ANGLE_1*self->args[4];
|
||||
newangle = self->Angles.Yaw + self->args[4];
|
||||
}
|
||||
else
|
||||
{
|
||||
newangle = self->angle - ANGLE_1*self->args[4];
|
||||
newangle = self->Angles.Yaw - self->args[4];
|
||||
}
|
||||
|
||||
// Adjust velocity vector to new direction
|
||||
newangle >>= ANGLETOFINESHIFT;
|
||||
self->vel.x = FixedMul (self->Speed, finecosine[newangle]);
|
||||
self->vel.y = FixedMul (self->Speed, finesine[newangle]);
|
||||
self->VelFromAngle(newangle, self->Speed);
|
||||
|
||||
if (pr_batmove()<15)
|
||||
{
|
||||
|
@ -92,7 +92,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BatMove)
|
|||
}
|
||||
|
||||
// Handle Z movement
|
||||
self->SetZ(self->target->Z() + 16*finesine[self->args[0] << BOBTOFINESHIFT]);
|
||||
self->SetZ(self->target->Z() + 2 * BobSin(self->args[0]));
|
||||
self->args[0] = (self->args[0]+3)&63;
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -80,7 +80,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopMissileWeave)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
A_Weave(self, 2, 2, 2*FRACUNIT, FRACUNIT);
|
||||
A_Weave(self, 2, 2, 2., 1.);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -118,15 +118,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopDoBlur)
|
|||
self->special1 = (pr_doblur() & 3) + 3; // Random number of blurs
|
||||
if (pr_doblur() < 120)
|
||||
{
|
||||
P_ThrustMobj (self, self->angle + ANG90, 11*FRACUNIT);
|
||||
self->Thrust(self->Angles.Yaw + 90, 11);
|
||||
}
|
||||
else if (pr_doblur() > 125)
|
||||
{
|
||||
P_ThrustMobj (self, self->angle - ANG90, 11*FRACUNIT);
|
||||
self->Thrust(self->Angles.Yaw - 90, 11);
|
||||
}
|
||||
else
|
||||
{ // Thrust forward
|
||||
P_ThrustMobj (self, self->angle, 11*FRACUNIT);
|
||||
self->Thrust(11);
|
||||
}
|
||||
S_Sound (self, CHAN_BODY, "BishopBlur", 1, ATTN_NORM);
|
||||
return 0;
|
||||
|
@ -146,8 +146,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopSpawnBlur)
|
|||
|
||||
if (!--self->special1)
|
||||
{
|
||||
self->vel.x = 0;
|
||||
self->vel.y = 0;
|
||||
self->Vel.X = self->Vel.Y = 0;
|
||||
if (pr_sblur() > 96)
|
||||
{
|
||||
self->SetState (self->SeeState);
|
||||
|
@ -160,7 +159,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopSpawnBlur)
|
|||
mo = Spawn ("BishopBlur", self->Pos(), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->angle = self->angle;
|
||||
mo->Angles.Yaw = self->Angles.Yaw;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -175,9 +174,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopChase)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
fixed_t newz = self->Z() - finesine[self->special2 << BOBTOFINESHIFT] * 4;
|
||||
double newz = self->Z() - BobSin(self->special2) / 2.;
|
||||
self->special2 = (self->special2 + 4) & 63;
|
||||
newz += finesine[self->special2 << BOBTOFINESHIFT] * 4;
|
||||
newz += BobSin(self->special2) / 2.;
|
||||
self->SetZ(newz);
|
||||
return 0;
|
||||
}
|
||||
|
@ -194,10 +193,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopPuff)
|
|||
|
||||
AActor *mo;
|
||||
|
||||
mo = Spawn ("BishopPuff", self->PosPlusZ(40*FRACUNIT), ALLOW_REPLACE);
|
||||
mo = Spawn ("BishopPuff", self->PosPlusZ(40.), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->vel.z = FRACUNIT/2;
|
||||
mo->Vel.Z = -.5;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -219,13 +218,13 @@ DEFINE_ACTION_FUNCTION(AActor, A_BishopPainBlur)
|
|||
self->SetState (self->FindState ("Blur"));
|
||||
return 0;
|
||||
}
|
||||
fixed_t xo = (pr_pain.Random2() << 12);
|
||||
fixed_t yo = (pr_pain.Random2() << 12);
|
||||
fixed_t zo = (pr_pain.Random2() << 11);
|
||||
double xo = pr_pain.Random2() / 16.;
|
||||
double yo = pr_pain.Random2() / 16.;
|
||||
double zo = pr_pain.Random2() / 32.;
|
||||
mo = Spawn ("BishopPainBlur", self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->angle = self->angle;
|
||||
mo->Angles.Yaw = self->Angles.Yaw;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -9,8 +9,8 @@
|
|||
*/
|
||||
|
||||
/* For reference, the default values:
|
||||
#define BLAST_RADIUS_DIST 255*FRACUNIT
|
||||
#define BLAST_SPEED 20*FRACUNIT
|
||||
#define BLAST_RADIUS_DIST 255*F.RACUNIT
|
||||
#define BLAST_SPEED 20*F.RACUNIT
|
||||
#define BLAST_FULLSTRENGTH 255
|
||||
*/
|
||||
|
||||
|
@ -22,11 +22,11 @@
|
|||
//
|
||||
//==========================================================================
|
||||
|
||||
void BlastActor (AActor *victim, fixed_t strength, fixed_t speed, AActor *Owner, PClassActor *blasteffect, bool dontdamage)
|
||||
void BlastActor (AActor *victim, double strength, double speed, AActor *Owner, PClassActor *blasteffect, bool dontdamage)
|
||||
{
|
||||
angle_t angle,ang;
|
||||
DAngle angle;
|
||||
AActor *mo;
|
||||
fixedvec3 pos;
|
||||
DVector3 pos;
|
||||
|
||||
if (!victim->SpecialBlastHandling (Owner, strength))
|
||||
{
|
||||
|
@ -34,35 +34,33 @@ void BlastActor (AActor *victim, fixed_t strength, fixed_t speed, AActor *Owner,
|
|||
}
|
||||
|
||||
angle = Owner->AngleTo(victim);
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
victim->vel.x = FixedMul (speed, finecosine[angle]);
|
||||
victim->vel.y = FixedMul (speed, finesine[angle]);
|
||||
DVector2 move = angle.ToVector(speed);
|
||||
victim->Vel.X = move.X;
|
||||
victim->Vel.Y = move.Y;
|
||||
|
||||
// Spawn blast puff
|
||||
ang = victim->AngleTo(Owner);
|
||||
ang >>= ANGLETOFINESHIFT;
|
||||
angle -= 180.;
|
||||
pos = victim->Vec3Offset(
|
||||
FixedMul (victim->radius+FRACUNIT, finecosine[ang]),
|
||||
FixedMul (victim->radius+FRACUNIT, finesine[ang]),
|
||||
-victim->floorclip + (victim->height>>1));
|
||||
(victim->radius + 1) * angle.Cos(),
|
||||
(victim->radius + 1) * angle.Sin(),
|
||||
(victim->Height / 2) - victim->Floorclip);
|
||||
mo = Spawn (blasteffect, pos, ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->vel.x = victim->vel.x;
|
||||
mo->vel.y = victim->vel.y;
|
||||
mo->Vel.X = victim->Vel.X;
|
||||
mo->Vel.Y = victim->Vel.Y;
|
||||
}
|
||||
if (victim->flags & MF_MISSILE)
|
||||
{
|
||||
// [RH] Floor and ceiling huggers should not be blasted vertically.
|
||||
if (!(victim->flags3 & (MF3_FLOORHUGGER|MF3_CEILINGHUGGER)))
|
||||
{
|
||||
victim->vel.z = 8*FRACUNIT;
|
||||
mo->vel.z = victim->vel.z;
|
||||
mo->Vel.Z = victim->Vel.Z = 8;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
victim->vel.z = (1000 / victim->Mass) << FRACBITS;
|
||||
victim->Vel.Z = 1000. / victim->Mass;
|
||||
}
|
||||
if (victim->player)
|
||||
{
|
||||
|
@ -99,15 +97,14 @@ DEFINE_ACTION_FUNCTION_PARAMS (AActor, A_Blast)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
PARAM_INT_OPT (blastflags) { blastflags = 0; }
|
||||
PARAM_FIXED_OPT (strength) { strength = 255*FRACUNIT; }
|
||||
PARAM_FIXED_OPT (radius) { radius = 255*FRACUNIT; }
|
||||
PARAM_FIXED_OPT (speed) { speed = 20*FRACUNIT; }
|
||||
PARAM_FLOAT_OPT (strength) { strength = 255; }
|
||||
PARAM_FLOAT_OPT (radius) { radius = 255; }
|
||||
PARAM_FLOAT_OPT (speed) { speed = 20; }
|
||||
PARAM_CLASS_OPT (blasteffect, AActor) { blasteffect = PClass::FindActor("BlastEffect"); }
|
||||
PARAM_SOUND_OPT (blastsound) { blastsound = "BlastRadius"; }
|
||||
|
||||
AActor *mo;
|
||||
TThinkerIterator<AActor> iterator;
|
||||
fixed_t dist;
|
||||
|
||||
if (self->player && (blastflags & BF_USEAMMO) && ACTION_CALL_FROM_WEAPON())
|
||||
{
|
||||
|
@ -146,8 +143,7 @@ DEFINE_ACTION_FUNCTION_PARAMS (AActor, A_Blast)
|
|||
{ // Must be monster, player, missile, touchy or vulnerable
|
||||
continue;
|
||||
}
|
||||
dist = self->AproxDistance (mo);
|
||||
if (dist > radius)
|
||||
if (self->Distance2D(mo) > radius)
|
||||
{ // Out of range
|
||||
continue;
|
||||
}
|
||||
|
|
|
@ -29,7 +29,7 @@ bool AArtiBoostArmor::Use (bool pickup)
|
|||
|
||||
for (int i = 0; i < 4; ++i)
|
||||
{
|
||||
armor = Spawn<AHexenArmor> (0,0,0, NO_REPLACE);
|
||||
armor = Spawn<AHexenArmor>();
|
||||
armor->flags |= MF_DROPPED;
|
||||
armor->health = i;
|
||||
armor->Amount = 1;
|
||||
|
@ -46,7 +46,7 @@ bool AArtiBoostArmor::Use (bool pickup)
|
|||
}
|
||||
else
|
||||
{
|
||||
ABasicArmorBonus *armor = Spawn<ABasicArmorBonus> (0,0,0, NO_REPLACE);
|
||||
ABasicArmorBonus *armor = Spawn<ABasicArmorBonus>();
|
||||
armor->flags |= MF_DROPPED;
|
||||
armor->SaveAmount = 50;
|
||||
armor->MaxSaveAmount = 300;
|
||||
|
|
|
@ -13,9 +13,8 @@
|
|||
#include "thingdef/thingdef.h"
|
||||
*/
|
||||
|
||||
const fixed_t FLAMESPEED = fixed_t(0.45*FRACUNIT);
|
||||
const fixed_t CFLAMERANGE = 12*64*FRACUNIT;
|
||||
const fixed_t FLAMEROTSPEED = 2*FRACUNIT;
|
||||
const double FLAMESPEED = 0.45;
|
||||
const double FLAMEROTSPEED = 2.;
|
||||
|
||||
static FRandom pr_missile ("CFlameMissile");
|
||||
|
||||
|
@ -43,20 +42,18 @@ void ACFlameMissile::BeginPlay ()
|
|||
|
||||
void ACFlameMissile::Effect ()
|
||||
{
|
||||
fixed_t newz;
|
||||
|
||||
if (!--special1)
|
||||
{
|
||||
special1 = 4;
|
||||
newz = Z()-12*FRACUNIT;
|
||||
double newz = Z() - 12;
|
||||
if (newz < floorz)
|
||||
{
|
||||
newz = floorz;
|
||||
}
|
||||
AActor *mo = Spawn ("CFlameFloor", X(), Y(), newz, ALLOW_REPLACE);
|
||||
AActor *mo = Spawn ("CFlameFloor", PosAtZ(newz), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->angle = angle;
|
||||
mo->Angles.Yaw = Angles.Yaw;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -99,9 +96,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CFlamePuff)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->renderflags &= ~RF_INVISIBLE;
|
||||
self->vel.x = 0;
|
||||
self->vel.y = 0;
|
||||
self->vel.z = 0;
|
||||
self->Vel.Zero();
|
||||
S_Sound (self, CHAN_BODY, "ClericFlameExplode", 1, ATTN_NORM);
|
||||
return 0;
|
||||
}
|
||||
|
@ -117,8 +112,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_CFlameMissile)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int i;
|
||||
int an, an90;
|
||||
fixed_t dist;
|
||||
DAngle an;
|
||||
double dist;
|
||||
AActor *mo;
|
||||
|
||||
self->renderflags &= ~RF_INVISIBLE;
|
||||
|
@ -126,33 +121,28 @@ DEFINE_ACTION_FUNCTION(AActor, A_CFlameMissile)
|
|||
AActor *BlockingMobj = self->BlockingMobj;
|
||||
if (BlockingMobj && BlockingMobj->flags&MF_SHOOTABLE)
|
||||
{ // Hit something, so spawn the flame circle around the thing
|
||||
dist = BlockingMobj->radius+18*FRACUNIT;
|
||||
dist = BlockingMobj->radius + 18;
|
||||
for (i = 0; i < 4; i++)
|
||||
{
|
||||
an = (i*ANG45)>>ANGLETOFINESHIFT;
|
||||
an90 = (i*ANG45+ANG90)>>ANGLETOFINESHIFT;
|
||||
mo = Spawn ("CircleFlame", BlockingMobj->Vec3Offset(
|
||||
FixedMul(dist, finecosine[an]),
|
||||
FixedMul(dist, finesine[an]),
|
||||
5*FRACUNIT), ALLOW_REPLACE);
|
||||
an = i*45.;
|
||||
mo = Spawn ("CircleFlame", BlockingMobj->Vec3Angle(dist, an, 5), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->angle = an<<ANGLETOFINESHIFT;
|
||||
mo->Angles.Yaw = an;
|
||||
mo->target = self->target;
|
||||
mo->vel.x = mo->special1 = FixedMul(FLAMESPEED, finecosine[an]);
|
||||
mo->vel.y = mo->special2 = FixedMul(FLAMESPEED, finesine[an]);
|
||||
mo->VelFromAngle(FLAMESPEED);
|
||||
mo->specialf1 = mo->Vel.X;
|
||||
mo->specialf2 = mo->Vel.Y;
|
||||
mo->tics -= pr_missile()&3;
|
||||
}
|
||||
mo = Spawn ("CircleFlame", BlockingMobj->Vec3Offset(
|
||||
-FixedMul(dist, finecosine[an]),
|
||||
-FixedMul(dist, finesine[an]),
|
||||
5*FRACUNIT), ALLOW_REPLACE);
|
||||
mo = Spawn("CircleFlame", BlockingMobj->Vec3Angle(dist, an, 5), ALLOW_REPLACE);
|
||||
if(mo)
|
||||
{
|
||||
mo->angle = ANG180+(an<<ANGLETOFINESHIFT);
|
||||
mo->Angles.Yaw = an + 180.;
|
||||
mo->target = self->target;
|
||||
mo->vel.x = mo->special1 = FixedMul(-FLAMESPEED, finecosine[an]);
|
||||
mo->vel.y = mo->special2 = FixedMul(-FLAMESPEED, finesine[an]);
|
||||
mo->VelFromAngle(-FLAMESPEED);
|
||||
mo->specialf1 = mo->Vel.X;
|
||||
mo->specialf2 = mo->Vel.Y;
|
||||
mo->tics -= pr_missile()&3;
|
||||
}
|
||||
}
|
||||
|
@ -171,11 +161,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_CFlameRotate)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int an;
|
||||
DAngle an = self->Angles.Yaw + 90.;
|
||||
self->VelFromAngle(an, FLAMEROTSPEED);
|
||||
self->Vel += DVector2(self->specialf1, self->specialf2);
|
||||
|
||||
an = (self->angle+ANG90)>>ANGLETOFINESHIFT;
|
||||
self->vel.x = self->special1+FixedMul(FLAMEROTSPEED, finecosine[an]);
|
||||
self->vel.y = self->special2+FixedMul(FLAMEROTSPEED, finesine[an]);
|
||||
self->angle += ANG90/15;
|
||||
self->Angles.Yaw += 6.;
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -63,7 +63,7 @@ IMPLEMENT_CLASS (ACWeapWraithverge)
|
|||
|
||||
IMPLEMENT_CLASS (AHolySpirit)
|
||||
|
||||
bool AHolySpirit::Slam (AActor *thing)
|
||||
bool AHolySpirit::Slam(AActor *thing)
|
||||
{
|
||||
if (thing->flags&MF_SHOOTABLE && thing != target)
|
||||
{
|
||||
|
@ -91,14 +91,14 @@ bool AHolySpirit::Slam (AActor *thing)
|
|||
// ghost burns out faster when attacking players/bosses
|
||||
health -= 6;
|
||||
}
|
||||
P_DamageMobj (thing, this, target, dam, NAME_Melee);
|
||||
P_DamageMobj(thing, this, target, dam, NAME_Melee);
|
||||
if (pr_spiritslam() < 128)
|
||||
{
|
||||
Spawn ("HolyPuff", Pos(), ALLOW_REPLACE);
|
||||
S_Sound (this, CHAN_WEAPON, "SpiritAttack", 1, ATTN_NORM);
|
||||
Spawn("HolyPuff", Pos(), ALLOW_REPLACE);
|
||||
S_Sound(this, CHAN_WEAPON, "SpiritAttack", 1, ATTN_NORM);
|
||||
if (thing->flags3&MF3_ISMONSTER && pr_spiritslam() < 128)
|
||||
{
|
||||
thing->Howl ();
|
||||
thing->Howl();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -110,7 +110,7 @@ bool AHolySpirit::Slam (AActor *thing)
|
|||
return true;
|
||||
}
|
||||
|
||||
bool AHolySpirit::SpecialBlastHandling (AActor *source, fixed_t strength)
|
||||
bool AHolySpirit::SpecialBlastHandling (AActor *source, double strength)
|
||||
{
|
||||
if (tracer == source)
|
||||
{
|
||||
|
@ -133,7 +133,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_CHolyAttack2)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int j;
|
||||
int i;
|
||||
AActor *mo;
|
||||
|
||||
for (j = 0; j < 4; j++)
|
||||
|
@ -145,23 +144,24 @@ DEFINE_ACTION_FUNCTION(AActor, A_CHolyAttack2)
|
|||
}
|
||||
switch (j)
|
||||
{ // float bob index
|
||||
|
||||
case 0:
|
||||
mo->special2 = pr_holyatk2(8 << BOBTOFINESHIFT); // upper-left
|
||||
mo->WeaveIndexZ = pr_holyatk2() & 7; // upper-left
|
||||
break;
|
||||
case 1:
|
||||
mo->special2 = FINEANGLES/2 + pr_holyatk2(8 << BOBTOFINESHIFT); // upper-right
|
||||
mo->WeaveIndexZ = 32 + (pr_holyatk2() & 7); // upper-right
|
||||
break;
|
||||
case 2:
|
||||
mo->special2 = (FINEANGLES/2 + pr_holyatk2(8 << BOBTOFINESHIFT)) << 16; // lower-left
|
||||
mo->WeaveIndexXY = 32 + (pr_holyatk2() & 7); // lower-left
|
||||
break;
|
||||
case 3:
|
||||
i = pr_holyatk2(8 << BOBTOFINESHIFT);
|
||||
mo->special2 = ((FINEANGLES/2 + i) << 16) + FINEANGLES/2 + pr_holyatk2(8 << BOBTOFINESHIFT);
|
||||
mo->WeaveIndexXY = 32 + (pr_holyatk2() & 7);
|
||||
mo->WeaveIndexZ = 32 + (pr_holyatk2() & 7);
|
||||
break;
|
||||
}
|
||||
mo->SetZ(self->Z());
|
||||
mo->angle = self->angle+(ANGLE_45+ANGLE_45/2)-ANGLE_45*j;
|
||||
P_ThrustMobj(mo, mo->angle, mo->Speed);
|
||||
mo->Angles.Yaw = self->Angles.Yaw + 67.5 - 45.*j;
|
||||
mo->Thrust();
|
||||
mo->target = self->target;
|
||||
mo->args[0] = 10; // initial turn value
|
||||
mo->args[1] = 0; // initial look angle
|
||||
|
@ -225,7 +225,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CHolyAttack)
|
|||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
AActor *missile = P_SpawnPlayerMissile (self, 0,0,0, PClass::FindActor("HolyMissile"), self->angle, &t);
|
||||
AActor *missile = P_SpawnPlayerMissile (self, 0,0,0, PClass::FindActor("HolyMissile"), self->Angles.Yaw, &t);
|
||||
if (missile != NULL && !t.unlinked)
|
||||
{
|
||||
missile->tracer = t.linetarget;
|
||||
|
@ -263,42 +263,41 @@ DEFINE_ACTION_FUNCTION(AActor, A_CHolyPalette)
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
static void CHolyTailFollow (AActor *actor, fixed_t dist)
|
||||
static void CHolyTailFollow(AActor *actor, double dist)
|
||||
{
|
||||
AActor *child;
|
||||
int an;
|
||||
fixed_t oldDistance, newDistance;
|
||||
DAngle an;
|
||||
double oldDistance, newDistance;
|
||||
|
||||
while (actor)
|
||||
{
|
||||
child = actor->tracer;
|
||||
if (child)
|
||||
{
|
||||
an = actor->AngleTo(child) >> ANGLETOFINESHIFT;
|
||||
oldDistance = child->AproxDistance (actor);
|
||||
if (P_TryMove (child, actor->X()+FixedMul(dist, finecosine[an]),
|
||||
actor->Y()+FixedMul(dist, finesine[an]), true))
|
||||
an = actor->AngleTo(child);
|
||||
oldDistance = child->Distance2D(actor);
|
||||
if (P_TryMove(child, actor->Pos().XY() + an.ToVector(dist), true))
|
||||
{
|
||||
newDistance = child->AproxDistance (actor)-FRACUNIT;
|
||||
if (oldDistance < FRACUNIT)
|
||||
newDistance = child->Distance2D(actor) - 1;
|
||||
if (oldDistance < 1)
|
||||
{
|
||||
if (child->Z() < actor->Z())
|
||||
{
|
||||
child->SetZ(actor->Z()-dist);
|
||||
child->SetZ(actor->Z() - dist);
|
||||
}
|
||||
else
|
||||
{
|
||||
child->SetZ(actor->Z()+dist);
|
||||
child->SetZ(actor->Z() + dist);
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
child->SetZ(actor->Z() + Scale (newDistance, child->Z()-actor->Z(), oldDistance));
|
||||
child->SetZ(actor->Z() + (newDistance * (child->Z() - actor->Z()) / oldDistance));
|
||||
}
|
||||
}
|
||||
}
|
||||
actor = child;
|
||||
dist -= FRACUNIT;
|
||||
dist -= 1;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -341,13 +340,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_CHolyTail)
|
|||
}
|
||||
else
|
||||
{
|
||||
if (P_TryMove (self,
|
||||
parent->X() - 14*finecosine[parent->angle>>ANGLETOFINESHIFT],
|
||||
parent->Y() - 14*finesine[parent->angle>>ANGLETOFINESHIFT], true))
|
||||
if (P_TryMove(self, parent->Vec2Angle(14., parent->Angles.Yaw, true), true))
|
||||
{
|
||||
self->SetZ(parent->Z()-5*FRACUNIT);
|
||||
self->SetZ(parent->Z() - 5.);
|
||||
}
|
||||
CHolyTailFollow (self, 10*FRACUNIT);
|
||||
CHolyTailFollow(self, 10);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -377,34 +374,32 @@ static void CHolyFindTarget (AActor *actor)
|
|||
// Similar to P_SeekerMissile, but seeks to a random Z on the target
|
||||
//============================================================================
|
||||
|
||||
static void CHolySeekerMissile (AActor *actor, angle_t thresh, angle_t turnMax)
|
||||
static void CHolySeekerMissile (AActor *actor, DAngle thresh, DAngle turnMax)
|
||||
{
|
||||
int dir;
|
||||
int dist;
|
||||
angle_t delta;
|
||||
angle_t angle;
|
||||
DAngle delta;
|
||||
AActor *target;
|
||||
fixed_t newZ;
|
||||
fixed_t deltaZ;
|
||||
double newZ;
|
||||
double deltaZ;
|
||||
|
||||
target = actor->tracer;
|
||||
if (target == NULL)
|
||||
{
|
||||
return;
|
||||
}
|
||||
if(!(target->flags&MF_SHOOTABLE)
|
||||
|| (!(target->flags3&MF3_ISMONSTER) && !target->player))
|
||||
if (!(target->flags&MF_SHOOTABLE)
|
||||
|| (!(target->flags3&MF3_ISMONSTER) && !target->player))
|
||||
{ // Target died/target isn't a player or creature
|
||||
actor->tracer = NULL;
|
||||
actor->flags &= ~(MF_NOCLIP|MF_SKULLFLY);
|
||||
actor->flags &= ~(MF_NOCLIP | MF_SKULLFLY);
|
||||
actor->flags |= MF_MISSILE;
|
||||
CHolyFindTarget (actor);
|
||||
CHolyFindTarget(actor);
|
||||
return;
|
||||
}
|
||||
dir = P_FaceMobj (actor, target, &delta);
|
||||
if (delta > thresh)
|
||||
{
|
||||
delta >>= 1;
|
||||
delta /= 2;
|
||||
if (delta > turnMax)
|
||||
{
|
||||
delta = turnMax;
|
||||
|
@ -412,72 +407,36 @@ static void CHolySeekerMissile (AActor *actor, angle_t thresh, angle_t turnMax)
|
|||
}
|
||||
if (dir)
|
||||
{ // Turn clockwise
|
||||
actor->angle += delta;
|
||||
actor->Angles.Yaw += delta;
|
||||
}
|
||||
else
|
||||
{ // Turn counter clockwise
|
||||
actor->angle -= delta;
|
||||
actor->Angles.Yaw -= delta;
|
||||
}
|
||||
angle = actor->angle>>ANGLETOFINESHIFT;
|
||||
actor->vel.x = FixedMul (actor->Speed, finecosine[angle]);
|
||||
actor->vel.y = FixedMul (actor->Speed, finesine[angle]);
|
||||
actor->VelFromAngle();
|
||||
|
||||
if (!(level.time&15)
|
||||
|| actor->Z() > target->Top()
|
||||
|| actor->Top() < target->Z())
|
||||
{
|
||||
newZ = target->Z()+((pr_holyseeker()*target->height)>>8);
|
||||
newZ = target->Z() + ((pr_holyseeker()*target->Height) / 256.);
|
||||
deltaZ = newZ - actor->Z();
|
||||
if (abs(deltaZ) > 15*FRACUNIT)
|
||||
if (fabs(deltaZ) > 15)
|
||||
{
|
||||
if (deltaZ > 0)
|
||||
{
|
||||
deltaZ = 15*FRACUNIT;
|
||||
deltaZ = 15;
|
||||
}
|
||||
else
|
||||
{
|
||||
deltaZ = -15*FRACUNIT;
|
||||
deltaZ = -15;
|
||||
}
|
||||
}
|
||||
dist = actor->AproxDistance (target);
|
||||
dist = dist / actor->Speed;
|
||||
if (dist < 1)
|
||||
{
|
||||
dist = 1;
|
||||
}
|
||||
actor->vel.z = deltaZ / dist;
|
||||
actor->Vel.Z = deltaZ / actor->DistanceBySpeed(target, actor->Speed);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
//
|
||||
// A_CHolyWeave
|
||||
//
|
||||
//============================================================================
|
||||
|
||||
void CHolyWeave (AActor *actor, FRandom &pr_random)
|
||||
{
|
||||
fixed_t newX, newY, newZ;
|
||||
int weaveXY, weaveZ;
|
||||
int angle;
|
||||
|
||||
weaveXY = actor->special2 >> 16;
|
||||
weaveZ = actor->special2 & FINEMASK;
|
||||
angle = (actor->angle + ANG90) >> ANGLETOFINESHIFT;
|
||||
newX = actor->X() - FixedMul(finecosine[angle], finesine[weaveXY] * 32);
|
||||
newY = actor->Y() - FixedMul(finesine[angle], finesine[weaveXY] * 32);
|
||||
weaveXY = (weaveXY + pr_random(5 << BOBTOFINESHIFT)) & FINEMASK;
|
||||
newX += FixedMul(finecosine[angle], finesine[weaveXY] * 32);
|
||||
newY += FixedMul(finesine[angle], finesine[weaveXY] * 32);
|
||||
P_TryMove(actor, newX, newY, true);
|
||||
newZ = actor->Z();
|
||||
newZ -= finesine[weaveZ] * 16;
|
||||
weaveZ = (weaveZ + pr_random(5 << BOBTOFINESHIFT)) & FINEMASK;
|
||||
newZ += finesine[weaveZ] * 16;
|
||||
actor->SetZ(newZ);
|
||||
actor->special2 = weaveZ + (weaveXY << 16);
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
//
|
||||
// A_CHolySeek
|
||||
|
@ -491,23 +450,25 @@ DEFINE_ACTION_FUNCTION(AActor, A_CHolySeek)
|
|||
self->health--;
|
||||
if (self->health <= 0)
|
||||
{
|
||||
self->vel.x >>= 2;
|
||||
self->vel.y >>= 2;
|
||||
self->vel.z = 0;
|
||||
self->Vel.X /= 4;
|
||||
self->Vel.Y /= 4;
|
||||
self->Vel.Z = 0;
|
||||
self->SetState (self->FindState(NAME_Death));
|
||||
self->tics -= pr_holyseek()&3;
|
||||
return 0;
|
||||
}
|
||||
if (self->tracer)
|
||||
{
|
||||
CHolySeekerMissile (self, self->args[0]*ANGLE_1,
|
||||
self->args[0]*ANGLE_1*2);
|
||||
CHolySeekerMissile (self, (double)self->args[0], self->args[0]*2.);
|
||||
if (!((level.time+7)&15))
|
||||
{
|
||||
self->args[0] = 5+(pr_holyseek()/20);
|
||||
}
|
||||
}
|
||||
CHolyWeave (self, pr_holyweave);
|
||||
|
||||
int xyspeed = (pr_holyweave() % 5);
|
||||
int zspeed = (pr_holyweave() % 5);
|
||||
A_Weave(self, xyspeed, zspeed, 4., 2.);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -546,7 +507,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ClericAttack)
|
|||
|
||||
if (!self->target) return 0;
|
||||
|
||||
AActor * missile = P_SpawnMissileZ (self, self->Z() + 40*FRACUNIT, self->target, PClass::FindActor ("HolyMissile"));
|
||||
AActor * missile = P_SpawnMissileZ (self, self->Z() + 40., self->target, PClass::FindActor ("HolyMissile"));
|
||||
if (missile != NULL) missile->tracer = NULL; // No initial target
|
||||
S_Sound (self, CHAN_WEAPON, "HolySymbolFire", 1, ATTN_NORM);
|
||||
return 0;
|
||||
|
|
|
@ -17,9 +17,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_CMaceAttack)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
int slope;
|
||||
DAngle slope;
|
||||
int i;
|
||||
player_t *player;
|
||||
FTranslatedLineTarget t;
|
||||
|
@ -36,7 +36,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CMaceAttack)
|
|||
{
|
||||
for (int j = 1; j >= -1; j -= 2)
|
||||
{
|
||||
angle = player->mo->angle + j*i*(ANG45 / 16);
|
||||
angle = player->mo->Angles.Yaw + j*i*(45. / 16);
|
||||
slope = P_AimLineAttack(player->mo, angle, 2 * MELEERANGE, &t);
|
||||
if (t.linetarget)
|
||||
{
|
||||
|
@ -44,7 +44,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CMaceAttack)
|
|||
if (t.linetarget != NULL)
|
||||
{
|
||||
AdjustPlayerAngle(player->mo, &t);
|
||||
goto macedone;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -52,9 +52,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_CMaceAttack)
|
|||
// didn't find any creatures, so try to strike any walls
|
||||
player->mo->weaponspecial = 0;
|
||||
|
||||
angle = player->mo->angle;
|
||||
angle = player->mo->Angles.Yaw;
|
||||
slope = P_AimLineAttack (player->mo, angle, MELEERANGE);
|
||||
P_LineAttack (player->mo, angle, MELEERANGE, slope, damage, NAME_Melee, hammertime);
|
||||
macedone:
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -51,8 +51,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffCheck)
|
|||
APlayerPawn *pmo;
|
||||
int damage;
|
||||
int newLife, max;
|
||||
angle_t angle;
|
||||
int slope;
|
||||
DAngle angle;
|
||||
DAngle slope;
|
||||
int i;
|
||||
player_t *player;
|
||||
FTranslatedLineTarget t;
|
||||
|
@ -72,14 +72,14 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffCheck)
|
|||
{
|
||||
for (int j = 1; j >= -1; j -= 2)
|
||||
{
|
||||
angle = pmo->angle + j*i*(ANG45 / 16);
|
||||
slope = P_AimLineAttack(pmo, angle, fixed_t(1.5*MELEERANGE), &t, 0, ALF_CHECK3D);
|
||||
angle = pmo->Angles.Yaw + j*i*(45. / 16);
|
||||
slope = P_AimLineAttack(pmo, angle, 1.5 * MELEERANGE, &t, 0., ALF_CHECK3D);
|
||||
if (t.linetarget)
|
||||
{
|
||||
P_LineAttack(pmo, angle, fixed_t(1.5*MELEERANGE), slope, damage, NAME_Melee, puff, false, &t);
|
||||
P_LineAttack(pmo, angle, 1.5 * MELEERANGE, slope, damage, NAME_Melee, puff, false, &t);
|
||||
if (t.linetarget != NULL)
|
||||
{
|
||||
pmo->angle = t.angleFromSource;
|
||||
pmo->Angles.Yaw = t.angleFromSource;
|
||||
if (((t.linetarget->player && (!t.linetarget->IsTeammate(pmo) || level.teamdamage != 0)) || t.linetarget->flags3&MF3_ISMONSTER)
|
||||
&& (!(t.linetarget->flags2&(MF2_DORMANT | MF2_INVULNERABLE))))
|
||||
{
|
||||
|
@ -131,12 +131,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffAttack)
|
|||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
mo = P_SpawnPlayerMissile (self, RUNTIME_CLASS(ACStaffMissile), self->angle-(ANG45/15));
|
||||
mo = P_SpawnPlayerMissile (self, RUNTIME_CLASS(ACStaffMissile), self->Angles.Yaw - 3.0);
|
||||
if (mo)
|
||||
{
|
||||
mo->WeaveIndexXY = 32;
|
||||
}
|
||||
mo = P_SpawnPlayerMissile (self, RUNTIME_CLASS(ACStaffMissile), self->angle+(ANG45/15));
|
||||
mo = P_SpawnPlayerMissile (self, RUNTIME_CLASS(ACStaffMissile), self->Angles.Yaw + 3.0);
|
||||
if (mo)
|
||||
{
|
||||
mo->WeaveIndexXY = 0;
|
||||
|
@ -155,7 +155,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CStaffMissileSlither)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
A_Weave(self, 3, 0, FRACUNIT, 0);
|
||||
A_Weave(self, 3, 0, 1., 0.);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -22,16 +22,15 @@ DECLARE_ACTION(A_DragonFlight)
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
static void DragonSeek (AActor *actor, angle_t thresh, angle_t turnMax)
|
||||
static void DragonSeek (AActor *actor, DAngle thresh, DAngle turnMax)
|
||||
{
|
||||
int dir;
|
||||
int dist;
|
||||
angle_t delta;
|
||||
angle_t angle;
|
||||
double dist;
|
||||
DAngle delta;
|
||||
AActor *target;
|
||||
int i;
|
||||
angle_t bestAngle;
|
||||
angle_t angleToSpot, angleToTarget;
|
||||
DAngle bestAngle;
|
||||
DAngle angleToSpot, angleToTarget;
|
||||
AActor *mo;
|
||||
|
||||
target = actor->tracer;
|
||||
|
@ -42,7 +41,7 @@ static void DragonSeek (AActor *actor, angle_t thresh, angle_t turnMax)
|
|||
dir = P_FaceMobj (actor, target, &delta);
|
||||
if (delta > thresh)
|
||||
{
|
||||
delta >>= 1;
|
||||
delta /= 2;
|
||||
if (delta > turnMax)
|
||||
{
|
||||
delta = turnMax;
|
||||
|
@ -50,30 +49,25 @@ static void DragonSeek (AActor *actor, angle_t thresh, angle_t turnMax)
|
|||
}
|
||||
if (dir)
|
||||
{ // Turn clockwise
|
||||
actor->angle += delta;
|
||||
actor->Angles.Yaw += delta;
|
||||
}
|
||||
else
|
||||
{ // Turn counter clockwise
|
||||
actor->angle -= delta;
|
||||
actor->Angles.Yaw -= delta;
|
||||
}
|
||||
angle = actor->angle>>ANGLETOFINESHIFT;
|
||||
actor->vel.x = FixedMul (actor->Speed, finecosine[angle]);
|
||||
actor->vel.y = FixedMul (actor->Speed, finesine[angle]);
|
||||
dist = actor->AproxDistance (target) / actor->Speed;
|
||||
actor->VelFromAngle();
|
||||
|
||||
dist = actor->DistanceBySpeed(target, actor->Speed);
|
||||
if (actor->Top() < target->Z() ||
|
||||
target->Top() < actor->Z())
|
||||
{
|
||||
if (dist < 1)
|
||||
{
|
||||
dist = 1;
|
||||
}
|
||||
actor->vel.z = (target->Z() - actor->Z())/dist;
|
||||
actor->Vel.Z = (target->Z() - actor->Z()) / dist;
|
||||
}
|
||||
if (target->flags&MF_SHOOTABLE && pr_dragonseek() < 64)
|
||||
{ // attack the destination mobj if it's attackable
|
||||
AActor *oldTarget;
|
||||
|
||||
if (absangle(actor->angle - actor->AngleTo(target)) < ANGLE_45/2)
|
||||
|
||||
if (absangle(actor->Angles.Yaw, actor->AngleTo(target)) < 22.5)
|
||||
{
|
||||
oldTarget = actor->target;
|
||||
actor->target = target;
|
||||
|
@ -97,7 +91,7 @@ static void DragonSeek (AActor *actor, angle_t thresh, angle_t turnMax)
|
|||
if (actor->target && pr_dragonseek() < 200)
|
||||
{
|
||||
AActor *bestActor = NULL;
|
||||
bestAngle = ANGLE_MAX;
|
||||
bestAngle = 360.;
|
||||
angleToTarget = actor->AngleTo(actor->target);
|
||||
for (i = 0; i < 5; i++)
|
||||
{
|
||||
|
@ -112,9 +106,10 @@ static void DragonSeek (AActor *actor, angle_t thresh, angle_t turnMax)
|
|||
continue;
|
||||
}
|
||||
angleToSpot = actor->AngleTo(mo);
|
||||
if (absangle(angleToSpot-angleToTarget) < bestAngle)
|
||||
DAngle diff = absangle(angleToSpot, angleToTarget);
|
||||
if (diff < bestAngle)
|
||||
{
|
||||
bestAngle = absangle(angleToSpot-angleToTarget);
|
||||
bestAngle = diff;
|
||||
bestActor = mo;
|
||||
}
|
||||
}
|
||||
|
@ -182,9 +177,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_DragonFlight)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
|
||||
DragonSeek (self, 4*ANGLE_1, 8*ANGLE_1);
|
||||
DragonSeek (self, 4., 8.);
|
||||
if (self->target)
|
||||
{
|
||||
if(!(self->target->flags&MF_SHOOTABLE))
|
||||
|
@ -192,15 +187,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_DragonFlight)
|
|||
self->target = NULL;
|
||||
return 0;
|
||||
}
|
||||
angle = self->AngleTo(self->target);
|
||||
if (absangle(self->angle-angle) < ANGLE_45/2 && self->CheckMeleeRange())
|
||||
angle = absangle(self->Angles.Yaw, self->AngleTo(self->target));
|
||||
if (angle <22.5 && self->CheckMeleeRange())
|
||||
{
|
||||
int damage = pr_dragonflight.HitDice (8);
|
||||
int newdam = P_DamageMobj (self->target, self, self, damage, NAME_Melee);
|
||||
P_TraceBleed (newdam > 0 ? newdam : damage, self->target, self);
|
||||
S_Sound (self, CHAN_WEAPON, self->AttackSound, 1, ATTN_NORM);
|
||||
}
|
||||
else if (absangle(self->angle-angle) <= ANGLE_1*20)
|
||||
else if (angle <= 20)
|
||||
{
|
||||
self->SetState (self->MissileState);
|
||||
S_Sound (self, CHAN_WEAPON, self->AttackSound, 1, ATTN_NORM);
|
||||
|
@ -266,9 +261,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_DragonFX2)
|
|||
delay = 16+(pr_dragonfx2()>>3);
|
||||
for (i = 1+(pr_dragonfx2()&3); i; i--)
|
||||
{
|
||||
fixed_t xo = ((pr_dragonfx2() - 128) << 14);
|
||||
fixed_t yo = ((pr_dragonfx2() - 128) << 14);
|
||||
fixed_t zo = ((pr_dragonfx2() - 128) << 12);
|
||||
double xo = (pr_dragonfx2() - 128) / 4.;
|
||||
double yo = (pr_dragonfx2() - 128) / 4.;
|
||||
double zo = (pr_dragonfx2() - 128) / 16.;
|
||||
|
||||
mo = Spawn ("DragonExplosion", self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
#include "thingdef/thingdef.h"
|
||||
*/
|
||||
|
||||
#define AXERANGE ((fixed_t)(2.25*MELEERANGE))
|
||||
#define AXERANGE (2.25 * MELEERANGE)
|
||||
|
||||
static FRandom pr_axeatk ("FAxeAtk");
|
||||
|
||||
|
@ -199,10 +199,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeAttack)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
fixed_t power;
|
||||
DAngle angle;
|
||||
int power;
|
||||
int damage;
|
||||
int slope;
|
||||
DAngle slope;
|
||||
int i;
|
||||
int useMana;
|
||||
player_t *player;
|
||||
|
@ -223,7 +223,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeAttack)
|
|||
if (player->ReadyWeapon->Ammo1->Amount > 0)
|
||||
{
|
||||
damage <<= 1;
|
||||
power = 6*FRACUNIT;
|
||||
power = 6;
|
||||
pufftype = PClass::FindActor ("AxePuffGlow");
|
||||
useMana = 1;
|
||||
}
|
||||
|
@ -236,7 +236,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeAttack)
|
|||
{
|
||||
for (int j = 1; j >= -1; j -= 2)
|
||||
{
|
||||
angle = pmo->angle + j*i*(ANG45 / 16);
|
||||
angle = pmo->Angles.Yaw + j*i*(45. / 16);
|
||||
slope = P_AimLineAttack(pmo, angle, AXERANGE, &t);
|
||||
if (t.linetarget)
|
||||
{
|
||||
|
@ -245,7 +245,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeAttack)
|
|||
{
|
||||
if (t.linetarget->flags3&MF3_ISMONSTER || t.linetarget->player)
|
||||
{
|
||||
P_ThrustMobj(t.linetarget, t.angleFromSource, power);
|
||||
t.linetarget->Thrust(t.angleFromSource, power);
|
||||
}
|
||||
AdjustPlayerAngle(pmo, &t);
|
||||
useMana++;
|
||||
|
@ -257,7 +257,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FAxeAttack)
|
|||
// didn't find any creatures, so try to strike any walls
|
||||
pmo->weaponspecial = 0;
|
||||
|
||||
angle = pmo->angle;
|
||||
angle = pmo->Angles.Yaw;
|
||||
slope = P_AimLineAttack (pmo, angle, MELEERANGE);
|
||||
P_LineAttack (pmo, angle, MELEERANGE, slope, damage, NAME_Melee, pufftype, true);
|
||||
|
||||
|
|
|
@ -13,7 +13,7 @@
|
|||
#include "thingdef/thingdef.h"
|
||||
*/
|
||||
|
||||
const fixed_t HAMMER_RANGE = MELEERANGE+MELEERANGE/2;
|
||||
const double HAMMER_RANGE = 1.5 * MELEERANGE;
|
||||
|
||||
static FRandom pr_hammeratk ("FHammerAtk");
|
||||
|
||||
|
@ -27,10 +27,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_FHammerAttack)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
fixed_t power;
|
||||
int slope;
|
||||
DAngle slope;
|
||||
int i;
|
||||
player_t *player;
|
||||
FTranslatedLineTarget t;
|
||||
|
@ -43,46 +42,32 @@ DEFINE_ACTION_FUNCTION(AActor, A_FHammerAttack)
|
|||
AActor *pmo=player->mo;
|
||||
|
||||
damage = 60+(pr_hammeratk()&63);
|
||||
power = 10*FRACUNIT;
|
||||
hammertime = PClass::FindActor("HammerPuff");
|
||||
for (i = 0; i < 16; i++)
|
||||
{
|
||||
angle = pmo->angle + i*(ANG45/32);
|
||||
slope = P_AimLineAttack (pmo, angle, HAMMER_RANGE, &t, 0, ALF_CHECK3D);
|
||||
if (t.linetarget != NULL)
|
||||
for (int j = 1; j >= -1; j -= 2)
|
||||
{
|
||||
P_LineAttack(pmo, angle, HAMMER_RANGE, slope, damage, NAME_Melee, hammertime, true, &t);
|
||||
angle = pmo->Angles.Yaw + j*i*(45. / 32);
|
||||
slope = P_AimLineAttack(pmo, angle, HAMMER_RANGE, &t, 0., ALF_CHECK3D);
|
||||
if (t.linetarget != NULL)
|
||||
{
|
||||
AdjustPlayerAngle(pmo, &t);
|
||||
if (t.linetarget->flags3 & MF3_ISMONSTER || t.linetarget->player)
|
||||
P_LineAttack(pmo, angle, HAMMER_RANGE, slope, damage, NAME_Melee, hammertime, true, &t);
|
||||
if (t.linetarget != NULL)
|
||||
{
|
||||
P_ThrustMobj(t.linetarget, t.angleFromSource, power);
|
||||
AdjustPlayerAngle(pmo, &t);
|
||||
if (t.linetarget->flags3 & MF3_ISMONSTER || t.linetarget->player)
|
||||
{
|
||||
t.linetarget->Thrust(t.angleFromSource, 10);
|
||||
}
|
||||
pmo->weaponspecial = false; // Don't throw a hammer
|
||||
goto hammerdone;
|
||||
}
|
||||
pmo->weaponspecial = false; // Don't throw a hammer
|
||||
goto hammerdone;
|
||||
}
|
||||
}
|
||||
angle = pmo->angle-i*(ANG45/32);
|
||||
slope = P_AimLineAttack(pmo, angle, HAMMER_RANGE, &t, 0, ALF_CHECK3D);
|
||||
if (t.linetarget != NULL)
|
||||
{
|
||||
P_LineAttack(pmo, angle, HAMMER_RANGE, slope, damage, NAME_Melee, hammertime, true, &t);
|
||||
if (t.linetarget != NULL)
|
||||
{
|
||||
AdjustPlayerAngle(pmo, &t);
|
||||
if (t.linetarget->flags3 & MF3_ISMONSTER || t.linetarget->player)
|
||||
{
|
||||
P_ThrustMobj(t.linetarget, t.angleFromSource, power);
|
||||
}
|
||||
pmo->weaponspecial = false; // Don't throw a hammer
|
||||
goto hammerdone;
|
||||
}
|
||||
}
|
||||
}
|
||||
// didn't find any targets in meleerange, so set to throw out a hammer
|
||||
angle = pmo->angle;
|
||||
slope = P_AimLineAttack (pmo, angle, HAMMER_RANGE, NULL, 0, ALF_CHECK3D);
|
||||
angle = pmo->Angles.Yaw;
|
||||
slope = P_AimLineAttack (pmo, angle, HAMMER_RANGE, NULL, 0., ALF_CHECK3D);
|
||||
if (P_LineAttack (pmo, angle, HAMMER_RANGE, slope, damage, NAME_Melee, hammertime, true) != NULL)
|
||||
{
|
||||
pmo->weaponspecial = false;
|
||||
|
|
|
@ -23,29 +23,25 @@ static FRandom pr_fpatk ("FPunchAttack");
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
#define MAX_ANGLE_ADJUST (5*ANGLE_1)
|
||||
#define MAX_ANGLE_ADJUST (5.)
|
||||
|
||||
void AdjustPlayerAngle (AActor *pmo, FTranslatedLineTarget *t)
|
||||
{
|
||||
angle_t angle;
|
||||
int difference;
|
||||
|
||||
angle = pmo->AngleTo(t->linetarget);
|
||||
difference = (int)angle - (int)pmo->angle;
|
||||
if (abs(difference) > MAX_ANGLE_ADJUST)
|
||||
DAngle difference = deltaangle(pmo->Angles.Yaw, pmo->AngleTo(t->linetarget));
|
||||
if (fabs(difference) > MAX_ANGLE_ADJUST)
|
||||
{
|
||||
if (difference > 0)
|
||||
{
|
||||
pmo->angle += MAX_ANGLE_ADJUST;
|
||||
pmo->Angles.Yaw += MAX_ANGLE_ADJUST;
|
||||
}
|
||||
else
|
||||
{
|
||||
pmo->angle -= MAX_ANGLE_ADJUST;
|
||||
pmo->Angles.Yaw -= MAX_ANGLE_ADJUST;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
pmo->angle = angle;
|
||||
pmo->Angles.Yaw = t->angleFromSource;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -57,11 +53,11 @@ void AdjustPlayerAngle (AActor *pmo, FTranslatedLineTarget *t)
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
static bool TryPunch(APlayerPawn *pmo, angle_t angle, int damage, fixed_t power)
|
||||
static bool TryPunch(APlayerPawn *pmo, DAngle angle, int damage, int power)
|
||||
{
|
||||
PClassActor *pufftype;
|
||||
FTranslatedLineTarget t;
|
||||
int slope;
|
||||
DAngle slope;
|
||||
|
||||
slope = P_AimLineAttack (pmo, angle, 2*MELEERANGE, &t);
|
||||
if (t.linetarget != NULL)
|
||||
|
@ -82,7 +78,7 @@ static bool TryPunch(APlayerPawn *pmo, angle_t angle, int damage, fixed_t power)
|
|||
if (t.linetarget->player != NULL ||
|
||||
(t.linetarget->Mass != INT_MAX && (t.linetarget->flags3 & MF3_ISMONSTER)))
|
||||
{
|
||||
P_ThrustMobj (t.linetarget, t.angleFromSource, power);
|
||||
t.linetarget->Thrust(t.angleFromSource, power);
|
||||
}
|
||||
AdjustPlayerAngle (pmo, &t);
|
||||
return true;
|
||||
|
@ -102,7 +98,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_FPunchAttack)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int damage;
|
||||
fixed_t power;
|
||||
int i;
|
||||
player_t *player;
|
||||
|
||||
|
@ -113,11 +108,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_FPunchAttack)
|
|||
APlayerPawn *pmo = player->mo;
|
||||
|
||||
damage = 40+(pr_fpatk()&15);
|
||||
power = 2*FRACUNIT;
|
||||
for (i = 0; i < 16; i++)
|
||||
{
|
||||
if (TryPunch(pmo, pmo->angle + i*(ANG45/16), damage, power) ||
|
||||
TryPunch(pmo, pmo->angle - i*(ANG45/16), damage, power))
|
||||
if (TryPunch(pmo, pmo->Angles.Yaw + i*(45./16), damage, 2) ||
|
||||
TryPunch(pmo, pmo->Angles.Yaw - i*(45./16), damage, 2))
|
||||
{ // hit something
|
||||
if (pmo->weaponspecial >= 3)
|
||||
{
|
||||
|
@ -131,7 +125,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FPunchAttack)
|
|||
// didn't find any creatures, so try to strike any walls
|
||||
pmo->weaponspecial = 0;
|
||||
|
||||
int slope = P_AimLineAttack (pmo, pmo->angle, MELEERANGE);
|
||||
P_LineAttack (pmo, pmo->angle, MELEERANGE, slope, damage, NAME_Melee, PClass::FindActor("PunchPuff"), true);
|
||||
DAngle slope = P_AimLineAttack (pmo, pmo->Angles.Yaw, MELEERANGE);
|
||||
P_LineAttack (pmo, pmo->Angles.Yaw, MELEERANGE, slope, damage, NAME_Melee, PClass::FindActor("PunchPuff"), true);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -31,7 +31,7 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DropWeaponPieces)
|
|||
PARAM_CLASS(p2, AActor);
|
||||
PARAM_CLASS(p3, AActor);
|
||||
|
||||
for (int i = 0, j = 0, fineang = 0; i < 3; ++i)
|
||||
for (int i = 0, j = 0; i < 3; ++i)
|
||||
{
|
||||
PClassActor *cls = j == 0 ? p1 : j == 1 ? p2 : p3;
|
||||
if (cls)
|
||||
|
@ -39,11 +39,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AActor, A_DropWeaponPieces)
|
|||
AActor *piece = Spawn (cls, self->Pos(), ALLOW_REPLACE);
|
||||
if (piece != NULL)
|
||||
{
|
||||
piece->vel.x = self->vel.x + finecosine[fineang];
|
||||
piece->vel.y = self->vel.y + finesine[fineang];
|
||||
piece->vel.z = self->vel.z;
|
||||
piece->Vel = self->Vel + DAngle(i*120.).ToVector(1);
|
||||
piece->flags |= MF_DROPPED;
|
||||
fineang += FINEANGLES/3;
|
||||
j = (j == 0) ? (pr_quietusdrop() & 1) + 1 : 3-j;
|
||||
}
|
||||
}
|
||||
|
@ -95,11 +92,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_FSwordAttack)
|
|||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
P_SpawnPlayerMissile (self, 0, 0, -10*FRACUNIT, RUNTIME_CLASS(AFSwordMissile), self->angle+ANGLE_45/4);
|
||||
P_SpawnPlayerMissile (self, 0, 0, -5*FRACUNIT, RUNTIME_CLASS(AFSwordMissile), self->angle+ANGLE_45/8);
|
||||
P_SpawnPlayerMissile (self, 0, 0, 0, RUNTIME_CLASS(AFSwordMissile), self->angle);
|
||||
P_SpawnPlayerMissile (self, 0, 0, 5*FRACUNIT, RUNTIME_CLASS(AFSwordMissile), self->angle-ANGLE_45/8);
|
||||
P_SpawnPlayerMissile (self, 0, 0, 10*FRACUNIT, RUNTIME_CLASS(AFSwordMissile), self->angle-ANGLE_45/4);
|
||||
P_SpawnPlayerMissile (self, 0, 0, -10, RUNTIME_CLASS(AFSwordMissile), self->Angles.Yaw + (45./4));
|
||||
P_SpawnPlayerMissile (self, 0, 0, -5, RUNTIME_CLASS(AFSwordMissile), self->Angles.Yaw + (45./8));
|
||||
P_SpawnPlayerMissile (self, 0, 0, 0, RUNTIME_CLASS(AFSwordMissile), self->Angles.Yaw);
|
||||
P_SpawnPlayerMissile (self, 0, 0, 5, RUNTIME_CLASS(AFSwordMissile), self->Angles.Yaw - (45./8));
|
||||
P_SpawnPlayerMissile (self, 0, 0, 10, RUNTIME_CLASS(AFSwordMissile), self->Angles.Yaw - (45./4));
|
||||
S_Sound (self, CHAN_WEAPON, "FighterSwordFire", 1, ATTN_NORM);
|
||||
return 0;
|
||||
}
|
||||
|
@ -118,9 +115,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_FSwordFlames)
|
|||
|
||||
for (i = 1+(pr_fswordflame()&3); i; i--)
|
||||
{
|
||||
fixed_t xo = ((pr_fswordflame() - 128) << 12);
|
||||
fixed_t yo = ((pr_fswordflame() - 128) << 12);
|
||||
fixed_t zo = ((pr_fswordflame() - 128) << 11);
|
||||
double xo = (pr_fswordflame() - 128) / 16.;
|
||||
double yo = (pr_fswordflame() - 128) / 16.;
|
||||
double zo = (pr_fswordflame() - 128) / 8.;
|
||||
Spawn ("FSwordFlame", self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
}
|
||||
return 0;
|
||||
|
@ -138,13 +135,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_FighterAttack)
|
|||
|
||||
if (!self->target) return 0;
|
||||
|
||||
angle_t angle = self->angle;
|
||||
|
||||
P_SpawnMissileAngle (self, RUNTIME_CLASS(AFSwordMissile), angle+ANG45/4, 0);
|
||||
P_SpawnMissileAngle (self, RUNTIME_CLASS(AFSwordMissile), angle+ANG45/8, 0);
|
||||
P_SpawnMissileAngle (self, RUNTIME_CLASS(AFSwordMissile), angle, 0);
|
||||
P_SpawnMissileAngle (self, RUNTIME_CLASS(AFSwordMissile), angle-ANG45/8, 0);
|
||||
P_SpawnMissileAngle (self, RUNTIME_CLASS(AFSwordMissile), angle-ANG45/4, 0);
|
||||
P_SpawnMissileAngle(self, RUNTIME_CLASS(AFSwordMissile), self->Angles.Yaw + (45. / 4), 0);
|
||||
P_SpawnMissileAngle(self, RUNTIME_CLASS(AFSwordMissile), self->Angles.Yaw + (45. / 8), 0);
|
||||
P_SpawnMissileAngle(self, RUNTIME_CLASS(AFSwordMissile), self->Angles.Yaw, 0);
|
||||
P_SpawnMissileAngle(self, RUNTIME_CLASS(AFSwordMissile), self->Angles.Yaw - (45. / 8), 0);
|
||||
P_SpawnMissileAngle(self, RUNTIME_CLASS(AFSwordMissile), self->Angles.Yaw - (45. / 4), 0);
|
||||
S_Sound (self, CHAN_WEAPON, "FighterSwordFire", 1, ATTN_NORM);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -9,7 +9,7 @@
|
|||
#include "thingdef/thingdef.h"
|
||||
*/
|
||||
|
||||
#define FIREDEMON_ATTACK_RANGE 64*8*FRACUNIT
|
||||
#define FIREDEMON_ATTACK_RANGE (64*8.)
|
||||
|
||||
static FRandom pr_firedemonrock ("FireDemonRock");
|
||||
static FRandom pr_smbounce ("SMBounce");
|
||||
|
@ -54,16 +54,16 @@ void A_FiredSpawnRock (AActor *actor)
|
|||
break;
|
||||
}
|
||||
|
||||
fixed_t xo = ((pr_firedemonrock() - 128) << 12);
|
||||
fixed_t yo = ((pr_firedemonrock() - 128) << 12);
|
||||
fixed_t zo = (pr_firedemonrock() << 11);
|
||||
double xo = (pr_firedemonrock() - 128) / 16.;
|
||||
double yo = (pr_firedemonrock() - 128) / 16.;
|
||||
double zo = pr_firedemonrock() / 32.;
|
||||
mo = Spawn (rtype, actor->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->target = actor;
|
||||
mo->vel.x = (pr_firedemonrock() - 128) <<10;
|
||||
mo->vel.y = (pr_firedemonrock() - 128) <<10;
|
||||
mo->vel.z = (pr_firedemonrock() << 10);
|
||||
mo->Vel.X = (pr_firedemonrock() - 128) / 64.;
|
||||
mo->Vel.Y = (pr_firedemonrock() - 128) / 64.;
|
||||
mo->Vel.Z = (pr_firedemonrock() / 64.);
|
||||
mo->special1 = 2; // Number bounces
|
||||
}
|
||||
|
||||
|
@ -101,10 +101,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_SmBounce)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
// give some more velocity (x,y,&z)
|
||||
self->SetZ(self->floorz + FRACUNIT);
|
||||
self->vel.z = (2*FRACUNIT) + (pr_smbounce() << 10);
|
||||
self->vel.x = pr_smbounce()%3<<FRACBITS;
|
||||
self->vel.y = pr_smbounce()%3<<FRACBITS;
|
||||
self->SetZ(self->floorz + 1);
|
||||
self->Vel.Z = 2. + pr_smbounce() / 64.;
|
||||
self->Vel.X = pr_smbounce() % 3;
|
||||
self->Vel.Y = pr_smbounce() % 3;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -137,20 +137,20 @@ DEFINE_ACTION_FUNCTION(AActor, A_FiredChase)
|
|||
|
||||
int weaveindex = self->special1;
|
||||
AActor *target = self->target;
|
||||
angle_t ang;
|
||||
fixed_t dist;
|
||||
DAngle ang;
|
||||
double dist;
|
||||
|
||||
if (self->reactiontime) self->reactiontime--;
|
||||
if (self->threshold) self->threshold--;
|
||||
|
||||
// Float up and down
|
||||
self->AddZ(finesine[weaveindex << BOBTOFINESHIFT] * 8);
|
||||
self->AddZ(BobSin(weaveindex));
|
||||
self->special1 = (weaveindex + 2) & 63;
|
||||
|
||||
// Ensure it stays above certain height
|
||||
if (self->Z() < self->floorz + (64*FRACUNIT))
|
||||
if (self->Z() < self->floorz + 64)
|
||||
{
|
||||
self->AddZ(2*FRACUNIT);
|
||||
self->AddZ(2);
|
||||
}
|
||||
|
||||
if(!self->target || !(self->target->flags&MF_SHOOTABLE))
|
||||
|
@ -167,20 +167,18 @@ DEFINE_ACTION_FUNCTION(AActor, A_FiredChase)
|
|||
else
|
||||
{
|
||||
self->special2 = 0;
|
||||
self->vel.x = self->vel.y = 0;
|
||||
dist = self->AproxDistance (target);
|
||||
self->Vel.X = self->Vel.Y = 0;
|
||||
dist = self->Distance2D(target);
|
||||
if (dist < FIREDEMON_ATTACK_RANGE)
|
||||
{
|
||||
if (pr_firedemonchase() < 30)
|
||||
{
|
||||
ang = self->AngleTo(target);
|
||||
if (pr_firedemonchase() < 128)
|
||||
ang += ANGLE_90;
|
||||
ang += 90;
|
||||
else
|
||||
ang -= ANGLE_90;
|
||||
ang >>= ANGLETOFINESHIFT;
|
||||
self->vel.x = finecosine[ang] << 3; //FixedMul (8*FRACUNIT, finecosine[ang]);
|
||||
self->vel.y = finesine[ang] << 3; //FixedMul (8*FRACUNIT, finesine[ang]);
|
||||
ang -= 90;
|
||||
self->Thrust(ang, 8);
|
||||
self->special2 = 3; // strafe time
|
||||
}
|
||||
}
|
||||
|
@ -235,16 +233,16 @@ DEFINE_ACTION_FUNCTION(AActor, A_FiredSplotch)
|
|||
mo = Spawn ("FireDemonSplotch1", self->Pos(), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->vel.x = (pr_firedemonsplotch() - 128) << 11;
|
||||
mo->vel.y = (pr_firedemonsplotch() - 128) << 11;
|
||||
mo->vel.z = (pr_firedemonsplotch() << 10) + FRACUNIT*3;
|
||||
mo->Vel.X = (pr_firedemonsplotch() - 128) / 32.;
|
||||
mo->Vel.Y = (pr_firedemonsplotch() - 128) / 32.;
|
||||
mo->Vel.Z = (pr_firedemonsplotch() / 64.) + 3;
|
||||
}
|
||||
mo = Spawn ("FireDemonSplotch2", self->Pos(), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->vel.x = (pr_firedemonsplotch() - 128) << 11;
|
||||
mo->vel.y = (pr_firedemonsplotch() - 128) << 11;
|
||||
mo->vel.z = (pr_firedemonsplotch() << 10) + FRACUNIT*3;
|
||||
mo->Vel.X = (pr_firedemonsplotch() - 128) / 32.;
|
||||
mo->Vel.Y = (pr_firedemonsplotch() - 128) / 32.;
|
||||
mo->Vel.Z = (pr_firedemonsplotch() / 64.) + 3;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -39,13 +39,10 @@ IMPLEMENT_CLASS (AArtiPoisonBag1)
|
|||
|
||||
bool AArtiPoisonBag1::Use (bool pickup)
|
||||
{
|
||||
angle_t angle = Owner->angle >> ANGLETOFINESHIFT;
|
||||
AActor *mo;
|
||||
|
||||
mo = Spawn ("PoisonBag", Owner->Vec3Offset(
|
||||
16*finecosine[angle],
|
||||
24*finesine[angle],
|
||||
-Owner->floorclip+8*FRACUNIT), ALLOW_REPLACE);
|
||||
AActor *mo = Spawn("PoisonBag", Owner->Vec3Offset(
|
||||
16 * Owner->Angles.Yaw.Cos(),
|
||||
24 * Owner->Angles.Yaw.Sin(),
|
||||
-Owner->Floorclip + 8), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->target = Owner;
|
||||
|
@ -67,13 +64,10 @@ IMPLEMENT_CLASS (AArtiPoisonBag2)
|
|||
|
||||
bool AArtiPoisonBag2::Use (bool pickup)
|
||||
{
|
||||
angle_t angle = Owner->angle >> ANGLETOFINESHIFT;
|
||||
AActor *mo;
|
||||
|
||||
mo = Spawn ("FireBomb", Owner->Vec3Offset(
|
||||
16*finecosine[angle],
|
||||
24*finesine[angle],
|
||||
-Owner->floorclip+8*FRACUNIT), ALLOW_REPLACE);
|
||||
AActor *mo = Spawn("FireBomb", Owner->Vec3Offset(
|
||||
16 * Owner->Angles.Yaw.Cos(),
|
||||
24 * Owner->Angles.Yaw.Sin(),
|
||||
-Owner->Floorclip + 8), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->target = Owner;
|
||||
|
@ -97,14 +91,14 @@ bool AArtiPoisonBag3::Use (bool pickup)
|
|||
{
|
||||
AActor *mo;
|
||||
|
||||
mo = Spawn("ThrowingBomb", Owner->PosPlusZ(-Owner->floorclip+35*FRACUNIT + (Owner->player? Owner->player->crouchoffset : 0)), ALLOW_REPLACE);
|
||||
mo = Spawn("ThrowingBomb", Owner->PosPlusZ(35. - Owner->Floorclip + (Owner->player? Owner->player->crouchoffset : 0)), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->angle = Owner->angle + (((pr_poisonbag()&7) - 4) << 24);
|
||||
mo->Angles.Yaw = Owner->Angles.Yaw + (((pr_poisonbag() & 7) - 4) * (360./256.));
|
||||
|
||||
/* Original flight code from Hexen
|
||||
* mo->momz = 4*FRACUNIT+((player->lookdir)<<(FRACBITS-4));
|
||||
* mo->z += player->lookdir<<(FRACBITS-4);
|
||||
* mo->momz = 4*F.RACUNIT+((player->lookdir)<<(F.RACBITS-4));
|
||||
* mo->z += player->lookdir<<(F.RACBITS-4);
|
||||
* P_ThrustMobj(mo, mo->angle, mo->info->speed);
|
||||
* mo->momx += player->mo->momx>>1;
|
||||
* mo->momy += player->mo->momy>>1;
|
||||
|
@ -114,16 +108,16 @@ bool AArtiPoisonBag3::Use (bool pickup)
|
|||
// is as set by the projectile. To accommodate this with a proper trajectory, we
|
||||
// aim the projectile ~20 degrees higher than we're looking at and increase the
|
||||
// speed we fire at accordingly.
|
||||
angle_t orgpitch = angle_t(-Owner->pitch) >> ANGLETOFINESHIFT;
|
||||
angle_t modpitch = angle_t(0xDC00000 - Owner->pitch) >> ANGLETOFINESHIFT;
|
||||
angle_t angle = mo->angle >> ANGLETOFINESHIFT;
|
||||
fixed_t speed = fixed_t(sqrt((double)mo->Speed*mo->Speed + (4.0*65536*4*65536)));
|
||||
fixed_t xyscale = FixedMul(speed, finecosine[modpitch]);
|
||||
DAngle orgpitch = -Owner->Angles.Pitch;
|
||||
DAngle modpitch = clamp<DAngle>(-Owner->Angles.Pitch + 20, -89., 89.);
|
||||
DAngle angle = mo->Angles.Yaw;
|
||||
double speed = DVector2(mo->Speed, 4.).Length();
|
||||
double xyscale = speed * modpitch.Cos();
|
||||
|
||||
mo->vel.z = FixedMul(speed, finesine[modpitch]);
|
||||
mo->vel.x = FixedMul(xyscale, finecosine[angle]) + (Owner->vel.x >> 1);
|
||||
mo->vel.y = FixedMul(xyscale, finesine[angle]) + (Owner->vel.y >> 1);
|
||||
mo->AddZ(FixedMul(mo->Speed, finesine[orgpitch]));
|
||||
mo->Vel.Z = speed * modpitch.Sin();
|
||||
mo->Vel.X = xyscale * angle.Cos() + Owner->Vel.X / 2;
|
||||
mo->Vel.Y = xyscale * angle.Sin() + Owner->Vel.Y / 2;
|
||||
mo->AddZ(mo->Speed * orgpitch.Sin());
|
||||
|
||||
mo->target = Owner;
|
||||
mo->tics -= pr_poisonbag()&3;
|
||||
|
@ -265,7 +259,7 @@ AInventory *AArtiPoisonBag::CreateCopy (AActor *other)
|
|||
|
||||
AInventory *copy;
|
||||
PClassActor *spawntype = GetFlechetteType(other);
|
||||
copy = static_cast<AInventory *>(Spawn (spawntype, 0, 0, 0, NO_REPLACE));
|
||||
copy = static_cast<AInventory *>(Spawn (spawntype));
|
||||
copy->Amount = Amount;
|
||||
copy->MaxAmount = MaxAmount;
|
||||
GoAwayAndDie ();
|
||||
|
@ -306,7 +300,7 @@ IMPLEMENT_CLASS (APoisonCloud)
|
|||
|
||||
void APoisonCloud::BeginPlay ()
|
||||
{
|
||||
vel.x = 1; // missile objects must move to impact other objects
|
||||
Vel.X = MinVel; // missile objects must move to impact other objects
|
||||
special1 = 24+(pr_poisoncloud()&7);
|
||||
special2 = 0;
|
||||
}
|
||||
|
@ -324,7 +318,7 @@ int APoisonCloud::DoSpecialDamage (AActor *victim, int damage, FName damagetype)
|
|||
}
|
||||
else
|
||||
{
|
||||
dopoison = victim->player->poisoncount < (int)(4.f * level.teamdamage);
|
||||
dopoison = victim->player->poisoncount < (int)(4. * level.teamdamage);
|
||||
}
|
||||
|
||||
if (dopoison)
|
||||
|
@ -332,7 +326,7 @@ int APoisonCloud::DoSpecialDamage (AActor *victim, int damage, FName damagetype)
|
|||
int damage = 15 + (pr_poisoncloudd()&15);
|
||||
if (mate)
|
||||
{
|
||||
damage = (int)((double)damage * level.teamdamage);
|
||||
damage = (int)(damage * level.teamdamage);
|
||||
}
|
||||
// Handle passive damage modifiers (e.g. PowerProtection)
|
||||
if (victim->Inventory != NULL)
|
||||
|
@ -340,11 +334,7 @@ int APoisonCloud::DoSpecialDamage (AActor *victim, int damage, FName damagetype)
|
|||
victim->Inventory->ModifyDamage(damage, damagetype, damage, true);
|
||||
}
|
||||
// Modify with damage factors
|
||||
damage = FixedMul(damage, victim->DamageFactor);
|
||||
if (damage > 0)
|
||||
{
|
||||
damage = DamageTypeDefinition::ApplyMobjDamageFactor(damage, damagetype, victim->GetClass()->DamageFactors);
|
||||
}
|
||||
damage = victim->ApplyDamageFactor(damagetype, damage);
|
||||
if (damage > 0)
|
||||
{
|
||||
P_PoisonDamage (victim->player, this,
|
||||
|
@ -376,7 +366,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PoisonBagInit)
|
|||
|
||||
AActor *mo;
|
||||
|
||||
mo = Spawn<APoisonCloud> (self->PosPlusZ(28*FRACUNIT), ALLOW_REPLACE);
|
||||
mo = Spawn<APoisonCloud> (self->PosPlusZ(28.), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->target = self->target;
|
||||
|
@ -419,7 +409,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PoisonBagDamage)
|
|||
|
||||
P_RadiusAttack (self, self->target, 4, 40, self->DamageType, RADF_HURTSOURCE);
|
||||
bobIndex = self->special2;
|
||||
self->AddZ(finesine[bobIndex << BOBTOFINESHIFT] >> 1);
|
||||
self->AddZ(BobSin(bobIndex) / 16);
|
||||
self->special2 = (bobIndex + 1) & 63;
|
||||
return 0;
|
||||
}
|
||||
|
@ -452,15 +442,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_CheckThrowBomb2)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
// [RH] Check using actual velocity, although the vel.z < 2 check still stands
|
||||
//if (abs(self->vel.x) < FRACUNIT*3/2 && abs(self->vel.y) < FRACUNIT*3/2
|
||||
// && self->vel.z < 2*FRACUNIT)
|
||||
if (self->vel.z < 2*FRACUNIT &&
|
||||
TMulScale32 (self->vel.x, self->vel.x, self->vel.y, self->vel.y, self->vel.z, self->vel.z)
|
||||
< (3*3)/(2*2))
|
||||
if (self->Vel.Z < 2 && self->Vel.LengthSquared() < (9./4.))
|
||||
{
|
||||
self->SetState (self->SpawnState + 6);
|
||||
self->SetZ(self->floorz);
|
||||
self->vel.z = 0;
|
||||
self->Vel.Z = 0;
|
||||
self->BounceFlags = BOUNCE_None;
|
||||
self->flags &= ~MF_MISSILE;
|
||||
}
|
||||
|
|
|
@ -84,26 +84,24 @@ DEFINE_ACTION_FUNCTION(AActor, A_FlyBuzz)
|
|||
return 0;
|
||||
}
|
||||
|
||||
angle_t ang = self->AngleTo(targ);
|
||||
self->angle = ang;
|
||||
self->Angles.Yaw = self->AngleTo(targ);
|
||||
self->args[0]++;
|
||||
ang >>= ANGLETOFINESHIFT;
|
||||
if (!P_TryMove(self, self->X() + 6 * finecosine[ang], self->Y() + 6 * finesine[ang], true))
|
||||
if (!P_TryMove(self, self->Pos().XY() + self->Angles.Yaw.ToVector(6), true))
|
||||
{
|
||||
self->SetIdle(true);
|
||||
return 0;
|
||||
}
|
||||
if (self->args[0] & 2)
|
||||
{
|
||||
self->vel.x += (pr_fly() - 128) << BOBTOFINESHIFT;
|
||||
self->vel.y += (pr_fly() - 128) << BOBTOFINESHIFT;
|
||||
self->Vel.X += (pr_fly() - 128) / 512.;
|
||||
self->Vel.Y += (pr_fly() - 128) / 512.;
|
||||
}
|
||||
int zrand = pr_fly();
|
||||
if (targ->Z() + 5*FRACUNIT < self->Z() && zrand > 150)
|
||||
if (targ->Z() + 5. < self->Z() && zrand > 150)
|
||||
{
|
||||
zrand = -zrand;
|
||||
}
|
||||
self->vel.z = zrand << BOBTOFINESHIFT;
|
||||
self->Vel.Z = zrand / 512.;
|
||||
if (pr_fly() < 40)
|
||||
{
|
||||
S_Sound(self, CHAN_VOICE, self->ActiveSound, 0.5f, ATTN_STATIC);
|
||||
|
|
|
@ -15,7 +15,7 @@ static FRandom pr_fogspawn ("FogSpawn");
|
|||
// args[3] Lifetime countdown
|
||||
// args[4] Boolean: fog moving?
|
||||
// special1 Internal: Counter for spawn frequency
|
||||
// special2 Internal: Index into floatbob table
|
||||
// WeaveIndexZ Internal: Index into floatbob table
|
||||
//
|
||||
//==========================================================================
|
||||
|
||||
|
@ -37,7 +37,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FogSpawn)
|
|||
};
|
||||
|
||||
AActor *mo = NULL;
|
||||
angle_t delta;
|
||||
int delta;
|
||||
|
||||
if (self->special1-- > 0)
|
||||
{
|
||||
|
@ -51,13 +51,13 @@ DEFINE_ACTION_FUNCTION(AActor, A_FogSpawn)
|
|||
{
|
||||
delta = self->args[1];
|
||||
if (delta==0) delta=1;
|
||||
mo->angle = self->angle + (((pr_fogspawn()%delta)-(delta>>1))<<24);
|
||||
mo->Angles.Yaw = self->Angles.Yaw + (((pr_fogspawn() % delta) - (delta >> 1)) * (360 / 256.));
|
||||
mo->target = self;
|
||||
if (self->args[0] < 1) self->args[0] = 1;
|
||||
mo->args[0] = (pr_fogspawn() % (self->args[0]))+1; // Random speed
|
||||
mo->args[3] = self->args[3]; // Set lifetime
|
||||
mo->args[4] = 1; // Set to moving
|
||||
mo->special2 = pr_fogspawn()&63;
|
||||
mo->WeaveIndexZ = pr_fogspawn()&63;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -72,8 +72,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FogMove)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int speed = self->args[0]<<FRACBITS;
|
||||
angle_t angle;
|
||||
double speed = self->args[0];
|
||||
int weaveindex;
|
||||
|
||||
if (!self->args[4])
|
||||
|
@ -89,14 +88,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_FogMove)
|
|||
|
||||
if ((self->args[3] % 4) == 0)
|
||||
{
|
||||
weaveindex = self->special2;
|
||||
self->AddZ(finesine[weaveindex << BOBTOFINESHIFT] * 4);
|
||||
self->special2 = (weaveindex + 1) & 63;
|
||||
weaveindex = self->WeaveIndexZ;
|
||||
self->AddZ(BobSin(weaveindex) / 2);
|
||||
self->WeaveIndexZ = (weaveindex + 1) & 63;
|
||||
}
|
||||
|
||||
angle = self->angle>>ANGLETOFINESHIFT;
|
||||
self->vel.x = FixedMul(speed, finecosine[angle]);
|
||||
self->vel.y = FixedMul(speed, finesine[angle]);
|
||||
self->VelFromAngle(speed);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -12,7 +12,7 @@
|
|||
#include "doomstat.h"
|
||||
*/
|
||||
|
||||
#define HEAL_RADIUS_DIST 255*FRACUNIT
|
||||
#define HEAL_RADIUS_DIST 255.
|
||||
|
||||
static FRandom pr_healradius ("HealRadius");
|
||||
|
||||
|
@ -42,7 +42,7 @@ bool AArtiHealingRadius::Use (bool pickup)
|
|||
if (playeringame[i] &&
|
||||
players[i].mo != NULL &&
|
||||
players[i].mo->health > 0 &&
|
||||
players[i].mo->AproxDistance (Owner) <= HEAL_RADIUS_DIST)
|
||||
players[i].mo->Distance2D (Owner) <= HEAL_RADIUS_DIST)
|
||||
{
|
||||
// Q: Is it worth it to make this selectable as a player property?
|
||||
// A: Probably not - but it sure doesn't hurt.
|
||||
|
@ -52,7 +52,7 @@ bool AArtiHealingRadius::Use (bool pickup)
|
|||
case NAME_Armor:
|
||||
for (int j = 0; j < 4; ++j)
|
||||
{
|
||||
AHexenArmor *armor = Spawn<AHexenArmor> (0,0,0, NO_REPLACE);
|
||||
AHexenArmor *armor = Spawn<AHexenArmor> ();
|
||||
armor->health = j;
|
||||
armor->Amount = 1;
|
||||
if (!armor->CallTryPickup (players[i].mo))
|
||||
|
|
|
@ -16,7 +16,7 @@
|
|||
// Sorcerer stuff
|
||||
//
|
||||
// Sorcerer Variables
|
||||
// special1 Angle of ball 1 (all others relative to that)
|
||||
// specialf1 Angle of ball 1 (all others relative to that)
|
||||
// StopBall which ball to stop at in stop mode (MT_???)
|
||||
// args[0] Defense time
|
||||
// args[1] Number of full rotations since stopping mode
|
||||
|
@ -24,7 +24,7 @@
|
|||
// args[3] Movement mode (see SORC_ macros)
|
||||
// args[4] Current ball orbit speed
|
||||
// Sorcerer Ball Variables
|
||||
// special1 Previous angle of ball (for woosh)
|
||||
// specialf1 Previous angle of ball (for woosh)
|
||||
// special2 Countdown of rapid fire (FX4)
|
||||
//============================================================================
|
||||
|
||||
|
@ -45,9 +45,9 @@
|
|||
#define SORC_NORMAL 5
|
||||
#define SORC_FIRING_SPELL 6
|
||||
|
||||
#define BALL1_ANGLEOFFSET 0
|
||||
#define BALL2_ANGLEOFFSET (ANGLE_MAX/3)
|
||||
#define BALL3_ANGLEOFFSET ((ANGLE_MAX/3)*2)
|
||||
#define BALL1_ANGLEOFFSET 0.
|
||||
#define BALL2_ANGLEOFFSET 120.
|
||||
#define BALL3_ANGLEOFFSET 240.
|
||||
|
||||
void A_SlowBalls (AActor *actor);
|
||||
void A_StopBalls (AActor *actor);
|
||||
|
@ -65,6 +65,7 @@ class AHeresiarch : public AActor
|
|||
DECLARE_CLASS (AHeresiarch, AActor)
|
||||
public:
|
||||
const PClass *StopBall;
|
||||
DAngle BallAngle;
|
||||
|
||||
void Serialize (FArchive &arc);
|
||||
void Die (AActor *source, AActor *inflictor, int dmgflags);
|
||||
|
@ -75,7 +76,7 @@ IMPLEMENT_CLASS (AHeresiarch)
|
|||
void AHeresiarch::Serialize (FArchive &arc)
|
||||
{
|
||||
Super::Serialize (arc);
|
||||
arc << StopBall;
|
||||
arc << StopBall << BallAngle;
|
||||
}
|
||||
|
||||
void AHeresiarch::Die (AActor *source, AActor *inflictor, int dmgflags)
|
||||
|
@ -101,15 +102,16 @@ public:
|
|||
virtual void DoFireSpell ();
|
||||
virtual void SorcUpdateBallAngle ();
|
||||
virtual void CastSorcererSpell ();
|
||||
angle_t AngleOffset;
|
||||
DAngle AngleOffset;
|
||||
DAngle OldAngle;
|
||||
|
||||
void Serialize (FArchive &arc)
|
||||
{
|
||||
Super::Serialize (arc);
|
||||
arc << AngleOffset;
|
||||
arc << AngleOffset << OldAngle;
|
||||
}
|
||||
|
||||
bool SpecialBlastHandling (AActor *source, fixed_t strength)
|
||||
bool SpecialBlastHandling (AActor *source, double strength)
|
||||
{ // don't blast sorcerer balls
|
||||
return false;
|
||||
}
|
||||
|
@ -169,26 +171,6 @@ IMPLEMENT_CLASS (ASorcBall3)
|
|||
|
||||
// Sorcerer spell 1 (The burning, bouncing head thing) ----------------------
|
||||
|
||||
/*
|
||||
class ASorcFX1 : public AActor
|
||||
{
|
||||
DECLARE_CLASS (ASorcFX1, AActor)
|
||||
public:
|
||||
bool FloorBounceMissile (secplane_t &plane)
|
||||
{
|
||||
fixed_t orgvelz = vel.z;
|
||||
|
||||
if (!Super::FloorBounceMissile (plane))
|
||||
{
|
||||
vel.z = -orgvelz; // no energy absorbed
|
||||
return false;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
};
|
||||
IMPLEMENT_CLASS (ASorcFX1)
|
||||
*/
|
||||
|
||||
//============================================================================
|
||||
//
|
||||
// SorcBall::DoFireSpell
|
||||
|
@ -231,7 +213,7 @@ void ASorcBall1::DoFireSpell ()
|
|||
|
||||
DEFINE_ACTION_FUNCTION(AActor, A_SorcSpinBalls)
|
||||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
PARAM_ACTION_PROLOGUE_TYPE(AHeresiarch);
|
||||
|
||||
AActor *mo;
|
||||
|
||||
|
@ -240,9 +222,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcSpinBalls)
|
|||
self->args[0] = 0; // Currently no defense
|
||||
self->args[3] = SORC_NORMAL;
|
||||
self->args[4] = SORCBALL_INITIAL_SPEED; // Initial orbit speed
|
||||
self->special1 = ANGLE_1;
|
||||
self->BallAngle = 1.;
|
||||
|
||||
fixedvec3 pos = self->PosPlusZ(-self->floorclip + self->height);
|
||||
DVector3 pos = self->PosPlusZ(-self->Floorclip + self->Height);
|
||||
|
||||
mo = Spawn("SorcBall1", pos, NO_REPLACE);
|
||||
if (mo)
|
||||
|
@ -262,11 +244,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcSpinBalls)
|
|||
//
|
||||
// A_SorcBallOrbit
|
||||
//
|
||||
// - actor is ball
|
||||
//============================================================================
|
||||
|
||||
DEFINE_ACTION_FUNCTION(AActor, A_SorcBallOrbit)
|
||||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
PARAM_ACTION_PROLOGUE_TYPE(ASorcBall);
|
||||
|
||||
// [RH] If no parent, then die instead of crashing
|
||||
if (self->target == NULL)
|
||||
|
@ -275,78 +258,78 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcBallOrbit)
|
|||
return 0;
|
||||
}
|
||||
|
||||
ASorcBall *actor;
|
||||
angle_t angle, baseangle;
|
||||
int mode = self->target->args[3];
|
||||
AHeresiarch *parent = barrier_cast<AHeresiarch *>(self->target);
|
||||
int dist = parent->radius - (self->radius<<1);
|
||||
angle_t prevangle = self->special1;
|
||||
double dist = parent->radius - (self->radius*2);
|
||||
|
||||
#if 0
|
||||
// This cannot happen anymore because this is defined locally in SorcBall
|
||||
if (!self->IsKindOf (RUNTIME_CLASS(ASorcBall)))
|
||||
{
|
||||
I_Error ("Corrupted sorcerer:\nTried to use a %s", self->GetClass()->TypeName.GetChars());
|
||||
}
|
||||
actor = static_cast<ASorcBall *> (self);
|
||||
#endif
|
||||
|
||||
if (actor->target->health <= 0)
|
||||
if (self->target->health <= 0)
|
||||
{
|
||||
actor->SetState (actor->FindState(NAME_Pain));
|
||||
self->SetState (self->FindState(NAME_Pain));
|
||||
return 0;
|
||||
}
|
||||
|
||||
baseangle = (angle_t)parent->special1;
|
||||
angle = baseangle + actor->AngleOffset;
|
||||
actor->angle = angle;
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
DAngle prevangle = self->OldAngle;
|
||||
DAngle baseangle = parent->BallAngle;
|
||||
DAngle angle = baseangle + self->AngleOffset;
|
||||
|
||||
self->Angles.Yaw = angle;
|
||||
|
||||
switch (mode)
|
||||
{
|
||||
case SORC_NORMAL: // Balls rotating normally
|
||||
actor->SorcUpdateBallAngle ();
|
||||
self->SorcUpdateBallAngle ();
|
||||
break;
|
||||
|
||||
case SORC_DECELERATE: // Balls decelerating
|
||||
A_DecelBalls(actor);
|
||||
actor->SorcUpdateBallAngle ();
|
||||
A_DecelBalls(self);
|
||||
self->SorcUpdateBallAngle ();
|
||||
break;
|
||||
|
||||
case SORC_ACCELERATE: // Balls accelerating
|
||||
A_AccelBalls(actor);
|
||||
actor->SorcUpdateBallAngle ();
|
||||
A_AccelBalls(self);
|
||||
self->SorcUpdateBallAngle ();
|
||||
break;
|
||||
|
||||
case SORC_STOPPING: // Balls stopping
|
||||
if ((parent->StopBall == actor->GetClass()) &&
|
||||
if ((parent->StopBall == self->GetClass()) &&
|
||||
(parent->args[1] > SORCBALL_SPEED_ROTATIONS) &&
|
||||
(absangle(angle - (parent->angle>>ANGLETOFINESHIFT)) < (30<<5)))
|
||||
absangle(angle, parent->Angles.Yaw) < 42.1875)
|
||||
{
|
||||
// Can stop now
|
||||
actor->target->args[3] = SORC_FIRESPELL;
|
||||
actor->target->args[4] = 0;
|
||||
self->target->args[3] = SORC_FIRESPELL;
|
||||
self->target->args[4] = 0;
|
||||
// Set angle so self angle == sorcerer angle
|
||||
parent->special1 = (int)(parent->angle - actor->AngleOffset);
|
||||
parent->BallAngle = parent->Angles.Yaw - self->AngleOffset;
|
||||
}
|
||||
else
|
||||
{
|
||||
actor->SorcUpdateBallAngle ();
|
||||
self->SorcUpdateBallAngle ();
|
||||
}
|
||||
break;
|
||||
|
||||
case SORC_FIRESPELL: // Casting spell
|
||||
if (parent->StopBall == actor->GetClass())
|
||||
if (parent->StopBall == self->GetClass())
|
||||
{
|
||||
// Put sorcerer into special throw spell anim
|
||||
if (parent->health > 0)
|
||||
parent->SetState (parent->FindState("Attack1"));
|
||||
|
||||
actor->DoFireSpell ();
|
||||
self->DoFireSpell ();
|
||||
}
|
||||
break;
|
||||
|
||||
case SORC_FIRING_SPELL:
|
||||
if (parent->StopBall == actor->GetClass())
|
||||
if (parent->StopBall == self->GetClass())
|
||||
{
|
||||
if (actor->special2-- <= 0)
|
||||
if (self->special2-- <= 0)
|
||||
{
|
||||
// Done rapid firing
|
||||
parent->args[3] = SORC_STOPPED;
|
||||
|
@ -357,7 +340,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcBallOrbit)
|
|||
else
|
||||
{
|
||||
// Do rapid fire spell
|
||||
A_SorcOffense2(actor);
|
||||
A_SorcOffense2(self);
|
||||
}
|
||||
}
|
||||
break;
|
||||
|
@ -367,21 +350,18 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcBallOrbit)
|
|||
break;
|
||||
}
|
||||
|
||||
if ((angle < prevangle) && (parent->args[4]==SORCBALL_TERMINAL_SPEED))
|
||||
if (deltaangle(angle, prevangle) < 0 && (parent->args[4]==SORCBALL_TERMINAL_SPEED))
|
||||
{
|
||||
parent->args[1]++; // Bump rotation counter
|
||||
// Completed full rotation - make woosh sound
|
||||
S_Sound (actor, CHAN_BODY, "SorcererBallWoosh", 1, ATTN_NORM);
|
||||
S_Sound (self, CHAN_BODY, "SorcererBallWoosh", 1, ATTN_NORM);
|
||||
}
|
||||
actor->special1 = angle; // Set previous angle
|
||||
self->OldAngle = angle; // Set previous angle
|
||||
|
||||
fixedvec3 pos = parent->Vec3Offset(
|
||||
FixedMul(dist, finecosine[angle]),
|
||||
FixedMul(dist, finesine[angle]),
|
||||
-parent->floorclip + parent->height);
|
||||
actor->SetOrigin (pos, true);
|
||||
actor->floorz = parent->floorz;
|
||||
actor->ceilingz = parent->ceilingz;
|
||||
DVector3 pos = parent->Vec3Angle(dist, angle, -parent->Floorclip + parent->Height);
|
||||
self->SetOrigin (pos, true);
|
||||
self->floorz = parent->floorz;
|
||||
self->ceilingz = parent->ceilingz;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -411,10 +391,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_SpeedBalls)
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
void A_SlowBalls(AActor *actor)
|
||||
void A_SlowBalls(AActor *self)
|
||||
{
|
||||
actor->args[3] = SORC_DECELERATE; // slow mode
|
||||
actor->args[2] = SORCBALL_INITIAL_SPEED; // target speed
|
||||
self->args[3] = SORC_DECELERATE; // slow mode
|
||||
self->args[2] = SORCBALL_INITIAL_SPEED; // target speed
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
|
@ -428,23 +408,23 @@ void A_SlowBalls(AActor *actor)
|
|||
|
||||
void A_StopBalls(AActor *scary)
|
||||
{
|
||||
AHeresiarch *actor = static_cast<AHeresiarch *> (scary);
|
||||
AHeresiarch *self = static_cast<AHeresiarch *> (scary);
|
||||
int chance = pr_heresiarch();
|
||||
actor->args[3] = SORC_STOPPING; // stopping mode
|
||||
actor->args[1] = 0; // Reset rotation counter
|
||||
self->args[3] = SORC_STOPPING; // stopping mode
|
||||
self->args[1] = 0; // Reset rotation counter
|
||||
|
||||
if ((actor->args[0] <= 0) && (chance < 200))
|
||||
if ((self->args[0] <= 0) && (chance < 200))
|
||||
{
|
||||
actor->StopBall = RUNTIME_CLASS(ASorcBall2); // Blue
|
||||
self->StopBall = RUNTIME_CLASS(ASorcBall2); // Blue
|
||||
}
|
||||
else if((actor->health < (actor->SpawnHealth() >> 1)) &&
|
||||
else if((self->health < (self->SpawnHealth() >> 1)) &&
|
||||
(chance < 200))
|
||||
{
|
||||
actor->StopBall = RUNTIME_CLASS(ASorcBall3); // Green
|
||||
self->StopBall = RUNTIME_CLASS(ASorcBall3); // Green
|
||||
}
|
||||
else
|
||||
{
|
||||
actor->StopBall = RUNTIME_CLASS(ASorcBall1); // Yellow
|
||||
self->StopBall = RUNTIME_CLASS(ASorcBall1); // Yellow
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -456,9 +436,9 @@ void A_StopBalls(AActor *scary)
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
void A_AccelBalls(AActor *actor)
|
||||
void A_AccelBalls(AActor *self)
|
||||
{
|
||||
AActor *sorc = actor->target;
|
||||
AActor *sorc = self->target;
|
||||
|
||||
if (sorc->args[4] < sorc->args[2])
|
||||
{
|
||||
|
@ -483,9 +463,9 @@ void A_AccelBalls(AActor *actor)
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
void A_DecelBalls(AActor *actor)
|
||||
void A_DecelBalls(AActor *self)
|
||||
{
|
||||
AActor *sorc = actor->target;
|
||||
AActor *sorc = self->target;
|
||||
|
||||
if (sorc->args[4] > sorc->args[2])
|
||||
{
|
||||
|
@ -506,7 +486,7 @@ void A_DecelBalls(AActor *actor)
|
|||
|
||||
void ASorcBall1::SorcUpdateBallAngle ()
|
||||
{
|
||||
target->special1 += ANGLE_1*target->args[4];
|
||||
barrier_cast<AHeresiarch*>(target)->BallAngle += target->args[4];
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
|
@ -551,7 +531,7 @@ void ASorcBall2::CastSorcererSpell ()
|
|||
AActor *parent = target;
|
||||
AActor *mo;
|
||||
|
||||
mo = Spawn("SorcFX2", PosPlusZ(-parent->floorclip + SORC_DEFENSE_HEIGHT*FRACUNIT), ALLOW_REPLACE);
|
||||
mo = Spawn("SorcFX2", PosPlusZ(parent->Floorclip + SORC_DEFENSE_HEIGHT), ALLOW_REPLACE);
|
||||
parent->flags2 |= MF2_REFLECTIVE|MF2_INVULNERABLE;
|
||||
parent->args[0] = SORC_DEFENSE_TIME;
|
||||
if (mo) mo->target = parent;
|
||||
|
@ -570,24 +550,24 @@ void ASorcBall3::CastSorcererSpell ()
|
|||
Super::CastSorcererSpell ();
|
||||
|
||||
AActor *mo;
|
||||
angle_t ang1, ang2;
|
||||
DAngle ang1, ang2;
|
||||
AActor *parent = target;
|
||||
|
||||
ang1 = angle - ANGLE_45;
|
||||
ang2 = angle + ANGLE_45;
|
||||
ang1 = Angles.Yaw.Degrees - 45;
|
||||
ang2 = Angles.Yaw.Degrees + 45;
|
||||
PClassActor *cls = PClass::FindActor("SorcFX3");
|
||||
if (health < (SpawnHealth()/3))
|
||||
{ // Spawn 2 at a time
|
||||
mo = P_SpawnMissileAngle(parent, cls, ang1, 4*FRACUNIT);
|
||||
mo = P_SpawnMissileAngle(parent, cls, ang1, 4.);
|
||||
if (mo) mo->target = parent;
|
||||
mo = P_SpawnMissileAngle(parent, cls, ang2, 4*FRACUNIT);
|
||||
mo = P_SpawnMissileAngle(parent, cls, ang2, 4.);
|
||||
if (mo) mo->target = parent;
|
||||
}
|
||||
else
|
||||
{
|
||||
if (pr_heresiarch() < 128)
|
||||
ang1 = ang2;
|
||||
mo = P_SpawnMissileAngle(parent, cls, ang1, 4*FRACUNIT);
|
||||
mo = P_SpawnMissileAngle(parent, cls, ang1, 4.);
|
||||
if (mo) mo->target = parent;
|
||||
}
|
||||
}
|
||||
|
@ -596,12 +576,12 @@ void ASorcBall3::CastSorcererSpell ()
|
|||
/*
|
||||
void A_SpawnReinforcements(AActor *actor)
|
||||
{
|
||||
AActor *parent = actor->target;
|
||||
AActor *parent = self->target;
|
||||
AActor *mo;
|
||||
angle_t ang;
|
||||
DAngle ang;
|
||||
|
||||
ang = ANGLE_1 * P_Random();
|
||||
mo = P_SpawnMissileAngle(actor, MT_SORCFX3, ang, 5*FRACUNIT);
|
||||
ang = P_Random();
|
||||
mo = P_SpawnMissileAngle(actor, MT_SORCFX3, ang, 5.);
|
||||
if (mo) mo->target = parent;
|
||||
}
|
||||
*/
|
||||
|
@ -619,11 +599,11 @@ void ASorcBall1::CastSorcererSpell ()
|
|||
Super::CastSorcererSpell ();
|
||||
|
||||
AActor *mo;
|
||||
angle_t ang1, ang2;
|
||||
DAngle ang1, ang2;
|
||||
AActor *parent = target;
|
||||
|
||||
ang1 = angle + ANGLE_1*70;
|
||||
ang2 = angle - ANGLE_1*70;
|
||||
ang1 = Angles.Yaw.Degrees + 70;
|
||||
ang2 = Angles.Yaw.Degrees - 70;
|
||||
PClassActor *cls = PClass::FindActor("SorcFX1");
|
||||
mo = P_SpawnMissileAngle (parent, cls, ang1, 0);
|
||||
if (mo)
|
||||
|
@ -651,14 +631,15 @@ void ASorcBall1::CastSorcererSpell ()
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
void A_SorcOffense2(AActor *actor)
|
||||
void A_SorcOffense2(AActor *self)
|
||||
{
|
||||
angle_t ang1;
|
||||
DAngle ang1;
|
||||
AActor *mo;
|
||||
int delta, index;
|
||||
AActor *parent = actor->target;
|
||||
double delta;
|
||||
int index;
|
||||
AActor *parent = self->target;
|
||||
AActor *dest = parent->target;
|
||||
int dist;
|
||||
double dist;
|
||||
|
||||
// [RH] If no enemy, then don't try to shoot.
|
||||
if (dest == NULL)
|
||||
|
@ -666,18 +647,17 @@ void A_SorcOffense2(AActor *actor)
|
|||
return;
|
||||
}
|
||||
|
||||
index = actor->args[4] << 5;
|
||||
actor->args[4] = (actor->args[4] + 15) & 255;
|
||||
delta = (finesine[index])*SORCFX4_SPREAD_ANGLE;
|
||||
delta = (delta>>FRACBITS)*ANGLE_1;
|
||||
ang1 = actor->angle + delta;
|
||||
index = self->args[4];
|
||||
self->args[4] = (self->args[4] + 15) & 255;
|
||||
delta = DAngle(index * (360 / 256.f)).Sin() * SORCFX4_SPREAD_ANGLE;
|
||||
|
||||
ang1 = self->Angles.Yaw + delta;
|
||||
mo = P_SpawnMissileAngle(parent, PClass::FindActor("SorcFX4"), ang1, 0);
|
||||
if (mo)
|
||||
{
|
||||
mo->special2 = 35*5/2; // 5 seconds
|
||||
dist = mo->AproxDistance(dest) / mo->Speed;
|
||||
if(dist < 1) dist = 1;
|
||||
mo->vel.z = (dest->Z() - mo->Z()) / dist;
|
||||
dist = mo->DistanceBySpeed(dest, mo->Speed);
|
||||
mo->Vel.Z = (dest->Z() - mo->Z()) / dist;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -709,22 +689,21 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcBossAttack)
|
|||
DEFINE_ACTION_FUNCTION(AActor, A_SpawnFizzle)
|
||||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
fixed_t dist = 5*FRACUNIT;
|
||||
fixed_t speed = self->Speed >> FRACBITS;
|
||||
angle_t rangle;
|
||||
int speed = (int)self->Speed;
|
||||
DAngle rangle;
|
||||
AActor *mo;
|
||||
int ix;
|
||||
|
||||
fixedvec3 pos = self->Vec3Angle(dist, self->angle, -self->floorclip + (self->height >> 1));
|
||||
DVector3 pos = self->Vec3Angle(5., self->Angles.Yaw, -self->Floorclip + self->Height / 2. );
|
||||
for (ix=0; ix<5; ix++)
|
||||
{
|
||||
mo = Spawn("SorcSpark1", pos, ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
rangle = (self->angle >> ANGLETOFINESHIFT) + ((pr_heresiarch()%5) << 1);
|
||||
mo->vel.x = FixedMul(pr_heresiarch()%speed, finecosine[rangle]);
|
||||
mo->vel.y = FixedMul(pr_heresiarch()%speed, finesine[rangle]);
|
||||
mo->vel.z = FRACUNIT*2;
|
||||
rangle = self->Angles.Yaw + (pr_heresiarch() % 5) * (4096 / 360.);
|
||||
mo->Vel.X = (pr_heresiarch() % speed) * rangle.Cos();
|
||||
mo->Vel.Y = (pr_heresiarch() % speed) * rangle.Sin();
|
||||
mo->Vel.Z = 2;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
|
@ -744,7 +723,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX1Seek)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
A_DoBounceCheck (self, "SorcererHeadScream");
|
||||
P_SeekerMissile (self,ANGLE_1*2,ANGLE_1*6);
|
||||
P_SeekerMissile(self, 2, 6);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -758,7 +737,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX1Seek)
|
|||
//============================================================================
|
||||
//
|
||||
// FX2 Variables
|
||||
// special1 current angle
|
||||
// specialf1 current angle
|
||||
// special2
|
||||
// args[0] 0 = CW, 1 = CCW
|
||||
// args[1]
|
||||
|
@ -776,7 +755,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX2Split)
|
|||
{
|
||||
mo->target = self->target;
|
||||
mo->args[0] = 0; // CW
|
||||
mo->special1 = self->angle; // Set angle
|
||||
mo->specialf1 = self->Angles.Yaw.Degrees; // Set angle
|
||||
mo->SetState (mo->FindState("Orbit"));
|
||||
}
|
||||
mo = Spawn(self->GetClass(), self->Pos(), NO_REPLACE);
|
||||
|
@ -784,7 +763,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX2Split)
|
|||
{
|
||||
mo->target = self->target;
|
||||
mo->args[0] = 1; // CCW
|
||||
mo->special1 = self->angle; // Set angle
|
||||
mo->specialf1 = self->Angles.Yaw.Degrees; // Set angle
|
||||
mo->SetState (mo->FindState("Orbit"));
|
||||
}
|
||||
self->Destroy ();
|
||||
|
@ -803,8 +782,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX2Orbit)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
fixedvec3 pos;
|
||||
DAngle angle;
|
||||
DVector3 pos;
|
||||
AActor *parent = self->target;
|
||||
|
||||
// [RH] If no parent, then disappear
|
||||
|
@ -814,7 +793,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX2Orbit)
|
|||
return 0;
|
||||
}
|
||||
|
||||
fixed_t dist = parent->radius;
|
||||
double dist = parent->radius;
|
||||
|
||||
if ((parent->health <= 0) || // Sorcerer is dead
|
||||
(!parent->args[0])) // Time expired
|
||||
|
@ -835,25 +814,18 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcFX2Orbit)
|
|||
// Move to new position based on angle
|
||||
if (self->args[0]) // Counter clock-wise
|
||||
{
|
||||
self->special1 += ANGLE_1*10;
|
||||
angle = ((angle_t)self->special1) >> ANGLETOFINESHIFT;
|
||||
pos = parent->Vec3Offset(
|
||||
FixedMul(dist, finecosine[angle]),
|
||||
FixedMul(dist, finesine[angle]),
|
||||
parent->floorclip + SORC_DEFENSE_HEIGHT*FRACUNIT);
|
||||
pos.z += FixedMul(15*FRACUNIT,finecosine[angle]);
|
||||
self->specialf1 += 10;
|
||||
angle = self->specialf1;
|
||||
pos = parent->Vec3Angle(dist, angle, parent->Floorclip + SORC_DEFENSE_HEIGHT);
|
||||
pos.Z += 15 * angle.Cos();
|
||||
// Spawn trailer
|
||||
Spawn("SorcFX2T1", pos, ALLOW_REPLACE);
|
||||
}
|
||||
else // Clock wise
|
||||
{
|
||||
self->special1 -= ANGLE_1*10;
|
||||
angle = ((angle_t)self->special1) >> ANGLETOFINESHIFT;
|
||||
pos = parent->Vec3Offset(
|
||||
FixedMul(dist, finecosine[angle]),
|
||||
FixedMul(dist, finesine[angle]),
|
||||
parent->floorclip + SORC_DEFENSE_HEIGHT*FRACUNIT);
|
||||
pos.z += FixedMul(20*FRACUNIT,finesine[angle]);
|
||||
self->specialf1 -= 10;
|
||||
pos = parent->Vec3Angle(dist, angle, parent->Floorclip + SORC_DEFENSE_HEIGHT);
|
||||
pos.Z += 20 * angle.Sin();
|
||||
// Spawn trailer
|
||||
Spawn("SorcFX2T1", pos, ALLOW_REPLACE);
|
||||
}
|
||||
|
@ -943,11 +915,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_SorcBallPop)
|
|||
|
||||
S_Sound (self, CHAN_BODY, "SorcererBallPop", 1, ATTN_NONE);
|
||||
self->flags &= ~MF_NOGRAVITY;
|
||||
self->gravity = FRACUNIT/8;
|
||||
self->vel.x = ((pr_heresiarch()%10)-5) << FRACBITS;
|
||||
self->vel.y = ((pr_heresiarch()%10)-5) << FRACBITS;
|
||||
self->vel.z = (2+(pr_heresiarch()%3)) << FRACBITS;
|
||||
self->special2 = 4*FRACUNIT; // Initial bounce factor
|
||||
self->Gravity = 1. / 8;;
|
||||
|
||||
self->Vel.X = ((pr_heresiarch()%10)-5);
|
||||
self->Vel.Y = ((pr_heresiarch()%10)-5);
|
||||
self->Vel.Z = (2+(pr_heresiarch()%3));
|
||||
self->args[4] = BOUNCE_TIME_UNIT; // Bounce time unit
|
||||
self->args[3] = 5; // Bounce time in seconds
|
||||
return 0;
|
||||
|
|
|
@ -10,7 +10,7 @@ class AHolySpirit : public AActor
|
|||
DECLARE_CLASS (AHolySpirit, AActor)
|
||||
public:
|
||||
bool Slam (AActor *thing);
|
||||
bool SpecialBlastHandling (AActor *source, fixed_t strength);
|
||||
bool SpecialBlastHandling (AActor *source, double strength);
|
||||
};
|
||||
|
||||
class AFighterWeapon : public AWeapon
|
||||
|
|
|
@ -66,9 +66,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_PotteryExplode)
|
|||
if (mo)
|
||||
{
|
||||
mo->SetState (mo->SpawnState + (pr_pottery()%5));
|
||||
mo->vel.z = ((pr_pottery()&7)+5)*(3*FRACUNIT/4);
|
||||
mo->vel.x = (pr_pottery.Random2())<<(FRACBITS-6);
|
||||
mo->vel.y = (pr_pottery.Random2())<<(FRACBITS-6);
|
||||
mo->Vel.X = pr_pottery.Random2() / 64.;
|
||||
mo->Vel.Y = pr_pottery.Random2() / 64.;
|
||||
mo->Vel.Z = ((pr_pottery() & 7) + 5) * 0.75;
|
||||
}
|
||||
}
|
||||
S_Sound (mo, CHAN_BODY, "PotteryExplode", 1, ATTN_NORM);
|
||||
|
@ -117,7 +117,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PotteryCheck)
|
|||
if (playeringame[i])
|
||||
{
|
||||
AActor *pmo = players[i].mo;
|
||||
if (P_CheckSight (self, pmo) && (absangle(pmo->AngleTo(self) - pmo->angle) <= ANGLE_45))
|
||||
if (P_CheckSight (self, pmo) && (absangle(pmo->AngleTo(self), pmo->Angles.Yaw) <= 45))
|
||||
{ // Previous state (pottery bit waiting state)
|
||||
self->SetState (self->state - 1);
|
||||
return 0;
|
||||
|
@ -141,7 +141,7 @@ IMPLEMENT_CLASS (AZCorpseLynchedNoHeart)
|
|||
void AZCorpseLynchedNoHeart::PostBeginPlay ()
|
||||
{
|
||||
Super::PostBeginPlay ();
|
||||
Spawn ("BloodPool", X(), Y(), floorz, ALLOW_REPLACE);
|
||||
Spawn ("BloodPool", PosAtZ(floorz), ALLOW_REPLACE);
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
|
@ -156,7 +156,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_CorpseBloodDrip)
|
|||
|
||||
if (pr_drip() <= 128)
|
||||
{
|
||||
Spawn ("CorpseBloodDrip", self->PosPlusZ(self->height/2), ALLOW_REPLACE);
|
||||
Spawn ("CorpseBloodDrip", self->PosPlusZ(self->Height / 2), ALLOW_REPLACE);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -180,9 +180,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_CorpseExplode)
|
|||
if (mo)
|
||||
{
|
||||
mo->SetState (mo->SpawnState + (pr_foo()%3));
|
||||
mo->vel.z = ((pr_foo()&7)+5)*(3*FRACUNIT/4);
|
||||
mo->vel.x = pr_foo.Random2()<<(FRACBITS-6);
|
||||
mo->vel.y = pr_foo.Random2()<<(FRACBITS-6);
|
||||
mo->Vel.X = pr_foo.Random2() / 64.;
|
||||
mo->Vel.Y = pr_foo.Random2() / 64.;
|
||||
mo->Vel.Z = ((pr_foo() & 7) + 5) * 0.75;
|
||||
}
|
||||
}
|
||||
// Spawn a skull
|
||||
|
@ -190,9 +190,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_CorpseExplode)
|
|||
if (mo)
|
||||
{
|
||||
mo->SetState (mo->SpawnState + 3);
|
||||
mo->vel.z = ((pr_foo()&7)+5)*(3*FRACUNIT/4);
|
||||
mo->vel.x = pr_foo.Random2()<<(FRACBITS-6);
|
||||
mo->vel.y = pr_foo.Random2()<<(FRACBITS-6);
|
||||
mo->Vel.X = pr_foo.Random2() / 64.;
|
||||
mo->Vel.Y = pr_foo.Random2() / 64.;
|
||||
mo->Vel.Z = ((pr_foo() & 7) + 5) * 0.75;
|
||||
}
|
||||
S_Sound (self, CHAN_BODY, self->DeathSound, 1, ATTN_IDLE);
|
||||
self->Destroy ();
|
||||
|
@ -214,15 +214,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_LeafSpawn)
|
|||
|
||||
for (i = (pr_leaf()&3)+1; i; i--)
|
||||
{
|
||||
fixed_t xo = (pr_leaf.Random2() << 14);
|
||||
fixed_t yo = (pr_leaf.Random2() << 14);
|
||||
fixed_t zo = (pr_leaf() << 14);
|
||||
double xo = pr_leaf.Random2() / 4.;
|
||||
double yo = pr_leaf.Random2() / 4.;
|
||||
double zo = pr_leaf() / 4.;
|
||||
mo = Spawn (pr_leaf()&1 ? PClass::FindActor ("Leaf1") : PClass::FindActor ("Leaf2"),
|
||||
self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
|
||||
if (mo)
|
||||
{
|
||||
P_ThrustMobj (mo, self->angle, (pr_leaf()<<9)+3*FRACUNIT);
|
||||
mo->Thrust(pr_leaf() / 128. + 3);
|
||||
mo->target = self;
|
||||
mo->special1 = 0;
|
||||
}
|
||||
|
@ -242,7 +242,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LeafThrust)
|
|||
|
||||
if (pr_leafthrust() <= 96)
|
||||
{
|
||||
self->vel.z += (pr_leafthrust()<<9)+FRACUNIT;
|
||||
self->Vel.Z += pr_leafthrust() / 128. + 1;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -263,18 +263,18 @@ DEFINE_ACTION_FUNCTION(AActor, A_LeafCheck)
|
|||
self->SetState (NULL);
|
||||
return 0;
|
||||
}
|
||||
angle_t ang = self->target ? self->target->angle : self->angle;
|
||||
DAngle ang = self->target ? self->target->Angles.Yaw : self->Angles.Yaw;
|
||||
if (pr_leafcheck() > 64)
|
||||
{
|
||||
if (!self->vel.x && !self->vel.y)
|
||||
if (self->Vel.X == 0 && self->Vel.Y == 0)
|
||||
{
|
||||
P_ThrustMobj (self, ang, (pr_leafcheck()<<9)+FRACUNIT);
|
||||
self->Thrust(ang, pr_leafcheck() / 128. + 1);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
self->SetState (self->SpawnState + 7);
|
||||
self->vel.z = (pr_leafcheck()<<9)+FRACUNIT;
|
||||
P_ThrustMobj (self, ang, (pr_leafcheck()<<9)+2*FRACUNIT);
|
||||
self->Vel.Z = pr_leafcheck() / 128. + 1;
|
||||
self->Thrust(ang, pr_leafcheck() / 128. + 2);
|
||||
self->flags |= MF_MISSILE;
|
||||
return 0;
|
||||
}
|
||||
|
@ -289,7 +289,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PoisonShroom)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->tics = 128+(pr_shroom()<<1);
|
||||
self->tics = 128 + (pr_shroom() << 1);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -308,16 +308,16 @@ DEFINE_ACTION_FUNCTION(AActor, A_SoAExplode)
|
|||
|
||||
for (i = 0; i < 10; i++)
|
||||
{
|
||||
fixed_t xo = ((pr_soaexplode() - 128) << 12);
|
||||
fixed_t yo = ((pr_soaexplode() - 128) << 12);
|
||||
fixed_t zo = (pr_soaexplode()*self->height / 256);
|
||||
double xo = (pr_soaexplode() - 128) / 16.;
|
||||
double yo = (pr_soaexplode() - 128) / 16.;
|
||||
double zo = pr_soaexplode()*self->Height / 256.;
|
||||
mo = Spawn ("ZArmorChunk", self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->SetState (mo->SpawnState + i);
|
||||
mo->vel.z = ((pr_soaexplode()&7)+5)*FRACUNIT;
|
||||
mo->vel.x = pr_soaexplode.Random2()<<(FRACBITS-6);
|
||||
mo->vel.y = pr_soaexplode.Random2()<<(FRACBITS-6);
|
||||
mo->Vel.X = pr_soaexplode.Random2() / 64.;
|
||||
mo->Vel.Y = pr_soaexplode.Random2() / 64.;
|
||||
mo->Vel.Z = (pr_soaexplode() & 7) + 5;
|
||||
}
|
||||
}
|
||||
// Spawn an item?
|
||||
|
@ -365,7 +365,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_BellReset1)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->flags |= MF_NOGRAVITY;
|
||||
self->height <<= 2;
|
||||
self->Height *= 4;
|
||||
if (self->special)
|
||||
{ // Initiate death action
|
||||
P_ExecuteSpecial(self->special, NULL, NULL, false, self->args[0],
|
||||
|
|
|
@ -28,19 +28,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_IceGuyLook)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
fixed_t dist;
|
||||
fixed_t an;
|
||||
double dist;
|
||||
DAngle an;
|
||||
|
||||
CALL_ACTION(A_Look, self);
|
||||
if (pr_iceguylook() < 64)
|
||||
{
|
||||
dist = ((pr_iceguylook()-128)*self->radius)>>7;
|
||||
an = (self->angle+ANG90)>>ANGLETOFINESHIFT;
|
||||
|
||||
Spawn(WispTypes[pr_iceguylook() & 1], self->Vec3Offset(
|
||||
FixedMul(dist, finecosine[an]),
|
||||
FixedMul(dist, finesine[an]),
|
||||
60 * FRACUNIT), ALLOW_REPLACE);
|
||||
dist = (pr_iceguylook() - 128) * self->radius / 128.;
|
||||
an = self->Angles.Yaw + 90;
|
||||
Spawn(WispTypes[pr_iceguylook() & 1], self->Vec3Angle(dist, an, 60.), ALLOW_REPLACE);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -55,25 +51,19 @@ DEFINE_ACTION_FUNCTION(AActor, A_IceGuyChase)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
fixed_t dist;
|
||||
fixed_t an;
|
||||
double dist;
|
||||
DAngle an;
|
||||
AActor *mo;
|
||||
|
||||
A_Chase (stack, self);
|
||||
A_Chase(stack, self);
|
||||
if (pr_iceguychase() < 128)
|
||||
{
|
||||
dist = ((pr_iceguychase()-128)*self->radius)>>7;
|
||||
an = (self->angle+ANG90)>>ANGLETOFINESHIFT;
|
||||
|
||||
mo = Spawn(WispTypes[pr_iceguychase() & 1], self->Vec3Offset(
|
||||
FixedMul(dist, finecosine[an]),
|
||||
FixedMul(dist, finesine[an]),
|
||||
60 * FRACUNIT), ALLOW_REPLACE);
|
||||
dist = (pr_iceguychase() - 128) * self->radius / 128.;
|
||||
an = self->Angles.Yaw + 90;
|
||||
mo = Spawn(WispTypes[pr_iceguylook() & 1], self->Vec3Angle(dist, an, 60.), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->vel.x = self->vel.x;
|
||||
mo->vel.y = self->vel.y;
|
||||
mo->vel.z = self->vel.z;
|
||||
mo->Vel = self->Vel;
|
||||
mo->target = self;
|
||||
}
|
||||
}
|
||||
|
@ -94,8 +84,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_IceGuyAttack)
|
|||
{
|
||||
return 0;
|
||||
}
|
||||
P_SpawnMissileXYZ(self->Vec3Angle(self->radius>>1, self->angle+ANG90, 40*FRACUNIT), self, self->target, PClass::FindActor ("IceGuyFX"));
|
||||
P_SpawnMissileXYZ(self->Vec3Angle(self->radius>>1, self->angle-ANG90, 40*FRACUNIT), self, self->target, PClass::FindActor ("IceGuyFX"));
|
||||
P_SpawnMissileXYZ(self->Vec3Angle(self->radius / 2, self->Angles.Yaw + 90, 40.), self, self->target, PClass::FindActor("IceGuyFX"));
|
||||
P_SpawnMissileXYZ(self->Vec3Angle(self->radius / 2, self->Angles.Yaw - 90, 40.), self, self->target, PClass::FindActor("IceGuyFX"));
|
||||
S_Sound (self, CHAN_WEAPON, self->AttackSound, 1, ATTN_NORM);
|
||||
return 0;
|
||||
}
|
||||
|
@ -110,10 +100,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_IceGuyDie)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->vel.x = 0;
|
||||
self->vel.y = 0;
|
||||
self->vel.z = 0;
|
||||
self->height = self->GetDefault()->height;
|
||||
self->Vel.Zero();
|
||||
self->Height = self->GetDefault()->Height;
|
||||
CALL_ACTION(A_FreezeDeathChunks, self);
|
||||
return 0;
|
||||
}
|
||||
|
@ -133,8 +121,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_IceGuyMissileExplode)
|
|||
|
||||
for (i = 0; i < 8; i++)
|
||||
{
|
||||
mo = P_SpawnMissileAngleZ (self, self->Z()+3*FRACUNIT,
|
||||
PClass::FindActor("IceGuyFX2"), i*ANG45, (fixed_t)(-0.3*FRACUNIT));
|
||||
mo = P_SpawnMissileAngleZ (self, self->Z()+3, PClass::FindActor("IceGuyFX2"), DAngle(i*45.), -0.3);
|
||||
if (mo)
|
||||
{
|
||||
mo->target = self->target;
|
||||
|
|
|
@ -37,18 +37,18 @@ const int KORAX_TID = 245;
|
|||
const int KORAX_FIRST_TELEPORT_TID = 248;
|
||||
const int KORAX_TELEPORT_TID = 249;
|
||||
|
||||
const int KORAX_DELTAANGLE = 85*ANGLE_1;
|
||||
const int KORAX_DELTAANGLE = 85;
|
||||
const int KORAX_ARM_EXTENSION_SHORT = 40;
|
||||
const int KORAX_ARM_EXTENSION_LONG = 55;
|
||||
|
||||
const int KORAX_ARM1_HEIGHT = 108*FRACUNIT;
|
||||
const int KORAX_ARM2_HEIGHT = 82*FRACUNIT;
|
||||
const int KORAX_ARM3_HEIGHT = 54*FRACUNIT;
|
||||
const int KORAX_ARM4_HEIGHT = 104*FRACUNIT;
|
||||
const int KORAX_ARM5_HEIGHT = 86*FRACUNIT;
|
||||
const int KORAX_ARM6_HEIGHT = 53*FRACUNIT;
|
||||
const int KORAX_ARM1_HEIGHT = 108;
|
||||
const int KORAX_ARM2_HEIGHT = 82;
|
||||
const int KORAX_ARM3_HEIGHT = 54;
|
||||
const int KORAX_ARM4_HEIGHT = 104;
|
||||
const int KORAX_ARM5_HEIGHT = 86;
|
||||
const int KORAX_ARM6_HEIGHT = 53;
|
||||
|
||||
const int KORAX_BOLT_HEIGHT = 48*FRACUNIT;
|
||||
const double KORAX_BOLT_HEIGHT = 48.;
|
||||
const int KORAX_BOLT_LIFETIME = 3;
|
||||
|
||||
|
||||
|
@ -76,8 +76,7 @@ void A_KBoltRaise (AActor *);
|
|||
|
||||
void KoraxFire (AActor *actor, PClassActor *type, int arm);
|
||||
void KSpiritInit (AActor *spirit, AActor *korax);
|
||||
AActor *P_SpawnKoraxMissile (fixed_t x, fixed_t y, fixed_t z,
|
||||
AActor *source, AActor *dest, PClassActor *type);
|
||||
AActor *P_SpawnKoraxMissile (const DVector3 &pos, AActor *source, AActor *dest, PClassActor *type);
|
||||
|
||||
extern void SpawnSpiritTail (AActor *spirit);
|
||||
|
||||
|
@ -99,7 +98,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_KoraxChase)
|
|||
spot = iterator.Next ();
|
||||
if (spot != NULL)
|
||||
{
|
||||
P_Teleport (self, spot->X(), spot->Y(), ONFLOORZ, spot->angle, TELF_SOURCEFOG | TELF_DESTFOG);
|
||||
P_Teleport (self, spot->PosAtZ(ONFLOORZ), spot->Angles.Yaw, TELF_SOURCEFOG | TELF_DESTFOG);
|
||||
}
|
||||
|
||||
P_StartScript (self, NULL, 249, NULL, NULL, 0, 0);
|
||||
|
@ -141,7 +140,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_KoraxChase)
|
|||
self->tracer = spot;
|
||||
if (spot)
|
||||
{
|
||||
P_Teleport (self, spot->X(), spot->Y(), ONFLOORZ, spot->angle, TELF_SOURCEFOG | TELF_DESTFOG);
|
||||
P_Teleport (self, spot->PosAtZ(ONFLOORZ), spot->Angles.Yaw, TELF_SOURCEFOG | TELF_DESTFOG);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -164,7 +163,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_KoraxBonePop)
|
|||
// Spawn 6 spirits equalangularly
|
||||
for (i = 0; i < 6; ++i)
|
||||
{
|
||||
mo = P_SpawnMissileAngle (self, PClass::FindActor("KoraxSpirit"), ANGLE_60*i, 5*FRACUNIT);
|
||||
mo = P_SpawnMissileAngle (self, PClass::FindActor("KoraxSpirit"), DAngle(60.*i), 5.);
|
||||
if (mo)
|
||||
{
|
||||
KSpiritInit (mo, self);
|
||||
|
@ -186,7 +185,7 @@ void KSpiritInit (AActor *spirit, AActor *korax)
|
|||
spirit->health = KORAX_SPIRIT_LIFETIME;
|
||||
|
||||
spirit->tracer = korax; // Swarm around korax
|
||||
spirit->special2 = FINEANGLES/2 + pr_kspiritinit(8 << BOBTOFINESHIFT); // Float bob index
|
||||
spirit->WeaveIndexZ = 32 + (pr_kspiritinit() & 7); // Float bob index
|
||||
spirit->args[0] = 10; // initial turn value
|
||||
spirit->args[1] = 0; // initial look angle
|
||||
|
||||
|
@ -235,23 +234,23 @@ DEFINE_ACTION_FUNCTION(AActor, A_KoraxMissile)
|
|||
{ "SerpentFX", "CentaurLeaderAttack" }
|
||||
};
|
||||
|
||||
int type = pr_koraxmissile()%6;
|
||||
int type = pr_koraxmissile() % 6;
|
||||
int i;
|
||||
PClassActor *info;
|
||||
|
||||
S_Sound (self, CHAN_VOICE, "KoraxAttack", 1, ATTN_NORM);
|
||||
S_Sound(self, CHAN_VOICE, "KoraxAttack", 1, ATTN_NORM);
|
||||
|
||||
info = PClass::FindActor(choices[type].type);
|
||||
if (info == NULL)
|
||||
{
|
||||
I_Error ("Unknown Korax missile: %s\n", choices[type].type);
|
||||
I_Error("Unknown Korax missile: %s\n", choices[type].type);
|
||||
}
|
||||
|
||||
// Fire all 6 missiles at once
|
||||
S_Sound (self, CHAN_WEAPON, choices[type].sound, 1, ATTN_NONE);
|
||||
S_Sound(self, CHAN_WEAPON, choices[type].sound, 1, ATTN_NONE);
|
||||
for (i = 0; i < 6; ++i)
|
||||
{
|
||||
KoraxFire (self, info, i);
|
||||
KoraxFire(self, info, i);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
@ -267,17 +266,14 @@ DEFINE_ACTION_FUNCTION(AActor, A_KoraxMissile)
|
|||
DEFINE_ACTION_FUNCTION(AActor, A_KoraxCommand)
|
||||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
angle_t ang;
|
||||
DAngle ang;
|
||||
int numcommands;
|
||||
|
||||
S_Sound (self, CHAN_VOICE, "KoraxCommand", 1, ATTN_NORM);
|
||||
|
||||
// Shoot stream of lightning to ceiling
|
||||
ang = (self->angle - ANGLE_90) >> ANGLETOFINESHIFT;
|
||||
fixedvec3 pos = self->Vec3Offset(
|
||||
KORAX_COMMAND_OFFSET * finecosine[ang],
|
||||
KORAX_COMMAND_OFFSET * finesine[ang],
|
||||
KORAX_COMMAND_HEIGHT*FRACUNIT);
|
||||
ang = self->Angles.Yaw - 90;
|
||||
DVector3 pos = self->Vec3Angle(KORAX_COMMAND_OFFSET, ang, KORAX_COMMAND_HEIGHT);
|
||||
Spawn("KoraxBolt", pos, ALLOW_REPLACE);
|
||||
|
||||
if (self->health <= (self->SpawnHealth() >> 1))
|
||||
|
@ -319,7 +315,7 @@ void KoraxFire (AActor *actor, PClassActor *type, int arm)
|
|||
KORAX_ARM_EXTENSION_LONG,
|
||||
KORAX_ARM_EXTENSION_LONG
|
||||
};
|
||||
static const fixed_t armheight[6] =
|
||||
static const int armheight[6] =
|
||||
{
|
||||
KORAX_ARM1_HEIGHT,
|
||||
KORAX_ARM2_HEIGHT,
|
||||
|
@ -329,40 +325,24 @@ void KoraxFire (AActor *actor, PClassActor *type, int arm)
|
|||
KORAX_ARM6_HEIGHT
|
||||
};
|
||||
|
||||
angle_t ang;
|
||||
|
||||
ang = (actor->angle + (arm < 3 ? -KORAX_DELTAANGLE : KORAX_DELTAANGLE)) >> ANGLETOFINESHIFT;
|
||||
fixedvec3 pos = actor->Vec3Offset(
|
||||
extension[arm] * finecosine[ang],
|
||||
extension[arm] * finesine[ang],
|
||||
-actor->floorclip + armheight[arm]);
|
||||
P_SpawnKoraxMissile (pos.x, pos.y, pos.z, actor, actor->target, type);
|
||||
DAngle ang = actor->Angles.Yaw + (arm < 3 ? -KORAX_DELTAANGLE : KORAX_DELTAANGLE);
|
||||
DVector3 pos = actor->Vec3Angle(extension[arm], ang, armheight[arm] - actor->Floorclip);
|
||||
P_SpawnKoraxMissile (pos, actor, actor->target, type);
|
||||
}
|
||||
|
||||
//============================================================================
|
||||
//
|
||||
// A_KSpiritWeave
|
||||
// [BL] Was identical to CHolyWeave so lets just use that
|
||||
//
|
||||
//============================================================================
|
||||
|
||||
void CHolyWeave (AActor *actor, FRandom &pr_random);
|
||||
|
||||
//============================================================================
|
||||
//
|
||||
// A_KSpiritSeeker
|
||||
//
|
||||
//============================================================================
|
||||
|
||||
void A_KSpiritSeeker (AActor *actor, angle_t thresh, angle_t turnMax)
|
||||
static void A_KSpiritSeeker (AActor *actor, DAngle thresh, DAngle turnMax)
|
||||
{
|
||||
int dir;
|
||||
int dist;
|
||||
angle_t delta;
|
||||
angle_t angle;
|
||||
DAngle delta;
|
||||
AActor *target;
|
||||
fixed_t newZ;
|
||||
fixed_t deltaZ;
|
||||
double newZ;
|
||||
double deltaZ;
|
||||
|
||||
target = actor->tracer;
|
||||
if (target == NULL)
|
||||
|
@ -372,7 +352,7 @@ void A_KSpiritSeeker (AActor *actor, angle_t thresh, angle_t turnMax)
|
|||
dir = P_FaceMobj (actor, target, &delta);
|
||||
if (delta > thresh)
|
||||
{
|
||||
delta >>= 1;
|
||||
delta /= 2;
|
||||
if(delta > turnMax)
|
||||
{
|
||||
delta = turnMax;
|
||||
|
@ -380,39 +360,33 @@ void A_KSpiritSeeker (AActor *actor, angle_t thresh, angle_t turnMax)
|
|||
}
|
||||
if(dir)
|
||||
{ // Turn clockwise
|
||||
actor->angle += delta;
|
||||
actor->Angles.Yaw += delta;
|
||||
}
|
||||
else
|
||||
{ // Turn counter clockwise
|
||||
actor->angle -= delta;
|
||||
actor->Angles.Yaw -= delta;
|
||||
}
|
||||
angle = actor->angle>>ANGLETOFINESHIFT;
|
||||
actor->vel.x = FixedMul (actor->Speed, finecosine[angle]);
|
||||
actor->vel.y = FixedMul (actor->Speed, finesine[angle]);
|
||||
actor->VelFromAngle();
|
||||
|
||||
if (!(level.time&15)
|
||||
|| actor->Z() > target->Z()+(target->GetDefault()->height)
|
||||
|| actor->Z() > target->Z() + target->GetDefault()->Height
|
||||
|| actor->Top() < target->Z())
|
||||
{
|
||||
newZ = target->Z()+((pr_kspiritseek()*target->GetDefault()->height)>>8);
|
||||
newZ = target->Z() + pr_kspiritseek() * target->GetDefault()->Height / 256;
|
||||
deltaZ = newZ-actor->Z();
|
||||
if (abs(deltaZ) > 15*FRACUNIT)
|
||||
|
||||
if (fabs(deltaZ) > 15)
|
||||
{
|
||||
if(deltaZ > 0)
|
||||
{
|
||||
deltaZ = 15*FRACUNIT;
|
||||
deltaZ = 15;
|
||||
}
|
||||
else
|
||||
{
|
||||
deltaZ = -15*FRACUNIT;
|
||||
deltaZ = -15;
|
||||
}
|
||||
}
|
||||
dist = actor->AproxDistance (target) / actor->Speed;
|
||||
if (dist < 1)
|
||||
{
|
||||
dist = 1;
|
||||
}
|
||||
actor->vel.z = deltaZ/dist;
|
||||
actor->Vel.Z = deltaZ + actor->DistanceBySpeed(target, actor->Speed);
|
||||
}
|
||||
return;
|
||||
}
|
||||
|
@ -436,10 +410,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_KSpiritRoam)
|
|||
{
|
||||
if (self->tracer)
|
||||
{
|
||||
A_KSpiritSeeker (self, self->args[0]*ANGLE_1,
|
||||
self->args[0]*ANGLE_1*2);
|
||||
A_KSpiritSeeker(self, (double)self->args[0], self->args[0] * 2.);
|
||||
}
|
||||
CHolyWeave(self, pr_kspiritweave);
|
||||
int xyspeed = (pr_kspiritweave() % 5);
|
||||
int zspeed = (pr_kspiritweave() % 5);
|
||||
A_Weave(self, xyspeed, zspeed, 4., 2.);
|
||||
|
||||
if (pr_kspiritroam()<50)
|
||||
{
|
||||
S_Sound (self, CHAN_VOICE, "SpiritActive", 1, ATTN_NONE);
|
||||
|
@ -477,14 +453,13 @@ DEFINE_ACTION_FUNCTION(AActor, A_KBoltRaise)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
AActor *mo;
|
||||
fixed_t z;
|
||||
|
||||
// Spawn a child upward
|
||||
z = self->Z() + KORAX_BOLT_HEIGHT;
|
||||
double z = self->Z() + KORAX_BOLT_HEIGHT;
|
||||
|
||||
if ((z + KORAX_BOLT_HEIGHT) < self->ceilingz)
|
||||
{
|
||||
mo = Spawn("KoraxBolt", self->X(), self->Y(), z, ALLOW_REPLACE);
|
||||
mo = Spawn("KoraxBolt", self->PosAtZ(z), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->special1 = KORAX_BOLT_LIFETIME;
|
||||
|
@ -503,30 +478,22 @@ DEFINE_ACTION_FUNCTION(AActor, A_KBoltRaise)
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
AActor *P_SpawnKoraxMissile (fixed_t x, fixed_t y, fixed_t z,
|
||||
AActor *source, AActor *dest, PClassActor *type)
|
||||
AActor *P_SpawnKoraxMissile (const DVector3 &pos, AActor *source, AActor *dest, PClassActor *type)
|
||||
{
|
||||
AActor *th;
|
||||
angle_t an;
|
||||
int dist;
|
||||
DAngle an;
|
||||
double dist;
|
||||
|
||||
z -= source->floorclip;
|
||||
th = Spawn (type, x, y, z, ALLOW_REPLACE);
|
||||
th = Spawn (type, source->PosPlusZ(-source->Floorclip), ALLOW_REPLACE);
|
||||
th->target = source; // Originator
|
||||
an = th->AngleTo(dest);
|
||||
if (dest->flags & MF_SHADOW)
|
||||
{ // Invisible target
|
||||
an += pr_kmissile.Random2()<<21;
|
||||
an += pr_kmissile.Random2() * (45/256.);
|
||||
}
|
||||
th->angle = an;
|
||||
an >>= ANGLETOFINESHIFT;
|
||||
th->vel.x = FixedMul (th->Speed, finecosine[an]);
|
||||
th->vel.y = FixedMul (th->Speed, finesine[an]);
|
||||
dist = dest->AproxDistance (th) / th->Speed;
|
||||
if (dist < 1)
|
||||
{
|
||||
dist = 1;
|
||||
}
|
||||
th->vel.z = (dest->Z()-z+(30*FRACUNIT))/dist;
|
||||
th->Angles.Yaw = an;
|
||||
th->VelFromAngle();
|
||||
dist = dest->DistanceBySpeed(th, th->Speed);
|
||||
th->Vel.Z = (dest->Z() - pos.Z + 30) / dist;
|
||||
return (P_CheckMissileSpawn(th, source->radius) ? th : NULL);
|
||||
}
|
||||
|
|
|
@ -53,9 +53,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireConePL1)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
int slope;
|
||||
DAngle slope;
|
||||
int i;
|
||||
AActor *mo;
|
||||
bool conedone=false;
|
||||
|
@ -78,11 +78,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_FireConePL1)
|
|||
damage = 90+(pr_cone()&15);
|
||||
for (i = 0; i < 16; i++)
|
||||
{
|
||||
angle = self->angle+i*(ANG45/16);
|
||||
slope = P_AimLineAttack (self, angle, MELEERANGE, &t, 0, ALF_CHECK3D);
|
||||
angle = self->Angles.Yaw + i*(45./16);
|
||||
slope = P_AimLineAttack (self, angle, MELEERANGE, &t, 0., ALF_CHECK3D);
|
||||
if (t.linetarget)
|
||||
{
|
||||
P_DamageMobj (t.linetarget, self, self, damage, NAME_Ice, DMG_USEANGLE, t.angleFromSource);
|
||||
P_DamageMobj (t.linetarget, self, self, damage, NAME_Ice, DMG_USEANGLE, t.angleFromSource.Degrees);
|
||||
conedone = true;
|
||||
break;
|
||||
}
|
||||
|
@ -128,35 +128,35 @@ DEFINE_ACTION_FUNCTION(AActor, A_ShedShard)
|
|||
// every so many calls, spawn a new missile in its set directions
|
||||
if (spawndir & SHARDSPAWN_LEFT)
|
||||
{
|
||||
mo = P_SpawnMissileAngleZSpeed (self, self->Z(), RUNTIME_CLASS(AFrostMissile), self->angle+(ANG45/9),
|
||||
0, (20+2*spermcount)<<FRACBITS, self->target);
|
||||
mo = P_SpawnMissileAngleZSpeed(self, self->Z(), RUNTIME_CLASS(AFrostMissile),
|
||||
self->Angles.Yaw + 5, 0, (20. + 2 * spermcount), self->target);
|
||||
if (mo)
|
||||
{
|
||||
mo->special1 = SHARDSPAWN_LEFT;
|
||||
mo->special2 = spermcount;
|
||||
mo->vel.z = self->vel.z;
|
||||
mo->Vel.Z = self->Vel.Z;
|
||||
mo->args[0] = (spermcount==3)?2:0;
|
||||
}
|
||||
}
|
||||
if (spawndir & SHARDSPAWN_RIGHT)
|
||||
{
|
||||
mo = P_SpawnMissileAngleZSpeed (self, self->Z(), RUNTIME_CLASS(AFrostMissile), self->angle-(ANG45/9),
|
||||
0, (20+2*spermcount)<<FRACBITS, self->target);
|
||||
mo = P_SpawnMissileAngleZSpeed(self, self->Z(), RUNTIME_CLASS(AFrostMissile),
|
||||
self->Angles.Yaw - 5, 0, (20. + 2 * spermcount), self->target);
|
||||
if (mo)
|
||||
{
|
||||
mo->special1 = SHARDSPAWN_RIGHT;
|
||||
mo->special2 = spermcount;
|
||||
mo->vel.z = self->vel.z;
|
||||
mo->Vel.Z = self->Vel.Z;
|
||||
mo->args[0] = (spermcount==3)?2:0;
|
||||
}
|
||||
}
|
||||
if (spawndir & SHARDSPAWN_UP)
|
||||
{
|
||||
mo = P_SpawnMissileAngleZSpeed (self, self->Z()+8*FRACUNIT, RUNTIME_CLASS(AFrostMissile), self->angle,
|
||||
0, (15+2*spermcount)<<FRACBITS, self->target);
|
||||
mo = P_SpawnMissileAngleZSpeed(self, self->Z() + 8., RUNTIME_CLASS(AFrostMissile),
|
||||
self->Angles.Yaw, 0, (15. + 2 * spermcount), self->target);
|
||||
if (mo)
|
||||
{
|
||||
mo->vel.z = self->vel.z;
|
||||
mo->Vel.Z = self->Vel.Z;
|
||||
if (spermcount & 1) // Every other reproduction
|
||||
mo->special1 = SHARDSPAWN_UP | SHARDSPAWN_LEFT | SHARDSPAWN_RIGHT;
|
||||
else
|
||||
|
@ -167,11 +167,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_ShedShard)
|
|||
}
|
||||
if (spawndir & SHARDSPAWN_DOWN)
|
||||
{
|
||||
mo = P_SpawnMissileAngleZSpeed (self, self->Z()-4*FRACUNIT, RUNTIME_CLASS(AFrostMissile), self->angle,
|
||||
0, (15+2*spermcount)<<FRACBITS, self->target);
|
||||
mo = P_SpawnMissileAngleZSpeed(self, self->Z() - 4., RUNTIME_CLASS(AFrostMissile),
|
||||
self->Angles.Yaw, 0, (15. + 2 * spermcount), self->target);
|
||||
if (mo)
|
||||
{
|
||||
mo->vel.z = self->vel.z;
|
||||
mo->Vel.Z = self->Vel.Z;
|
||||
if (spermcount & 1) // Every other reproduction
|
||||
mo->special1 = SHARDSPAWN_DOWN | SHARDSPAWN_LEFT | SHARDSPAWN_RIGHT;
|
||||
else
|
||||
|
|
|
@ -14,7 +14,7 @@
|
|||
#include "g_level.h"
|
||||
*/
|
||||
|
||||
#define ZAGSPEED FRACUNIT
|
||||
#define ZAGSPEED 1.
|
||||
|
||||
static FRandom pr_lightningready ("LightningReady");
|
||||
static FRandom pr_lightningclip ("LightningClip");
|
||||
|
@ -42,8 +42,8 @@ int ALightning::SpecialMissileHit (AActor *thing)
|
|||
{
|
||||
if (thing->Mass != INT_MAX)
|
||||
{
|
||||
thing->vel.x += vel.x>>4;
|
||||
thing->vel.y += vel.y>>4;
|
||||
thing->Vel.X += Vel.X / 16;
|
||||
thing->Vel.Y += Vel.Y / 16;
|
||||
}
|
||||
if ((!thing->player && !(thing->flags2&MF2_BOSS))
|
||||
|| !(level.time&1))
|
||||
|
@ -161,7 +161,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightningClip)
|
|||
}
|
||||
else if (self->flags3 & MF3_CEILINGHUGGER)
|
||||
{
|
||||
self->SetZ(self->ceilingz-self->height);
|
||||
self->SetZ(self->ceilingz - self->Height);
|
||||
target = self->tracer;
|
||||
}
|
||||
if (self->flags3 & MF3_FLOORHUGGER)
|
||||
|
@ -170,19 +170,19 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightningClip)
|
|||
zigZag = pr_lightningclip();
|
||||
if((zigZag > 128 && self->special1 < 2) || self->special1 < -2)
|
||||
{
|
||||
P_ThrustMobj(self, self->angle+ANG90, ZAGSPEED);
|
||||
self->Thrust(self->Angles.Yaw + 90, ZAGSPEED);
|
||||
if(cMo)
|
||||
{
|
||||
P_ThrustMobj(cMo, self->angle+ANG90, ZAGSPEED);
|
||||
cMo->Thrust(self->Angles.Yaw + 90, ZAGSPEED);
|
||||
}
|
||||
self->special1++;
|
||||
}
|
||||
else
|
||||
{
|
||||
P_ThrustMobj(self, self->angle-ANG90, ZAGSPEED);
|
||||
self->Thrust(self->Angles.Yaw - 90, ZAGSPEED);
|
||||
if(cMo)
|
||||
{
|
||||
P_ThrustMobj(cMo, cMo->angle-ANG90, ZAGSPEED);
|
||||
cMo->Thrust(self->Angles.Yaw - 90, ZAGSPEED);
|
||||
}
|
||||
self->special1--;
|
||||
}
|
||||
|
@ -195,10 +195,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightningClip)
|
|||
}
|
||||
else
|
||||
{
|
||||
self->angle = self->AngleTo(target);
|
||||
self->vel.x = 0;
|
||||
self->vel.y = 0;
|
||||
P_ThrustMobj (self, self->angle, self->Speed>>1);
|
||||
self->Angles.Yaw = self->AngleTo(target);
|
||||
self->VelFromAngle(self->Speed / 2);
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
|
@ -217,7 +215,6 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightningZap)
|
|||
|
||||
PClassActor *lightning = PClass::FindActor(self->GetClass()->MissileName);
|
||||
AActor *mo;
|
||||
fixed_t deltaZ;
|
||||
|
||||
if (lightning == NULL)
|
||||
{
|
||||
|
@ -232,32 +229,18 @@ DEFINE_ACTION_FUNCTION(AActor, A_LightningZap)
|
|||
self->SetState (self->FindState(NAME_Death));
|
||||
return 0;
|
||||
}
|
||||
if (self->flags3 & MF3_FLOORHUGGER)
|
||||
{
|
||||
deltaZ = 10*FRACUNIT;
|
||||
}
|
||||
else
|
||||
{
|
||||
deltaZ = -10*FRACUNIT;
|
||||
}
|
||||
fixed_t xo = ((pr_zap() - 128)*self->radius / 256);
|
||||
fixed_t yo = ((pr_zap() - 128)*self->radius / 256);
|
||||
double deltaX = (pr_zap() - 128) * self->radius / 256;
|
||||
double deltaY = (pr_zap() - 128) * self->radius / 256;
|
||||
double deltaZ = (self->flags3 & MF3_FLOORHUGGER) ? 10 : -10;
|
||||
|
||||
mo = Spawn(lightning, self->Vec3Offset(xo, yo, deltaZ), ALLOW_REPLACE);
|
||||
mo = Spawn(lightning, self->Vec3Offset(deltaX, deltaY, deltaZ), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->lastenemy = self;
|
||||
mo->vel.x = self->vel.x;
|
||||
mo->vel.y = self->vel.y;
|
||||
mo->Vel.X = self->Vel.X;
|
||||
mo->Vel.Y = self->Vel.Y;
|
||||
mo->Vel.Z = (self->flags3 & MF3_FLOORHUGGER) ? 20 : -20;
|
||||
mo->target = self->target;
|
||||
if (self->flags3 & MF3_FLOORHUGGER)
|
||||
{
|
||||
mo->vel.z = 20*FRACUNIT;
|
||||
}
|
||||
else
|
||||
{
|
||||
mo->vel.z = -20*FRACUNIT;
|
||||
}
|
||||
}
|
||||
if ((self->flags3 & MF3_FLOORHUGGER) && pr_zapf() < 160)
|
||||
{
|
||||
|
@ -328,8 +311,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_ZapMimic)
|
|||
}
|
||||
else
|
||||
{
|
||||
self->vel.x = mo->vel.x;
|
||||
self->vel.y = mo->vel.y;
|
||||
self->Vel.X = mo->Vel.X;
|
||||
self->Vel.Y = mo->Vel.Y;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
|
@ -356,7 +339,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LastZap)
|
|||
if (mo)
|
||||
{
|
||||
mo->SetState (mo->FindState (NAME_Death));
|
||||
mo->vel.z = 40*FRACUNIT;
|
||||
mo->Vel.Z = 40;
|
||||
mo->Damage = NULL;
|
||||
}
|
||||
return 0;
|
||||
|
|
|
@ -64,7 +64,7 @@ class AMageStaffFX2 : public AActor
|
|||
DECLARE_CLASS(AMageStaffFX2, AActor)
|
||||
public:
|
||||
int SpecialMissileHit (AActor *victim);
|
||||
bool SpecialBlastHandling (AActor *source, fixed_t strength);
|
||||
bool SpecialBlastHandling (AActor *source, double strength);
|
||||
};
|
||||
|
||||
IMPLEMENT_CLASS (AMageStaffFX2)
|
||||
|
@ -81,7 +81,7 @@ int AMageStaffFX2::SpecialMissileHit (AActor *victim)
|
|||
return -1;
|
||||
}
|
||||
|
||||
bool AMageStaffFX2::SpecialBlastHandling (AActor *source, fixed_t strength)
|
||||
bool AMageStaffFX2::SpecialBlastHandling (AActor *source, double strength)
|
||||
{
|
||||
// Reflect to originator
|
||||
tracer = target;
|
||||
|
@ -97,13 +97,12 @@ bool AMageStaffFX2::SpecialBlastHandling (AActor *source, fixed_t strength)
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
void MStaffSpawn (AActor *pmo, angle_t angle, AActor *alttarget)
|
||||
void MStaffSpawn (AActor *pmo, DAngle angle, AActor *alttarget)
|
||||
{
|
||||
AActor *mo;
|
||||
FTranslatedLineTarget t;
|
||||
|
||||
mo = P_SpawnPlayerMissile (pmo, 0, 0, 8*FRACUNIT,
|
||||
RUNTIME_CLASS(AMageStaffFX2), angle, &t);
|
||||
mo = P_SpawnPlayerMissile (pmo, 0, 0, 8, RUNTIME_CLASS(AMageStaffFX2), angle, &t);
|
||||
if (mo)
|
||||
{
|
||||
mo->target = pmo;
|
||||
|
@ -124,7 +123,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MStaffAttack)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
player_t *player;
|
||||
FTranslatedLineTarget t;
|
||||
|
||||
|
@ -139,21 +138,21 @@ DEFINE_ACTION_FUNCTION(AActor, A_MStaffAttack)
|
|||
if (!weapon->DepleteAmmo (weapon->bAltFire))
|
||||
return 0;
|
||||
}
|
||||
angle = self->angle;
|
||||
angle = self->Angles.Yaw;
|
||||
|
||||
// [RH] Let's try and actually track what the player aimed at
|
||||
P_AimLineAttack (self, angle, PLAYERMISSILERANGE, &t, ANGLE_1*32);
|
||||
P_AimLineAttack (self, angle, PLAYERMISSILERANGE, &t, 32.);
|
||||
if (t.linetarget == NULL)
|
||||
{
|
||||
BlockCheckLine.x = self->X();
|
||||
BlockCheckLine.y = self->Y();
|
||||
BlockCheckLine.dx = -finesine[angle >> ANGLETOFINESHIFT];
|
||||
BlockCheckLine.dy = -finecosine[angle >> ANGLETOFINESHIFT];
|
||||
BlockCheckLine.dx = -angle.Sin();
|
||||
BlockCheckLine.dy = -angle.Cos();
|
||||
t.linetarget = P_BlockmapSearch (self, 10, FrontBlockCheck);
|
||||
}
|
||||
MStaffSpawn (self, angle, t.linetarget);
|
||||
MStaffSpawn (self, angle-ANGLE_1*5, t.linetarget);
|
||||
MStaffSpawn (self, angle+ANGLE_1*5, t.linetarget);
|
||||
MStaffSpawn (self, angle-5, t.linetarget);
|
||||
MStaffSpawn (self, angle+5, t.linetarget);
|
||||
S_Sound (self, CHAN_WEAPON, "MageStaffFire", 1, ATTN_NORM);
|
||||
weapon->MStaffCount = 3;
|
||||
return 0;
|
||||
|
@ -194,7 +193,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MStaffTrack)
|
|||
{
|
||||
self->tracer = P_RoughMonsterSearch (self, 10, true);
|
||||
}
|
||||
P_SeekerMissile (self, ANGLE_1*2, ANGLE_1*10);
|
||||
P_SeekerMissile(self, 2, 10);
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -214,7 +213,7 @@ static AActor *FrontBlockCheck (AActor *mo, int index, void *)
|
|||
{
|
||||
if (link->Me != mo)
|
||||
{
|
||||
if (P_PointOnDivlineSide (link->Me->X(), link->Me->Y(), &BlockCheckLine) == 0 &&
|
||||
if (P_PointOnDivlineSide(link->Me->X(), link->Me->Y(), &BlockCheckLine) == 0 &&
|
||||
mo->IsOkayToAttack (link->Me))
|
||||
{
|
||||
return link->Me;
|
||||
|
@ -230,12 +229,11 @@ static AActor *FrontBlockCheck (AActor *mo, int index, void *)
|
|||
//
|
||||
//============================================================================
|
||||
|
||||
void MStaffSpawn2 (AActor *actor, angle_t angle)
|
||||
void MStaffSpawn2 (AActor *actor, DAngle angle)
|
||||
{
|
||||
AActor *mo;
|
||||
|
||||
mo = P_SpawnMissileAngleZ (actor, actor->Z()+40*FRACUNIT,
|
||||
RUNTIME_CLASS(AMageStaffFX2), angle, 0);
|
||||
mo = P_SpawnMissileAngleZ (actor, actor->Z()+40, RUNTIME_CLASS(AMageStaffFX2), angle, 0.);
|
||||
if (mo)
|
||||
{
|
||||
mo->target = actor;
|
||||
|
@ -257,11 +255,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_MageAttack)
|
|||
{
|
||||
return 0;
|
||||
}
|
||||
angle_t angle;
|
||||
angle = self->angle;
|
||||
MStaffSpawn2 (self, angle);
|
||||
MStaffSpawn2 (self, angle-ANGLE_1*5);
|
||||
MStaffSpawn2 (self, angle+ANGLE_1*5);
|
||||
S_Sound (self, CHAN_WEAPON, "MageStaffFire", 1, ATTN_NORM);
|
||||
DAngle angle = self->Angles.Yaw;
|
||||
MStaffSpawn2(self, angle);
|
||||
MStaffSpawn2(self, angle - 5);
|
||||
MStaffSpawn2(self, angle + 5);
|
||||
S_Sound(self, CHAN_WEAPON, "MageStaffFire", 1, ATTN_NORM);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -35,7 +35,7 @@ void APigPlayer::MorphPlayerThink ()
|
|||
{
|
||||
return;
|
||||
}
|
||||
if(!(vel.x | vel.y) && pr_pigplayerthink() < 64)
|
||||
if(Vel.X == 0 && Vel.Y == 0 && pr_pigplayerthink() < 64)
|
||||
{ // Snout sniff
|
||||
if (player->ReadyWeapon != NULL)
|
||||
{
|
||||
|
@ -60,9 +60,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_SnoutAttack)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int damage;
|
||||
int slope;
|
||||
DAngle slope;
|
||||
player_t *player;
|
||||
AActor *puff;
|
||||
FTranslatedLineTarget t;
|
||||
|
@ -73,7 +73,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SnoutAttack)
|
|||
}
|
||||
|
||||
damage = 3+(pr_snoutattack()&3);
|
||||
angle = player->mo->angle;
|
||||
angle = player->mo->Angles.Yaw;
|
||||
slope = P_AimLineAttack(player->mo, angle, MELEERANGE);
|
||||
puff = P_LineAttack(player->mo, angle, MELEERANGE, slope, damage, NAME_Melee, "SnoutPuff", true, &t);
|
||||
S_Sound(player->mo, CHAN_VOICE, "PigActive", 1, ATTN_NORM);
|
||||
|
@ -101,7 +101,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_PigPain)
|
|||
CALL_ACTION(A_Pain, self);
|
||||
if (self->Z() <= self->floorz)
|
||||
{
|
||||
self->vel.z = FRACUNIT*7/2;
|
||||
self->Vel.Z = 3.5;
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -28,7 +28,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentUnHide)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->renderflags &= ~RF_INVISIBLE;
|
||||
self->floorclip = 24*FRACUNIT;
|
||||
self->Floorclip = 24;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -43,7 +43,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentHide)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->renderflags |= RF_INVISIBLE;
|
||||
self->floorclip = 0;
|
||||
self->Floorclip = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -58,7 +58,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentRaiseHump)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->floorclip -= 4*FRACUNIT;
|
||||
self->Floorclip -= 4;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -72,7 +72,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentLowerHump)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->floorclip += 4*FRACUNIT;
|
||||
self->Floorclip += 4;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -228,17 +228,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_SerpentSpawnGibs)
|
|||
|
||||
for (int i = countof(GibTypes)-1; i >= 0; --i)
|
||||
{
|
||||
fixedvec2 pos = self->Vec2Offset(
|
||||
((pr_serpentgibs() - 128) << 12),
|
||||
((pr_serpentgibs() - 128) << 12));
|
||||
double x = (pr_serpentgibs() - 128) / 16.;
|
||||
double y = (pr_serpentgibs() - 128) / 16.;
|
||||
|
||||
mo = Spawn (GibTypes[i], pos.x, pos.y,
|
||||
self->floorz+FRACUNIT, ALLOW_REPLACE);
|
||||
mo = Spawn (GibTypes[i], self->Vec2OffsetZ(x, y, self->floorz + 1), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->vel.x = (pr_serpentgibs()-128)<<6;
|
||||
mo->vel.y = (pr_serpentgibs()-128)<<6;
|
||||
mo->floorclip = 6*FRACUNIT;
|
||||
mo->Vel.X = (pr_serpentgibs() - 128) / 1024.f;
|
||||
mo->Vel.Y = (pr_serpentgibs() - 128) / 1024.f;
|
||||
mo->Floorclip = 6;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
|
@ -254,7 +252,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FloatGib)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->floorclip -= FRACUNIT;
|
||||
self->Floorclip -= 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -268,7 +266,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_SinkGib)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->floorclip += FRACUNIT;
|
||||
self->Floorclip += 1;;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
|
|
@ -82,7 +82,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ThrustInitUp)
|
|||
|
||||
self->special2 = 5; // Raise speed
|
||||
self->args[0] = 1; // Mark as up
|
||||
self->floorclip = 0;
|
||||
self->Floorclip = 0;
|
||||
self->flags = MF_SOLID;
|
||||
self->flags2 = MF2_NOTELEPORT|MF2_FLOORCLIP;
|
||||
self->special1 = 0L;
|
||||
|
@ -95,7 +95,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ThrustInitDn)
|
|||
|
||||
self->special2 = 5; // Raise speed
|
||||
self->args[0] = 0; // Mark as down
|
||||
self->floorclip = self->GetDefault()->height;
|
||||
self->Floorclip = self->GetDefault()->Height;
|
||||
self->flags = 0;
|
||||
self->flags2 = MF2_NOTELEPORT|MF2_FLOORCLIP;
|
||||
self->renderflags = RF_INVISIBLE;
|
||||
|
@ -111,7 +111,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ThrustRaise)
|
|||
|
||||
AThrustFloor *actor = static_cast<AThrustFloor *>(self);
|
||||
|
||||
if (A_RaiseMobj (actor, self->special2*FRACUNIT))
|
||||
if (A_RaiseMobj (actor, self->special2))
|
||||
{ // Reached it's target height
|
||||
actor->args[0] = 1;
|
||||
if (actor->args[1])
|
||||
|
@ -121,7 +121,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ThrustRaise)
|
|||
}
|
||||
|
||||
// Lose the dirt clump
|
||||
if ((actor->floorclip < actor->height) && actor->DirtClump)
|
||||
if ((actor->Floorclip < actor->Height) && actor->DirtClump)
|
||||
{
|
||||
actor->DirtClump->Destroy ();
|
||||
actor->DirtClump = NULL;
|
||||
|
@ -138,7 +138,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_ThrustLower)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
if (A_SinkMobj (self, 6*FRACUNIT))
|
||||
if (A_SinkMobj (self, 6))
|
||||
{
|
||||
self->args[0] = 0;
|
||||
if (self->args[1])
|
||||
|
@ -160,8 +160,8 @@ DEFINE_ACTION_FUNCTION(AActor, A_ThrustImpale)
|
|||
FMultiBlockThingsIterator::CheckResult cres;
|
||||
while (it.Next(&cres))
|
||||
{
|
||||
fixed_t blockdist = self->radius + cres.thing->radius;
|
||||
if (abs(cres.thing->X() - cres.position.x) >= blockdist || abs(cres.thing->Y() - cres.position.y) >= blockdist)
|
||||
double blockdist = self->radius + cres.thing->radius;
|
||||
if (fabs(cres.thing->X() - cres.Position.X) >= blockdist || fabs(cres.thing->Y() - cres.Position.Y) >= blockdist)
|
||||
continue;
|
||||
|
||||
// Q: Make this z-aware for everything? It never was before.
|
||||
|
|
|
@ -36,7 +36,7 @@ bool AArtiDarkServant::Use (bool pickup)
|
|||
{
|
||||
mo->target = Owner;
|
||||
mo->tracer = Owner;
|
||||
mo->vel.z = 5*FRACUNIT;
|
||||
mo->Vel.Z = 5;
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
@ -53,13 +53,13 @@ DEFINE_ACTION_FUNCTION(AActor, A_Summon)
|
|||
|
||||
AMinotaurFriend *mo;
|
||||
|
||||
mo = Spawn<AMinotaurFriend> (self->Pos(), ALLOW_REPLACE);
|
||||
mo = Spawn<AMinotaurFriend>(self->Pos(), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
if (P_TestMobjLocation(mo) == false || !self->tracer)
|
||||
{ // Didn't fit - change back to artifact
|
||||
mo->Destroy ();
|
||||
AActor *arti = Spawn<AArtiDarkServant> (self->Pos(), ALLOW_REPLACE);
|
||||
mo->Destroy();
|
||||
AActor *arti = Spawn<AArtiDarkServant>(self->Pos(), ALLOW_REPLACE);
|
||||
if (arti) arti->flags |= MF_DROPPED;
|
||||
return 0;
|
||||
}
|
||||
|
@ -72,14 +72,14 @@ DEFINE_ACTION_FUNCTION(AActor, A_Summon)
|
|||
else
|
||||
{
|
||||
mo->tracer = self->tracer; // Pointer to master
|
||||
AInventory *power = Spawn<APowerMinotaur> (0, 0, 0, NO_REPLACE);
|
||||
power->CallTryPickup (self->tracer);
|
||||
AInventory *power = Spawn<APowerMinotaur>();
|
||||
power->CallTryPickup(self->tracer);
|
||||
mo->SetFriendPlayer(self->tracer->player);
|
||||
}
|
||||
|
||||
// Make smoke puff
|
||||
Spawn ("MinotaurSmoke", self->Pos(), ALLOW_REPLACE);
|
||||
S_Sound (self, CHAN_VOICE, mo->ActiveSound, 1, ATTN_NORM);
|
||||
Spawn("MinotaurSmoke", self->Pos(), ALLOW_REPLACE);
|
||||
S_Sound(self, CHAN_VOICE, mo->ActiveSound, 1, ATTN_NORM);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -55,11 +55,9 @@ static void TeloSpawn (AActor *source, const char *type)
|
|||
if (fx)
|
||||
{
|
||||
fx->special1 = TELEPORT_LIFE; // Lifetime countdown
|
||||
fx->angle = source->angle;
|
||||
fx->Angles.Yaw = source->Angles.Yaw;
|
||||
fx->target = source->target;
|
||||
fx->vel.x = source->vel.x >> 1;
|
||||
fx->vel.y = source->vel.y >> 1;
|
||||
fx->vel.z = source->vel.z >> 1;
|
||||
fx->Vel = source->Vel / 2;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -166,14 +164,12 @@ int ATelOtherFX1::DoSpecialDamage (AActor *target, int damage, FName damagetype)
|
|||
|
||||
void P_TeleportToPlayerStarts (AActor *victim)
|
||||
{
|
||||
fixed_t destX,destY;
|
||||
angle_t destAngle;
|
||||
DVector3 dest;
|
||||
|
||||
FPlayerStart *start = G_PickPlayerStart(0, PPS_FORCERANDOM | PPS_NOBLOCKINGCHECK);
|
||||
destX = start->x;
|
||||
destY = start->y;
|
||||
destAngle = ANG45 * (start->angle/45);
|
||||
P_Teleport (victim, destX, destY, ONFLOORZ, destAngle, TELF_SOURCEFOG | TELF_DESTFOG);
|
||||
dest = start->pos;
|
||||
dest.Z = ONFLOORZ;
|
||||
P_Teleport (victim, dest, (double)start->angle, TELF_SOURCEFOG | TELF_DESTFOG);
|
||||
}
|
||||
|
||||
//===========================================================================
|
||||
|
@ -185,17 +181,15 @@ void P_TeleportToPlayerStarts (AActor *victim)
|
|||
void P_TeleportToDeathmatchStarts (AActor *victim)
|
||||
{
|
||||
unsigned int i, selections;
|
||||
fixed_t destX,destY;
|
||||
angle_t destAngle;
|
||||
DVector3 dest;
|
||||
|
||||
selections = deathmatchstarts.Size ();
|
||||
if (selections > 0)
|
||||
{
|
||||
i = pr_teledm() % selections;
|
||||
destX = deathmatchstarts[i].x;
|
||||
destY = deathmatchstarts[i].y;
|
||||
destAngle = ANG45 * (deathmatchstarts[i].angle/45);
|
||||
P_Teleport (victim, destX, destY, ONFLOORZ, destAngle, TELF_SOURCEFOG | TELF_DESTFOG);
|
||||
dest = deathmatchstarts[i].pos;
|
||||
dest.Z = ONFLOORZ;
|
||||
P_Teleport (victim, dest, (double)deathmatchstarts[i].angle, TELF_SOURCEFOG | TELF_DESTFOG);
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
@ -15,12 +15,6 @@ static FRandom pr_wraithfx2 ("WraithFX2");
|
|||
static FRandom pr_wraithfx3 ("WraithFX3");
|
||||
static FRandom pr_wraithfx4 ("WraithFX4");
|
||||
|
||||
//============================================================================
|
||||
// Wraith Variables
|
||||
//
|
||||
// special1 Internal index into floatbob
|
||||
//============================================================================
|
||||
|
||||
//============================================================================
|
||||
//
|
||||
// A_WraithInit
|
||||
|
@ -31,15 +25,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithInit)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->AddZ(48<<FRACBITS);
|
||||
self->AddZ(48);
|
||||
|
||||
// [RH] Make sure the wraith didn't go into the ceiling
|
||||
if (self->Top() > self->ceilingz)
|
||||
{
|
||||
self->SetZ(self->ceilingz - self->height);
|
||||
self->SetZ(self->ceilingz - self->Height);
|
||||
}
|
||||
|
||||
self->special1 = 0; // index into floatbob
|
||||
self->WeaveIndexZ = 0; // index into floatbob
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -57,7 +51,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithRaiseInit)
|
|||
self->flags2 &= ~MF2_NONSHOOTABLE;
|
||||
self->flags3 &= ~MF3_DONTBLAST;
|
||||
self->flags |= MF_SHOOTABLE|MF_SOLID;
|
||||
self->floorclip = self->height;
|
||||
self->Floorclip = self->Height;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -71,7 +65,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithRaise)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
if (A_RaiseMobj (self, 2*FRACUNIT))
|
||||
if (A_RaiseMobj (self, 2))
|
||||
{
|
||||
// Reached it's target height
|
||||
// [RH] Once a buried wraith is fully raised, it should be
|
||||
|
@ -119,7 +113,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithFX2)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
AActor *mo;
|
||||
angle_t angle;
|
||||
DAngle angle;
|
||||
int i;
|
||||
|
||||
for (i = 2; i; --i)
|
||||
|
@ -127,21 +121,17 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithFX2)
|
|||
mo = Spawn ("WraithFX2", self->Pos(), ALLOW_REPLACE);
|
||||
if(mo)
|
||||
{
|
||||
if (pr_wraithfx2 ()<128)
|
||||
angle = pr_wraithfx2() * (360 / 1024.f);
|
||||
if (pr_wraithfx2() >= 128)
|
||||
{
|
||||
angle = self->angle+(pr_wraithfx2()<<22);
|
||||
angle = -angle;
|
||||
}
|
||||
else
|
||||
{
|
||||
angle = self->angle-(pr_wraithfx2()<<22);
|
||||
}
|
||||
mo->vel.z = 0;
|
||||
mo->vel.x = FixedMul((pr_wraithfx2()<<7)+FRACUNIT,
|
||||
finecosine[angle>>ANGLETOFINESHIFT]);
|
||||
mo->vel.y = FixedMul((pr_wraithfx2()<<7)+FRACUNIT,
|
||||
finesine[angle>>ANGLETOFINESHIFT]);
|
||||
angle += self->Angles.Yaw;
|
||||
mo->Vel.X = ((pr_wraithfx2() << 7) + 1) * angle.Cos();
|
||||
mo->Vel.Y = ((pr_wraithfx2() << 7) + 1) * angle.Sin();
|
||||
mo->Vel.Z = 0;
|
||||
mo->target = self;
|
||||
mo->floorclip = 10*FRACUNIT;
|
||||
mo->Floorclip = 10;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
|
@ -160,15 +150,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithFX3)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
AActor *mo;
|
||||
int numdropped = pr_wraithfx3()%15;
|
||||
int numdropped = pr_wraithfx3() % 15;
|
||||
|
||||
while (numdropped-- > 0)
|
||||
{
|
||||
fixed_t xo = (pr_wraithfx3() - 128) << 11;
|
||||
fixed_t yo = (pr_wraithfx3() - 128) << 11;
|
||||
fixed_t zo = pr_wraithfx3() << 10;
|
||||
double xo = (pr_wraithfx3() - 128) / 32.;
|
||||
double yo = (pr_wraithfx3() - 128) / 32.;
|
||||
double zo = pr_wraithfx3() / 64.;
|
||||
|
||||
mo = Spawn ("WraithFX3", self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
mo = Spawn("WraithFX3", self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->floorz = self->floorz;
|
||||
|
@ -216,9 +206,9 @@ void A_WraithFX4 (AActor *self)
|
|||
|
||||
if (spawn4)
|
||||
{
|
||||
fixed_t xo = (pr_wraithfx4() - 128) << 12;
|
||||
fixed_t yo = (pr_wraithfx4() - 128) << 12;
|
||||
fixed_t zo = (pr_wraithfx4() << 10);
|
||||
double xo = (pr_wraithfx4() - 128) / 16.;
|
||||
double yo = (pr_wraithfx4() - 128) / 16.;
|
||||
double zo = (pr_wraithfx4() / 64.);
|
||||
|
||||
mo = Spawn ("WraithFX4", self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
|
@ -230,9 +220,9 @@ void A_WraithFX4 (AActor *self)
|
|||
}
|
||||
if (spawn5)
|
||||
{
|
||||
fixed_t xo = (pr_wraithfx4() - 128) << 11;
|
||||
fixed_t yo = (pr_wraithfx4() - 128) << 11;
|
||||
fixed_t zo = (pr_wraithfx4()<<10);
|
||||
double xo = (pr_wraithfx4() - 128) / 32.;
|
||||
double yo = (pr_wraithfx4() - 128) / 32.;
|
||||
double zo = (pr_wraithfx4() / 64.);
|
||||
|
||||
mo = Spawn ("WraithFX5", self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
|
@ -254,10 +244,10 @@ DEFINE_ACTION_FUNCTION(AActor, A_WraithChase)
|
|||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
int weaveindex = self->special1;
|
||||
self->AddZ(finesine[weaveindex << BOBTOFINESHIFT] * 8);
|
||||
self->special1 = (weaveindex + 2) & 63;
|
||||
// if (self->floorclip > 0)
|
||||
int weaveindex = self->WeaveIndexZ;
|
||||
self->AddZ(BobSin(weaveindex));
|
||||
self->WeaveIndexZ = (weaveindex + 2) & 63;
|
||||
// if (self->Floorclip > 0)
|
||||
// {
|
||||
// P_SetMobjState(self, S_WRAITH_RAISE2);
|
||||
// return;
|
||||
|
|
120
src/g_level.cpp
120
src/g_level.cpp
|
@ -1228,7 +1228,7 @@ void G_FinishTravel ()
|
|||
{
|
||||
Printf(TEXTCOLOR_RED "No player %d start to travel to!\n", pnum + 1);
|
||||
// Move to the coordinates this player had when they left the level.
|
||||
pawn->SetXYZ(pawndup->X(), pawndup->Y(), pawndup->Z());
|
||||
pawn->SetXYZ(pawndup->Pos());
|
||||
}
|
||||
}
|
||||
oldpawn = pawndup;
|
||||
|
@ -1240,13 +1240,10 @@ void G_FinishTravel ()
|
|||
{
|
||||
if (!(changeflags & CHANGELEVEL_KEEPFACING))
|
||||
{
|
||||
pawn->angle = pawndup->angle;
|
||||
pawn->pitch = pawndup->pitch;
|
||||
pawn->Angles = pawndup->Angles;
|
||||
}
|
||||
pawn->SetXYZ(pawndup->X(), pawndup->Y(), pawndup->Z());
|
||||
pawn->vel.x = pawndup->vel.x;
|
||||
pawn->vel.y = pawndup->vel.y;
|
||||
pawn->vel.z = pawndup->vel.z;
|
||||
pawn->SetXYZ(pawndup->Pos());
|
||||
pawn->Vel = pawndup->Vel;
|
||||
pawn->Sector = pawndup->Sector;
|
||||
pawn->floorz = pawndup->floorz;
|
||||
pawn->ceilingz = pawndup->ceilingz;
|
||||
|
@ -1256,7 +1253,7 @@ void G_FinishTravel ()
|
|||
pawn->floorterrain = pawndup->floorterrain;
|
||||
pawn->ceilingsector = pawndup->ceilingsector;
|
||||
pawn->ceilingpic = pawndup->ceilingpic;
|
||||
pawn->floorclip = pawndup->floorclip;
|
||||
pawn->Floorclip = pawndup->Floorclip;
|
||||
pawn->waterlevel = pawndup->waterlevel;
|
||||
}
|
||||
else
|
||||
|
@ -1316,7 +1313,7 @@ void G_InitLevelLocals ()
|
|||
NormalLight.ChangeColor (PalEntry (255, 255, 255), 0);
|
||||
|
||||
level.gravity = sv_gravity * 35/TICRATE;
|
||||
level.aircontrol = (fixed_t)(sv_aircontrol * 65536.f);
|
||||
level.aircontrol = sv_aircontrol;
|
||||
level.teamdamage = teamdamage;
|
||||
level.flags = 0;
|
||||
level.flags2 = 0;
|
||||
|
@ -1357,7 +1354,7 @@ void G_InitLevelLocals ()
|
|||
}
|
||||
if (info->aircontrol != 0.f)
|
||||
{
|
||||
level.aircontrol = (fixed_t)(info->aircontrol * 65536.f);
|
||||
level.aircontrol = info->aircontrol;
|
||||
}
|
||||
if (info->teamdamage != 0.f)
|
||||
{
|
||||
|
@ -1462,15 +1459,14 @@ FString CalcMapName (int episode, int level)
|
|||
|
||||
void G_AirControlChanged ()
|
||||
{
|
||||
if (level.aircontrol <= 256)
|
||||
if (level.aircontrol <= 1/256.)
|
||||
{
|
||||
level.airfriction = FRACUNIT;
|
||||
level.airfriction = 1.;
|
||||
}
|
||||
else
|
||||
{
|
||||
// Friction is inversely proportional to the amount of control
|
||||
float fric = ((float)level.aircontrol/65536.f) * -0.0941f + 1.0004f;
|
||||
level.airfriction = (fixed_t)(fric * 65536.f);
|
||||
level.airfriction = level.aircontrol * -0.0941 + 1.0004;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1497,26 +1493,11 @@ void G_SerializeLevel (FArchive &arc, bool hubLoad)
|
|||
<< level.maptime
|
||||
<< i;
|
||||
|
||||
if (SaveVersion >= 3313)
|
||||
{
|
||||
// This is a player property now
|
||||
int nextmusic;
|
||||
arc << nextmusic;
|
||||
}
|
||||
|
||||
// Hub transitions must keep the current total time
|
||||
if (!hubLoad)
|
||||
level.totaltime = i;
|
||||
|
||||
if (SaveVersion >= 4507)
|
||||
{
|
||||
arc << level.skytexture1 << level.skytexture2;
|
||||
}
|
||||
else
|
||||
{
|
||||
level.skytexture1 = TexMan.GetTexture(arc.ReadName(), FTexture::TEX_Wall, FTextureManager::TEXMAN_Overridable | FTextureManager::TEXMAN_ReturnFirst);
|
||||
level.skytexture2 = TexMan.GetTexture(arc.ReadName(), FTexture::TEX_Wall, FTextureManager::TEXMAN_Overridable | FTextureManager::TEXMAN_ReturnFirst);
|
||||
}
|
||||
arc << level.skytexture1 << level.skytexture2;
|
||||
if (arc.IsLoading())
|
||||
{
|
||||
sky1texture = level.skytexture1;
|
||||
|
@ -1557,12 +1538,7 @@ void G_SerializeLevel (FArchive &arc, bool hubLoad)
|
|||
P_SerializeSubsectors(arc);
|
||||
StatusBar->Serialize (arc);
|
||||
|
||||
if (SaveVersion >= 4222)
|
||||
{ // This must be done *after* thinkers are serialized.
|
||||
arc << level.DefaultSkybox;
|
||||
}
|
||||
|
||||
arc << level.total_monsters << level.total_items << level.total_secrets;
|
||||
arc << level.DefaultSkybox << level.total_monsters << level.total_items << level.total_secrets;
|
||||
|
||||
// Does this level have custom translations?
|
||||
FRemapTable *trans;
|
||||
|
@ -1792,8 +1768,6 @@ void G_WriteSnapshots (FILE *file)
|
|||
void G_ReadSnapshots (PNGHandle *png)
|
||||
{
|
||||
DWORD chunkLen;
|
||||
BYTE namelen;
|
||||
char mapname[256];
|
||||
FString MapName;
|
||||
level_info_t *i;
|
||||
|
||||
|
@ -1806,14 +1780,7 @@ void G_ReadSnapshots (PNGHandle *png)
|
|||
DWORD snapver;
|
||||
|
||||
arc << snapver;
|
||||
if (SaveVersion < 4508)
|
||||
{
|
||||
arc << namelen;
|
||||
arc.Read(mapname, namelen);
|
||||
mapname[namelen] = 0;
|
||||
MapName = mapname;
|
||||
}
|
||||
else arc << MapName;
|
||||
arc << MapName;
|
||||
i = FindLevelInfo (MapName);
|
||||
i->snapshotVer = snapver;
|
||||
i->snapshot = new FCompressedMemFile;
|
||||
|
@ -1828,14 +1795,7 @@ void G_ReadSnapshots (PNGHandle *png)
|
|||
DWORD snapver;
|
||||
|
||||
arc << snapver;
|
||||
if (SaveVersion < 4508)
|
||||
{
|
||||
arc << namelen;
|
||||
arc.Read(mapname, namelen);
|
||||
mapname[namelen] = 0;
|
||||
MapName = mapname;
|
||||
}
|
||||
else arc << MapName;
|
||||
arc << MapName;
|
||||
TheDefaultLevelInfo.snapshotVer = snapver;
|
||||
TheDefaultLevelInfo.snapshot = new FCompressedMemFile;
|
||||
TheDefaultLevelInfo.snapshot->Serialize (arc);
|
||||
|
@ -1846,25 +1806,10 @@ void G_ReadSnapshots (PNGHandle *png)
|
|||
{
|
||||
FPNGChunkArchive arc (png->File->GetFile(), VIST_ID, chunkLen);
|
||||
|
||||
if (SaveVersion < 4508)
|
||||
while (arc << MapName, MapName.Len() > 0)
|
||||
{
|
||||
arc << namelen;
|
||||
while (namelen != 0)
|
||||
{
|
||||
arc.Read(mapname, namelen);
|
||||
mapname[namelen] = 0;
|
||||
i = FindLevelInfo(mapname);
|
||||
i->flags |= LEVEL_VISITED;
|
||||
arc << namelen;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
while (arc << MapName, MapName.Len() > 0)
|
||||
{
|
||||
i = FindLevelInfo(MapName);
|
||||
i->flags |= LEVEL_VISITED;
|
||||
}
|
||||
i = FindLevelInfo(MapName);
|
||||
i->flags |= LEVEL_VISITED;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1960,8 +1905,6 @@ void P_WriteACSDefereds (FILE *file)
|
|||
|
||||
void P_ReadACSDefereds (PNGHandle *png)
|
||||
{
|
||||
BYTE namelen;
|
||||
char mapname[256];
|
||||
FString MapName;
|
||||
size_t chunklen;
|
||||
|
||||
|
@ -1971,33 +1914,14 @@ void P_ReadACSDefereds (PNGHandle *png)
|
|||
{
|
||||
FPNGChunkArchive arc (png->File->GetFile(), ACSD_ID, chunklen);
|
||||
|
||||
if (SaveVersion < 4508)
|
||||
while (arc << MapName, MapName.Len() > 0)
|
||||
{
|
||||
arc << namelen;
|
||||
while (namelen != 0)
|
||||
level_info_t *i = FindLevelInfo(MapName);
|
||||
if (i == NULL)
|
||||
{
|
||||
arc.Read(mapname, namelen);
|
||||
mapname[namelen] = 0;
|
||||
level_info_t *i = FindLevelInfo(mapname);
|
||||
if (i == NULL)
|
||||
{
|
||||
I_Error("Unknown map '%s' in savegame", mapname);
|
||||
}
|
||||
arc << i->defered;
|
||||
arc << namelen;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
while (arc << MapName, MapName.Len() > 0)
|
||||
{
|
||||
level_info_t *i = FindLevelInfo(MapName);
|
||||
if (i == NULL)
|
||||
{
|
||||
I_Error("Unknown map '%s' in savegame", MapName.GetChars());
|
||||
}
|
||||
arc << i->defered;
|
||||
I_Error("Unknown map '%s' in savegame", MapName.GetChars());
|
||||
}
|
||||
arc << i->defered;
|
||||
}
|
||||
}
|
||||
png->File->ResetFilePtr();
|
||||
|
|
|
@ -304,8 +304,8 @@ struct level_info_t
|
|||
DWORD outsidefog;
|
||||
int cdtrack;
|
||||
unsigned int cdid;
|
||||
float gravity;
|
||||
float aircontrol;
|
||||
double gravity;
|
||||
double aircontrol;
|
||||
int WarpTrans;
|
||||
int airsupply;
|
||||
DWORD compatflags, compatflags2;
|
||||
|
@ -329,7 +329,7 @@ struct level_info_t
|
|||
FString SoundInfo;
|
||||
FString SndSeq;
|
||||
|
||||
float teamdamage;
|
||||
double teamdamage;
|
||||
|
||||
FOptData optdata;
|
||||
FMusicMap MusicMap;
|
||||
|
@ -377,7 +377,7 @@ struct level_info_t
|
|||
// [RH] These get zeroed every tic and are updated by thinkers.
|
||||
struct FSectorScrollValues
|
||||
{
|
||||
fixed_t ScrollX, ScrollY;
|
||||
DVector2 Scroll;
|
||||
};
|
||||
|
||||
struct FLevelLocals
|
||||
|
@ -429,9 +429,9 @@ struct FLevelLocals
|
|||
int total_monsters;
|
||||
int killed_monsters;
|
||||
|
||||
float gravity;
|
||||
fixed_t aircontrol;
|
||||
fixed_t airfriction;
|
||||
double gravity;
|
||||
double aircontrol;
|
||||
double airfriction;
|
||||
int airsupply;
|
||||
int DefaultEnvironment; // Default sound environment.
|
||||
|
||||
|
@ -444,7 +444,7 @@ struct FLevelLocals
|
|||
|
||||
bool FromSnapshot; // The current map was restored from a snapshot
|
||||
|
||||
float teamdamage;
|
||||
double teamdamage;
|
||||
|
||||
bool IsJumpingAllowed() const;
|
||||
bool IsCrouchingAllowed() const;
|
||||
|
@ -545,28 +545,33 @@ void G_ClearHubInfo();
|
|||
|
||||
enum ESkillProperty
|
||||
{
|
||||
SKILLP_AmmoFactor,
|
||||
SKILLP_DropAmmoFactor,
|
||||
SKILLP_DamageFactor,
|
||||
SKILLP_FastMonsters,
|
||||
SKILLP_Respawn,
|
||||
SKILLP_RespawnLimit,
|
||||
SKILLP_Aggressiveness,
|
||||
SKILLP_DisableCheats,
|
||||
SKILLP_AutoUseHealth,
|
||||
SKILLP_SpawnFilter,
|
||||
SKILLP_EasyBossBrain,
|
||||
SKILLP_ACSReturn,
|
||||
SKILLP_MonsterHealth,
|
||||
SKILLP_FriendlyHealth,
|
||||
SKILLP_NoPain,
|
||||
SKILLP_ArmorFactor,
|
||||
SKILLP_HealthFactor,
|
||||
SKILLP_EasyKey,
|
||||
SKILLP_SlowMonsters,
|
||||
SKILLP_Infight,
|
||||
};
|
||||
enum EFSkillProperty // floating point properties
|
||||
{
|
||||
SKILLP_AmmoFactor,
|
||||
SKILLP_DropAmmoFactor,
|
||||
SKILLP_ArmorFactor,
|
||||
SKILLP_HealthFactor,
|
||||
SKILLP_DamageFactor,
|
||||
SKILLP_Aggressiveness,
|
||||
SKILLP_MonsterHealth,
|
||||
SKILLP_FriendlyHealth,
|
||||
};
|
||||
|
||||
int G_SkillProperty(ESkillProperty prop);
|
||||
double G_SkillProperty(EFSkillProperty prop);
|
||||
const char * G_SkillName();
|
||||
|
||||
typedef TMap<FName, FString> SkillMenuNames;
|
||||
|
@ -576,8 +581,11 @@ typedef TMap<FName, FName> SkillActorReplacement;
|
|||
struct FSkillInfo
|
||||
{
|
||||
FName Name;
|
||||
fixed_t AmmoFactor, DoubleAmmoFactor, DropAmmoFactor;
|
||||
fixed_t DamageFactor;
|
||||
double AmmoFactor, DoubleAmmoFactor, DropAmmoFactor;
|
||||
double DamageFactor;
|
||||
double ArmorFactor;
|
||||
double HealthFactor;
|
||||
|
||||
bool FastMonsters;
|
||||
bool SlowMonsters;
|
||||
bool DisableCheats;
|
||||
|
@ -587,7 +595,7 @@ struct FSkillInfo
|
|||
bool EasyKey;
|
||||
int RespawnCounter;
|
||||
int RespawnLimit;
|
||||
fixed_t Aggressiveness;
|
||||
double Aggressiveness;
|
||||
int SpawnFilter;
|
||||
int ACSReturn;
|
||||
FString MenuName;
|
||||
|
@ -599,12 +607,10 @@ struct FSkillInfo
|
|||
FString TextColor;
|
||||
SkillActorReplacement Replace;
|
||||
SkillActorReplacement Replaced;
|
||||
fixed_t MonsterHealth;
|
||||
fixed_t FriendlyHealth;
|
||||
double MonsterHealth;
|
||||
double FriendlyHealth;
|
||||
bool NoPain;
|
||||
int Infighting;
|
||||
fixed_t ArmorFactor;
|
||||
fixed_t HealthFactor;
|
||||
|
||||
FSkillInfo() {}
|
||||
FSkillInfo(const FSkillInfo &other)
|
||||
|
|
|
@ -989,14 +989,14 @@ DEFINE_MAP_OPTION(gravity, true)
|
|||
{
|
||||
parse.ParseAssign();
|
||||
parse.sc.MustGetFloat();
|
||||
info->gravity = float(parse.sc.Float);
|
||||
info->gravity = parse.sc.Float;
|
||||
}
|
||||
|
||||
DEFINE_MAP_OPTION(aircontrol, true)
|
||||
{
|
||||
parse.ParseAssign();
|
||||
parse.sc.MustGetFloat();
|
||||
info->aircontrol = float(parse.sc.Float);
|
||||
info->aircontrol = parse.sc.Float;
|
||||
}
|
||||
|
||||
DEFINE_MAP_OPTION(airsupply, true)
|
||||
|
@ -1150,7 +1150,7 @@ DEFINE_MAP_OPTION(teamdamage, true)
|
|||
{
|
||||
parse.ParseAssign();
|
||||
parse.sc.MustGetFloat();
|
||||
info->teamdamage = float(parse.sc.Float);
|
||||
info->teamdamage = parse.sc.Float;
|
||||
}
|
||||
|
||||
DEFINE_MAP_OPTION(mapbackground, true)
|
||||
|
|
|
@ -27,26 +27,24 @@ IMPLEMENT_CLASS (AArtiTeleport)
|
|||
|
||||
bool AArtiTeleport::Use (bool pickup)
|
||||
{
|
||||
fixed_t destX;
|
||||
fixed_t destY;
|
||||
angle_t destAngle;
|
||||
DVector3 dest;
|
||||
int destAngle;
|
||||
|
||||
if (deathmatch)
|
||||
{
|
||||
unsigned int selections = deathmatchstarts.Size ();
|
||||
unsigned int i = pr_tele() % selections;
|
||||
destX = deathmatchstarts[i].x;
|
||||
destY = deathmatchstarts[i].y;
|
||||
destAngle = ANG45 * (deathmatchstarts[i].angle/45);
|
||||
dest = deathmatchstarts[i].pos;
|
||||
destAngle = deathmatchstarts[i].angle;
|
||||
}
|
||||
else
|
||||
{
|
||||
FPlayerStart *start = G_PickPlayerStart(int(Owner->player - players));
|
||||
destX = start->x;
|
||||
destY = start->y;
|
||||
destAngle = ANG45 * (start->angle/45);
|
||||
dest = start->pos;
|
||||
destAngle = start->angle;
|
||||
}
|
||||
P_Teleport (Owner, destX, destY, ONFLOORZ, destAngle, TELF_SOURCEFOG | TELF_DESTFOG);
|
||||
dest.Z = ONFLOORZ;
|
||||
P_Teleport (Owner, dest, (double)destAngle, TELF_SOURCEFOG | TELF_DESTFOG);
|
||||
bool canlaugh = true;
|
||||
if (Owner->player->morphTics && (Owner->player->MorphStyle & MORPH_UNDOBYCHAOSDEVICE))
|
||||
{ // Teleporting away will undo any morph effects (pig)
|
||||
|
|
|
@ -161,7 +161,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk1)
|
|||
if ((player = self->target->player) != NULL &&
|
||||
player->mo == self->target)
|
||||
{ // Squish the player
|
||||
player->deltaviewheight = -16*FRACUNIT;
|
||||
player->deltaviewheight = -16;
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
|
@ -175,16 +175,15 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk1)
|
|||
//
|
||||
//----------------------------------------------------------------------------
|
||||
|
||||
#define MNTR_CHARGE_SPEED (13*FRACUNIT)
|
||||
#define MNTR_CHARGE_SPEED (13.)
|
||||
|
||||
DEFINE_ACTION_FUNCTION(AActor, A_MinotaurDecide)
|
||||
{
|
||||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
bool friendly = !!(self->flags5 & MF5_SUMMONEDMONSTER);
|
||||
angle_t angle;
|
||||
AActor *target;
|
||||
int dist;
|
||||
double dist;
|
||||
|
||||
target = self->target;
|
||||
if (!target)
|
||||
|
@ -195,11 +194,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurDecide)
|
|||
{
|
||||
S_Sound (self, CHAN_WEAPON, "minotaur/sight", 1, ATTN_NORM);
|
||||
}
|
||||
dist = self->AproxDistance (target);
|
||||
dist = self->Distance2D(target);
|
||||
if (target->Top() > self->Z()
|
||||
&& target->Top() < self->Top()
|
||||
&& dist < (friendly ? 16*64*FRACUNIT : 8*64*FRACUNIT)
|
||||
&& dist > 1*64*FRACUNIT
|
||||
&& dist < (friendly ? 16*64. : 8*64.)
|
||||
&& dist > 1*64.
|
||||
&& pr_minotaurdecide() < 150)
|
||||
{ // Charge attack
|
||||
// Don't call the state function right away
|
||||
|
@ -210,13 +209,11 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurDecide)
|
|||
self->flags2 |= MF2_INVULNERABLE;
|
||||
}
|
||||
A_FaceTarget (self);
|
||||
angle = self->angle>>ANGLETOFINESHIFT;
|
||||
self->vel.x = FixedMul (MNTR_CHARGE_SPEED, finecosine[angle]);
|
||||
self->vel.y = FixedMul (MNTR_CHARGE_SPEED, finesine[angle]);
|
||||
self->VelFromAngle(MNTR_CHARGE_SPEED);
|
||||
self->special1 = TICRATE/2; // Charge duration
|
||||
}
|
||||
else if (target->Z() == target->floorz
|
||||
&& dist < 9*64*FRACUNIT
|
||||
&& dist < 9*64.
|
||||
&& pr_minotaurdecide() < (friendly ? 100 : 220))
|
||||
{ // Floor fire attack
|
||||
self->SetState (self->FindState ("Hammer"));
|
||||
|
@ -260,7 +257,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurCharge)
|
|||
type = PClass::FindActor("PunchPuff");
|
||||
}
|
||||
puff = Spawn (type, self->Pos(), ALLOW_REPLACE);
|
||||
puff->vel.z = 2*FRACUNIT;
|
||||
puff->Vel.Z = 2;
|
||||
self->special1--;
|
||||
}
|
||||
else
|
||||
|
@ -285,9 +282,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk2)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
AActor *mo;
|
||||
angle_t angle;
|
||||
fixed_t vz;
|
||||
fixed_t z;
|
||||
DAngle angle;
|
||||
double vz;
|
||||
double z;
|
||||
bool friendly = !!(self->flags5 & MF5_SUMMONEDMONSTER);
|
||||
|
||||
if (self->target == NULL)
|
||||
|
@ -303,7 +300,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk2)
|
|||
P_TraceBleed (newdam > 0 ? newdam : damage, self->target, self);
|
||||
return 0;
|
||||
}
|
||||
z = self->Z() + 40*FRACUNIT;
|
||||
z = self->Z() + 40;
|
||||
PClassActor *fx = PClass::FindActor("MinotaurFX1");
|
||||
if (fx)
|
||||
{
|
||||
|
@ -311,12 +308,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk2)
|
|||
if (mo != NULL)
|
||||
{
|
||||
// S_Sound (mo, CHAN_WEAPON, "minotaur/attack2", 1, ATTN_NORM);
|
||||
vz = mo->vel.z;
|
||||
angle = mo->angle;
|
||||
P_SpawnMissileAngleZ (self, z, fx, angle-(ANG45/8), vz);
|
||||
P_SpawnMissileAngleZ (self, z, fx, angle+(ANG45/8), vz);
|
||||
P_SpawnMissileAngleZ (self, z, fx, angle-(ANG45/16), vz);
|
||||
P_SpawnMissileAngleZ (self, z, fx, angle+(ANG45/16), vz);
|
||||
vz = mo->Vel.Z;
|
||||
angle = mo->Angles.Yaw;
|
||||
P_SpawnMissileAngleZ (self, z, fx, angle-(45./8), vz);
|
||||
P_SpawnMissileAngleZ (self, z, fx, angle+(45./8), vz);
|
||||
P_SpawnMissileAngleZ (self, z, fx, angle-(45./16), vz);
|
||||
P_SpawnMissileAngleZ (self, z, fx, angle+(45./16), vz);
|
||||
}
|
||||
}
|
||||
return 0;
|
||||
|
@ -353,12 +350,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurAtk3)
|
|||
if ((player = self->target->player) != NULL &&
|
||||
player->mo == self->target)
|
||||
{ // Squish the player
|
||||
player->deltaviewheight = -16*FRACUNIT;
|
||||
player->deltaviewheight = -16;
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
if (self->floorclip > 0 && (i_compatflags & COMPATF_MINOTAUR))
|
||||
if (self->Floorclip > 0 && (i_compatflags & COMPATF_MINOTAUR))
|
||||
{
|
||||
// only play the sound.
|
||||
S_Sound (self, CHAN_WEAPON, "minotaur/fx2hit", 1, ATTN_NORM);
|
||||
|
@ -393,12 +390,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_MntrFloorFire)
|
|||
AActor *mo;
|
||||
|
||||
self->SetZ(self->floorz);
|
||||
fixedvec2 pos = self->Vec2Offset(
|
||||
(pr_fire.Random2 () << 10),
|
||||
(pr_fire.Random2 () << 10));
|
||||
mo = Spawn("MinotaurFX3", pos.x, pos.y, self->floorz, ALLOW_REPLACE);
|
||||
double x = pr_fire.Random2() / 64.;
|
||||
double y = pr_fire.Random2() / 64.;
|
||||
|
||||
mo = Spawn("MinotaurFX3", self->Vec2OffsetZ(x, y, self->floorz), ALLOW_REPLACE);
|
||||
mo->target = self->target;
|
||||
mo->vel.x = 1; // Force block checking
|
||||
mo->Vel.X = MinVel; // Force block checking
|
||||
P_CheckMissileSpawn (mo, self->radius);
|
||||
return 0;
|
||||
}
|
||||
|
@ -411,18 +408,16 @@ DEFINE_ACTION_FUNCTION(AActor, A_MntrFloorFire)
|
|||
|
||||
void P_MinotaurSlam (AActor *source, AActor *target)
|
||||
{
|
||||
angle_t angle;
|
||||
fixed_t thrust;
|
||||
DAngle angle;
|
||||
double thrust;
|
||||
int damage;
|
||||
|
||||
angle = source->AngleTo(target);
|
||||
angle >>= ANGLETOFINESHIFT;
|
||||
thrust = 16*FRACUNIT+(pr_minotaurslam()<<10);
|
||||
target->vel.x += FixedMul (thrust, finecosine[angle]);
|
||||
target->vel.y += FixedMul (thrust, finesine[angle]);
|
||||
thrust = 16 + pr_minotaurslam() / 64.;
|
||||
target->VelFromAngle(angle, thrust);
|
||||
damage = pr_minotaurslam.HitDice (static_cast<AMinotaur *>(source) ? 4 : 6);
|
||||
int newdam = P_DamageMobj (target, NULL, NULL, damage, NAME_Melee);
|
||||
P_TraceBleed (newdam > 0 ? newdam : damage, target, angle, 0);
|
||||
P_TraceBleed (newdam > 0 ? newdam : damage, target, angle, 0.);
|
||||
if (target->player)
|
||||
{
|
||||
target->reactiontime = 14+(pr_minotaurslam()&7);
|
||||
|
@ -491,7 +486,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurRoam)
|
|||
//
|
||||
// Look for enemy of player
|
||||
//----------------------------------------------------------------------------
|
||||
#define MINOTAUR_LOOK_DIST (16*54*FRACUNIT)
|
||||
#define MINOTAUR_LOOK_DIST (16*54.)
|
||||
|
||||
DEFINE_ACTION_FUNCTION(AActor, A_MinotaurLook)
|
||||
{
|
||||
|
@ -505,7 +500,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurLook)
|
|||
|
||||
AActor *mo = NULL;
|
||||
player_t *player;
|
||||
fixed_t dist;
|
||||
double dist;
|
||||
int i;
|
||||
AActor *master = self->tracer;
|
||||
|
||||
|
@ -519,7 +514,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurLook)
|
|||
mo = player->mo;
|
||||
if (mo == master) continue;
|
||||
if (mo->health <= 0) continue;
|
||||
dist = self->AproxDistance(mo);
|
||||
dist = self->Distance2D(mo);
|
||||
if (dist > MINOTAUR_LOOK_DIST) continue;
|
||||
self->target = mo;
|
||||
break;
|
||||
|
@ -544,7 +539,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_MinotaurLook)
|
|||
if (!(mo->flags3 & MF3_ISMONSTER)) continue;
|
||||
if (mo->health <= 0) continue;
|
||||
if (!(mo->flags & MF_SHOOTABLE)) continue;
|
||||
dist = self->AproxDistance(mo);
|
||||
dist = self->Distance2D(mo);
|
||||
if (dist > MINOTAUR_LOOK_DIST) continue;
|
||||
if ((mo == master) || (mo == self)) continue;
|
||||
if ((mo->flags5 & MF5_SUMMONEDMONSTER) && (mo->tracer == master)) continue;
|
||||
|
|
|
@ -63,7 +63,7 @@ void A_Unblock(AActor *self, bool drop)
|
|||
// [RH] Andy Baker's stealth monsters
|
||||
if (self->flags & MF_STEALTH)
|
||||
{
|
||||
self->alpha = OPAQUE;
|
||||
self->Alpha = 1.;
|
||||
self->visdir = 0;
|
||||
}
|
||||
|
||||
|
@ -142,7 +142,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_UnSetFloorClip)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->flags2 &= ~MF2_FLOORCLIP;
|
||||
self->floorclip = 0;
|
||||
self->Floorclip = 0;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -189,7 +189,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FreezeDeath)
|
|||
self->flags |= MF_SOLID|MF_SHOOTABLE|MF_NOBLOOD|MF_ICECORPSE;
|
||||
self->flags2 |= MF2_PUSHABLE|MF2_TELESTOMP|MF2_PASSMOBJ|MF2_SLIDE;
|
||||
self->flags3 |= MF3_CRASHED;
|
||||
self->height = self->GetDefault()->height;
|
||||
self->Height = self->GetDefault()->Height;
|
||||
// Remove fuzz effects from frozen actors.
|
||||
if (self->RenderStyle.BlendOp >= STYLEOP_Fuzz && self->RenderStyle.BlendOp <= STYLEOP_FuzzOrRevSub)
|
||||
{
|
||||
|
@ -201,7 +201,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_FreezeDeath)
|
|||
// [RH] Andy Baker's stealth monsters
|
||||
if (self->flags & MF_STEALTH)
|
||||
{
|
||||
self->alpha = OPAQUE;
|
||||
self->Alpha = 1;
|
||||
self->visdir = 0;
|
||||
}
|
||||
|
||||
|
@ -274,12 +274,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_FreezeDeathChunks)
|
|||
int numChunks;
|
||||
AActor *mo;
|
||||
|
||||
if ((self->vel.x || self->vel.y || self->vel.z) && !(self->flags6 & MF6_SHATTERING))
|
||||
if (!self->Vel.isZero() && !(self->flags6 & MF6_SHATTERING))
|
||||
{
|
||||
self->tics = 3*TICRATE;
|
||||
return 0;
|
||||
}
|
||||
self->vel.x = self->vel.y = self->vel.z = 0;
|
||||
self->Vel.Zero();
|
||||
S_Sound (self, CHAN_BODY, "misc/icebreak", 1, ATTN_NORM);
|
||||
|
||||
// [RH] In Hexen, this creates a random number of shards (range [24,56])
|
||||
|
@ -287,23 +287,24 @@ DEFINE_ACTION_FUNCTION(AActor, A_FreezeDeathChunks)
|
|||
// base the number of shards on the size of the dead thing, so bigger
|
||||
// things break up into more shards than smaller things.
|
||||
// An actor with radius 20 and height 64 creates ~40 chunks.
|
||||
numChunks = MAX<int> (4, (self->radius>>FRACBITS)*(self->height>>FRACBITS)/32);
|
||||
numChunks = MAX<int>(4, int(self->radius * self->Height)/32);
|
||||
i = (pr_freeze.Random2()) % (numChunks/4);
|
||||
for (i = MAX (24, numChunks + i); i >= 0; i--)
|
||||
{
|
||||
fixed_t xo = (((pr_freeze() - 128)*self->radius) >> 7);
|
||||
fixed_t yo = (((pr_freeze() - 128)*self->radius) >> 7);
|
||||
fixed_t zo = (pr_freeze()*self->height / 255);
|
||||
double xo = (pr_freeze() - 128)*self->radius / 128;
|
||||
double yo = (pr_freeze() - 128)*self->radius / 128;
|
||||
double zo = (pr_freeze()*self->Height / 255);
|
||||
|
||||
mo = Spawn("IceChunk", self->Vec3Offset(xo, yo, zo), ALLOW_REPLACE);
|
||||
if (mo)
|
||||
{
|
||||
mo->SetState (mo->SpawnState + (pr_freeze()%3));
|
||||
mo->vel.z = FixedDiv(mo->Z() - self->Z(), self->height)<<2;
|
||||
mo->vel.x = pr_freeze.Random2 () << (FRACBITS-7);
|
||||
mo->vel.y = pr_freeze.Random2 () << (FRACBITS-7);
|
||||
mo->SetState (mo->SpawnState + (pr_freeze()%3));
|
||||
mo->Vel.X = pr_freeze.Random2() / 128.;
|
||||
mo->Vel.Y = pr_freeze.Random2() / 128.;
|
||||
mo->Vel.Z = (mo->Z() - self->Z()) / self->Height * 4;
|
||||
CALL_ACTION(A_IceSetTics, mo); // set a random tic wait
|
||||
mo->RenderStyle = self->RenderStyle;
|
||||
mo->alpha = self->alpha;
|
||||
mo->Alpha = self->Alpha;
|
||||
}
|
||||
}
|
||||
if (self->player)
|
||||
|
@ -311,11 +312,12 @@ DEFINE_ACTION_FUNCTION(AActor, A_FreezeDeathChunks)
|
|||
AActor *head = Spawn("IceChunkHead", self->PosPlusZ(self->player->mo->ViewHeight), ALLOW_REPLACE);
|
||||
if (head != NULL)
|
||||
{
|
||||
head->vel.z = FixedDiv(head->Z() - self->Z(), self->height)<<2;
|
||||
head->vel.x = pr_freeze.Random2 () << (FRACBITS-7);
|
||||
head->vel.y = pr_freeze.Random2 () << (FRACBITS-7);
|
||||
head->Vel.X = pr_freeze.Random2() / 128.;
|
||||
head->Vel.Y = pr_freeze.Random2() / 128.;
|
||||
head->Vel.Z = (mo->Z() - self->Z()) / self->Height * 4;
|
||||
|
||||
head->health = self->health;
|
||||
head->angle = self->angle;
|
||||
head->Angles.Yaw = self->Angles.Yaw;
|
||||
if (head->IsKindOf(RUNTIME_CLASS(APlayerPawn)))
|
||||
{
|
||||
head->player = self->player;
|
||||
|
@ -323,9 +325,9 @@ DEFINE_ACTION_FUNCTION(AActor, A_FreezeDeathChunks)
|
|||
self->player = NULL;
|
||||
head->ObtainInventory (self);
|
||||
}
|
||||
head->pitch = 0;
|
||||
head->Angles.Pitch = 0.;
|
||||
head->RenderStyle = self->RenderStyle;
|
||||
head->alpha = self->alpha;
|
||||
head->Alpha = self->Alpha;
|
||||
if (head->player->camera == self)
|
||||
{
|
||||
head->player->camera = head;
|
||||
|
@ -611,7 +613,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_Gravity)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->flags &= ~MF_NOGRAVITY;
|
||||
self->gravity = FRACUNIT;
|
||||
self->Gravity = 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -626,7 +628,7 @@ DEFINE_ACTION_FUNCTION(AActor, A_LowGravity)
|
|||
PARAM_ACTION_PROLOGUE;
|
||||
|
||||
self->flags &= ~MF_NOGRAVITY;
|
||||
self->gravity = FRACUNIT/8;
|
||||
self->Gravity = 1. / 8;;
|
||||
return 0;
|
||||
}
|
||||
|
||||
|
@ -636,34 +638,33 @@ DEFINE_ACTION_FUNCTION(AActor, A_LowGravity)
|
|||
//
|
||||
//===========================================================================
|
||||
|
||||
void FaceMovementDirection (AActor *actor)
|
||||
void FaceMovementDirection(AActor *actor)
|
||||
{
|
||||
switch (actor->movedir)
|
||||
{
|
||||
case DI_EAST:
|
||||
actor->angle = 0<<24;
|
||||
actor->Angles.Yaw = 0.;
|
||||
break;
|
||||
case DI_NORTHEAST:
|
||||
actor->angle = 32<<24;
|
||||
actor->Angles.Yaw = 45.;
|
||||
break;
|
||||
case DI_NORTH:
|
||||
actor->angle = 64<<24;
|
||||
actor->Angles.Yaw = 90.;
|
||||
break;
|
||||
case DI_NORTHWEST:
|
||||
actor->angle = 96<<24;
|
||||
actor->Angles.Yaw = 135.;
|
||||
break;
|
||||
case DI_WEST:
|
||||
actor->angle = 128<<24;
|
||||
actor->Angles.Yaw = 180.;
|
||||
break;
|
||||
case DI_SOUTHWEST:
|
||||
actor->angle = 160<<24;
|
||||
actor->Angles.Yaw = 225.;
|
||||
break;
|
||||
case DI_SOUTH:
|
||||
actor->angle = 192<<24;
|
||||
actor->Angles.Yaw = 270.;
|
||||
break;
|
||||
case DI_SOUTHEAST:
|
||||
actor->angle = 224<<24;
|
||||
actor->Angles.Yaw = 315.;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -24,12 +24,7 @@ IMPLEMENT_CLASS (AHexenArmor)
|
|||
void ABasicArmor::Serialize (FArchive &arc)
|
||||
{
|
||||
Super::Serialize (arc);
|
||||
arc << SavePercent << BonusCount << MaxAbsorb << MaxFullAbsorb << AbsorbCount << ArmorType;
|
||||
|
||||
if (SaveVersion >= 4511)
|
||||
{
|
||||
arc << ActualSaveAmount;
|
||||
}
|
||||
arc << SavePercent << BonusCount << MaxAbsorb << MaxFullAbsorb << AbsorbCount << ArmorType << ActualSaveAmount;
|
||||
}
|
||||
|
||||
//===========================================================================
|
||||
|
@ -67,8 +62,8 @@ AInventory *ABasicArmor::CreateCopy (AActor *other)
|
|||
{
|
||||
// BasicArmor that is in use is stored in the inventory as BasicArmor.
|
||||
// BasicArmor that is in reserve is not.
|
||||
ABasicArmor *copy = Spawn<ABasicArmor> (0, 0, 0, NO_REPLACE);
|
||||
copy->SavePercent = SavePercent != 0 ? SavePercent : FRACUNIT/3;
|
||||
ABasicArmor *copy = Spawn<ABasicArmor> ();
|
||||
copy->SavePercent = SavePercent != 0 ? SavePercent : 0.33335; // slightly more than 1/3 to avoid roundoff errors.
|
||||
copy->Amount = Amount;
|
||||
copy->MaxAmount = MaxAmount;
|
||||
copy->Icon = Icon;
|
||||
|
@ -96,13 +91,13 @@ bool ABasicArmor::HandlePickup (AInventory *item)
|
|||
{
|
||||
ABasicArmorBonus *armor = static_cast<ABasicArmorBonus*>(item);
|
||||
|
||||
armor->SaveAmount = FixedMul(armor->SaveAmount, G_SkillProperty(SKILLP_ArmorFactor));
|
||||
armor->SaveAmount = int(armor->SaveAmount * G_SkillProperty(SKILLP_ArmorFactor));
|
||||
}
|
||||
else if (item->IsKindOf(RUNTIME_CLASS(ABasicArmorPickup)) && !(item->ItemFlags & IF_IGNORESKILL))
|
||||
{
|
||||
ABasicArmorPickup *armor = static_cast<ABasicArmorPickup*>(item);
|
||||
|
||||
armor->SaveAmount = FixedMul(armor->SaveAmount, G_SkillProperty(SKILLP_ArmorFactor));
|
||||
armor->SaveAmount = int(armor->SaveAmount * G_SkillProperty(SKILLP_ArmorFactor));
|
||||
}
|
||||
if (Inventory != NULL)
|
||||
{
|
||||
|
@ -130,7 +125,7 @@ void ABasicArmor::AbsorbDamage (int damage, FName damageType, int &newdamage)
|
|||
}
|
||||
else
|
||||
{
|
||||
saved = full + FixedMul (damage - full, SavePercent);
|
||||
saved = full + int((damage - full) * SavePercent);
|
||||
if (MaxAbsorb > 0 && saved + AbsorbCount > MaxAbsorb)
|
||||
{
|
||||
saved = MAX(0, MaxAbsorb - AbsorbCount);
|
||||
|
@ -179,15 +174,10 @@ void ABasicArmor::AbsorbDamage (int damage, FName damageType, int &newdamage)
|
|||
// This code is taken and adapted from APowerProtection::ModifyDamage().
|
||||
// The differences include not using a default value, and of course the way
|
||||
// the damage factor info is obtained.
|
||||
const fixed_t *pdf = NULL;
|
||||
DmgFactors *df = PClass::FindActor(ArmorType)->DamageFactors;
|
||||
if (df != NULL && df->CountUsed() != 0)
|
||||
if (df != NULL)
|
||||
{
|
||||
pdf = df->CheckFactor(damageType);
|
||||
if (pdf != NULL)
|
||||
{
|
||||
damage = newdamage = FixedMul(damage, *pdf);
|
||||
}
|
||||
damage = newdamage = df->Apply(damageType, damage);
|
||||
}
|
||||
}
|
||||
if (Inventory != NULL)
|
||||
|
@ -221,7 +211,7 @@ AInventory *ABasicArmorPickup::CreateCopy (AActor *other)
|
|||
|
||||
if (!(ItemFlags & IF_IGNORESKILL))
|
||||
{
|
||||
SaveAmount = FixedMul(SaveAmount, G_SkillProperty(SKILLP_ArmorFactor));
|
||||
SaveAmount = int(SaveAmount * G_SkillProperty(SKILLP_ArmorFactor));
|
||||
}
|
||||
|
||||
copy->SavePercent = SavePercent;
|
||||
|
@ -249,7 +239,7 @@ bool ABasicArmorPickup::Use (bool pickup)
|
|||
|
||||
if (armor == NULL)
|
||||
{
|
||||
armor = Spawn<ABasicArmor> (0,0,0, NO_REPLACE);
|
||||
armor = Spawn<ABasicArmor> ();
|
||||
armor->BecomeItem ();
|
||||
Owner->AddInventory (armor);
|
||||
}
|
||||
|
@ -303,7 +293,7 @@ AInventory *ABasicArmorBonus::CreateCopy (AActor *other)
|
|||
|
||||
if (!(ItemFlags & IF_IGNORESKILL))
|
||||
{
|
||||
SaveAmount = FixedMul(SaveAmount, G_SkillProperty(SKILLP_ArmorFactor));
|
||||
SaveAmount = int(SaveAmount * G_SkillProperty(SKILLP_ArmorFactor));
|
||||
}
|
||||
|
||||
copy->SavePercent = SavePercent;
|
||||
|
@ -332,7 +322,7 @@ bool ABasicArmorBonus::Use (bool pickup)
|
|||
|
||||
if (armor == NULL)
|
||||
{
|
||||
armor = Spawn<ABasicArmor> (0,0,0, NO_REPLACE);
|
||||
armor = Spawn<ABasicArmor> ();
|
||||
armor->BecomeItem ();
|
||||
armor->Amount = 0;
|
||||
armor->MaxAmount = MaxSaveAmount;
|
||||
|
@ -401,7 +391,7 @@ AInventory *AHexenArmor::CreateCopy (AActor *other)
|
|||
// Like BasicArmor, HexenArmor is used in the inventory but not the map.
|
||||
// health is the slot this armor occupies.
|
||||
// Amount is the quantity to give (0 = normal max).
|
||||
AHexenArmor *copy = Spawn<AHexenArmor> (0, 0, 0, NO_REPLACE);
|
||||
AHexenArmor *copy = Spawn<AHexenArmor> ();
|
||||
copy->AddArmorToSlot (other, health, Amount);
|
||||
GoAwayAndDie ();
|
||||
return copy;
|
||||
|
@ -452,7 +442,7 @@ bool AHexenArmor::HandlePickup (AInventory *item)
|
|||
bool AHexenArmor::AddArmorToSlot (AActor *actor, int slot, int amount)
|
||||
{
|
||||
APlayerPawn *ppawn;
|
||||
int hits;
|
||||
double hits;
|
||||
|
||||
if (actor->player != NULL)
|
||||
{
|
||||
|
@ -478,9 +468,9 @@ bool AHexenArmor::AddArmorToSlot (AActor *actor, int slot, int amount)
|
|||
}
|
||||
else
|
||||
{
|
||||
hits = amount * 5 * FRACUNIT;
|
||||
fixed_t total = Slots[0]+Slots[1]+Slots[2]+Slots[3]+Slots[4];
|
||||
fixed_t max = SlotsIncrement[0]+SlotsIncrement[1]+SlotsIncrement[2]+SlotsIncrement[3]+Slots[4]+4*5*FRACUNIT;
|
||||
hits = amount * 5;
|
||||
auto total = Slots[0] + Slots[1] + Slots[2] + Slots[3] + Slots[4];
|
||||
auto max = SlotsIncrement[0] + SlotsIncrement[1] + SlotsIncrement[2] + SlotsIncrement[3] + Slots[4] + 4 * 5;
|
||||
if (total < max)
|
||||
{
|
||||
Slots[slot] += hits;
|
||||
|
@ -500,13 +490,13 @@ void AHexenArmor::AbsorbDamage (int damage, FName damageType, int &newdamage)
|
|||
{
|
||||
if (!DamageTypeDefinition::IgnoreArmor(damageType))
|
||||
{
|
||||
fixed_t savedPercent = Slots[0] + Slots[1] + Slots[2] + Slots[3] + Slots[4];
|
||||
double savedPercent = Slots[0] + Slots[1] + Slots[2] + Slots[3] + Slots[4];
|
||||
|
||||
if (savedPercent)
|
||||
{ // armor absorbed some damage
|
||||
if (savedPercent > 100*FRACUNIT)
|
||||
if (savedPercent > 100)
|
||||
{
|
||||
savedPercent = 100*FRACUNIT;
|
||||
savedPercent = 100;
|
||||
}
|
||||
for (int i = 0; i < 4; i++)
|
||||
{
|
||||
|
@ -516,15 +506,8 @@ void AHexenArmor::AbsorbDamage (int damage, FName damageType, int &newdamage)
|
|||
// with the dragon skin bracers.
|
||||
if (damage < 10000)
|
||||
{
|
||||
#if __APPLE__ && __GNUC__ == 4 && __GNUC_MINOR__ == 2 && __GNUC_PATCHLEVEL__ == 1
|
||||
// -O1 optimizer bug work around. Only needed for
|
||||
// GCC 4.2.1 on OS X for 10.4/10.5 tools compatibility.
|
||||
volatile fixed_t tmp = 300;
|
||||
Slots[i] -= Scale (damage, SlotsIncrement[i], tmp);
|
||||
#else
|
||||
Slots[i] -= Scale (damage, SlotsIncrement[i], 300);
|
||||
#endif
|
||||
if (Slots[i] < 2*FRACUNIT)
|
||||
Slots[i] -= damage * SlotsIncrement[i] / 300.;
|
||||
if (Slots[i] < 2)
|
||||
{
|
||||
Slots[i] = 0;
|
||||
}
|
||||
|
@ -535,10 +518,10 @@ void AHexenArmor::AbsorbDamage (int damage, FName damageType, int &newdamage)
|
|||
}
|
||||
}
|
||||
}
|
||||
int saved = Scale (damage, savedPercent, 100*FRACUNIT);
|
||||
if (saved > savedPercent >> (FRACBITS-1))
|
||||
int saved = int(damage * savedPercent / 100.);
|
||||
if (saved > savedPercent*2)
|
||||
{
|
||||
saved = savedPercent >> (FRACBITS-1);
|
||||
saved = int(savedPercent*2);
|
||||
}
|
||||
newdamage -= saved;
|
||||
damage = newdamage;
|
||||
|
|
Some files were not shown because too many files have changed in this diff Show more
Loading…
Reference in a new issue