ported from perforce
This commit is contained in:
@@ -0,0 +1,20 @@
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record AcceptCardCommand(Guid RequestId) : Command(RequestId, typeof(DrawGlitchRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
intents.Add(new AcceptGlitch(coreLoop.GlitchDeck[coreLoop.NextGlitch]));
|
||||
intents.Add(new NextGlitch());
|
||||
intents.Add(new NextPhase(ERunPhase.Improve));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Accept card command";
|
||||
}
|
||||
}
|
||||
31
RobotAndDonkey.Game/Execution/Commands/BuyCardsCommand.cs
Normal file
31
RobotAndDonkey.Game/Execution/Commands/BuyCardsCommand.cs
Normal file
@@ -0,0 +1,31 @@
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record BuyCardsCommand(Guid RequestId, int[] Cards) : Command(RequestId, typeof(ImproveRequest), typeof(GambleRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
var gamble = coreLoop.RunPhase == ERunPhase.Gamble;
|
||||
foreach (var index in Cards)
|
||||
{
|
||||
if (index < 0)
|
||||
continue;
|
||||
|
||||
if (gamble && index < coreLoop.BoosterPack.Count)
|
||||
intents.Add(new BuyPatch(coreLoop.BoosterPack[index], true));
|
||||
else if (!gamble && index < coreLoop.Shop.Count)
|
||||
intents.Add(new BuyPatch(coreLoop.Shop[index], false));
|
||||
}
|
||||
|
||||
if (coreLoop.RunPhase == ERunPhase.Gamble)
|
||||
intents.Add(new NextPhase(ERunPhase.Improve));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Buy cards command {string.Join(", ", Cards.Select(c => c.ToString()))}";
|
||||
}
|
||||
}
|
||||
82
RobotAndDonkey.Game/Execution/Commands/Command.cs
Normal file
82
RobotAndDonkey.Game/Execution/Commands/Command.cs
Normal file
@@ -0,0 +1,82 @@
|
||||
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<Intent> intents);
|
||||
|
||||
public List<Result> Preview(CoreLoop coreLoop)
|
||||
{
|
||||
var mockCoreLoop = new CoreLoop(coreLoop) { IsPreview = true };
|
||||
return Execute(mockCoreLoop, false, false);
|
||||
}
|
||||
|
||||
public List<Result> Execute(CoreLoop coreLoop, bool force, bool verbose)
|
||||
{
|
||||
var results = new List<Result>();
|
||||
var intents = new List<Intent>();
|
||||
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;
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using RobotAndDonkey.Game.Data;
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record DeferCardCommand(Guid RequestId) : Command(RequestId, typeof(DrawGlitchRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
intents.Add(new DeferGlitch(Balancing.Instance.GetDeferGlitchEnergyCost(coreLoop.DeferGlitchCount)));
|
||||
intents.Add(new NextGlitch());
|
||||
intents.Add(new NextPhase(ERunPhase.Improve));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Defer card command";
|
||||
}
|
||||
}
|
||||
22
RobotAndDonkey.Game/Execution/Commands/DestroyCardCommand.cs
Normal file
22
RobotAndDonkey.Game/Execution/Commands/DestroyCardCommand.cs
Normal file
@@ -0,0 +1,22 @@
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record DestroyCardCommand(Guid RequestId, int HandIndex) : Command(RequestId, typeof(BufferOverflowRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
var handCards = coreLoop.GetHandCards();
|
||||
if (HandIndex < 0 || HandIndex >= handCards.Count)
|
||||
return;
|
||||
|
||||
intents.Add(new DestroyCard(handCards[HandIndex]));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Destroy card command {HandIndex}";
|
||||
}
|
||||
}
|
||||
22
RobotAndDonkey.Game/Execution/Commands/DiscardCommand.cs
Normal file
22
RobotAndDonkey.Game/Execution/Commands/DiscardCommand.cs
Normal file
@@ -0,0 +1,22 @@
|
||||
using System;
|
||||
using System.Linq;
|
||||
using RobotAndDonkey.Game.Data;
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record DiscardCommand(Guid RequestId, Guid[] CardIds) : Command(RequestId, typeof(ExecuteProgramRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
var cost = CardIds.Length * Balancing.Instance.DiscardEnergyCost;
|
||||
intents.Add(new Discard(CardIds, cost));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Discard cards command {string.Join(", ", CardIds.Select(id => id.ToString()))}";
|
||||
}
|
||||
}
|
||||
20
RobotAndDonkey.Game/Execution/Commands/MoveCardsCommand.cs
Normal file
20
RobotAndDonkey.Game/Execution/Commands/MoveCardsCommand.cs
Normal file
@@ -0,0 +1,20 @@
|
||||
using System;
|
||||
using System.Linq;
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record MoveCardsCommand(Guid RequestId, Guid[] OrderedCards, Guid[] TapeCardIds) : Command(RequestId, typeof(ExecuteProgramRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
intents.Add(new MoveCards(OrderedCards, TapeCardIds));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Move cards command: order={string.Join(", ", OrderedCards.Select(c => c.ToString()))}; tape={string.Join(", ", TapeCardIds.Select(c => c.ToString()))}";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record NextAssignmentCommand(Guid RequestId) : Command(RequestId, typeof(ScoringRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
coreLoop.ResetShop();
|
||||
intents.Add(new NextPhase(ERunPhase.DrawGlitch));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Next assignment command";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,19 @@
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record PreviewProgramCommand(Guid RequestId) : Command(RequestId, typeof(ImproveRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
intents.Add(new NextPhase(ERunPhase.ExecuteProgram));
|
||||
intents.Add(new EnterPreview());
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Preview program command";
|
||||
}
|
||||
}
|
||||
21
RobotAndDonkey.Game/Execution/Commands/RerollCommand.cs
Normal file
21
RobotAndDonkey.Game/Execution/Commands/RerollCommand.cs
Normal file
@@ -0,0 +1,21 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using RobotAndDonkey.Game.Data;
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record RerollCommand(Guid RequestId) : Command(RequestId, typeof(ImproveRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
intents.Add(new Reroll(Balancing.Instance.GetRerollEnergyCost(coreLoop.RerollCount)));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Reroll command";
|
||||
}
|
||||
}
|
||||
18
RobotAndDonkey.Game/Execution/Commands/RunProgramCommand.cs
Normal file
18
RobotAndDonkey.Game/Execution/Commands/RunProgramCommand.cs
Normal file
@@ -0,0 +1,18 @@
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record RunProgramCommand(Guid RequestId) : Command(RequestId, typeof(ExecuteProgramRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
intents.Add(new RunProgram());
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Run program command";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using RobotAndDonkey.Game.Data;
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record StartBufferOverflowCommand(Guid RequestId) : Command(RequestId, typeof(ImproveRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
intents.Add(new EnterBufferOverflow(Balancing.Instance.BufferOverflowEnergyCost));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Start buffer overflow command";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,21 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using RobotAndDonkey.Game.Data;
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record StartGamblingCommand(Guid RequestId) : Command(RequestId, typeof(ImproveRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
intents.Add(new EnterGamble(Balancing.Instance.GambleEnergyCost));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Start gambling command";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record StopBufferOverflowCommand(Guid RequestId) : Command(RequestId, typeof(BufferOverflowRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
var handCards = coreLoop.GetHandCards();
|
||||
coreLoop.PatchDeck.AddRange(handCards);
|
||||
foreach (var handCard in handCards)
|
||||
{
|
||||
coreLoop.RemoveProgramCard(handCard);
|
||||
}
|
||||
coreLoop.ClearTapeSelection();
|
||||
intents.Add(new NextPhase(ERunPhase.Improve));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Stop buffer overflow command";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,20 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
public sealed record StopGamblingCommand(Guid RequestId) : Command(RequestId, typeof(GambleRequest))
|
||||
{
|
||||
protected override void CreateIntents(CoreLoop coreLoop, List<Intent> intents)
|
||||
{
|
||||
intents.Add(new NextPhase(ERunPhase.Improve));
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Stop gambling command";
|
||||
}
|
||||
}
|
||||
13
RobotAndDonkey.Game/Execution/ERunPhase.cs
Normal file
13
RobotAndDonkey.Game/Execution/ERunPhase.cs
Normal file
@@ -0,0 +1,13 @@
|
||||
namespace RobotAndDonkey.Game.Execution;
|
||||
|
||||
public enum ERunPhase
|
||||
{
|
||||
Init,
|
||||
ExecuteProgram,
|
||||
Scoring,
|
||||
DrawGlitch,
|
||||
Improve,
|
||||
Gamble,
|
||||
BufferOverflow,
|
||||
_Count
|
||||
}
|
||||
139
RobotAndDonkey.Game/Execution/GameRuntime.cs
Normal file
139
RobotAndDonkey.Game/Execution/GameRuntime.cs
Normal file
@@ -0,0 +1,139 @@
|
||||
using RobotAndDonkey.Game.Execution.Commands;
|
||||
using RobotAndDonkey.Game.Execution.Requests;
|
||||
using RobotAndDonkey.Game.Execution.Results;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using RobotAndDonkey.Game.Intents;
|
||||
using System;
|
||||
using System.Collections.Immutable;
|
||||
using System.Threading;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution;
|
||||
|
||||
public sealed record GameEvent(long Sequence, DateTimeOffset Time, object Payload);
|
||||
|
||||
public sealed record NextStepIssued(Request Step);
|
||||
|
||||
public sealed record StepApplied(ImmutableArray<Result> Results);
|
||||
|
||||
public sealed record StepRejected(Guid RequestId, string Reason);
|
||||
|
||||
public sealed record StateChanged;
|
||||
|
||||
public sealed record GameOver(string Reason);
|
||||
|
||||
public sealed class GameRuntime
|
||||
{
|
||||
public event EventHandler<GameEvent>? Published;
|
||||
|
||||
public void Start(CoreLoop coreLoop)
|
||||
{
|
||||
lock (m_Gate)
|
||||
{
|
||||
m_CoreLoop = coreLoop;
|
||||
Publish(new StateChanged());
|
||||
IssueNextStepLocked();
|
||||
}
|
||||
}
|
||||
|
||||
public void Submit(Command command, CancellationToken ct = default)
|
||||
{
|
||||
lock (m_Gate)
|
||||
{
|
||||
if (m_CoreLoop == null)
|
||||
{
|
||||
Publish(new StepRejected(command.RequestId, "No core loop started."));
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_ExpectedRequest is null)
|
||||
{
|
||||
Publish(new StepRejected(command.RequestId, "No step expected (game over or not started)."));
|
||||
return;
|
||||
}
|
||||
|
||||
if (m_ExpectedRequest.RequestId != command.RequestId)
|
||||
{
|
||||
Publish(new StepRejected(command.RequestId, "Command does not match the expected step."));
|
||||
return;
|
||||
}
|
||||
|
||||
if (!m_ExpectedRequest.IsCommandCompatible(command))
|
||||
{
|
||||
Publish(new StepRejected(command.RequestId, "Command not compatible with the current step."));
|
||||
return;
|
||||
}
|
||||
|
||||
var results = command.Execute(m_CoreLoop, false, false);
|
||||
|
||||
Publish(new StepApplied([..results]));
|
||||
Publish(new StateChanged());
|
||||
|
||||
IssueNextStepLocked();
|
||||
}
|
||||
}
|
||||
|
||||
private void IssueNextStepLocked()
|
||||
{
|
||||
m_ExpectedRequest = NextRequest();
|
||||
|
||||
if (m_ExpectedRequest is null)
|
||||
Publish(new GameOver("No more steps."));
|
||||
else
|
||||
Publish(new NextStepIssued(m_ExpectedRequest));
|
||||
}
|
||||
|
||||
private Request? NextRequest()
|
||||
{
|
||||
var coreLoop = m_CoreLoop!;
|
||||
switch (coreLoop.RunPhase)
|
||||
{
|
||||
case ERunPhase.Init:
|
||||
{
|
||||
const ERunPhase firstPhase = ERunPhase.ExecuteProgram;
|
||||
coreLoop.ResetShop();
|
||||
new EnterPreview().Run(Guid.Empty, coreLoop, [], []);
|
||||
// DEBUG
|
||||
// const ERunPhase firstPhase = ERunPhase.DrawGlitch;
|
||||
coreLoop.RunPhase = firstPhase;
|
||||
goto case firstPhase;
|
||||
}
|
||||
case ERunPhase.DrawGlitch:
|
||||
{
|
||||
return DrawGlitchRequest.Create(coreLoop);
|
||||
}
|
||||
case ERunPhase.Improve:
|
||||
{
|
||||
return ImproveRequest.Create(coreLoop);
|
||||
}
|
||||
case ERunPhase.Gamble:
|
||||
{
|
||||
return GambleRequest.Create(coreLoop);
|
||||
}
|
||||
case ERunPhase.BufferOverflow:
|
||||
{
|
||||
return BufferOverflowRequest.Create(coreLoop);
|
||||
}
|
||||
case ERunPhase.ExecuteProgram:
|
||||
{
|
||||
return ExecuteProgramRequest.Create(coreLoop);
|
||||
}
|
||||
case ERunPhase.Scoring:
|
||||
{
|
||||
return ScoringRequest.Create(coreLoop);
|
||||
}
|
||||
}
|
||||
|
||||
return null;
|
||||
}
|
||||
|
||||
private void Publish(object payload)
|
||||
{
|
||||
Published?.Invoke(this, new(Interlocked.Increment(ref m_Sequence), DateTimeOffset.UtcNow, payload));
|
||||
}
|
||||
|
||||
private CoreLoop? m_CoreLoop;
|
||||
|
||||
private readonly Lock m_Gate = new();
|
||||
private Request? m_ExpectedRequest;
|
||||
private long m_Sequence;
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Requests;
|
||||
|
||||
public sealed record BufferOverflowRequest(Guid RequestId) : Request(RequestId)
|
||||
{
|
||||
public static BufferOverflowRequest Create(CoreLoop coreLoop)
|
||||
{
|
||||
coreLoop.ShuffleDeck();
|
||||
coreLoop.DrawHand();
|
||||
return new(Guid.NewGuid());
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Buffer overflow request";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
using System;
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Requests;
|
||||
|
||||
public sealed record DrawGlitchRequest(Guid RequestId, Card Card) : Request(RequestId)
|
||||
{
|
||||
public static DrawGlitchRequest Create(CoreLoop coreLoop)
|
||||
{
|
||||
return new(Guid.NewGuid(), coreLoop.GlitchDeck[coreLoop.NextGlitch]);
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Draw glitch request: {Card}";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,18 @@
|
||||
using System;
|
||||
using RobotAndDonkey.Game.Execution.Commands;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Requests;
|
||||
|
||||
public sealed record ExecuteProgramRequest(Guid RequestId) : Request(RequestId)
|
||||
{
|
||||
public static ExecuteProgramRequest Create(CoreLoop coreLoop)
|
||||
{
|
||||
return new(Guid.NewGuid());
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Execute program request";
|
||||
}
|
||||
}
|
||||
20
RobotAndDonkey.Game/Execution/Requests/GambleRequest.cs
Normal file
20
RobotAndDonkey.Game/Execution/Requests/GambleRequest.cs
Normal file
@@ -0,0 +1,20 @@
|
||||
using System;
|
||||
using System.Collections.Immutable;
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
using RobotAndDonkey.Game.Data;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Requests;
|
||||
|
||||
public sealed record GambleRequest(Guid RequestId) : Request(RequestId)
|
||||
{
|
||||
public static GambleRequest Create(CoreLoop coreLoop)
|
||||
{
|
||||
return new(Guid.NewGuid());
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Gamble request";
|
||||
}
|
||||
}
|
||||
18
RobotAndDonkey.Game/Execution/Requests/ImproveRequest.cs
Normal file
18
RobotAndDonkey.Game/Execution/Requests/ImproveRequest.cs
Normal file
@@ -0,0 +1,18 @@
|
||||
using System;
|
||||
using RobotAndDonkey.Game.Execution.Commands;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Requests;
|
||||
|
||||
public sealed record ImproveRequest(Guid RequestId) : Request(RequestId)
|
||||
{
|
||||
public static ImproveRequest Create(CoreLoop coreLoop)
|
||||
{
|
||||
return new(Guid.NewGuid());
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Improve request";
|
||||
}
|
||||
}
|
||||
22
RobotAndDonkey.Game/Execution/Requests/Request.cs
Normal file
22
RobotAndDonkey.Game/Execution/Requests/Request.cs
Normal file
@@ -0,0 +1,22 @@
|
||||
using System;
|
||||
using RobotAndDonkey.Game.Execution.Commands;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Requests;
|
||||
|
||||
public abstract record Request(Guid RequestId)
|
||||
{
|
||||
public bool IsCommandCompatible(Command command)
|
||||
{
|
||||
foreach (var requestType in command.RequestTypes)
|
||||
{
|
||||
if (requestType == GetType())
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
public static readonly EmptyRequest s_Empty = new();
|
||||
}
|
||||
|
||||
public sealed record EmptyRequest() : Request(Guid.Empty);
|
||||
18
RobotAndDonkey.Game/Execution/Requests/ScoringRequest.cs
Normal file
18
RobotAndDonkey.Game/Execution/Requests/ScoringRequest.cs
Normal file
@@ -0,0 +1,18 @@
|
||||
using System;
|
||||
using RobotAndDonkey.Game.Execution.Commands;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Requests;
|
||||
|
||||
public sealed record ScoringRequest(Guid RequestId) : Request(RequestId)
|
||||
{
|
||||
public static ScoringRequest Create(CoreLoop coreLoop)
|
||||
{
|
||||
return new(Guid.NewGuid());
|
||||
}
|
||||
|
||||
public override string ToString()
|
||||
{
|
||||
return "Scoring request";
|
||||
}
|
||||
}
|
||||
11
RobotAndDonkey.Game/Execution/Results/CellTypeResult.cs
Normal file
11
RobotAndDonkey.Game/Execution/Results/CellTypeResult.cs
Normal file
@@ -0,0 +1,11 @@
|
||||
using RobotAndDonkey.Game.Utils;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record CellTypeResult(Guid RequestId, Board.Board Board, Hex Hex) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Cell type result: {Hex}";
|
||||
}
|
||||
}
|
||||
13
RobotAndDonkey.Game/Execution/Results/CurrencyResult.cs
Normal file
13
RobotAndDonkey.Game/Execution/Results/CurrencyResult.cs
Normal file
@@ -0,0 +1,13 @@
|
||||
using RobotAndDonkey.Game.Board;
|
||||
using RobotAndDonkey.Game.GameState;
|
||||
using System;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record CurrencyResult(Guid RequestId, Currency NewCurrency) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Currency result: {NewCurrency}";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
using System;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record DeferGlitchCountResult(Guid RequestId, int NewDeferGlitchCount) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Defer glitch count result: {NewDeferGlitchCount}";
|
||||
}
|
||||
}
|
||||
13
RobotAndDonkey.Game/Execution/Results/DiscardResult.cs
Normal file
13
RobotAndDonkey.Game/Execution/Results/DiscardResult.cs
Normal file
@@ -0,0 +1,13 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record DiscardResult(Guid RequestId, IReadOnlyList<Card> Discard) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Discard result: {string.Join(", ", Discard.Select(c => c.ToString()))}";
|
||||
}
|
||||
}
|
||||
13
RobotAndDonkey.Game/Execution/Results/HandResult.cs
Normal file
13
RobotAndDonkey.Game/Execution/Results/HandResult.cs
Normal file
@@ -0,0 +1,13 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record HandResult(Guid RequestId, IReadOnlyList<Card> Hand) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Hand result: {string.Join(", ", Hand.Select(c => c.ToString()))}";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,27 @@
|
||||
using System;
|
||||
using RobotAndDonkey.Game.Board;
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public enum EInvalidReason
|
||||
{
|
||||
NotFound,
|
||||
Invariant,
|
||||
Blocked,
|
||||
OutOfBounds,
|
||||
NoEnergy,
|
||||
NoTarget,
|
||||
NoAmount,
|
||||
AlreadyExecuted,
|
||||
Invalid,
|
||||
NoSpace
|
||||
}
|
||||
|
||||
public record InvalidInstructionResult(Guid RequestId, EInvalidReason Reason, Card? Card, Cell? Cell) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Invalid instruction result: {Reason}, {Card}, {Cell}";
|
||||
}
|
||||
}
|
||||
13
RobotAndDonkey.Game/Execution/Results/InventoryResult.cs
Normal file
13
RobotAndDonkey.Game/Execution/Results/InventoryResult.cs
Normal file
@@ -0,0 +1,13 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record DeckResult(Guid RequestId, IReadOnlyList<Card> Deck) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Deck result: {string.Join(", ", Deck.Select(c => c.ToString()))}";
|
||||
}
|
||||
}
|
||||
22
RobotAndDonkey.Game/Execution/Results/ModifyCardResult.cs
Normal file
22
RobotAndDonkey.Game/Execution/Results/ModifyCardResult.cs
Normal file
@@ -0,0 +1,22 @@
|
||||
using System;
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public enum ECardLocation
|
||||
{
|
||||
Tape,
|
||||
Hand,
|
||||
Deck,
|
||||
Discard,
|
||||
Robot,
|
||||
Board
|
||||
}
|
||||
|
||||
public record ModifyCardResult(Guid RequestId, Card Card, EModifierId Modifier, ECardLocation Location) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Modify card result in {Location}: {Card} - {Modifier}";
|
||||
}
|
||||
}
|
||||
11
RobotAndDonkey.Game/Execution/Results/ModifyCellResult.cs
Normal file
11
RobotAndDonkey.Game/Execution/Results/ModifyCellResult.cs
Normal file
@@ -0,0 +1,11 @@
|
||||
using RobotAndDonkey.Game.Utils;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record ModifyCellResult(Guid RequestId, Board.Board Board, EModifierId Modifier, Hex Hex) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Modify Cell result: {Hex} {Modifier}";
|
||||
}
|
||||
}
|
||||
11
RobotAndDonkey.Game/Execution/Results/ModifyRobotResult.cs
Normal file
11
RobotAndDonkey.Game/Execution/Results/ModifyRobotResult.cs
Normal file
@@ -0,0 +1,11 @@
|
||||
using System;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record ModifyRobotResult(Guid RequestId) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return "Modify robot result";
|
||||
}
|
||||
}
|
||||
11
RobotAndDonkey.Game/Execution/Results/NextGlitchResult.cs
Normal file
11
RobotAndDonkey.Game/Execution/Results/NextGlitchResult.cs
Normal file
@@ -0,0 +1,11 @@
|
||||
using System;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record NextGlitchResult(Guid RequestId, int NewNextGlitch) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Next glitch result: {NewNextGlitch}";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
using System;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record NoMoreBufferOverflowResult(Guid RequestId) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"No more buffer overflow result";
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,11 @@
|
||||
using System;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record NoMoreGamblingResult(Guid RequestId) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return "No more gambling result";
|
||||
}
|
||||
}
|
||||
12
RobotAndDonkey.Game/Execution/Results/PoiResult.cs
Normal file
12
RobotAndDonkey.Game/Execution/Results/PoiResult.cs
Normal file
@@ -0,0 +1,12 @@
|
||||
using RobotAndDonkey.Game.Pois;
|
||||
using RobotAndDonkey.Game.Utils;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record PoiResult(Guid RequestId, Board.Board Board, Poi? Poi, Hex Hex) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Poi result: {Hex}";
|
||||
}
|
||||
}
|
||||
11
RobotAndDonkey.Game/Execution/Results/ProgramResult.cs
Normal file
11
RobotAndDonkey.Game/Execution/Results/ProgramResult.cs
Normal file
@@ -0,0 +1,11 @@
|
||||
using System;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record ProgramResult(Guid RequestId, int NewProgram) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Program result: {NewProgram}";
|
||||
}
|
||||
}
|
||||
14
RobotAndDonkey.Game/Execution/Results/ProgramRowResult.cs
Normal file
14
RobotAndDonkey.Game/Execution/Results/ProgramRowResult.cs
Normal file
@@ -0,0 +1,14 @@
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record ProgramRowResult(Guid RequestId, IReadOnlyList<Card> OrderedCards, IReadOnlyCollection<Guid> TapeCardIds) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Program row result: {string.Join(", ", OrderedCards.Select(c => c.ToString()))}; tape={string.Join(", ", TapeCardIds.Select(id => id.ToString()))}";
|
||||
}
|
||||
}
|
||||
5
RobotAndDonkey.Game/Execution/Results/Result.cs
Normal file
5
RobotAndDonkey.Game/Execution/Results/Result.cs
Normal file
@@ -0,0 +1,5 @@
|
||||
using System;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public abstract record Result(Guid RequestId);
|
||||
12
RobotAndDonkey.Game/Execution/Results/RunCardResult.cs
Normal file
12
RobotAndDonkey.Game/Execution/Results/RunCardResult.cs
Normal file
@@ -0,0 +1,12 @@
|
||||
using System;
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record RunCardResult(Guid RequestId, Card? Card) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Run card result: {Card}";
|
||||
}
|
||||
}
|
||||
11
RobotAndDonkey.Game/Execution/Results/RunPhaseResult.cs
Normal file
11
RobotAndDonkey.Game/Execution/Results/RunPhaseResult.cs
Normal file
@@ -0,0 +1,11 @@
|
||||
using System;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record RunPhaseResult(Guid RequestId, ERunPhase NewRunPhase) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Run phase result: {NewRunPhase}";
|
||||
}
|
||||
}
|
||||
11
RobotAndDonkey.Game/Execution/Results/ShopResult.cs
Normal file
11
RobotAndDonkey.Game/Execution/Results/ShopResult.cs
Normal file
@@ -0,0 +1,11 @@
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record ShopResult(Guid RequestId, Card[] Shop) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Shop result: {string.Join(", ", Shop.Select(c => c.ToString()))}";
|
||||
}
|
||||
}
|
||||
11
RobotAndDonkey.Game/Execution/Results/TapeResult.cs
Normal file
11
RobotAndDonkey.Game/Execution/Results/TapeResult.cs
Normal file
@@ -0,0 +1,11 @@
|
||||
using RobotAndDonkey.Game.Cards;
|
||||
|
||||
namespace RobotAndDonkey.Game.Execution.Results;
|
||||
|
||||
public record TapeResult(Guid RequestId, IReadOnlyList<Card> Tape) : Result(RequestId)
|
||||
{
|
||||
public override string ToString()
|
||||
{
|
||||
return $"Tape result: {string.Join(", ", Tape.Select(c => c.ToString()))}";
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user