diff options
| author | FluorescentCIAAfricanAmerican <[email protected]> | 2020-04-22 12:56:21 -0400 |
|---|---|---|
| committer | FluorescentCIAAfricanAmerican <[email protected]> | 2020-04-22 12:56:21 -0400 |
| commit | 3bf9df6b2785fa6d951086978a3e66f49427166a (patch) | |
| tree | 2c0f1f0c63c4832882bc93814ebd2c2b1c6224e5 /game/client/tf/tf_hud_menu_engy_destroy.cpp | |
| download | archived-source-engine-2018-hl2-src-master.tar.xz archived-source-engine-2018-hl2-src-master.zip | |
Diffstat (limited to 'game/client/tf/tf_hud_menu_engy_destroy.cpp')
| -rw-r--r-- | game/client/tf/tf_hud_menu_engy_destroy.cpp | 410 |
1 files changed, 410 insertions, 0 deletions
diff --git a/game/client/tf/tf_hud_menu_engy_destroy.cpp b/game/client/tf/tf_hud_menu_engy_destroy.cpp new file mode 100644 index 0000000..d8d3a5f --- /dev/null +++ b/game/client/tf/tf_hud_menu_engy_destroy.cpp @@ -0,0 +1,410 @@ +//========= Copyright Valve Corporation, All rights reserved. ============// +// +// Purpose: +// +// $NoKeywords: $ +//============================================================================= + +#include "cbase.h" +#include "hud.h" +#include "hudelement.h" +#include "c_tf_player.h" +#include "iclientmode.h" +#include "ienginevgui.h" +#include "tf_gamerules.h" +#include <vgui/ILocalize.h> +#include <vgui/ISurface.h> +#include <vgui/IVGui.h> +#include "c_baseobject.h" + +#include "tf_hud_menu_engy_destroy.h" +#include "tf_hud_menu_engy_build.h" + +// memdbgon must be the last include file in a .cpp file!!! +#include "tier0/memdbgon.h" + +using namespace vgui; + +extern const EngyConstructBuilding_t g_kEngyBuildings[]; + +//====================================== + +DECLARE_BUILD_FACTORY( CEngyDestroyMenuItem ); + + +//====================================== + +DECLARE_HUDELEMENT_DEPTH( CHudMenuEngyDestroy, 40 ); // in front of engy building status + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +CHudMenuEngyDestroy::CHudMenuEngyDestroy( const char *pElementName ) + : CHudBaseBuildMenu( pElementName, "HudMenuEngyDestroy" ) +{ + Panel *pParent = g_pClientMode->GetViewport(); + SetParent( pParent ); + + m_iCurrentDestroyMenuLayout = DESTROYMENU_DEFAULT; + + SetHiddenBits( HIDEHUD_MISCSTATUS ); + + for ( int i=0; i<NUM_ENGY_BUILDINGS; i++ ) + { + char buf[32]; + + Q_snprintf( buf, sizeof(buf), "active_item_%d", i+1 ); + m_pActiveItems[i] = new CEngyDestroyMenuItem( this, buf ); + + Q_snprintf( buf, sizeof(buf), "inactive_item_%d", i+1 ); + m_pInactiveItems[i] = new CEngyDestroyMenuItem( this, buf ); + + Q_snprintf( buf, sizeof(buf), "unavailable_item_%d", i+1 ); + m_pUnavailableItems[i] = new CEngyDestroyMenuItem( this, buf ); + } + + vgui::ivgui()->AddTickSignal( GetVPanel() ); + + RegisterForRenderGroup( "mid" ); +} + +//----------------------------------------------------------------------------- +// Purpose: called whenever a new level is starting +//----------------------------------------------------------------------------- +void CHudMenuEngyDestroy::LevelInit( void ) +{ + //RecalculateBuildingItemState( ALL_BUILDINGS ); + + CHudElement::LevelInit(); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void CHudMenuEngyDestroy::ApplySchemeSettings( IScheme *pScheme ) +{ + const char *pszCustomDir = NULL; + switch( m_iCurrentDestroyMenuLayout ) + { + case DESTROYMENU_PIPBOY: + pszCustomDir = "resource/UI/destroy_menu/pipboy"; + break; + + default: + case DESTROYMENU_DEFAULT: + pszCustomDir = "resource/UI/destroy_menu"; + break; + } + + // load control settings... + LoadControlSettings( VarArgs("%s/HudMenuEngyDestroy.res",pszCustomDir) ); + + for ( int i=0; i<NUM_ENGY_BUILDINGS; ++i ) + { + CExLabel *pNumberLabel = NULL; + if ( m_Buildings[i].m_pszDestroyActiveObjectRes ) + { + m_pActiveItems[i]->LoadControlSettings( VarArgs( "%s/%s", pszCustomDir, m_Buildings[i].m_pszDestroyActiveObjectRes ) ); + } + + if ( m_Buildings[i].m_pszDestroyInactiveObjectRes ) + { + m_pInactiveItems[i]->LoadControlSettings( VarArgs( "%s/%s", pszCustomDir, m_Buildings[i].m_pszDestroyInactiveObjectRes ) ); + } + + if ( m_Buildings[i].m_pszDestroyUnavailableObjectRes ) + { + m_pUnavailableItems[i]->LoadControlSettings( VarArgs( "%s/%s", pszCustomDir, m_Buildings[i].m_pszDestroyUnavailableObjectRes ) ); + } + + // Set the Numerical Number + pNumberLabel = dynamic_cast<CExLabel *>( m_pActiveItems[i]->FindChildByName( "NumberLabel" ) ); + if ( pNumberLabel ) + { + pNumberLabel->SetText( VarArgs( "%d", i + 1 ) ); + } + pNumberLabel = dynamic_cast<CExLabel *>( m_pInactiveItems[i]->FindChildByName( "NumberLabel" ) ); + if ( pNumberLabel ) + { + pNumberLabel->SetText( VarArgs( "%d", i + 1 ) ); + } + pNumberLabel = dynamic_cast<CExLabel *>( m_pUnavailableItems[i]->FindChildByName( "NumberLabel" ) ); + if ( pNumberLabel ) + { + pNumberLabel->SetText( VarArgs( "%d", i + 1 ) ); + } + } + + for ( int i = 0; i < NUM_ENGY_BUILDINGS; ++i ) + { + vgui::Panel* pNotBuiltLabel = m_pUnavailableItems[i]->FindChildByName( "NotBuiltLabel" ); + vgui::Panel* pUnavailableLabel = m_pUnavailableItems[i]->FindChildByName( "UnavailableLabel" ); + if ( pNotBuiltLabel ) + { + pNotBuiltLabel->SetVisible( false ); + } + if ( pUnavailableLabel ) + { + pUnavailableLabel->SetVisible( true ); + } + } + + BaseClass::ApplySchemeSettings( pScheme ); +} + +//----------------------------------------------------------------------------- +// Purpose: Keyboard input hook. Return 0 if handled +//----------------------------------------------------------------------------- +int CHudMenuEngyDestroy::HudElementKeyInput( int down, ButtonCode_t keynum, const char *pszCurrentBinding ) +{ + if ( !ShouldDraw() ) + { + return 1; + } + + if ( !down ) + { + return 1; + } + + C_TFPlayer *pLocalPlayer = C_TFPlayer::GetLocalTFPlayer(); + + if ( !pLocalPlayer ) + return 1; + + bool bCanDestroyBuildings = true; + if ( TFGameRules() && TFGameRules()->IsInTraining() ) + { + ConVarRef training_can_destroy_buildings("training_can_destroy_buildings"); + bCanDestroyBuildings = training_can_destroy_buildings.GetBool(); + } + if ( bCanDestroyBuildings == false ) + { + return 1; + } + + bool bHandled = false; + + int iSlot = -1; + + // convert slot1, slot2 etc to 1,2,3,4 + if( pszCurrentBinding && !Q_strncmp( pszCurrentBinding, "slot", NUM_ENGY_BUILDINGS ) && Q_strlen(pszCurrentBinding) > NUM_ENGY_BUILDINGS ) + { + const char *pszNum = pszCurrentBinding+NUM_ENGY_BUILDINGS; + iSlot = atoi(pszNum); + + // slot10 cancels + if ( iSlot == 10 ) + { + engine->ExecuteClientCmd( "lastinv" ); + return 0; + } + + iSlot -= 1; // adjust to be 0 based + + // allow slot1 - slot4 + if ( iSlot < 0 || iSlot > 3 ) + return 1; + } + else + { + switch( keynum ) + { + case KEY_1: + case KEY_XBUTTON_UP: + iSlot = 0; + bHandled = true; + break; + case KEY_2: + case KEY_XBUTTON_RIGHT: + iSlot = 1; + bHandled = true; + break; + case KEY_3: + case KEY_XBUTTON_DOWN: + iSlot = 2; + bHandled = true; + break; + case KEY_4: + case KEY_XBUTTON_LEFT: + iSlot = 3; + bHandled = true; + break; + + case KEY_5: + case KEY_6: + case KEY_7: + case KEY_8: + case KEY_9: + // Eat these keys + bHandled = true; + break; + + case KEY_0: + case KEY_XBUTTON_B: + engine->ExecuteClientCmd( "lastinv" ); + bHandled = true; + break; + + default: + break; + } + } + + if ( iSlot >= 0 ) + { + int iBuildingID, iMode; + CHudMenuEngyBuild::GetBuildingIDAndModeFromSlot( iSlot+1, iBuildingID, iMode, m_Buildings ); + + C_BaseObject *pObj = pLocalPlayer->GetObjectOfType( iBuildingID, iMode ); + + if ( pObj && !pObj->HasSapper() && !pObj->IsPlasmaDisabled() ) + { + char szCmd[128]; + Q_snprintf( szCmd, sizeof(szCmd), "destroy %d %d; lastinv", iBuildingID, iMode ); + engine->ExecuteClientCmd( szCmd ); + } + else + { + ErrorSound(); + } + } + + // return 0 if we ate the key + return ( bHandled == false ); +} + +void CHudMenuEngyDestroy::ErrorSound( void ) +{ + C_TFPlayer *pLocalPlayer = C_TFPlayer::GetLocalTFPlayer(); + + if ( pLocalPlayer ) + { + pLocalPlayer->EmitSound( "Player.DenyWeaponSelection" ); + } +} + + +void CHudMenuEngyDestroy::OnTick( void ) +{ + C_TFPlayer *pLocalPlayer = C_TFPlayer::GetLocalTFPlayer(); + + bool bCanDestroyBuildings = true; + if ( TFGameRules() && TFGameRules()->IsInTraining() ) + { + ConVarRef training_can_destroy_buildings("training_can_destroy_buildings"); + bCanDestroyBuildings = training_can_destroy_buildings.GetBool(); + } + + int i; + + for ( i=0;i<NUM_ENGY_BUILDINGS; i++ ) + { + int iRemappedObjectID, iMode; + CHudMenuEngyBuild::GetBuildingIDAndModeFromSlot( i + 1, iRemappedObjectID, iMode, m_Buildings ); + + // update this slot + C_BaseObject *pObj = NULL; + + if ( pLocalPlayer ) + { + pObj = pLocalPlayer->GetObjectOfType( iRemappedObjectID, iMode ); + } + + // If the building is built, we can destroy it + // unless we are in training, then we check the convar + if( m_Buildings[i].m_bEnabled == false ) + { + m_pActiveItems[i]->SetVisible( false ); + m_pInactiveItems[i]->SetVisible( false ); + m_pUnavailableItems[i]->SetVisible( false ); + } + else if ( bCanDestroyBuildings == false ) + { + m_pActiveItems[i]->SetVisible( false ); + m_pInactiveItems[i]->SetVisible( false ); + m_pUnavailableItems[i]->SetVisible( true ); + } + else if ( pObj != NULL && !pObj->IsPlacing() ) + { + m_pActiveItems[i]->SetVisible( true ); + m_pInactiveItems[i]->SetVisible( false ); + m_pUnavailableItems[i]->SetVisible( false ); + } + else + { + m_pActiveItems[i]->SetVisible( false ); + m_pInactiveItems[i]->SetVisible( true ); + m_pUnavailableItems[i]->SetVisible( false ); + } + } +} + +void CHudMenuEngyDestroy::SetVisible( bool state ) +{ + if ( state == IsVisible() ) + return; + + InitBuildings(); + + if ( state == true ) + { + // See if our layout needs to change, due to equipped items + int iDesired = CalcCustomDestroyMenuLayout(); + if ( iDesired != m_iCurrentDestroyMenuLayout ) + { + m_iCurrentDestroyMenuLayout = (destroymenulayouts_t)iDesired; + InvalidateLayout( true, true ); + } + + // set the %lastinv% dialog var to our binding + const char *key = engine->Key_LookupBinding( "lastinv" ); + if ( !key ) + { + key = "< not bound >"; + } + + SetDialogVariable( "lastinv", key ); + + //RecalculateBuildingState( ALL_BUILDINGS ); + + HideLowerPriorityHudElementsInGroup( "mid" ); + } + else + { + UnhideLowerPriorityHudElementsInGroup( "mid" ); + } + + BaseClass::SetVisible( state ); +} + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +int CHudMenuEngyDestroy::CalcCustomDestroyMenuLayout( void ) +{ + C_TFPlayer *pLocalPlayer = C_TFPlayer::GetLocalTFPlayer(); + if ( !pLocalPlayer ) + return DESTROYMENU_DEFAULT; + + int iMenu = DESTROYMENU_DEFAULT; + CALL_ATTRIB_HOOK_INT_ON_OTHER( pLocalPlayer, iMenu, set_custom_buildmenu ); + return iMenu; +} + + +//----------------------------------------------------------------------------- +// Purpose: +//----------------------------------------------------------------------------- +void CHudMenuEngyDestroy::InitBuildings() +{ + for( int i=0; i<NUM_ENGY_BUILDINGS; ++i ) + { + m_Buildings[i] = g_kEngyBuildings[i]; + } + + CHudMenuEngyBuild::ReplaceBuildings( m_Buildings ); + + InvalidateLayout( true, true ); +} + |