Bonjour,

Je suis actuellement en train d'essayer de coder un programme permettant de faire rebondir plusieurs balles sur des parois tout en gérant les collisions.

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
 
# --- Importer les bibliothèques utilisées ---- #
import tkinter as tk    # pour Python 2.x, c'est Tkinter (majuscule initiale)
import random
import time
 
# --- Variables  --- #
 
w_fen, h_fen = 500, 400 # Dimensions de notre zone graphique.
balle = int(input("Choisissez le nombre de balles"))
x = [random.randint(0,500) for i in range(balle+1)] # Position x aléatoire des balles.
y = [random.randint(0,400) for i in range(balle+1)] # Position y aléatoire des balles.
r = 8 # ayon de la balle.
n = 0 # Variable compteur.
dx = [random.randint(-5,5) for i in range(balle+1)] # Etape 4 : Rebond aléatoire.
dy = [random.randint(-5,5) for i in range(balle+1)] # Etape 4 : Rebond aléatoire.
drapeau = True
Couleur = ["Red","Yellow","Gray","White","Black","Blue","Green","Orange","Pink"]
 
while n != balle : # Empecher d'avoir le 0 comme valeur et ainsi empecher un non mouvement possible d'une balle.
    if dx[n] == 0 or dy[n] == 0 :
        dx = [random.randint(-5,5) for i in range(balle+1)] # Etape 4 : Rebond aléatoire.
        dy = [random.randint(-5,5) for i in range(balle+1)] # Etape 4 : Rebond aléatoire.
        n = - 1
    n = n + 1
n = 1
 
 
 
# --- Fonctions de modification de l'interface graphique --- #
def fin(event=None):
    "Fin anticipée (Maj+Ctrl+Fin)."
    fen.destroy()
# Etape 3 : Touche <Return> et <Space>
def arret(event=None): # Arret des mouvements a l'appui de la touche Entree.
    global drapeau
    drapeau = True
def reprise(event=None): # Reprise des mouvements a l'appui de la touche Espace.
    global drapeau
    drapeau = False
def cercle(x, y, r, nom = n): #Fonction cercle
    a = x - r
    b = y - r
    c = x + r
    d = y + r 
    return can.create_oval((a,b,c,d), fill=Couleur[NbCouleur], outline="black", tag = nom)
 
# --- Fenêtre principale --- #
fen = tk.Tk()           # Crée la fenêtre principale de l'application.
fen.title("Boules & Billes...")
 
tit = tk.Label(fen, text="Boules & Billes :")       # Un petit titre...
tit.pack(side=tk.TOP)
 
can = tk.Canvas(fen)    # Puis une surface 'pour dessiner' à l'intérieur.
can.configure(width=w_fen, height=h_fen, bg='white')
can.pack(side=tk.TOP)
 
# --- COMMANDES --- # 
boutQuit=tk.Button(fen, text="Quitter", command=fin).pack(side=tk.BOTTOM)
fen.bind("<Shift-Control-End>", fin)
fen.bind("<Return>",arret)
fen.bind("<space>",reprise)
 
# --- PARTIE PRINCIPALE DU CODE --- #
 
while n!=balle +1 : # Affichage des cercles un a un.
    NbCouleur = random.randint(0,8)
    cercle(x[n],y[n],r) 
    n = n + 1
n = 1 # Remise de n a 0 pour commencer le mouvement des balles une par une.
while 1:
    while drapeau == False :
        fen.update()
    while drapeau == True : # Boucle infinie.
 
        # --- GESTION DU MOUVEMENT --- #
        can.move(n,dx[n],dy[n]) # Déplacement de la balle selon dx et dy.
        fen.update()  # Actualisation de la fenetre graphique.
        fen.after(3) # Vitesse de la balle.
 
        # --- GESTION DES REBONDS SUR LES BORDS --- #
        if 500 - r < x[n] < 500 + r or -r < x[n] < r : # Si la balle touche le bord en x ...
            dx[n] = -dx[n] # Gestion du rebord en prenant l'inverse de dx pour un rebond coherent.
        if 400 - r < y[n] < 400 + r or -r < y[n] < r : # Si la balle touche le bord en y ...
            dy[n] = -dy[n] # Gestion du rebord en prenant l'inverse de dy pour un rebond coherent.
        y[n] = y[n] + dy[n] # Incrementation de dy sur y.
        x[n] = x[n] + dx[n] # Incrementation de dx sur x.
 
        if n == (balle): # Si on a fait bouger toute les balles une fois ... 
            n = -1 # ... On reinitialise n pour recommencer une boucle.
        n = n + 1
        col = 1
 
 
# ------------------------------------ #
 
fen.mainloop()
Je suis entrain de chercher comme mieux gérer les rebonds sur les parois pour commencer :

Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
 
if x[n] + dx[n] > 500 - 5 :
                can.move(n,(500-dx[n]-r),0)
                fen.upload()
                fen.after(10)
                x[n] = x[n] + (500-dx[n]-r)
                dx[n] = -dx[n]
J'avais penser a quelques choses du style.
Seulement, au début de mon programme, j'ai utilisé une magouille en faisant les randoms sur (balle + 1) et non balle car ma fonction can.move ne veut pas bouger ma balles "0". Je suis donc contraint de générer une balles de plus pour avoir le nombres voulu, ce qui fait qu'il y a une pair de coordonnée générer aléatoirement en trop.
Ceci entraînant des problèmes dans la suite du programme et faussant totalement mes rebonds sur les parois ainsi que mes essaies de collisions.

J'ai trouver un début de formule pour la gestion des collisions :
En gros la conditions serait la suivante.
(x[col] serait les collisions des balles tester une par une contre la balles [n])

Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
 
while n != col :
                if x[n] + ((x[col]-x[n])/2) = x[col] - ((x[col]-x[n])/2) :
                                "Gestion de mouvement après collisions"
                col = col + 1
Pourriez vous m'aider a résoudre ses problèmes ? Je reste ouvert a une discussion via Mp ou Skype si nécessaire.

Bromy