using System; using System.Collections.Generic; using RobotAndDonkey.Game.Execution.Results; using RobotAndDonkey.Game.GameState; using RobotAndDonkey.Game.Intents; using RobotAndDonkey.Game.Modifiers; using RobotAndDonkey.Game.Pois; namespace RobotAndDonkey.Game.Execution.Commands; public abstract record Command(Guid RequestId, params Type[] RequestTypes) { protected abstract void CreateIntents(CoreLoop coreLoop, List intents); public List Preview(CoreLoop coreLoop) { var mockCoreLoop = new CoreLoop(coreLoop) { IsPreview = true }; return Execute(mockCoreLoop, false, false); } public List Execute(CoreLoop coreLoop, bool force, bool verbose) { var results = new List(); var intents = new List(); CreateIntents(coreLoop, intents); var modifiers = GetModifierStack(coreLoop); modifiers.Execute(RequestId, coreLoop, intents, results, force, verbose); return results; } private static ModifierStack GetModifierStack(CoreLoop coreLoop) { var modifiers = new ModifierStack(); modifiers.Push(coreLoop.Robot); foreach (var cell in coreLoop.Board.Cells) { if (cell.Poi is Avatar) { modifiers.Push(cell); } } return modifiers; } public bool IsValid(CoreLoop coreLoop, out EInvalidReason reason) { var results = Preview(coreLoop); if (results.Count == 0) { reason = EInvalidReason.Invariant; return false; } if (results is [InvalidInstructionResult]) { reason = EInvalidReason.Invalid; return false; } reason = (EInvalidReason)(-1); return true; } public int EstimateEnergyCost(CoreLoop coreLoop) { var results = Preview(coreLoop); if (results.Count == 0) return 0; var newEnergy = 0; foreach (var result in results) { if (result is CurrencyResult currencyResult) newEnergy = currencyResult.NewCurrency.Energy; } return coreLoop.Currency.Energy - newEnergy; } }