Forums Développement Multimédia

Aller au contenu

Génération de particules et collisions ✔

AS3 Collisions Particules CODE Actionscript

9 réponses à ce sujet

#1 BlackBonobo

    Ceinture Blanche

  • Members
  • Pip
  • 4 messages

Posté 23 January 2012 - 22:40 PM

Bonjour,

Alors voilà, je suis un peu un noob en AS3, j'ai un projet que j'imaginais plus simple que prévu :

Je dois faire une animation qui génere des particules quand l'utilisateur clique sur la scène, et quand les particules se rencontrent.

Aucun boulot graphique, on sera content quand 4 cercles seront générées pour un des des deux évenements précités, avec une taille, une couleur et une direction aléatoire.

Je bloque sur la gestion des collisions, mon problème étant que les particules partent toujours du même point. Du coup si je fait un HitTestObject quand une particule en rencontre une autre, je crée une boucle infinie dès la première génération, et ça c'est moche.

Je n'ai pas trouver de solution efficace jusqu'à maintenant, je suis en train de complexifier énormément mon code pour gérer ce bug.

Merci beaucoup pour l'aide que vous pourrez m'aporter.

#2 Nataly

    Community Jane

  • Moderateur
  • PipPipPipPipPipPipPipPip
  • 5783 messages

Posté 24 January 2012 - 07:29 AM

Salut et bienvenue ici :)

Puisque tu parles d'hitTest je déduis que tu parles de sprites en tant que particules - sinon tu peux faire une recherche sur 'particule' et ou 'fontaine' Tlecoz et Dldler entre autres se sont bien amusés avec ça il y a quelque temps -

Si tu procèdes par génération de sprites, je ne vois pas comment tu peux avoir une boucle infinie en parcourant leur contenant commun… :roll:

Imaginons les clips générés dans un conteneur commun.
Le constructeur (de la classe) s'occupe du disque, de la couleur aléatoire et du mouvement pareil. Après un délai à calculer*, parcour de la liste d'affichage du parent et hitTestObject sur chaque enfant (à l'exception de l'objet considéré)… tu ne peux pas avoir de boucle infinie.

* sans quoi, si tu en génères une poignée il va forcément y avoir collision au tout début

Reste à savoir combien tu en veux de ces disques particules, le hitTest restant gourmand :(


Tiens nous au courant ;)
Le savoir est le seul bien qui s'accroit quand on le partage
une tartine de tutos

#3 Nataly

    Community Jane

  • Moderateur
  • PipPipPipPipPipPipPipPip
  • 5783 messages

Posté 25 January 2012 - 09:18 AM

Slt :)

je me demandais cette histoire de hitTest… quelles seraient les limites :roll: alors j'ai essayé.

