public void UpdateObjectives(float deltaTime)
        {
            UpdateOrderObjective(ForcedOrder);

            if (CurrentOrders.Any())
            {
                foreach (var order in CurrentOrders)
                {
                    var orderObjective = order.Objective;
                    UpdateOrderObjective(orderObjective);
                }
            }

            void UpdateOrderObjective(AIObjective orderObjective)
            {
                if (orderObjective == null)
                {
                    return;
                }
#if DEBUG
                // Note: don't automatically remove orders here. Removing orders needs to be done via dismissing.
                if (!orderObjective.CanBeCompleted)
                {
                    DebugConsole.NewMessage($"{character.Name}: ORDER {orderObjective.DebugTag}, CANNOT BE COMPLETED.", Color.Red);
                }
#endif
                orderObjective.Update(deltaTime);
            }

            if (WaitTimer > 0)
            {
                WaitTimer -= deltaTime;
                return;
            }
            for (int i = 0; i < Objectives.Count; i++)
            {
                var objective = Objectives[i];
                if (objective.IsCompleted)
                {
#if DEBUG
                    DebugConsole.NewMessage($"{character.Name}: Removing objective {objective.DebugTag}, because it is completed.", Color.LightBlue);
#endif
                    Objectives.Remove(objective);
                }
                else if (!objective.CanBeCompleted)
                {
#if DEBUG
                    DebugConsole.NewMessage($"{character.Name}: Removing objective {objective.DebugTag}, because it cannot be completed.", Color.Red);
#endif
                    Objectives.Remove(objective);
                    FailedAutonomousObjectives = true;
                }
                else
                {
                    objective.Update(deltaTime);
                }
            }
            GetCurrentObjective();
        }
示例#2
0
 public bool HasOrder <T>() where T : AIObjective
 {
     return(ForcedOrder is T || CurrentOrders.Any(o => o.Objective is T));
 }
示例#3
0
 public bool HasOrders()
 {
     return(ForcedOrder != null || CurrentOrders.Any());
 }
示例#4
0
 public bool IsOrder(AIObjective objective)
 {
     return(objective == ForcedOrder || CurrentOrders.Any(o => o.Objective == objective));
 }
示例#5
0
        public void SetOrder(Order order, string option, int priority, Character orderGiver, bool speak)
        {
            if (character.IsDead)
            {
#if DEBUG
                DebugConsole.ThrowError("Attempted to set an order for a dead character");
#else
                return;
#endif
            }
            ClearIgnored();

            if (order == null || order.Identifier == "dismissed")
            {
                if (!string.IsNullOrEmpty(option))
                {
                    if (CurrentOrders.Any(o => o.MatchesDismissedOrder(option)))
                    {
                        var dismissedOrderInfo = CurrentOrders.First(o => o.MatchesDismissedOrder(option));
                        CurrentOrders.Remove(dismissedOrderInfo);
                    }
                }
                else
                {
                    CurrentOrders.Clear();
                }
            }

            // Make sure the order priorities reflect those set by the player
            for (int i = CurrentOrders.Count - 1; i >= 0; i--)
            {
                var currentOrder = CurrentOrders[i];
                if (currentOrder.Objective == null || currentOrder.MatchesOrder(order, option))
                {
                    CurrentOrders.RemoveAt(i);
                    continue;
                }
                var currentOrderInfo = character.GetCurrentOrder(currentOrder.Order, currentOrder.OrderOption);
                if (currentOrderInfo.HasValue)
                {
                    int currentPriority = currentOrderInfo.Value.ManualPriority;
                    if (currentOrder.ManualPriority != currentPriority)
                    {
                        CurrentOrders[i] = new OrderInfo(currentOrder, currentPriority);
                    }
                }
                else
                {
                    CurrentOrders.RemoveAt(i);
                }
            }

            var newCurrentOrder = CreateObjective(order, option, orderGiver, isAutonomous: false);
            if (newCurrentOrder != null)
            {
                CurrentOrders.Add(new OrderInfo(order, option, priority, newCurrentOrder));
            }
            if (!HasOrders())
            {
                // Recreate objectives, because some of them may be removed, if impossible to complete (e.g. due to path finding)
                CreateAutonomousObjectives();
            }
            else
            {
                // This should be redundant, because all the objectives are reset when they are selected as active.
                newCurrentOrder?.Reset();

                if (speak && character.IsOnPlayerTeam)
                {
                    character.Speak(TextManager.Get("DialogAffirmative"), null, 1.0f);
                    //if (speakRoutine != null)
                    //{
                    //    CoroutineManager.StopCoroutines(speakRoutine);
                    //}
                    //speakRoutine = CoroutineManager.InvokeAfter(() =>
                    //{
                    //    if (GameMain.GameSession == null || Level.Loaded == null) { return; }
                    //    if (newCurrentOrder != null && character.SpeechImpediment < 100.0f)
                    //    {
                    //        if (newCurrentOrder is AIObjectiveRepairItems repairItems && repairItems.Targets.None())
                    //        {
                    //            character.Speak(TextManager.Get("DialogNoRepairTargets"), null, 3.0f, "norepairtargets");
                    //        }
                    //        else if (newCurrentOrder is AIObjectiveChargeBatteries chargeBatteries && chargeBatteries.Targets.None())
                    //        {
                    //            character.Speak(TextManager.Get("DialogNoBatteries"), null, 3.0f, "nobatteries");
                    //        }
                    //        else if (newCurrentOrder is AIObjectiveExtinguishFires extinguishFires && extinguishFires.Targets.None())
                    //        {
                    //            character.Speak(TextManager.Get("DialogNoFire"), null, 3.0f, "nofire");
                    //        }
                    //        else if (newCurrentOrder is AIObjectiveFixLeaks fixLeaks && fixLeaks.Targets.None())
                    //        {
                    //            character.Speak(TextManager.Get("DialogNoLeaks"), null, 3.0f, "noleaks");
                    //        }
                    //        else if (newCurrentOrder is AIObjectiveFightIntruders fightIntruders && fightIntruders.Targets.None())
                    //        {
                    //            character.Speak(TextManager.Get("DialogNoEnemies"), null, 3.0f, "noenemies");
                    //        }
                    //        else if (newCurrentOrder is AIObjectiveRescueAll rescueAll && rescueAll.Targets.None())
                    //        {
                    //            character.Speak(TextManager.Get("DialogNoRescueTargets"), null, 3.0f, "norescuetargets");
                    //        }
                    //        else if (newCurrentOrder is AIObjectivePumpWater pumpWater && pumpWater.Targets.None())
                    //        {
                    //            character.Speak(TextManager.Get("DialogNoPumps"), null, 3.0f, "nopumps");
                    //        }
                    //    }
                    //}, 3);
                }
            }
        }