From 5b424cc22c9bb41ab7dab8f97523f50254268099 Mon Sep 17 00:00:00 2001 From: Roman Chistokhodov Date: Wed, 22 May 2024 14:05:40 +0300 Subject: [PATCH] Add player_maxhealth and player_maxarmor features. Add maxhealth and maxarmor parameters in the map config. Add parameters for game_player_settings --- cl_dll/battery.cpp | 6 ++- cl_dll/health.cpp | 10 +++-- cl_dll/health.h | 1 + cl_dll/hud.h | 1 + dlls/game.cpp | 5 +++ dlls/game.h | 13 ++++++ dlls/gamerules.cpp | 15 +++++-- dlls/h_battery.cpp | 4 +- dlls/islave.cpp | 6 +-- dlls/items.cpp | 4 +- dlls/mapconfig.cpp | 9 ++++ dlls/mapconfig.h | 2 + dlls/maprules.cpp | 35 +++++++++++++-- dlls/multiplay_gamerules.cpp | 2 +- dlls/player.cpp | 79 +++++++++++++++++++++++++++++----- dlls/player.h | 7 +++ dlls/weapons.h | 2 - features/featureful_server.cfg | 10 +++++ fgd/halflife.fgd | 16 ++++++- 19 files changed, 192 insertions(+), 35 deletions(-) diff --git a/cl_dll/battery.cpp b/cl_dll/battery.cpp index dcc4f63f36..b4d53c703c 100644 --- a/cl_dll/battery.cpp +++ b/cl_dll/battery.cpp @@ -27,6 +27,7 @@ DECLARE_MESSAGE( m_Battery, Battery ) int CHudBattery::Init( void ) { m_iBat = 0; + m_iMaxBat = 100; m_fFade = 0; m_iFlags = 0; @@ -56,6 +57,7 @@ int CHudBattery::MsgFunc_Battery( const char *pszName, int iSize, void *pbuf ) BEGIN_READ( pbuf, iSize ); int x = READ_SHORT(); + m_iMaxBat = READ_SHORT(); if( x != m_iBat ) { @@ -122,7 +124,9 @@ int CHudBattery::Draw( float flTime ) } x += ( m_prc1->right - m_prc1->left ); - x = gHUD.DrawHudNumber( x, y, DHN_3DIGITS | DHN_DRAWZERO, m_iBat, r, g, b ); + + const int digitFlag = m_iBat >= 1000 ? DHN_4DIGITS : DHN_3DIGITS; + x = gHUD.DrawHudNumber( x, y, digitFlag | DHN_DRAWZERO, m_iBat, r, g, b ); return 1; } diff --git a/cl_dll/health.cpp b/cl_dll/health.cpp index cf2975759e..118e27df06 100644 --- a/cl_dll/health.cpp +++ b/cl_dll/health.cpp @@ -55,6 +55,7 @@ int CHudHealth::Init( void ) HOOK_MESSAGE( Health ); HOOK_MESSAGE( Damage ); m_iHealth = 100; + m_iMaxHealth = 100; m_fFade = 0; m_iFlags = 0; m_bitsDamage = 0; @@ -98,7 +99,8 @@ int CHudHealth::MsgFunc_Health( const char *pszName, int iSize, void *pbuf ) { // TODO: update local health data BEGIN_READ( pbuf, iSize ); - int x = READ_BYTE(); + int x = READ_SHORT(); + m_iMaxHealth = READ_SHORT(); m_iFlags |= HUD_ACTIVE; @@ -108,7 +110,6 @@ int CHudHealth::MsgFunc_Health( const char *pszName, int iSize, void *pbuf ) m_fFade = FADE_TIME; m_iHealth = x; } - return 1; } @@ -230,9 +231,10 @@ int CHudHealth::Draw( float flTime ) CHud::Renderer().SPR_DrawAdditive( gHUD.GetSprite( m_HUD_cross ), r, g, b, x, y, &gHUD.GetSpriteRect( m_HUD_cross ) ); - x = CrossWidth + HealthWidth / 2; + x += CrossWidth; - x = gHUD.DrawHudNumber( x, y, DHN_3DIGITS | DHN_DRAWZERO, m_iHealth, r, g, b ); + const int digitFlag = m_iHealth >= 1000 ? DHN_4DIGITS : DHN_3DIGITS; + x = gHUD.DrawHudNumber( x, y, digitFlag | DHN_DRAWZERO, m_iHealth, r, g, b ); x += HealthWidth / 2; diff --git a/cl_dll/health.h b/cl_dll/health.h index f1503289cf..e130eb63e3 100644 --- a/cl_dll/health.h +++ b/cl_dll/health.h @@ -83,6 +83,7 @@ class CHudHealth : public CHudBase int MsgFunc_Health( const char *pszName, int iSize, void *pbuf ); int MsgFunc_Damage( const char *pszName, int iSize, void *pbuf ); int m_iHealth; + int m_iMaxHealth; int m_HUD_dmg_bio; int m_HUD_cross; float m_fAttackFront, m_fAttackRear, m_fAttackLeft, m_fAttackRight; diff --git a/cl_dll/hud.h b/cl_dll/hud.h index 831c59f793..812e9c4f2b 100644 --- a/cl_dll/hud.h +++ b/cl_dll/hud.h @@ -491,6 +491,7 @@ class CHudBattery : public CHudBase wrect_t *m_prc1; wrect_t *m_prc2; int m_iBat; + int m_iMaxBat; float m_fFade; int m_iHeight; // width of the battery innards }; diff --git a/dlls/game.cpp b/dlls/game.cpp index 6f63c326af..ff8f14481e 100644 --- a/dlls/game.cpp +++ b/dlls/game.cpp @@ -49,6 +49,9 @@ ModFeatures::ModFeatures() memset(wall_puff3, 0, sizeof(StringBuf)); memset(wall_puff4, 0, sizeof(StringBuf)); + player_maxhealth = MAX_NORMAL_HEALTH; + player_maxarmor = MAX_NORMAL_BATTERY; + suit_light = SUIT_LIGHT_FLASHLIGHT; suit_light_allow_both = false; suit_sentences = true; @@ -170,6 +173,8 @@ bool ModFeatures::SetValue(const char *key, const char *value) } KeyValueDefinition integers[] = { + KEY_VALUE_DEF(player_maxhealth), + KEY_VALUE_DEF(player_maxarmor), KEY_VALUE_DEF(scientist_random_heads), }; diff --git a/dlls/game.h b/dlls/game.h index abc8a58ce5..46423589a1 100644 --- a/dlls/game.h +++ b/dlls/game.h @@ -22,6 +22,9 @@ extern void GameDLLInit( void ); +#define MAX_NORMAL_HEALTH 100 +#define MAX_NORMAL_BATTERY 100 + struct ModFeatures { enum { @@ -50,6 +53,13 @@ struct ModFeatures void EnableMonster(const char* name); bool IsMonsterEnabled(const char* name) const; + int MaxPlayerHealth() { + return player_maxhealth > 0 ? player_maxhealth : MAX_NORMAL_HEALTH; + } + int MaxPlayerArmor() { + return player_maxarmor > 0 ? player_maxarmor : MAX_NORMAL_BATTERY; + } + int suit_light; bool suit_light_allow_both; bool suit_sentences; @@ -59,6 +69,9 @@ struct ModFeatures bool satchels_pickable; bool gauss_fidget; + int player_maxhealth; + int player_maxarmor; + bool alien_teleport_sound; bool warpball_at_monster_center; diff --git a/dlls/gamerules.cpp b/dlls/gamerules.cpp index 1b203728a7..1bc748f285 100644 --- a/dlls/gamerules.cpp +++ b/dlls/gamerules.cpp @@ -626,10 +626,19 @@ bool CGameRules::EquipPlayerFromMapConfig(CBasePlayer *pPlayer, const MapConfig pPlayer->GiveNamedItem("weapon_medkit"); } #endif + if (mapConfig.maxhealth > 0) + { + pPlayer->SetMaxHealth(mapConfig.maxhealth); + pPlayer->pev->health = pPlayer->pev->max_health; + } + if (mapConfig.maxarmor > 0) + { + pPlayer->SetMaxArmor(mapConfig.maxarmor); + } if (mapConfig.startarmor > 0) - pPlayer->pev->armorvalue = Q_min(mapConfig.startarmor, MAX_NORMAL_BATTERY); - if (mapConfig.starthealth > 0 && mapConfig.starthealth < pPlayer->pev->max_health) - pPlayer->pev->health = mapConfig.starthealth; + pPlayer->SetArmor(mapConfig.startarmor); + if (mapConfig.starthealth > 0) + pPlayer->SetHealth(mapConfig.starthealth); if (mapConfig.longjump) { diff --git a/dlls/h_battery.cpp b/dlls/h_battery.cpp index 9ee501c33b..889ec9e7ed 100644 --- a/dlls/h_battery.cpp +++ b/dlls/h_battery.cpp @@ -318,7 +318,7 @@ void CRechargeDecay::Use(CBaseEntity *pActivator, CBaseEntity *pCaller, USE_TYPE CBasePlayer* pPlayer = static_cast(pCaller); // if the player doesn't have the suit, or there is no juice left, make the deny noise - if( ( m_iJuice <= 0 ) || ( !pPlayer->HasSuit() ) || pPlayer->pev->armorvalue >= MAX_NORMAL_BATTERY ) + if( ( m_iJuice <= 0 ) || ( !pPlayer->HasSuit() ) || pPlayer->pev->armorvalue >= pPlayer->MaxArmor() ) { if( m_flSoundTime <= gpGlobals->time ) { @@ -375,7 +375,7 @@ void CRechargeDecay::Use(CBaseEntity *pActivator, CBaseEntity *pCaller, USE_TYPE } // charge the player - if( pPlayer->pev->armorvalue < MAX_NORMAL_BATTERY ) + if( pPlayer->pev->armorvalue < pPlayer->MaxArmor() ) { if (m_triggerOnFirstUse) { diff --git a/dlls/islave.cpp b/dlls/islave.cpp index 88271c661f..15f1ea1a0c 100644 --- a/dlls/islave.cpp +++ b/dlls/islave.cpp @@ -220,10 +220,10 @@ void CChargeToken::Precache() void CChargeToken::ArmorPieceTouch(CBaseEntity *pOther) { - if (pOther->IsPlayer() && (static_cast(pOther))->HasSuit()) + CBasePlayer* pPlayer = pOther->IsPlayer() ? static_cast(pOther) : nullptr; + if (pPlayer && pPlayer->HasSuit()) { - pOther->pev->armorvalue += pev->health; - pOther->pev->armorvalue = Q_min(pOther->pev->armorvalue, MAX_NORMAL_BATTERY); + pPlayer->TakeArmor(this, pev->health); EMIT_SOUND_DYN( ENT( pOther->pev ), CHAN_ITEM, "items/suitchargeok1.wav", 1, ATTN_NORM, 0, 150 ); SetTouch(NULL); SetThink(&CBaseEntity::SUB_Remove); diff --git a/dlls/items.cpp b/dlls/items.cpp index c880b6c2e8..08f6d85b76 100644 --- a/dlls/items.cpp +++ b/dlls/items.cpp @@ -587,7 +587,7 @@ class CItemBattery : public CItem return FALSE; } - if( ( pPlayer->pev->armorvalue < MAX_NORMAL_BATTERY ) && pPlayer->HasSuit() ) + if( ( pPlayer->pev->armorvalue < pPlayer->MaxArmor() ) && pPlayer->HasSuit() ) { pPlayer->TakeArmor(this, pev->health > 0 ? pev->health : DefaultCapacity()); @@ -603,7 +603,7 @@ class CItemBattery : public CItem char szcharge[64]; // Suit reports new power level // For some reason this wasn't working in release build -- round it. - pct = (int)( (float)( pPlayer->pev->armorvalue * 100.0f ) * ( 1.0f / MAX_NORMAL_BATTERY ) + 0.5f ); + pct = (int)( (float)( pPlayer->pev->armorvalue * 100.0f ) * ( 1.0f / 100 ) + 0.5f ); pct = ( pct / 5 ); if( pct > 0 ) pct--; diff --git a/dlls/mapconfig.cpp b/dlls/mapconfig.cpp index 4fa74f833d..55241b08b5 100644 --- a/dlls/mapconfig.cpp +++ b/dlls/mapconfig.cpp @@ -8,6 +8,7 @@ PickupEnt::PickupEnt(): entName(0), count(0) {} MapConfig::MapConfig() : pickupEntCount(0), ammoCount(0), cvarCount(0), starthealth(0), startarmor(0), + maxhealth(0), maxarmor(0), nomedkit(false), nosuit(false), suitLogon(SuitNoLogon), suit_light(SUIT_LIGHT_DEFAULT), longjump(false), valid(false) @@ -135,6 +136,14 @@ bool ReadMapConfigFromText(MapConfig& mapConfig, byte* pMemFile, int fileSize) { mapConfig.starthealth = atoi(value); } + else if (strcmp(key, "maxhealth") == 0) + { + mapConfig.maxhealth = atoi(value); + } + else if (strcmp(key, "maxarmor") == 0) + { + mapConfig.maxarmor = atoi(value); + } else if (strncmp(key, "sv_", 3) == 0 || strncmp(key, "mp_", 3) == 0 || strncmp(key, "npc_", 4) == 0) { if (mapConfig.cvarCount < 32) diff --git a/dlls/mapconfig.h b/dlls/mapconfig.h index 9403ea6ebb..659aca968f 100644 --- a/dlls/mapconfig.h +++ b/dlls/mapconfig.h @@ -48,6 +48,8 @@ struct MapConfig int starthealth; int startarmor; + int maxhealth; + int maxarmor; bool nomedkit; // for co-op diff --git a/dlls/maprules.cpp b/dlls/maprules.cpp index 61f70b3362..d5969dad32 100644 --- a/dlls/maprules.cpp +++ b/dlls/maprules.cpp @@ -965,6 +965,8 @@ class CGamePlayerSettings : public CRulePointEntity int m_ammoCounts[MAX_AMMO_TYPES]; short m_suitLogon; short m_suitLight; + BOOL m_allowOverheal; + BOOL m_allowOvercharge; }; LINK_ENTITY_TO_CLASS( game_player_settings, CGamePlayerSettings ) @@ -974,6 +976,8 @@ TYPEDESCRIPTION CGamePlayerSettings::m_SaveData[] = DEFINE_ARRAY( CGamePlayerSettings, m_ammoCounts, FIELD_INTEGER, MAX_AMMO_TYPES ), DEFINE_FIELD( CGamePlayerSettings, m_suitLogon, FIELD_SHORT ), DEFINE_FIELD( CGamePlayerSettings, m_suitLight, FIELD_SHORT ), + DEFINE_FIELD( CGamePlayerSettings, m_allowOverheal, FIELD_BOOLEAN ), + DEFINE_FIELD( CGamePlayerSettings, m_allowOvercharge, FIELD_BOOLEAN ), }; IMPLEMENT_SAVERESTORE( CGamePlayerSettings, CRulePointEntity ) @@ -1002,6 +1006,21 @@ void CGamePlayerSettings::KeyValue(KeyValueData *pkvd) m_suitLight = atoi(pkvd->szValue); pkvd->fHandled = TRUE; } + else if (FStrEq(pkvd->szKeyName, "max_armor")) + { + pev->armortype = atoi(pkvd->szValue); + pkvd->fHandled = TRUE; + } + else if (FStrEq(pkvd->szKeyName, "allow_overheal")) + { + m_allowOverheal = atoi(pkvd->szValue) != 0; + pkvd->fHandled = TRUE; + } + else if (FStrEq(pkvd->szKeyName, "allow_overcharge")) + { + m_allowOvercharge = atoi(pkvd->szValue) != 0; + pkvd->fHandled = TRUE; + } else CRulePointEntity::KeyValue(pkvd); } @@ -1013,13 +1032,21 @@ void CGamePlayerSettings::EquipPlayer(CBaseEntity *pPlayer) CBasePlayer* player = (CBasePlayer*)pPlayer; - if (pev->health > 0 && pev->health <= player->pev->max_health) + if (pev->max_health > 0) + { + player->SetMaxHealth(pev->max_health, !m_allowOverheal); + } + if (pev->armortype > 0) + { + player->SetMaxArmor(pev->armortype, !m_allowOvercharge); + } + if (pev->health > 0) { - player->pev->health = (int)pev->health; + player->SetHealth((int)pev->health, m_allowOverheal); } - if (pev->armorvalue > 0 && pev->armorvalue <= MAX_NORMAL_BATTERY) + if (pev->armorvalue > 0) { - player->pev->armorvalue = (int)pev->armorvalue; + player->SetArmor((int)pev->armorvalue, m_allowOvercharge); } if (pev->spawnflags & SF_PLAYER_SETTINGS_SUIT) diff --git a/dlls/multiplay_gamerules.cpp b/dlls/multiplay_gamerules.cpp index 12f20c6eb5..dc443d87fa 100644 --- a/dlls/multiplay_gamerules.cpp +++ b/dlls/multiplay_gamerules.cpp @@ -2127,7 +2127,7 @@ void CMultiplayBusters::PlayerGotWeapon( CBasePlayer *pPlayer, CBasePlayerWeapon UTIL_ClientPrintAll( HUD_PRINTTALK, UTIL_VarArgs( "%s is busting!\n", STRING( pPlayer->pev->netname ))); SetPlayerModel( pPlayer, TRUE ); pPlayer->pev->health = pPlayer->pev->max_health; - pPlayer->pev->armorvalue = MAX_NORMAL_BATTERY; + pPlayer->pev->armorvalue = pPlayer->MaxArmor(); pPlayer->pev->renderfx = kRenderFxGlowShell; pPlayer->pev->renderamt = 25; pPlayer->pev->rendercolor = Vector( 0, 75, 250 ); diff --git a/dlls/player.cpp b/dlls/player.cpp index f1a6df5990..2e79b58374 100644 --- a/dlls/player.cpp +++ b/dlls/player.cpp @@ -240,9 +240,9 @@ void LinkUserMessages( void ) gmsgGeigerRange = REG_USER_MSG( "Geiger", 1 ); gmsgFlashlight = REG_USER_MSG( "Flashlight", 2 ); gmsgFlashBattery = REG_USER_MSG( "FlashBat", 1 ); - gmsgHealth = REG_USER_MSG( "Health", 1 ); + gmsgHealth = REG_USER_MSG( "Health", 4 ); gmsgDamage = REG_USER_MSG( "Damage", 12 ); - gmsgBattery = REG_USER_MSG( "Battery", 2); + gmsgBattery = REG_USER_MSG( "Battery", 4); gmsgTrain = REG_USER_MSG( "Train", 1 ); //gmsgHudText = REG_USER_MSG( "HudTextPro", -1 ); gmsgHudText = REG_USER_MSG( "HudText", -1 ); // we don't use the message but 3rd party addons may! @@ -459,17 +459,63 @@ int CBasePlayer::TakeHealth( CBaseEntity* pHealer, float flHealth, int bitsDamag return healed; } +void CBasePlayer::SetHealth(int health, bool allowOverheal) +{ + pev->health = health; + if (pev->health > pev->max_health && !allowOverheal) + { + pev->health = pev->max_health; + } +} + +void CBasePlayer::SetMaxHealth(int maxHealth, bool clampValue) +{ + pev->max_health = maxHealth; + if (clampValue && pev->health > pev->max_health) + { + pev->health = pev->max_health; + } +} + int CBasePlayer::TakeArmor(CBaseEntity *pCharger, float flArmor) { - if (pev->armorvalue >= MAX_NORMAL_BATTERY) + if (pev->armorvalue >= MaxArmor()) return false; pev->armorvalue += flArmor; - pev->armorvalue = Q_min( pev->armorvalue, MAX_NORMAL_BATTERY ); + pev->armorvalue = Q_min( pev->armorvalue, MaxArmor() ); if (pev->armorvalue < 0) pev->armorvalue = 0; return true; } +int CBasePlayer::MaxArmor() +{ + if (pev->armortype > 0) + { + return pev->armortype; + } + return g_modFeatures.MaxPlayerArmor(); +} + +void CBasePlayer::SetMaxArmor(int maxArmor, bool clampValue) +{ + pev->armortype = maxArmor; + if (clampValue && pev->armorvalue > MaxArmor()) + { + pev->armorvalue = MaxArmor(); + } +} + +void CBasePlayer::SetArmor(int armor, bool allowOvercharge) +{ + pev->armorvalue = armor; + const int maxArmor = MaxArmor(); + if (pev->armorvalue > maxArmor && !allowOvercharge) + { + pev->armorvalue = maxArmor; + } +} + Vector CBasePlayer::GetGunPosition() { //UTIL_MakeVectors( pev->v_angle ); @@ -1097,8 +1143,10 @@ void CBasePlayer::Killed( entvars_t *pevInflictor, entvars_t *pevAttacker, int i // send "health" update message to zero m_iClientHealth = 0; + m_iClientMaxHealth = (int)pev->max_health; MESSAGE_BEGIN( MSG_ONE, gmsgHealth, NULL, pev ); WRITE_BYTE( m_iClientHealth ); + WRITE_BYTE( (int)pev->max_health ); MESSAGE_END(); // Tell Ammo Hud that the player is dead @@ -3560,12 +3608,12 @@ void CBasePlayer::Spawn( void ) { m_flStartCharge = gpGlobals->time; pev->classname = MAKE_STRING( "player" ); - pev->health = 100; pev->armorvalue = 0; + SetMaxArmor(g_modFeatures.MaxPlayerArmor()); pev->takedamage = DAMAGE_AIM; pev->solid = SOLID_SLIDEBOX; pev->movetype = MOVETYPE_WALK; - pev->max_health = pev->health; + pev->health = pev->max_health = g_modFeatures.MaxPlayerHealth(); pev->flags &= FL_PROXY; // keep proxy flag sey by engine pev->flags |= FL_CLIENT; pev->air_finished = gpGlobals->time + 12; @@ -3638,6 +3686,7 @@ void CBasePlayer::Spawn( void ) m_fWeapon = FALSE; m_pClientActiveItem = NULL; m_iClientBattery = -1; + m_iClientMaxBattery = -1; // reset all ammo values to 0 for( int i = 0; i < MAX_AMMO_TYPES; i++ ) @@ -3671,6 +3720,7 @@ void CBasePlayer::Precache( void ) m_bitsHUDDamage = -1; m_iClientBattery = -1; + m_iClientMaxBattery = -1; m_flFlashLightTime = 1; @@ -4168,7 +4218,9 @@ Reset stuff so that the state is transmitted. void CBasePlayer::ForceClientDllUpdate( void ) { m_iClientHealth = -1; + m_iClientMaxHealth = -1; m_iClientBattery = -1; + m_iClientMaxBattery = -1; m_iClientHideHUD = -1; // Vit_amiN: forcing to update m_iClientFOV = -1; // Vit_amiN: force client weapons to be sent m_ClientSndRoomtype = -1; @@ -4851,30 +4903,35 @@ void CBasePlayer::UpdateClientData( void ) gDisplayTitle = 0; } - if( pev->health != m_iClientHealth ) + if( pev->health != m_iClientHealth || pev->health != m_iClientMaxHealth ) { #define clamp( val, min, max ) ( ((val) > (max)) ? (max) : ( ((val) < (min)) ? (min) : (val) ) ) - int iHealth = clamp( pev->health, 0, 255 ); // make sure that no negative health values are sent + int iHealth = clamp( pev->health, 0, 9999 ); // make sure that no negative health values are sent if( pev->health > 0.0f && pev->health <= 1.0f ) iHealth = 1; // send "health" update message MESSAGE_BEGIN( MSG_ONE, gmsgHealth, NULL, pev ); - WRITE_BYTE( iHealth ); + WRITE_SHORT( iHealth ); + WRITE_SHORT( (int)pev->max_health ); MESSAGE_END(); m_iClientHealth = (int)pev->health; + m_iClientMaxHealth = (int)pev->max_health; } - if( (int)pev->armorvalue != m_iClientBattery ) + const int maxArmor = MaxArmor(); + if( (int)pev->armorvalue != m_iClientBattery || maxArmor != m_iClientMaxBattery ) { m_iClientBattery = (int)pev->armorvalue; + m_iClientMaxBattery = maxArmor; ASSERT( gmsgBattery > 0 ); // send "health" update message MESSAGE_BEGIN( MSG_ONE, gmsgBattery, NULL, pev ); WRITE_SHORT( (int)pev->armorvalue ); + WRITE_SHORT( maxArmor ); MESSAGE_END(); } @@ -5922,7 +5979,7 @@ class CPlayerCalcRatio : public CPointEntity { if (isFraction) { - return pPlayer->pev->armorvalue / MAX_NORMAL_BATTERY; + return pPlayer->pev->armorvalue / pPlayer->MaxArmor(); } else { diff --git a/dlls/player.h b/dlls/player.h index 9430f9ef2d..b0b601ef70 100644 --- a/dlls/player.h +++ b/dlls/player.h @@ -200,7 +200,9 @@ class CBasePlayer : public CBaseMonster float m_tSneaking; int m_iUpdateTime; // stores the number of frame ticks before sending HUD update messages int m_iClientHealth; // the health currently known by the client. If this changes, send a new + int m_iClientMaxHealth; int m_iClientBattery; // the Battery currently known by the client. If this changes, send a new + int m_iClientMaxBattery; int m_iHideHUD; // the players hud weapon info is to be hidden int m_iClientHideHUD; int m_iFOV; // field of view @@ -238,7 +240,12 @@ class CBasePlayer : public CBaseMonster virtual void PostThink( void ); virtual Vector GetGunPosition( void ); virtual int TakeHealth(CBaseEntity *pHealer, float flHealth, int bitsDamageType ); + void SetHealth(int health, bool allowOverheal = false); + void SetMaxHealth(int maxHealth, bool clampValue = true); virtual int TakeArmor(CBaseEntity *pCharger, float flArmor); + int MaxArmor(); + void SetMaxArmor(int maxArmor, bool clampValue = true); + void SetArmor(int armor, bool allowOvercharge = false); virtual void TraceAttack( entvars_t *pevInflictor, entvars_t *pevAttacker, float flDamage, Vector vecDir, TraceResult *ptr, int bitsDamageType); virtual int TakeDamage( entvars_t* pevInflictor, entvars_t* pevAttacker, float flDamage, int bitsDamageType); virtual void Killed( entvars_t *pevInflictor, entvars_t *pevAttacker, int iGib ); diff --git a/dlls/weapons.h b/dlls/weapons.h index 1cf198c459..1c0a07e987 100644 --- a/dlls/weapons.h +++ b/dlls/weapons.h @@ -72,8 +72,6 @@ class CGrenade : public CBaseMonster #define ITEM_SECURITY 3 #define ITEM_BATTERY 4 -#define MAX_NORMAL_BATTERY 100 - // weapon weight factors (for auto-switching) (-1 = noswitch) #define CROWBAR_WEIGHT 0 #define GLOCK_WEIGHT 10 diff --git a/features/featureful_server.cfg b/features/featureful_server.cfg index e758a4abf0..e09c568771 100644 --- a/features/featureful_server.cfg +++ b/features/featureful_server.cfg @@ -1,3 +1,13 @@ +///////// +// PLAYER +///////// + +// Default max health for the player +player_maxhealth 100 + +// Default max armor for the player +player_maxarmor 100 + ///////// // ITEMS ///////// diff --git a/fgd/halflife.fgd b/fgd/halflife.fgd index efa568384c..5ab1c0fbf8 100644 --- a/fgd/halflife.fgd +++ b/fgd/halflife.fgd @@ -2876,8 +2876,20 @@ 1: "Flashlight" 2: "NVG" ] - health(integer) : "Starting health" - armorvalue(integer) : "Starting armor" + health(integer) : "Set health" + allow_overheal(choices) : "Allow OverHeal" : : "Allow overheal if new health is higher than the current max health. Don't clamp health value to the max health if the new max health is lower than the current health." = + [ + 0: "No" + 1: "Yes" + ] + max_health(integer): "Set max health" + armorvalue(integer) : "Set armor" + allow_overcharge(choices) : "Allow armor OverCharge" : : "Allow armor overcharge if new armor is higher than the current max armor. Don't clamp armor value to the max armor if the new max armor is lower than the current armor." = + [ + 0: "No" + 1: "Yes" + ] + max_armor(integer): "Set max armor" ] @PointClass base(Targetname, Targetx) = game_team_master : "Team based master/relay"