- Fixed: The StrifePlayer couldn't obtain his default inventory because

APlayerPawn::GiveDefaultInventory gave him some HexenArmor even though
  he doesn't need it.
- Added custom blood type properties to DECORATE.
- Converted Blood to DECORATE and made some minor changes to the code
  in preparation for custom blood types.
- Converted the bot helper things to DECORATE.
- Added damage type specific crash states.


SVN r395 (trunk)
This commit is contained in:
Christoph Oelckers 2006-11-29 10:03:35 +00:00
parent 4467cd6563
commit 0ba809234e
20 changed files with 337 additions and 215 deletions

View file

@ -1,8 +1,19 @@
November 28, 2006 (Changes by Graf Zahl)
- Fixed: The StrifePlayer couldn't obtain his default inventory because
APlayerPawn::GiveDefaultInventory gave him some HexenArmor even though
he doesn't need it.
- Added custom blood type properties to DECORATE.
- Converted Blood to DECORATE and made some minor changes to the code
in preparation for custom blood types.
- Converted the bot helper things to DECORATE.
- Added damage type specific crash states.
November 28, 2006 November 28, 2006
- Started adding action function declarations to objects. - Started adding action function declarations to objects.
- Added integer constant declarations to objects. - Added integer constant declarations to objects.
- Added a simple symbol table to PClass. - Added a simple symbol table to PClass.
>>>>>>> .r394
November 27, 2006 (Changes by Graf Zahl) November 27, 2006 (Changes by Graf Zahl)
- Changed: When playing a shareware game no external WADs are loaded at all, - Changed: When playing a shareware game no external WADs are loaded at all,
not even zvox.wad or the skins directory. not even zvox.wad or the skins directory.
@ -3072,7 +3083,7 @@ February 10, 2005
as fast as their Doom counterparts. as fast as their Doom counterparts.
- Fixed: Strife auto-uses the best ammo first, not the worst. I got confused because - Fixed: Strife auto-uses the best ammo first, not the worst. I got confused because
in Strife ARM1 is the best armor, but in Doom it's ARM2 that is best. in Strife ARM1 is the best armor, but in Doom it's ARM2 that is best.
- Fixed: Strife does not double ammo at it's highest skill level. - Fixed: Strife does not double ammo at its highest skill level.
- New: Using Degnin Ore will drop it, similar to the Teleporter Beacon. - New: Using Degnin Ore will drop it, similar to the Teleporter Beacon.
- Fixed: In nightmare skill, every actor is spawned with a reactiontime of 0. This - Fixed: In nightmare skill, every actor is spawned with a reactiontime of 0. This
make's Strife's HE Grenades explode immediately, because they use their reactiontime make's Strife's HE Grenades explode immediately, because they use their reactiontime
@ -4793,7 +4804,7 @@ January 2, 2004
nearest integer when determining TexelLength instead of always round down. nearest integer when determining TexelLength instead of always round down.
- Fixed: Using an empty string with HUDMSG_TYPEON caused a crash. - Fixed: Using an empty string with HUDMSG_TYPEON caused a crash.
- Fixed: A buried wraith could enter its pain state while rising from the - Fixed: A buried wraith could enter its pain state while rising from the
ground and not properly finish raising, so it's bottom portion would remain ground and not properly finish raising, so its bottom portion would remain
clipped for the rest of its existance. clipped for the rest of its existance.
- Fixed: Using a switch to start a script on another map would not make the - Fixed: Using a switch to start a script on another map would not make the
switch switch. switch switch.
@ -5110,7 +5121,7 @@ November 1, 2003
- Changed the sector soundorg calculation so that it can't overflow. - Changed the sector soundorg calculation so that it can't overflow.
October 31, 2003 October 31, 2003
- Added Strife's Reaver. Aside from it's unknown flag, it should be fully - Added Strife's Reaver. Aside from its unknown flag, it should be fully
functional. functional.
- Added Strife's dagger-wielding fist. It has a chance of doing 0 damage, - Added Strife's dagger-wielding fist. It has a chance of doing 0 damage,
which seems odd. which seems odd.
@ -7633,7 +7644,7 @@ August 3, 2002
July 31, 2002 July 31, 2002
- Fixed some stuff with local doors already performing a ceiling action. - Fixed some stuff with local doors already performing a ceiling action.
In particular, if the ceiling was moving but not as a door, it's thinker In particular, if the ceiling was moving but not as a door, its thinker
would be replaced with a door thinker instead of being left alone. would be replaced with a door thinker instead of being left alone.
- Wallrunning seems to be gone. I don't know when it disappeared. I - Wallrunning seems to be gone. I don't know when it disappeared. I
certainly set out trying to fix it. certainly set out trying to fix it.
@ -9579,7 +9590,7 @@ April 20, 2001
April 17, 2001 April 17, 2001
- Fixed: It was possible to stand at the very edge of a steep slope and not - Fixed: It was possible to stand at the very edge of a steep slope and not
fall off of it. It is still possible to "balance" by running away from the fall off of it. It is still possible to "balance" by running away from the
edge, but I think that will take more time to fix than it's work (especially edge, but I think that will take more time to fix than it's worth (especially
if I really do go ahead and rewrite the level geometry collision detection.) if I really do go ahead and rewrite the level geometry collision detection.)
- Added in-air friction that depends on aircontrol: The greater aircontrol is, - Added in-air friction that depends on aircontrol: The greater aircontrol is,
the more friction affects things. Only affects players. the more friction affects things. Only affects players.
@ -11247,7 +11258,7 @@ February 12, 2000
to find the following causes of the problem: 1. When monsters went up to find the following causes of the problem: 1. When monsters went up
steps, they didn't check to make sure there was nothing in the way above steps, they didn't check to make sure there was nothing in the way above
them. 2. When P_CheckOnmobj() found a monster's move to be blocked, the them. 2. When P_CheckOnmobj() found a monster's move to be blocked, the
monster could still float down inside the head of it's blocker, causing monster could still float down inside the head of its blocker, causing
the blocking monster to get stuck until it floated up again. the blocking monster to get stuck until it floated up again.
February 9, 2000 February 9, 2000
@ -11765,7 +11776,7 @@ July 7, 1999
removed the use of short ints. removed the use of short ints.
July 6, 1999 July 6, 1999
- Restored Cmd_Exec to it's 1.17c version. I'm not sure what I was trying to - Restored Cmd_Exec to its 1.17c version. I'm not sure what I was trying to
accomplish with the changes I made, but they broke it under certain accomplish with the changes I made, but they broke it under certain
situations. situations.
@ -13679,7 +13690,7 @@ May 19, 1998
starting with ';'. starting with ';'.
- Changed the default config file to zdoom.cfg and added the -config - Changed the default config file to zdoom.cfg and added the -config
parameter to choose alternate ones. (Blargh! Doom Legacy decided to parameter to choose alternate ones. (Blargh! Doom Legacy decided to
use config.cfg as it's default config file, when I've been using it use config.cfg as its default config file, when I've been using it
all along!) all along!)
May 18, 1998 May 18, 1998

