Damage Calculation Is Hard

The thing about damage calculation is you kinda have to feel it out by vibes. You want increasing stats by certain amounts to feel like a noticeable difference in your damage output, whether that's +1 or +10, or anything else. But to achieve this, it feels like you need to write damage formula and then shape everything else around it and hope for the best.

Which is a problem if you reach a point or come back to it later and the vibes are off.

I'm presently struggling with looking at Witness To Unity's damage formula and thinking... this thing seems a mess. I'm multiplying or dividing the stats a lot just to get things into the "shape" I want, and maybe that's bad? I'm not sure how to explain this, so I'll start with how the stats and all currently work.

Equipment AttackComes from weapons. Affects Attack command damage. Hit RateComes from weapons. Affects Attack command accuracy*. DefenceComes from armour. Affects overall damage resistance. EvasionComes from armour. Usually affects overall evasion, except for certain skills. Innate Stats StrengthAffects physical damage of unarmed, most weapons, and physical skills. Does not factor into guns*. IntelligenceAffects damage of "magic" skills. EnduranceAffects overall damage resistance. Does not factor into healing. (Obviously.) AgilityAffects turn-order, rate, and native hit-rate/evasion.

Additional notes: The equipment stats will probably range from about 10 to 320. (Though hit-rate and evasion are 0-100, as percentages.) The innate stats will range from 10 to 128-ish from level 1 to 99. The goal is for damage in early game to be around 10-30 points a hit, and end-game the average attack shouldn't be consistently like, 9999.

With all that out of the way, let's get into the damage formula as it currently exists. For my own convenience I'll be using the variable names in the damage formula as follows, with some edits, so I hope that it remains understandable with the above as reference. (As in some cases the internal variables are named differently.)

First, we work out what kinda skill we're dealing with, and calculate the "base power" before other stats get involved. This might be a little confusing, as skills also have a "base power", so I'll call the following calculated power. Skill types include: Physical, Magical, Unarmed, Weapon, Gun, Healing, and Infinity.

... alright, the last one just returns Float::INFINITY. We can ignore that.

Physical/Unarmed@a.str * 8 Magic/Healing@a.int * 8 Weapon(Physical) + @a.atk Gun@a.atk * 2

During this phase, the calculated defence is also determined, but this is pretty consistent.

Defence(@b.res * 4) + @b.def

The damage formula varies a little between types, but the following basically occurs:

  1. Square root (calculated-power - calculated-defence), multiplied by 4.5 for physical skills, or 5 for everything else.
  2. Multiply this by the skill base power. This is a stat unique to each skill. "Weapon skills" have a base power of 1 so as to only use the stats of the weapons/characters themselves.
  3. Divide by 30 for physical skills, 35 for magic, 15 for unarmed, ignore for weapons and guns.
  4. Healing follows things a little differently: square root (calculated-power * skill base power / 3.)

So let's see how say, a physical skill's damage formula ends up looking, once it's all tied together.

sqrt(((@a.str * 8) - ((@b.res * 4) + @b.def)) * 4.5) * power / 30

Jesus christ.

So I started writing this for one main reason: what am I doing here. The fact I'm multiplying and dividing a lot of damage formulas feels like I'm doing things totally wrong. I've referenced Persona and Shin Megami Tensei a lot in my development of this project. A lot of stats and structure to things are shared with those games. But they most certainly aren't doing things like this.

Let's take a look at how P5 does this sort of thing. Note I am using terminology from my project to make the comparison easier.

Weaponssqrt(@a.atk / 2) * sqrt(@a.str) Physical Skillssqrt(skill base power) * sqrt(@a.str) Magical Skillssqrt(skill base power) * sqrt(@a.int) Defencecalculated power / sqrt((@b.res * 8) + @b.def)

I'm not too sure why the calculated power does square-roots separately like this, as near as I can tell combining them wouldn't make a difference. I'm simply following what the wiki is using here.

So let's try an experiment. Arin has a native Strength of 15. An enemy has 10 Defence and 13 Endurance. (Enemies don't have equipment, but I needed to add it to them so they didn't shatter like glass, which might be a factor in problems with my formula.) Arin uses Dragonian Slash, a Physical skill with a base power of 70.

  1. @a.str * 8 = 15 * 8 = 120
  2. @b.res * 4 + @b.def = 13 * 4 + 10 = 62
  3. sqrt((120 * 4.5) * 62) * 70 / 30 = 37

Let's see what happens if we use P5's formula.

  1. sqrt(70 * @a.str) = sqrt(70 * 15) = 32
  2. 32 / sqrt(@b.res * 8 + @b.def) = 32 / 10 = 3

Okay I'm truncating things a lot here, but decimal values aren't going to factor into the final damage.

... alright, so we don't really want the final damage to be that small, even for a beginning skill. Heck even P5 isn't that way, so I'm not sure what's going on. If I make this theoretical enemy have basically no defence this skill will do about 11 damage, but I don't really want that either. In a theoretical scenario of characters with about equal stats, it makes more sense to me to be doing a bit more damage.

The more I think about it the more I must be missing something. In the example testing this user did, they are getting a damage range of 22-24 from a 2 Magic/Int Arsene using Psiodyne. Psiodyne according to the wiki has a base power of 160. Near as I can work out, sqrt(160) * sqrt(2) is 17, not... say, 23. If the Full Moon challenge's Level is below 99 enough to take +30% damage from the player, it results in 23 damage. But that's before dividing by defence gets involved!

You can see now why this stuff is kinda hard. It's all theoretical, based on vibes, and there's sooo many factors to consider that shifting one or another thing throws everything else off. I'm also relying on 50-80 being a good value for the internal "base power" of an early-game skill.

I know what I want the numbers to be at the start (the numbers you see, the base power), what numbers I want to end up with as damage, and what kinda scaling I want over the course of the game, but the route there currently just feels dirty.

I would later come to the theory that Persona 3's damage formula is as follows.

sqrt(((@a.str * 8) / (@b.res * 4 + @b.def)) * power) * 7.4

I just have to determine if the growth rate of this damage works out as stats increase, whether to include level difference scaling (and how to scale the "levels" of enemies), and if this feels good for weapon and other damage types.

This would also suggest that defence is divided during damage calculation, but not against calculated power like the Megaten wiki believes. (At least for P3, but I'm leaning on the damage formulas being pretty similar between modern Atlus games if they share similar stat structures.)