public override void TickPerTurn(params object[] parameters) { HealthEntityCombatObject target = parameters[0] as HealthEntityCombatObject; AbilityStep_Damage dam = CreateInstance <AbilityStep_Damage>(); dam.amount = amount; dam.damageType = AbilityStep_Damage.DamageType.True; dam.damageTypePerc = AbilityStep_Damage.DamageTypePerc.Flat; target.TakeDamage(dam, null); }
public override void OnAttacked(params object[] parameters) { HealthEntityCombatObject attacker = parameters[0] as HealthEntityCombatObject; AbilityStep_Damage dam = new AbilityStep_Damage(); dam.amount = amount; dam.damageType = AbilityStep_Damage.DamageType.True; dam.damageTypePerc = AbilityStep_Damage.DamageTypePerc.Flat; attacker.TakeDamage(dam, null); }
public static ClashResult CaclulateFlatDamage(AbilityStep_Damage step, HealthEntityCombatObject attacker, HealthEntityCombatObject defender) { ClashResult result = new ClashResult(); // If defender is dead, result fails. if (step == null || defender == null || defender.IsDead) { result.name = ClashResult.Name.Failed; return(result); } // If defender is immune to damage, result immune. if (defender.IsImmuneToDamage()) { result.name = ClashResult.Name.Immune; return(result); } // Grab the damage amount. result.damage = step.amount; if (attacker != null) { // Multiply with raw damage of the attacker. result.damage = (int)(result.damage * attacker.Stats.rawDamageMultiplier.Value); // Check for vulnerable if (defender.IsVulnerable()) { result.damage = (int)(result.damage * 1.5f); } // Crit calculator. if (step.canCriticallyStrike) { float attackerCritChance = attacker.Stats.criticalChance.Value; // Get negative crit multiplier on target. foreach (var behaviour in defender.GetCritMultiplierBehaviours()) { attackerCritChance *= behaviour.modifyCritChanceAgainst; } // Roll the crit and double the damage. float critValue = Random.Range(0f, 1f); // Critical is success. if (critValue < attackerCritChance) { result.damage *= 2; result.criticalHit = true; } } // Calculate damage against armor or magic resist. switch (step.damageType) { case AbilityStep_Damage.DamageType.None: result.damage = 0; break; case AbilityStep_Damage.DamageType.Physical: // defender armor - attacker armor pen => clamped between 0-1. float defenderPenetratedArmor = Mathf.Clamp01(defender.Stats.armor.Value - attacker.Stats.armorPenetration.Value); result.damage = (int)(result.damage * (1 - defenderPenetratedArmor)); break; case AbilityStep_Damage.DamageType.Magic: // defender MR - attacker mr pen => clamped between 0-1. float defenderPenetratedMR = Mathf.Clamp01(defender.Stats.magicResist.Value - attacker.Stats.magicPenetration.Value); result.damage = (int)(result.damage * (1 - defenderPenetratedMR)); break; } } // Clamp it to 0. result.damage = Mathf.Max(0, result.damage); // If the clamped damage is 0, result immune. if (result.damage < 1) { result.name = ClashResult.Name.Immune; return(result); } result.name = ClashResult.Name.Damage; return(result); }
public DamageInfo TakeDamage(AbilityStep_Damage stepInfo, HealthEntityCombatObject attacker) { var result = DamageCalculator.CaclulateFlatDamage(stepInfo, attacker, this); /* * if (IsDead) * { * return default(DamageInfo); * } * * if (IsImmuneToDamage()) * { * Animator.SetTrigger("Block"); * DamageNumberCanvas canv = GameObject.Instantiate(FindObjectOfType<CombatManager>().damageNumberCanvasPrefab).GetComponent<DamageNumberCanvas>(); * canv.Display("Immune", Color.magenta); * canv.transform.position = transform.position; * return default(DamageInfo); * } */ DamageInfo damageInfo = new DamageInfo(); /* * * int amount = stepInfo.amount; * amount = Mathf.Max(0, amount); * if (attacker != null) * { * amount = (int)(amount * attacker.Stats.rawDamageMultiplier.Value); * } * * float random = Random.Range(0f, 1f); * float attackerCritChance = attacker.Stats.criticalChance.Value; * * foreach (var statusEffect in StatusEffects) * { * foreach (var behaviour in statusEffect.behaviour) * { * if (behaviour is WeakenBehaviour weaken) * { * attackerCritChance *= weaken.modifyCritChanceAgainst; * } * } * } * * bool crit = false; * if (attacker != null && random < attackerCritChance && stepInfo.canCriticallyStrike) * { * crit = true; * amount *= 2; * } * * switch (stepInfo.damageTypePerc) * { * case AbilityStep_Damage.DamageTypePerc.PercentageMaxHP: * amount = (int)(MaxHealth * (amount / 100f)); * break; * case AbilityStep_Damage.DamageTypePerc.None: * amount = 0; * break; * } * * switch (stepInfo.damageType) * { * case AbilityStep_Damage.DamageType.Physical: * amount = (int)Mathf.Ceil(amount * (1 - Mathf.Clamp01(Stats.armor.Value - ((attacker != null) ? attacker.Stats.armorPenetration.Value : 0)))); * break; * case AbilityStep_Damage.DamageType.Magic: * amount = (int)Mathf.Ceil(amount * (1 - Mathf.Clamp01(Stats.magicResist.Value - ((attacker != null) ? attacker.Stats.magicPenetration.Value : 0)))); * break; * case AbilityStep_Damage.DamageType.None: * amount = 0; * break; * }*/ //int amountRemaining = amount; switch (result.name) { case DamageCalculator.ClashResult.Name.Failed: return(default); case DamageCalculator.ClashResult.Name.Immune: Animator.SetTrigger("Block"); DamageNumberCanvas canv = GameObject.Instantiate(FindObjectOfType <CombatManager>().damageNumberCanvasPrefab).GetComponent <DamageNumberCanvas>(); canv.Display("Immune", Color.magenta); canv.transform.position = transform.position; return(default); } ReduceBlock(ref result.damage); /* * amountRemaining -= Block; * ModifyBlock(-amount); * * amountRemaining = Mathf.Clamp(amountRemaining, 0, amountRemaining);*/ if (result.damage > 0) { damageInfo.damageDealt = result.damage; DamageNumberCanvas canv = GameObject.Instantiate(FindObjectOfType <CombatManager>().damageNumberCanvasPrefab).GetComponent <DamageNumberCanvas>(); if (result.criticalHit) { canv.Display("CRIT! " + damageInfo.damageDealt.ToString(), Color.red); } else { canv.Display(damageInfo.damageDealt.ToString(), Color.red); } canv.transform.position = transform.position; Entity.Health -= damageInfo.damageDealt; Entity.Health = Mathf.Clamp(Health, 0, MaxHealth); if (Entity.Health > 0) { Animator.SetTrigger("Hit"); } } else { Animator.SetTrigger("Block"); DamageNumberCanvas canv = GameObject.Instantiate(FindObjectOfType <CombatManager>().damageNumberCanvasPrefab).GetComponent <DamageNumberCanvas>(); canv.Display("Blocked", Color.grey); canv.transform.position = transform.position; } if (attacker != null) { if (OnAttackedBehaviour != null) { OnAttackedBehaviour(attacker); } } if (Health <= 0) { Die(); OnDeath(this); } RefreshUI(); return(damageInfo); }