Crit power stat now functional, added comments on each stat field to better describe what the stat does and what values should be used.

This commit is contained in:
Sam 2021-05-20 21:08:42 -05:00 committed by Marcel Märtens
parent c3b834ec15
commit 855384fbeb
5 changed files with 43 additions and 12 deletions

View File

@ -9,7 +9,7 @@ ItemDef(
poise_resilience: Invincible,
energy_max: 9000,
energy_recovery: 9.0,
crit_chance: 1000.0,
crit_power: 1000.0,
stealth: 1000.0,
),
)

View File

@ -899,3 +899,19 @@ pub fn combat_rating(
// skills would account for. It should only not be 1.0 for non-humanoids
combined_rating * body.combat_multiplier()
}
pub fn compute_crit_mult(inventory: Option<&Inventory>) -> f32 {
// Starts with a value of 1.25 when summing the stats from each armor piece, and
// defaults to a value of 1.25 if no inventory is equipped
inventory.map_or(1.25, |inv| {
inv.equipped_items()
.filter_map(|item| {
if let ItemKind::Armor(armor) = &item.kind() {
Some(armor.get_crit_power())
} else {
None
}
})
.fold(1.25, |a, b| a + b)
})
}

View File

@ -29,15 +29,27 @@ impl Armor {
#[derive(Clone, Copy, Debug, PartialEq, Serialize, Deserialize)]
pub struct Stats {
#[serde(default)]
/// Protection is non-linearly transformed to a damage reduction using
/// (prot / (60 + prot))
protection: Protection,
#[serde(default)]
/// Poise protection is non-linearly transformed to a poise damage reduction
/// using (prot / (60 + prot))
poise_resilience: Protection,
#[serde(default)]
/// Energy max is summed, and then applied directly to the max energy stat
/// (multiply values by 10 for expected results, as energy internally is 10x
/// larger to allow smaller changes to occur with an integer)
energy_max: i32,
#[serde(default)]
/// Energy recovery is summed, and then added to 1.0. When attacks reward
/// energy, it is then multiplied by this value before the energy is
/// rewarded.
energy_recovery: f32,
#[serde(default)]
crit_chance: f32,
/// Crit power is summed, and then added to the default crit multiplier of
/// 1.25. Damage is multiplied by this value when an attack crits.
crit_power: f32,
#[serde(default)]
stealth: f32,
}
@ -50,7 +62,7 @@ impl Stats {
poise_resilience: Protection,
energy_max: i32,
energy_recovery: f32,
crit_chance: f32,
crit_power: f32,
stealth: f32,
) -> Self {
Self {
@ -58,7 +70,7 @@ impl Stats {
poise_resilience,
energy_max,
energy_recovery,
crit_chance,
crit_power,
stealth,
}
}
@ -71,7 +83,7 @@ impl Stats {
pub fn get_energy_recovery(&self) -> f32 { self.energy_recovery }
pub fn get_crit_chance(&self) -> f32 { self.crit_chance }
pub fn get_crit_chance(&self) -> f32 { self.crit_power }
pub fn get_stealth(&self) -> f32 { self.stealth }
}
@ -85,7 +97,7 @@ impl Sub<Stats> for Stats {
poise_resilience: self.poise_resilience - other.poise_resilience,
energy_max: self.energy_max - other.energy_max,
energy_recovery: self.energy_recovery - other.energy_recovery,
crit_chance: self.crit_chance - other.crit_chance,
crit_power: self.crit_power - other.crit_power,
stealth: self.stealth - other.stealth,
}
}
@ -143,7 +155,7 @@ impl Armor {
pub fn get_energy_recovery(&self) -> f32 { self.stats.energy_recovery }
pub fn get_crit_chance(&self) -> f32 { self.stats.crit_chance }
pub fn get_crit_power(&self) -> f32 { self.stats.crit_power }
pub fn get_stealth(&self) -> f32 { self.stats.stealth }

View File

@ -64,9 +64,9 @@ pub struct Stats {
pub power: f32,
pub poise_strength: f32,
pub speed: f32,
pub crit_chance: f32,
// Done for testing purposes, properly remove stat from weapons later
#[serde(skip)]
pub crit_chance: f32,
pub crit_mult: f32,
}

View File

@ -1,4 +1,5 @@
use crate::{
combat,
comp::{
biped_large, biped_small,
inventory::slot::EquipSlot,
@ -730,22 +731,24 @@ pub fn get_hands(data: &JoinData) -> (Option<Hands>, Option<Hands>) {
)
}
/// Returns (critical chance, critical multiplier) which is calculated from
/// equipped weapon and equipped armor respectively
pub fn get_crit_data(data: &JoinData, ai: AbilityInfo) -> (f32, f32) {
const DEFAULT_CRIT_DATA: (f32, f32) = (0.5, 1.3);
const DEFAULT_CRIT_CHANCE: f32 = 0.1;
let crit_mult = combat::compute_crit_mult(Some(data.inventory));
use HandInfo::*;
let slot = match ai.hand {
Some(TwoHanded) | Some(MainHand) => EquipSlot::ActiveMainhand,
Some(OffHand) => EquipSlot::ActiveOffhand,
None => return DEFAULT_CRIT_DATA,
None => return DEFAULT_CRIT_CHANCE, crit_mult),
};
if let Some(item) = data.inventory.equipped(slot) {
if let ItemKind::Tool(tool) = item.kind() {
let crit_chance = tool.base_crit_chance(data.msm, item.components());
let crit_mult = tool.base_crit_mult(data.msm, item.components());
return (crit_chance, crit_mult);
}
}
DEFAULT_CRIT_DATA
(DEFAULT_CRIT_CHANCE, crit_mult)
}
pub fn handle_state_interrupt(data: &JoinData, update: &mut StateUpdate, attacks_interrupt: bool) {