Fin des documentations doxygen corelibrary
continuous-integration/drone/push Build is passing Details

master
Céleste BARBOSA 12 months ago
commit f3f3791373

@ -1,147 +1,172 @@
using CoreLibrary.Events;
using CoreLibrary;
namespace ConsoleApp
{
/// <summary>
/// Fournit des gestionnaires d'événements les événements liés au déroulement de la partie.
/// </summary>
public static class Evenements
{
/// <summary>
/// Gestionnaire d'événement pour l'ajout d'un joueur.
/// </summary>
public static string? DemanderJoueur(Object? sender, DemanderJoueurEventArgs e)
{
Console.WriteLine($"Joueur {e.Numero}");
Console.Write(">>> ");
string? nom = Console.ReadLine();
Console.WriteLine();
return nom;
}
/// <summary>
/// Gestionnaire d'événement pour le début de la partie.
/// </summary>
public static void CommencerLaPartie(Object? sender, DebutPartieEventArgs e)
{
Utils.DessinerSeparateur();
Console.WriteLine("La partie commence, bonne chance à tous !\n");
}
/// <summary>
/// Gestionnaire d'événement pour le début d'un nouveau tour.
/// </summary>
public static void NouveauTour(Object? sender, NouveauTourEventArgs e)
{
Utils.DessinerSeparateur();
Console.WriteLine($"Tour {e.Tour} - {e.Joueur.Nom}\n");
Utils.DessinerPlateau(e.Grille, e.Indicateurs);
Console.WriteLine();
}
/// <summary>
/// Gestionnaire d'événement pour la demande d'ajout d'un jeton.
/// </summary>
public static Jeton? DemanderJeton(Object? sender, DemanderJetonEventArgs e)
{
Console.TreatControlCAsInput = true;
bool aChoisi = false;
int indice = 0;
Couleur[] couleurs = (Couleur[])Enum.GetValues(typeof(Couleur));
while (!aChoisi)
{
Utils.DessinerPion(couleurs[indice]);
Console.Write("\b\b\b");
switch (Console.ReadKey(true).Key)
{
case ConsoleKey.Enter:
aChoisi = true;
break;
case ConsoleKey.LeftArrow:
--indice;
break;
case ConsoleKey.RightArrow:
++indice;
break;
case ConsoleKey.Escape:
return null;
default:
break;
}
if (indice < 0)
indice = couleurs.Length - 1;
else if (indice >= couleurs.Length)
indice = 0;
}
Console.TreatControlCAsInput = false;
return new Jeton(couleurs[indice]);
}
/// <summary>
/// Gestionnaire d'événement pour l'ajout d'un jeton.
/// </summary>
public static void AjouterJeton(Object? sender, AjouterJetonEventArgs e)
{
Utils.DessinerPion(e.Jeton.Couleur);
}
/// <summary>
/// Gestionnaire d'événement pour la suppression du dernier jeton ajouté.
/// </summary>
public static void SupprimerDernierJeton(Object? sender, SupprimerDernierJetonEventArgs e)
{
Console.Write("\b\b\b \b\b\b\b\b\b");
}
/// <summary>
/// Gestionnaire d'événement pour l'ajout d'un code.
/// </summary>
public static void AjouterCode(Object? sender, AjouterCodeEventArgs e)
{
Console.WriteLine();
Utils.DessinerSeparateur();
}
/// <summary>
/// Gestionnaire d'événement pour la fin de la partie.
/// </summary>
public static void PartieTerminee(Object? sender, PartieTermineeEventArgs e)
{
Joueur[] gagnants = e.Gagnants.ToArray();
if (gagnants.Length > 1)
{
Console.WriteLine("C'est une égalité !");
}
else if (gagnants.Length == 1)
{
Console.WriteLine($"C'est une victoire de {gagnants[0].Nom}.");
}
else
{
Console.WriteLine("C'est une défaite des deux joueurs...");
}
}
}
}
using CoreLibrary.Events;
using CoreLibrary;
namespace ConsoleApp
{
/// <summary>
/// Fournit un ensemble de méthodes écoutant les événements liés au déroulement de la partie.
/// </summary>
public static class Evenements
{
/// <summary>
/// Ecoute l'événement en rapport avec la demande du nom d'un joueur.
/// <param name="sender">La classe qui appelle l'événement; ici Partie.</param>
/// <param name="e">L'instance de l'événement DemanderJoueurEventArgs créée par Partie.</param>
/// <returns>Le nom du joueur.</returns>
/// </summary>
public static string? DemanderJoueur(Object? sender, DemanderJoueurEventArgs e)
{
Console.WriteLine($"Joueur {e.Numero}");
Console.Write(">>> ");
string? nom = Console.ReadLine();
Console.WriteLine();
return nom;
}
/// <summary>
/// Ecoute l'événement en rapport avec le début de la partie.
/// <param name="sender">La classe qui appelle l'événement; ici Partie.</param>
/// <param name="e">L'instance de l'événement DebutPartieEventArgs créée par Partie.</param>
/// </summary>
public static void CommencerLaPartie(Object? sender, DebutPartieEventArgs e)
{
Utils.DessinerSeparateur();
Console.WriteLine("La partie commence, bonne chance à tous !\n");
}
/// <summary>
/// Ecoute l'événement en rapport avec un nouveau tour.
/// <param name="sender">La classe qui appelle l'événement; ici Partie.</param>
/// <param name="e">L'instance de l'événement NouveauTourEventArgs créée par Partie.</param>
/// </summary>
public static void NouveauTour(Object? sender, NouveauTourEventArgs e)
{
Utils.DessinerSeparateur();
Console.WriteLine($"Tour {e.Tour} - {e.Joueur.Nom}\n");
Utils.DessinerPlateau(e.Grille, e.Indicateurs);
Console.WriteLine();
}
/// <summary>
/// Ecoute l'événement en rapport avec la demande d'un jeton.
/// <param name="sender">La classe qui appelle l'événement; ici Partie.</param>
/// <param name="e">L'instance de l'événement DemanderJetonEventArgs créée par Partie.</param>
/// <returns>Le jeton choisi par le joueur.</returns>
/// </summary>
public static Jeton? DemanderJeton(Object? sender, DemanderJetonEventArgs e)
{
Console.TreatControlCAsInput = true;
Console.CursorVisible = false;
bool aChoisi = false;
int indice = 0;
Couleur[] couleurs = (Couleur[])Enum.GetValues(typeof(Couleur));
while (!aChoisi)
{
Utils.DessinerPion(couleurs[indice]);
Console.Write("\b\b\b");
switch (Console.ReadKey(true).Key)
{
case ConsoleKey.Enter:
aChoisi = true;
break;
case ConsoleKey.LeftArrow:
--indice;
break;
case ConsoleKey.RightArrow:
++indice;
break;
case ConsoleKey.Escape:
if (e.Indice != 0)
{
aChoisi = true;
indice = -2;
}
break;
default:
break;
}
if (indice == -1)
indice = couleurs.Length - 1;
else if (indice == couleurs.Length)
indice = 0;
}
Console.TreatControlCAsInput = false;
Console.CursorVisible = true;
return indice != -2 ? new Jeton(couleurs[indice]) : null;
}
/// <summary>
/// Ecoute l'événement en rapport avec l'ajout d'un jeton dans le code.
/// <param name="sender">La classe qui appelle l'événement; ici Partie.</param>
/// <param name="e">L'instance de l'événement AjouterJetonEventArgs créée par Partie.</param>
/// </summary>
public static void AjouterJeton(Object? sender, AjouterJetonEventArgs e)
{
Utils.DessinerPion(e.Jeton.Couleur);
}
/// <summary>
/// Ecoute l'événement en rapport avec la suppression du dernier jeton ajouté dans le code.
/// <param name="sender">La classe qui appelle l'événement; ici Partie.</param>
/// <param name="e">L'instance de l'événement SupprimerDernierJetonEventArgs créée par Partie.</param>
/// </summary>
public static void SupprimerDernierJeton(Object? sender, SupprimerDernierJetonEventArgs e)
{
Console.Write("\b\b\b \b\b\b\b\b\b");
}
/// <summary>
/// Ecoute l'événement en rapport avec l'ajout d'un code dans le plateau.
/// <param name="sender">La classe qui appelle l'événement; ici Partie.</param>
/// <param name="e">L'instance de l'événement AjouterCodeEventArgs créée par Partie.</param>
/// </summary>
public static void AjouterCode(Object? sender, AjouterCodeEventArgs e)
{
Console.WriteLine();
Utils.DessinerSeparateur();
}
/// <summary>
/// Ecoute l'événement en rapport avec la fin de la partie.
/// <param name="sender">La classe qui appelle l'événement; ici Partie.</param>
/// <param name="e">L'instance de l'événement PartieTermineeEventArgs créée par Partie.</param>
/// </summary>
public static void PartieTerminee(Object? sender, PartieTermineeEventArgs e)
{
Joueur[] gagnants = e.Gagnants.ToArray();
if (gagnants.Length > 1)
{
Console.WriteLine("C'est une égalité !");
}
else if (gagnants.Length == 1)
{
Console.WriteLine($"C'est une victoire de {gagnants[0].Nom}.");
}
else
{
Console.WriteLine("C'est une défaite des deux joueurs...");
}
}
}
}

