with Farm ; with Gada.Text_IO ; procedure Mission6 is package F renames Farm ; package Txt renames GAda.Text_IO ; --- Affiche les informations basiques du joueur procedure Affiche_Base (Jeu : F.T_Jeu) is begin Txt.Put_Line("Bienvenue dans Top-Farmer !") ; Txt.New_Line ; Txt.Put_Line(" Score : " & Integer'Image(Jeu.Score)) ; Txt.Put_Line(" Argent : " & Integer'Image(Jeu.Argent) & " chbufs." ) ; Txt.New_Line ; if Jeu.Nombre_Enclos = 0 then Txt.Put_Line(" Aucun enclos.") ; else Txt.Put_Line(" La ferme est composée de " & Integer'Image(Jeu.Nombre_Enclos) & " enclos.") ; end if ; end Affiche_Base ; --- Affiche une grille représentant le plan. procedure Affiche_Plan (Plan : F.T_Plan) is -- Symbole que l'on affiche pour représenter un enclos. Symbole : Character ; Enclos : F.T_Enclos ; begin for Rangee in Plan'Range(1) loop for Col in Plan'Range(2) loop -- Accède à l'enclos situé sur cette rangée et sur cette colonne. Enclos := Plan(Rangee, Col) ; -- Cas particulier : l'enclos est vide. if Enclos.Bebetes = 0 then Symbole := '.' ; else -- Sinon, le symbole cela dépend du type d'animaux. case Plan(Rangee, Col).Animal is when F.Canard => Symbole := 'C' ; when F.Vache => Symbole := 'V' ; when F.Poule => Symbole := 'P' ; when F.Mouton => Symbole := 'M' ; end case ; end if ; Txt.Put(Symbole) ; end loop ; Txt.New_Line ; end loop ; end Affiche_Plan ; procedure Affiche (Jeu : F.T_Jeu) is begin Affiche_Base(Jeu) ; Affiche_Plan(Jeu.Plan) ; end Affiche ; --- Cout des enclos function Cout_Enclos (Aire : Float ; Animal : F.T_Animal) return Integer is Cout_Par_M2 : Float ; begin case Animal is when F.Canard => Cout_Par_M2 := 2.0 ; when F.Vache => Cout_Par_M2 := 6.0 ; when F.Poule => Cout_Par_M2 := 1.5 ; when F.Mouton => Cout_Par_M2 := 4.0 ; end case ; return Integer(Cout_Par_M2 * Aire) ; end Cout_Enclos ; --- Ajoute un enclos si le joueur a assez d'argent. procedure Ajoute_Enclos (Aire : Float ; Animal : F.T_Animal ; Jeu : in out F.T_Jeu ; Ligne : Integer ; Colonne : Integer) is Cout : Integer ; begin Cout := Cout_Enclos(Aire, Animal) ; if Jeu.Argent >= Cout then Jeu.Argent := Jeu.Argent - Cout ; Jeu.Nombre_Enclos := Jeu.Nombre_Enclos + 1 ; Jeu.Plan(Ligne, Colonne) := ( Superficie => Aire, Animal => Animal, Bebetes => 8) ; Txt.Put_Line("Enclos ajouté. Coût = " & Integer'Image(Cout) & " chbufs") ; else Txt.Put_Line("Pas assez d'argent. Coût = " & Integer'Image(Cout) & " chbufs") ; end if ; end Ajoute_Enclos ; --- Calcul du bonus : 100 points par animal. procedure Bonus (Jeu : in out F.T_Jeu) is begin for Rangee in Jeu.Plan'Range(1) loop for Col in Jeu.Plan'Range(2) loop Jeu.Score := Jeu.Score + 100 * Jeu.Plan(Rangee,Col).Bebetes ; end loop ; end loop ; end Bonus ; --- Remplace les canards par des poules. procedure Plus_De_Carnard (Jeu : in out F.T_Jeu) is Enclos : F.T_Enclos ; begin -- Pour chaque enclos, for Ligne in Jeu.Plan'Range(1) loop for Colonne in Jeu.Plan'Range(2) loop -- Quel enclos à ces coordonnées ? Enclos := Jeu.Plan(Ligne, Colonne) ; -- Est-ce un enclos à canards ? case Enclos.Animal is when F.Canard => Enclos.Animal := F.Poule ; Enclos.Bebetes := 1 ; -- On replace l'enclos modifié dans la grille. Jeu.Plan(Ligne, Colonne) := Enclos ; when others => null ; end case ; end loop ; end loop ; end Plus_De_Carnard ; --- Les extra-terrestres clonent les animaux procedure Reproduction (Jeu : in out F.T_Jeu) is Enclos : F.T_Enclos ; Pcent : Integer ; begin for Ligne in Jeu.Plan'Range(1) loop for Colonne in Jeu.Plan'Range(2) loop -- Pour chaque enclos peuplé, ... Enclos := Jeu.Plan(Ligne, Colonne) ; if Enclos.Bebetes > 0 then -- Faire croître le nombre de bebêtes. case Enclos.Animal is when F.Poule => Pcent := 100 ; when F.Canard => Pcent := 80 ; when F.Vache => Pcent := 40 ; when F.Mouton => Pcent := 60 ; end case ; Enclos.Bebetes := (Enclos.Bebetes * (100 + Pcent)) / 100 ; -- On remet bien l'enclos dans le plan. Jeu.Plan(Ligne, Colonne) := Enclos ; end if ; end loop ; end loop ; end Reproduction ; --- Fabrique une liste des enclos. function Lister(Jeu : F.T_Jeu) return F.T_Liste_Enclos is Resultat : F.T_Liste_Enclos(1..Jeu.Nombre_Enclos) ; -- Cette variable indique combien d'enclos ont déjà été mis dans la liste. Compte : Integer := 0 ; begin -- Parcours du plan for Ligne in Jeu.Plan'Range(1) loop for Colonne in Jeu.Plan'Range(2) loop if Jeu.Plan(Ligne, Colonne).Bebetes > 0 then -- Un enclos non vide Compte := Compte + 1 ; Resultat(Compte) := Jeu.Plan(Ligne, Colonne) ; end if ; end loop ; end loop ; return Resultat ; end Lister ; --- Afficher les enclos de la liste procedure Afficher_Liste (Liste : F.T_Liste_Enclos) is Enclos : F.T_Enclos ; begin for Index in Liste'Range loop Enclos := Liste(Index) ; Txt.Put_Line( "Enclos " & Integer'Image(Index) & " : " & Integer'Image(Enclos.Bebetes) & " " & F.T_Animal'Image(Enclos.Animal) & "(s)") ; end loop ; end Afficher_Liste ; --- Enclos peuplé avec le moins d'animaux. function Min_Enclos (Liste : F.T_Liste_Enclos) return Integer is Enclos : F.T_Enclos ; Min_Animaux : Integer := Integer'Last ; Indice_Min : Integer ; begin for Index in Liste'Range loop Enclos := Liste(Index) ; if Enclos.Bebetes < Min_Animaux then Min_Animaux := Enclos.Bebetes ; Indice_Min := Index ; end if ; end loop ; return Indice_Min ; end Min_Enclos ; --- Trouver une rangée vide function Rangee_Vide (Jeu : F.T_Jeu) return Integer is Trouve : Boolean := False ; No_Rangee : Integer := Jeu.Plan'First(1) ; Resultat : Integer ; begin -- Algorithme de recherche : trouver une rangée vide. while (not Trouve) and No_Rangee <= Jeu.Plan'Last(1) loop -- Si la première case (enclos) est vide, la rangée est vide. if Jeu.Plan(No_Rangee, 1).Bebetes = 0 then Resultat := No_Rangee ; Trouve := True ; else No_Rangee := No_Rangee + 1 ; end if ; end loop ; if not Trouve then Resultat := -1 ; end if ; return Resultat ; end Rangee_Vide ; --- --- Calcul du bonus assorti (en plusieurs étapes) --- -- Détecte si une rangée est assortie. function Assortie (Plan : F.T_Plan ; Rangee : Integer) return Boolean is Resultat : Boolean ; Total : Integer := 0 ; begin -- On vérifie d'abord que la rangée n'a pas d'enclos vide. -- (Il suffit de vérifier que le dernier enclos n'est pas vide) Resultat := ( Plan(Rangee, Plan'Last(2)).Bebetes > 0 ) ; if Resultat then -- Pour vérifier si tous les animaux sont présents, on ajoute des points par type d'animaux -- 1 pour les poules, 10 pour les moutons, 100 pour les vaches, 1000 pour les canards. -- Tous les animaux sont présents si le total est égal à 1111. for Col in Plan'Range(2) loop case Plan(Rangee, Col).Animal is when F.Poule => Total := Total + 1 ; when F.Mouton => Total := Total + 10 ; when F.Vache => Total := Total + 100 ; when F.Canard => Total := Total + 1000 ; end case ; end loop ; Resultat := (Total = 1111) ; end if ; return Resultat ; end Assortie ; -- Compte le nombre de rangées assorties function Nb_Assorties (Jeu : F.T_Jeu) return Integer is Compte : Integer := 0 ; begin for Rangee in Jeu.Plan'Range(1) loop if Assortie(Jeu.Plan, Rangee) then Compte := Compte + 1 ; end if ; end loop ; return Compte ; end Nb_Assorties ; -- Ajoute le bonus des rangées assorties procedure Bonus_Assorti (Jeu : in out F.T_Jeu) is Bonus : Integer ; begin case Nb_Assorties(Jeu) is when 0 => Bonus := 0 ; when 1 => Bonus := 5_000 ; when 2 => Bonus := 20_000 ; when 3 => Bonus := 30_000 ; when 4 => Bonus := 50_000 ; when 5 => Bonus := 80_000 ; when 6 => Bonus := 100_000 ; when others => Bonus := 0 ; --- ce cas ne devrait pas arriver end case ; Jeu.Score := Jeu.Score + Bonus ; end Bonus_Assorti ; --- Trois variables pour tester Enclos_Vide : F.T_Enclos := ( Superficie => 100.0, Animal => F.Poule, Bebetes => 0 ) ; Plan_Initial : F.T_Plan(1..6, 1..4) := (others => (others => Enclos_Vide)) ; Jeu : F.T_Jeu := ( Score => 0, Argent => 8000, Nombre_Enclos => 0, Plan => Plan_Initial ) ; begin -- Jeu initial Affiche_Base(Jeu) ; Affiche_Plan(Jeu.Plan) ; -- On ajoute quelques enclos Ajoute_Enclos(100.0, F.Poule, Jeu, 1, 1) ; Ajoute_Enclos(100.0, F.Poule, Jeu, 1, 2) ; Ajoute_Enclos(200.0, F.Canard, Jeu, 2, 1) ; Ajoute_Enclos(200.0, F.Vache, Jeu, 4, 1) ; Ajoute_Enclos(100.0, F.Mouton, Jeu, 4, 2) ; Ajoute_Enclos(100.0, F.Poule, Jeu, 4, 3) ; Ajoute_Enclos(100.0, F.Canard, Jeu, 6, 1) ; Ajoute_Enclos(100.0, F.Mouton, Jeu, 6, 2) ; Ajoute_Enclos(5000.0, F.Mouton, Jeu, 6, 4) ; Bonus(Jeu) ; Affiche(Jeu) ; -- Canard => Poule Plus_De_Carnard(Jeu) ; Affiche(Jeu) ; -- Multiplication des bebetes Reproduction(Jeu) ; Bonus(Jeu) ; Affiche(Jeu) ; Afficher_Liste( Lister(Jeu) ) ; -- L'enclos le moins peuplé Txt.Put_Line("Enclos le moins peuplé : " & Integer'Image(Min_Enclos( Lister(Jeu) ))) ; -- Rangee vide Txt.Put_Line("Une rangée vide : " & Integer'Image( Rangee_Vide(Jeu))) ; -- Test des rangées assorties Ajoute_Enclos(100.0, F.Canard, Jeu, 4,4) ; -- Une rangée assortie Bonus_Assorti(Jeu) ; Affiche(Jeu) ; -- Et une deuxième Ajoute_Enclos(100.0, F.Canard, Jeu, 6,3) ; Ajoute_Enclos(100.0, F.Vache, Jeu, 6,4) ; Bonus_Assorti(Jeu) ; Affiche(Jeu) ; end Mission6 ;