Page 1 sur 2
Cascade d'evenements
Publié : lun. 25/sept./2006 16:41
par SPH
Imaginez une scene spaciale et 2 spheres entrant en collision. De cette collision nait plusieurs autres spheres qui s'eparpillent dans l'espace, entrant elles aussi en collisions.
Bref, de 2, on passe a 10, 100, 1000, etc (ici, des chiffres "ronds" mais qu'importe, on vois une explosion demographique).
Comment gereriez-vous la "naissance" presque infini des nouveaux objets ??
Je pose la question car meme si l'on prevois un tableau de 1000 objets, si les collisions faisait naitre un 1001eme objet, comment le prendriez vous en compte ??
Ce n'est pas que je sois en difficulté avec ce concept mais j'aimerais voir si vous avez des techniques qui me sont etrangeres...
Publié : lun. 25/sept./2006 16:45
par Patrick88
y'a un truc du genre qui existait et qui s'appelait "jeu de la vie"
pat
Publié : lun. 25/sept./2006 17:02
par Frenchy Pilou
Pour le jeu de la vie
http://www.anselm.edu/homepage/dbanach/31life.htm
et charger life32 cela cartonne
Pour les automates cellulaires
http://www.rennard.org/alife/french/ + ses liens !
Pour le reste cela ressemble plus a du system D
suivant que l'on a besoin ou non des états des objets qui sortent de l'écran
Une chose est sûre c'est que pour un écran de 1024* 768 pas la peine de mémoriser plus de 786 432 entités

Publié : lun. 25/sept./2006 17:04
par Anonyme
C'est très simple, regarde ca , tu vas comprendre
Code : Tout sélectionner
; Dans cette structure , tu stockes toute les propriétés de tes sphères
Structure SPHERES
X.f : Y.f : Z.f ; La position
IsExist.b ; Si la sphere existe
Size.l ; Sa taille
; Etc...
EndStructure
Global Dim Sphere.SPHERES(1000)
; Voila un test primaire de collision :
If SphereA Collision SphereB
For i = 1 to 1000
if Sphere(i)\IsExist=0
Sphere(i)\IsExist=1
Sphere(i)\Size=10+Random(100)
Sphere(i)\x = SphereA\x
Sphere(i)\y = SphereA\y
Sphere(i)\z = SphereA\z
Breack 1
endif
next i
endif
ensuite tu gère ton affichage , tu affiches si Sphere(i)IsExist = 1
@++
Publié : lun. 25/sept./2006 17:12
par Dr. Dri
si tu ne connais pas a l'avance le nombre d'éléments regarde du côté des listes chaînées...
Dri
Publié : lun. 25/sept./2006 17:39
par SPH
Frenchy Pilou a écrit :Une chose est sûre c'est que pour un écran de 1024* 768 pas la peine de mémoriser plus de 786 432 entités

Pas forcement. Si les objets peuvent se chevaucher, et si en plus le programme gere plusieurs plans spacials, ca peux aller au dela.
Publié : lun. 25/sept./2006 19:37
par Flype
les listes chainees - comme dit dr dri - c'est la voie à suivre.
voici une trame que je me suis amusé à faire vite fait.
à toi d'inventer la vie qui va avec
Code : Tout sélectionner
; Gestion des objets
Structure OBJET
t.l ; type
x.l ; x
y.l ; y
r.l ; rayon
c.l ; couleur
xd.l ; delta x
yd.l ; delta y
age.l ; durée de vie
EndStructure
Global NewList objet.OBJET()
Procedure NouvelObjet()
If AddElement(objet())
objet()\t = Random(2)
objet()\x = Random(640)
objet()\y = Random(480)
objet()\r = Random(32) + 1
objet()\xd = Random(4) + 1
objet()\yd = Random(4) + 1
objet()\age = Random(1000) + 1000
objet()\c = RGB(0, 0, Random(255))
If Random(1) : objet()\xd * -1 : EndIf
If Random(1) : objet()\yd * -1 : EndIf
EndIf
EndProcedure
; Variables
ww.l = 640
wh.l = 480
FPS_Timer.l = 0 ;
FPS_Frame.l = 0 ;
FPS_Texte.s = "" ;
TotalObjet.l = 0 ; Total objet (liste)
TotalAjout.l = 0 ; Total objet ajoutés
TotalSuppr.l = 0 ; Total objet supprimés
; Ouvre une fenêtre
If CreateImage(0, ww, wh) And OpenWindow(0, 0, 0, ww, wh, "", #PB_Window_SystemMenu|#PB_Window_ScreenCentered)
; Créér une multitude d'objets
For i = 0 To 1000
NouvelObjet()
Next
; Gestion des évênements de la fenêtre
Repeat
Select WindowEvent()
Case #PB_Event_CloseWindow
Break
Case #Null
; Ajoute aléatoirement un objet
If Not Random(1)
NouvelObjet() : TotalAjout + 1
EndIf
; Actualise l'image (buffer)
If StartDrawing(ImageOutput(0))
; Efface le buffer (image noire)
Box(0, 0, ww, wh, #Black)
; Parcours chaque objet
TotalAge.l = 0
ForEach objet()
With objet()
; Algorithme Collision (simpliste)
If \x < 0 : \x = 0 : \xd = -(\xd) : EndIf
If \x > ww : \x = ww : \xd = -(\xd) : EndIf
If \y < 0 : \y = 0 : \yd = -(\yd) : EndIf
If \y > wh : \y = wh : \yd = -(\yd) : EndIf
; Affiche Objet en fonction de son type
Select \t
Case 0: Plot (\x, \y, \c)
Case 1: Box (\x, \y, \r, \r, \c)
Case 2: Circle(\x, \y, \r, \c)
EndSelect
; Calcul Nouvelle Position
\x + \xd
\y + \yd
; Vérifie l'age de l'objet
\age - 1
If \age = 0
DeleteElement(objet(), 1) : TotalSuppr + 1
EndIf
; Calcul Moyenne d'age
TotalAge + \age
EndWith
Next
StopDrawing()
EndIf
; Calcul du FPS
If ElapsedMilliseconds() - FPS_Timer > 1000
FPS_Timer = ElapsedMilliseconds()
FPS_Texte = Str(FPS_Frame)
FPS_Frame = 0
EndIf
; Statistique
TotalObjet = CountList(objet())
info$ = "FPS : " + FPS_Texte
info$ + ", TotalObjet : " + Str(TotalObjet)
info$ + ", TotalAjout : " + Str(TotalAjout)
info$ + ", TotalSuppr : " + Str(TotalSuppr)
info$ + ", Moyenne d'âge : " + StrF(TotalAge / TotalObjet, 2)
; Actualise la fenetre
SetWindowTitle(0, info$)
If StartDrawing(WindowOutput(0))
DrawImage(ImageID(0), 0, 0)
FPS_Frame + 1
StopDrawing()
EndIf
; Delay(1)
EndSelect
ForEver
EndIf
Publié : lun. 25/sept./2006 20:02
par SPH
Flype, ton code est tres bien.
Tiens, pour montrer a vitesse grand V ce que ca fait avec des plot :
Code : Tout sélectionner
; Gestion des objets
Structure OBJET
x.f ; x
y.f ; y
c.l ; couleur
xd.f ; delta x
yd.f ; delta y
EndStructure
Global NewList objet.OBJET()
Procedure Objet_Ajoute()
If AddElement(objet())
objet()\x = Random(102300) /100
objet()\y = Random(76700) /100
objet()\c = RGB(200+Random(55), 200+Random(55), 200+Random(55))
objet()\xd = ((Random(2000) + 1 )/6000)*((Random(1)*2)-1)
objet()\yd = ((Random(2000) + 1 )/6000)*((Random(1)*2)-1)
EndIf
EndProcedure
; Ouvre une fenêtre
ww = 1024
wh = 768
If CreateImage(0, ww, wh) And OpenWindow(0, 0, 0, ww, wh, "", #PB_Window_SystemMenu|#PB_Window_ScreenCentered)
; Gestion des évênements
Repeat
Select WindowEvent()
Case #PB_Event_CloseWindow
Break
Case #Null
; Rajoute un objet
Objet_Ajoute()
; Actualise l'image (buffer)
If StartDrawing(ImageOutput(0))
Box(0, 0, ww, wh, #Black)
ForEach objet()
With objet()
If \x < 0 : \x = 0 : \xd = -(\xd) : EndIf
If \x > ww : \x = ww : \xd = -(\xd) : EndIf
If \y < 0 : \y = 0 : \yd = -(\yd) : EndIf
If \y > wh : \y = wh : \yd = -(\yd) : EndIf
Plot(\x, \y, \c)
\x + \xd
\y + \yd
EndWith
Next
StopDrawing()
EndIf
; Actualise la fenetre
SetWindowTitle(0, "Objet : " + Str(CountList(objet())))
If StartDrawing(WindowOutput(0))
DrawImage(ImageID(0), 0, 0)
StopDrawing()
EndIf
Delay(1)
EndSelect
ForEver
EndIf
Publié : lun. 25/sept./2006 20:11
par Flype
ou comme çà
[EDIT]
j'ai supprimé le source - voir le précédent.
Publié : lun. 25/sept./2006 20:14
par SPH
Design interessant

V le laisser tourner 5 minutes pour voir...
PS : en supprimant le Delay, c'est plus puregolo... heu, rigolo...
Publié : lun. 25/sept./2006 20:19
par Flype
j'ai mis à jour le code.
comme çà tu pourrais imaginer que seul les objets de meme type peuvent s'accoupler, et que s'ils sont dans une tranche de couleur proche, par ex.
on peut aussi ajouter facilement la durée de vie d'un objet (age).
Publié : lun. 25/sept./2006 20:25
par SPH
Oui, mais je ne te raconte pas le nombre de test a faire !
ps : tu peux rajouter le nombre de frame par secondes ? (steuplai)
Publié : lun. 25/sept./2006 21:21
par Flype
pour le FPS je suis pas spécialiste
mais bon j'ai bricolé un truc - ca semble fonctionné. (voir 1er code)
Publié : lun. 25/sept./2006 22:33
par Frenchy Pilou
Rafraichissant!
C'est comme du Perrier , cela fait des bulles

Grosso modo, quelles sont les règles?
Il semble que le quadrant en haut à gauche soit moins peuplé que les 3 autres?
Publié : lun. 25/sept./2006 22:41
par SPH
Frenchy Pilou a écrit :Il semble que le quadrant en haut à gauche soit moins peuplé que les 3 autres?
Bien sur !! et c'est logique... Tu ne devines pas ???