j'ai fait précisément ce que je te proposais : une classe qui gère le déplacement, balaie les enfants du contenant en testant la collision à chacun et génère une poignée d'instances de cette même classe en cas de collision.
Forcé, on a une réaction en chaine qui gave vite les ressources.
En limitant le nombre de disques à 200 et le test de collision à 150 enfants pour chaque objet (150 x 200 hitTest j'ai jugé que ça suffisait) ça fait un truc tout à fait hypnotisant (et sans grand autre intérêt)

Je pense que c'est un modèle du genre de ce qu'il ne faut pas faire. :mrgreen:
Mais maintenant que j'ai bien fait joujou (merci de l'idée, ça m'a délassée de ma mauvaise humeur) je te mets la classe, peut-être que ça te donnera une idée de comment faire autrement ;)

le swf de test lache une poignée de pastilles au clic, plusieurs clics finissent par déclencher la réaction.

Fichier(s) joint(s)


Le savoir est le seul bien qui s'accroit quand on le partage
une tartine de tutos

#4 BlackBonobo

    Ceinture Blanche

  • Members
  • Pip
  • 4 messages

Posté 27 January 2012 - 20:05 PM

Woow carrément t'as fait mon boulot ! Dommage que je ne peux pas ouvrir le .fla que tu as fait avec CS5 j'imagine, alors que moi, pauvre newbie, j'ai juste CS4. Merci pour la classe en tout cas.

Je vois que par contre que ton idée de calculer un laps de temps minimum avant que les disque puissent déclencher une collision ne marche pas dans mon cas. Vu qu'il y a des chances pour que certains partent dans la même direction, et déclenchent donc une collision de toute façon, on se retrouve 4 fois sur 5 avec un écran complétement saturé dès le premier clique.

A la base je pensais appeler un sprite conteneur pour chaque génération de particules et faire en sorte que les particules d'un même sprite ne puissent pas déclencher de collision. Sauf que c'est le même sprite qui est appelé, je ne voyais pas comment les differencier.

Ce soir j'ai une nouvelle idée : je vais donner aux particule un attribut .name en fonction des coordonnée x y où elles ont été crées et tenter d'interdire les collisions entre particules du même nom. Du coup si l'utilisateur clique deux fois exactement au même endroit ce sera considéré comme la même génération, mais ça c'est la vie.

Sinon pourquoi un modèle du genre de ce qu'il ne faut pas faire ? Trop gourmand ?

Si tu veux savoir à quoi ça va servir, c'est pour animer un stand qui proposera entre autre de taper sur un écran tactile pour créer des particules, écran qui sera relié à un rétroprojecteur caché, qui balancera de la lumière dans des blocs de cristaux. J'espère bien que ça va être hypnotisant, c'est le seul but.

Merci pour ton aide. Je n'avais pas vu tes réponses, je m'attendais à recevoir une alerte. ++

#5 Nataly

    Community Jane

  • Moderateur
  • PipPipPipPipPipPipPipPip
  • 5783 messages

Posté 27 January 2012 - 20:52 PM

ah bah zutalors, je l'ai laissé en 5, hop ! converti :)

Citation

il y a des chances pour que certains partent dans la même direction, et déclenchent donc une collision de toute façon

chez moi aussi, et plus que des chances au début pcq pour aller vite et pas me creuser je les faisais se déplacer uniquement sur les x ou y (4 axes :mrgreen: ). vu que dès qu'il y a collision le clip est supprimé avant de générer une poignée d'autres clips… ça va bien.

en revanche il faut impérativement limiter le nombre de hitTest, c'est ça qui ralenti grave, d'où les bidouilles au pif :


// déjà là je limite le nombre de clips
                         if (max > 200) {
                                        //trace("ça suffit "+max);
                                        parent.removeChild(this);
                                        return;
                                }
// et là je limite le nombre d'appels à hitTest (je ne parcours pas tout, certaines collisions sont donc ignorées, ça résout en partie le pb des trajets superposés)
                                //Limiter les tests de collision - parfaitement au pif -
                                trace("max "+max);
                                max = max > 150 ? 100:max;
                                for (var i:int = 0; i < max; i++) {
                                        var c:Coliz = Coliz(parent.getChildAt(i));
                                        if (c != this) {
                                                if (this.hitTestObject(c)) {
 

Citation

je vais donner aux particule un attribut .name en fonction des coordonnée x y où elles ont été crées et tenter d'interdire les collisions entre particules du même nom.

tu veux dire les récupérer via getChildByName ? outch ! pas bonne idée ds ce contexte, c'est très gourmand donc déconseillé typiquement ds ce cas là ;)

Citation

J'espère bien que ça va être hypnotisant, c'est le seul but.

Alors ça vaut peut-être le coup de creuser l'idée de base… ;)


Nb, je ne remets pas la classe, les .as tu peux les ouvrir. D'ailleurs pour ce qu'il y a sur le fla… je le colle ici, au moins ce sera multiversion ;)

stage.addEventListener(MouseEvent.CLICK,qdClic);

function qdClic(me:MouseEvent):void {
        for (var i:int=0; i<4; i++) {
                var t:Coliz=new Coliz();
                t.x = mouseX;
                t.y = mouseY;
                addChild(t);

        }

}

Amuse toi bien :)


[edit]
tu as un bouton 'suivre le sujet' en haut à gauche de la fenêtre -_-
Le savoir est le seul bien qui s'accroit quand on le partage
une tartine de tutos

#6 Nataly

    Community Jane

  • Moderateur
  • PipPipPipPipPipPipPipPip
  • 5783 messages

Posté 27 January 2012 - 21:26 PM

je te troll ton sujet ! :mrgreen:

me suis dit que ce serait mieux à tester sur une grande surface, et j'ai ajouté une statique (et un if :oops: ) pour pouvoir déclencher/arrêter l'effet collision.

Du coup, on peut perdre encore plus de temps à regarder le nuage se déplacer, se tasser dans un coin, et puis arrêter (clique sur la scène bascule, une fois ça génère une poignée de pastilles, l'autre ça désactive l'effet collision) et regarder les truc disparaître, et relancer, et… se dire que tiens, ça saccade, peut-être pas… peut-être que si… qu'il suffirait de… STOOOOP ! je ferme ce fla ! :D

stage.addEventListener(MouseEvent.CLICK,qdClic);
var marche:Boolean = false;
function qdClic(me:MouseEvent):void {
        if (! marche) {
                for (var i:int=0; i<5; i++) {
                        var t:Coliz=new Coliz();
                        t.x = mouseX;
                        t.y = mouseY;
                        addChild(t);
                }
        }
        Coliz.desactivé = marche;
        marche = ! marche;
}

… uiiii… 'pas pu m'empêcher de la variable à accent :jesors:

Fichier(s) joint(s)


Le savoir est le seul bien qui s'accroit quand on le partage
une tartine de tutos

#7 BlackBonobo

    Ceinture Blanche

  • Members
  • Pip
  • 4 messages

Posté 31 January 2012 - 23:29 PM

Nataly, j'ai fini par faire ce que je voulais en partant de ton code, merci beaucoup!

J'ai pu interdire les collisions entre les particules issues du même cliques en leur donnant un nom et en mettant une condition if (c.name!=this.name ). Après, comme je ne voulais pas générer une infinité de particule dès la première collision, j'ai rendu celles déjà issue d'une collision stérile, en leur donnant toutes le même nom.

Pour finir, je me suis pas mal pris la tête avec les couleurs, juste pour avoir 6 tonalité différentes : j'ai mis un tableau avec des valeur du style "FF00"+_mc, où mc = ((Math.random()*239)+16).toString(16).

Bon, il y avait peut-être plus simple, mais ça marche, c'est cool. Heuresement que t'était là pour troller ;-)

Fichier(s) joint(s)



#8 Nataly

    Community Jane

  • Moderateur
  • PipPipPipPipPipPipPipPip
  • 5783 messages

Posté 01 February 2012 - 09:56 AM

Voir le messageBlackBonobo, le 31 January 2012 - 23:29 PM, dit :

Nataly, j'ai fini par faire ce que je voulais
goud niouz ! \o/

c'est vachement sympa avec un camaïeu, (je viens encore d'engloutir des minutes à cliquer et à m'ébaudir). Je pense que j'aurais fait un truc du même goût que toi pour rester dans la nuance. Je n'ai pas les techniques efficaces pour la couleur. Si dldler passe par là (ou d'autres hein ! moi je fais que dénoncer ceux que je connais :P) il te donnera peut-être une technique plus rusée :roll:





