IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Tkinter Python Discussion :

Problème projet ISN BAC


Sujet :

Tkinter Python

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Avril 2019
    Messages
    4
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Avril 2019
    Messages : 4
    Par défaut Problème projet ISN BAC
    Bonjour,

    Nous avons décidé de réaliser un casse brique en Python à l'aide module Tkinter.
    Seulement voilà plusieurs jours que nous sommes bloqué sur un point. En effet la balle rebondit correctement sur la longueur de chaque rectangles (constituant les briques) mais pas sur la largeur. Cela implique plusieurs bugs puisque la balle entre à l'intérieur des rectangles tout en rebondissant sur la longueur de ces derniers.

    Pouvez-vous m'aider à résoudre ce problème, je n'arrive vraiment pas à comprendre pourquoi la balle rebondit bien sur la longueur mais pas la largeur alors que j'ai utilisé le même procédé que pour la longueur.

    PS : Nous n'avons pas l'autorisation d'utiliser le module PyGame.

    Voici le programme (j'ai joint l'ensemble des images et .txt nécessaire à l'exécution) : https://drive.google.com/drive/folde...H8?usp=sharing

    niveau.txtNom : BV.gif
Affichages : 221
Taille : 4,9 KoNom : BR.gif
Affichages : 226
Taille : 4,4 KoNom : BJ.gif
Affichages : 232
Taille : 3,9 KoThe Py Breaker.pyNom : Background.gif
Affichages : 253
Taille : 622,5 Ko

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
    138
    139
    140
    141
    142
    143
    144
    145
    146
    147
    148
    149
    150
    151
    152
    153
    154
    155
    156
    157
    158
    159
    160
    from tkinter import *
     
    #INITIALISATION FENETRE + FOND
     
    fenetre =Tk()
    fenetre.title("The Py Breaker !")
    fenetre.geometry("1100x800")
     
    Fond=Canvas(fenetre,width=1100,height=800,bg="black")
    Fond.place(x=0,y=0)
     
    Background=PhotoImage(file="Background.gif")
    Fond.create_image(0,0,image=Background,anchor="nw")
     
    #INITIALISATION DU NIVEAU
     
    #1
    BV=PhotoImage(file="BV.gif")
    x,y=0,0
    fichier=open('niveau.txt')
    V=[]
     
    for ligne in fichier:
        for i in range(11): #Nb. caractères dans une ligne
            case=ligne[i]
            if case=="V":
                Fond.create_image(x,y,image=BV,anchor="nw")
                a=Fond.create_rectangle(x,y,x+99,y+49,outline="green")
                V.append(a)
            x=x+100
        x=0
        y=y+100
     
    #2
    BJ=PhotoImage(file="BJ.gif")
    x,y=0,0
    fichier=open('niveau.txt')
    J=[]
     
    for ligne in fichier:
        for i in range(11): #Nb. caractères dans une ligne
            case=ligne[i]
            if case=="J":
                Fond.create_image(x,y,image=BJ,anchor="nw")
                b=Fond.create_rectangle(x,y,x+99,y+49,outline="yellow")
                J.append(b)
            x=x+100
        x=0
        y=y+100
     
    #3
    BR=PhotoImage(file="BR.gif")
    x,y=0,0
    fichier=open('niveau.txt')
    R=[]
     
    for ligne in fichier:
        for i in range(11): #Nb. caractères dans une ligne
            case=ligne[i]
            if case=="R":
                Fond.create_image(x,y,image=BR,anchor="nw")
                c=Fond.create_rectangle(x,y,x+99,y+49,outline="red")
                R.append(c)
            x=x+100            
        x=0
        y=y+100
     
    #INITIALISATION BARRE
     
    Barre=Fond.create_rectangle(480,775,620,750,fill="black")
     
     
    #INITIALISATION BALLE
     
    Balle=Fond.create_oval(530,720,560,750,fill='red')
     
    #REBODNDS BORDS ECRAN
     
    def deplacement():
        global dx,dy
        if Fond.coords(Balle)[3]<=0:
            dy=-1*dy
        if (Fond.coords(Balle)[1]>800):
            dy=-1*dy
        if (Fond.coords(Balle)[0]<0) or (Fond.coords(Balle)[2]>1100):
            dx=-1*dx
     
     
    #REBONDS BRIQUES VERTES
     
        if (Fond.coords(Balle)[1]<Fond.coords(V[0])[3]) and (Fond.coords(Balle)[0]<Fond.coords(V[0])[2]) and (Fond.coords(Balle)[2]>Fond.coords(V[0])[0]) and (Fond.coords(Balle)[3]>Fond.coords(V[0])[1]): 
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(V[1])[3]) and (Fond.coords(Balle)[0]<Fond.coords(V[1])[2]) and (Fond.coords(Balle)[2]>Fond.coords(V[1])[0]) and (Fond.coords(Balle)[3]>Fond.coords(V[1])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(V[2])[3]) and (Fond.coords(Balle)[0]<Fond.coords(V[2])[2]) and (Fond.coords(Balle)[2]>Fond.coords(V[2])[0]) and (Fond.coords(Balle)[3]>Fond.coords(V[2])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(V[3])[3]) and (Fond.coords(Balle)[0]<Fond.coords(V[3])[2]) and (Fond.coords(Balle)[2]>Fond.coords(V[3])[0]) and (Fond.coords(Balle)[3]>Fond.coords(V[3])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(V[4])[3]) and (Fond.coords(Balle)[0]<Fond.coords(V[4])[2]) and (Fond.coords(Balle)[2]>Fond.coords(V[4])[0]) and (Fond.coords(Balle)[3]>Fond.coords(V[4])[1]):
                dy=-1*dy
     
    #REBONDS BRIQUES JAUNES
     
        if (Fond.coords(Balle)[1]<Fond.coords(J[0])[3]) and (Fond.coords(Balle)[0]<Fond.coords(J[0])[2]) and (Fond.coords(Balle)[2]>Fond.coords(J[0])[0]) and (Fond.coords(Balle)[3]>Fond.coords(J[0])[1]): 
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(J[1])[3]) and (Fond.coords(Balle)[0]<Fond.coords(J[1])[2]) and (Fond.coords(Balle)[2]>Fond.coords(J[1])[0]) and (Fond.coords(Balle)[3]>Fond.coords(J[1])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(J[2])[3]) and (Fond.coords(Balle)[0]<Fond.coords(J[2])[2]) and (Fond.coords(Balle)[2]>Fond.coords(J[2])[0]) and (Fond.coords(Balle)[3]>Fond.coords(J[2])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(J[3])[3]) and (Fond.coords(Balle)[0]<Fond.coords(J[3])[2]) and (Fond.coords(Balle)[2]>Fond.coords(J[3])[0]) and (Fond.coords(Balle)[3]>Fond.coords(J[3])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(J[4])[3]) and (Fond.coords(Balle)[0]<Fond.coords(J[4])[2]) and (Fond.coords(Balle)[2]>Fond.coords(J[4])[0]) and (Fond.coords(Balle)[3]>Fond.coords(J[4])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(J[5])[3]) and (Fond.coords(Balle)[0]<Fond.coords(J[5])[2]) and (Fond.coords(Balle)[2]>Fond.coords(J[5])[0]) and (Fond.coords(Balle)[3]>Fond.coords(J[5])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(J[6])[3]) and (Fond.coords(Balle)[0]<Fond.coords(J[6])[2]) and (Fond.coords(Balle)[2]>Fond.coords(J[6])[0]) and (Fond.coords(Balle)[3]>Fond.coords(J[6])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(J[7])[3]) and (Fond.coords(Balle)[0]<Fond.coords(J[7])[2]) and (Fond.coords(Balle)[2]>Fond.coords(J[7])[0]) and (Fond.coords(Balle)[3]>Fond.coords(J[7])[1]):
                dy=-1*dy
     
    #REBONDS BRIQUES ROUGES
     
        if (Fond.coords(Balle)[1]<Fond.coords(R[0])[3]) and (Fond.coords(Balle)[0]<Fond.coords(R[0])[2]) and (Fond.coords(Balle)[2]>Fond.coords(R[0])[0]) and (Fond.coords(Balle)[3]>Fond.coords(R[0])[1]): 
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(R[1])[3]) and (Fond.coords(Balle)[0]<Fond.coords(R[1])[2]) and (Fond.coords(Balle)[2]>Fond.coords(R[1])[0]) and (Fond.coords(Balle)[3]>Fond.coords(R[1])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(R[2])[3]) and (Fond.coords(Balle)[0]<Fond.coords(R[2])[2]) and (Fond.coords(Balle)[2]>Fond.coords(R[2])[0]) and (Fond.coords(Balle)[3]>Fond.coords(R[2])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(R[3])[3]) and (Fond.coords(Balle)[0]<Fond.coords(R[3])[2]) and (Fond.coords(Balle)[2]>Fond.coords(R[3])[0]) and (Fond.coords(Balle)[3]>Fond.coords(R[3])[1]):
                dy=-1*dy
        if (Fond.coords(Balle)[1]<Fond.coords(R[4])[3]) and (Fond.coords(Balle)[0]<Fond.coords(R[4])[2]) and (Fond.coords(Balle)[2]>Fond.coords(R[4])[0]) and (Fond.coords(Balle)[3]>Fond.coords(R[4])[1]):
                dy=-1*dy
     
    #REBONDS SUR BARRE
     
        if (Fond.coords(Balle)[3]>Fond.coords(Barre)[1]) and (Fond.coords(Balle)[0]<Fond.coords(Barre)[2]) and (Fond.coords(Balle)[2]>Fond.coords(Barre)[0]):
            dy=-1*dy
     
        Fond.move(Balle,dx,dy)
        fenetre.after(1,deplacement)
     
    dx=-2
    dy=-10
     
    #DEPLACEMENT BARRE
     
    def droite(event):
        Fond.move(Barre,15,0)
     
    def gauche(event):
        Fond.move(Barre,-15,0)
     
    Fond.bind_all('<Right>',droite)
    Fond.bind_all('<Left>',gauche)
     
    #LANCEMENT DU JEU
     
    fichier.close()
    deplacement()
    fenetre.mainloop()

  2. #2
    Membre très actif

    Homme Profil pro
    Bidouilleur
    Inscrit en
    Avril 2016
    Messages
    721
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Bidouilleur

    Informations forums :
    Inscription : Avril 2016
    Messages : 721
    Billets dans le blog
    1
    Par défaut
    Salut.

    La première chose est qu'il faut vraiment apprendre à se servir de boucles et d'itérables (list, dict).
    Pourquoi faire en X fois ce qui peut se faire en une seule ? La lecture de ton fichier et la construction des briques doit se faire en une fois.
    Les tests de collisions sur les briques doivent aussi s'effectuer dans une boucle, il n'est pas envisageable de continuer comme tu as fait.

    Le test de collision justement :
    On regarde d'abord si le prochain y et y2 de la balle entre en collision avec une brique, si c'est le cas, on regarde si le x ou x2 de la balle est dans l'intervalle x, x2 de la brique, si oui, on inverse le dy, si non, on regarde alors si le porchain x ou x2 de la balle se situera dans l'intervalle x, x2 de la brique, si oui, on inverse le dx, et hop voilà le tour est joué.

    Voici un exemple de ce à quoi ton code devrait ressembler.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    from tkinter import *
     
    fenetre = Tk()
    fenetre.title("The Py Breaker !")
    fenetre.geometry("1100x800")
     
    can = Canvas(fenetre, width=1100, height=800, bg="black")
    can.grid()
     
    Background = PhotoImage(file="Background.gif")
    can.create_image(0, 0, image=Background, anchor="nw")
     
     
    ATTRIBUTS_BRIQUES = dict(
        V=dict(image=PhotoImage(file="BV.gif"), couleur="vert"),
        J=dict(image=PhotoImage(file="BJ.gif"), couleur="jaune"),
        R=dict(image=PhotoImage(file="BR.gif"), couleur="rouge"),
    )
     
    briques = {}
     
    with open("niveau.txt") as fichier:
        y = 0
        for ligne in fichier:
            x = 0
            for car in ligne:
                if car in ATTRIBUTS_BRIQUES:
                    iid = can.create_image(
                        x, y, image=ATTRIBUTS_BRIQUES[car]["image"], anchor="nw"
                    )
                    coords = can.bbox(iid)
                    briques[iid] = dict(coords=coords)
                x += 100
            y += 100
     
     
    coords_balle = [530, 720, 560, 750]
    balle = can.create_oval(coords_balle, fill="red")
     
     
    def deplacer_balle(dx, dy):
        if coords_balle[1] + dy < 0 or coords_balle[3] + dy > 800:
            dy *= -1
        elif coords_balle[0] + dx < 0 or coords_balle[2] + dx > 1100:
            dx *= -1
        else:
            for iid in briques:
                coords = briques[iid]["coords"]
                # Si le prochain y ou y2 de la balle sera en collision avec la brique
                if (
                    coords[1] <= coords_balle[1] + dy <= coords[3]
                    or coords[1] <= coords_balle[3] + dy <= coords[3]
                ):
                    # Si le x ou x2 de la balle est DÉJÀ à l'intérieur de la brique
                    if (
                        coords[0] <= coords_balle[0] <= coords[2]
                        or coords[0] <= coords_balle[2] <= coords[2]
                    ):
                        dy *= -1
                        break
                    # Si le prochain x ou x2 de la balle sera à l'intérieur de la brique
                    elif (
                        coords[0] <= coords_balle[0] + dx <= coords[2]
                        or coords[0] <= coords_balle[2] + dx <= coords[2]
                    ):
                        dx *= -1
                        break
        # Mise à jour des coordonnées de la balle
        coords_balle[0] += dx
        coords_balle[2] += dx
        coords_balle[1] += dy
        coords_balle[3] += dy
        # Mise à jour de la position de la balle sur le canvas
        can.coords(balle, coords_balle)
        can.after(10, deplacer_balle, dx, dy)
     
     
    deplacer_balle(-2, -10)
     
    fenetre.mainloop()
    Maintenant, il faut y ajouter la raquette, la gestion de la collision de celle-ci avec la balle, destruction des briques, cela devrait être un jeu d'enfant.

  3. #3
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Avril 2019
    Messages
    4
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Avril 2019
    Messages : 4
    Par défaut
    Tout d'abord merci beaucoup pour ton aide, en effet c'est beaucoup plus claire et simple de cette manière. Je vais travailler sur l'ajout de la raquette en revanche je pense que je vais avoir quelques problèmes en m'attaquant à la destruction des briques lorsque celles-ci sont touchées. Pourrais-tu m'en dire plus à ce sujet ? J'ai pensé a détruire le Canvas de chaque brique mais je ne sais pas comment faire cela pour une brique donnée mais aussi faire en sorte que le programme ne prenne plus en compte ses coordonnées pour ne plus que la balle rebondisse dessus.

    Cordialement,
    Hugo B.

  4. #4
    Membre très actif

    Homme Profil pro
    Bidouilleur
    Inscrit en
    Avril 2016
    Messages
    721
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Bidouilleur

    Informations forums :
    Inscription : Avril 2016
    Messages : 721
    Billets dans le blog
    1
    Par défaut
    Salut.

    Citation Envoyé par hugobsh Voir le message
    en revanche je pense que je vais avoir quelques problèmes en m'attaquant à la destruction des briques lorsque celles-ci sont touchées. Pourrais-tu m'en dire plus à ce sujet ? J'ai pensé a détruire le Canvas de chaque brique mais je ne sais pas comment faire cela pour une brique donnée mais aussi faire en sorte que le programme ne prenne plus en compte ses coordonnées pour ne plus que la balle rebondisse dessus.
    Pour faire cela, c'est plus que simple, on crée un fonction supprimer_brique devant recevoir l'identifiant de la brique à supprimer (iid), dans le corps de celle-ci, on supprime la brique sur le canvas à l'aide de la méthode delete de Canvas, puis on supprime également l'item du dictionnaire briques en utilisant l'instruction (fonction) del de python.
    Cela fait, il ne reste plus qu'à appeler cette fonction lorsqu'une collision avec une brique est détectée (lors des inversions de pas).

  5. #5
    Membre à l'essai
    Homme Profil pro
    Étudiant
    Inscrit en
    Avril 2019
    Messages
    4
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Moselle (Lorraine)

    Informations professionnelles :
    Activité : Étudiant

    Informations forums :
    Inscription : Avril 2019
    Messages : 4
    Par défaut
    Citation Envoyé par bistouille Voir le message
    Salut.



    Pour faire cela, c'est plus que simple, on crée un fonction supprimer_brique devant recevoir l'identifiant de la brique à supprimer (iid), dans le corps de celle-ci, on supprime la brique sur le canvas à l'aide de la méthode delete de Canvas, puis on supprime également l'item du dictionnaire briques en utilisant l'instruction (fonction) del de python.
    Cela fait, il ne reste plus qu'à appeler cette fonction lorsqu'une collision avec une brique est détectée (lors des inversions de pas).
    Salut,

    Encore merci pour ton aide, j'ai eu pas mal de temps pour améliorer le programme et évidement j'ai rencontré d'autres problèmes. Désormais j'ai essayer de faire en sorte que la balle prenne une direction différente selon l'endroit ou elle rebondit sur la raquette mais cela n'as pas l'air de fonctionner correctement, je pense que c'est indispensable sinon le jeu est monotone...

    Je pense qu'il y a des améliorations à faire c'est pour cela que je reviens vers vous car j'ai à peine les bases en Python et je trouve le programme un déjà un peu complexe, j'aimerais simplifier le tout.
    J'ai ajouter un système de score, un message lorsque le joueur à perdu mais pour l'instant toujours rien quand le joueur gagne. Il reste aussi a faire la résistance des briques mais j'avoue que j'ai du mal à m'y mettre.

    Voici le programme au jour d'aujourd'hui:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    26
    27
    28
    29
    30
    31
    32
    33
    34
    35
    36
    37
    38
    39
    40
    41
    42
    43
    44
    45
    46
    47
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
    58
    59
    60
    61
    62
    63
    64
    65
    66
    67
    68
    69
    70
    71
    72
    73
    74
    75
    76
    77
    78
    79
    80
    81
    82
    83
    84
    85
    86
    87
    88
    89
    90
    91
    92
    93
    94
    95
    96
    97
    98
    99
    100
    101
    102
    103
    104
    105
    106
    107
    108
    109
    110
    111
    112
    113
    114
    115
    116
    117
    118
    119
    120
    121
    122
    123
    124
    125
    126
    127
    128
    129
    130
    131
    132
    133
    134
    135
    136
    137
    138
    139
    140
    141
    142
    143
    144
    145
    146
    147
    148
    149
    150
    151
    152
    153
    154
    155
    156
    157
    158
    159
    160
    161
    162
    163
    164
    165
    from tkinter import *
     
    fenetre = Tk()
    fenetre.title("The Py Breaker !")
    fenetre.geometry("1100x800")
     
    can = Canvas(fenetre, width=1100, height=800, bg="black")
    can.grid()
     
    Background = PhotoImage(file="Background.gif")
    can.create_image(0, 0, image=Background, anchor="nw")
     
     
    ATTRIBUTS_BRIQUES = dict(
        V=dict(image=PhotoImage(file="BV.gif"), couleur="vert"),
        J=dict(image=PhotoImage(file="BJ.gif"), couleur="jaune"),
        R=dict(image=PhotoImage(file="BR.gif"), couleur="rouge"),
    )
     
    briques = {}
     
    with open("niveau.txt") as fichier:
        y = 0
        for ligne in fichier:
            x = 0
            for car in ligne:
                if car in ATTRIBUTS_BRIQUES:
                    iid = can.create_image(
                        x, y, image=ATTRIBUTS_BRIQUES[car]["image"], anchor="nw")
                    coords = can.bbox(iid)
                    briques[iid] = dict(coords=coords)
                x += 100
            y += 100
     
    #Temporisation entre deux boucle
    temp = 15
     
    deplacementX = -2
    deplacementY = 15
     
    coords_balle = [530, 720, 560, 750]
    balle = can.create_oval(coords_balle, fill="red")
     
    coords_barre =  [480, 775, 620, 750]
    barre = can.create_rectangle(coords_barre, fill="black")
     
    #boolean permettant de connaitre direction sur l'axe Y de la balle
    balle_deplacement_vers_haut = True
    #boolean permettant de connaitre direction sur l'axe X de la balle
    balle_deplacement_vers_gauche = True
     
    score = 0
     
    #DEPLACEMENT BALLE
    def deplacer_balle(dx, dy):
        global balle_deplacement_vers_haut
        global balle_deplacement_vers_gauche
        global score
     
        #Rebonds bords de l'écran
        if coords_balle[1] + dy < 0 or coords_balle[3] + dy > 800:
            dy*= -1
        elif coords_balle[0] + dx < 0 or coords_balle[2] + dx > 1100:
            dx*= -1
     
        #Rebonds raquette
        if (
                coords_balle[1] + dy >= coords_barre[3]
            and 
                not balle_deplacement_vers_haut
        ):
            balle_touche_barre = False
            balle_touche_coin_gauche = (coords_balle[0] + dx < coords_barre[0] and coords_balle[2] + dx > coords_barre[0])
            balle_touche_coin_droite = (coords_balle[2] + dx > coords_barre[2] and coords_balle[0] + dx < coords_barre[2])
            balle_touche_dans_barre = (coords_balle[0] + dx >= coords_barre[0] and coords_balle[2] + dx <= coords_barre[2])
            if (
                    (balle_touche_coin_gauche or balle_touche_coin_droite) 
                and 
                    not balle_touche_dans_barre 
            ):
                balle_touche_barre = True
                if (not balle_deplacement_vers_gauche and balle_touche_coin_gauche and not balle_touche_coin_droite):
                    dx = deplacementX
                    balle_deplacement_vers_gauche = True
                elif (balle_deplacement_vers_gauche and not balle_touche_coin_gauche and balle_touche_coin_droite):
                    dx = deplacementX*-1
                    balle_deplacement_vers_gauche = False
     
            if (balle_touche_barre or balle_touche_dans_barre): 
                dy*=-1
                balle_deplacement_vers_haut = True
            #Perdu
            elif (coords_balle[2] + dy <= coords_barre[1]):
                textscore = "Score : %s points" % (score)
                can.create_text(550, 400, text="Perdu", fill='RED', font='Arial 45 bold')
                can.create_text(550, 450, text=textscore, fill='RED', font='Arial 45 bold')
                return
     
     
        #Rebonds briques
        else:
            for iid in briques:
                coords = briques[iid]["coords"]
                # Si le prochain y ou y2 de la balle sera en collision avec la brique
                if (
                        coords[1] <= coords_balle[1] + dy <= coords[3] 
                    or 
                        coords[1] <= coords_balle[3] + dy <= coords[3]
                ):
                    balle_deplacement_vers_haut = False
                    # Si le x ou x2 de la balle est DÉJÀ à l'intérieur de la brique
                    if (
                            coords[0] <= coords_balle[0] <= coords[2]
                        or 
                            coords[0] <= coords_balle[2] <= coords[2]
                    ):
                        dy *= -1
                        suprimer_brique(iid)
                        score += 10
                        break
                    # Si le prochain x ou x2 de la balle sera à l'intérieur de la brique
                    elif (
                            coords[0] <= coords_balle[0] + dx <= coords[2]
                        or 
                            coords[0] <= coords_balle[2] + dx <= coords[2]
                    ):
                        dx *= -1
                        suprimer_brique(iid)
                        score += 10
                        break
     
        #Mise à jour des coordonnées de la balle
        coords_balle[0] += dx
        coords_balle[1] += dy
        coords_balle[2] += dx 
        coords_balle[3] += dy 
        #Mise à jour de la position de la balle sur le canvas
        can.coords(balle, coords_balle)
        can.after(temp, deplacer_balle, dx, dy)
     
    #DEPLACEMENT RAQUETTE
    def droite(event):
        can.move(barre,15,0)
        #Mise à jour des coordonnées de la barre
        coords_barre[0] += 15
        coords_barre[2] += 15
     
    def gauche(event):
        can.move(barre,-15,0)
        #mise a jour des coordonnées de la barre
        coords_barre[0] -= 15
        coords_barre[2] -= 15
     
    #DESTRUCTION BRIQUES
    def suprimer_brique(iid):
        can.delete(iid) #On supprime le canvas
        del(briques[iid]) #On supprime les coordonnées du canvas
     
    can.bind_all("<Right>", droite)
    can.bind_all("<Left>", gauche)
     
    #LANCEMENT DU JEU
    deplacer_balle(deplacementX, deplacementY)
     
    fenetre.mainloop()
    Cordialement,
    Hugo B.

  6. #6
    Membre très actif

    Homme Profil pro
    Bidouilleur
    Inscrit en
    Avril 2016
    Messages
    721
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Bidouilleur

    Informations forums :
    Inscription : Avril 2016
    Messages : 721
    Billets dans le blog
    1
    Par défaut
    Salut.

    Faire varier l'angle en fonction de l'endroit de la raquette que la balle percute peut se calculer simplement en se basant sur la position centrale de ces 2 éléments, de multiplier leur différence par une valeur et l'ajouter au dx de base, bon je suis nul en maths et en jargon mathématique, comme tu es étudiant, tu dois être bien meilleur que moi et un peu deviner à quoi je fais allusion. Et en effet, il y a trop de choses compliquées dans ton code, des variables inutiles balle_deplacement_vers_haut, balle_deplacement_vers_bas, etc, dont je n'ai pas bien compris l'utilité, ton code de collision avec la raquette en gros pourrait se résumer à faire.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    balle_centre_x = coords_balle[0] + (coords_balle[2] - coords_balle[0]) / 2
    raquette_centre_x = coords_barre[0] + (coords_barre[2] - coords_barre[0]) / 2
    distx = balle_centre_x - raquette_centre_x
    # 2 est le déplacement de base, 0.12 une valeur à ajuster afin d'obtenir un angle potable
    dx = 2 * distx * 0.12
    Note que pour détecter la collision avec la raquette, il faut regarder comme tu as fait si le prochain déplacement percute celle-ci en y, mais il faut également regarder si c'est aussi le cas pour l'abscisse.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    if (
        coords_balle[3] + dy >= coords_barre[1] and 
        (
            coords_barre[0] <= coords_balle[0] + dx <= coords_barre[2] or
            coords_barre[0] <= coords_balle[2] + dx <= coords_barre[2]
        )
    ) :
        # code
    Il est aussi préférable de modifier le score dans une autre fonction que celle du déplacement de la balle, si les briques ont des résistances différentes, alors on peut ajouter dans les propriétés des briques un item aux dictionnaires correspondant à cette résistance.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    ATTRIBUTS_BRIQUES = dict(
        V=dict(image=PhotoImage(file="BV.gif"), couleur="vert", resistance=1),
        J=dict(image=PhotoImage(file="BJ.gif"), couleur="jaune", resistance=2),
        R=dict(image=PhotoImage(file="BR.gif"), couleur="rouge", resistance=3),
    )
    Puis d'ajouter cet item lors de la boucle de construction.

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    briques[iid] = dict(coords=coords, resistance=ATTRIBUTS_BRIQUES[car]['resistance'])
    Et ensuite, lors du test des collisions de la balle avec une brique, on n'appellerait plus la fonction supprimer_brique, mais une autre fonction (à créer), par ex. actualiser_brique laquelle décrémenterait la résistance de la brique (identifiant) fourni en paramètre, changerait éventuellement son image pour visualiser une brique plus ou moins fissurée ou supprimerait (appel de la fonction de suppression) la brique si la résistance est arrivée à 0. C'est plus dans la fonction de suppression que le score devra être incrémenté, d'ailleurs dans les propriétés des briques, il serait aussi pas mal d'ajouter un item définisssant combien de point rapporte la destruction des briques, voir même plein d'autres items, brique cassable, faisant spawn des items, etc. Bon si c'est un projet à rendre pour mardi, ça va être un peu juste pour faire tout ça, et mieux vaut aller à l'essentiel, un jeu jouable et pas trop bogué , même l'implémentation du score n'est pas le plus important dans tout ça.

    Bon courage et bonne chance.

Discussions similaires

  1. [Python 3.X] [ISN Bac] Space Invaders problème création des ennemis Tkinter
    Par DKwaws dans le forum Programmation multimédia/Jeux
    Réponses: 0
    Dernier message: 22/05/2017, 20h00
  2. [Python 3.X] Projet ISN Terminale BAC
    Par Xeode dans le forum Tkinter
    Réponses: 6
    Dernier message: 12/05/2017, 12h46
  3. [Python 3.X] Projet ISN Terminale BAC
    Par Xeode dans le forum Programmation multimédia/Jeux
    Réponses: 4
    Dernier message: 11/05/2017, 18h50
  4. [Python 3.X] Projet ISN jeu problème compréhension du code
    Par core54 dans le forum Programmation multimédia/Jeux
    Réponses: 0
    Dernier message: 08/05/2017, 13h24

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo