Overwrite
Complete Overwrite of the Folder with the free shard. ServUO 57.3 has been added.
This commit is contained in:
596
Scripts/Services/Pet Training/AreaEffects.cs
Normal file
596
Scripts/Services/Pet Training/AreaEffects.cs
Normal file
@@ -0,0 +1,596 @@
|
||||
using System;
|
||||
using Server;
|
||||
using System.Collections.Generic;
|
||||
using Server.Spells;
|
||||
using System.Linq;
|
||||
using Server.Network;
|
||||
using Server.Items;
|
||||
|
||||
namespace Server.Mobiles
|
||||
{
|
||||
public abstract class AreaEffect
|
||||
{
|
||||
public virtual int ManaCost { get { return 20; } }
|
||||
public virtual int MaxRange { get { return 3; } }
|
||||
public virtual double TriggerChance { get { return 1.0; } }
|
||||
public virtual TimeSpan CooldownDuration { get { return TimeSpan.FromSeconds(30); } }
|
||||
public virtual bool RequiresCombatant { get { return true; } }
|
||||
|
||||
public virtual int EffectRange { get { return 5; } }
|
||||
|
||||
public AreaEffect()
|
||||
{
|
||||
}
|
||||
|
||||
public static bool CheckThinkTrigger(BaseCreature bc)
|
||||
{
|
||||
var profile = PetTrainingHelper.GetAbilityProfile(bc);
|
||||
|
||||
if (profile != null)
|
||||
{
|
||||
AreaEffect effect = null;
|
||||
|
||||
var effects = profile.GetAreaEffects().Where(a => !a.IsInCooldown(bc)).ToArray();
|
||||
|
||||
if (effects != null && effects.Length > 0)
|
||||
{
|
||||
effect = effects[Utility.Random(effects.Length)];
|
||||
}
|
||||
|
||||
if (effect != null)
|
||||
{
|
||||
return effect.Trigger(bc, bc.Combatant as Mobile);
|
||||
}
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
public virtual bool Trigger(BaseCreature creature, Mobile combatant)
|
||||
{
|
||||
if (CheckMana(creature) && Validate(creature, combatant) && TriggerChance >= Utility.RandomDouble())
|
||||
{
|
||||
creature.Mana -= ManaCost;
|
||||
|
||||
DoEffects(creature, combatant);
|
||||
AddToCooldown(creature);
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
public virtual bool Validate(BaseCreature attacker, Mobile defender)
|
||||
{
|
||||
if (!attacker.Alive || attacker.Deleted || attacker.IsDeadBondedPet || attacker.BardPacified)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
|
||||
return !RequiresCombatant || (defender != null && defender.Alive && !defender.Deleted &&
|
||||
!defender.IsDeadBondedPet && defender.InRange(attacker.Location, MaxRange) &&
|
||||
defender.Map == attacker.Map && attacker.InLOS(defender));
|
||||
}
|
||||
|
||||
public bool CheckMana(BaseCreature bc)
|
||||
{
|
||||
return !bc.Controlled || bc.Mana >= ManaCost;
|
||||
}
|
||||
|
||||
public virtual void DoEffects(BaseCreature creature, Mobile combatant)
|
||||
{
|
||||
if (creature.Map == null || creature.Map == Map.Internal)
|
||||
return;
|
||||
|
||||
var count = 0;
|
||||
|
||||
foreach (var m in FindValidTargets(creature, EffectRange))
|
||||
{
|
||||
count++;
|
||||
DoEffect(creature, m);
|
||||
}
|
||||
|
||||
if (count > 0)
|
||||
{
|
||||
OnAfterEffects(creature, combatant);
|
||||
}
|
||||
}
|
||||
|
||||
public virtual void DoEffect(BaseCreature creature, Mobile defender)
|
||||
{
|
||||
}
|
||||
|
||||
public virtual void OnAfterEffects(BaseCreature creature, Mobile defender)
|
||||
{
|
||||
}
|
||||
|
||||
public static IEnumerable<Mobile> FindValidTargets(BaseCreature creature, int range)
|
||||
{
|
||||
IPooledEnumerable eable = creature.GetMobilesInRange(range);
|
||||
|
||||
foreach (Mobile m in eable.OfType<Mobile>())
|
||||
{
|
||||
if (ValidTarget(creature, m))
|
||||
{
|
||||
yield return m;
|
||||
}
|
||||
}
|
||||
|
||||
eable.Free();
|
||||
}
|
||||
|
||||
public static bool ValidTarget(Mobile from, Mobile to)
|
||||
{
|
||||
return to != from && to.Alive && !to.IsDeadBondedPet &&
|
||||
from.CanBeHarmful(to, false) &&
|
||||
SpellHelper.ValidIndirectTarget(from, to) &&
|
||||
from.InLOS(to);
|
||||
}
|
||||
|
||||
public List<BaseCreature> _Cooldown;
|
||||
|
||||
public bool IsInCooldown(BaseCreature m)
|
||||
{
|
||||
return _Cooldown != null && _Cooldown.Contains(m);
|
||||
}
|
||||
|
||||
public void AddToCooldown(BaseCreature bc)
|
||||
{
|
||||
var cooldown = GetCooldown(bc);
|
||||
|
||||
if (cooldown != TimeSpan.MinValue)
|
||||
{
|
||||
if (_Cooldown == null)
|
||||
_Cooldown = new List<BaseCreature>();
|
||||
|
||||
_Cooldown.Add(bc);
|
||||
Timer.DelayCall<BaseCreature>(cooldown, RemoveFromCooldown, bc);
|
||||
}
|
||||
}
|
||||
|
||||
public virtual TimeSpan GetCooldown(BaseCreature m)
|
||||
{
|
||||
return CooldownDuration;
|
||||
}
|
||||
|
||||
public void RemoveFromCooldown(BaseCreature m)
|
||||
{
|
||||
_Cooldown.Remove(m);
|
||||
}
|
||||
|
||||
public static AreaEffect[] Effects { get { return _Effects; } }
|
||||
private static AreaEffect[] _Effects;
|
||||
|
||||
static AreaEffect()
|
||||
{
|
||||
_Effects = new AreaEffect[7];
|
||||
|
||||
_Effects[0] = new AuraOfEnergy();
|
||||
_Effects[1] = new AuraOfNausea();
|
||||
_Effects[2] = new EssenceOfDisease();
|
||||
_Effects[3] = new EssenceOfEarth();
|
||||
_Effects[4] = new ExplosiveGoo();
|
||||
_Effects[5] = new AuraDamage();
|
||||
_Effects[6] = new PoisonBreath();
|
||||
}
|
||||
|
||||
public static AreaEffect AuraOfEnergy
|
||||
{
|
||||
get
|
||||
{
|
||||
return _Effects[0];
|
||||
}
|
||||
}
|
||||
|
||||
public static AreaEffect AuraOfNausea
|
||||
{
|
||||
get
|
||||
{
|
||||
return _Effects[1];
|
||||
}
|
||||
}
|
||||
|
||||
public static AreaEffect EssenceOfDisease
|
||||
{
|
||||
get
|
||||
{
|
||||
return _Effects[2];
|
||||
}
|
||||
}
|
||||
|
||||
public static AreaEffect EssenceOfEarth
|
||||
{
|
||||
get
|
||||
{
|
||||
return _Effects[3];
|
||||
}
|
||||
}
|
||||
|
||||
public static AreaEffect ExplosiveGoo
|
||||
{
|
||||
get
|
||||
{
|
||||
return _Effects[4];
|
||||
}
|
||||
}
|
||||
|
||||
public static AreaEffect AuraDamage
|
||||
{
|
||||
get
|
||||
{
|
||||
return _Effects[5];
|
||||
}
|
||||
}
|
||||
|
||||
public static AreaEffect PoisonBreath
|
||||
{
|
||||
get
|
||||
{
|
||||
return _Effects[6];
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public class AuraOfEnergy : AreaEffect
|
||||
{
|
||||
public AuraOfEnergy()
|
||||
{
|
||||
}
|
||||
|
||||
public override void DoEffect(BaseCreature creature, Mobile defender)
|
||||
{
|
||||
AOS.Damage(defender, creature, Utility.RandomMinMax(20, 30), 0, 0, 0, 0, 100);
|
||||
|
||||
defender.SendLocalizedMessage(1072073, false, creature.Name); // : The creature's aura of energy is damaging you!
|
||||
|
||||
creature.DoHarmful(defender);
|
||||
defender.FixedParticles(0x374A, 10, 30, 5052, 1278, 0, EffectLayer.Waist);
|
||||
defender.PlaySound(0x51D);
|
||||
}
|
||||
}
|
||||
|
||||
public class AuraOfNausea : AreaEffect
|
||||
{
|
||||
public override TimeSpan CooldownDuration { get { return TimeSpan.FromSeconds(40 + Utility.RandomDouble() * 30); } }
|
||||
public override int MaxRange { get { return 4; } }
|
||||
public override int EffectRange { get { return 4; } }
|
||||
public override int ManaCost { get { return 100; } }
|
||||
|
||||
public static Dictionary<Mobile, Timer> _Table;
|
||||
|
||||
public AuraOfNausea()
|
||||
{
|
||||
}
|
||||
|
||||
public override void DoEffect(BaseCreature creature, Mobile defender)
|
||||
{
|
||||
if (_Table == null)
|
||||
{
|
||||
_Table = new Dictionary<Mobile, Timer>();
|
||||
}
|
||||
|
||||
if (_Table.ContainsKey(defender))
|
||||
{
|
||||
Timer timer = _Table[defender];
|
||||
|
||||
if (timer != null)
|
||||
timer.Stop();
|
||||
|
||||
_Table[defender] = Timer.DelayCall<Mobile>(TimeSpan.FromSeconds(30), EndNausea, defender);
|
||||
}
|
||||
else
|
||||
{
|
||||
_Table.Add(defender, Timer.DelayCall<Mobile>(TimeSpan.FromSeconds(30), EndNausea, defender));
|
||||
}
|
||||
|
||||
defender.Animate(32, 5, 1, true, false, 0); // bow animation
|
||||
defender.SendLocalizedMessage(1072068); // Your enemy's putrid presence envelops you, overwhelming you with nausea.
|
||||
|
||||
BuffInfo.AddBuff(defender, new BuffInfo(BuffIcon.AuraOfNausea, 1153792, 1153819, TimeSpan.FromSeconds(30), defender, "60\t60\t60\t5"));
|
||||
}
|
||||
|
||||
public static void EndNausea(Mobile m)
|
||||
{
|
||||
if (_Table != null && _Table.ContainsKey(m))
|
||||
{
|
||||
_Table.Remove(m);
|
||||
|
||||
BuffInfo.RemoveBuff(m, BuffIcon.AuraOfNausea);
|
||||
m.Delta(MobileDelta.WeaponDamage);
|
||||
|
||||
if (_Table.Count == 0)
|
||||
_Table = null;
|
||||
}
|
||||
}
|
||||
|
||||
public static bool UnderNausea(Mobile m)
|
||||
{
|
||||
return _Table != null && _Table.ContainsKey(m);
|
||||
}
|
||||
}
|
||||
|
||||
public class EssenceOfDisease : AreaEffect
|
||||
{
|
||||
public EssenceOfDisease()
|
||||
{
|
||||
}
|
||||
|
||||
public override void DoEffect(BaseCreature creature, Mobile defender)
|
||||
{
|
||||
AOS.Damage(defender, creature, Utility.RandomMinMax(20, 30), 0, 0, 0, 100, 0);
|
||||
|
||||
defender.SendLocalizedMessage(1072074, false, creature.Name);
|
||||
|
||||
creature.DoHarmful(defender);
|
||||
defender.FixedParticles(0x374A, 10, 30, 5052, 1272, 0, EffectLayer.Waist);
|
||||
defender.PlaySound(0x476);
|
||||
}
|
||||
}
|
||||
|
||||
public class EssenceOfEarth : AreaEffect
|
||||
{
|
||||
public EssenceOfEarth()
|
||||
{
|
||||
}
|
||||
|
||||
public override void DoEffect(BaseCreature creature, Mobile defender)
|
||||
{
|
||||
AOS.Damage(defender, creature, Utility.RandomMinMax(20, 30), 100, 0, 0, 0, 0);
|
||||
|
||||
defender.SendLocalizedMessage(1072075, false, creature.Name);
|
||||
|
||||
creature.DoHarmful(defender);
|
||||
defender.FixedParticles(0x374A, 10, 30, 5052, 1836, 0, EffectLayer.Waist);
|
||||
defender.PlaySound(0x22C);
|
||||
}
|
||||
}
|
||||
|
||||
public class ExplosiveGoo : AreaEffect
|
||||
{
|
||||
public override int ManaCost { get { return 30; } }
|
||||
|
||||
private bool _DoingEffect;
|
||||
|
||||
public ExplosiveGoo()
|
||||
{
|
||||
}
|
||||
|
||||
public override void DoEffects(BaseCreature creature, Mobile combatant)
|
||||
{
|
||||
if (_DoingEffect)
|
||||
return;
|
||||
|
||||
Server.Effects.SendTargetParticles(creature, 0x3709, 10, 15, 2724, 0, 9907, EffectLayer.LeftFoot, 0);
|
||||
creature.PlaySound(0x348);
|
||||
|
||||
_DoingEffect = true;
|
||||
|
||||
Timer.DelayCall(TimeSpan.FromSeconds(1.0), () =>
|
||||
{
|
||||
base.DoEffects(creature, combatant);
|
||||
_DoingEffect = false;
|
||||
});
|
||||
}
|
||||
|
||||
public override void DoEffect(BaseCreature creature, Mobile defender)
|
||||
{
|
||||
Timer.DelayCall<Mobile>(TimeSpan.FromMilliseconds(Utility.RandomMinMax(10, 1000)), m =>
|
||||
{
|
||||
if (m.Alive && !m.Deleted && m.Map != null)
|
||||
{
|
||||
Point3D p = m.Location;
|
||||
for (int x = -1; x <= 1; x++)
|
||||
{
|
||||
for (int y = -1; y <= 1; y++)
|
||||
{
|
||||
Server.Effects.SendLocationEffect(new Point3D(p.X + x, p.Y + y, p.Z), m.Map, 0x3728, 13, 1921, 3);
|
||||
}
|
||||
}
|
||||
|
||||
creature.DoHarmful(defender);
|
||||
AOS.Damage(m, creature, Utility.RandomMinMax(30, 40), 0, 100, 0, 0, 0);
|
||||
m.SendLocalizedMessage(1112366); // The flammable goo covering you bursts into flame!
|
||||
}
|
||||
}, defender);
|
||||
}
|
||||
}
|
||||
|
||||
public class PoisonBreath : AreaEffect
|
||||
{
|
||||
public override double TriggerChance { get { return 0.4; } }
|
||||
public override int EffectRange { get { return 10; } }
|
||||
public override int ManaCost { get { return 50; } }
|
||||
|
||||
public PoisonBreath()
|
||||
{
|
||||
}
|
||||
|
||||
public override void DoEffect(BaseCreature creature, Mobile m)
|
||||
{
|
||||
m.ApplyPoison(creature, GetPoison(creature));
|
||||
|
||||
Server.Effects.SendLocationParticles(
|
||||
EffectItem.Create(m.Location, m.Map, EffectItem.DefaultDuration), 0x36B0, 1, 14, 63, 7, 9915, 0);
|
||||
|
||||
Server.Effects.PlaySound(m.Location, m.Map, 0x229);
|
||||
var damage = GetDamage(creature);
|
||||
|
||||
if (damage > 0)
|
||||
{
|
||||
creature.DoHarmful(m);
|
||||
AOS.Damage(m, creature, damage, 0, 0, 0, 100, 0);
|
||||
}
|
||||
}
|
||||
|
||||
public override void OnAfterEffects(BaseCreature creature, Mobile defender)
|
||||
{
|
||||
if (creature.Controlled)
|
||||
{
|
||||
var profile = PetTrainingHelper.GetAbilityProfile(creature);
|
||||
|
||||
if ((profile != null && profile.HasAbility(MagicalAbility.Poisoning)) || 0.2 > Utility.RandomDouble())
|
||||
creature.CheckSkill(SkillName.Poisoning, 0, creature.Skills[SkillName.Poisoning].Cap);
|
||||
}
|
||||
}
|
||||
|
||||
public Poison GetPoison(BaseCreature bc)
|
||||
{
|
||||
int level = 0;
|
||||
double total = bc.Skills[SkillName.Poisoning].Value;
|
||||
|
||||
if (total >= 100)
|
||||
level = 4;
|
||||
else if (total > 60)
|
||||
level = 3;
|
||||
else if (total > 40)
|
||||
level = 2;
|
||||
else if (total > 20)
|
||||
level = 1;
|
||||
|
||||
return Poison.GetPoison(level);
|
||||
}
|
||||
|
||||
public int GetDamage(BaseCreature bc)
|
||||
{
|
||||
if (_DamageCreatures.Any(t => t == bc.GetType()))
|
||||
return 50;
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
private Type[] _DamageCreatures =
|
||||
{
|
||||
typeof(ValoriteElemental), typeof(BronzeElemental), typeof(Dimetrosaur), typeof(ChiefParoxysmus)
|
||||
};
|
||||
}
|
||||
|
||||
public class AuraDamage : AreaEffect
|
||||
{
|
||||
public override double TriggerChance { get { return 0.4; } }
|
||||
public override int EffectRange { get { return 10; } }
|
||||
public override int ManaCost { get { return 0; } }
|
||||
public override bool RequiresCombatant { get { return false; } }
|
||||
|
||||
public AuraDamage()
|
||||
{
|
||||
}
|
||||
|
||||
public override TimeSpan GetCooldown(BaseCreature bc)
|
||||
{
|
||||
return AuraDefinition.GetDefinition(bc).Cooldown;
|
||||
}
|
||||
|
||||
public override void DoEffect(BaseCreature creature, Mobile m)
|
||||
{
|
||||
var def = AuraDefinition.GetDefinition(creature);
|
||||
|
||||
if (def.Damage > 0)
|
||||
{
|
||||
AOS.Damage(
|
||||
m,
|
||||
creature,
|
||||
def.Damage,
|
||||
def.Physical,
|
||||
def.Fire,
|
||||
def.Cold,
|
||||
def.Poison,
|
||||
def.Energy,
|
||||
def.Chaos,
|
||||
def.Direct,
|
||||
DamageType.SpellAOE);
|
||||
|
||||
m.RevealingAction();
|
||||
}
|
||||
|
||||
if (creature is IAuraCreature)
|
||||
{
|
||||
((IAuraCreature)creature).AuraEffect(m);
|
||||
}
|
||||
}
|
||||
|
||||
public class AuraDefinition
|
||||
{
|
||||
public TimeSpan Cooldown { get; set; }
|
||||
public int Range { get; set; }
|
||||
|
||||
public int Damage { get; set; }
|
||||
public int Physical { get; set; }
|
||||
public int Fire { get; set; }
|
||||
public int Cold { get; set; }
|
||||
public int Poison { get; set; }
|
||||
public int Energy { get; set; }
|
||||
public int Chaos { get; set; }
|
||||
public int Direct { get; set; }
|
||||
|
||||
public Type[] Uses { get; private set; }
|
||||
|
||||
public AuraDefinition()
|
||||
: this(TimeSpan.FromSeconds(5), 4, 5, 0, 0, 0, 0, 0, 0, 100, new Type[] { })
|
||||
{
|
||||
}
|
||||
|
||||
public AuraDefinition(params Type[] uses)
|
||||
: this(TimeSpan.FromSeconds(5), 2, 5, 0, 100, 0, 0, 0, 0, 0, uses)
|
||||
{
|
||||
}
|
||||
|
||||
public AuraDefinition(TimeSpan cooldown, int range, int baseDamage, int phys, int fire, int cold, int poison, int energy, int chaos, int direct, Type[] uses)
|
||||
{
|
||||
Cooldown = cooldown;
|
||||
Range = range;
|
||||
Damage = baseDamage;
|
||||
Physical = phys;
|
||||
Fire = fire;
|
||||
Cold = cold;
|
||||
Poison = poison;
|
||||
Energy = energy;
|
||||
Chaos = chaos;
|
||||
Direct = direct;
|
||||
|
||||
Uses = uses;
|
||||
}
|
||||
|
||||
public static List<AuraDefinition> Definitions { get; private set; } = new List<AuraDefinition>();
|
||||
|
||||
public static void Initialize()
|
||||
{
|
||||
AuraDefinition defaul;
|
||||
AuraDefinition cora;
|
||||
AuraDefinition fireAura;
|
||||
AuraDefinition coldAura;
|
||||
|
||||
defaul = new AuraDefinition();
|
||||
Definitions.Add(defaul);
|
||||
|
||||
cora = new AuraDefinition(typeof(CoraTheSorceress));
|
||||
cora.Range = 3;
|
||||
cora.Damage = 10;
|
||||
cora.Fire = 0;
|
||||
Definitions.Add(cora);
|
||||
|
||||
fireAura = new AuraDefinition(typeof(FlameElemental), typeof(FireDaemon), typeof(LesserFlameElemental));
|
||||
fireAura.Range = 5;
|
||||
fireAura.Damage = 7;
|
||||
Definitions.Add(fireAura);
|
||||
|
||||
coldAura = new AuraDefinition(typeof(ColdDrake), typeof(FrostDrake), typeof(FrostDragon), typeof(SnowElemental), typeof(FrostMite), typeof(IceFiend), typeof(IceElemental), typeof(CorporealBrume));
|
||||
coldAura.Damage = 15;
|
||||
coldAura.Fire = 0;
|
||||
coldAura.Cold = 100;
|
||||
Definitions.Add(coldAura);
|
||||
}
|
||||
|
||||
public static AuraDefinition GetDefinition(BaseCreature bc)
|
||||
{
|
||||
var def = Definitions.FirstOrDefault(d => d.Uses.Any(t => t == bc.GetType()));
|
||||
|
||||
if (def == null)
|
||||
{
|
||||
return Definitions[0]; // Default
|
||||
}
|
||||
|
||||
return def;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user