]> de.git.xonotic.org Git - xonotic/xonotic-data.pk3dir.git/commitdiff
Added handicap API.
authorLyberta <lyberta@lyberta.net>
Wed, 6 Sep 2017 05:55:03 +0000 (08:55 +0300)
committerLyberta <lyberta@lyberta.net>
Wed, 6 Sep 2017 05:55:03 +0000 (08:55 +0300)
qcsrc/common/mutators/mutator/dynamic_handicap/sv_dynamic_handicap.qc
qcsrc/server/_mod.inc
qcsrc/server/_mod.qh
qcsrc/server/client.qc
qcsrc/server/handicap.qc [new file with mode: 0644]
qcsrc/server/handicap.qh [new file with mode: 0644]
qcsrc/server/player.qc

index 43f10fd2c6bb2b568a2ddb34897305c28c2f2d00..817e561859194cdbec01d457966d55e14876c60a 100644 (file)
@@ -13,8 +13,6 @@ float autocvar_g_dynamic_handicap_scale;
 float autocvar_g_dynamic_handicap_min; ///< The minimum value of the handicap.
 float autocvar_g_dynamic_handicap_max; ///< The maximum value of the handicap.
 
-.float dynamic_handicap; ///< Holds the dynamic handicap value.
-
 //====================== Forward declarations =================================
 
 /// \brief Returns the base value of the handicap.
@@ -43,9 +41,9 @@ void DynamicHandicap_UpdateHandicap(entity player)
        //PrintToChat(player, strcat("Base handicap = ", ftos(handicap)));
        handicap = DynamicHandicap_ScaleHandicap(handicap);
        //PrintToChat(player, strcat("Scaled handicap = ", ftos(handicap)));
-       player.dynamic_handicap = DynamicHandicap_ClampHandicap(handicap);
-       //PrintToChat(player, strcat("Clamped handicap = ",
-       //      ftos(player.dynamic_handicap)));
+       handicap = DynamicHandicap_ClampHandicap(handicap);
+       //PrintToChat(player, strcat("Clamped handicap = ", ftos(handicap)));
+       Handicap_SetForcedHandicap(player, handicap);
 }
 
 float DynamicHandicap_GetBaseValue(entity player)
@@ -130,28 +128,6 @@ MUTATOR_HOOKFUNCTION(dynamic_handicap, ClientConnect)
        DynamicHandicap_UpdateHandicap(player);
 }
 
-/// \brief Hook which is called when the damage amount must be determined.
-MUTATOR_HOOKFUNCTION(dynamic_handicap, Damage_Calculate)
-{
-       entity frag_attacker = M_ARGV(1, entity);
-       entity frag_target = M_ARGV(2, entity);
-       float deathtype = M_ARGV(3, float);
-       float damage = M_ARGV(4, float);
-       if (DEATH_ISSPECIAL(deathtype))
-       {
-               return;
-       }
-       if (IS_CLIENT(frag_attacker))
-       {
-               damage /= frag_attacker.dynamic_handicap;
-       }
-       if (IS_CLIENT(frag_target))
-       {
-               damage *= frag_target.dynamic_handicap;
-       }
-       M_ARGV(4, float) = damage;
-}
-
 /// \brief Hook that is called when player dies.
 MUTATOR_HOOKFUNCTION(dynamic_handicap, PlayerDies)
 {
index 99115fbdc4fcaa48d2b3b33f8aca6458d530d718..de7e01aa7a862d3f328d0c02a3fdd542e5238ad9 100644 (file)
@@ -10,6 +10,7 @@
 #include <server/g_models.qc>
 #include <server/g_subs.qc>
 #include <server/g_world.qc>
+#include <server/handicap.qc>
 #include <server/impulse.qc>
 #include <server/ipban.qc>
 #include <server/item_key.qc>
index 3a8898670354511f40a1e515d25aeae0d5b28068..67f6aae4db511fd7cb1b91cb1cdb7412c7f017ea 100644 (file)
@@ -10,6 +10,7 @@
 #include <server/g_models.qh>
 #include <server/g_subs.qh>
 #include <server/g_world.qh>
+#include <server/handicap.qh>
 #include <server/impulse.qh>
 #include <server/ipban.qh>
 #include <server/item_key.qh>
index 6a978c6aebe631eef3c51e8016815a7697a24a93..13111fbd6517b71108b696429732f92b98d622a0 100644 (file)
@@ -14,6 +14,7 @@
 #include "spawnpoints.qh"
 #include "resources.qh"
 #include "g_damage.qh"
+#include "handicap.qh"
 #include "g_hook.qh"
 #include "command/common.qh"
 #include "cheats.qh"
@@ -1272,6 +1273,8 @@ void ClientConnect(entity this)
                it.init_for_player(it, this);
        });
 
