You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
507 lines
16 KiB
507 lines
16 KiB
using System.Collections.ObjectModel;
|
|
using Moq;
|
|
using Models.Game;
|
|
using Models.Interfaces;
|
|
using System.Reflection;
|
|
using static System.Type;
|
|
|
|
namespace Tests;
|
|
|
|
public class GameTests
|
|
{
|
|
private readonly Mock<IPersistence> _mockPersistence; // Mocking (faking) the persistence layer to allow for testing without a persistent connection
|
|
private readonly Game _game;
|
|
|
|
public GameTests()
|
|
{
|
|
_mockPersistence = new Mock<IPersistence>();
|
|
_game = new Game(_mockPersistence.Object);
|
|
}
|
|
|
|
private void SetDiceValues(Game game, int value1, int value2)
|
|
{
|
|
var dice1Field = typeof(Game).GetProperty("Dice1", BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public);
|
|
var dice2Field = typeof(Game).GetProperty("Dice2", BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public);
|
|
|
|
if (dice1Field != null && dice2Field != null)
|
|
{
|
|
var dice1 = (Dice)dice1Field?.GetValue(game)!;
|
|
var dice2 = (Dice)dice2Field?.GetValue(game)!;
|
|
|
|
var valueField = typeof(Dice).GetField("_value", BindingFlags.Instance | BindingFlags.NonPublic);
|
|
valueField?.SetValue(dice1, value1);
|
|
valueField?.SetValue(dice2, value2);
|
|
}
|
|
}
|
|
|
|
[Fact]
|
|
public void DefaultConstructor_ShouldInitializeLists()
|
|
{
|
|
Assert.NotNull(_game.Players);
|
|
Assert.NotNull(_game.Games);
|
|
Assert.NotNull(_game.Maps);
|
|
Assert.NotNull(_game.BestScores);
|
|
Assert.NotNull(_game.GameRules);
|
|
Assert.False(_game.IsRunning);
|
|
}
|
|
|
|
[Fact]
|
|
public void AddPlayer_ShouldAddPlayerToList()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
|
|
_game.AddPlayer(player);
|
|
|
|
Assert.Contains(player, _game.Players);
|
|
}
|
|
|
|
[Fact]
|
|
public void AddGame_ShouldAddGameToList()
|
|
{
|
|
var game = new Game(_mockPersistence.Object);
|
|
|
|
_game.AddGame(game);
|
|
|
|
Assert.Contains(game, _game.Games);
|
|
}
|
|
|
|
[Fact]
|
|
public void AddMap_ShouldAddMapToList()
|
|
{
|
|
var map = new Map("test_name", "test_background.png");
|
|
|
|
_game.AddMap(map);
|
|
|
|
Assert.Contains(map, _game.Maps);
|
|
}
|
|
|
|
[Fact]
|
|
public void AddBestScore_ShouldAddBestScoreToList()
|
|
{
|
|
var bestScore = new BestScore(3, 125);
|
|
|
|
_game.AddBestScore(bestScore);
|
|
|
|
Assert.Contains(bestScore, _game.BestScores);
|
|
}
|
|
|
|
[Fact]
|
|
public void LoadData_ShouldLoadDataFromPersistence()
|
|
{
|
|
var players = new ObservableCollection<Player> { new Player("test", "DefaultProfilePicture") };
|
|
var games = new ObservableCollection<Game> { new Game(_mockPersistence.Object) };
|
|
var maps = new ObservableCollection<Map> { new Map("test_name", "test_background.png") };
|
|
var bestScores = new ObservableCollection<BestScore> { new BestScore(1, 26) };
|
|
|
|
_mockPersistence.Setup(p => p.LoadData()).Returns((players, games, maps, bestScores));
|
|
|
|
_game.LoadData();
|
|
|
|
Assert.Equal(players, _game.Players);
|
|
Assert.Equal(games, _game.Games);
|
|
Assert.Equal(maps, _game.Maps);
|
|
Assert.Equal(bestScores, _game.BestScores);
|
|
}
|
|
|
|
[Fact]
|
|
public void SaveData_ShouldCallPersistenceSaveData()
|
|
{
|
|
_game.SaveData();
|
|
|
|
_mockPersistence.Verify(p => p.SaveData(_game.Players, _game.Games, _game.Maps, _game.BestScores), Times.Once); // Times.Once is to verify if the method is called exactly one time
|
|
}
|
|
|
|
[Fact]
|
|
public void InitializeGame_ShouldInitializeGameAndNotTriggerEventWhenNotStarted()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
bool eventTriggered = false;
|
|
|
|
_game.GameStarted += (sender, args) =>
|
|
{
|
|
eventTriggered = true;
|
|
};
|
|
|
|
_game.InitializeGame(map, player, false);
|
|
Assert.False(eventTriggered);
|
|
Assert.False(_game.IsRunning);
|
|
Assert.Equal(map, _game.UsedMap);
|
|
Assert.Equal(player, _game.CurrentPlayer);
|
|
}
|
|
|
|
[Fact]
|
|
public void InitializeGame_ShouldInitializeGameAndTriggerEventWhenStarted()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
bool eventTriggered = false;
|
|
|
|
_game.GameEnded += (sender, args) =>
|
|
{
|
|
eventTriggered = true;
|
|
};
|
|
|
|
_game.InitializeGame(map, player, true);
|
|
Assert.True(eventTriggered);
|
|
Assert.False(_game.IsRunning);
|
|
Assert.Equal(map, _game.UsedMap);
|
|
Assert.Equal(player, _game.CurrentPlayer);
|
|
}
|
|
|
|
[Theory]
|
|
[InlineData(Operation.ADDITION, 3, 4, 7)]
|
|
[InlineData(Operation.SUBTRACTION, 6, 4, 2)]
|
|
[InlineData(Operation.MULTIPLICATION, 2, 3, 6)]
|
|
[InlineData(Operation.LOWER, 1, 4, 1)]
|
|
[InlineData(Operation.HIGHER, 2, 5, 5)]
|
|
public void HandlePlayerOperation_ShouldPerformCorrectOperationAndTriggerEvent(Operation operation, int value1, int value2, int expectedResult)
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
_game.InitializeGame(map, player, false);
|
|
|
|
bool eventTriggered = false;
|
|
int actualResult = 0;
|
|
|
|
_game.OperationChosen += (sender, args) =>
|
|
{
|
|
eventTriggered = true;
|
|
actualResult = args.Result;
|
|
};
|
|
|
|
SetDiceValues(_game, value1, value2);
|
|
|
|
|
|
_game.HandlePlayerOperation(operation);
|
|
|
|
|
|
Assert.True(eventTriggered);
|
|
Assert.Equal(expectedResult, actualResult);
|
|
}
|
|
|
|
[Fact]
|
|
public void Game_Initialization_SetsMap()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
|
|
_game.InitializeGame(map, player);
|
|
|
|
Assert.Equal(map, _game.UsedMap);
|
|
}
|
|
|
|
[Fact]
|
|
public void Game_Initialization_SetsPlayer()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
|
|
_game.InitializeGame(map, player);
|
|
|
|
Assert.Equal(player, _game.CurrentPlayer);
|
|
}
|
|
|
|
[Fact]
|
|
public void Game_Initialization_SetsDice()
|
|
{
|
|
Player player = new Player("test_player", "DefaultProfilePicture");
|
|
Map map = new Map("test_name", "test_background.png");
|
|
|
|
_game.InitializeGame(map, player);
|
|
|
|
Assert.NotNull(_game.Dice1);
|
|
Assert.NotNull(_game.Dice2);
|
|
}
|
|
|
|
[Fact]
|
|
public void Game_Initialization_SetsGameRules()
|
|
{
|
|
var game = new Game(_mockPersistence.Object);
|
|
|
|
Assert.NotNull(game.GameRules);
|
|
}
|
|
|
|
[Fact]
|
|
public void MarkOperationAsChecked_Check_Well()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
|
|
_game.InitializeGame(map, player);
|
|
|
|
// Use of reflection to call private method
|
|
/*
|
|
var methodInfo = typeof(Game).GetMethod("MarkOperationAsChecked", BindingFlags.NonPublic | BindingFlags.Instance);
|
|
Assert.NotNull(methodInfo);
|
|
*/
|
|
|
|
var operation = Operation.ADDITION;
|
|
|
|
|
|
//methodInfo.Invoke(_game, new object[] { operation });
|
|
|
|
_game.MarkOperationAsChecked(operation);
|
|
|
|
int operationIndex = (int)operation;
|
|
int operationsPerType = 4;
|
|
bool isChecked = false;
|
|
|
|
for (int i = operationIndex * operationsPerType; i < (operationIndex + 1) * operationsPerType; i++)
|
|
{
|
|
if (_game.UsedMap.OperationGrid[i].IsChecked)
|
|
{
|
|
isChecked = true;
|
|
break;
|
|
}
|
|
}
|
|
|
|
Assert.True(isChecked);
|
|
}
|
|
|
|
[Fact]
|
|
public void IsPlaceOperationCorrect()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
|
|
_game.InitializeGame(map, player);
|
|
Assert.NotNull(_game.GameRules);
|
|
_game.UsedMap.Boards[0].Value = 1;
|
|
_game.UsedMap.Boards[1].Value = 2;
|
|
|
|
var methodInfo = typeof(Game).GetMethod("PlaceResult", BindingFlags.NonPublic | BindingFlags.Instance);
|
|
Assert.NotNull(methodInfo);
|
|
|
|
var cell = new Cell(0, 2);
|
|
cell.Value = 3;
|
|
methodInfo.Invoke(_game, new object[] { cell, 3 });
|
|
|
|
Assert.Equal(3, _game.UsedMap.Boards[2].Value);
|
|
}
|
|
|
|
[Fact]
|
|
public void IsHandlePlayerChoice_Handling()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
|
|
_game.InitializeGame(map, player);
|
|
|
|
var cell = new Cell(0, 1);
|
|
_game.UsedMap.Boards[0].Value = 1;
|
|
bool result = _game.HandlePlayerChoice(cell, 1);
|
|
Assert.True(result);
|
|
}
|
|
|
|
[Fact]
|
|
public void IsHandlePlayerChoice_InvalidCell()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
|
|
_game.InitializeGame(map, player);
|
|
|
|
var cell = new Cell(0, 7);
|
|
cell.Value = 1;
|
|
bool result = _game.HandlePlayerChoice(cell, 1);
|
|
Assert.False(result);
|
|
}
|
|
|
|
[Fact]
|
|
public void IsHandlePlayerChoice_InvalidPlace()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
|
|
_game.InitializeGame(map, player);
|
|
|
|
var cell = new Cell(0, 0);
|
|
cell.Value = 1;
|
|
var othercell = new Cell(3, 3);
|
|
bool result = _game.HandlePlayerChoice(othercell, 1);
|
|
Assert.False(result);
|
|
}
|
|
|
|
[Fact]
|
|
public void ShouldTriggerEventWhenEnded()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
bool eventTriggered = false;
|
|
|
|
_game.GameEnded += (sender, args) =>
|
|
{
|
|
eventTriggered = true;
|
|
};
|
|
|
|
_game.InitializeGame(map, player, true);
|
|
Assert.True(eventTriggered);
|
|
Assert.False(_game.IsRunning);
|
|
Assert.Equal(map, _game.UsedMap);
|
|
Assert.Equal(player, _game.CurrentPlayer);
|
|
}
|
|
|
|
[Fact]
|
|
public void RemovePlayerTest_ShouldRemovePlayer()
|
|
{
|
|
Game game = new Game();
|
|
Player player = new Player("test", "DefaultProfilePicture");
|
|
game.AddPlayer(player);
|
|
Assert.True(game.RemovePlayer("test"));
|
|
}
|
|
|
|
[Fact]
|
|
public void RemovePlayerTest_ShouldNotRemovePlayer()
|
|
{
|
|
Game game = new Game();
|
|
Player player = new Player("test", "DefaultProfilePicture");
|
|
game.AddPlayer(player);
|
|
Assert.False(game.RemovePlayer("otherName"));
|
|
}
|
|
|
|
[Fact]
|
|
public void PutPenalty_ShouldPutPenalty()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
_game.InitializeGame(map, player);
|
|
_game.UsedMap.Boards[1].Value = 5;
|
|
|
|
var methodInfo = typeof(Game).GetMethod("PlaceResult", BindingFlags.NonPublic | BindingFlags.Instance);
|
|
Assert.NotNull(methodInfo);
|
|
|
|
var cell = new Cell(0, 2);
|
|
cell.Value = 14;
|
|
methodInfo.Invoke(_game, new object[] { cell, 14 });
|
|
|
|
Assert.True(_game.UsedMap.Boards[2].Penalty);
|
|
}
|
|
|
|
[Fact]
|
|
public void PutPenalty_ShouldPutPenalty_ForDangerous()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
_game.InitializeGame(map, player);
|
|
_game.UsedMap.Boards[1].Value = 5;
|
|
_game.UsedMap.Boards[2].IsDangerous = true;
|
|
|
|
var methodInfo = typeof(Game).GetMethod("PlaceResult", BindingFlags.NonPublic | BindingFlags.Instance);
|
|
Assert.NotNull(methodInfo);
|
|
|
|
var cell = new Cell(0, 2);
|
|
cell.Value = 7;
|
|
methodInfo.Invoke(_game, new object[] { cell, 7 });
|
|
|
|
Assert.True(_game.UsedMap.Boards[2].Penalty);
|
|
}
|
|
|
|
[Fact]
|
|
public void PutPenaltyForLostCells_ReallyPutPenalty_ForZones()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
_game.InitializeGame(map, player);
|
|
|
|
_game.UsedMap.Boards[1].Value = 5;
|
|
_game.UsedMap.Boards[2].Value = 5;
|
|
_game.UsedMap.Boards[3].Value = 5;
|
|
_game.UsedMap.Boards[0].Value = 0;
|
|
|
|
foreach (var cells in _game.UsedMap.Boards.ToList())
|
|
{
|
|
_game.GameRules.IsZoneValidAndAddToZones(cells, _game.UsedMap);
|
|
}
|
|
|
|
_game.PutPenaltyForLostCells(_game.UsedMap.Boards);
|
|
|
|
Assert.True(_game.UsedMap.Boards[0].Penalty);
|
|
|
|
}
|
|
|
|
[Fact]
|
|
public void PutPenaltyForLostCells_ReallyPutPenalty_ForRopePathes()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
_game.InitializeGame(map, player);
|
|
|
|
_game.UsedMap.Boards[1].Value = 1;
|
|
_game.UsedMap.Boards[2].Value = 2;
|
|
_game.UsedMap.Boards[3].Value = 5;
|
|
_game.UsedMap.Boards[0].Value = 0;
|
|
|
|
var methodInfo = typeof(Game).GetMethod("AddToRopePath", BindingFlags.NonPublic | BindingFlags.Instance);
|
|
Assert.NotNull(methodInfo);
|
|
|
|
foreach (var cells in _game.UsedMap.Boards.ToList())
|
|
{
|
|
methodInfo.Invoke(_game, new object[] { cells, _game.UsedMap.Boards.ToList() });
|
|
}
|
|
|
|
_game.PutPenaltyForLostCells(_game.UsedMap.Boards);
|
|
|
|
Assert.True(_game.UsedMap.Boards[3].Penalty);
|
|
|
|
}
|
|
|
|
[Fact]
|
|
public void CalculusOfPenalty_ReallyCalculusPenalty()
|
|
{
|
|
var player = new Player("test_player", "DefaultProfilePicture");
|
|
var map = new Map("test_name", "test_background.png");
|
|
_game.InitializeGame(map, player);
|
|
|
|
_game.UsedMap.Boards[0].Valid = true;
|
|
_game.UsedMap.Boards[1].Valid = true;
|
|
_game.UsedMap.Boards[2].Valid = true;
|
|
_game.UsedMap.Boards[7].Valid = true;
|
|
_game.UsedMap.Boards[8].Valid = true;
|
|
_game.UsedMap.Boards[9].Valid = true;
|
|
_game.UsedMap.Boards[10].Valid = true;
|
|
_game.UsedMap.Boards[11].Valid = true;
|
|
_game.UsedMap.Boards[12].Valid = true;
|
|
_game.UsedMap.Boards[13].Valid = true;
|
|
|
|
|
|
_game.UsedMap.Boards[0].Value = 0;
|
|
_game.UsedMap.Boards[1].Value = 1;
|
|
_game.UsedMap.Boards[2].Value = 2;
|
|
_game.UsedMap.Boards[8].Value = 5;
|
|
_game.UsedMap.Boards[7].Value = 5;
|
|
_game.UsedMap.Boards[9].Value = 5;
|
|
_game.UsedMap.Boards[10].Value = 6;
|
|
_game.UsedMap.Boards[11].IsDangerous = true;
|
|
_game.UsedMap.Boards[12].Value = 13; //One penalty because it is over 12
|
|
_game.UsedMap.Boards[13].Value = 9; //One penalty because it is lost
|
|
|
|
var place = typeof(Game).GetMethod("PlaceResult", BindingFlags.NonPublic | BindingFlags.Instance);
|
|
Assert.NotNull(place);
|
|
|
|
var cell = new Cell(1, 4);
|
|
cell.Value = 7;
|
|
cell.Valid = true;
|
|
cell.IsDangerous = true;
|
|
place.Invoke(_game, new object[] { cell, 7 }); //One penalty
|
|
|
|
var methodInfo = typeof(Game).GetMethod("AddToRopePath", BindingFlags.NonPublic | BindingFlags.Instance);
|
|
Assert.NotNull(methodInfo);
|
|
|
|
foreach (var cells in _game.UsedMap.Boards.ToList())
|
|
{
|
|
_game.GameRules.IsZoneValidAndAddToZones(cells, _game.UsedMap);
|
|
methodInfo.Invoke(_game, new object[] { cells, _game.GameRules.EveryAdjacentCells(cells, _game.UsedMap.Boards.ToList()) });
|
|
}
|
|
|
|
_game.PutPenaltyForLostCells(_game.UsedMap.Boards);
|
|
|
|
Assert.True(_game.UsedMap.Boards[10].Penalty);
|
|
Assert.True(_game.UsedMap.Boards[11].Penalty);
|
|
Assert.True(_game.UsedMap.Boards[12].Penalty);
|
|
|
|
Assert.Equal(9, _game.CalculusOfPenalty(_game.UsedMap.Boards));
|
|
|
|
}
|
|
}
|