View file

@ -173,6 +173,7 @@ enum
MF2_THRUGHOST = 0x00004000, // missile will pass through ghosts [RH] was 8 MF2_THRUGHOST = 0x00004000, // missile will pass through ghosts [RH] was 8
MF2_BOSS = 0x00008000, // mobj is a major boss MF2_BOSS = 0x00008000, // mobj is a major boss
MF2_DONTTRANSLATE = 0x00010000, // Don't apply palette translations
MF2_NODMGTHRUST = 0x00020000, // does not thrust target when damaging MF2_NODMGTHRUST = 0x00020000, // does not thrust target when damaging
MF2_TELESTOMP = 0x00040000, // mobj can stomp another MF2_TELESTOMP = 0x00040000, // mobj can stomp another
MF2_FLOATBOB = 0x00080000, // use float bobbing z movement MF2_FLOATBOB = 0x00080000, // use float bobbing z movement
@ -419,6 +420,9 @@ enum
AMETA_RDFactor, // Radius damage factor AMETA_RDFactor, // Radius damage factor
AMETA_CameraHeight, // Height of camera when used as such AMETA_CameraHeight, // Height of camera when used as such
AMETA_HowlSound, // Sound being played when electrocuted or poisoned AMETA_HowlSound, // Sound being played when electrocuted or poisoned
AMETA_BloodType, // Blood replacement type
AMETA_BloodType2, // Bloodsplatter replacement type
AMETA_BloodType3, // AxeBlood replacement type
}; };
// Map Object definition. // Map Object definition.
@ -589,6 +593,9 @@ public:
// What species am I? // What species am I?
virtual const PClass *GetSpecies(); virtual const PClass *GetSpecies();
// Enter the crash state
void Crash();
// Check for monsters that count as kill but excludes all friendlies. // Check for monsters that count as kill but excludes all friendlies.
bool CountsAsKill() const bool CountsAsKill() const
{ {

View file

@ -446,15 +446,6 @@ AActor *DCajunMaster::Find_enemy (AActor *bot)
} }
class ACajunBodyNode : public AActor
{
DECLARE_STATELESS_ACTOR (ACajunBodyNode, AActor)
};
IMPLEMENT_STATELESS_ACTOR (ACajunBodyNode, Any, -1, 0)
PROP_Flags (MF_NOSECTOR | MF_NOGRAVITY)
PROP_RenderFlags (RF_INVISIBLE)
END_DEFAULTS
//Creates a temporary mobj (invisible) at the given location. //Creates a temporary mobj (invisible) at the given location.
void DCajunMaster::SetBodyAt (fixed_t x, fixed_t y, fixed_t z, int hostnum) void DCajunMaster::SetBodyAt (fixed_t x, fixed_t y, fixed_t z, int hostnum)
@ -464,14 +455,14 @@ void DCajunMaster::SetBodyAt (fixed_t x, fixed_t y, fixed_t z, int hostnum)
if (body1) if (body1)
body1->SetOrigin (x, y, z); body1->SetOrigin (x, y, z);
else else
body1 = Spawn<ACajunBodyNode> (x, y, z, NO_REPLACE); body1 = Spawn ("ACajunBodyNode", x, y, z, NO_REPLACE);
} }
else if (hostnum == 2) else if (hostnum == 2)
{ {
if (body2) if (body2)
body2->SetOrigin (x, y, z); body2->SetOrigin (x, y, z);
else else
body2 = Spawn<ACajunBodyNode> (x, y, z, NO_REPLACE); body2 = Spawn ("ACajunBodyNode", x, y, z, NO_REPLACE);
} }
} }
@ -483,23 +474,11 @@ void DCajunMaster::SetBodyAt (fixed_t x, fixed_t y, fixed_t z, int hostnum)
//This function assumes actor->player->angle //This function assumes actor->player->angle
//has been set an is the main aiming angle. //has been set an is the main aiming angle.
class ACajunTrace : public AActor
{
DECLARE_STATELESS_ACTOR (ACajunTrace, AActor)
};
IMPLEMENT_STATELESS_ACTOR (ACajunTrace, Any, -1, 0)
PROP_SpeedFixed (12)
PROP_RadiusFixed (6)
PROP_HeightFixed (8)
PROP_Flags (MF_NOBLOCKMAP|MF_DROPOFF|MF_MISSILE|MF_NOGRAVITY)
PROP_Flags2 (MF2_NOTELEPORT)
END_DEFAULTS
//Emulates missile travel. Returns distance travelled. //Emulates missile travel. Returns distance travelled.
fixed_t DCajunMaster::FakeFire (AActor *source, AActor *dest, ticcmd_t *cmd) fixed_t DCajunMaster::FakeFire (AActor *source, AActor *dest, ticcmd_t *cmd)
{ {
AActor *th = Spawn<ACajunTrace> (source->x, source->y, source->z + 4*8*FRACUNIT, NO_REPLACE); AActor *th = Spawn ("CajunTrace", source->x, source->y, source->z + 4*8*FRACUNIT, NO_REPLACE);
th->target = source; // where it came from th->target = source; // where it came from

View file

@ -188,7 +188,7 @@ void A_DripBlood (AActor *actor)
x = actor->x + (pr_dripblood.Random2 () << 11); x = actor->x + (pr_dripblood.Random2 () << 11);
y = actor->y + (pr_dripblood.Random2 () << 11); y = actor->y + (pr_dripblood.Random2 () << 11);
mo = Spawn<ABlood> (x, y, actor->z, ALLOW_REPLACE); mo = Spawn ("Blood", x, y, actor->z, ALLOW_REPLACE);
mo->momx = pr_dripblood.Random2 () << 10; mo->momx = pr_dripblood.Random2 () << 10;
mo->momy = pr_dripblood.Random2 () << 10; mo->momy = pr_dripblood.Random2 () << 10;
mo->flags2 |= MF2_LOGRAV; mo->flags2 |= MF2_LOGRAV;

View file

@ -15,7 +15,6 @@
#define AXERANGE ((fixed_t)(2.25*MELEERANGE)) #define AXERANGE ((fixed_t)(2.25*MELEERANGE))
static FRandom pr_atk ("FAxeAtk"); static FRandom pr_atk ("FAxeAtk");
static FRandom pr_splat ("FAxeSplatter");
void A_FAxeCheckReady (AActor *actor); void A_FAxeCheckReady (AActor *actor);
void A_FAxeCheckUp (AActor *actor); void A_FAxeCheckUp (AActor *actor);
@ -192,34 +191,6 @@ IMPLEMENT_ACTOR (AAxePuffGlow, Hexen, -1, 0)
PROP_SpawnState (0) PROP_SpawnState (0)
END_DEFAULTS END_DEFAULTS
// Axe Blood ----------------------------------------------------------------
class AAxeBlood : public AActor
{
DECLARE_ACTOR (AAxeBlood, AActor)
};
FState AAxeBlood::States[] =
{
S_NORMAL (FAXE, 'F', 3, NULL , &States[1]),
S_NORMAL (FAXE, 'G', 3, NULL , &States[2]),
S_NORMAL (FAXE, 'H', 3, NULL , &States[3]),
S_NORMAL (FAXE, 'I', 3, NULL , &States[4]),
S_NORMAL (FAXE, 'J', 3, NULL , &States[5]),
S_NORMAL (FAXE, 'K', 3, NULL , NULL),
};
IMPLEMENT_ACTOR (AAxeBlood, Hexen, -1, 0)
PROP_Mass (5)
PROP_RadiusFixed (2)
PROP_HeightFixed (4)
PROP_Flags (MF_NOBLOCKMAP|MF_NOGRAVITY|MF_DROPOFF)
PROP_Flags2 (MF2_NOTELEPORT|MF2_CANNOTPUSH)
PROP_SpawnState (0)
PROP_DeathState (5)
END_DEFAULTS
//============================================================================ //============================================================================
// //
// A_FAxeCheckReady // A_FAxeCheckReady
@ -431,34 +402,3 @@ axedone:
return; return;
} }
//===========================================================================
//
// P_BloodSplatter2
//
//===========================================================================
void P_BloodSplatter2 (fixed_t x, fixed_t y, fixed_t z, AActor *originator)
{
PalEntry bloodcolor = (PalEntry)originator->GetClass()->Meta.GetMetaInt(AMETA_BloodColor);
if (cl_bloodtype <= 1)
{
AActor *mo;
x += ((pr_splat()-128)<<11);
y += ((pr_splat()-128)<<11);
mo = Spawn<AAxeBlood> (x, y, z, ALLOW_REPLACE);
mo->target = originator;
// colorize the blood!
if (bloodcolor != 0)
{
mo->Translation = TRANSLATION(TRANSLATION_Blood, bloodcolor.a);
}
}
if (cl_bloodtype >= 1)
{
P_DrawSplash2 (100, x, y, z, R_PointToAngle2 (0, 0, originator->x - x, originator->y - y), 2, bloodcolor);
}
}

