The Ability System provides a flexible, extendable way to bundle behaviors which characters or objects can use to activate abilities.
Each ability is a scriptable object, which holds reference to any number of “condition” and “effect” scripts. Conditions limit the use of an ability, which can be “charge based” (like a grenade with 3 charges) or “recharge based”. If the ability is used when a condition is not met, it aborts the use action. Effects are the behaviors of an ability, such as increasing a stat, adding an effect to a weapon’s damage (such as fire or poison), or maintaining a passive effect (such as “gain stack of Fury after taking damage”). New effects and conditions can be easily scripted to add to an ever growing pool of functionality.
Scriptable objects are great for static data and behaviors, but cannot not hold a modifiable state. To overcome this, an ability at runtime is actually an “AbilityWrapper”. The ability scriptable object never handles the ability, but it does output an “AbilityWrapper” which contains all the functionality of the ability and can hold state. This wrapper is then used by scripts on a character to activate the ability.
I have implemented an upgrade system, which is rather rigid with regard to its form. It includes a “choice” upgrade path in the way of “Ability Unlocked -> Upgrade 1 -> Upgrade2 -> Upgrade 3a/ 3b->Upgrade 4a/ 4b -> Upgrade 5a/ 5b”. It cannot easily change this formula. However, the upgrade system merely determines how functionality is added when an ability is “upgraded” and can be easily replaced with another Upgrade System. This suits my needs perfectly, as upgrade/ progression systems are usually tailor made to a certain game.
One of the most ubiquitous effects is the “Change Stat” effect. This effect has its own “modifier” system which I created based off of this GDC talk by Aurelie Le Chevalier about the modifier system in “For Honor”. My Modifier system contains two parts, stats local to the ability, and an overall “modifier” system that effects whole characters.
The ability local stats are adjusted whenever the “change stat” upgrade is selected, such as “fire damage +50%”, and the character local stats are adjusted whenever the “change stats” ability effect is contained in the list of effects. When the ability is activated, the “change stats” effect interfaces with the modifier handler on the character and adds a modifier, such as “fire damage +50%”. When any ability, weapon, or behavior which relies on a stat updates, it will check with the modifier handler and adjust base stats against percent changes. In the case of “Fire Damage +50%”, all weapons, abilities, and behaviors which use the stat “Fire Damage” will handle increasing their base values by 50%.