You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
502 lines
13 KiB
502 lines
13 KiB
//========= Copyright Valve Corporation, All rights reserved. ============// |
|
// |
|
// Purpose: |
|
// |
|
//=============================================================================// |
|
|
|
#include "cbase.h" |
|
#include "hud.h" |
|
#include "hudelement.h" |
|
#include "hud_macros.h" |
|
#include "hud_numericdisplay.h" |
|
#include "iclientmode.h" |
|
#include "iclientvehicle.h" |
|
#include <vgui_controls/AnimationController.h> |
|
#include <vgui/ILocalize.h> |
|
#include <vgui/ISurface.h> |
|
#include "ihudlcd.h" |
|
|
|
// memdbgon must be the last include file in a .cpp file!!! |
|
#include "tier0/memdbgon.h" |
|
|
|
using namespace vgui; |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Displays current ammunition level |
|
//----------------------------------------------------------------------------- |
|
class CHudAmmo : public CHudNumericDisplay, public CHudElement |
|
{ |
|
DECLARE_CLASS_SIMPLE( CHudAmmo, CHudNumericDisplay ); |
|
|
|
public: |
|
CHudAmmo( const char *pElementName ); |
|
void Init( void ); |
|
void VidInit( void ); |
|
void Reset(); |
|
|
|
void SetAmmo(int ammo, bool playAnimation); |
|
void SetAmmo2(int ammo2, bool playAnimation); |
|
virtual void Paint( void ); |
|
|
|
protected: |
|
virtual void OnThink(); |
|
|
|
void UpdateAmmoDisplays(); |
|
void UpdatePlayerAmmo( C_BasePlayer *player ); |
|
void UpdateVehicleAmmo( C_BasePlayer *player, IClientVehicle *pVehicle ); |
|
|
|
private: |
|
CHandle< C_BaseCombatWeapon > m_hCurrentActiveWeapon; |
|
CHandle< C_BaseEntity > m_hCurrentVehicle; |
|
int m_iAmmo; |
|
int m_iAmmo2; |
|
CHudTexture *m_iconPrimaryAmmo; |
|
}; |
|
|
|
DECLARE_HUDELEMENT( CHudAmmo ); |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Constructor |
|
//----------------------------------------------------------------------------- |
|
CHudAmmo::CHudAmmo( const char *pElementName ) : BaseClass(NULL, "HudAmmo"), CHudElement( pElementName ) |
|
{ |
|
SetHiddenBits( HIDEHUD_HEALTH | HIDEHUD_PLAYERDEAD | HIDEHUD_NEEDSUIT | HIDEHUD_WEAPONSELECTION ); |
|
|
|
hudlcd->SetGlobalStat( "(ammo_primary)", "0" ); |
|
hudlcd->SetGlobalStat( "(ammo_secondary)", "0" ); |
|
hudlcd->SetGlobalStat( "(weapon_print_name)", "" ); |
|
hudlcd->SetGlobalStat( "(weapon_name)", "" ); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CHudAmmo::Init( void ) |
|
{ |
|
m_iAmmo = -1; |
|
m_iAmmo2 = -1; |
|
|
|
m_iconPrimaryAmmo = NULL; |
|
|
|
wchar_t *tempString = g_pVGuiLocalize->Find("#Valve_Hud_AMMO"); |
|
if (tempString) |
|
{ |
|
SetLabelText(tempString); |
|
} |
|
else |
|
{ |
|
SetLabelText(L"AMMO"); |
|
} |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: |
|
//----------------------------------------------------------------------------- |
|
void CHudAmmo::VidInit( void ) |
|
{ |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Resets hud after save/restore |
|
//----------------------------------------------------------------------------- |
|
void CHudAmmo::Reset() |
|
{ |
|
BaseClass::Reset(); |
|
|
|
m_hCurrentActiveWeapon = NULL; |
|
m_hCurrentVehicle = NULL; |
|
m_iAmmo = 0; |
|
m_iAmmo2 = 0; |
|
|
|
UpdateAmmoDisplays(); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: called every frame to get ammo info from the weapon |
|
//----------------------------------------------------------------------------- |
|
void CHudAmmo::UpdatePlayerAmmo( C_BasePlayer *player ) |
|
{ |
|
// Clear out the vehicle entity |
|
m_hCurrentVehicle = NULL; |
|
|
|
C_BaseCombatWeapon *wpn = GetActiveWeapon(); |
|
|
|
hudlcd->SetGlobalStat( "(weapon_print_name)", wpn ? wpn->GetPrintName() : " " ); |
|
hudlcd->SetGlobalStat( "(weapon_name)", wpn ? wpn->GetName() : " " ); |
|
|
|
if ( !wpn || !player || !wpn->UsesPrimaryAmmo() ) |
|
{ |
|
hudlcd->SetGlobalStat( "(ammo_primary)", "n/a" ); |
|
hudlcd->SetGlobalStat( "(ammo_secondary)", "n/a" ); |
|
|
|
SetPaintEnabled(false); |
|
SetPaintBackgroundEnabled(false); |
|
return; |
|
} |
|
|
|
SetPaintEnabled(true); |
|
SetPaintBackgroundEnabled(true); |
|
|
|
// Get our icons for the ammo types |
|
m_iconPrimaryAmmo = gWR.GetAmmoIconFromWeapon( wpn->GetPrimaryAmmoType() ); |
|
|
|
// get the ammo in our clip |
|
int ammo1 = wpn->Clip1(); |
|
int ammo2; |
|
if (ammo1 < 0) |
|
{ |
|
// we don't use clip ammo, just use the total ammo count |
|
ammo1 = player->GetAmmoCount(wpn->GetPrimaryAmmoType()); |
|
ammo2 = 0; |
|
} |
|
else |
|
{ |
|
// we use clip ammo, so the second ammo is the total ammo |
|
ammo2 = player->GetAmmoCount(wpn->GetPrimaryAmmoType()); |
|
} |
|
|
|
hudlcd->SetGlobalStat( "(ammo_primary)", VarArgs( "%d", ammo1 ) ); |
|
hudlcd->SetGlobalStat( "(ammo_secondary)", VarArgs( "%d", ammo2 ) ); |
|
|
|
if (wpn == m_hCurrentActiveWeapon) |
|
{ |
|
// same weapon, just update counts |
|
SetAmmo(ammo1, true); |
|
SetAmmo2(ammo2, true); |
|
} |
|
else |
|
{ |
|
// diferent weapon, change without triggering |
|
SetAmmo(ammo1, false); |
|
SetAmmo2(ammo2, false); |
|
|
|
// update whether or not we show the total ammo display |
|
if (wpn->UsesClipsForAmmo1()) |
|
{ |
|
SetShouldDisplaySecondaryValue(true); |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("WeaponUsesClips"); |
|
} |
|
else |
|
{ |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("WeaponDoesNotUseClips"); |
|
SetShouldDisplaySecondaryValue(false); |
|
} |
|
|
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("WeaponChanged"); |
|
m_hCurrentActiveWeapon = wpn; |
|
} |
|
} |
|
|
|
void CHudAmmo::UpdateVehicleAmmo( C_BasePlayer *player, IClientVehicle *pVehicle ) |
|
{ |
|
m_hCurrentActiveWeapon = NULL; |
|
CBaseEntity *pVehicleEnt = pVehicle->GetVehicleEnt(); |
|
|
|
if ( !pVehicleEnt || pVehicle->GetPrimaryAmmoType() < 0 ) |
|
{ |
|
SetPaintEnabled(false); |
|
SetPaintBackgroundEnabled(false); |
|
return; |
|
} |
|
|
|
SetPaintEnabled(true); |
|
SetPaintBackgroundEnabled(true); |
|
|
|
// get the ammo in our clip |
|
int ammo1 = pVehicle->GetPrimaryAmmoClip(); |
|
int ammo2; |
|
if (ammo1 < 0) |
|
{ |
|
// we don't use clip ammo, just use the total ammo count |
|
ammo1 = pVehicle->GetPrimaryAmmoCount(); |
|
ammo2 = 0; |
|
} |
|
else |
|
{ |
|
// we use clip ammo, so the second ammo is the total ammo |
|
ammo2 = pVehicle->GetPrimaryAmmoCount(); |
|
} |
|
|
|
if (pVehicleEnt == m_hCurrentVehicle) |
|
{ |
|
// same weapon, just update counts |
|
SetAmmo(ammo1, true); |
|
SetAmmo2(ammo2, true); |
|
} |
|
else |
|
{ |
|
// diferent weapon, change without triggering |
|
SetAmmo(ammo1, false); |
|
SetAmmo2(ammo2, false); |
|
|
|
// update whether or not we show the total ammo display |
|
if (pVehicle->PrimaryAmmoUsesClips()) |
|
{ |
|
SetShouldDisplaySecondaryValue(true); |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("WeaponUsesClips"); |
|
} |
|
else |
|
{ |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("WeaponDoesNotUseClips"); |
|
SetShouldDisplaySecondaryValue(false); |
|
} |
|
|
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("WeaponChanged"); |
|
m_hCurrentVehicle = pVehicleEnt; |
|
} |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: called every frame to get ammo info from the weapon |
|
//----------------------------------------------------------------------------- |
|
void CHudAmmo::OnThink() |
|
{ |
|
UpdateAmmoDisplays(); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: updates the ammo display counts |
|
//----------------------------------------------------------------------------- |
|
void CHudAmmo::UpdateAmmoDisplays() |
|
{ |
|
C_BasePlayer *player = C_BasePlayer::GetLocalPlayer(); |
|
IClientVehicle *pVehicle = player ? player->GetVehicle() : NULL; |
|
|
|
if ( !pVehicle ) |
|
{ |
|
UpdatePlayerAmmo( player ); |
|
} |
|
else |
|
{ |
|
UpdateVehicleAmmo( player, pVehicle ); |
|
} |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Updates ammo display |
|
//----------------------------------------------------------------------------- |
|
void CHudAmmo::SetAmmo(int ammo, bool playAnimation) |
|
{ |
|
if (ammo != m_iAmmo) |
|
{ |
|
if (ammo == 0) |
|
{ |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("AmmoEmpty"); |
|
} |
|
else if (ammo < m_iAmmo) |
|
{ |
|
// ammo has decreased |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("AmmoDecreased"); |
|
} |
|
else |
|
{ |
|
// ammunition has increased |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("AmmoIncreased"); |
|
} |
|
|
|
m_iAmmo = ammo; |
|
} |
|
|
|
SetDisplayValue(ammo); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Updates 2nd ammo display |
|
//----------------------------------------------------------------------------- |
|
void CHudAmmo::SetAmmo2(int ammo2, bool playAnimation) |
|
{ |
|
if (ammo2 != m_iAmmo2) |
|
{ |
|
if (ammo2 == 0) |
|
{ |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("Ammo2Empty"); |
|
} |
|
else if (ammo2 < m_iAmmo2) |
|
{ |
|
// ammo has decreased |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("Ammo2Decreased"); |
|
} |
|
else |
|
{ |
|
// ammunition has increased |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("Ammo2Increased"); |
|
} |
|
|
|
m_iAmmo2 = ammo2; |
|
} |
|
|
|
SetSecondaryValue(ammo2); |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: We add an icon into the |
|
//----------------------------------------------------------------------------- |
|
void CHudAmmo::Paint( void ) |
|
{ |
|
BaseClass::Paint(); |
|
|
|
#ifndef HL2MP |
|
if ( m_hCurrentVehicle == NULL && m_iconPrimaryAmmo ) |
|
{ |
|
int nLabelHeight; |
|
int nLabelWidth; |
|
surface()->GetTextSize( m_hTextFont, m_LabelText, nLabelWidth, nLabelHeight ); |
|
|
|
// Figure out where we're going to put this |
|
int x = text_xpos + ( nLabelWidth - m_iconPrimaryAmmo->Width() ) / 2; |
|
int y = text_ypos - ( nLabelHeight + ( m_iconPrimaryAmmo->Height() / 2 ) ); |
|
|
|
m_iconPrimaryAmmo->DrawSelf( x, y, GetFgColor() ); |
|
} |
|
#endif // HL2MP |
|
} |
|
|
|
//----------------------------------------------------------------------------- |
|
// Purpose: Displays the secondary ammunition level |
|
//----------------------------------------------------------------------------- |
|
class CHudSecondaryAmmo : public CHudNumericDisplay, public CHudElement |
|
{ |
|
DECLARE_CLASS_SIMPLE( CHudSecondaryAmmo, CHudNumericDisplay ); |
|
|
|
public: |
|
CHudSecondaryAmmo( const char *pElementName ) : BaseClass( NULL, "HudAmmoSecondary" ), CHudElement( pElementName ) |
|
{ |
|
m_iAmmo = -1; |
|
|
|
SetHiddenBits( HIDEHUD_HEALTH | HIDEHUD_WEAPONSELECTION | HIDEHUD_PLAYERDEAD | HIDEHUD_NEEDSUIT ); |
|
} |
|
|
|
void Init( void ) |
|
{ |
|
#ifndef HL2MP |
|
wchar_t *tempString = g_pVGuiLocalize->Find("#Valve_Hud_AMMO_ALT"); |
|
if (tempString) |
|
{ |
|
SetLabelText(tempString); |
|
} |
|
else |
|
{ |
|
SetLabelText(L"ALT"); |
|
} |
|
#endif // HL2MP |
|
} |
|
|
|
void VidInit( void ) |
|
{ |
|
} |
|
|
|
void SetAmmo( int ammo ) |
|
{ |
|
if (ammo != m_iAmmo) |
|
{ |
|
if (ammo == 0) |
|
{ |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("AmmoSecondaryEmpty"); |
|
} |
|
else if (ammo < m_iAmmo) |
|
{ |
|
// ammo has decreased |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("AmmoSecondaryDecreased"); |
|
} |
|
else |
|
{ |
|
// ammunition has increased |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("AmmoSecondaryIncreased"); |
|
} |
|
|
|
m_iAmmo = ammo; |
|
} |
|
SetDisplayValue( ammo ); |
|
} |
|
|
|
void Reset() |
|
{ |
|
// hud reset, update ammo state |
|
BaseClass::Reset(); |
|
m_iAmmo = 0; |
|
m_hCurrentActiveWeapon = NULL; |
|
SetAlpha( 0 ); |
|
UpdateAmmoState(); |
|
} |
|
|
|
virtual void Paint( void ) |
|
{ |
|
BaseClass::Paint(); |
|
|
|
#ifndef HL2MP |
|
if ( m_iconSecondaryAmmo ) |
|
{ |
|
int nLabelHeight; |
|
int nLabelWidth; |
|
surface()->GetTextSize( m_hTextFont, m_LabelText, nLabelWidth, nLabelHeight ); |
|
|
|
// Figure out where we're going to put this |
|
int x = text_xpos + ( nLabelWidth - m_iconSecondaryAmmo->Width() ) / 2; |
|
int y = text_ypos - ( nLabelHeight + ( m_iconSecondaryAmmo->Height() / 2 ) ); |
|
|
|
m_iconSecondaryAmmo->DrawSelf( x, y, GetFgColor() ); |
|
} |
|
#endif // HL2MP |
|
} |
|
|
|
protected: |
|
|
|
virtual void OnThink() |
|
{ |
|
// set whether or not the panel draws based on if we have a weapon that supports secondary ammo |
|
C_BaseCombatWeapon *wpn = GetActiveWeapon(); |
|
C_BasePlayer *player = C_BasePlayer::GetLocalPlayer(); |
|
IClientVehicle *pVehicle = player ? player->GetVehicle() : NULL; |
|
if (!wpn || !player || pVehicle) |
|
{ |
|
m_hCurrentActiveWeapon = NULL; |
|
SetPaintEnabled(false); |
|
SetPaintBackgroundEnabled(false); |
|
return; |
|
} |
|
else |
|
{ |
|
SetPaintEnabled(true); |
|
SetPaintBackgroundEnabled(true); |
|
} |
|
|
|
UpdateAmmoState(); |
|
} |
|
|
|
void UpdateAmmoState() |
|
{ |
|
C_BaseCombatWeapon *wpn = GetActiveWeapon(); |
|
C_BasePlayer *player = C_BasePlayer::GetLocalPlayer(); |
|
|
|
if (player && wpn && wpn->UsesSecondaryAmmo()) |
|
{ |
|
SetAmmo(player->GetAmmoCount(wpn->GetSecondaryAmmoType())); |
|
} |
|
|
|
if ( m_hCurrentActiveWeapon != wpn ) |
|
{ |
|
if ( wpn->UsesSecondaryAmmo() ) |
|
{ |
|
// we've changed to a weapon that uses secondary ammo |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("WeaponUsesSecondaryAmmo"); |
|
} |
|
else |
|
{ |
|
// we've changed away from a weapon that uses secondary ammo |
|
g_pClientMode->GetViewportAnimationController()->StartAnimationSequence("WeaponDoesNotUseSecondaryAmmo"); |
|
} |
|
m_hCurrentActiveWeapon = wpn; |
|
|
|
// Get the icon we should be displaying |
|
m_iconSecondaryAmmo = gWR.GetAmmoIconFromWeapon( m_hCurrentActiveWeapon->GetSecondaryAmmoType() ); |
|
} |
|
} |
|
|
|
private: |
|
CHandle< C_BaseCombatWeapon > m_hCurrentActiveWeapon; |
|
CHudTexture *m_iconSecondaryAmmo; |
|
int m_iAmmo; |
|
}; |
|
|
|
DECLARE_HUDELEMENT( CHudSecondaryAmmo ); |
|
|
|
|