@ -1,9 +1,12 @@
/// <summary>
/// Permet de jouer une partie de mastermind, avec les règles classiques
/// (2 joueurs, 12 tours, un code à 4 couleurs parmi 6)
/// </summary>
using ConsoleApp;
using CoreLibrary;
Console.OutputEncoding = System.Text.Encoding.UTF8;
Utils.DessinerTitre();
Partie maPartie = new Partie(new ReglesClassiques());

@ -2,8 +2,12 @@
namespace ConsoleApp
{
/// <summary>
/// Classe utilitaire contenant des méthodes pour dessiner des éléments dans la console.
/// </summary>
public static class Utils
{
// Dictionnaires associant les valeurs des énumérations avec les couleurs de la console
private readonly static Dictionary<Couleur, ConsoleColor> couleursTerminal = new Dictionary<Couleur, ConsoleColor>()
{
{Couleur.NOIR, ConsoleColor.Black },
@ -20,6 +24,9 @@ namespace ConsoleApp
{Indicateur.BONNECOULEUR, ConsoleColor.White }
};
/// <summary>
/// Dessine le titre du jeu dans la console.
/// </summary>
public static void DessinerTitre()
{
Console.WriteLine(@"
@ -31,7 +38,9 @@ namespace ConsoleApp
DessinerSeparateur();
}
/// <summary>
/// Dessine un séparateur dans la console.
/// </summary>
public static void DessinerSeparateur()
{
Console.WriteLine(@"
@ -42,31 +51,50 @@ namespace ConsoleApp
");
}
/// <summary>
/// Dessine un pion dans la console.
/// </summary>
/// <param name="pion">Le pion à dessiner (une couleur ou un indicateur).</param>
public static void DessinerPion(Enum pion)
{
Console.Write(" ");
// Sélectionne la couleur appropriée en fonction du type de pion (une couleur ou un indicateur)
// Si Couleur.ROUGE alors le fond sera ConsoleColor.Red
// Si Indicateur.BONNEPLACE alors le fond sera ConsoleColor.Black
Console.ForegroundColor = pion.GetType().Equals(typeof(Couleur)) ?
couleursTerminal.GetValueOrDefault((Couleur)pion) :
indicateursTerminal.GetValueOrDefault((Indicateur)pion);
// Si la couleur du pion est noir, alors le fond devient blanc, sinon il reste noir
Console.BackgroundColor = Console.ForegroundColor.Equals(ConsoleColor.Black) ? ConsoleColor.White : ConsoleColor.Black;
Console.Write("⬤");
Console.OutputEncoding = System.Text.Encoding.UTF8;
Console.Write("O");
Console.ResetColor();
Console.Write(" ");
}
/// <summary>
/// Dessine une ligne de pions sur la console.
/// </summary>
/// <param name="ligne">Un tableau d'énumérations représentant les pions à dessiner.</param>
private static void DessinerLigne(Enum[] ligne)
{
foreach(Enum pion in ligne)
DessinerPion(pion);
// Ajoute des espaces s'il y a moins de 4 pions à dessiner
Console.Write("".PadLeft((4 - ligne.Length) * 3));
}
/// <summary>
/// Dessine un plateau de jeu dans la console, affichant les codes et leurs indicateurs.
/// </summary>
/// <param name="grille">La grille de jeu.</param>
/// <param name="indicateurs">Les indicateurs associés à chaque ligne.</param>
public static void DessinerPlateau(IEnumerable<IEnumerable<Jeton?>> grille, IEnumerable<IEnumerable<Indicateur>> indicateurs)
{
IEnumerable<Jeton?>[] grilleTableau = grille.ToArray();

@ -3,15 +3,22 @@
namespace CoreLibrary
{
/// <summary>
/// Classe représentant un code, composé des jetons et méthodes
/// Représente un code composé de jetons.
/// </summary>
public class Code
{
private readonly Jeton?[] lesJetons;
/// <summary>
/// Obtenir le nombre de jetons dans le code.
/// </summary>
public int NbJetons { get; private set; } = 0;
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="Code"/> avec la longueur de code spécifiée.
/// </summary>
/// <param name="tailleCode">La longueur du code.</param>
/// <exception cref="TailleCodeException">Levée lorsque la longueur du code spécifiée est inférieure ou égale à zéro.</exception>
public Code(int tailleCode)
{
if(tailleCode <= 0)
@ -22,9 +29,14 @@ namespace CoreLibrary
lesJetons = new Jeton?[tailleCode];
}
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="Code"/> avec les jetons spécifiés.
/// </summary>
/// <param name="jetons">Les jetons pour initaliser le code.</param>
/// <exception cref="TailleCodeException">Levée lorsque la collection de jetons spécifiée est vide.</exception>
public Code(IEnumerable<Jeton> jetons)
{
if (jetons.Any())
if (!jetons.Any())
{
throw new TailleCodeException(jetons.Count());
}
@ -36,6 +48,11 @@ namespace CoreLibrary
}
}
/// <summary>
/// Ajoute un jeton au code.
/// </summary>
/// <param name="jeton">Le jeton à ajouter</param>
/// <exception cref="CodeCompletException">Levée lorsque le code est plein.</exception>
public void AjouterJeton(Jeton jeton)
{
if (NbJetons == TailleMaximale())
@ -46,6 +63,10 @@ namespace CoreLibrary
lesJetons[NbJetons++] = jeton;
}
/// <summary>
/// Supprime le dernier jeton ajouté au code.
/// </summary>
/// <exception cref="CodeVideException">Levée lorsque le code est vide.</exception>
public void SupprimerDernierJeton()
{
if(NbJetons == 0)
@ -56,9 +77,15 @@ namespace CoreLibrary
lesJetons[--NbJetons] = null;
}
/// <summary>
/// Récupère le jeton à l'indice spécifié dans le code.
/// </summary>
/// <param name="indice">L'indice du jeton a récupéré.</param>
/// <returns>Le jeton situé à l'indice spécifié.</returns>
/// <exception cref="IndiceCodeException">Levée lorsque l'indice est supérieur à la taille maximale du code, inférieur à 0 ou qu'il n'y a pas de jeton à l'indice spécifié</exception>
public Jeton RecupererJeton(int indice)
{
if(indice < 0 || indice > TailleMaximale())
if(indice < 0 || indice >= TailleMaximale())
throw new IndiceCodeException(indice, NbJetons-1);
Jeton? jeton = lesJetons[indice];
@ -69,28 +96,47 @@ namespace CoreLibrary
return jeton.Value;
}
/// <summary>
/// Récupère une énumération des jetons dans le code.
/// </summary>
/// <returns>Enumération des jetons du code</returns>
public IEnumerable<Jeton?> Jetons()
{
return lesJetons;
}
/// <summary>
/// Vérifie si le code est complet.
/// </summary>
/// <returns>True si le code est complet, sinon False.</returns>
public bool EstComplet()
{
return NbJetons == lesJetons.Length;
}
/// <summary>
/// Recupère la taille maximal du code.
/// </summary>
/// <returns>Taille maximal du code.</returns>
public int TailleMaximale()
{
return lesJetons.Length;
}
/// <summary>
/// Compare le code avec un autre code et génère des indcateurs de correspondance.
/// </summary>
/// <param name="autreCode">Le code à comparer avec le code actuel</param>
/// <returns>Enumération d'indicateurs de correspondance entre les deux codes.</returns>
public IEnumerable<Indicateur> Comparer(Code autreCode)
{
// Mon code est le code correct, l'autre code est celui qui teste
Indicateur[] indicateurs = [];
if (!EstComplet() || !autreCode.EstComplet())
if (!autreCode.EstComplet())
return indicateurs;
List<Jeton?> mesJetons = new List<Jeton?>(Jetons());
@ -113,13 +159,14 @@ namespace CoreLibrary
for (int i = 0; i < sesJetons.Count; ++i)
{
Jeton? sonJeton = sesJetons[i];
if (sonJeton.HasValue && mesJetons.Contains(sonJeton.Value))
{
indicateurs = indicateurs.Append(Indicateur.BONNECOULEUR).ToArray();
mesJetons[mesJetons.IndexOf(sonJeton.Value)] = null;
mesJetons[mesJetons.IndexOf(sonJeton)] = null;
sesJetons[i] = null;
break;
}
}

@ -1,20 +1,19 @@

namespace CoreLibrary.Events
namespace CoreLibrary.Events
{
/// <summary>
/// Représente les arguments d'événement pour l'événement de l'ajout d'un code.
/// Classe contenant les arguments passées en paramètre lors de l'événement AjouterCode.
/// </summary>
public class AjouterCodeEventArgs : EventArgs
{
/// <summary>
/// Obtient le code ajouté.
/// Le code ajouté.
/// </summary>
public Code Code { get; private set; }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="AjouterCodeEventArgs"/> avec le code spécifié.
/// </summary>
/// <param name="code">Le code à ajouter.</param>
/// <param name="code">Le code qui a été ajouté.</param>
public AjouterCodeEventArgs(Code code)
{
Code = code;

@ -1,21 +1,19 @@

namespace CoreLibrary.Events
namespace CoreLibrary.Events
{
/// <summary>
/// Représente les arguments d'événement pour l'événement d'ajout d'un jeton.
/// Classe contenant les arguments passées en paramètre lors de l'événement AjouterJeton.
/// </summary>
public class AjouterJetonEventArgs : EventArgs
{
/// <summary>
/// Obtient le jeton ajouté.
/// Le jeton ajouté.
/// </summary>
public Jeton Jeton { get; private set; }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="AjouterJetonEventArgs"/> avec le jeton spécifié.
/// </summary>
/// <param name="jeton">Le jeton à ajouter.</param>
/// <param name="jeton">Le jeton qui a été ajouté.</param>
public AjouterJetonEventArgs(Jeton jeton)
{
Jeton = jeton;

@ -1,19 +1,19 @@
namespace CoreLibrary.Events
{
/// <summary>
/// Représente les arguments d'événement pour l'événement d'ajout d'un joueur.
/// Classe contenant les arguments passées en paramètre lors de l'événement AjouterJoueur.
/// </summary>
public class AjouterJoueursEventArgs : EventArgs
{
/// <summary>
/// Obtient le joueur ajouté.
/// Le joueur ajouté.
/// </summary>
public Joueur Joueur { get; private set; }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="AjouterJoueursEventArgs"/> avec le joueur spécifié.
/// </summary>
/// <param name="joueur">Le joueur à ajouter.</param>
/// <param name="joueur">Le joueur qui a été ajouté.</param>
public AjouterJoueursEventArgs(Joueur joueur)
{
Joueur = joueur;

@ -1,7 +1,7 @@
namespace CoreLibrary.Events
{
/// <summary>
/// Représente les arguments d'événement pour le début d'une partie.
// <summary>
/// Classe contenant les arguments passées en paramètre lors de l'événement DebutPartie
/// </summary>
public class DebutPartieEventArgs : EventArgs
{

@ -1,10 +1,22 @@

namespace CoreLibrary.Events
namespace CoreLibrary.Events
{
/// <summary>
/// Représente les arguments d'événement pour la demande d'ajout d'un jeton.
/// <summary>
/// Classe contenant les arguments passées en paramètre lors de l'événement DemanderJeton.
/// </summary>
public class DemanderJetonEventArgs : EventArgs
{
/// <summary>
/// L'indice du code où le jeton va être ajouté.
/// </summary>
public int Indice { get; private set; }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="DemanderJetonEventArgs"/> avec l'indice spécifié.
/// </summary>
/// <param name="joueur">L'indice du jeton qui va été ajouté.</param>
public DemanderJetonEventArgs(int indice)
{
Indice = indice;
}
}
}

@ -1,12 +1,12 @@
namespace CoreLibrary.Events
{
/// <summary>
/// Représente les arguments d'événement pour la demande d'ajout d'un joueur.
/// Classe contenant les arguments passées en paramètre lors de l'événement DemanderJoueur.
/// </summary>
public class DemanderJoueurEventArgs : EventArgs
{
/// <summary>
/// Obtient le numéro du joueur à ajouter.
/// Le numéro du joueur (Joueur 1 ou 2, 3..).
/// </summary>
public int Numero { get; private set; }
@ -14,7 +14,7 @@
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="DemanderJoueurEventArgs"/> avec le numéro du joueur spécifié.
/// </summary>
/// <param name="numero">Le numéro du joueur à ajouter.</param>
/// <param name="numero">Le numéro du joueur qui va être ajouté.</param>
public DemanderJoueurEventArgs(int numero)
{
Numero = numero;

@ -1,29 +1,27 @@
using CoreLibrary.Exceptions;
namespace CoreLibrary.Events
namespace CoreLibrary.Events
{
/// <summary>
/// Représente les arguments d'événement pour le début d'un nouveau tour.
/// Classe contenant les arguments passées en paramètre lors de l'événement NouveauTour.
/// </summary>
public class NouveauTourEventArgs : EventArgs
{
/// <summary>
/// Obtient le joueur dont c'est le tour.
/// Le joueur dont c'est le tour.
/// </summary>
public Joueur Joueur { get; private set; }
/// <summary>
/// Obtient le numéro du tour.
/// Le numéro du tour.
/// </summary>
public int Tour { get; private set; }
/// <summary>
/// Obtient la grille du joueur actuelle.
/// La grille du joueur actuelle.
/// </summary>
public IEnumerable<IEnumerable<Jeton?>> Grille { get; private set; }
/// <summary>
/// Obtient les indicateurs de la grille de jeu.
/// Les indicateurs de la grille de jeu.
/// </summary>
public IEnumerable<IEnumerable<Indicateur>> Indicateurs { get; private set; }

@ -1,31 +1,25 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace CoreLibrary.Events
namespace CoreLibrary.Events
{
/// <summary>
/// Représente les arguments d'événement pour la fin d'une partie.
/// Classe contenant les arguments passées en paramètre lors de l'événement PartieTerminee.
/// </summary>
public class PartieTermineeEventArgs : EventArgs
{
/// <summary>
/// Obtient les joueurs gagnants de la partie.
/// Les joueurs gagnants de la partie.
/// </summary>
public IEnumerable<Joueur> Gagnants { get; private set; }
/// <summary>
/// Obtient les joueurs perdants de la partie.
/// Les joueurs perdants de la partie.
/// </summary>
public IEnumerable<Joueur> Perdants { get; private set; }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="PartieTermineeEventArgs"/> avec les gagnants et les perdants spécifiés.
/// </summary>
/// <param name="gagnants">Les joueurs gagnants de la partie.</param>
/// <param name="perdants">Les joueurs perdants de la partie.</param>
/// <param name="gagnants">Les gagnants.</param>
/// <param name="perdants">Les perdants.</param>
public PartieTermineeEventArgs(IEnumerable<Joueur> gagnants, IEnumerable<Joueur> perdants)
{
Gagnants = gagnants;

@ -1,7 +1,7 @@
namespace CoreLibrary.Events
{
/// <summary>
/// Représente les arguments d'événement pour le passage de la main au joueur suivant.
/// Classe contenant les arguments passées en paramètre lors de l'événement PasserMain.
/// </summary>
public class PasserMainEventArgs : EventArgs
{

@ -1,7 +1,7 @@
namespace CoreLibrary.Events
{
/// <summary>
/// Représente les arguments d'événement pour la suppression du dernier jeton ajouté.
/// Classe contenant les arguments passées en paramètre lors de l'événement SupprimerDernierJeton.
/// </summary>
public class SupprimerDernierJetonEventArgs : EventArgs
{

@ -8,17 +8,24 @@ namespace CoreLibrary.Exceptions
[Serializable]
public class CodeCompletException : Exception
{
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeCompletException"/>.
/// </summary>
// Message par défaut
private const string messageDefaut = "Le code dans lequel vous essayez d'ajouter un jeton est déjà complet.";
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeCompletException"/> avec le message par défaut.
/// </summary>
public CodeCompletException() : base(messageDefaut)
{}
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeCompletException"/> avec le message spécifié.
/// </summary>
public CodeCompletException(string message) : base(message)
{}
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeCompletException"/> avec le message et l'exception parent spécifiés.
/// </summary>
public CodeCompletException(string message, Exception exception) : base(message, exception)
{}

@ -8,17 +8,24 @@ namespace CoreLibrary.Exceptions
[Serializable]
public class CodeIncompletException : Exception
{
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeIncompletException"/>.
/// </summary>
// Message par défaut
private const string messageDefaut = "Le code que vous essayez d'ajouter dans la grille n'est pas complet.";
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeIncompletException"/> avec le message par défaut.
/// </summary>
public CodeIncompletException() : base(messageDefaut)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeIncompletException"/> avec le message spécifié.
/// </summary>
public CodeIncompletException(string message) : base(message)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeIncompletException"/> avec le message et l'exception parent spécifié.
/// </summary>
public CodeIncompletException(string message, Exception exception) : base(message, exception)
{ }

@ -8,23 +8,33 @@ namespace CoreLibrary.Exceptions
[Serializable]
public class CodeInvalideException : Exception
{
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeInvalideException"/>.
/// </summary>
/// <param name="tailleCodeAjoute">La taille du code que vous essayez d'ajouter.</param>
/// <param name="tailleCodePlateau">La taille du code que le plateau attend.</param>
// Message par défaut
private const string messageDefaut = "Le code que vous essayez d'ajouter est invalide.";
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeInvalideException"/> avec le message par défaut.
/// </summary>
public CodeInvalideException() : base(messageDefaut)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeInvalideException"/> avec des attributs spécifiés.
/// </summary>
/// <param name="tailleCodeAjoute">La taille du code que vous essayez d'ajouter.</param>
/// <param name="tailleCodePlateau">La taille du code que le plateau attend.</param>
public CodeInvalideException(int tailleCodeAjoute, int tailleCodePlateau) :
base($"Le code que vous essayez d'ajouter est un code de taille {tailleCodeAjoute}, or le plateau attend un code de {tailleCodePlateau}.")
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeInvalideException"/> avec le message spécifié.
/// </summary>
public CodeInvalideException(string message) : base(message)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeInvalideException"/> avec le message et l'exception parent spécifiés.
/// </summary>
public CodeInvalideException(string message, Exception exception) : base(message, exception)
{ }

@ -8,17 +8,24 @@ namespace CoreLibrary.Exceptions
[Serializable]
public class CodeVideException : Exception
{
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeVideException"/>.
/// </summary>
// Message par défaut
private const string messageDefaut = "Le code dans lequel vous essayez de supprimer un jeton est déjà vide.";
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeVideException"/> avec le message par défaut.
/// </summary>
public CodeVideException() : base(messageDefaut)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeVideException"/> avec le message spécifié.
/// </summary>
public CodeVideException(string message) : base(message)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="CodeVideException"/> avec le message et l'exception parent spécifiés.
/// </summary>
public CodeVideException(string message, Exception exception) : base(message, exception)
{ }

@ -8,17 +8,24 @@ namespace CoreLibrary.Exceptions
[Serializable]
public class GrilleCompleteException : Exception
{
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="GrilleCompleteException"/>.
/// </summary>
// Message par défaut
private const string messageDefaut = "La grille dans laquelle vous essayez d'ajouter un code est déjà complète.";
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="GrilleCompleteException"/> avec le message par défaut.
/// </summary>
public GrilleCompleteException() : base(messageDefaut)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="GrilleCompleteException"/> avec le message spécifié.
/// </summary>
public GrilleCompleteException(string message) : base(message)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="GrilleCompleteException"/> avec le message et l'exception parent spécifiés.
/// </summary>
public GrilleCompleteException(string message, Exception exception) : base(message, exception)
{ }

@ -8,23 +8,33 @@ namespace CoreLibrary.Exceptions
[Serializable]
public class IndiceCodeException : Exception
{
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="IndiceCodeException"/>.
/// </summary>
/// <param name="indice">L'indice incorrect qui a été spécifié.</param>
/// <param name="indiceMax">L'indice maximum permis.</param>
// Message par défaut
private const string messageDefaut = "L'indice du jeton que vous essayez de récupérer est hors de la plage valide.";
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="IndiceCodeException"/> avec le message par défaut.
/// </summary>
public IndiceCodeException() : base(messageDefaut)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="IndiceCodeException"/> avec les attributs spécifiés.
/// </summary>
/// <param name="indice">L'indice incorrect qui a été spécifié.</param>
/// <param name="indiceMax">L'indice maximum permis.</param>
public IndiceCodeException(int indice, int indiceMax) :
base($"Vous avez essayé de récupérer le jeton à la place {indice}, mais son indice doit être compris entre 0 et {indiceMax}.")
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="IndiceCodeException"/> avec le message spécifié.
/// </summary>
public IndiceCodeException(string message) : base(message)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="IndiceCodeException"/> avec le message et l'exception parent spécifiés.
/// </summary>
public IndiceCodeException(string message, Exception exception) : base(message, exception)
{ }

@ -8,17 +8,24 @@ namespace CoreLibrary.Exceptions
[Serializable]
public class PartieNonCommenceeException : Exception
{
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="PartieNonCommenceeException"/>.
/// </summary>
// Message par défaut
private const string messageDefaut = "La partie n'a pas encore commencée.";
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="PartieNonCommenceeException"/> avec le message par défaut.
/// </summary>
public PartieNonCommenceeException() : base(messageDefaut)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="PartieNonCommenceeException"/> avec le message spécifié.
/// </summary>
public PartieNonCommenceeException(string message) : base(message)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="PartieNonCommenceeException"/> avec le message et l'exception parent spécifiés.
/// </summary>
public PartieNonCommenceeException(string message, Exception exception) : base(message, exception)
{ }

@ -8,22 +8,31 @@ namespace CoreLibrary.Exceptions
[Serializable]
public class TailleCodeException : Exception
{
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="TailleCodeException"/>.
/// </summary>
/// <param name="taille">La taille du code spécifiée.</param>
// Message par défaut
private const string messageDefaut = "Un code doit avoir une taille positive non nulle.";
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="TailleCodeException"/> avec le message par défaut.
/// </summary>
public TailleCodeException() : base(messageDefaut)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="TailleCodeException"/> avec l'attribut spécifié.
/// </summary>
public TailleCodeException(int taille) :
base($"Un code doit avoir une taille positive non nulle, or il a reçu {taille}.")
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="TailleCodeException"/> avec le message spécifié.
/// </summary>
public TailleCodeException(string message) : base(message)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="TailleCodeException"/> avec le message et l'exception parent spécifiés.
/// </summary>
public TailleCodeException(string message, Exception exception) : base(message, exception)
{ }

@ -8,22 +8,32 @@ namespace CoreLibrary.Exceptions
[Serializable]
public class TailleGrilleException : Exception
{
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="TailleGrilleException"/>.
/// </summary>
/// <param name="taille">La taille de grille spécifiée.</param>
// Message par défaut
private const string messageDefaut = "Une grille doit avoir une taille positive non nulle.";
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="TailleGrilleException"/> avec le message par défaut.
/// </summary>
public TailleGrilleException() : base(messageDefaut)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="TailleGrilleException"/> avec l'attribut spécifié.
/// <param name="taille">La taille de la grille.</param>
/// </summary>
public TailleGrilleException(int taille) :
base($"Une grille doit avoir une taille positive non nulle, or elle a reçu {taille}.")
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="TailleGrilleException"/> avec le message spécifié.
/// </summary>
public TailleGrilleException(string message) : base(message)
{ }
/// <summary>
/// Initialise une nouvelle instance de la classe <see cref="TailleGrilleException"/> avec le message et l'exception parent spécifiés.
/// </summary>
public TailleGrilleException(string message, Exception exception) : base(message, exception)
{ }

@ -2,56 +2,159 @@
namespace CoreLibrary
{
/// <summary>
/// Représente une partie de jeu.
/// </summary>
public class Partie
{
private readonly IRegles regles;
/// <summary>
/// Définit le délégué pour gérer les événements avec des arguments de type string.
/// </summary>
public delegate string? StringEventHandler<in TEventArgs>(Object? sender, TEventArgs e);
/// <summary>
/// Définit le délégué pour gérer les événements avec des arguments de type Jeton.
/// </summary>
public delegate Jeton? JetonEventHandler<in TEventArgs>(Object? sender, TEventArgs e);
/// <summary>
/// Événement déclenché lorsqu'il est nécessaire de d'ajouter un joueur.
/// </summary>
public event StringEventHandler<DemanderJoueurEventArgs>? DemanderJoueur;
/// <summary>
/// Événement déclenché lorsqu'il est nécessaire d'ajouter un jeton.
/// </summary>
public event JetonEventHandler<DemanderJetonEventArgs>? DemanderJeton;
/// <summary>
/// Événement déclenché lorsqu'il est nécessaire d'ajouter un joueur.
/// </summary>
public event EventHandler<AjouterJoueursEventArgs>? AjouterJoueur;
/// <summary>
/// Événement déclenché lorsqu'une partie commence.
/// </summary>
public event EventHandler<DebutPartieEventArgs>? DebutPartie;
/// <summary>
/// Événement déclenché lorsqu'un nouveau tour commence.
/// </summary>
public event EventHandler<NouveauTourEventArgs>? NouveauTour;
/// <summary>
/// Événement déclenché lorsqu'il est nécessaire d'ajouter un jeton.
/// </summary>
public event EventHandler<AjouterJetonEventArgs>? AjouterJeton;
/// <summary>
/// Événement déclenché lorsqu'un jeton est supprimé.
/// </summary>
public event EventHandler<SupprimerDernierJetonEventArgs>? SupprimerDernierJeton;
/// <summary>
/// Événement déclenché lorsqu'un code est ajouté.
/// </summary>
public event EventHandler<AjouterCodeEventArgs>? AjouterCode;
/// <summary>
/// Événement déclenché lorsque la main est passée au joueur suivant.
/// </summary>
public event EventHandler<PasserMainEventArgs>? PasserMain;
/// <summary>
/// Événement déclenché lorsque la partie est terminée.
/// </summary>
public event EventHandler<PartieTermineeEventArgs>? PartieTerminee;
/// <summary>
/// Méthode pour déclencher l'événement de demande d'ajout d'un joueur.
/// </summary>
/// <param name="numero">Le numéro du joueur à ajouter</param>
/// <returns>Le nom du joueur demandé</returns></returns>
private string? QuandDemanderJoueur(int numero) => DemanderJoueur?.Invoke(this, new DemanderJoueurEventArgs(numero));
private Jeton? QuandDemanderJeton() => DemanderJeton?.Invoke(this, new DemanderJetonEventArgs());
/// <summary>
/// Méthode pour déclencher l'événement de demande d'ajout d'un jeton.
/// </summary>
/// <returns>Le jeton demandé</returns>
private Jeton? QuandDemanderJeton(int indice) => DemanderJeton?.Invoke(this, new DemanderJetonEventArgs(indice));
/// <summary>
/// Méthode pour déclencher l'événement d'ajout d'un joueur.
/// </summary>
/// <param name="joueur">Le joueur à ajouter.</param>
private void QuandAjouterJoueur(Joueur joueur) => AjouterJoueur?.Invoke(this, new AjouterJoueursEventArgs(joueur));
/// <summary>
/// Méthode pour déclencher l'événement du début d'un partie.
/// </summary>
private void QuandDebutPartie() => DebutPartie?.Invoke(this, new DebutPartieEventArgs());
/// <summary>
/// Méthode pour déclencher l'événement d'un nouveau tour.
/// </summary>
/// <param name="joueur">Le joueur dont c'est le tour.</param>
/// <param name="tour">Le numéro du tour.</param>
/// <param name="grille">La grille de jeu.</param>
/// <param name="indicateurs">Les indicateurs de jeu.</param>
private void QuandNouveauTour(Joueur joueur, int tour, IEnumerable<IEnumerable<Jeton?>> grille, IEnumerable<IEnumerable<Indicateur>> indicateurs) => NouveauTour?.Invoke(this, new NouveauTourEventArgs(joueur, tour, grille, indicateurs));
/// <summary>
/// Méthode pour déclencher l'événement d'ajout d'un nouveau jeton.
/// </summary>
/// <param name="jeton">Le jeton à ajouter.</param>
private void QuandNouveauJeton(Jeton jeton) => AjouterJeton?.Invoke(this, new AjouterJetonEventArgs(jeton));
/// <summary>
/// Méthode pour déclencher l'événement de suppression du dernier jeton du code.
/// </summary>
private void QuandSupprimerDernierJeton() => SupprimerDernierJeton?.Invoke(this, new SupprimerDernierJetonEventArgs());
/// <summary>
/// Méthode pour déclencher l'événement d'ajout d'un nouveau code.
/// </summary>
/// <param name="code">Le code à ajouter.</param>
private void QuandNouveauCode(Code code) => AjouterCode?.Invoke(this, new AjouterCodeEventArgs(code));
/// <summary>
/// Méthode pour déclencher l'événement de passage de la main au joueur suivant.
/// </summary>
private void QuandPasserMain() => PasserMain?.Invoke(this, new PasserMainEventArgs());
private void QuandPartieTerminee(IEnumerable<Joueur> gagnants, IEnumerable<Joueur> perdants) => PartieTerminee?.Invoke(this, new PartieTermineeEventArgs(gagnants, perdants));
/// <summary>
/// Méthode pour déclencher l'événement de fin de partie.
/// </summary>
/// <param name="gagnants">La liste des joueurs gagnants.</param>
/// <param name="perdants">La liste des joueurs perdants.</param>
private void QuandPartieTerminee(IEnumerable<Joueur> gagnants, IEnumerable<Joueur> perdants) => PartieTerminee?.Invoke(this, new PartieTermineeEventArgs(gagnants, perdants));
/// <summary>
/// Crée une nouvelle instance de la classe Partie.
/// </summary>
/// <param name="regles">Les règles de la partie.</param>
public Partie(IRegles regles)
{
this.regles = regles;
}
/// <summary>
/// Lance le déroulement de la partie.
/// </summary>
public void Jouer()
{
while (regles.NbJoueurs != regles.NbJoueursMaximum)
{
string nom = QuandDemanderJoueur(regles.NbJoueurs + 1) ?? $"Joueur {regles.NbJoueurs+1}";
Joueur joueur = regles.AjouterJoueur(nom);
QuandAjouterJoueur(joueur);
}
/// Ajout des joueurs jusqu'à atteindre le nombre maximum de joueurs défini par les règles
AjouterJoueurs();
regles.CommencerLaPartie();
QuandDebutPartie();
// Boucle principale du jeu qui dure jusqu'à qu'une condition de fin soit déclenchée
while (!regles.EstTerminee())
{
Joueur joueurCourant = regles.JoueurCourant();
@ -61,31 +164,10 @@ namespace CoreLibrary
Code code = regles.GenererCode();
while (!code.EstComplet())
{
Jeton? jeton = QuandDemanderJeton();
if(jeton == null)
{
if(DemanderJeton != null)
{
// Si quelqu'un écoute l'événement mais ne renvoie rien, alors on supprime le dernier jeton
code.SupprimerDernierJeton();
QuandSupprimerDernierJeton();
}
else
{
// Si personne n'écoute l'évenment, on met un jeton aléatoire
jeton = new Jeton();
}
}
if(jeton != null)
{
code.AjouterJeton(jeton.Value);
QuandNouveauJeton(jeton.Value);
}
}
CreerCode(code);
// Phase de saisie du code par le joueur jusqu'à que le code soit complet.
plateauCourant.AjouterCode(code);
QuandNouveauCode(code);
@ -99,5 +181,39 @@ namespace CoreLibrary
QuandPartieTerminee(regles.Gagnants(), regles.Perdants());
}
private void AjouterJoueurs()
{
while (regles.NbJoueurs != regles.NbJoueursMaximum)
{
string nom = QuandDemanderJoueur(regles.NbJoueurs + 1) ?? $"Joueur {regles.NbJoueurs + 1}";
Joueur joueur = regles.AjouterJoueur(nom);
QuandAjouterJoueur(joueur);
}
}
private void CreerCode(Code code)
{
while (!code.EstComplet())
{
Jeton? jeton = QuandDemanderJeton(code.NbJetons);
if (DemanderJeton == null)
{
jeton = new Jeton();
}
if(!jeton.HasValue)
{
code.SupprimerDernierJeton();
QuandSupprimerDernierJeton();
}
else
{
code.AjouterJeton(jeton.Value);
QuandNouveauJeton(jeton.Value);
}
}
}
}
}

@ -0,0 +1,197 @@
using CoreLibrary;
using CoreLibrary.Exceptions;
using Xunit;
namespace UnitTesting
{
public class CodeUT
{
[Fact]
public void TestFirstConstructorValidArguments()
{
Code code = new Code(4);
Assert.NotNull(code);
Assert.Equal(4, code.Jetons().Count());
Assert.Equal(0, code.NbJetons);
}
[Fact]
public void TestConstructorInvalidArguments()
{
Assert.Throws<TailleCodeException>(() => new Code(0));
Assert.Throws<TailleCodeException>(() => new Code(-1));
}
[Fact]
public void TestSecondConstructorValidArguments()
{
Jeton[] jetons = [new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLEU)];
Code code = new Code(jetons);
Assert.NotNull(code);
Assert.Equal(3, code.Jetons().Count());
Assert.Equal(3, code.NbJetons);
}
[Fact]
public void TestSecondConstructorInvalidArguments()
{
Assert.Throws<TailleCodeException>(() => new Code([]));
}
[Fact]
public void TestAjouterJetonValid()
{
Jeton jeton = new Jeton(Couleur.JAUNE);
Code code = new Code(3);
code.AjouterJeton(jeton);
Assert.Equal(1, code.NbJetons);
Assert.Equal(jeton, code.Jetons().ElementAt(0));
}
[Fact]
public void TestAjouterJetonInvalid()
{
Code code = new Code([new Jeton(Couleur.NOIR)]);
Assert.Throws<CodeCompletException>(() => code.AjouterJeton(new Jeton(Couleur.ROUGE)));
}
[Fact]
public void TestSupprimerDernierJetonValid()
{
Code code = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC)]);
code.SupprimerDernierJeton();
Assert.Equal(2, code.NbJetons);
}
[Fact]
public void TestSupprimerDernierJetonInvalid()
{
Code code = new Code(4);
Assert.Throws<CodeVideException>(() => code.SupprimerDernierJeton());
}
[Fact]
public void TestRecupererJetonValid()
{
Code code = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC)]);
Jeton jetonAttendu = new Jeton(Couleur.BLEU);
Jeton jeton = code.RecupererJeton(1);
Assert.Equal(jetonAttendu.Couleur, jeton.Couleur);
}
[Fact]
public void TestRecupererJetonInvalid()
{
Code code = new Code(4);
Assert.Throws<IndiceCodeException>(() => code.RecupererJeton(-1));
Assert.Throws<IndiceCodeException>(() => code.RecupererJeton(4));
}
[Fact]
public void TestJetonsValid()
{
Jeton[] jetonsAttendus = [new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLEU)];
Code code = new Code(jetonsAttendus);
IEnumerable<Jeton?> lesJetons = code.Jetons();
Assert.Equal(jetonsAttendus.Length, lesJetons.Count());
int index = 0;
foreach (Jeton jetonAttendu in jetonsAttendus)
{
Assert.Equal(jetonAttendu.Couleur, lesJetons.ElementAt(index)?.Couleur);
index++;
}
}
[Fact]
public void TestEstCompletValid()
{
Code code = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC)]);
bool estComplet = code.EstComplet();
Assert.True(estComplet);
}
[Fact]
public void TestEstCompletInvalid()
{
Code code = new Code(3);
bool estComplet = code.EstComplet();
Assert.False(estComplet);
}
[Fact]
public void TestTailleMaximaleValid()
{
Jeton[] jetons = [new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLEU)];
Code code = new Code(jetons);
int tailleMaximale = code.TailleMaximale();
Assert.Equal(jetons.Length, tailleMaximale);
}
[Fact]
public void TestComparerValid()
{
Code code = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC)]);
Code autreCode = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC)]);
IEnumerable<Indicateur> indicateurs = code.Comparer(autreCode);
Assert.Equal(3, indicateurs.Count());
Assert.Contains(Indicateur.BONNEPLACE, indicateurs);
Assert.DoesNotContain(Indicateur.BONNECOULEUR, indicateurs);
}
[Fact]
public void TestComparerGoodPlace()
{
Code code = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC)]);
Code autreCode = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.NOIR)]);
IEnumerable<Indicateur> indicateurs = code.Comparer(autreCode);
Assert.Equal(2, indicateurs.Count());
Assert.Contains(Indicateur.BONNEPLACE, indicateurs);
Assert.DoesNotContain(Indicateur.BONNECOULEUR, indicateurs);
}
[Fact]
public void TestComparerGoodColor()
{
Code code = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC)]);
Code autreCode = new Code([new Jeton(Couleur.BLEU), new Jeton(Couleur.ROUGE), new Jeton(Couleur.NOIR)]);
IEnumerable<Indicateur> indicateurs = code.Comparer(autreCode);
Assert.Equal(2, indicateurs.Count());
Assert.Contains(Indicateur.BONNECOULEUR, indicateurs);
Assert.DoesNotContain(Indicateur.BONNEPLACE, indicateurs);
}
[Fact]
public void TestComparerGoodPlaceAndColor()
{
Code code = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC)]);
Code autreCode = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLANC), new Jeton(Couleur.BLEU)]);
IEnumerable<Indicateur> indicateurs = code.Comparer(autreCode);
Assert.Equal(3, indicateurs.Count());
Assert.Contains(Indicateur.BONNEPLACE, indicateurs);
Assert.Contains(Indicateur.BONNECOULEUR, indicateurs);
}
[Fact]
public void TestComparerNoMatch()
{
Code code = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC)]);
Code autreCode = new Code([new Jeton(Couleur.VERT), new Jeton(Couleur.JAUNE), new Jeton(Couleur.NOIR)]);
IEnumerable<Indicateur> indicateurs = code.Comparer(autreCode);
Assert.Empty(indicateurs);
}
}
}

@ -0,0 +1,20 @@
using CoreLibrary;
using Xunit;
namespace UnitTesting
{
public class JetonUT
{
[Fact]
public void TestConstructorValid()
{
Couleur[] listeCouleurs = (Couleur[])Enum.GetValues(typeof(Couleur));
for (int i=0; i<listeCouleurs.Length; ++i)
{
Jeton jeton = new Jeton(listeCouleurs[i]);
Assert.Equal(listeCouleurs[i], jeton.Couleur);
}
}
}
}

@ -0,0 +1,18 @@
using CoreLibrary;
using Xunit;
namespace UnitTesting
{
public class JoueurUT
{
[Fact]
public void TestConstructorWithValidArguments()
{
Plateau plateau = new Plateau(4, 10);
Joueur joueur = new Joueur("MonJoueur", plateau);
Assert.Equal("MonJoueur", joueur.Nom);
Assert.Equal(plateau, joueur.Plateau);
}
}
}

@ -0,0 +1,130 @@
using CoreLibrary;
using CoreLibrary.Exceptions;
using System.Linq;
using Xunit;
namespace UnitTesting
{
public class PlateauUT
{
[Fact]
public void TestConstructorValid()
{
Plateau plateau = new Plateau(4,12);
Assert.NotNull(plateau);
Assert.Equal(1, plateau.Tour);
Assert.False(plateau.Victoire);
}
[Fact]
public void TestConstructorInvalid()
{
Assert.Throws<TailleCodeException>(() => new Plateau(0, 10));
}
[Fact]
public void TestEstCompletTrue()
{
Plateau plateau = new Plateau(4, 3);
Code code = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC), new Jeton(Couleur.JAUNE)]);
plateau.AjouterCode(code);
plateau.AjouterCode(code);
plateau.AjouterCode(code);
bool estComplet = plateau.EstComplet();
Assert.True(estComplet);
}
[Fact]
public void TestEstCompletFalse()
{
Plateau plateau = new Plateau(4, 3);
Code code = new Code([new Jeton(Couleur.ROUGE), new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC), new Jeton(Couleur.JAUNE)]);
plateau.AjouterCode(code);
plateau.AjouterCode(code);
bool estComplet = plateau.EstComplet();
Assert.False(estComplet);
}
[Fact]
public void TestAjouterCodeValid()
{
Plateau plateau = new Plateau(4, 10);
Code code = new Code([new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC), new Jeton(Couleur.JAUNE), new Jeton(Couleur.BLANC)]);
plateau.AjouterCode(code);
Assert.Equal(2, plateau.Tour);
}
[Fact]
public void TestAjouterCodeIncorrectSize()
{
Plateau plateau = new Plateau(4, 10);
Code code = new Code([new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC), new Jeton(Couleur.JAUNE), new Jeton(Couleur.BLANC), new Jeton(Couleur.JAUNE)]);
Assert.Throws<CodeInvalideException>(() => plateau.AjouterCode(code));
}
[Fact]
public void TestAjouterCodeIncomplete()
{
Plateau plateau = new Plateau(4, 10);
Code code = new Code(4);
Assert.Throws<CodeIncompletException>(() => plateau.AjouterCode(code));
}
[Fact]
public void TestEstBonCodeTrue()
{
}
[Fact]
public void TestEstBonCodeFalse()
{
Plateau plateau = new Plateau(4, 10);
Code code = new Code([new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC), new Jeton(Couleur.JAUNE), new Jeton(Couleur.BLANC)]);
plateau.AjouterCode(code);
Assert.False(plateau.EstBonCode(code));
}
[Fact]
public void TestGrilleValid()
{
Plateau plateau = new Plateau(4, 3);
Code code1 = new Code([new Jeton(Couleur.BLEU), new Jeton(Couleur.BLANC), new Jeton(Couleur.JAUNE), new Jeton(Couleur.BLANC)]);
Code code2 = new Code([new Jeton(Couleur.VERT), new Jeton(Couleur.JAUNE), new Jeton(Couleur.ROUGE), new Jeton(Couleur.NOIR)]);
plateau.AjouterCode(code1);
plateau.AjouterCode(code2);
IEnumerable<IEnumerable<Jeton?>> grille = plateau.Grille();
Assert.Equal(4, grille.First().Count());
Assert.Equal(4, grille.Last().Count());
Assert.Equal(code1.Jetons(), grille.ElementAt(0));
Assert.Equal(code2.Jetons(), grille.ElementAt(1));
}
[Fact]
public void TestGrilleEmpty()
{
Plateau plateau = new Plateau(4, 3);
IEnumerable<IEnumerable<Jeton?>> grille = plateau.Grille();
foreach (IEnumerable<Jeton?> tour in grille)
{
Assert.All(tour, jeton => Assert.Null(jeton));
}
}
}
}

