using Server.Mobiles;
using Server.Network;
using Server.Spells;
using System;
using System.Collections.Generic;
using System.Linq;
namespace Server.Items
{
///
/// A quick attack to all enemies in range of your weapon that causes damage over time. Requires Bushido or Ninjitsu skill.
///
public class FrenziedWhirlwind : WeaponAbility
{
public override SkillName GetSecondarySkill(Mobile from)
{
return from.Skills[SkillName.Ninjitsu].Base > from.Skills[SkillName.Bushido].Base ? SkillName.Ninjitsu : SkillName.Bushido;
}
public override int BaseMana => 20;
private static readonly Dictionary m_Registry = new Dictionary();
public static Dictionary Registry => m_Registry;
public override void OnHit(Mobile attacker, Mobile defender, int damage)
{
if (!Validate(attacker)) //Mana check after check that there are targets
return;
ClearCurrentAbility(attacker);
Map map = attacker.Map;
if (map == null)
return;
BaseWeapon weapon = attacker.Weapon as BaseWeapon;
if (weapon == null)
return;
List targets = SpellHelper.AcquireIndirectTargets(attacker, attacker.Location, attacker.Map, 2).OfType().ToList();
if (targets.Count > 0)
{
if (!CheckMana(attacker, true))
return;
attacker.FixedEffect(0x3728, 10, 15);
attacker.PlaySound(0x2A1);
if (m_Registry.ContainsKey(attacker))
{
RemoveFromRegistry(attacker);
}
m_Registry[attacker] = new InternalTimer(attacker, targets);
foreach (PlayerMobile pm in targets.OfType())
{
BuffInfo.AddBuff(pm, new BuffInfo(BuffIcon.SplinteringEffect, 1153804, 1028852, TimeSpan.FromSeconds(2.0), pm));
}
if (defender is PlayerMobile && attacker is PlayerMobile)
{
defender.SendSpeedControl(SpeedControlType.WalkSpeed);
BuffInfo.AddBuff(defender, new BuffInfo(BuffIcon.SplinteringEffect, 1153804, 1152144, TimeSpan.FromSeconds(2.0), defender));
Timer.DelayCall(TimeSpan.FromSeconds(2), mob => mob.SendSpeedControl(SpeedControlType.Disable), defender);
}
if (attacker is BaseCreature)
PetTrainingHelper.OnWeaponAbilityUsed((BaseCreature)attacker, SkillName.Ninjitsu);
}
}
public static void RemoveFromRegistry(Mobile from)
{
if (m_Registry.ContainsKey(from))
{
m_Registry[from].Stop();
m_Registry.Remove(from);
}
}
private class InternalTimer : Timer
{
private readonly Mobile m_Attacker;
private readonly List m_List;
private readonly long m_Start;
public InternalTimer(Mobile attacker, List list)
: base(TimeSpan.FromMilliseconds(500), TimeSpan.FromMilliseconds(500))
{
m_Attacker = attacker;
m_List = list;
m_Start = Core.TickCount;
Priority = TimerPriority.TwentyFiveMS;
DoHit();
Start();
}
protected override void OnTick()
{
if (m_Attacker.Alive)
DoHit();
if (!m_Attacker.Alive || m_Start + 2000 < Core.TickCount)
{
ColUtility.Free(m_List);
RemoveFromRegistry(m_Attacker);
}
}
private void DoHit()
{
if (m_List == null)
return;
foreach (Mobile m in m_List)
{
if (m_Attacker.InRange(m.Location, 2) && m.Alive && m.Map == m_Attacker.Map)
{
m_Attacker.FixedEffect(0x3728, 10, 15);
m_Attacker.PlaySound(0x2A1);
int skill = m_Attacker is BaseCreature ? (int)m_Attacker.Skills[SkillName.Ninjitsu].Value :
(int)Math.Max(m_Attacker.Skills[SkillName.Bushido].Value, m_Attacker.Skills[SkillName.Ninjitsu].Value);
int baseMin = Math.Max(5, (skill / 50) * 5);
AOS.Damage(m, m_Attacker, Utility.RandomMinMax(baseMin, (baseMin * 3) + 2), 100, 0, 0, 0, 0);
}
}
}
}
}
}