Skip to content

Battle Fight Stats

Cromha edited this page Mar 26, 2024 · 13 revisions

Table Of Contents

Introduction

There are many attributes and statistics that modifies and vary battle fights. These attributes directly interact into the fight, such as damage, defense, protection or agility stats. Each of these attributes are used and calculated differently, with different formulas, making it hard for contributors or plugins creators to understand how these stats really affects the game. In this page, I'll explain every attributes/battle stats one by one, in each of its use case, with math graphics to understand better.

Note that you can find most of the formulas in the source/battle.py source code. Check the Enemies Difficulty Increasing wiki page for further knowledge.

Different Stats

Here are all attributes that affects the battle fights:

  • damage # defines how much a weapon/enemy can deal damage at its maximum (without taking in count the critical hit chance)
  • critical chance # how much chance a weapon/enemy can deal a critical hit (2 times the max damage)
  • agility # how much the player or an enemy have a chance to dodge attacks or run away at the start of the fight
  • armor protection # how much the enemies damages are reduced from the player's health
  • defend # how much a weapon could possibly restores health to the player when defending

Stats explanation

Damage Formulas

The damage stats probably the most defining stat in battle fights, being the core stats that defines how much an enemy/weapon could deal damage to an opponent. When used in weapons definitions, the damage stats comes alone with the damage attributes, defining directly that this weapon could deal from 0 to x damage. While in enemies definitions, it comes with both min damage and max damage attributes, defining that this enemy could dead from x to y damage.

So as you'd have guessed, the damage stats comes with 2 formulas: one for enemies damages and one for player damages.

Player Formula

player_damage = random.randint(1, int(item[player["held item"]]["damage"]))

Pretty straightforward formula, as you can see.

Enemy Formula

damage = random.randint(
    enemy_min_damage, enemy_max_damage
) * enemies_damage_coefficient - defend * (
    armor_protection * round(random.uniform(.50, .90), 1)
)
damage = round(damage)

The enemy formula is more complicated than the player formula: the enemy damage is equal to a random integer from the enemy minimum damage attribute to the enemy maximum damage, minus the player defend stat times the player's armor protection times a random floating number between .5 and .9; which could be simplified as: RandInt(enemy_min;enemy_max) * enemies_damage_coefficient - player_defend * (player_protection * RandFloat(.5;.9)). The enemies_damage_coefficient is a variable that's define in the main.py class, which is calculated depending on the player elapsed time game days. It's made so that the more the player's experienced, the more the enemies will deal more damage. You can check the Gameplay Guide wiki page about combat for more information.

        # x < 25days  => .85
        # x < 45days  => .95
        # x < 50days  => 1
        # x < 80days  => 1.15
        # x < 100days => 1.25
        # x < 150days => 1.35
        # x < 220days => 1.45
        # x < 300days => 1.5
$$f(enemymin;enemymax;playerdefend;playerprotection) = RandInt(enemymin;enemymax) - playerdefend * (playerprotection * RandFloat(.5;.9))$$

Critical Chance Formula

As said sooner, the critical chance stats defines how much an enemy or the player has a chance to deal a critical hit, which is equal to the maximum damage this entity can deal, times 2. Note that if the player's already dealt a critical hit, the enemy can't deal a critical hit to the player. Also, the critical chance formula is the same for every entity (both enemy and player). The critical hit chance stat is simply a floating number between 0 and 1, defining a percentage of chance on 100.

So if you have a critical hit chance of .17 let's say, you'll have 17% of chance to deal a critical hit.

Agility Formulas

The agility stats can act on many things: first, how much you have a chance to be able to run away at the beginning of a fight, then, how much you have a chance to dodge an enemy attack and finally how you much the defense stats work.


The first act of the agility stats is this formula, that determines if you can run away or not at the start of the fight, when the player first encounter the enemy:

if player["agility"] / round(random.uniform(1.10, 1.25), 2) > enemy_agility:
    print("You succeeded in running away from your enemy!")
    fighting = False

So, this formula will output a True boolean value if the player's current agility, split by a random floating number between 1.10 and 1.12 is greater than the enemy agility stats.


The second act of the agility stats is the following formula, which determines if the player have the ability to dodge the enemy attack:

if round(random.uniform(.30, player_agility), 2) > enemy_agility / 1.15 and random.uniform(0, 1) > .65:
    player_dodged = True
    print("You dodged your enemy attack!")

This formula will output a True boolean value if the random generated number from .30 to the player's current agility stats is greater than the enemy's agility split by 1.15 and also add a random change of 35% to that.

This formula also exists in a second way, but for the enemy (determine if the enemy can dodge your attack:

if round(random.uniform(.30, enemy_agility), 2) > player_agility / 1.15 and random.uniform(0, 1) > .65:
    enemy_dodged = True
    print("Your enemy dodged your attack!")

This formula will output a True boolean value if the random generated number from .30 to the enemy's current agility stats is greater than the player's agility split by 1.15 and also add a random change of 35% to that.


The third act of the agility stats is this next formula, defining how much the defend formulas works:

defend += random.randint(int(item[player["held item"]]["defend"]) / 2, int(item[player["held item"]]["defend"])) * player_agility

So, in this formula, the player's agility stats will multiply the base defense health regeneration.

Armor Protection Formula

The armor protection stats is the most complex stats. This stats will reduce the damage formula from the enemy, making the player getting less damage. Here is the formula where the armor protection stats is used:

damage = random.randint(
    enemy_min_damage, enemy_max_damage
) - defend * (
    armor_protection * round(random.uniform(.50, .90), 1)
)

As you can see, the armor protection is here to decrease, with the defend stats the damage taken by the player. To illustrate the act of the armor protection stats, here is a graph:

image

This shows every damage value if the enemy base damage is 7, the enemy defend value is 5 and the random number is .65. As shown, with an armor protection value of 0, the damage taken by the player will be approximately 5.4; with a value of .5, the taken damage will be about 5 and so on, where with a value of armor protection of 2.2, the taken damage will be equal to 0.

If we had other equations with other defend and armor protection values, it will clearly make a difference:

image


image


image

Here, you can see that with the green arrow, with negative defend values, the player will actually loose more health, so it could interesting to make a very weak weapon with a negative defend value, that will handicap the player. With the brown arrow, we can also see that the player may have the best armor protection stats, if he has no defend stats, it won't reduce the damage.


This graph may illustrate better:

image

Defend Formulas

The defend stats act on 2 cases: while the player is choosing to defend, and while the player is taking damage. You can look here to see how the defend stats affect on the second case. For the first case, look at the third act of the agility formulas heading.

Clone this wiki locally