@ -0,0 +1,119 @@
using CoreLibrary;
using CoreLibrary.Exceptions;
using Xunit;
namespace UnitTesting
{
public class ReglesClassiquesUT
{
[Fact]
public void TestConstructor()
{
ReglesClassiques regles = new ReglesClassiques();
Assert.NotNull(regles);
Assert.Equal(0, regles.NbJoueurs);
Assert.Equal(2, regles.NbJoueursMaximum);
}
[Fact]
public void TestAjouterJoueur()
{
ReglesClassiques regles = new ReglesClassiques();
regles.AjouterJoueur("MonJoueur");
Assert.Equal(1, regles.NbJoueurs);
}
[Fact]
public void TestJoueurCourantWithPlayer()
{
ReglesClassiques regles = new ReglesClassiques();
regles.AjouterJoueur("joueur1");
regles.AjouterJoueur("joueur2");
regles.CommencerLaPartie();
Joueur joueurCourant = regles.JoueurCourant();
Assert.NotNull(joueurCourant);
Assert.Equal("joueur1", joueurCourant.Nom);
}
[Fact]
public void TestJoueurCourantNoPlayer()
{
ReglesClassiques regles = new ReglesClassiques();
Assert.Throws<PartieNonCommenceeException>(() => regles.JoueurCourant());
}
[Fact]
public void TestPasserLaMainValid()
{
ReglesClassiques regles = new ReglesClassiques();
regles.AjouterJoueur("joueur1");
regles.AjouterJoueur("joueur2");
regles.CommencerLaPartie();
Joueur joueurCourantInitial = regles.JoueurCourant();
regles.PasserLaMain();
Joueur joueurCourantSuivant = regles.JoueurCourant();
Assert.NotEqual(joueurCourantInitial, joueurCourantSuivant);
Assert.Equal("joueur2", joueurCourantSuivant.Nom);
}
[Fact]
public void TestPasserLaMainInvalid()
{
ReglesClassiques regles = new ReglesClassiques();
Assert.Throws<PartieNonCommenceeException>(() => regles.PasserLaMain());
}
[Fact]
public void TestGenererCode()
{
ReglesClassiques regles = new ReglesClassiques();
Code code = regles.GenererCode();
Assert.NotNull(code);
Assert.Equal(regles.TailleCodeMaximum, code.TailleMaximale());
}
[Fact]
public void TestCommencerLaPartie()
{
ReglesClassiques regles = new ReglesClassiques();
regles.AjouterJoueur("joueur1");
regles.AjouterJoueur("joueur2");
regles.CommencerLaPartie();
Joueur joueurCourant = regles.JoueurCourant();
Assert.NotNull(joueurCourant);
Assert.Equal("joueur1", joueurCourant.Nom);
}
[Fact]
public void TestEstTermineeTrue()
{
//
}
[Fact]
public void TestEstTermineeFalse()
{
ReglesClassiques regles = new ReglesClassiques();
regles.AjouterJoueur("joueur1");
regles.AjouterJoueur("joueur2");
regles.CommencerLaPartie();
bool estTerminee = regles.EstTerminee();
Assert.False(estTerminee);
}
//Test Gagnants et Perdants + TestEstTermineeTrue + TestConstructor PB
}
}

@ -1,4 +1,4 @@
<Project Sdk="Microsoft.NET.Sdk">
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>net8.0</TargetFramework>
@ -22,4 +22,8 @@
</PackageReference>
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\CoreLibrary\CoreLibrary.csproj" />
</ItemGroup>
</Project>

Loading…
Cancel
Save