View file

@ -33,13 +33,6 @@ class APatrolSpecial : public AActor
DECLARE_STATELESS_ACTOR (APatrolSpecial, AActor) DECLARE_STATELESS_ACTOR (APatrolSpecial, AActor)
}; };
class ABlood : public AActor
{
DECLARE_ACTOR (ABlood, AActor)
public:
void SetDamage (int damage);
};
class AMapSpot : public AActor class AMapSpot : public AActor
{ {
DECLARE_STATELESS_ACTOR (AMapSpot, AActor) DECLARE_STATELESS_ACTOR (AMapSpot, AActor)

View file

@ -41,66 +41,6 @@ IMPLEMENT_STATELESS_ACTOR (APatrolSpecial, Any, 9047, 0)
PROP_RenderStyle (STYLE_None) PROP_RenderStyle (STYLE_None)
END_DEFAULTS END_DEFAULTS
// Blood sprite - adjusts itself for each game -----------------------------
FState ABlood::States[] =
{
#define S_DBLOOD 0
S_NORMAL (BLUD, 'C', 8, NULL , &States[S_DBLOOD+1]),
S_NORMAL (BLUD, 'B', 8, NULL , &States[S_DBLOOD+2]),
S_NORMAL (BLUD, 'A', 8, NULL , NULL),
#define S_SBLOOD (S_DBLOOD+3)
S_NORMAL (SPRY, 'A', 3, NULL , &States[S_SBLOOD+1]),
S_NORMAL (SPRY, 'B', 3, NULL , &States[S_SBLOOD+2]),
S_NORMAL (SPRY, 'C', 3, NULL , &States[S_SBLOOD+3]),
S_NORMAL (SPRY, 'D', 3, NULL , &States[S_SBLOOD+4]),
S_NORMAL (SPRY, 'E', 3, NULL , &States[S_SBLOOD+5]),
S_NORMAL (SPRY, 'F', 3, NULL , &States[S_SBLOOD+6]),
S_NORMAL (SPRY, 'G', 2, NULL , NULL),
};
IMPLEMENT_ACTOR (ABlood, Any, -1, 130)
PROP_Flags (MF_NOBLOCKMAP)
PROP_Flags2 (MF2_NOTELEPORT)
PROP_SpawnState(S_DBLOOD)
PROP_Mass (5)
END_DEFAULTS
void ABlood::SetDamage (int damage)
{
if (gameinfo.gametype == GAME_Doom)
{
if (damage <= 12 && damage >= 9)
{
SetState (SpawnState + 1);
}
else if (damage < 9)
{
SetState (SpawnState + 2);
}
}
else if (gameinfo.gametype == GAME_Strife)
{
if (damage > 13)
{
SetState (&States[S_SBLOOD]);
}
else if (damage >= 10)
{
SetState (&States[S_DBLOOD]);
}
else if (damage >= 7)
{
SetState (&States[S_DBLOOD+1]);
}
else
{
SetState (&States[S_DBLOOD+2]);
}
}
}
// Map spot ---------------------------------------------------------------- // Map spot ----------------------------------------------------------------
IMPLEMENT_STATELESS_ACTOR (AMapSpot, Any, 9001, 0) IMPLEMENT_STATELESS_ACTOR (AMapSpot, Any, 9001, 0)

View file

@ -7,6 +7,17 @@ xx(Actor)
xx(Untranslated) xx(Untranslated)
xx(Doom)
xx(Heretic)
xx(Hexen)
xx(Strife)
// blood spawning
xx(Blood)
xx(BloodSplatter)
xx(AxeBlood)
xx(Spray)
// Invulnerability types // Invulnerability types
xx(Ghost) xx(Ghost)
xx(Reflective) xx(Reflective)

View file

@ -641,9 +641,11 @@ void AActor::Die (AActor *source, AActor *inflictor)
if ((health<gibhealth || flags4 & MF4_EXTREMEDEATH) && !(flags4 & MF4_NOEXTREMEDEATH)) if ((health<gibhealth || flags4 & MF4_EXTREMEDEATH) && !(flags4 & MF4_NOEXTREMEDEATH))
{ // Extreme death { // Extreme death
diestate = FindState (2, NAME_Death, NAME_Extreme); diestate = GetClass()->ActorInfo->FindStateExact (2, NAME_Death, NAME_Extreme);
// if a non-player mark as extremely dead for the crash state.
if (diestate != NULL && player == NULL && health >= gibhealth) health = gibhealth-1;
} }
else if (diestate == NULL)
{ // Normal death { // Normal death
diestate = FindState (NAME_Death); diestate = FindState (NAME_Death);
} }

