feat: Adds ability groups, DOT abilities, and combat abilities (#1264)
- [X] Adds `MonsterAbilitySingleTarget` - [X] Adds `MonsterAbilitySingleTargetDoT` - [X] Adds monster ability groups with weighted abilities - [X] Adds rune corruption ability - [X] Adds poison gas counter ability - [X] Adds stun attack ability - [X] Adds throw hatchet counter ability - [X] Adds fanning fire ability - [X] Fixes destroy equipment to skip spell channel items
This commit is contained in:
parent
df9a58dd49
commit
520f15e46c
62 changed files with 644 additions and 546 deletions
|
|
@ -0,0 +1,79 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
namespace Server.Mobiles;
|
||||
|
||||
public abstract class MonsterAbilitySingleTargetDoT : MonsterAbilitySingleTarget
|
||||
{
|
||||
private Dictionary<Mobile, ExpireTimer> _table;
|
||||
|
||||
public virtual TimeSpan MinDelay => TimeSpan.FromSeconds(10.0);
|
||||
public virtual TimeSpan MaxDelay => TimeSpan.FromSeconds(10.0);
|
||||
|
||||
protected override void OnTarget(MonsterAbilityTrigger trigger, BaseCreature source, Mobile defender)
|
||||
{
|
||||
_table ??= new Dictionary<Mobile, ExpireTimer>();
|
||||
|
||||
var duration = Utility.RandomMinMax(MinDelay, MaxDelay);
|
||||
var count = GetCount(source, defender);
|
||||
var timer = _table[defender] = new ExpireTimer(this, source, defender, duration, count);
|
||||
timer.Start();
|
||||
|
||||
StartEffect(source, defender);
|
||||
}
|
||||
|
||||
protected virtual int GetCount(BaseCreature source, Mobile defender) => 1;
|
||||
|
||||
protected abstract void StartEffect(BaseCreature source, Mobile defender);
|
||||
|
||||
protected virtual void EffectTick(BaseCreature source, Mobile defender, out TimeSpan nextDelay)
|
||||
{
|
||||
nextDelay = Utility.RandomMinMax(MinDelay, MaxDelay);
|
||||
}
|
||||
|
||||
protected abstract void EndEffect(BaseCreature source, Mobile defender);
|
||||
protected abstract void OnEffectExpired(BaseCreature source, Mobile defender);
|
||||
|
||||
public bool IsUnderEffect(Mobile defender) => _table?.ContainsKey(defender) == true;
|
||||
|
||||
protected bool RemoveEffect(BaseCreature source, Mobile defender)
|
||||
{
|
||||
if (_table?.Remove(defender, out var timer) == true)
|
||||
{
|
||||
timer.Stop();
|
||||
EndEffect(source, defender);
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
private class ExpireTimer : Timer
|
||||
{
|
||||
private BaseCreature _source;
|
||||
private Mobile _defender;
|
||||
private MonsterAbilitySingleTargetDoT _ability;
|
||||
|
||||
public ExpireTimer(
|
||||
MonsterAbilitySingleTargetDoT ability,
|
||||
BaseCreature source,
|
||||
Mobile defender,
|
||||
TimeSpan delay,
|
||||
int count
|
||||
) : base(delay, delay, count)
|
||||
{
|
||||
_ability = ability;
|
||||
_source = source;
|
||||
_defender = defender;
|
||||
}
|
||||
|
||||
protected override void OnTick()
|
||||
{
|
||||
_ability.EffectTick(_source, _defender, out var delay);
|
||||
Delay = delay;
|
||||
|
||||
_ability.RemoveEffect(_source, _defender);
|
||||
_ability.OnEffectExpired(_source, _defender);
|
||||
}
|
||||
}
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue