diff --git a/src/components.rs b/src/components.rs index 000624c..14e0ab6 100644 --- a/src/components.rs +++ b/src/components.rs @@ -156,6 +156,8 @@ pub struct MeleeWeapon { pub damage_die_type: i32, pub damage_bonus: i32, pub hit_bonus: i32, + pub proc_chance: Option, + pub proc_target: Option, } #[derive(Component, ConvertSaveload, Clone)] diff --git a/src/melee_combat_system.rs b/src/melee_combat_system.rs index e438899..62cd79a 100644 --- a/src/melee_combat_system.rs +++ b/src/melee_combat_system.rs @@ -64,12 +64,15 @@ impl<'a> System<'a> for MeleeCombatSystem { if attacker_pools.hit_points.current > 0 && target_pools.hit_points.current > 0 { let target_name = names.get(wants_melee.target).unwrap(); + // Define the basic unarmed attack -- overridden by wielding check below if a weapon is equipped let mut weapon_info = MeleeWeapon { attribute: WeaponAttribute::Might, hit_bonus: 0, damage_n_dice: 1, damage_die_type: 4, damage_bonus: 0, + proc_chance: None, + proc_target: None, }; if let Some(nat) = natural.get(entity) { @@ -89,9 +92,13 @@ impl<'a> System<'a> for MeleeCombatSystem { } } - for (wielded, melee) in (&equipped_items, &meleeweapons).join() { + let mut weapon_entity: Option = None; + for (weaponentity, wielded, melee) in + (&entities, &equipped_items, &meleeweapons).join() + { if wielded.owner == entity && wielded.slot == EquipmentSlot::Melee { weapon_info = melee.clone(); + weapon_entity = Some(weaponentity); } } @@ -159,6 +166,26 @@ impl<'a> System<'a> for MeleeCombatSystem { "{} hits {} for {} hp.", &name.name, &target_name.name, damage )); + + // Proc effects + if let Some(chance) = &weapon_info.proc_chance { + if rng.roll_dice(1, 100) <= (chance * 100.0) as i32 { + let effect_target = if weapon_info.proc_target.unwrap() == "Self" { + Targets::Single { target: entity } + } else { + Targets::Single { + target: wants_melee.target, + } + }; + add_effect( + Some(entity), + EffectType::ItemUse { + item: weapon_entity.unwrap(), + }, + effect_target, + ); + } + } } else if natural_roll == 1 { // Natural 1 miss log.append(format!( diff --git a/src/raws/item_structs.rs b/src/raws/item_structs.rs index 45ae687..53a459b 100644 --- a/src/raws/item_structs.rs +++ b/src/raws/item_structs.rs @@ -37,6 +37,9 @@ pub struct Weapon { pub attribute: String, pub base_damage: String, pub hit_bonus: i32, + pub proc_chance: Option, + pub proc_target: Option, + pub proc_effects: Option>, } #[derive(Deserialize, Debug)] diff --git a/src/raws/rawmaster.rs b/src/raws/rawmaster.rs index b28ce91..f28163b 100644 --- a/src/raws/rawmaster.rs +++ b/src/raws/rawmaster.rs @@ -401,6 +401,8 @@ pub fn spawn_named_item( damage_die_type: die_type, damage_bonus: bonus, hit_bonus: weapon.hit_bonus, + proc_chance: weapon.proc_chance, + proc_target: weapon.proc_target.clone(), }; wpn.attribute = match weapon.attribute.as_str() { @@ -409,6 +411,10 @@ pub fn spawn_named_item( }; eb = eb.with(wpn); + + if let Some(proc_effects) = &weapon.proc_effects { + apply_effects!(proc_effects, eb); + } } if let Some(wearable) = &item_template.wearable {