View file

@ -305,7 +305,7 @@ void P_TraceBleed (int damage, fixed_t x, fixed_t y, fixed_t z, AActor *target,
void P_TraceBleed (int damage, AActor *target, angle_t angle, int pitch); void P_TraceBleed (int damage, AActor *target, angle_t angle, int pitch);
void P_TraceBleed (int damage, AActor *target, AActor *missile); // missile version void P_TraceBleed (int damage, AActor *target, AActor *missile); // missile version
void P_TraceBleed (int damage, AActor *target); // random direction version void P_TraceBleed (int damage, AActor *target); // random direction version
void P_RailAttack (AActor *source, int damage, int offset, int color1 = 0, int color2 = 0, float maxdiff = 0, bool silent = false); // [RH] Shoot a railgun void P_RailAttack (AActor *source, int damage, int offset, int color1 = 0, int color2 = 0, float maxdiff = 0, bool silent = false, FName puff = NAME_BulletPuff); // [RH] Shoot a railgun
bool P_HitFloor (AActor *thing); bool P_HitFloor (AActor *thing);
bool P_HitWater (AActor *thing, sector_t *sec); bool P_HitWater (AActor *thing, sector_t *sec);
bool P_CheckMissileSpawn (AActor *missile); bool P_CheckMissileSpawn (AActor *missile);

View file

@ -3010,7 +3010,7 @@ static bool ProcessRailHit (FTraceResults &res)
return true; return true;
} }
void P_RailAttack (AActor *source, int damage, int offset, int color1, int color2, float maxdiff, bool silent) void P_RailAttack (AActor *source, int damage, int offset, int color1, int color2, float maxdiff, bool silent, FName puff)
{ {
fixed_t vx, vy, vz; fixed_t vx, vy, vz;
angle_t angle, pitch; angle_t angle, pitch;
@ -3080,11 +3080,11 @@ void P_RailAttack (AActor *source, int damage, int offset, int color1, int color
} }
if (trace.CrossedWater) if (trace.CrossedWater)
{ {
AActor *puff = Spawn ("BulletPuff", 0, 0, 0, ALLOW_REPLACE); AActor *thepuff = Spawn ("BulletPuff", 0, 0, 0, ALLOW_REPLACE);
if (puff != NULL) if (thepuff != NULL)
{ {
SpawnDeepSplash (source, trace, puff, vx, vy, vz); SpawnDeepSplash (source, trace, thepuff, vx, vy, vz);
puff->Destroy (); thepuff->Destroy ();
} }
} }
@ -3102,7 +3102,8 @@ void P_RailAttack (AActor *source, int damage, int offset, int color1, int color
if ((RailHits[i].HitActor->flags & MF_NOBLOOD) || if ((RailHits[i].HitActor->flags & MF_NOBLOOD) ||
(RailHits[i].HitActor->flags2 & (MF2_DORMANT|MF2_INVULNERABLE))) (RailHits[i].HitActor->flags2 & (MF2_DORMANT|MF2_INVULNERABLE)))
{ {
P_SpawnPuff (PClass::FindClass(NAME_BulletPuff), x, y, z, source->angle - ANG180, 1, true); const PClass *puffclass = PClass::FindClass(puff);
if (puffclass != NULL) P_SpawnPuff (puffclass, x, y, z, source->angle - ANG180, 1, true);
} }
else else
{ {
@ -3939,18 +3940,22 @@ void P_DoCrunch (AActor *thing)
(!(thing->flags2&(MF2_INVULNERABLE|MF2_DORMANT)))) (!(thing->flags2&(MF2_INVULNERABLE|MF2_DORMANT))))
{ {
PalEntry bloodcolor = (PalEntry)thing->GetClass()->Meta.GetMetaInt(AMETA_BloodColor); PalEntry bloodcolor = (PalEntry)thing->GetClass()->Meta.GetMetaInt(AMETA_BloodColor);
const PClass *bloodcls = PClass::FindClass((ENamedName)thing->GetClass()->Meta.GetMetaInt(AMETA_BloodType, NAME_Blood));
P_TraceBleed (crushchange, thing); P_TraceBleed (crushchange, thing);
if (cl_bloodtype <= 1) if (cl_bloodtype <= 1 && bloodcls != NULL)
{ {
AActor *mo; AActor *mo;
mo = Spawn<ABlood> (thing->x, thing->y, mo = Spawn (bloodcls, thing->x, thing->y,
thing->z + thing->height/2, ALLOW_REPLACE); thing->z + thing->height/2, ALLOW_REPLACE);
mo->momx = pr_crunch.Random2 () << 12; mo->momx = pr_crunch.Random2 () << 12;
mo->momy = pr_crunch.Random2 () << 12; mo->momy = pr_crunch.Random2 () << 12;
if (bloodcolor!=0) mo->Translation = TRANSLATION(TRANSLATION_Blood, bloodcolor.a); if (bloodcolor != 0 && !(mo->flags2 & MF2_DONTTRANSLATE))
{
mo->Translation = TRANSLATION(TRANSLATION_Blood, bloodcolor.a);
}
} }
if (cl_bloodtype >= 1) if (cl_bloodtype >= 1)
{ {

View file

@ -92,6 +92,7 @@ static FRandom pr_spawnpuff ("SpawnPuff");
static FRandom pr_spawnblood ("SpawnBlood"); static FRandom pr_spawnblood ("SpawnBlood");
static FRandom pr_splatter ("BloodSplatter"); static FRandom pr_splatter ("BloodSplatter");
static FRandom pr_takedamage ("TakeDamage"); static FRandom pr_takedamage ("TakeDamage");
static FRandom pr_splat ("FAxeSplatter");
static FRandom pr_ripperblood ("RipperBlood"); static FRandom pr_ripperblood ("RipperBlood");
static FRandom pr_chunk ("Chunk"); static FRandom pr_chunk ("Chunk");
static FRandom pr_checkmissilespawn ("CheckMissileSpawn"); static FRandom pr_checkmissilespawn ("CheckMissileSpawn");
@ -1973,14 +1974,7 @@ void P_ZMovement (AActor *mo)
{ // The skull slammed into something { // The skull slammed into something
mo->momz = -mo->momz; mo->momz = -mo->momz;
} }
if ((mo->flags & MF_CORPSE) && mo->Crash();
!(mo->flags3 & MF3_CRASHED) &&
mo->DamageType != NAME_Ice)
{
FState * crashstate = mo->FindState(NAME_Crash);
if (crashstate != NULL) mo->SetState(crashstate);
mo->flags3 |= MF3_CRASHED;
}
} }
} }
@ -2847,14 +2841,7 @@ void AActor::Tick ()
} }
flags2 |= MF2_ONMOBJ; flags2 |= MF2_ONMOBJ;
momz = 0; momz = 0;
if ((flags & MF_CORPSE) && Crash();
!(flags3 & MF3_CRASHED) &&
DamageType != NAME_Ice)
{
FState * crashstate = FindState(NAME_Crash);
if (crashstate != NULL) SetState(crashstate);
flags3 |= MF3_CRASHED;
}
} }
} }
else else
@ -2867,14 +2854,7 @@ void AActor::Tick ()
} }
else if (z <= floorz) else if (z <= floorz)
{ {
if ((flags & MF_CORPSE) && Crash();
!(flags3 & MF3_CRASHED) &&
DamageType != NAME_Ice)
{
FState * crashstate = FindState(NAME_Crash);
if (crashstate != NULL) SetState(crashstate);
flags3 |= MF3_CRASHED;
}
} }
if (UpdateWaterLevel (oldz)) if (UpdateWaterLevel (oldz))
@ -3948,18 +3928,22 @@ AActor *P_SpawnPuff (const PClass *pufftype, fixed_t x, fixed_t y, fixed_t z, an
//---------------------------------------------------------------------------
// //
// P_SpawnBlood // P_SpawnBlood
// //
//---------------------------------------------------------------------------
void P_SpawnBlood (fixed_t x, fixed_t y, fixed_t z, angle_t dir, int damage, AActor *originator) void P_SpawnBlood (fixed_t x, fixed_t y, fixed_t z, angle_t dir, int damage, AActor *originator)
{ {
ABlood *th; AActor *th;
PalEntry bloodcolor = (PalEntry)originator->GetClass()->Meta.GetMetaInt(AMETA_BloodColor); PalEntry bloodcolor = (PalEntry)originator->GetClass()->Meta.GetMetaInt(AMETA_BloodColor);
const PClass *bloodcls = PClass::FindClass((ENamedName)originator->GetClass()->Meta.GetMetaInt(AMETA_BloodType, NAME_Blood));
if (cl_bloodtype <= 1) if (bloodcls!=NULL && cl_bloodtype <= 1)
{ {
z += pr_spawnblood.Random2 () << 10; z += pr_spawnblood.Random2 () << 10;
th = Spawn<ABlood> (x, y, z, ALLOW_REPLACE); th = Spawn (bloodcls, x, y, z, ALLOW_REPLACE);
th->momz = FRACUNIT*2; th->momz = FRACUNIT*2;
th->angle = dir; th->angle = dir;
if (gameinfo.gametype == GAME_Doom) if (gameinfo.gametype == GAME_Doom)
@ -3969,12 +3953,33 @@ void P_SpawnBlood (fixed_t x, fixed_t y, fixed_t z, angle_t dir, int damage, AAc
if (th->tics < 1) if (th->tics < 1)
th->tics = 1; th->tics = 1;
} }
// colorize the blood! // colorize the blood
if (bloodcolor != 0) if (bloodcolor != 0 && !(th->flags2 & MF2_DONTTRANSLATE))
{ {
th->Translation = TRANSLATION(TRANSLATION_Blood, bloodcolor.a); th->Translation = TRANSLATION(TRANSLATION_Blood, bloodcolor.a);
} }
th->SetDamage (damage);
// Moved out of the blood actor so that replacing blood is easier
if (gameinfo.gametype & GAME_DoomStrife)
{
if (gameinfo.gametype == GAME_Strife)
{
if (damage > 13)
{
FState *state = th->FindState(NAME_Spray);
if (state != NULL) th->SetState (state);
}
else damage+=2;
}
if (damage <= 12 && damage >= 9)
{
th->SetState (th->SpawnState + 1);
}
else if (damage < 9)
{
th->SetState (th->SpawnState + 2);
}
}
} }
if (cl_bloodtype >= 1) if (cl_bloodtype >= 1)
@ -3990,19 +3995,23 @@ void P_SpawnBlood (fixed_t x, fixed_t y, fixed_t z, angle_t dir, int damage, AAc
void P_BloodSplatter (fixed_t x, fixed_t y, fixed_t z, AActor *originator) void P_BloodSplatter (fixed_t x, fixed_t y, fixed_t z, AActor *originator)
{ {
PalEntry bloodcolor = (PalEntry)originator->GetClass()->Meta.GetMetaInt(AMETA_BloodColor); PalEntry bloodcolor = (PalEntry)originator->GetClass()->Meta.GetMetaInt(AMETA_BloodColor);
const PClass *bloodcls = PClass::FindClass((ENamedName)originator->GetClass()->Meta.GetMetaInt(AMETA_BloodType2, NAME_BloodSplatter));
if (cl_bloodtype <= 1) if (bloodcls!=NULL && cl_bloodtype <= 1)
{ {
AActor *mo; AActor *mo;
mo = Spawn("BloodSplatter", x, y, z, ALLOW_REPLACE); mo = Spawn(bloodcls, x, y, z, ALLOW_REPLACE);
mo->target = originator; mo->target = originator;
mo->momx = pr_splatter.Random2 () << 10; mo->momx = pr_splatter.Random2 () << 10;
mo->momy = pr_splatter.Random2 () << 10; mo->momy = pr_splatter.Random2 () << 10;
mo->momz = 3*FRACUNIT; mo->momz = 3*FRACUNIT;
// colorize the blood! // colorize the blood!
if (bloodcolor!=0) mo->Translation = TRANSLATION(TRANSLATION_Blood, bloodcolor.a); if (bloodcolor!=0 && !(mo->flags2 & MF2_DONTTRANSLATE))
{
mo->Translation = TRANSLATION(TRANSLATION_Blood, bloodcolor.a);
}
} }
if (cl_bloodtype >= 1) if (cl_bloodtype >= 1)
{ {
@ -4010,6 +4019,39 @@ void P_BloodSplatter (fixed_t x, fixed_t y, fixed_t z, AActor *originator)
} }
} }
//===========================================================================
//
// P_BloodSplatter2
//
//===========================================================================
void P_BloodSplatter2 (fixed_t x, fixed_t y, fixed_t z, AActor *originator)
{
PalEntry bloodcolor = (PalEntry)originator->GetClass()->Meta.GetMetaInt(AMETA_BloodColor);
const PClass *bloodcls = PClass::FindClass((ENamedName)originator->GetClass()->Meta.GetMetaInt(AMETA_BloodType3, NAME_AxeBlood));
if (bloodcls!=NULL && cl_bloodtype <= 1)
{
AActor *mo;
x += ((pr_splat()-128)<<11);
y += ((pr_splat()-128)<<11);
mo = Spawn (bloodcls, x, y, z, ALLOW_REPLACE);
mo->target = originator;
// colorize the blood!
if (bloodcolor != 0 && !(mo->flags2 & MF2_DONTTRANSLATE))
{
mo->Translation = TRANSLATION(TRANSLATION_Blood, bloodcolor.a);
}
}
if (cl_bloodtype >= 1)
{
P_DrawSplash2 (100, x, y, z, R_PointToAngle2 (0, 0, originator->x - x, originator->y - y), 2, bloodcolor);
}
}
//--------------------------------------------------------------------------- //---------------------------------------------------------------------------
// //
// PROC P_RipperBlood // PROC P_RipperBlood
@ -4020,14 +4062,15 @@ void P_RipperBlood (AActor *mo, AActor *bleeder)
{ {
fixed_t x, y, z; fixed_t x, y, z;
PalEntry bloodcolor = (PalEntry)bleeder->GetClass()->Meta.GetMetaInt(AMETA_BloodColor); PalEntry bloodcolor = (PalEntry)bleeder->GetClass()->Meta.GetMetaInt(AMETA_BloodColor);
const PClass *bloodcls = PClass::FindClass((ENamedName)bleeder->GetClass()->Meta.GetMetaInt(AMETA_BloodType, NAME_Blood));
x = mo->x + (pr_ripperblood.Random2 () << 12); x = mo->x + (pr_ripperblood.Random2 () << 12);
y = mo->y + (pr_ripperblood.Random2 () << 12); y = mo->y + (pr_ripperblood.Random2 () << 12);
z = mo->z + (pr_ripperblood.Random2 () << 12); z = mo->z + (pr_ripperblood.Random2 () << 12);
if (cl_bloodtype <= 1) if (bloodcls!=NULL && cl_bloodtype <= 1)
{ {
AActor *th; AActor *th;
th = Spawn<ABlood> (x, y, z, ALLOW_REPLACE); th = Spawn (bloodcls, x, y, z, ALLOW_REPLACE);
if (gameinfo.gametype == GAME_Heretic) if (gameinfo.gametype == GAME_Heretic)
th->flags |= MF_NOGRAVITY; th->flags |= MF_NOGRAVITY;
th->momx = mo->momx >> 1; th->momx = mo->momx >> 1;
@ -4035,7 +4078,10 @@ void P_RipperBlood (AActor *mo, AActor *bleeder)
th->tics += pr_ripperblood () & 3; th->tics += pr_ripperblood () & 3;
// colorize the blood! // colorize the blood!
if (bloodcolor!=0) th->Translation = TRANSLATION(TRANSLATION_Blood, bloodcolor.a); if (bloodcolor!=0 && !(th->flags2 & MF2_DONTTRANSLATE))
{
th->Translation = TRANSLATION(TRANSLATION_Blood, bloodcolor.a);
}
} }
if (cl_bloodtype >= 1) if (cl_bloodtype >= 1)
{ {
@ -4694,6 +4740,39 @@ int AActor::TakeSpecialDamage (AActor *inflictor, AActor *source, int damage, FN
return (death == NULL) ? -1 : damage; return (death == NULL) ? -1 : damage;
} }
void AActor::Crash()
{
if ((flags & MF_CORPSE) &&
!(flags3 & MF3_CRASHED) &&
!(flags & MF_ICECORPSE))
{
FState * crashstate=NULL;
if (DamageType != NAME_None)
{
crashstate = GetClass()->ActorInfo->FindStateExact(2, NAME_Crash, DamageType);
}
if (crashstate == NULL)
{
int gibhealth = -abs(GetClass()->Meta.GetMetaInt (AMETA_GibHealth,
gameinfo.gametype == GAME_Doom ? -GetDefault()->health : -GetDefault()->health/2));
if (health<gibhealth)
{ // Extreme death
crashstate = FindState (2, NAME_Crash, NAME_Extreme);
}
else
{ // Normal death
crashstate = FindState (NAME_Crash);
}
}
if (crashstate != NULL) SetState(crashstate);
// Set MF3_CRASHED regardless of the presence of a crash state
// so this code doesn't have to be executed repeatedly.
flags3 |= MF3_CRASHED;
}
}
FArchive &operator<< (FArchive &arc, FSoundIndex &snd) FArchive &operator<< (FArchive &arc, FSoundIndex &snd)
{ {
if (arc.IsStoring ()) if (arc.IsStoring ())

View file

@ -141,6 +141,67 @@ IMPLEMENT_STATELESS_ACTOR (ATeleportDest3, Any, 9043, 0)
PROP_FlagsClear (MF_NOGRAVITY) PROP_FlagsClear (MF_NOGRAVITY)
END_DEFAULTS END_DEFAULTS
//==========================================================================
//
// P_SpawnTeleportFog
//
// The beginning of customizable teleport fog
// (not active yet)
//
//==========================================================================
void P_SpawnTeleportFog(fixed_t x, fixed_t y, fixed_t z, int spawnid)
{
const PClass *fog=NULL;
if (spawnid > 0 && spawnid < MAX_SPAWNABLES && SpawnableThings[spawnid] != NULL)
{
fog = SpawnableThings[spawnid];
}
/* if (fog != NULL && level.info->teleportfog != NAME_None)
{
fog = PClass::FindClass(level.info->teleportfog);
}
*/
if (fog == NULL)
{
AActor *mo = Spawn ("TeleportFog", x, y, z + TELEFOGHEIGHT, ALLOW_REPLACE);
if (mo != NULL)
{
FState * state = NULL;
switch(gameinfo.gametype)
{
default:
case GAME_Doom:
state = mo->FindState(NAME_Doom);
break;
case GAME_Heretic:
state = mo->FindState(NAME_Heretic);
break;
case GAME_Hexen:
state = mo->FindState(NAME_Hexen);
break;
case GAME_Strife:
state = mo->FindState(NAME_Strife);
break;
}
if (state == NULL) state = mo->SpawnState; // allow execution of code pointers in the spawn state
mo->SetState(state);
}
}
else
{
AActor *mo = Spawn (fog, x, y, z, ALLOW_REPLACE);
if (mo != NULL) mo->SetState(mo->SpawnState);
}
}
// //
// TELEPORTATION // TELEPORTATION
// //

View file

@ -915,7 +915,7 @@ void APlayerPawn::GiveDefaultInventory ()
} }
fixed_t hx[5]; fixed_t hx[5];
bool ishx; bool ishx=false;
for(int i=0;i<5;i++) for(int i=0;i<5;i++)
{ {

View file

@ -144,6 +144,7 @@ static flagdef ActorFlags[]=
DEFINE_FLAG(MF2, THRUGHOST, AActor, flags2), DEFINE_FLAG(MF2, THRUGHOST, AActor, flags2),
DEFINE_FLAG(MF2, BOSS, AActor, flags2), DEFINE_FLAG(MF2, BOSS, AActor, flags2),
DEFINE_FLAG2(MF2_NODMGTHRUST, NODAMAGETHRUST, AActor, flags2), DEFINE_FLAG2(MF2_NODMGTHRUST, NODAMAGETHRUST, AActor, flags2),
DEFINE_FLAG(MF2, DONTTRANSLATE, AActor, flags2),
DEFINE_FLAG(MF2, TELESTOMP, AActor, flags2), DEFINE_FLAG(MF2, TELESTOMP, AActor, flags2),
DEFINE_FLAG(MF2, FLOATBOB, AActor, flags2), DEFINE_FLAG(MF2, FLOATBOB, AActor, flags2),
DEFINE_FLAG(MF2, HEXENBOUNCE, AActor, flags2), DEFINE_FLAG(MF2, HEXENBOUNCE, AActor, flags2),
@ -693,7 +694,7 @@ AFuncDesc AFTable[]=
FUNC(A_Jump, "XL+" ) FUNC(A_Jump, "XL+" )
FUNC(A_CustomMissile, "MXXxxx" ) FUNC(A_CustomMissile, "MXXxxx" )
FUNC(A_CustomBulletAttack, "XXXXmx" ) FUNC(A_CustomBulletAttack, "XXXXmx" )
FUNC(A_CustomRailgun, "Xxccxxx" ) FUNC(A_CustomRailgun, "Xxccxxxm" )
FUNC(A_JumpIfHealthLower, "XL" ) FUNC(A_JumpIfHealthLower, "XL" )
FUNC(A_JumpIfCloser, "XL" ) FUNC(A_JumpIfCloser, "XL" )
FUNC(A_JumpIfInventory, "MXL" ) FUNC(A_JumpIfInventory, "MXL" )
@ -725,7 +726,7 @@ AFuncDesc AFTable[]=
FUNC(A_CustomPunch, "Xxymx" ) FUNC(A_CustomPunch, "Xxymx" )
FUNC(A_FireBullets, "XXXXmyx" ) FUNC(A_FireBullets, "XXXXmyx" )
FUNC(A_FireCustomMissile, "Mxyxxx" ) FUNC(A_FireCustomMissile, "Mxyxxx" )
FUNC(A_RailAttack, "Xxyccxx" ) FUNC(A_RailAttack, "Xxyccxxm" )
FUNC(A_Recoil, "X") FUNC(A_Recoil, "X")
FUNC(A_JumpIfInTargetInventory, "MXL" ) FUNC(A_JumpIfInTargetInventory, "MXL" )
FUNC(A_GiveToTarget, "Mx" ) FUNC(A_GiveToTarget, "Mx" )
@ -3347,6 +3348,33 @@ static void ActorBloodColor (AActor *defaults, Baggage &bag)
} }
//==========================================================================
//
//==========================================================================
static void ActorBloodType (AActor *defaults, Baggage &bag)
{
SC_MustGetString();
FName blood = sc_String;
// normal blood
bag.Info->Class->Meta.SetMetaInt (AMETA_BloodType, blood);
if (SC_CheckString(","))
{
SC_MustGetString();
blood = sc_String;
}
// blood splatter
bag.Info->Class->Meta.SetMetaInt (AMETA_BloodType2, blood);
if (SC_CheckString(","))
{
SC_MustGetString();
blood = sc_String;
}
// axe blood
bag.Info->Class->Meta.SetMetaInt (AMETA_BloodType3, blood);
}
//========================================================================== //==========================================================================
// //
//========================================================================== //==========================================================================
@ -4258,6 +4286,7 @@ static const ActorProps props[] =
{ "armor.savepercent", (apf)ArmorSavePercent, RUNTIME_CLASS(AActor) }, { "armor.savepercent", (apf)ArmorSavePercent, RUNTIME_CLASS(AActor) },
{ "attacksound", ActorAttackSound, RUNTIME_CLASS(AActor) }, { "attacksound", ActorAttackSound, RUNTIME_CLASS(AActor) },
{ "bloodcolor", ActorBloodColor, RUNTIME_CLASS(AActor) }, { "bloodcolor", ActorBloodColor, RUNTIME_CLASS(AActor) },
{ "bloodtype", ActorBloodType, RUNTIME_CLASS(AActor) },
{ "bouncecount", ActorBounceCount, RUNTIME_CLASS(AActor) }, { "bouncecount", ActorBounceCount, RUNTIME_CLASS(AActor) },
{ "bouncefactor", ActorBounceFactor, RUNTIME_CLASS(AActor) }, { "bouncefactor", ActorBounceFactor, RUNTIME_CLASS(AActor) },
{ "burn", ActorBurnState, RUNTIME_CLASS(AActor) }, { "burn", ActorBurnState, RUNTIME_CLASS(AActor) },

View file

@ -1117,6 +1117,7 @@ void A_RailAttack (AActor * self)
int Color2=StateParameters[index+4]; int Color2=StateParameters[index+4];
bool Silent=!!EvalExpressionI (StateParameters[index+5], self); bool Silent=!!EvalExpressionI (StateParameters[index+5], self);
float MaxDiff=EvalExpressionF (StateParameters[index+6], self); float MaxDiff=EvalExpressionF (StateParameters[index+6], self);
ENamedName PuffTypeName=(ENamedName)StateParameters[index+7];
AWeapon * weapon=self->player->ReadyWeapon; AWeapon * weapon=self->player->ReadyWeapon;
@ -1126,7 +1127,7 @@ void A_RailAttack (AActor * self)
if (!weapon->DepleteAmmo(weapon->bAltFire, true)) return; // out of ammo if (!weapon->DepleteAmmo(weapon->bAltFire, true)) return; // out of ammo
} }
P_RailAttack (self, Damage, Spawnofs_XY, Color1, Color2, MaxDiff, Silent); P_RailAttack (self, Damage, Spawnofs_XY, Color1, Color2, MaxDiff, Silent, PuffTypeName);
} }
//========================================================================== //==========================================================================
@ -1150,6 +1151,7 @@ void A_CustomRailgun (AActor *actor)
bool Silent=!!EvalExpressionI (StateParameters[index+4], actor); bool Silent=!!EvalExpressionI (StateParameters[index+4], actor);
bool aim=!!EvalExpressionI (StateParameters[index+5], actor); bool aim=!!EvalExpressionI (StateParameters[index+5], actor);
float MaxDiff=EvalExpressionF (StateParameters[index+6], actor); float MaxDiff=EvalExpressionF (StateParameters[index+6], actor);
ENamedName PuffTypeName=(ENamedName)StateParameters[index+7];
// [RH] Andy Baker's stealth monsters // [RH] Andy Baker's stealth monsters
if (actor->flags & MF_STEALTH) if (actor->flags & MF_STEALTH)
@ -1183,7 +1185,7 @@ void A_CustomRailgun (AActor *actor)
} }
} }
P_RailAttack (actor, Damage, Spawnofs_XY, Color1, Color2, MaxDiff, Silent); P_RailAttack (actor, Damage, Spawnofs_XY, Color1, Color2, MaxDiff, Silent, PuffTypeName);
} }
//=========================================================================== //===========================================================================
@ -1298,7 +1300,7 @@ static void InitSpawnedItem(AActor *self, AActor *mo, INTBOOL transfer_translati
{ {
AActor * originator = self; AActor * originator = self;
if (transfer_translation) if (transfer_translation && !(mo->flags2 & MF2_DONTTRANSLATE))
{ {
mo->Translation = self->Translation; mo->Translation = self->Translation;
} }

View file

@ -1,3 +1,4 @@
#include "actors/shared/botstuff.txt"
#include "actors/shared/blood.txt" #include "actors/shared/blood.txt"
#include "actors/shared/debris.txt" #include "actors/shared/debris.txt"
#include "actors/shared/splashes.txt" #include "actors/shared/splashes.txt"

View file

@ -1,8 +1,28 @@
// Blood sprite ------------------------------------------------------------
ACTOR Blood
{
SpawnID 130
Mass 5
+NOBLOCKMAP
+NOTELEPORT
States
{
Spawn:
BLUD CBA 8
Stop
Spray:
SPRY ABCDEF 3
SPRY G 2
Stop
}
}
// Blood splatter ----------------------------------------------------------- // Blood splatter -----------------------------------------------------------
ACTOR BloodSplatter ACTOR BloodSplatter
{ {
Game Raven
Radius 2 Radius 2
Height 4 Height 4
+NOBLOCKMAP +NOBLOCKMAP
@ -22,4 +42,26 @@ ACTOR BloodSplatter
} }
} }
// Axe Blood ----------------------------------------------------------------
ACTOR AxeBlood
{
Radius 2
Height 4
+NOBLOCKMAP
+NOGRAVITY
+DROPOFF
+NOTELEPORT
+CANNOTPUSH
Mass 5
States
{
Spawn:
FAXE FGHIJ 3
Death:
FAXE G 3
Stop
}
}

View file

@ -0,0 +1,19 @@
ACTOR CajunBodyNode
{
+NOSECTOR
+NOGRAVITY
+INVISIBLE
}
ACTOR CajunTrace
{
Speed 12
Radius 6
Height 8
+NOBLOCKMAP
+DROPOFF
+MISSILE
+NOGRAVITY
+NOTELEPORT
}

View file

@ -241,6 +241,7 @@ textcolors.txt textcolors.txt
decorate.txt decorate/decorate.txt decorate.txt decorate/decorate.txt
actors/shared/botstuff.txt decorate/shared/botstuff.txt
actors/shared/blood.txt decorate/shared/blood.txt actors/shared/blood.txt decorate/shared/blood.txt
actors/shared/debris.txt decorate/shared/debris.txt actors/shared/debris.txt decorate/shared/debris.txt
actors/shared/splashes.txt decorate/shared/splashes.txt actors/shared/splashes.txt decorate/shared/splashes.txt