INFORMATIQUE
TP 7
Jeu de George Noël
Il s'agit d'un jeu de stratégie à 2 joueurs. Le jeu ressemble au Master Mind® en ce sens qu'il faut découvrir une combinaison secrète à 5 chiffres.
Le premier joueur choisit un nombre à 5 chiffres. Ce nombre est la combinaison secrète que l'autre joueur devra découvrir.
Le second joueur fait des propositions successives de nombres à 5 chiffres, jusqu'à ce qu'il trouve la bonne combinaison ou que le nombre maximum d'essais autorisés est atteint. On peut fixer ce nombre maximum à 15 par exemple. Après chaque essai, le premier joueur fournit 2 indications :
- Le nombre de chiffres trop petits (par rapport à la combinaison secrète)
- Le nombre de chiffres trop grands.
Voici un début de partie où la combinaison secrète est 5 6 8 3 3
Combinaison secrète : 5 6 8 3 3 Trop petits Trop grandsEssai n° 1 : 1 2 3 4 5 3 2
Essai n° 2 : 3 4 5 1 2 5 0
Etc... l'objectif étant de trouver la bonne réponse en faisant le moins d'essais possible.
Dans la fiche principale, placer 2 composants StringGrid et 4 boutons.Voici les propriétés de ces composants :
Fiche principale Name fmGeorgeNoel Caption Jeu de George Noël Grille 1 Name grEssais Font Arial, gras, noir, taille 11 ColCount 6 RowCount 16 FixedCols 1 FixedRows 1 Options Grille 2 Name grReponses Font Arial, gras, bleu, taille 11 ColCount 2 RowCount 16 FixedCols 0 FixedRows 1 DefaultColWidth 90 Options Seules les 4 premières sont "true" Bouton 1 Name btNouvellePartie Caption &Nouvelle partie Bouton 2 Name btAbandon Caption &Abandon Bouton 3 Name btQuitter Caption &Quitter Bouton 4 Name btOK Caption &OK Enregistrer tout en créant un nouveau répertoire, dans votre dossier :
Unit1.pas sous le nom uGeorgeNoel.pas
Project1.dpr sous le nom GeorgeNoel.dpr
3. Début d'une nouvelle partie
Sélectionner le bouton " Nouvelle partie " et, dans l'inspecteur d'objets, onglet événements, choisir l'événement On Click puis compléter le texte comme ci-dessous :
var
fmGeorgeNoel: TfmGeorgeNoel;
NumeroEssai : byte;
Combinaison : array[1..5] of 0..9; //Tableau contenant les 5 chiffres à trouverimplementation
{$R *.DFM}
procedure TfmGeorgeNoel.btNouvellePartieClick(Sender: TObject);
var k : byte;
begin
with grEssais do
begin
for k:=0 to 6 do cols[k].clear; //Effacement des 7 colonnes
for k:=1 to 15 do cells[0,k]:=inttostr(k); //On remplit la colonne 0
for k:=1 to 5 do cells[k,0]:=chr(64+k);
//On remplit la ligne 0 avec les lettres A,B,C,D,E de codes 65,66,67,68,69
randomize; //initialisation du générateur de nombres aléatoires
for k:=1 to 5 do Combinaison[k]:=trunc(10*random);
//Fabrication de la combinaison secrète
end;
with grReponses do
begin
for k:=0 to 1 do cols[k].clear;
cells[0,0]:='Trop petits';
cells[1,0]:='Trop grands';
end;
NumeroEssai:=1; //n° du prochain essai
btOK.Enabled:=false;
end;Pour que le lancement d'une nouvelle partie soit automatique au départ, il faut sélectionner l'événement OnActivate de la fiche fmGeorgeNoel et ajouter le code suivant :
procedure TfmGeorgeNoel.FormActivate(Sender: TObject);
begin
btNouvellePartieClick(sender);
end;
4. Comment rendre le bouton OK accessible lorsque l'utilisateur a saisi son essai ?
Il faut faire en sorte que ce bouton ne soit accessible (propriété Enabled=true) uniquement lorsque l'utilisateur a saisi ses 5 chiffres, dans la bonne rangée !
Voici comment procéder (utiliser l'événement On KeyDown de la grille grEssai) :
procedure TfmGeorgeNoel.grEssaisKeyDown(Sender: TObject; var Key: Word;
Shift: TShiftState);
var OK : boolean;
k,n : byte; //un byte est un entier compris entre 0 et 255
err : integer;
ch : string;
begin
OK:=true;
with grEssais do for k:=1 to 5 do
begin
ch:=cells[k,NumeroEssai];
val(ch,n,err);
if (err>0)or(n>9) then OK:=false;
end;
btOK.Enabled:=OK;
end;
5. Réponse à un clic sur le bouton OK
Il s'agit de calculer le nombre de chiffres trop petits (de l'essai du joueur par rapport à la combinaison secrète) et le nombre de chiffres trop grands puis de les afficher dans la grille des réponses.
Le code ci-dessous se passe d'explications :
procedure TfmGeorgeNoel.btOKClick(Sender: TObject);
var k,TP,TG : byte;
begin
TP:=0;TG:=0; //Mise à zéro des compteurs de chiffres
with grEssais do
for k:=1 to 5 do
begin
if StrToInt(cells[k,NumeroEssai])<Combinaison[k] then inc(TP);
if StrToInt(cells[k,NumeroEssai])>Combinaison[k] then inc(TG);
end;
grReponses.Cells[0,NumeroEssai]:=IntToStr(TP);
grReponses.Cells[1,NumeroEssai]:=IntToStr(TG);
inc(NumeroEssai);
grReponses.row:=NumeroEssai;
btOK.Enabled:=false;
end;
6. Amélioration de l'affichage des grilles
Il est dommage que les composants StringGrid n'aient pas de propriété permettant de gérer l'alignement (centré ou à gauche ou à droite) dans chacune des cellules. Pour palier cet inconvénient, il faut utiliser le code suivant :
procedure TfmGeorgeNoel.grEssaisDrawCell(Sender: TObject; ACol,
ARow: Integer; Rect: TRect; State: TGridDrawState);
var ch : string;
begin
ch:=grEssais.cells[ACol,ARow];
with grEssais.Canvas do
begin
brush.Style:=bsSolid;
if (Acol=0)or(ARow=0) then brush.Color:=clSilver
else brush.color:=clWindow;
if (Acol=0)or(ARow=0)
then rectangle(rect.left,rect.top,rect.right,rect.bottom)
else rectangle(rect.left-1,rect.top-1,rect.right+1,rect.bottom+1);
brush.style:=bsClear;
textout((rect.left+rect.right-textwidth(ch))div 2,
(rect.top+rect.bottom-textheight(ch))div 2,ch);
end;
end;procedure TfmGeorgeNoel.grReponsesDrawCell(Sender: TObject; ACol,
ARow: Integer; Rect: TRect; State: TGridDrawState);
var ch : string;
begin
ch:=grReponses.cells[ACol,ARow];
with grReponses.Canvas do
begin
brush.Style:=bsSolid;
if (ARow=0) then brush.Color:=clSilver
else brush.color:=clWindow;
if (ARow=0) then rectangle(rect.left,rect.top,rect.right,rect.bottom)
else rectangle(rect.left-1,rect.top-1,rect.right+1,rect.bottom+1);
brush.style:=bsClear;
textout((rect.left+rect.right-textwidth(ch))div 2,
(rect.top+rect.bottom-textheight(ch))div 2,ch);
end;
end;
7. Gestion des boutons Quitter et Abandon
Pour le bouton Quitter, pas de problème : faire comme d'habitude.
Pour le bouton Abandon : remplir les cellules de la ligne 0 de la grille grEssais avec les 5 chiffres du tableau Combinaison.