Citation

J'ai pu interdire les collisions entre les particules issues du même cliques en leur donnant un nom et en mettant une condition if (c.name!=this.name ).
C'est marrant de détourner la prop name pour en faire un "tag"… pense à l'avenir, (si la ruse name ne marchait plus) que la classe MovieClip est dynamique tu peux créer des variables du type que tu veux :idea:


Citation

Heureusement que t'étais là pour troller ;-)

Pousse au crime ! :mrgreen:
Le savoir est le seul bien qui s'accroit quand on le partage
une tartine de tutos

#9 BlackBonobo

    Ceinture Blanche

  • Members
  • Pip
  • 4 messages

Posté 03 February 2012 - 22:49 PM

Voir le messageNataly, le 01 February 2012 - 09:56 AM, dit :

C'est marrant de détourner la prop name pour en faire un "tag"… pense à l'avenir, (si la ruse name ne marchait plus) que la classe MovieClip est dynamique tu peux créer des variables du type que tu veux :idea:

C'est noté :-)

#10 lilive

  • Moderateur
  • PipPipPipPipPipPipPipPip
  • 2993 messages

Posté 05 February 2012 - 13:53 PM

Salut BlackBonobo,

C'est pour te dire, au cas où ça t'intéresserait, qu'il existe des classes toutes faites pour créer et manipuler des particules. Par exemple http://flintparticles.org/. Il y a une étape de prise en main, heureusement on trouve des exemples, mais une fois qu'on a pris le coup on peut faire plein de choses assez simplement, varier les modes d'émission des particules, leurs interactions, leurs couleurs, etc.



1 utilisateur(s) li(sen)t ce sujet

0 membre(s), 1 invité(s), 0 utilisateur(s) anonyme(s)

authorised training centre

Centre de Formation Mediabox - Adobe et Apple Authorised Training Center.

Déclaré auprès de la Direction du Travail et de la Formation Professionnelle

Mediabox : SARL au capital de 62.000€ - Numéro d'activité : 11 75 44555 75 - SIRET : 49371646800035

MEDIABOX, 23, rue de Bruxelles, 75009 PARIS

FFP