+       Handicap_Initialize(this);
+
        MUTATOR_CALLHOOK(ClientConnect, this);
 
        if (IS_REAL_CLIENT(this))
diff --git a/qcsrc/server/handicap.qc b/qcsrc/server/handicap.qc
new file mode 100644 (file)
index 0000000..078c703
--- /dev/null
@@ -0,0 +1,38 @@
+#include "handicap.qh"
+
+/// \file
+/// \brief Source file that contains implementation of the handicap system.
+/// \author Lyberta
+/// \copyright GNU GPLv2 or any later version.
+
+.float m_handicap; ///< Holds the handicap value.
+
+void Handicap_Initialize(entity player)
+{
+       player.m_handicap = 1;
+}
+
+float Handicap_GetVoluntaryHandicap(entity player)
+{
+       return bound(1.0, CS(player).cvar_cl_handicap, 10.0);
+}
+
+float Handicap_GetForcedHandicap(entity player)
+{
+       return player.m_handicap;
+}
+
+void Handicap_SetForcedHandicap(entity player, float value)
+{
+       if (value <= 0)
+       {
+               error("Handicap_SetForcedHandicap: Invalid handicap value.");
+       }
+       player.m_handicap = value;
+}
+
+float Handicap_GetTotalHandicap(entity player)
+{
+       return Handicap_GetForcedHandicap(player) * Handicap_GetVoluntaryHandicap(
+               player);
+}
diff --git a/qcsrc/server/handicap.qh b/qcsrc/server/handicap.qh
new file mode 100644 (file)
index 0000000..fa45a0e
--- /dev/null
@@ -0,0 +1,40 @@
+#pragma once
+
+/// \file
+/// \brief Header file that describes the handicap system.
+/// \author Lyberta
+/// \copyright GNU GPLv2 or any later version.
+
+// Handicap is used to make the game harder for strong players and easier for
+// weak players. Values greater than 1 make the game harder and values less than
+// 1 make the game easier. Right now handicap only affects damage. There are 2
+// types of handicap: voluntary and forced. Voluntary handicap can be set via
+// cl_handicap cvar. For obvious reasons, it can't be less than 1. Forced
+// handicap can be set by server mutators. The total handicap is the product of
+// voluntary and forced handicap.
+
+/// \brief Initializes handicap to its default value.
+/// \param[in,out] player Player to initialize.
+/// \return No return.
+void Handicap_Initialize(entity player);
+
+/// \brief Returns the voluntary handicap of the player.
+/// \param[in] player Player to check.
+/// \return Voluntary handicap of the player.
+float Handicap_GetVoluntaryHandicap(entity player);
+
+/// \brief Returns the forced handicap of the player.
+/// \param[in] player Player to check.
+/// \return Forced handicap of the player.
+float Handicap_GetForcedHandicap(entity player);
+
+/// \brief Sets the forced handicap of the player.
+/// \param[in] player Player to alter.
+/// \param[in] value Handicap value to set.
+/// \return No return.
+void Handicap_SetForcedHandicap(entity player, float value);
+
+/// \brief Returns the total handicap of the player.
+/// \param[in] player Player to check.
+/// \return Total handicap of the player.
+float Handicap_GetTotalHandicap(entity player);
index dd061526265c12501deb2add452d694b5b7752be..ab4b8edc38d1556435adf7c8aea56b006ad284e6 100644 (file)
@@ -317,9 +317,11 @@ void PlayerDamage(entity this, entity inflictor, entity attacker, float damage,
 
        if(!DEATH_ISSPECIAL(deathtype))
        {
-               damage *= bound(1.0, CS(this).cvar_cl_handicap, 10.0);
-               if(this != attacker && IS_PLAYER(attacker))
-                       damage /= bound(1.0, CS(attacker).cvar_cl_handicap, 10.0);
+               damage *= Handicap_GetTotalHandicap(this);
+               if (this != attacker && IS_PLAYER(attacker))
+               {
+                       damage /= Handicap_GetTotalHandicap(attacker);
+               }
        }
 
        if (time < this.spawnshieldtime && autocvar_g_spawnshield_blockdamage < 1)