fix: Updates mysticism spells and adds bombard (#1124)
This commit is contained in:
parent
54da2c94a5
commit
fbf60b65a5
8 changed files with 153 additions and 75 deletions
|
|
@ -192,7 +192,7 @@ namespace Server.Spells
|
|||
// Register(685, typeof(SpellTriggerSpell));
|
||||
// Register(686, typeof(MassSleepSpell));
|
||||
// Register(687, typeof(CleansingWindsSpell));
|
||||
// Register(688, typeof(BombardSpell));
|
||||
Register(688, typeof(BombardSpell));
|
||||
Register(689, typeof(SpellPlagueSpell));
|
||||
Register(690, typeof(HailStormSpell));
|
||||
Register(691, typeof(NetherCycloneSpell));
|
||||
|
|
|
|||
|
|
@ -40,7 +40,7 @@ namespace Server.Spells.Mysticism
|
|||
}
|
||||
else if (SpellHelper.CheckTown(p, Caster) && CheckSequence())
|
||||
{
|
||||
var level = (int)((GetBaseSkill(Caster) + GetBoostSkill(Caster)) / 2.0);
|
||||
var level = (int)((GetBaseSkill(Caster) + GetDamageSkill(Caster)) / 2.0);
|
||||
|
||||
var duration = TimeSpan.FromSeconds(10 + level);
|
||||
|
||||
|
|
|
|||
89
Projects/UOContent/Spells/Mysticism/BombardSpell.cs
Normal file
89
Projects/UOContent/Spells/Mysticism/BombardSpell.cs
Normal file
|
|
@ -0,0 +1,89 @@
|
|||
using Server.Targeting;
|
||||
using System;
|
||||
|
||||
namespace Server.Spells.Mysticism
|
||||
{
|
||||
public class BombardSpell : MysticSpell, ISpellTargetingMobile
|
||||
{
|
||||
private static readonly SpellInfo _info = new(
|
||||
"Bombard", "Corp Por Ylem",
|
||||
230,
|
||||
9022,
|
||||
Reagent.Bloodmoss,
|
||||
Reagent.Garlic,
|
||||
Reagent.SulfurousAsh,
|
||||
Reagent.DragonsBlood
|
||||
);
|
||||
|
||||
public BombardSpell(Mobile caster, Item scroll) : base(caster, scroll, _info)
|
||||
{
|
||||
}
|
||||
|
||||
public override SpellCircle Circle => SpellCircle.Sixth;
|
||||
public override bool DelayedDamage => true;
|
||||
|
||||
public override Type[] DelayedDamageSpellFamilyStacking => AOSNoDelayedDamageStackingSelf;
|
||||
|
||||
public override void OnCast()
|
||||
{
|
||||
Caster.Target = new SpellTargetMobile(this, TargetFlags.Harmful);
|
||||
}
|
||||
|
||||
public void Target(Mobile m)
|
||||
{
|
||||
if (CheckHSequence(m))
|
||||
{
|
||||
SpellHelper.Turn(Caster, m);
|
||||
|
||||
if (HasDelayedDamageContext(m))
|
||||
{
|
||||
DoHurtFizzle();
|
||||
return;
|
||||
}
|
||||
|
||||
var source = Caster;
|
||||
|
||||
if (SpellHelper.CheckReflect(6, ref source, ref m))
|
||||
{
|
||||
Timer.StartTimer(TimeSpan.FromSeconds(0.5), () =>
|
||||
{
|
||||
source.MovingEffect(m, 0x1363, 12, 1, false, true, 0, 0);
|
||||
source.PlaySound(0x64B);
|
||||
});
|
||||
}
|
||||
|
||||
Caster.MovingEffect(m, 0x1363, 12, 1, false, true, 0, 0);
|
||||
Caster.PlaySound(0x64B);
|
||||
|
||||
SpellHelper.Damage(this, m, GetNewAosDamage(40, 1, 5, m), 100, 0, 0, 0, 0);
|
||||
|
||||
Timer.StartTimer(TimeSpan.FromSeconds(1.2), () =>
|
||||
{
|
||||
if (CheckResisted(m))
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
var damageSkill = GetDamageSkill(Caster);
|
||||
var resist = GetResistSkill(m);
|
||||
|
||||
int secs = Math.Max(0, (int)(damageSkill / 10 - resist / 10));
|
||||
|
||||
if (secs > 0)
|
||||
{
|
||||
m.Paralyze(TimeSpan.FromSeconds(secs));
|
||||
}
|
||||
|
||||
// Up to 12% chance by checking mysticism + imbuing/focus against resist
|
||||
var knockBackChance = (GetBaseSkill(Caster) + damageSkill - resist) / 20;
|
||||
if (knockBackChance > 0 && Utility.RandomDouble() < knockBackChance)
|
||||
{
|
||||
m.Move(Caster.GetDirectionTo(m));
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
FinishSequence();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -24,20 +24,27 @@ namespace Server.Spells.Mysticism
|
|||
|
||||
public void Target(Mobile m)
|
||||
{
|
||||
if (m == null)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
if (CheckHSequence(m))
|
||||
{
|
||||
/* Conjures a magical eagle that assaults the Target with
|
||||
* its talons, dealing energy damage.
|
||||
*/
|
||||
|
||||
SpellHelper.Turn(Caster, m);
|
||||
|
||||
SpellHelper.CheckReflect(2, Caster, ref m);
|
||||
if (Core.SA && HasDelayedDamageContext(m))
|
||||
{
|
||||
DoHurtFizzle();
|
||||
return;
|
||||
}
|
||||
|
||||
var source = Caster;
|
||||
|
||||
if (SpellHelper.CheckReflect(2, ref source, ref m))
|
||||
{
|
||||
Timer.StartTimer(TimeSpan.FromSeconds(0.5), () =>
|
||||
{
|
||||
/* Conjures a magical eagle that assaults the Target with its talons, dealing energy damage. */
|
||||
source.MovingEffect(m, 0x407A, 8, 1, false, true, 0, 0);
|
||||
source.PlaySound(0x2EE);
|
||||
});
|
||||
}
|
||||
|
||||
Caster.MovingParticles(m, 0x407A, 7, 0, false, true, 0, 0, 0xBBE, 0xFA6, 0xFFFF, 0);
|
||||
Caster.PlaySound(0x2EE);
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
using System.Collections.Generic;
|
||||
using Server.Collections;
|
||||
|
||||
namespace Server.Spells.Mysticism
|
||||
{
|
||||
|
|
@ -24,62 +24,49 @@ namespace Server.Spells.Mysticism
|
|||
|
||||
public void Target(IPoint3D p)
|
||||
{
|
||||
if (SpellHelper.CheckTown(p, Caster) && CheckSequence())
|
||||
var loc = (p as Item)?.GetWorldLocation() ?? new Point3D(p);
|
||||
|
||||
if (SpellHelper.CheckTown(loc, Caster) && CheckSequence())
|
||||
{
|
||||
/* Summons a storm of hailstones that strikes all Targets
|
||||
* within a radius around the Target's Location, dealing
|
||||
* cold damage.
|
||||
/* Summons a storm of hailstones that strikes all Targets within a radius around the Target's Location,
|
||||
* dealing cold damage.
|
||||
*/
|
||||
|
||||
SpellHelper.Turn(Caster, p);
|
||||
|
||||
if (p is Item item)
|
||||
{
|
||||
p = item.GetWorldLocation();
|
||||
}
|
||||
|
||||
var targets = new List<Mobile>();
|
||||
|
||||
var map = Caster.Map;
|
||||
|
||||
var pvp = false;
|
||||
|
||||
if (map != null)
|
||||
{
|
||||
var loc = new Point3D(p);
|
||||
using var pool = PooledRefQueue<Mobile>.Create();
|
||||
var pvp = false;
|
||||
|
||||
PlayEffect(loc, Caster.Map);
|
||||
|
||||
foreach (var m in map.GetMobilesInRange(loc, 2))
|
||||
{
|
||||
if (m == Caster)
|
||||
if (m == Caster || !SpellHelper.ValidIndirectTarget(Caster, m) || !Caster.CanBeHarmful(m, false)
|
||||
|| !Caster.CanSee(m) || !Caster.InLOS(m))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
if (SpellHelper.ValidIndirectTarget(Caster, m) && Caster.CanBeHarmful(m, false) && Caster.CanSee(m))
|
||||
pool.Enqueue(m);
|
||||
|
||||
if (m.Player)
|
||||
{
|
||||
if (!Caster.InLOS(m))
|
||||
{
|
||||
continue;
|
||||
}
|
||||
|
||||
targets.Add(m);
|
||||
|
||||
if (m.Player)
|
||||
{
|
||||
pvp = true;
|
||||
}
|
||||
pvp = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
double damage = GetNewAosDamage(51, 1, 5, pvp);
|
||||
double damage = GetNewAosDamage(51, 1, 5, pvp);
|
||||
|
||||
foreach (var m in targets)
|
||||
{
|
||||
Caster.DoHarmful(m);
|
||||
SpellHelper.Damage(this, m, damage, 0, 0, 100, 0, 0);
|
||||
while (pool.Count > 0)
|
||||
{
|
||||
var m = pool.Dequeue();
|
||||
Caster.DoHarmful(m);
|
||||
SpellHelper.Damage(this, m, damage, 0, 0, 100, 0, 0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -104,7 +91,9 @@ namespace Server.Spells.Mysticism
|
|||
|
||||
private static void PlaySingleEffect(Point3D p, Map map, int a, int b, int c, int d)
|
||||
{
|
||||
int x = p.X, y = p.Y, z = p.Z + 18;
|
||||
var x = p.X;
|
||||
var y = p.Y;
|
||||
var z = p.Z + 18;
|
||||
|
||||
SendEffectPacket(p, map, new Point3D(x + a, y + c, z), new Point3D(x + a, y + c, z));
|
||||
SendEffectPacket(p, map, new Point3D(x + b, y + c, z), new Point3D(x + b, y + c, z));
|
||||
|
|
|
|||
|
|
@ -97,8 +97,6 @@ namespace Server.Spells.Mysticism
|
|||
|
||||
public static double GetBaseSkill(Mobile m) => m.Skills.Mysticism.Value;
|
||||
|
||||
public static double GetBoostSkill(Mobile m) => Math.Max(m.Skills.Imbuing.Value, m.Skills.Focus.Value);
|
||||
|
||||
public virtual bool CheckResisted(Mobile target)
|
||||
{
|
||||
var n = GetResistPercent(target);
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
using System.Collections.Generic;
|
||||
using Server.Collections;
|
||||
|
||||
namespace Server.Spells.Mysticism
|
||||
{
|
||||
|
|
@ -23,7 +23,9 @@ namespace Server.Spells.Mysticism
|
|||
|
||||
public void Target(IPoint3D p)
|
||||
{
|
||||
if (SpellHelper.CheckTown(p, Caster) && CheckSequence())
|
||||
var loc = (p as Item)?.GetWorldLocation() ?? new Point3D(p);
|
||||
|
||||
if (SpellHelper.CheckTown(loc, Caster) && CheckSequence())
|
||||
{
|
||||
/* Summons a gale of lethal winds that strikes all Targets within a radius around
|
||||
* the Target's Location, dealing chaos damage. In addition to inflicting damage,
|
||||
|
|
@ -35,20 +37,12 @@ namespace Server.Spells.Mysticism
|
|||
|
||||
SpellHelper.Turn(Caster, p);
|
||||
|
||||
if (p is Item item)
|
||||
{
|
||||
p = item.GetWorldLocation();
|
||||
}
|
||||
|
||||
var targets = new List<Mobile>();
|
||||
|
||||
var map = Caster.Map;
|
||||
|
||||
var pvp = false;
|
||||
|
||||
if (map != null)
|
||||
{
|
||||
var loc = new Point3D(p);
|
||||
using var pool = PooledRefQueue<Mobile>.Create();
|
||||
var pvp = false;
|
||||
|
||||
PlayEffect(loc, Caster.Map);
|
||||
|
||||
|
|
@ -66,7 +60,7 @@ namespace Server.Spells.Mysticism
|
|||
continue;
|
||||
}
|
||||
|
||||
targets.Add(m);
|
||||
pool.Enqueue(m);
|
||||
|
||||
if (m.Player)
|
||||
{
|
||||
|
|
@ -74,20 +68,21 @@ namespace Server.Spells.Mysticism
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var damage = GetNewAosDamage(51, 1, 5, pvp);
|
||||
var reduction = (GetBaseSkill(Caster) + GetBoostSkill(Caster)) / 1200.0;
|
||||
var damage = GetNewAosDamage(51, 1, 5, pvp);
|
||||
var reduction = (GetBaseSkill(Caster) + GetDamageSkill(Caster)) / 1200.0;
|
||||
|
||||
foreach (var m in targets)
|
||||
{
|
||||
Caster.DoHarmful(m);
|
||||
SpellHelper.Damage(this, m, damage, 0, 0, 0, 0, 0, 100);
|
||||
while (pool.Count > 0)
|
||||
{
|
||||
var m = pool.Dequeue();
|
||||
Caster.DoHarmful(m);
|
||||
SpellHelper.Damage(this, m, damage, 0, 0, 0, 0, 0, 100);
|
||||
|
||||
var resistedReduction = reduction - m.Skills.MagicResist.Value / 800.0;
|
||||
var resistedReduction = reduction - m.Skills.MagicResist.Value / 800.0;
|
||||
|
||||
m.Stam -= (int)(m.StamMax * resistedReduction);
|
||||
m.Mana -= (int)(m.ManaMax * resistedReduction);
|
||||
m.Stam -= (int)(m.StamMax * resistedReduction);
|
||||
m.Mana -= (int)(m.ManaMax * resistedReduction);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -97,7 +97,7 @@ namespace Server.Spells.Mysticism
|
|||
Caster.BodyMod = 0x2C1;
|
||||
Caster.HueMod = 0;
|
||||
|
||||
var offset = (int)((GetBaseSkill(Caster) + GetBoostSkill(Caster)) / 24.0);
|
||||
var offset = (int)((GetBaseSkill(Caster) + GetDamageSkill(Caster)) / 24.0);
|
||||
|
||||
ResistanceMod[] mods =
|
||||
{
|
||||
|
|
@ -134,9 +134,9 @@ namespace Server.Spells.Mysticism
|
|||
FinishSequence();
|
||||
}
|
||||
|
||||
public static int GetDIBonus(Mobile m) => (int)((GetBaseSkill(m) + GetBoostSkill(m)) / 12.0);
|
||||
public static int GetDIBonus(Mobile m) => (int)((GetBaseSkill(m) + GetDamageSkill(m)) / 12.0);
|
||||
|
||||
public static int GetResistCapBonus(Mobile m) => (int)((GetBaseSkill(m) + GetBoostSkill(m)) / 48.0);
|
||||
public static int GetResistCapBonus(Mobile m) => (int)((GetBaseSkill(m) + GetDamageSkill(m)) / 48.0);
|
||||
|
||||
public static void RemoveEffects(Mobile m)
|
||||
{
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue