There are 3 types of Stats :
Stats have a Current value and a Base Value :
Note :
The component which handles all these stats is the StatsComponent. From it, you can :
Note : Try to always get the value of a Stat by its getter ! Doing this you can perform additional action inside the getter to modify the returned value.
For now, only Resistances and States are used. These two stats are used to handle damages.
Look at the TakeDamage() function to see them in action : IsDamageCounteredByState() will check if the damage can be ignored (For example if we have an Invincibility State) and the GetResistanceValueForDamage() get the resistance value to deduce from the damage value.
To add a new kind of stat all you need to do is add a new type of Resistance/State/Attribut, you just need to add/modify those enums (EAttributType, EResistenceType, EStateType) :
You'll also need to modify the DamageToResistanceMapping variable which is used to determine which resistance counters which damage type. In addition you may need to modify the content of the IsDamageCounteredByState() if you add/modify states.
I let you implement the solution you want for your game in terms of stats handling. Here are few ideas to help you.
1- If you want to modify the value of a stat based on another stat, then you can use the Getters to modify the return value based on the stats which influence to on you are getting.
Few examples :
2 - If you want to take into account the stats of the pawn which is damaging your Player and modify the damage received taking into account his stats, then you can implement this directly inside the TakeDamage function since the Instigator is the StatsComponent of the pawn responsible for damages :