368 lines
11 KiB
C++
368 lines
11 KiB
C++
//========= Copyright 1996-2005, Valve Corporation, All rights reserved. =============================//
|
|
//
|
|
// Purpose: Purpose: Displays HUD elements about armor, current weapon, ammo, and TR weapon progress
|
|
//
|
|
//======================================================================================================//
|
|
|
|
#include "cbase.h"
|
|
#include "hud.h"
|
|
#include "hudelement.h"
|
|
#include "hud_element_helper.h"
|
|
#include "iclientmode.h"
|
|
#include "view.h"
|
|
#include "vgui_controls/Controls.h"
|
|
#include "vgui/ISurface.h"
|
|
#include "ivrenderview.h"
|
|
#include "scaleformui/scaleformui.h"
|
|
#include "sfhudhealtharmorpanel.h"
|
|
#include "vgui/ILocalize.h"
|
|
#include "c_cs_hostage.h"
|
|
|
|
// memdbgon must be the last include file in a .cpp file!!!
|
|
#include "tier0/memdbgon.h"
|
|
|
|
#define SAFECALL( handle, func ) \
|
|
if ( handle ) \
|
|
{ \
|
|
func \
|
|
}
|
|
|
|
|
|
DECLARE_HUDELEMENT( SFHudHealthArmorPanel );
|
|
|
|
SFUI_BEGIN_GAME_API_DEF
|
|
SFUI_END_GAME_API_DEF( SFHudHealthArmorPanel, HealthArmorModule ); // Asset named WeaponModule to maintain consistency with Flash file naming
|
|
|
|
// global tunables
|
|
const float g_LowHealthPercent = 0.20f;
|
|
const float g_HealthFlashSeconds = 1.0f;
|
|
|
|
extern ConVar cl_draw_only_deathnotices;
|
|
|
|
SFHudHealthArmorPanel::SFHudHealthArmorPanel( const char *value ) : SFHudFlashInterface( value ),
|
|
m_PanelHandle( NULL ),
|
|
m_HealthTextHandle( NULL ),
|
|
m_HealthTextHandleRed( NULL ),
|
|
m_ArmorTextHandle( NULL ),
|
|
m_HealthBarHandle( NULL ),
|
|
m_HealthRedBarHandle( NULL ),
|
|
m_HealthPanel( NULL ),
|
|
m_HealthPanelRed( NULL ),
|
|
m_HealthPanelRedSmall( NULL ),
|
|
m_PrevHealth( -1 ),
|
|
m_PrevArmor( -1 ),
|
|
m_PrevHasHelmet( false ),
|
|
m_PrevHasHeavyArmor( false )
|
|
{
|
|
// TODO Auto-generated constructor stub
|
|
SetHiddenBits( HIDEHUD_HEALTH | HIDEHUD_PLAYERDEAD );
|
|
|
|
m_HealthFlashTimer.Invalidate();
|
|
}
|
|
|
|
|
|
SFHudHealthArmorPanel::~SFHudHealthArmorPanel()
|
|
{
|
|
// TODO Auto-generated destructor stub
|
|
}
|
|
|
|
void SFHudHealthArmorPanel::ShowPanel( bool value )
|
|
{
|
|
if ( !m_pScaleformUI )
|
|
return;
|
|
|
|
WITH_SLOT_LOCKED
|
|
{
|
|
if ( m_FlashAPI )
|
|
{
|
|
if ( value )
|
|
{
|
|
m_pScaleformUI->Value_InvokeWithoutReturn( m_FlashAPI, "showNow", NULL, 0 );
|
|
}
|
|
else
|
|
{
|
|
m_pScaleformUI->Value_InvokeWithoutReturn( m_FlashAPI, "hideNow", NULL, 0 );
|
|
}
|
|
}
|
|
|
|
// This forces the health and armor bars to reset
|
|
m_PrevHealth = -1;
|
|
m_PrevArmor = -1;
|
|
m_PrevHasHelmet = false;
|
|
m_PrevHasHeavyArmor = false;
|
|
}
|
|
}
|
|
|
|
void SFHudHealthArmorPanel::SetVisible( bool bVisible )
|
|
{
|
|
if ( FlashAPIIsValid() )
|
|
{
|
|
WITH_SFVALUEARRAY_SLOT_LOCKED( data, 1 )
|
|
{
|
|
m_pScaleformUI->ValueArray_SetElement( data, 0, bVisible );
|
|
m_pScaleformUI->Value_InvokeWithoutReturn( m_FlashAPI, "setVisible", data, 1 );
|
|
}
|
|
}
|
|
}
|
|
|
|
void SFHudHealthArmorPanel::LockSlot( bool wantItLocked, bool& currentlyLocked )
|
|
{
|
|
if ( currentlyLocked != wantItLocked )
|
|
{
|
|
if ( wantItLocked )
|
|
{
|
|
LockScaleformSlot();
|
|
}
|
|
else
|
|
{
|
|
UnlockScaleformSlot();
|
|
}
|
|
|
|
currentlyLocked = wantItLocked;
|
|
}
|
|
}
|
|
|
|
void SFHudHealthArmorPanel::ProcessInput( void )
|
|
{
|
|
// Update stats
|
|
int realHealth = 0;
|
|
int realArmor = 0;
|
|
float healthPercent = 0.0f;
|
|
float armorPercent = 0.0f;
|
|
bool bHasHelmet = false;
|
|
bool bHasHeavyArmor = false;
|
|
|
|
// Collect all player, weapon and game state data first:
|
|
|
|
C_CSPlayer *pPlayer = GetHudPlayer();
|
|
|
|
if ( pPlayer )
|
|
{
|
|
realHealth = MAX( pPlayer->GetHealth(), 0 );
|
|
|
|
realArmor = MAX( pPlayer->ArmorValue(), 0 );
|
|
|
|
healthPercent = ( ( float )realHealth / ( float )pPlayer->GetMaxHealth() );
|
|
|
|
// HACK (for now)
|
|
float flMaxArmor = pPlayer->HasHeavyArmor() ? 200 : 100;
|
|
|
|
armorPercent = ( ( float )realArmor / ( float )flMaxArmor );
|
|
|
|
bHasHelmet = pPlayer->HasHelmet();
|
|
bHasHeavyArmor = pPlayer->HasHeavyArmor();
|
|
}
|
|
|
|
// Updating flash, slot locking begins...
|
|
bool bSlotIsLocked = false;
|
|
char cNewStr[ 128 ];
|
|
|
|
// Update health and which color health bar to draw
|
|
if ( m_PrevHealth != realHealth )
|
|
{
|
|
LockSlot( true, bSlotIsLocked );
|
|
|
|
V_snprintf( cNewStr, sizeof( cNewStr ), "%d", realHealth );
|
|
SAFECALL( m_HealthTextHandle, m_pScaleformUI->Value_SetText( m_HealthTextHandle, cNewStr ); );
|
|
SAFECALL( m_HealthTextHandleRed, m_pScaleformUI->Value_SetText( m_HealthTextHandleRed, cNewStr ); );
|
|
|
|
bool bTurnHealthRed = false;
|
|
|
|
// if our health has decreased...
|
|
if ( realHealth < m_PrevHealth )
|
|
{
|
|
bTurnHealthRed = true;
|
|
|
|
if ( healthPercent <= g_LowHealthPercent )
|
|
{
|
|
// Turn a steady red, turn off the color restoring timer
|
|
m_HealthFlashTimer.Invalidate();
|
|
}
|
|
else
|
|
{
|
|
// Flash red briefly, set a timer to restore color later
|
|
m_HealthFlashTimer.Start( g_HealthFlashSeconds );
|
|
}
|
|
}
|
|
|
|
SAFECALL( m_HealthPanel, m_pScaleformUI->Value_SetVisible( m_HealthPanel, !( healthPercent <= g_LowHealthPercent ) ); );
|
|
|
|
ConVarRef cl_hud_healthammo_style( "cl_hud_healthammo_style" );
|
|
SAFECALL( m_HealthPanelRed, m_pScaleformUI->Value_SetVisible( m_HealthPanelRed, cl_hud_healthammo_style.GetInt() == 0 ? ( healthPercent <= g_LowHealthPercent ) : false ); );
|
|
SAFECALL( m_HealthPanelRedSmall, m_pScaleformUI->Value_SetVisible( m_HealthPanelRedSmall, cl_hud_healthammo_style.GetInt( ) == 1 ? ( healthPercent <= g_LowHealthPercent ) : false ); );
|
|
|
|
SAFECALL( m_HealthBarHandle, m_pScaleformUI->Value_SetVisible( m_HealthBarHandle, !bTurnHealthRed ); );
|
|
SAFECALL( m_HealthRedBarHandle, m_pScaleformUI->Value_SetVisible( m_HealthRedBarHandle, bTurnHealthRed ); );
|
|
|
|
SAFECALL( m_HealthTextHandle, m_pScaleformUI->Value_SetVisible( m_HealthTextHandle, !bTurnHealthRed ); );
|
|
SAFECALL( m_HealthTextHandleRed, m_pScaleformUI->Value_SetVisible( m_HealthTextHandleRed, bTurnHealthRed ); );
|
|
}
|
|
|
|
|
|
// When timer elapses, restore the standard health bar color
|
|
if ( m_HealthFlashTimer.HasStarted() && m_HealthFlashTimer.IsElapsed() )
|
|
{
|
|
LockSlot( true, bSlotIsLocked );
|
|
|
|
m_HealthFlashTimer.Invalidate();
|
|
|
|
SAFECALL( m_HealthBarHandle, m_pScaleformUI->Value_SetVisible( m_HealthBarHandle, true ); );
|
|
SAFECALL( m_HealthRedBarHandle, m_pScaleformUI->Value_SetVisible( m_HealthRedBarHandle, false ); );
|
|
|
|
SAFECALL( m_HealthTextHandle, m_pScaleformUI->Value_SetVisible( m_HealthTextHandle, true ); );
|
|
SAFECALL( m_HealthTextHandleRed, m_pScaleformUI->Value_SetVisible( m_HealthTextHandleRed, false ); );
|
|
}
|
|
|
|
|
|
// Update armor display
|
|
// $TODO: update the icon to reflect the type of armor, per design?
|
|
if ( m_PrevArmor != realArmor )
|
|
{
|
|
LockSlot( true, bSlotIsLocked );
|
|
|
|
V_snprintf( cNewStr, sizeof( cNewStr ), "%d", realArmor);
|
|
SAFECALL( m_ArmorTextHandle, m_pScaleformUI->Value_SetText( m_ArmorTextHandle, cNewStr ); );
|
|
}
|
|
|
|
|
|
// Update the health/armor bar lengths
|
|
if ( ( m_PrevHealth != realHealth ) ||
|
|
( m_PrevArmor != realArmor ) ||
|
|
( m_PrevHasHelmet != bHasHelmet ) ||
|
|
( m_PrevHasHeavyArmor != bHasHeavyArmor ) )
|
|
{
|
|
if ( FlashAPIIsValid() )
|
|
{
|
|
LockSlot( true, bSlotIsLocked );
|
|
|
|
WITH_SFVALUEARRAY( data, 6 )
|
|
{
|
|
m_pScaleformUI->ValueArray_SetElement( data, 0, realHealth );
|
|
m_pScaleformUI->ValueArray_SetElement( data, 1, clamp( int(healthPercent*100), 1, 100 ) );
|
|
m_pScaleformUI->ValueArray_SetElement( data, 2, clamp( realArmor, 1, 100 ) );
|
|
m_pScaleformUI->ValueArray_SetElement( data, 3, clamp( int(armorPercent*100), 1, 100 ) );
|
|
m_pScaleformUI->ValueArray_SetElement( data, 4, bHasHelmet );
|
|
m_pScaleformUI->ValueArray_SetElement( data, 5, bHasHeavyArmor );
|
|
m_pScaleformUI->Value_InvokeWithoutReturn( m_FlashAPI, "updateValues", data, 6 );
|
|
}
|
|
}
|
|
}
|
|
|
|
m_PrevHealth = realHealth;
|
|
m_PrevArmor = realArmor;
|
|
m_PrevHasHelmet = bHasHelmet;
|
|
m_PrevHasHeavyArmor = bHasHeavyArmor;
|
|
|
|
LockSlot( false, bSlotIsLocked );
|
|
}
|
|
|
|
static void GetTextBoxForElement( IScaleformUI *pScaleformUI, SFVALUE root, const char *elementName, const char *textElementName, SFVALUE &sfv )
|
|
{
|
|
SFVALUE TempHandle = pScaleformUI->Value_GetMember( root, elementName );
|
|
|
|
if ( TempHandle )
|
|
{
|
|
sfv = pScaleformUI->Value_GetMember( TempHandle, textElementName );
|
|
pScaleformUI->ReleaseValue( TempHandle );
|
|
}
|
|
}
|
|
|
|
void SFHudHealthArmorPanel::FlashReady( void )
|
|
{
|
|
m_PanelHandle = m_pScaleformUI->Value_GetMember( m_FlashAPI, "HudPanel" );
|
|
|
|
if ( m_PanelHandle )
|
|
{
|
|
SFVALUE AnimatedPanelHandle = m_pScaleformUI->Value_GetMember( m_PanelHandle, "HealthArmorPanel" );
|
|
|
|
if ( AnimatedPanelHandle )
|
|
{
|
|
GetTextBoxForElement( m_pScaleformUI, AnimatedPanelHandle, "Armor", "TextBox", m_ArmorTextHandle );
|
|
|
|
GetTextBoxForElement( m_pScaleformUI, AnimatedPanelHandle, "Health", "TextBox", m_HealthTextHandle );
|
|
GetTextBoxForElement( m_pScaleformUI, AnimatedPanelHandle, "HealthRed", "TextBox", m_HealthTextHandleRed );
|
|
|
|
m_HealthPanel = m_pScaleformUI->Value_GetMember( AnimatedPanelHandle, "HealthPanel" );
|
|
m_HealthPanelRed = m_pScaleformUI->Value_GetMember( AnimatedPanelHandle, "HealthPanelRed" );
|
|
m_HealthPanelRedSmall = m_pScaleformUI->Value_GetMember( AnimatedPanelHandle, "HealthPanelRed_small" );
|
|
|
|
SAFECALL( m_HealthPanelRed, m_pScaleformUI->Value_SetVisible( m_HealthPanelRed, false ); );
|
|
SAFECALL( m_HealthPanelRedSmall, m_pScaleformUI->Value_SetVisible( m_HealthPanelRedSmall, false ); );
|
|
|
|
SFVALUE HealthPanelHandle = m_pScaleformUI->Value_GetMember( AnimatedPanelHandle, "HealthBar" );
|
|
|
|
if ( HealthPanelHandle )
|
|
{
|
|
m_HealthBarHandle = m_pScaleformUI->Value_GetMember( HealthPanelHandle, "HealthBar" );
|
|
m_HealthRedBarHandle = m_pScaleformUI->Value_GetMember( HealthPanelHandle, "HealthBarRed" );
|
|
|
|
SafeReleaseSFVALUE( HealthPanelHandle );
|
|
}
|
|
|
|
SafeReleaseSFVALUE( AnimatedPanelHandle );
|
|
}
|
|
}
|
|
|
|
// hide everything initially
|
|
SetVisible( false );
|
|
}
|
|
|
|
bool SFHudHealthArmorPanel::PreUnloadFlash( void )
|
|
{
|
|
SafeReleaseSFVALUE( m_PanelHandle );
|
|
SafeReleaseSFVALUE( m_HealthTextHandle );
|
|
SafeReleaseSFVALUE( m_HealthTextHandleRed );
|
|
SafeReleaseSFVALUE( m_ArmorTextHandle );
|
|
SafeReleaseSFVALUE( m_HealthBarHandle );
|
|
SafeReleaseSFVALUE( m_HealthRedBarHandle );
|
|
SafeReleaseSFVALUE( m_HealthPanel );
|
|
SafeReleaseSFVALUE( m_HealthPanelRed );
|
|
SafeReleaseSFVALUE( m_HealthPanelRedSmall );
|
|
|
|
return true;
|
|
}
|
|
|
|
void SFHudHealthArmorPanel::LevelInit( void )
|
|
{
|
|
if ( !FlashAPIIsValid() )
|
|
{
|
|
SFUI_REQUEST_ELEMENT( SF_SS_SLOT( GET_ACTIVE_SPLITSCREEN_SLOT() ), g_pScaleformUI, SFHudHealthArmorPanel, this, HealthArmorModule );
|
|
}
|
|
else
|
|
{
|
|
// When initially loaded, hide this panel
|
|
SetVisible( false );
|
|
}
|
|
|
|
// Reset all transient data
|
|
m_PrevHealth = -1;
|
|
m_PrevArmor = -1;
|
|
m_PrevHasHelmet = false;
|
|
m_HealthFlashTimer.Invalidate();
|
|
}
|
|
|
|
void SFHudHealthArmorPanel::LevelShutdown( void )
|
|
{
|
|
if ( FlashAPIIsValid() )
|
|
{
|
|
RemoveFlashElement();
|
|
}
|
|
}
|
|
|
|
bool SFHudHealthArmorPanel::ShouldDraw( void )
|
|
{
|
|
return cl_drawhud.GetBool() && cl_draw_only_deathnotices.GetBool() == false && CHudElement::ShouldDraw();
|
|
}
|
|
|
|
|
|
void SFHudHealthArmorPanel::SetActive( bool bActive )
|
|
{
|
|
if ( bActive != m_bActive )
|
|
{
|
|
ShowPanel( bActive );
|
|
}
|
|
|
|
CHudElement::SetActive( bActive );
|
|
}
|
|
|