diff --git a/src/d_player.h b/src/d_player.h index 4e29da8f0..11611cded 100644 --- a/src/d_player.h +++ b/src/d_player.h @@ -225,7 +225,7 @@ enum WF_USER2OK = 1 << 9, WF_USER3OK = 1 << 10, WF_USER4OK = 1 << 11, -}; +}; #define WPIECE1 1 #define WPIECE2 2 diff --git a/src/g_shared/a_pickups.h b/src/g_shared/a_pickups.h index 80e1744e6..413b01db3 100644 --- a/src/g_shared/a_pickups.h +++ b/src/g_shared/a_pickups.h @@ -305,9 +305,7 @@ public: virtual FState *GetReadyState (); virtual FState *GetAtkState (bool hold); virtual FState *GetAltAtkState (bool hold); - virtual FState *GetRelState (); - virtual FState *GetZoomState (); - virtual FState *GetUserState(int state); + virtual FState *GetStateForButtonName (FName button); virtual void PostMorphWeapon (); virtual void EndPowerup (); diff --git a/src/g_shared/a_weapons.cpp b/src/g_shared/a_weapons.cpp index 79546737e..9c71ab0ea 100644 --- a/src/g_shared/a_weapons.cpp +++ b/src/g_shared/a_weapons.cpp @@ -683,47 +683,13 @@ FState *AWeapon::GetAltAtkState (bool hold) //=========================================================================== // -// AWeapon :: GetRelState +// AWeapon :: GetStateForButtonName // //=========================================================================== -FState *AWeapon::GetRelState () +FState *AWeapon::GetStateForButtonName (FName button) { - return FindState(NAME_Reload); -} - -//=========================================================================== -// -// AWeapon :: GetZoomState -// -//=========================================================================== - -FState *AWeapon::GetZoomState () -{ - return FindState(NAME_Zoom); -} - -//=========================================================================== -// -// AWeapon :: GetUserState -// -//=========================================================================== - -FState *AWeapon::GetUserState(int state) -{ - switch (state) - { - case 4: - return FindState(NAME_User4); - case 3: - return FindState(NAME_User3); - case 2: - return FindState(NAME_User2); - case 1: - return FindState(NAME_User1); - default: - return NULL; - } + return FindState(button); } diff --git a/src/p_pspr.cpp b/src/p_pspr.cpp index 9f3a24bad..ed7d675d3 100644 --- a/src/p_pspr.cpp +++ b/src/p_pspr.cpp @@ -38,6 +38,30 @@ // TYPES ------------------------------------------------------------------- +struct FGenericButtons +{ + int ReadyFlag; // Flag passed to A_WeaponReady + int StateFlag; // Flag set in WeaponState + int ButtonFlag; // Button to press + ENamedName StateName; // Name of the button/state +}; + +enum EWRF_Options +{ + WRF_NoBob = 1, + WRF_NoSwitch = 1 << 1, + WRF_NoPrimary = 1 << 2, + WRF_NoSecondary = 1 << 3, + WRF_NoFire = WRF_NoPrimary | WRF_NoSecondary, + WRF_AllowReload = 1 << 4, + WRF_AllowZoom = 1 << 5, + WRF_DisableSwitch = 1 << 6, + WRF_AllowUser1 = 1 << 7, + WRF_AllowUser2 = 1 << 8, + WRF_AllowUser3 = 1 << 9, + WRF_AllowUser4 = 1 << 10, +}; + // EXTERNAL FUNCTION PROTOTYPES -------------------------------------------- // PUBLIC FUNCTION PROTOTYPES ---------------------------------------------- @@ -57,6 +81,16 @@ CVAR(Int, sv_fastweapons, false, CVAR_SERVERINFO); static FRandom pr_wpnreadysnd ("WpnReadySnd"); static FRandom pr_gunshot ("GunShot"); +static const FGenericButtons ButtonChecks[] = +{ + { WRF_AllowReload, WF_WEAPONZOOMOK, BT_ZOOM, NAME_Zoom }, + { WRF_AllowZoom, WF_WEAPONRELOADOK, BT_RELOAD, NAME_Reload }, + { WRF_AllowUser1, WF_USER1OK, BT_USER1, NAME_User1 }, + { WRF_AllowUser2, WF_USER2OK, BT_USER2, NAME_User2 }, + { WRF_AllowUser3, WF_USER3OK, BT_USER3, NAME_User3 }, + { WRF_AllowUser4, WF_USER4OK, BT_USER4, NAME_User4 }, +}; + // CODE -------------------------------------------------------------------- //--------------------------------------------------------------------------- @@ -290,94 +324,6 @@ void P_FireWeaponAlt (player_t *player, FState *state) } } -//--------------------------------------------------------------------------- -// -// PROC P_ReloadWeapon -// -//--------------------------------------------------------------------------- - -void P_ReloadWeapon (player_t *player, FState *state) -{ - AWeapon *weapon; - if (player->Bot == NULL && bot_observer) - { - return; - } - - weapon = player->ReadyWeapon; - if (weapon == NULL) - { - return; - } - - if (state == NULL) - { - state = weapon->GetRelState(); - } - // [XA] don't change state if still null, so if the modder sets - // WRF_RELOAD to true but forgets to define the Reload state, the weapon - // won't disappear. ;) - if (state != NULL) - P_SetPsprite (player, ps_weapon, state); -} - -//--------------------------------------------------------------------------- -// -// PROC P_ZoomWeapon -// -//--------------------------------------------------------------------------- - -void P_ZoomWeapon (player_t *player, FState *state) -{ - AWeapon *weapon; - if (player->Bot == NULL && bot_observer) - { - return; - } - - weapon = player->ReadyWeapon; - if (weapon == NULL) - { - return; - } - - if (state == NULL) - { - state = weapon->GetZoomState(); - } - // [XA] don't change state if still null. Same reasons as above. - if (state != NULL) - P_SetPsprite (player, ps_weapon, state); -} - -//-------------------------------------------------------------------------- - -// -// PROC P_UserStateWeapon -// -//--------------------------------------------------------------------------- - -void P_UserStateWeapon(player_t *player, FState *state, int userstate) -{ - if (!userstate) - return; - - AWeapon *weapon; - if (player->Bot == NULL && bot_observer) - return; - - weapon = player->ReadyWeapon; - if (weapon == NULL) - return; - - if (state == NULL) - { - state = weapon->GetUserState(userstate); - } - if (state != NULL) - P_SetPsprite(player, ps_weapon, state); -} - - //--------------------------------------------------------------------------- // // PROC P_DropWeapon @@ -591,33 +537,21 @@ void DoReadyWeaponToBob (AActor *self) } } -void DoReadyWeaponToReload (AActor *self) +void DoReadyWeaponToGeneric(AActor *self, int paramflags) { - // Prepare for reload action. - player_t *player; - if (self && (player = self->player)) - player->WeaponState |= WF_WEAPONRELOADOK; - return; -} + int flags = 0; -void DoReadyWeaponToZoom (AActor *self) -{ - // Prepare for zoom action. - player_t *player; - if (self && (player = self->player)) - player->WeaponState |= WF_WEAPONZOOMOK; - return; -} - -void DoReadyWeaponToUser(AActor *self, int userStates) -{ - // Prepare for user state action. - player_t *player; - if (self && (player = self->player) && userStates) + for (size_t i = 0; i < countof(ButtonChecks); ++i) { - player->WeaponState |= userStates; + if (paramflags & ButtonChecks[i].ReadyFlag) + { + flags |= ButtonChecks[i].StateFlag; + } + } + if (self != NULL && self->player != NULL) + { + self->player->WeaponState |= flags; } - return; } // This function replaces calls to A_WeaponReady in other codepointers. @@ -626,27 +560,9 @@ void DoReadyWeapon(AActor *self) DoReadyWeaponToBob(self); DoReadyWeaponToFire(self); DoReadyWeaponToSwitch(self); - DoReadyWeaponToReload(self); - DoReadyWeaponToZoom(self); - DoReadyWeaponToUser(self, (WF_USER1OK | WF_USER2OK | WF_USER3OK | WF_USER4OK)); + DoReadyWeaponToGeneric(self, ~0); } -enum EWRF_Options -{ - WRF_NoBob = 1, - WRF_NoSwitch = 1 << 1, - WRF_NoPrimary = 1 << 2, - WRF_NoSecondary = 1 << 3, - WRF_NoFire = WRF_NoPrimary + WRF_NoSecondary, - WRF_AllowReload = 1 << 4, - WRF_AllowZoom = 1 << 5, - WRF_DisableSwitch = 1 << 6, - WRF_User1 = 1 << 7, - WRF_User2 = 1 << 8, - WRF_User3 = 1 << 9, - WRF_User4 = 1 << 10, -}; - DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_WeaponReady) { ACTION_PARAM_START(1); @@ -655,17 +571,8 @@ DEFINE_ACTION_FUNCTION_PARAMS(AInventory, A_WeaponReady) DoReadyWeaponToSwitch(self, !(paramflags & WRF_NoSwitch)); if ((paramflags & WRF_NoFire) != WRF_NoFire) DoReadyWeaponToFire(self, !(paramflags & WRF_NoPrimary), !(paramflags & WRF_NoSecondary)); if (!(paramflags & WRF_NoBob)) DoReadyWeaponToBob(self); - if ((paramflags & WRF_AllowReload)) DoReadyWeaponToReload(self); - if ((paramflags & WRF_AllowZoom)) DoReadyWeaponToZoom(self); - - int userStates = 0; - if (paramflags & WRF_User1) userStates |= WF_USER1OK; - if (paramflags & WRF_User2) userStates |= WF_USER2OK; - if (paramflags & WRF_User3) userStates |= WF_USER3OK; - if (paramflags & WRF_User4) userStates |= WF_USER4OK; - if (userStates) DoReadyWeaponToUser(self, userStates); - - DoReadyWeaponDisableSwitch(self, paramflags & WRF_DisableSwitch); + DoReadyWeaponToGeneric(self, paramflags); + DoReadyWeaponDisableSwitch(self, paramflags & WRF_DisableSwitch); } //--------------------------------------------------------------------------- @@ -742,79 +649,40 @@ void P_CheckWeaponSwitch (player_t *player) //--------------------------------------------------------------------------- // -// PROC P_CheckWeaponReload +// PROC P_CheckWeaponButtons // -// The player can reload the weapon. +// Check extra button presses for weapons. // //--------------------------------------------------------------------------- -void P_CheckWeaponReload (player_t *player) +static void P_CheckWeaponButtons (player_t *player) { - AWeapon *weapon = player->ReadyWeapon; - - if (weapon == NULL) + if (player->Bot == NULL && bot_observer) + { return; - - // Check for reload. - if ((player->WeaponState & WF_WEAPONRELOADOK) && (player->cmd.ucmd.buttons & BT_RELOAD)) - { - P_ReloadWeapon (player, NULL); } -} - -//--------------------------------------------------------------------------- -// -// PROC P_CheckWeaponZoom -// -// The player can use the weapon's zoom function. -// -//--------------------------------------------------------------------------- - -void P_CheckWeaponZoom (player_t *player) -{ AWeapon *weapon = player->ReadyWeapon; - if (weapon == NULL) + { return; - - // Check for zoom. - if ((player->WeaponState & WF_WEAPONZOOMOK) && (player->cmd.ucmd.buttons & BT_ZOOM)) - { - P_ZoomWeapon (player, NULL); } -} - -//--------------------------------------------------------------------------- -// -// PROC P_CheckWeaponUserState -// -// The player can use the weapon's user state functionalities. -// -//--------------------------------------------------------------------------- - -void P_CheckWeaponUserState(player_t *player) -{ - AWeapon *weapon = player->ReadyWeapon; - - if (weapon == NULL) - return; - - // Check for user state(s). - if ((player->WeaponState & WF_USER1OK) && (player->cmd.ucmd.buttons & BT_USER1)) + // The button checks are ordered by precedence. The first one to match a + // button press and affect a state change wins. + for (size_t i = 0; i < countof(ButtonChecks); ++i) { - P_UserStateWeapon(player, NULL, 1); - } - else if ((player->WeaponState & WF_USER2OK) && (player->cmd.ucmd.buttons & BT_USER2)) - { - P_UserStateWeapon(player, NULL, 2); - } - else if ((player->WeaponState & WF_USER3OK) && (player->cmd.ucmd.buttons & BT_USER3)) - { - P_UserStateWeapon(player, NULL, 3); - } - else if ((player->WeaponState & WF_USER4OK) && (player->cmd.ucmd.buttons & BT_USER4)) - { - P_UserStateWeapon(player, NULL, 4); + if ((player->WeaponState & ButtonChecks[i].StateFlag) && + (player->cmd.ucmd.buttons & ButtonChecks[i].ButtonFlag)) + { + FState *state = weapon->GetStateForButtonName(ButtonChecks[i].StateName); + // [XA] don't change state if still null, so if the modder + // sets WRF_xxx to true but forgets to define the corresponding + // state, the weapon won't disappear. ;) + if (state != NULL) + { + P_SetPsprite(player, ps_weapon, state); + return; + } + } } } @@ -1181,18 +1049,9 @@ void P_MovePsprites (player_t *player) { P_CheckWeaponFire (player); } - if (player->WeaponState & WF_WEAPONRELOADOK) - { - P_CheckWeaponReload (player); - } - if (player->WeaponState & WF_WEAPONZOOMOK) - { - P_CheckWeaponZoom (player); - } - if (player->WeaponState & (WF_USER1OK | WF_USER2OK | WF_USER3OK | WF_USER4OK)) - { - P_CheckWeaponUserState(player); - } + + // Check custom buttons + P_CheckWeaponButtons(player); } } diff --git a/wadsrc/static/actors/constants.txt b/wadsrc/static/actors/constants.txt index 1e4db4092..213e2109d 100644 --- a/wadsrc/static/actors/constants.txt +++ b/wadsrc/static/actors/constants.txt @@ -129,10 +129,10 @@ const int WRF_NOFIRE = WRF_NOPRIMARY | WRF_NOSECONDARY; const int WRF_ALLOWRELOAD = 16; const int WRF_ALLOWZOOM = 32; const int WRF_DISABLESWITCH = 64; -const int WRF_USER1 = 128; -const int WRF_USER2 = 256; -const int WRF_USER3 = 512; -const int WRF_USER4 = 1024; +const int WRF_ALLOWUSER1 = 128; +const int WRF_ALLOWUSER2 = 256; +const int WRF_ALLOWUSER3 = 512; +const int WRF_ALLOWUSER4 = 1024; // Morph constants const int MRF_ADDSTAMINA = 1;