private void Bash()
        {
            if (!Monster.CanCast)
            {
                return;
            }

            var obj = Monster.GetInfront(1);

            if (obj == null)
            {
                return;
            }


            if (Monster.Target != null)
            {
                if (!Monster.Facing(Target.X, Target.Y, out int direction))
                {
                    Monster.Direction = (byte)direction;
                    Monster.Turn();
                    return;
                }
            }


            if (Target == null || Target.CurrentHp == 0)
            {
                ClearTarget();
                return;
            }

            if (Monster != null && Monster.Target != null && SkillScripts.Count > 0)
            {
                var sobj = SkillScripts.FirstOrDefault(i => i.Skill.Ready);

                if (sobj != null)
                {
                    var skill = sobj.Skill;

                    sobj?.OnUse(Monster);
                    {
                        skill.InUse = true;

                        if (skill.Template.Cooldown > 0)
                        {
                            skill.NextAvailableUse = DateTime.UtcNow.AddSeconds(skill.Template.Cooldown);
                        }
                        else
                        {
                            skill.NextAvailableUse = DateTime.UtcNow.AddMilliseconds(ServerContext.Config.GlobalBaseSkillDelay);
                        }
                    }

                    skill.InUse = false;
                }
            }

            if (Monster != null && DefaultSkill != null)
            {
                DefaultSkill.OnUse(Monster);
            }
        }
Esempio n. 2
0
        public void Update(TimeSpan update)
        {
            if (Template == null)
            {
                return;
            }

            if (IsConfused || IsFrozen || IsParalyzed || IsSleeping)
            {
                return;
            }

            if (Target != null && !WithinRangeOf(Target))
            {
                Target = null;
            }

            var nearby = GetObjects <Aisling>(Map, i => i.WithinRangeOf(this));

            if (!nearby.Any())
            {
                return;
            }

            if (Template.ChatTimer != null)
            {
                Template.ChatTimer.Update(update);

                if (Template.ChatTimer.Elapsed && nearby.Any())
                {
                    foreach (var obj in nearby)
                    {
                        if (Template.Speech.Count > 0)
                        {
                            var msg = Template.Speech[ChatIdx++ % Template.Speech.Count];

                            obj.Show(Scope.Self,
                                     new ServerFormat0D
                            {
                                Serial = Serial,
                                Text   = msg,
                                Type   = 0
                            });
                        }
                    }

                    Template.ChatTimer.Reset();
                }
            }

            if (Template.EnableTurning)
            {
                if (Template.TurnTimer != null)
                {
                    Template.TurnTimer.Update(update);
                    if (Template.TurnTimer.Elapsed)
                    {
                        lock (Generator.Random)
                        {
                            Direction = (byte)Generator.Random.Next(0, 4);
                        }

                        Turn();

                        Template.TurnTimer.Reset();
                    }
                }
            }

            if (Template.EnableCasting)
            {
                Template.SpellTimer.Update(update);

                if (Template.SpellTimer.Elapsed)
                {
                    if (Target == null || Target.CurrentHp == 0 || !Target.WithinRangeOf(this))
                    {
                        var targets = GetObjects <Monster>(Map, i => i.WithinRangeOf(this))
                                      .OrderBy(i => i.Position.DistanceFrom(Position));

                        foreach (var t in targets)
                        {
                            t.Target = this;
                        }

                        var target = Target ?? targets.FirstOrDefault();

                        if (target?.CurrentHp == 0)
                        {
                            target = null;
                        }

                        if (!CanCast)
                        {
                            return;
                        }

                        Target = target;
                    }

                    if (Target != null && Target != null && SpellScripts.Count > 0)
                    {
                        var idx = 0;
                        lock (Generator.Random)
                        {
                            idx = Generator.Random.Next(SpellScripts.Count);
                        }

                        SpellScripts[idx].OnUse(this, Target);
                    }

                    Template.SpellTimer.Reset();
                }
            }

            if (Template.AttackTimer != null && Template.EnableWalking)
            {
                Template.AttackTimer.Update(update);
                if (Template.AttackTimer.Elapsed)
                {
                    var targets = GetObjects <Monster>(Map, i => i.WithinRangeOf(this))
                                  .OrderBy(i => i.Position.DistanceFrom(Position));

                    foreach (var t in targets)
                    {
                        t.Target = this;
                    }

                    var target = Target ?? targets.FirstOrDefault();

                    if (target?.CurrentHp == 0)
                    {
                        target = null;
                    }

                    if (target != null)
                    {
                        foreach (var script in Scripts.Values)
                        {
                            script?.TargetAcquired(target);
                        }

                        if (!Position.IsNextTo(target.Position))
                        {
                            WalkTo(target.XPos, target.YPos);
                        }
                        else
                        {
                            if (!Facing(target, out var direction))
                            {
                                Direction = (byte)direction;
                                Turn();
                            }
                            else
                            {
                                target.Target = this;
                                DefaultSkill?.OnUse(this);

                                if (SkillScripts.Count > 0 && target.Target != null)
                                {
                                    var obj = SkillScripts.FirstOrDefault(i => i.Skill.Ready);

                                    if (obj != null)
                                    {
                                        var skill = obj.Skill;

                                        obj?.OnUse(this);
                                        {
                                            skill.InUse = true;

                                            if (skill.Template.Cooldown > 0)
                                            {
                                                skill.NextAvailableUse =
                                                    DateTime.UtcNow.AddSeconds(skill.Template.Cooldown);
                                            }
                                            else
                                            {
                                                skill.NextAvailableUse =
                                                    DateTime.UtcNow.AddMilliseconds(ServerContext.Config
                                                                                    .GlobalBaseSkillDelay);
                                            }
                                        }

                                        skill.InUse = false;
                                    }
                                }
                            }
                        }
                    }
                    else
                    {
                        if (Template.PathQualifer.HasFlag(PathQualifer.Patrol))
                        {
                            if (Template.Waypoints == null)
                            {
                                Wander();
                            }
                            else
                            {
                                if (Template.Waypoints?.Count > 0)
                                {
                                    Patrol();
                                }
                                else
                                {
                                    Wander();
                                }
                            }
                        }
                        else
                        {
                            Wander();
                        }
                    }

                    Template.AttackTimer.Reset();
                }
            }
        }