Aller au contenu

TP⚓︎

Un jeu de retournement⚓︎

Exercice 1

Le jeu se joue seul, sur un plateau constitué de \(n \times n\) cases carrées. Chaque case est colorée soit en rouge (case « allumée »), soit en blanc (case «éteinte »). Lorsque le joueur choisit une case, elle change de couleur ainsi que les cases ayant un coté commun (ses voisines — au plus 4). Le but du jeu est, en partant d'un plateau entièrement éteint (blanc) d'obtenir un plateau entièrement allumé (rouge).

Réalisation : on imagine une fenêtre carrée de taille pixels de côté, quadrillée en \(n \times n\) cases carrées de même taille. Comme d'habitude, les pixels de la fenêtre sont repérés par leurs coordonnées : le pixel du coin supérieur gauche de la fenêtre a pour coordonnées (0, 0), celui du haut à droite est (taille-1, 0), celui du bas à gauche est (0, taille-1).

Les cases du plateau sont également numérotées par lignes et colonnes (en comptant à partir de 0). Attention, ce n'est pas le même repère que pour les pixels ! Par exemple, la case \((0, n-1)\) correspond à la case en haut à droite (et non à la case en bas à gauche !).

La configuration du plateau est représenté par une liste de listes, dont chaque élément est un int représentant l'état de la case correspondante : par exemple 0 pour une case éteinte (blanche), 1 pour une case allumée (rouge).

from davistk import *

LARGEUR = 400
HAUTEUR = 400
NB_CASES = 5

def init_plateau(n):
    """Initialise une liste de n listes de taille n remplies de 0

    Exemples
    >>> init_plateau(3)
    [[0, 0, 0], [0, 0, 0], [0, 0, 0]]
    >>> init_plateau(2)
    [[0, 0], [0, 0]]
    """
    ...

def gagne(plateau):
    """Détermine si le plateau est gagnant c'est à dire complètement allumé

    Exemples
    >>> gagne([[1, 1], [1, 1]])
    True
    >>> gagne([[1, 1], [1, 0]])
    False
    """
    ...

def pixel_vers_case(x, y):
    """Renvoie le numéro de la ligne et le numéro de la colonne de la case du plateau qui contient ce pixel

    Exemples avec des cases carrés de 80 de côté
    >>> pixel_vers_case(3, 4)
    (0, 0)
    >>> pixel_vers_case(100, 4)
    (1, 0)
    """
    ...

def voisines(i, j):
    """Renvoie une liste des cases voisines de i et j ainsi que la case elle même.

    Exemples
    >>> voisines(1, 0)
    [(1, 0), (0, 0), (2, 0), (1, 1)]
    >>> voisines(2, 2)
    [(2, 2), (2, 1), (2, 3), (1, 2), (3, 2)]
    """
    ...

def inverse(plateau, i, j):
    """Inverse la couleur de la case (i, j) du plateau

    Exemples
    >>> plateau = [[0, 1], [1, 1]]
    >>> inverse(plateau, 0, 0)
    >>> plateau
    [[1, 1], [1, 1]]
    >>> inverse(plateau, 1, 0)
    >>> plateau
    [[1, 1], [0, 1]]
    """
    ...

def dessine_plateau(plateau):
    """Dessine le plateau à l'aide de davistk"""
    ...



cree_fenetre(LARGEUR, HAUTEUR)
plateau = init_plateau(NB_CASES)
while not gagne(plateau):
    dessine_plateau(plateau)
    # On attend le prochain événement
    ev = attend_ev()

    # Si l'événement est de type 'Quitte', on sort de la boucle
    if type_ev(ev) == 'Quitte':
        break
    elif type_ev(ev) == 'ClicGauche':
        i, j = pixel_vers_case(abscisse(ev), ordonnee(ev))
        liste_des_voisines = voisines(i, j)
        for x, y in liste_des_voisines:
            inverse(plateau, x, y)
  1. Écrire une fonction init_plateau(n) qui reçoit un entier n et renvoie une liste de listes représentant un plateau entièrement éteint de n cases de côté.
  2. Écrire une fonction gagne(plateau) qui reçoit une liste de listes représentant un plateau de jeu et renvoie True si toutes les cases sont allumées.
  3. Écrire une fonction pixel_vers_case(x, y) qui reçoit les coordonnées (x, y) d'un pixel et renvoie le numéro de la ligne et le numéro de la colonne de la case du plateau qui contient ce pixel. On pourra supposer que le pixel est bien situé sur une case du plateau.
  4. Écrire une fonction voisines(i, j) qui reçoit le numéro de ligne i et le numéro de colonne j d'une case du plateau et renvoie la liste des coordonnées de ses voisines. On prendra soin de ne renvoyer que des coordonnées de cases réelles !
  5. Écrire une fonction inverse(plateau, i, j) qui reçoit un plateau et les coordonnées d'une case et inverse l'état de cette case et de toutes ses voisines : les cases allumées (représentées par un 1) s'éteignent (passent à 0) et vice-versa.
  6. Écrire une fonction dessine_plateau(plateau) qui reçoit une liste de listes représentant un plateau et dessine ses cases à l'aide du module davistk.
  7. Écrire un programme permettant de jouer une partie complète sur un plateau de \(5 \times 5\) cases.