From e83fa3dc43b071b7f8979b7798475cef0072e76a Mon Sep 17 00:00:00 2001 From: MonsterIestyn Date: Fri, 13 Feb 2015 16:15:58 +0000 Subject: [PATCH] Partial damage system overhaul: P_DamageMobj, P_KillMobj, P_HitDeathMessages and P_RingDamage now all take a "damagetype" variable that determines what type of damage was dealt. Does not replace the "damage" variable, we'll have to see if that is worth keeping another time? Currently the main benefit of these changes is that a number of non-Object-related hazards/deaths no long rely on dummy MT_NULL objects or other hacks to tell the game how you were hurt/killed, yay git-svn-id: https://code.orospakr.ca/svn/srb2/trunk@9039 6de4a73c-47e2-0310-b8c1-93d6ecd3f8cd --- src/d_netcmd.c | 4 +- src/g_game.c | 2 +- src/lua_baselib.c | 8 +- src/m_cheat.c | 2 +- src/p_enemy.c | 16 ++-- src/p_floor.c | 6 +- src/p_inter.c | 208 ++++++++++++++++++++++++++-------------------- src/p_local.h | 21 ++++- src/p_map.c | 63 +++++++------- src/p_mobj.c | 24 +++--- src/p_spec.c | 24 +++--- src/p_tick.c | 2 +- src/p_user.c | 34 +++----- 13 files changed, 226 insertions(+), 188 deletions(-) diff --git a/src/d_netcmd.c b/src/d_netcmd.c index 10605f20f..557715064 100644 --- a/src/d_netcmd.c +++ b/src/d_netcmd.c @@ -1911,7 +1911,7 @@ static void Got_Suicide(UINT8 **cp, INT32 playernum) } if (players[suicideplayer].mo) - P_DamageMobj(players[suicideplayer].mo, NULL, NULL, 10000); + P_DamageMobj(players[suicideplayer].mo, NULL, NULL, 1, DMG_INSTAKILL); } /** Deals with an ::XD_RANDOMSEED message in a netgame. @@ -2442,7 +2442,7 @@ static void Got_Teamchange(UINT8 **cp, INT32 playernum) if (players[playernum].mo) { if (!players[playernum].spectator) - P_DamageMobj(players[playernum].mo, NULL, NULL, 10000); + P_DamageMobj(players[playernum].mo, NULL, NULL, 1, DMG_INSTAKILL); else { P_RemoveMobj(players[playernum].mo); diff --git a/src/g_game.c b/src/g_game.c index d06edc62e..643ec8c93 100644 --- a/src/g_game.c +++ b/src/g_game.c @@ -4134,7 +4134,7 @@ void G_ConsGhostTic(void) if (demosynced) CONS_Alert(CONS_WARNING, M_GetText("Demo playback has desynced!\n")); demosynced = false; - P_DamageMobj(mobj, players[0].mo, players[0].mo, 1); + P_DamageMobj(mobj, players[0].mo, players[0].mo, 1, 0); } } } diff --git a/src/lua_baselib.c b/src/lua_baselib.c index ad5d740f8..9b0a34f17 100644 --- a/src/lua_baselib.c +++ b/src/lua_baselib.c @@ -1037,6 +1037,7 @@ static int lib_pDamageMobj(lua_State *L) { mobj_t *target = *((mobj_t **)luaL_checkudata(L, 1, META_MOBJ)), *inflictor = NULL, *source = NULL; INT32 damage; + UINT8 damagetype; NOHUD if (!target) return LUA_ErrInvalid(L, "mobj_t"); @@ -1045,13 +1046,15 @@ static int lib_pDamageMobj(lua_State *L) if (!lua_isnone(L, 3) && lua_isuserdata(L, 3)) source = *((mobj_t **)luaL_checkudata(L, 3, META_MOBJ)); damage = (INT32)luaL_optinteger(L, 4, 1); - lua_pushboolean(L, P_DamageMobj(target, inflictor, source, damage)); + damagetype = (UINT8)luaL_optinteger(L, 5, 0); + lua_pushboolean(L, P_DamageMobj(target, inflictor, source, damage, damagetype)); return 1; } static int lib_pKillMobj(lua_State *L) { mobj_t *target = *((mobj_t **)luaL_checkudata(L, 1, META_MOBJ)), *inflictor = NULL, *source = NULL; + UINT8 damagetype; NOHUD if (!target) return LUA_ErrInvalid(L, "mobj_t"); @@ -1059,7 +1062,8 @@ static int lib_pKillMobj(lua_State *L) inflictor = *((mobj_t **)luaL_checkudata(L, 2, META_MOBJ)); if (!lua_isnone(L, 3) && lua_isuserdata(L, 3)) source = *((mobj_t **)luaL_checkudata(L, 3, META_MOBJ)); - P_KillMobj(target, inflictor, source); + damagetype = (UINT8)luaL_optinteger(L, 4, 0); + P_KillMobj(target, inflictor, source, damagetype); return 0; } diff --git a/src/m_cheat.c b/src/m_cheat.c index bc32e6cfa..4da9b3ba7 100644 --- a/src/m_cheat.c +++ b/src/m_cheat.c @@ -372,7 +372,7 @@ void Command_Hurtme_f(void) return; } - P_DamageMobj(players[consoleplayer].mo, NULL, NULL, atoi(COM_Argv(1))); + P_DamageMobj(players[consoleplayer].mo, NULL, NULL, atoi(COM_Argv(1)), 0); } // Moves the NiGHTS player to another axis within the current mare diff --git a/src/p_enemy.c b/src/p_enemy.c index 5ae11320c..0896ad284 100644 --- a/src/p_enemy.c +++ b/src/p_enemy.c @@ -4813,7 +4813,7 @@ void A_UnidusBall(mobj_t *actor) boolean skull = (actor->target->flags2 & MF2_SKULLFLY) == MF2_SKULLFLY; if (actor->target->state == &states[actor->target->info->painstate]) { - P_KillMobj(actor, NULL, NULL); + P_KillMobj(actor, NULL, NULL, 0); return; } switch(actor->extravalue2) @@ -5278,7 +5278,7 @@ void A_RingExplode(mobj_t *actor) if (mo2->flags & MF_SHOOTABLE) { actor->flags2 |= MF2_DEBRIS; - P_DamageMobj(mo2, actor, actor->target, 1); + P_DamageMobj(mo2, actor, actor->target, 1, 0); continue; } } @@ -6383,7 +6383,7 @@ void A_EggmanBox(mobj_t *actor) return; } - P_DamageMobj(actor->target, actor, actor, 1); // Ow! + P_DamageMobj(actor->target, actor, actor, 1, 0); // Ow! } // Function: A_TurretFire @@ -9368,9 +9368,9 @@ void A_RemoteDamage(mobj_t *actor) if (locvar2 == 1) // Kill mobj! { if (target->player) // players die using P_DamageMobj instead for some reason - P_DamageMobj(target, source, source, 10000); + P_DamageMobj(target, source, source, 1, DMG_INSTAKILL); else - P_KillMobj(target, source, source); + P_KillMobj(target, source, source, 0); } else if (locvar2 == 2) // Remove mobj! { @@ -9380,7 +9380,7 @@ void A_RemoteDamage(mobj_t *actor) P_RemoveMobj(target); } else // default: Damage mobj! - P_DamageMobj(target, source, source, 1); + P_DamageMobj(target, source, source, 1, 0); } // Function: A_HomingChase @@ -9615,7 +9615,7 @@ void A_VileAttack(mobj_t *actor) return; S_StartSound(actor, soundtoplay); - P_DamageMobj(actor->target, actor, actor, 1); + P_DamageMobj(actor->target, actor, actor, 1, 0); //actor->target->momz = 1000*FRACUNIT/actor->target->info->mass; // How id did it actor->target->momz += FixedMul(10*FRACUNIT, actor->scale)*P_MobjFlip(actor->target); // How we're doing it if (explosionType != MT_NULL) @@ -9656,7 +9656,7 @@ void A_VileAttack(mobj_t *actor) continue; S_StartSound(actor, soundtoplay); - P_DamageMobj(players[i].mo, actor, actor, 1); + P_DamageMobj(players[i].mo, actor, actor, 1, 0); //actor->target->momz = 1000*FRACUNIT/actor->target->info->mass; // How id did it players[i].mo->momz += FixedMul(10*FRACUNIT, actor->scale)*P_MobjFlip(players[i].mo); // How we're doing it if (explosionType != MT_NULL) diff --git a/src/p_floor.c b/src/p_floor.c index 6892caaac..386cb5d43 100644 --- a/src/p_floor.c +++ b/src/p_floor.c @@ -1215,9 +1215,7 @@ void T_SpikeSector(levelspecthink_t *spikes) if (dothepain) { - mobj_t *killer = P_SpawnMobj(thing->x, thing->y, thing->z, MT_NULL); - killer->threshold = 43; // Special flag that it was spikes which hurt you. - P_DamageMobj(thing, killer, killer, 1); + P_DamageMobj(thing, NULL, NULL, 1, DMG_SPIKE); break; } } @@ -3125,7 +3123,7 @@ INT32 EV_MarioBlock(sector_t *sec, sector_t *roversector, fixed_t topheight, mob thing->momz = FixedMul(6*FRACUNIT, thing->scale); P_SetThingPosition(thing); if (thing->flags & MF_SHOOTABLE) - P_DamageMobj(thing, puncher, puncher, 1); + P_DamageMobj(thing, puncher, puncher, 1, 0); else if (thing->type == MT_RING || thing->type == MT_COIN) { thing->momz = FixedMul(3*FRACUNIT, thing->scale); diff --git a/src/p_inter.c b/src/p_inter.c index ef16ba631..d305cfc83 100644 --- a/src/p_inter.c +++ b/src/p_inter.c @@ -291,7 +291,7 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) { if (special->type == MT_BLACKEGGMAN) { - P_DamageMobj(toucher, special, special, 1); // ouch + P_DamageMobj(toucher, special, special, 1, 0); // ouch return; } @@ -303,7 +303,7 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) toucher->momz = -toucher->momz; toucher->momx = -toucher->momx; toucher->momy = -toucher->momy; - P_DamageMobj(special, toucher, toucher, 1); + P_DamageMobj(special, toucher, toucher, 1, 0); } else if (((toucher->z < special->z && !(toucher->eflags & MFE_VERTICALFLIP)) || (toucher->z + toucher->height > special->z + special->height && (toucher->eflags & MFE_VERTICALFLIP))) @@ -313,10 +313,10 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) { toucher->momz = -toucher->momz/2; - P_DamageMobj(special, toucher, toucher, 1); + P_DamageMobj(special, toucher, toucher, 1, 0); } else - P_DamageMobj(toucher, special, special, 1); + P_DamageMobj(toucher, special, special, 1, 0); return; } @@ -330,13 +330,13 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) && toucher->z < special->z + special->height && toucher->z + toucher->height > special->z) { // Can only hit snapper from above - P_DamageMobj(toucher, special, special, 1); + P_DamageMobj(toucher, special, special, 1, 0); } else if (special->type == MT_SHARP && ((special->state == &states[special->info->xdeathstate]) || (toucher->z > special->z + special->height/2))) { // Cannot hit sharp from above or when red and angry - P_DamageMobj(toucher, special, special, 1); + P_DamageMobj(toucher, special, special, 1, 0); } else if (((player->pflags & PF_NIGHTSMODE) && (player->pflags & PF_DRILLING)) || (player->pflags & (PF_JUMPED|PF_SPINNING|PF_GLIDING)) @@ -345,7 +345,7 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) if (P_MobjFlip(toucher)*toucher->momz < 0) toucher->momz = -toucher->momz; - P_DamageMobj(special, toucher, toucher, 1); + P_DamageMobj(special, toucher, toucher, 1, 0); } else if (((toucher->z < special->z && !(toucher->eflags & MFE_VERTICALFLIP)) || (toucher->z + toucher->height > special->z + special->height && (toucher->eflags & MFE_VERTICALFLIP))) // Flame is bad at logic - JTE @@ -356,16 +356,16 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) if (P_MobjFlip(toucher)*toucher->momz < 0) toucher->momz = -toucher->momz/2; - P_DamageMobj(special, toucher, toucher, 1); + P_DamageMobj(special, toucher, toucher, 1, 0); } else - P_DamageMobj(toucher, special, special, 1); + P_DamageMobj(toucher, special, special, 1, 0); return; } else if (special->flags & MF_FIRE) { - P_DamageMobj(toucher, special, special, 1); + P_DamageMobj(toucher, special, special, 1, DMG_FIRE); return; } else @@ -743,7 +743,7 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) if (mo2->flags & MF_SHOOTABLE) { - P_DamageMobj(mo2, toucher, toucher, 1); + P_DamageMobj(mo2, toucher, toucher, 1, 0); continue; } @@ -1351,7 +1351,7 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) case MT_SPECIALSPIKEBALL: if (!(!useNightsSS && G_IsSpecialStage(gamemap))) // Only for old special stages { - P_DamageMobj(toucher, special, special, 1); + P_DamageMobj(toucher, special, special, 1, 0); return; } @@ -1382,7 +1382,7 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) // Goomba Stomp'd! if (special->target->momz < 0) { - P_DamageMobj(toucher, special, special->target, 1); + P_DamageMobj(toucher, special, special->target, 1, 0); //special->target->momz = -special->target->momz; special->target->momx = special->target->momy = 0; special->target->momz = 0; @@ -1446,7 +1446,7 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) } S_StartSound(toucher, special->info->deathsound); // was NULL, but changed to player so you could hear others pick up rings - P_KillMobj(special, NULL, toucher); + P_KillMobj(special, NULL, toucher, 0); } #define CTFTEAMCODE(pl) pl->ctfteam ? (pl->ctfteam == 1 ? "\x85" : "\x84") : "" @@ -1457,8 +1457,9 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) * \param player Affected player. * \param inflictor The attack weapon used, can be NULL. * \param source The attacker, can be NULL. + * \param damagetype The type of damage dealt to the player. If bit 7 (0x80) is set, this was an instant-kill. */ -static void P_HitDeathMessages(player_t *player, mobj_t *inflictor, mobj_t *source) +static void P_HitDeathMessages(player_t *player, mobj_t *inflictor, mobj_t *source, UINT8 damagetype) { const char *str = NULL; boolean deathonly = false; @@ -1567,22 +1568,6 @@ static void P_HitDeathMessages(player_t *player, mobj_t *inflictor, mobj_t *sour } else switch (source->type) { - case MT_NULL: - switch(source->threshold) - { - case 42: - deathonly = true; - str = M_GetText("%s drowned.\n"); - break; - case 43: - str = M_GetText("%s was %s by spikes.\n"); - break; - case 44: - deathonly = true; - str = M_GetText("%s was crushed.\n"); - break; - } - break; case MT_EGGMANICO: case MT_EGGMANBOX: str = M_GetText("%s was %s by Eggman's nefarious TV magic.\n"); @@ -1598,30 +1583,52 @@ static void P_HitDeathMessages(player_t *player, mobj_t *inflictor, mobj_t *sour else { // null source, environment kills - // TERRIBLE HACK for hit damage because P_DoPlayerPain moves the player... - // I'll put it back, I promise! - player->mo->z -= player->mo->momz+1; - if (P_PlayerTouchingSectorSpecial(player, 1, 2)) - str = M_GetText("%s was %s by chemical water.\n"); - else if (P_PlayerTouchingSectorSpecial(player, 1, 3)) - str = M_GetText("%s was %s by molten lava.\n"); - else if (P_PlayerTouchingSectorSpecial(player, 1, 4)) - str = M_GetText("%s was %s by electricity.\n"); - else if (deadtarget) + switch (damagetype) { - deathonly = true; - if (P_PlayerTouchingSectorSpecial(player, 1, 6) - || P_PlayerTouchingSectorSpecial(player, 1, 7)) - str = M_GetText("%s fell into a bottomless pit.\n"); - else if (P_PlayerTouchingSectorSpecial(player, 1, 12)) - str = M_GetText("%s asphyxiated in space.\n"); - else - str = M_GetText("%s died.\n"); + case DMG_WATER: + str = M_GetText("%s was %s by chemical water.\n"); + break; + case DMG_FIRE: + str = M_GetText("%s was %s by molten lava.\n"); + break; + case DMG_ELECTRIC: + str = M_GetText("%s was %s by electricity.\n"); + break; + case DMG_SPIKE: + str = M_GetText("%s was %s by spikes.\n"); + break; + case DMG_DROWNED: + deathonly = true; + str = M_GetText("%s drowned.\n"); + break; + case DMG_CRUSHED: + deathonly = true; + str = M_GetText("%s was crushed.\n"); + break; + case DMG_DEATHPIT: + if (deadtarget) + { + deathonly = true; + str = M_GetText("%s fell into a bottomless pit.\n"); + } + break; + case DMG_SPACEDROWN: + if (deadtarget) + { + deathonly = true; + str = M_GetText("%s asphyxiated in space.\n"); + } + break; + default: + if (deadtarget) + { + deathonly = true; + str = M_GetText("%s died.\n"); + } + break; } if (!str) str = M_GetText("%s was %s by an environmental hazard.\n"); - - player->mo->z += player->mo->momz+1; } if (!str) // Should not happen! Unless we missed catching something above. @@ -1799,10 +1806,11 @@ boolean P_CheckRacers(void) * \param target The victim. * \param inflictor The attack weapon. May be NULL (environmental damage). * \param source The attacker. May be NULL. + * \param damagetype The type of damage dealt that killed the target. If bit 7 (0x80) was set, this was an instant-death. * \todo Cleanup, refactor, split up. * \sa P_DamageMobj */ -void P_KillMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source) +void P_KillMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, UINT8 damagetype) { mobjtype_t item; mobj_t *mo; @@ -2126,15 +2134,19 @@ void P_KillMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source) case MT_PLAYER: target->fuse = TICRATE*3; // timer before mobj disappears from view (even if not an actual player) target->momx = target->momy = target->momz = 0; - if (!(source && source->type == MT_NULL && source->threshold == 42)) // Don't jump up when drowning - P_SetObjectMomZ(target, 14*FRACUNIT, false); - - if (source && source->type == MT_NULL && source->threshold == 42) // drowned + if (damagetype == DMG_DROWNED) // drowned + { S_StartSound(target, sfx_drown); - else if (source && (source->type == MT_SPIKE || (source->type == MT_NULL && source->threshold == 43))) // Spikes - S_StartSound(target, sfx_spkdth); + // Don't jump up when drowning + } else - P_PlayDeathSound(target); + { + P_SetObjectMomZ(target, 14*FRACUNIT, false); + if ((source && source->type == MT_SPIKE) || damagetype == DMG_SPIKE) // Spikes + S_StartSound(target, sfx_spkdth); + else + P_PlayDeathSound(target); + } break; default: break; @@ -2384,7 +2396,7 @@ static inline boolean P_TagDamage(mobj_t *target, mobj_t *inflictor, mobj_t *sou if (source->player->pflags & PF_TAGIT && !(player->pflags & PF_TAGIT)) { P_AddPlayerScore(source->player, 100); //award points to tagger. - P_HitDeathMessages(player, inflictor, source); + P_HitDeathMessages(player, inflictor, source, 0); if (gametype == GT_TAG) //survivor { @@ -2640,7 +2652,7 @@ static void P_ShieldDamage(player_t *player, mobj_t *inflictor, mobj_t *source, } } -static void P_RingDamage(player_t *player, mobj_t *inflictor, mobj_t *source, INT32 damage) +static void P_RingDamage(player_t *player, mobj_t *inflictor, mobj_t *source, INT32 damage, UINT8 damagetype) { if (!(inflictor && ((inflictor->flags & MF_MISSILE) || inflictor->player) && player->powers[pw_super] && ALL7EMERALDS(player->powers[pw_emeralds]))) { @@ -2648,7 +2660,7 @@ static void P_RingDamage(player_t *player, mobj_t *inflictor, mobj_t *source, IN P_ForceFeed(player, 40, 10, TICRATE, 40 + min(damage, 100)*2); - if (source && (source->type == MT_SPIKE || (source->type == MT_NULL && source->threshold == 43))) // spikes + if ((source && source->type == MT_SPIKE) || damagetype == DMG_SPIKE) // spikes S_StartSound(player->mo, sfx_spkdth); } @@ -2677,21 +2689,21 @@ static void P_RingDamage(player_t *player, mobj_t *inflictor, mobj_t *source, IN /** Damages an object, which may or may not be a player. * For melee attacks, source and inflictor are the same. * - * \param target The object being damaged. - * \param inflictor The thing that caused the damage: creature, missile, - * gargoyle, and so forth. Can be NULL in the case of - * environmental damage, such as slime or crushing. - * \param source The creature or person responsible. For example, if a - * player is hit by a ring, the player who shot it. In some - * cases, the target will go after this object after - * receiving damage. This can be NULL. - * \param damage Amount of damage to be dealt. 10000 is instant death. + * \param target The object being damaged. + * \param inflictor The thing that caused the damage: creature, missile, + * gargoyle, and so forth. Can be NULL in the case of + * environmental damage, such as slime or crushing. + * \param source The creature or person responsible. For example, if a + * player is hit by a ring, the player who shot it. In some + * cases, the target will go after this object after + * receiving damage. This can be NULL. + * \param damage Amount of damage to be dealt. + * \param damagetype Type of damage to be dealt. If bit 7 (0x80) is set, this is an instant-kill. * \return True if the target sustained damage, otherwise false. * \todo Clean up this mess, split into multiple functions. - * \todo Get rid of the magic number 10000. * \sa P_KillMobj */ -boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage) +boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage, UINT8 damagetype) { player_t *player; #ifdef HAVE_BLUA @@ -2709,9 +2721,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da // Spectator handling if (netgame) { - if (damage == 42000 && target->player && target->player->spectator) - damage = 10000; - else if (target->player && target->player->spectator) + if (damagetype != DMG_SPECTATOR && target->player && target->player->spectator) return false; if (source && source->player && source->player->spectator) @@ -2819,6 +2829,21 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da if (!(target->player->pflags & (PF_NIGHTSMODE|PF_NIGHTSFALL)) && (maptol & TOL_NIGHTS)) return false; + + switch (damagetype) + { + case DMG_WATER: + case DMG_FIRE: + if ((player->powers[pw_shield] & SH_NOSTACK) == SH_ELEMENTAL) + return false; // Invincible to water/fire damage + break; + case DMG_ELECTRIC: + if ((player->powers[pw_shield] & SH_NOSTACK) == SH_ATTRACT) + return false; // Invincible to electric damage + break; + default: + break; + } } if (player->pflags & PF_NIGHTSMODE) // NiGHTS damage handling @@ -2840,12 +2865,12 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da return true; } - if (!force && inflictor && (inflictor->flags & MF_FIRE)) + if (!force && inflictor && inflictor->flags & MF_FIRE) { if ((player->powers[pw_shield] & SH_NOSTACK) == SH_ELEMENTAL) return false; // Invincible to fire objects - if (G_PlatformGametype() && source && source->player) + if (G_PlatformGametype() && inflictor && source && source->player) return false; // Don't get hurt by fire generated from friends. } @@ -2854,7 +2879,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da { if ((gametype == GT_MATCH || gametype == GT_TEAMMATCH || gametype == GT_CTF) && cv_suddendeath.value && !player->powers[pw_flashing] && !player->powers[pw_invulnerability]) - damage = 10000; + damagetype = DMG_INSTAKILL; } // Player hits another player @@ -2868,7 +2893,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da return false; // Instant-Death - if (damage == 10000) + if (damagetype & DMG_DEATHMASK) P_KillPlayer(player, source, damage); else if (metalrecording) { @@ -2876,7 +2901,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da inflictor = source; if (inflictor && inflictor->flags & MF_ENEMY) { // Metal Sonic destroy enemy !! - P_KillMobj(inflictor, NULL, target); + P_KillMobj(inflictor, NULL, target, damagetype); return false; } else if (inflictor && inflictor->flags & MF_MISSILE) @@ -2915,7 +2940,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da else if (player->mo->health > 1) // No shield but have rings. { damage = player->mo->health - 1; - P_RingDamage(player, inflictor, source, damage); + P_RingDamage(player, inflictor, source, damage, damagetype); } else // No shield, no rings, no invincibility. { @@ -2952,21 +2977,20 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da if (gametype == GT_CTF && (player->gotflag & (GF_REDFLAG|GF_BLUEFLAG))) P_PlayerFlagBurst(player, false); } + else if (damagetype & DMG_DEATHMASK) + player->health = 0; else { player->health -= damage; // mirror mobj health here - if (damage < 10000) - { - target->player->powers[pw_flashing] = flashingtics; - if (damage > 0) // don't spill emeralds/ammo/panels for shield damage - P_PlayerRingBurst(player, damage); - } + target->player->powers[pw_flashing] = flashingtics; + if (damage > 0) // don't spill emeralds/ammo/panels for shield damage + P_PlayerRingBurst(player, damage); } if (player->health < 0) player->health = 0; - P_HitDeathMessages(player, inflictor, source); + P_HitDeathMessages(player, inflictor, source, damagetype); P_ForceFeed(player, 40, 10, TICRATE, 40 + min(damage, 100)*2); } @@ -2974,7 +2998,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da // Killing dead. Just for kicks. // Require source and inflictor be player. Don't hurt for firing rings. if (cv_killingdead.value && (source && source->player) && (inflictor && inflictor->player) && P_Random() < 80) - P_DamageMobj(source, target, target, 1); + P_DamageMobj(source, target, target, 1, 0); // do the damage if (player && player->powers[pw_super] && ALL7EMERALDS(player->powers[pw_emeralds]) && inflictor && ((inflictor->flags & MF_MISSILE) || inflictor->player)) @@ -2983,6 +3007,8 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da if (target->health < 2) target->health = 2; } + else if (damagetype & DMG_DEATHMASK) + target->health = 0; else target->health -= damage; @@ -2991,7 +3017,7 @@ boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 da if (target->health <= 0) { - P_KillMobj(target, inflictor, source); + P_KillMobj(target, inflictor, source, damagetype); return true; } diff --git a/src/p_local.h b/src/p_local.h index 2f0b06268..e496990ca 100644 --- a/src/p_local.h +++ b/src/p_local.h @@ -342,12 +342,29 @@ typedef struct BasicFF_s INT32 Magnitude; ///< Magnitude of the effect, in the range from 0 through 10,000. } BasicFF_t; +/* Damage/death types, for P_DamageMobj and related */ +//// Damage types +//#define DMG_NORMAL 0 (unneeded?) +#define DMG_WATER 1 +#define DMG_FIRE 2 +#define DMG_ELECTRIC 3 +#define DMG_SPIKE 4 +//#define DMG_SPECIALSTAGE 5 +//// Death types - cannot be combined with damage types +#define DMG_INSTAKILL 0x80 +#define DMG_DROWNED 0x80+1 +#define DMG_SPACEDROWN 0x80+2 +#define DMG_DEATHPIT 0x80+3 +#define DMG_CRUSHED 0x80+4 +#define DMG_SPECTATOR 0x80+5 +#define DMG_DEATHMASK DMG_INSTAKILL // if bit 7 is set, this is a death type instead of a damage type + void P_ForceFeed(const player_t *player, INT32 attack, INT32 fade, tic_t duration, INT32 period); void P_ForceConstant(const BasicFF_t *FFInfo); void P_RampConstant(const BasicFF_t *FFInfo, INT32 Start, INT32 End); void P_RemoveShield(player_t *player); -boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage); -void P_KillMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source); +boolean P_DamageMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, INT32 damage, UINT8 damagetype); +void P_KillMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, UINT8 damagetype); void P_PlayerRingBurst(player_t *player, INT32 num_rings); /// \todo better fit in p_user.c void P_PlayerWeaponPanelBurst(player_t *player); void P_PlayerWeaponAmmoBurst(player_t *player); diff --git a/src/p_map.c b/src/p_map.c index b134971ab..6c5a47852 100644 --- a/src/p_map.c +++ b/src/p_map.c @@ -426,12 +426,12 @@ static boolean PIT_CheckThing(mobj_t *thing) S_StartSound(tmthing, thing->info->deathsound); for (thing = thing->subsector->sector->thinglist; thing; thing = thing->snext) if (thing->type == MT_SPIKE && thing->health > 0 && thing->flags & MF_SOLID && P_AproxDistance(thing->x - tmthing->x, thing->y - tmthing->y) < FixedMul(56*FRACUNIT, thing->scale)) - P_KillMobj(thing, tmthing, tmthing); + P_KillMobj(thing, tmthing, tmthing, 0); } else { thing->health = 0; - P_KillMobj(thing, tmthing, tmthing); + P_KillMobj(thing, tmthing, tmthing, 0); } return true; } @@ -483,7 +483,7 @@ static boolean PIT_CheckThing(mobj_t *thing) else thing->z = tmthing->z + tmthing->height + FixedMul(FRACUNIT, tmthing->scale); if (thing->flags & MF_SHOOTABLE) - P_DamageMobj(thing, tmthing, tmthing, 1); + P_DamageMobj(thing, tmthing, tmthing, 1, 0); return true; } @@ -495,7 +495,12 @@ static boolean PIT_CheckThing(mobj_t *thing) if (thing->z + thing->height < tmthing->z) return true; // underneath if (tmthing->player && tmthing->flags & MF_SHOOTABLE) - P_DamageMobj(tmthing, thing, thing, 1); + { + UINT8 damagetype = 0; + if (thing->flags & MF_FIRE) // BURN! + damagetype = DMG_FIRE; + P_DamageMobj(tmthing, thing, thing, 1, damagetype); + } return true; } else if (tmthing->flags & MF_PAIN) @@ -506,7 +511,12 @@ static boolean PIT_CheckThing(mobj_t *thing) if (tmthing->z + tmthing->height < thing->z) return true; // underneath if (thing->player && thing->flags & MF_SHOOTABLE) - P_DamageMobj(thing, tmthing, tmthing, 1); + { + UINT8 damagetype = 0; + if (tmthing->flags & MF_FIRE) // BURN! + damagetype = DMG_FIRE; + P_DamageMobj(thing, tmthing, tmthing, 1, damagetype); + } return true; } @@ -627,7 +637,7 @@ static boolean PIT_CheckThing(mobj_t *thing) return false; else // hit shield from behind, shield is destroyed! { - P_KillMobj(thing, tmthing, tmthing); + P_KillMobj(thing, tmthing, tmthing, 0); return false; } } @@ -636,7 +646,7 @@ static boolean PIT_CheckThing(mobj_t *thing) return true; // damage / explode if (tmthing->flags & MF_ENEMY) // An actual ENEMY! (Like the deton, for example) - P_DamageMobj(thing, tmthing, tmthing, 1); + P_DamageMobj(thing, tmthing, tmthing, 1, 0); else if (tmthing->type == MT_BLACKEGGMAN_MISSILE && thing->player && (thing->player->pflags & PF_JUMPED) && !thing->player->powers[pw_flashing] @@ -672,7 +682,7 @@ static boolean PIT_CheckThing(mobj_t *thing) P_SetThingPosition(tmthing); } else - P_DamageMobj(thing, tmthing, tmthing->target, 1); + P_DamageMobj(thing, tmthing, tmthing->target, 1, 0); // don't traverse any more @@ -786,11 +796,11 @@ static boolean PIT_CheckThing(mobj_t *thing) { if (thing->z + thing->height <= tmthing->z + FixedMul(FRACUNIT, tmthing->scale) && thing->z + thing->height + thing->momz >= tmthing->z + FixedMul(FRACUNIT, tmthing->scale) + tmthing->momz) - P_DamageMobj(thing, tmthing, tmthing, 1); + P_DamageMobj(thing, tmthing, tmthing, 1, 0); } else if (thing->z >= tmthing->z + tmthing->height - FixedMul(FRACUNIT, tmthing->scale) && thing->z + thing->momz <= tmthing->z + tmthing->height - FixedMul(FRACUNIT, tmthing->scale) + tmthing->momz) - P_DamageMobj(thing, tmthing, tmthing, 1); + P_DamageMobj(thing, tmthing, tmthing, 1, 0); } else if (thing->type == MT_SPIKE && thing->flags & MF_SOLID && tmthing->player) // unfortunate player falls into spike?! { @@ -798,11 +808,11 @@ static boolean PIT_CheckThing(mobj_t *thing) { if (tmthing->z + tmthing->height <= thing->z - FixedMul(FRACUNIT, thing->scale) && tmthing->z + tmthing->height + tmthing->momz >= thing->z - FixedMul(FRACUNIT, thing->scale)) - P_DamageMobj(tmthing, thing, thing, 1); + P_DamageMobj(tmthing, thing, thing, 1, 0); } else if (tmthing->z >= thing->z + thing->height + FixedMul(FRACUNIT, thing->scale) && tmthing->z + tmthing->momz <= thing->z + thing->height + FixedMul(FRACUNIT, thing->scale)) - P_DamageMobj(tmthing, thing, thing, 1); + P_DamageMobj(tmthing, thing, thing, 1, 0); } if (thing->flags & MF_PUSHABLE) @@ -832,10 +842,10 @@ static boolean PIT_CheckThing(mobj_t *thing) { if ((tmthing->player->powers[pw_invulnerability] || tmthing->player->powers[pw_super]) && !thing->player->powers[pw_super]) - P_DamageMobj(thing, tmthing, tmthing, 1); + P_DamageMobj(thing, tmthing, tmthing, 1, 0); else if ((thing->player->powers[pw_invulnerability] || thing->player->powers[pw_super]) && !tmthing->player->powers[pw_super]) - P_DamageMobj(tmthing, thing, thing, 1); + P_DamageMobj(tmthing, thing, thing, 1, 0); } // If players are using touch tag, seekers damage hiders. @@ -843,9 +853,9 @@ static boolean PIT_CheckThing(mobj_t *thing) ((thing->player->pflags & PF_TAGIT) != (tmthing->player->pflags & PF_TAGIT))) { if ((tmthing->player->pflags & PF_TAGIT) && !(thing->player->pflags & PF_TAGIT)) - P_DamageMobj(thing, tmthing, tmthing, 1); + P_DamageMobj(thing, tmthing, tmthing, 1, 0); else if ((thing->player->pflags & PF_TAGIT) && !(tmthing->player->pflags & PF_TAGIT)) - P_DamageMobj(tmthing, thing, tmthing, 1); + P_DamageMobj(tmthing, thing, tmthing, 1, 0); } } @@ -883,7 +893,7 @@ static boolean PIT_CheckThing(mobj_t *thing) { // Objects kill you if it falls from above. if (thing != tmthing->target) - P_DamageMobj(thing, tmthing, tmthing->target, 10000); + P_DamageMobj(thing, tmthing, tmthing->target, 1, DMG_INSTAKILL); tmthing->momz = -tmthing->momz/2; // Bounce, just for fun! // The tmthing->target allows the pusher of the object @@ -917,7 +927,7 @@ static boolean PIT_CheckThing(mobj_t *thing) { SINT8 flipval = P_MobjFlip(thing); // Save this value in case monitor gets removed. fixed_t *momz = &tmthing->momz; // tmthing gets changed by P_DamageMobj, so we need a new pointer?! X_x;; - P_DamageMobj(thing, tmthing, tmthing, 1); // break the monitor + P_DamageMobj(thing, tmthing, tmthing, 1, 0); // break the monitor // Going down? Then bounce back up. if ((P_MobjWasRemoved(thing) // Monitor was removed || !thing->health) // or otherwise popped @@ -3007,7 +3017,7 @@ static boolean PIT_RadiusAttack(mobj_t *thing) if (P_CheckSight(thing, bombspot)) { // must be in direct path - P_DamageMobj(thing, bombspot, bombsource, 1); // Tails 01-11-2001 + P_DamageMobj(thing, bombspot, bombsource, 1, 0); // Tails 01-11-2001 } return true; @@ -3140,22 +3150,15 @@ static boolean PIT_ChangeSector(mobj_t *thing, boolean realcrush) { // Crush the object if (netgame && thing->player && thing->player->spectator) - P_DamageMobj(thing, NULL, NULL, 42000); // Respawn crushed spectators + P_DamageMobj(thing, NULL, NULL, 1, DMG_SPECTATOR); // Respawn crushed spectators else - { - if (!killer) - { - //Nobody is responsible for crushing the object, so give a generic crush message - killer = P_SpawnMobj(thing->x, thing->y, thing->z, MT_NULL); - killer->threshold = 44; // Special flag for crushing - } - P_DamageMobj(thing, killer, killer, 10000); - } + P_DamageMobj(thing, killer, killer, 1, DMG_CRUSHED); + return true; } } if (realcrush && crushchange) - P_DamageMobj(thing, NULL, NULL, 1); + P_DamageMobj(thing, NULL, NULL, 1, 0); // keep checking (crush other things) return true; diff --git a/src/p_mobj.c b/src/p_mobj.c index 50708802b..9565648c2 100644 --- a/src/p_mobj.c +++ b/src/p_mobj.c @@ -712,7 +712,7 @@ void P_ExplodeMissile(mobj_t *mo) S_StartSound(explodemo, sfx_cybdth); // Hack: Release an animal. - P_DamageMobj(mo, NULL, NULL, 10000); + P_DamageMobj(mo, NULL, NULL, 1, DMG_INSTAKILL); } mo->flags &= ~MF_MISSILE; @@ -1744,7 +1744,7 @@ static boolean P_ZMovement(mobj_t *mo) // Kill enemies and bosses that fall into death pits. if (mo->health) { - P_KillMobj(mo, NULL, NULL); + P_KillMobj(mo, NULL, NULL, 0); return false; } } @@ -2800,7 +2800,7 @@ void P_DestroyRobots(void) continue; // Found a target enemy - P_KillMobj(mo, players[consoleplayer].mo, players[consoleplayer].mo); + P_KillMobj(mo, players[consoleplayer].mo, players[consoleplayer].mo, 0); } } @@ -3481,7 +3481,7 @@ static void P_Boss3Thinker(mobj_t *mobj) continue; if (players[i].mo->eflags & MFE_UNDERWATER) - P_DamageMobj(players[i].mo, mobj, mobj, 1); + P_DamageMobj(players[i].mo, mobj, mobj, 1, 0); } // Make the water flash @@ -3822,7 +3822,7 @@ static void P_Boss4PopSpikeballs(mobj_t *mobj) P_SetTarget(&base->tracer, NULL); for (seg = base; seg; seg = seg->hnext) if (seg->health) - P_KillMobj(seg, NULL, NULL); + P_KillMobj(seg, NULL, NULL, 0); base = next; } } @@ -4122,7 +4122,7 @@ static void P_Boss7Thinker(mobj_t *mobj) { INT32 i; - P_KillMobj(mobj, NULL, NULL); + P_KillMobj(mobj, NULL, NULL, 0); // It was a team effort for (i = 0; i < MAXPLAYERS; i++) @@ -4173,7 +4173,7 @@ static void P_Boss7Thinker(mobj_t *mobj) && players[i].mo->z < mobj->z + mobj->height + 128*FRACUNIT) // You can't be in the vicinity, either... { // Punch him! - P_DamageMobj(players[i].mo, mobj, mobj, 1); + P_DamageMobj(players[i].mo, mobj, mobj, 1, 0); mobj->state->nextstate = mobj->info->spawnstate; // Laugh @@ -4396,7 +4396,7 @@ static void P_Boss7Thinker(mobj_t *mobj) if (players[i].mo->z < mobj->z - 64*FRACUNIT) continue; - P_DamageMobj(players[i].mo, mobj, mobj, 1); + P_DamageMobj(players[i].mo, mobj, mobj, 1, 0); // Laugh S_StartSound(0, sfx_bewar1 + P_RandomKey(4)); @@ -5818,7 +5818,7 @@ void P_MobjThinker(mobj_t *mobj) if (mobj->flags & MF_FIRE && mobj->type != MT_PUMA && mobj->type != MT_FIREBALL && (mobj->eflags & (MFE_UNDERWATER|MFE_TOUCHWATER))) { - P_KillMobj(mobj, NULL, NULL); + P_KillMobj(mobj, NULL, NULL, 0); return; } } @@ -6450,7 +6450,7 @@ void P_MobjThinker(mobj_t *mobj) if (mobj->flags & MF_FIRE && mobj->type != MT_PUMA && mobj->type != MT_FIREBALL && (mobj->eflags & (MFE_UNDERWATER|MFE_TOUCHWATER))) { - P_KillMobj(mobj, NULL, NULL); + P_KillMobj(mobj, NULL, NULL, 0); return; } break; @@ -6699,7 +6699,7 @@ for (i = ((mobj->flags2 & MF2_STRONGBOX) ? strongboxamt : weakboxamt); i; --i) s if (mobj->flags & (MF_ENEMY|MF_BOSS) && mobj->health && P_CheckDeathPitCollide(mobj)) // extra pit check in case these didn't have momz { - P_KillMobj(mobj, NULL, NULL); + P_KillMobj(mobj, NULL, NULL, DMG_DEATHPIT); return; } @@ -6713,7 +6713,7 @@ for (i = ((mobj->flags2 & MF2_STRONGBOX) ? strongboxamt : weakboxamt); i; --i) s && !(mobj->flags & MF_NOCLIPHEIGHT) && mobj->health > 0) { - P_KillMobj(mobj, NULL, NULL); + P_KillMobj(mobj, NULL, NULL, DMG_CRUSHED); return; } } diff --git a/src/p_spec.c b/src/p_spec.c index b91a4a2ef..cb3340ee4 100644 --- a/src/p_spec.c +++ b/src/p_spec.c @@ -3472,19 +3472,19 @@ void P_ProcessSpecialSector(player_t *player, sector_t *sector, sector_t *rovers { case 1: // Damage (Generic) if (roversector || P_MobjReadyToTrigger(player->mo, sector)) - P_DamageMobj(player->mo, NULL, NULL, 1); + P_DamageMobj(player->mo, NULL, NULL, 1, 0); break; case 2: // Damage (Water) - if ((roversector || P_MobjReadyToTrigger(player->mo, sector)) && (player->powers[pw_underwater] || player->pflags & PF_NIGHTSMODE) && (player->powers[pw_shield] & SH_NOSTACK) != SH_ELEMENTAL) - P_DamageMobj(player->mo, NULL, NULL, 1); + if ((roversector || P_MobjReadyToTrigger(player->mo, sector)) && (player->powers[pw_underwater] || player->pflags & PF_NIGHTSMODE)) + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_WATER); break; case 3: // Damage (Fire) - if ((roversector || P_MobjReadyToTrigger(player->mo, sector)) && (player->powers[pw_shield] & SH_NOSTACK) != SH_ELEMENTAL) - P_DamageMobj(player->mo, NULL, NULL, 1); + if (roversector || P_MobjReadyToTrigger(player->mo, sector)) + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_FIRE); break; case 4: // Damage (Electrical) - if ((roversector || P_MobjReadyToTrigger(player->mo, sector)) && (player->powers[pw_shield] & SH_NOSTACK) != SH_ATTRACT) - P_DamageMobj(player->mo, NULL, NULL, 1); + if (roversector || P_MobjReadyToTrigger(player->mo, sector)) + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_ELECTRIC); break; case 5: // Spikes // Don't do anything. In Soviet Russia, spikes find you. @@ -3492,10 +3492,10 @@ void P_ProcessSpecialSector(player_t *player, sector_t *sector, sector_t *rovers case 6: // Death Pit (Camera Mod) case 7: // Death Pit (No Camera Mod) if (roversector || P_MobjReadyToTrigger(player->mo, sector)) - P_DamageMobj(player->mo, NULL, NULL, 10000); + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_DEATHPIT); break; case 8: // Instant Kill - P_DamageMobj(player->mo, NULL, NULL, 10000); + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_INSTAKILL); break; case 9: // Ring Drainer (Floor Touch) case 10: // Ring Drainer (No Floor Touch) @@ -3599,7 +3599,7 @@ void P_ProcessSpecialSector(player_t *player, sector_t *sector, sector_t *rovers mo2 = (mobj_t *)th; if (mo2->type == MT_EGGTRAP) - P_KillMobj(mo2, NULL, player->mo); + P_KillMobj(mo2, NULL, player->mo, 0); } // clear the special so you can't push the button twice. @@ -5355,9 +5355,9 @@ void T_LaserFlash(laserthink_t *flash) continue; if (thing->flags & MF_SHOOTABLE) - P_DamageMobj(thing, NULL, NULL, 1); + P_DamageMobj(thing, NULL, NULL, 1, 0); else if (thing->type == MT_EGGSHIELD) - P_KillMobj(thing, NULL, NULL); + P_KillMobj(thing, NULL, NULL, 0); } } diff --git a/src/p_tick.c b/src/p_tick.c index 2973505f3..15d3abc80 100644 --- a/src/p_tick.c +++ b/src/p_tick.c @@ -662,7 +662,7 @@ void P_Ticker(boolean run) if (!players[i].mo) continue; - P_DamageMobj(players[i].mo, NULL, NULL, 10000); + P_DamageMobj(players[i].mo, NULL, NULL, 1, DMG_INSTAKILL); } } diff --git a/src/p_user.c b/src/p_user.c index f8e634e48..7962c74bb 100644 --- a/src/p_user.c +++ b/src/p_user.c @@ -632,7 +632,7 @@ static void P_DeNightserizePlayer(player_t *player) continue; if (mo2->flags & MF_AMBUSH) - P_DamageMobj(player->mo, NULL, NULL, 10000); + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_INSTAKILL); break; } @@ -1998,21 +1998,15 @@ static void P_CheckUnderwaterAndSpaceTimer(player_t *player) // Underwater timer runs out else if (player->powers[pw_underwater] == 1) { - mobj_t *killer; - if ((netgame || multiplayer) && P_IsLocalPlayer(player)) S_ChangeMusic(mapmusic, true); - - killer = P_SpawnMobj(player->mo->x, player->mo->y, player->mo->z, MT_NULL); - killer->threshold = 42; // Special flag that it was drowning which killed you. - P_DamageMobj(player->mo, killer, killer, 10000); + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_DROWNED); } else if (player->powers[pw_spacetime] == 1) { if ((netgame || multiplayer) && P_IsLocalPlayer(player)) S_ChangeMusic(mapmusic, true); - - P_DamageMobj(player->mo, NULL, NULL, 10000); + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_SPACEDROWN); } if (numbermobj) @@ -6016,7 +6010,7 @@ static void P_NiGHTSMovement(player_t *player) if (player->powers[pw_flashing] == 1) player->powers[pw_flashing] = 3; else - P_DamageMobj(player->mo, NULL, NULL, 1); + P_DamageMobj(player->mo, NULL, NULL, 1, 0); } if (movingangle >= ANGLE_90 && movingangle <= ANGLE_180) @@ -6378,7 +6372,7 @@ static void P_MovePlayer(player_t *player) players[i].exiting = (14*TICRATE)/5 + 1; } else if (player->health > 1) - P_DamageMobj(player->mo, NULL, NULL, 1); + P_DamageMobj(player->mo, NULL, NULL, 1, 0); player->pflags &= ~PF_NIGHTSFALL; } } @@ -6906,13 +6900,9 @@ static void P_MovePlayer(player_t *player) else if (player->mo->ceilingz - player->mo->floorz < player->mo->height) { if ((netgame || multiplayer) && player->spectator) - P_DamageMobj(player->mo, NULL, NULL, 42000); // Respawn crushed spectators + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_SPECTATOR); // Respawn crushed spectators else - { - mobj_t *killer = P_SpawnMobj(player->mo->x, player->mo->y, player->mo->z, MT_NULL); - killer->threshold = 44; // Special flag that it was crushing which killed you. - P_DamageMobj(player->mo, killer, killer, 10000); - } + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_CRUSHED); if (player->playerstate == PST_DEAD) return; @@ -7343,7 +7333,7 @@ static void P_NukeAllPlayers(player_t *player) if (mo == player->mo) continue; - P_DamageMobj(mo, player->mo, player->mo, 1); + P_DamageMobj(mo, player->mo, player->mo, 1, 0); } CONS_Printf(M_GetText("%s caused a world of pain.\n"), player_names[player-players]); @@ -7401,12 +7391,12 @@ void P_NukeEnemies(mobj_t *inflictor, mobj_t *source, fixed_t radius) mo->flags |= MF_SPECIAL|MF_SHOOTABLE; if (mo->type == MT_EGGGUARD && mo->tracer) //nuke Egg Guard's shield! - P_KillMobj(mo->tracer, inflictor, source); + P_KillMobj(mo->tracer, inflictor, source, 0); if (mo->flags & MF_BOSS || mo->type == MT_PLAYER) //don't OHKO bosses nor players! - P_DamageMobj(mo, inflictor, source, 1); + P_DamageMobj(mo, inflictor, source, 1, 0); else - P_DamageMobj(mo, inflictor, source, 1000); + P_DamageMobj(mo, inflictor, source, 1000, 0); } } @@ -8679,7 +8669,7 @@ void P_PlayerThink(player_t *player) } player->lives = 2; // Don't start the game over music! - P_DamageMobj(player->mo, NULL, NULL, 10000); + P_DamageMobj(player->mo, NULL, NULL, 1, DMG_INSTAKILL); player->lives = 0; if (player->playerstate == PST_DEAD)