From b6a8df557ea5290b11d65cc0bd11d11ce58fa53d Mon Sep 17 00:00:00 2001 From: Yukita Mayako Date: Wed, 27 May 2015 00:45:34 -0400 Subject: [PATCH] New Match weapon/ammo dropping method. P_PlayerWeaponPanelOrAmmoBurst will go through all of the player's weapon rings and either drop the weapon panel itself (with no ammo attached, and no ammo taken away!) OR if the player has ammo but no weapon, it drops the ammo instead (and you lose it). --- src/lua_baselib.c | 11 +++++++ src/p_inter.c | 77 +++++++++++++++++++++++++++++++++++++++++++---- src/p_local.h | 1 + 3 files changed, 83 insertions(+), 6 deletions(-) diff --git a/src/lua_baselib.c b/src/lua_baselib.c index 9b0a34f17..57bee95ed 100644 --- a/src/lua_baselib.c +++ b/src/lua_baselib.c @@ -1100,6 +1100,16 @@ static int lib_pPlayerWeaponAmmoBurst(lua_State *L) return 0; } +static int lib_pPlayerWeaponPanelOrAmmoBurst(lua_State *L) +{ + player_t *player = *((player_t **)luaL_checkudata(L, 1, META_PLAYER)); + NOHUD + if (!player) + return LUA_ErrInvalid(L, "player_t"); + P_PlayerWeaponPanelOrAmmoBurst(player); + return 0; +} + static int lib_pPlayerEmeraldBurst(lua_State *L) { player_t *player = *((player_t **)luaL_checkudata(L, 1, META_PLAYER)); @@ -1965,6 +1975,7 @@ static luaL_Reg lib[] = { {"P_PlayerRingBurst",lib_pPlayerRingBurst}, {"P_PlayerWeaponPanelBurst",lib_pPlayerWeaponPanelBurst}, {"P_PlayerWeaponAmmoBurst",lib_pPlayerWeaponAmmoBurst}, + {"P_PlayerWeaponPanelOrAmmoBurst", lib_pPlayerWeaponPanelOrAmmoBurst}, {"P_PlayerEmeraldBurst",lib_pPlayerEmeraldBurst}, {"P_PlayerFlagBurst",lib_pPlayerFlagBurst}, {"P_PlayRinglossSound",lib_pPlayRinglossSound}, diff --git a/src/p_inter.c b/src/p_inter.c index d305cfc83..97a8624c1 100644 --- a/src/p_inter.c +++ b/src/p_inter.c @@ -437,7 +437,7 @@ void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck) { INT32 pindex = special->info->mass - (INT32)pw_infinityring; - player->powers[special->info->mass] += (UINT16)special->info->reactiontime; + player->powers[special->info->mass] += (UINT16)special->reactiontime; player->ringweapons |= 1 << (pindex-1); if (player->powers[special->info->mass] > rw_maximums[pindex]) @@ -3093,11 +3093,7 @@ void P_PlayerRingBurst(player_t *player, INT32 num_rings) P_PlayerEmeraldBurst(player, false); // Spill weapons first - if (player->ringweapons) - P_PlayerWeaponPanelBurst(player); - - // Spill the ammo - P_PlayerWeaponAmmoBurst(player); + P_PlayerWeaponPanelOrAmmoBurst(player); for (i = 0; i < num_rings; i++) { @@ -3354,6 +3350,75 @@ void P_PlayerWeaponAmmoBurst(player_t *player) } } +void P_PlayerWeaponPanelOrAmmoBurst(player_t *player) +{ + mobj_t *mo; + angle_t fa; + fixed_t ns; + INT32 i = 0; + fixed_t z; + + #define SETUP_DROP(thingtype) \ + z = player->mo->z; \ + if (player->mo->eflags & MFE_VERTICALFLIP) \ + z += player->mo->height - mobjinfo[thingtype].height; \ + fa = ((i*FINEANGLES/16) + (player->mo->angle>>ANGLETOFINESHIFT)) & FINEMASK; \ + ns = FixedMul(3*FRACUNIT, player->mo->scale); \ + + #define DROP_WEAPON(rwflag, pickup, ammo, power) \ + if (player->ringweapons & rwflag) \ + { \ + player->ringweapons &= ~rwflag; \ + SETUP_DROP(pickup) \ + mo = P_SpawnMobj(player->mo->x, player->mo->y, z, pickup); \ + mo->reactiontime = 0; \ + mo->flags2 |= MF2_DONTRESPAWN; \ + mo->flags &= ~(MF_NOGRAVITY|MF_NOCLIPHEIGHT); \ + P_SetTarget(&mo->target, player->mo); \ + mo->fuse = 12*TICRATE; \ + mo->destscale = player->mo->scale; \ + P_SetScale(mo, player->mo->scale); \ + mo->momx = FixedMul(FINECOSINE(fa),ns); \ + if (!(twodlevel || (player->mo->flags2 & MF2_TWOD))) \ + mo->momy = FixedMul(FINESINE(fa),ns); \ + P_SetObjectMomZ(mo, 4*FRACUNIT, false); \ + if (i & 1) \ + P_SetObjectMomZ(mo, 4*FRACUNIT, true); \ + ++i; \ + } \ + else if (player->powers[power] > 0) \ + { \ + SETUP_DROP(ammo) \ + mo = P_SpawnMobj(player->mo->x, player->mo->y, z, ammo); \ + mo->health = player->powers[power]; \ + mo->flags2 |= MF2_DONTRESPAWN; \ + mo->flags &= ~(MF_NOGRAVITY|MF_NOCLIPHEIGHT); \ + P_SetTarget(&mo->target, player->mo); \ + mo->fuse = 12*TICRATE; \ + mo->destscale = player->mo->scale; \ + P_SetScale(mo, player->mo->scale); \ + mo->momx = FixedMul(FINECOSINE(fa),ns); \ + if (!(twodlevel || (player->mo->flags2 & MF2_TWOD))) \ + mo->momy = FixedMul(FINESINE(fa),ns); \ + P_SetObjectMomZ(mo, 3*FRACUNIT, false); \ + if (i & 1) \ + P_SetObjectMomZ(mo, 3*FRACUNIT, true); \ + player->powers[power] = 0; \ + ++i; \ + } + + DROP_WEAPON(RW_BOUNCE, MT_BOUNCEPICKUP, MT_BOUNCERING, pw_bouncering); + DROP_WEAPON(RW_RAIL, MT_RAILPICKUP, MT_RAILRING, pw_railring); + DROP_WEAPON(RW_AUTO, MT_AUTOPICKUP, MT_AUTOMATICRING, pw_automaticring); + DROP_WEAPON(RW_EXPLODE, MT_EXPLODEPICKUP, MT_EXPLOSIONRING, pw_explosionring); + DROP_WEAPON(RW_SCATTER, MT_SCATTERPICKUP, MT_SCATTERRING, pw_scatterring); + DROP_WEAPON(RW_GRENADE, MT_GRENADEPICKUP, MT_GRENADERING, pw_grenadering); + DROP_WEAPON(0, 0, MT_INFINITYRING, pw_infinityring); + + #undef DROP_WEAPON + #undef SETUP_DROP +} + // // P_PlayerEmeraldBurst // diff --git a/src/p_local.h b/src/p_local.h index 1e0a9e2eb..337cc3663 100644 --- a/src/p_local.h +++ b/src/p_local.h @@ -371,6 +371,7 @@ void P_KillMobj(mobj_t *target, mobj_t *inflictor, mobj_t *source, UINT8 damaget 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); +void P_PlayerWeaponPanelOrAmmoBurst(player_t *player); void P_PlayerEmeraldBurst(player_t *player, boolean toss); void P_TouchSpecialThing(mobj_t *special, mobj_t *toucher, boolean heightcheck);