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

XNA/Monogame Discussion :

Collision dans un casse-brique


Sujet :

XNA/Monogame

  1. #1
    Candidat au Club
    Homme Profil pro
    Inscrit en
    Janvier 2012
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Janvier 2012
    Messages : 13
    Points : 4
    Points
    4
    Par défaut Collision dans un casse-brique
    Bonjour,

    Je débute actuellement sur XNA et je m'essaye, après un pong, à un casse-brique.
    Les collisions sur les cotés de l'écran et sur le pad fonctionne correctement, les rebonds se font comme il faut.

    Je bute sur les collisions balle-brique pour différentes raisons.
    1) Je ne sais pas où placer le code de collisions, est-ce plutôt au niveau de la balle (elle tape dans une brique et change de direction) ou sur la brique (qui se prends la balle ?). J'opterais plutôt pour la balle, car ceci me semble plus logique, mais peut-être que j'me trompe.

    2) La façon de gérer la collision.
    -Est-ce que je dois faire un test sur toutes les briques (foreach ?) ?
    Cela me semble un peu lourd.
    -Est-ce que je dois faire un test selon la position de la balle ?
    Mais comment faire ? Je ne vois pas.

    3) Actuellement, je fais ma collision pad-balle avec un rectangle autour du pad et un contains() sur le point en bas au milieu de la balle.
    J'ai lu quelque part des trucs comme "bounding sphere" et "bounding box". Est-ce mieux ? Qu'est-ce que c'est ? Est-ce que ça apporte plus que deux simples rectangles ?

    Merci d'avance pour votre aide.

    Yoru

  2. #2
    Responsable 2D/3D/Jeux


    Avatar de LittleWhite
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2008
    Messages
    26 826
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Mai 2008
    Messages : 26 826
    Points : 218 287
    Points
    218 287
    Billets dans le blog
    117
    Par défaut
    Bonjour,

    N'hésitait pas à nous montrer le casse brique une fois fini

    1) Je placerai le code de détection des collisions (je ne parle pas la de la fonction de calcul de collision en elle même) dans la fonction Update de mon World. Mais c'est un choix et tout le monde peut ne pas avoir le même point de vue. Je ferai comme cela, car c'est dans la mise à jour du monde que la balle bouge et que l'on doit donc vérifier l'état de la balle et des briques.

    2) Un foreach, c'est lourd mais nos machines sont assez puissantes. Par contre, les optimisations possibles sont en utilisant une technique de partitionnement de l'espace (voir Binary Space Partitionning (BSP) ou Quad Tree).

    3) Je pense que le contains suffit pour le moment. Il faudra les bouding box lorsque vous ferez un partitionnement de l'espace. Mais vos boites sont très simples, car identique aux rectangles des briques.
    Vous souhaitez participer à la rubrique 2D/3D/Jeux ? Contactez-moi

    Ma page sur DVP
    Mon Portfolio

    Qui connaît l'erreur, connaît la solution.

  3. #3
    Candidat au Club
    Homme Profil pro
    Inscrit en
    Janvier 2012
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Janvier 2012
    Messages : 13
    Points : 4
    Points
    4
    Par défaut
    Merci pour votre réponse.

    Citation Envoyé par LittleWhite Voir le message
    1) Je placerai le code de détection des collisions (je ne parle pas la de la fonction de calcul de collision en elle même) dans la fonction Update de mon World. Mais c'est un choix et tout le monde peut ne pas avoir le même point de vue. Je ferai comme cela, car c'est dans la mise à jour du monde que la balle bouge et que l'on doit donc vérifier l'état de la balle et des briques.
    Qu'entendez-vous par "World" ? C'est la classe hérité de Game ou est-ce une couche supplémentaire ?

    Peut-être que je m'y prends mal, pour l'instant j'ai :
    -Ma classe principale, hérité de Xna.Framework.Game
    -Une classe Sprite. (texture, position, direction, vitesse, et les méthodes draw/update/etc)
    -Une classe Balle qui hérite de Sprite.
    -Une classe Pad qui hérite de Sprite.
    -Une classe Brick qui hérite aussi de Sprite.

    Toute les méthodes (load/update/draw/etc) sont appelé dans ma classe principale.

    Est-ce que je devrais ajouter une classe intermédiaire Niveau(World ?) qui gère mes classe balle/pad/brick ? Qu'est-ce que ça changerais ?

    Merci d'avance

    Yoru

  4. #4
    Responsable 2D/3D/Jeux


    Avatar de LittleWhite
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2008
    Messages
    26 826
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Mai 2008
    Messages : 26 826
    Points : 218 287
    Points
    218 287
    Billets dans le blog
    117
    Par défaut
    Alors mettez dans votre classe principale (normalement XNA à une fonction Update ou UpdateGame que l'on peut utiliser).
    Pour l'instant je ne pense pas qu'il y ai besoin de classe World.
    Vous souhaitez participer à la rubrique 2D/3D/Jeux ? Contactez-moi

    Ma page sur DVP
    Mon Portfolio

    Qui connaît l'erreur, connaît la solution.

  5. #5
    Candidat au Club
    Homme Profil pro
    Inscrit en
    Janvier 2012
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Janvier 2012
    Messages : 13
    Points : 4
    Points
    4
    Par défaut
    J'essaye de mettre le code dans ma classe Game, mais je n'arrive pas à détecter la collision.
    Pourtant, le test est simple, et avec une seule brique :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    if(briqueTest.RectangleCollision.Intersects(balle.RectangleCollision))
    {
        briqueTest.prendreUnCoup();
        balle.Direction = new Vector2(balle.Direction.X, -balle.Direction.Y);
    }
    Avec cela, la brique est censé prendre un coup (et disparaitre) et ma balle est censée rebondir.

    Cependant, la balle passe à travers la brique comme si de rien n'était...

    EDIT : C'est bon !

    Le code de ma brique n'était pas cohérent, je définissait le Rectangle de collision en fonction de la position(init à (0,0)) tandis que la brique était dessinée en fonction de sa colonne et de sa ligne !

  6. #6
    Candidat au Club
    Homme Profil pro
    Inscrit en
    Janvier 2012
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Janvier 2012
    Messages : 13
    Points : 4
    Points
    4
    Par défaut
    Bonsoir !

    J'ai un nouveau problème, ma fonction de collision s'effectue comme cela :

    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
     
    private void Collision_balle_brick()
    {
        bool test = false;
        foreach (Brick b in bricks)
        {
            test = false;
            if (b.Existe)
            {
                //Collision haut/bas
                if (balle.RectangleCollision().Intersects(b.RectangleCollision(Cote.haut)) || balle.RectangleCollision().Intersects(b.RectangleCollision(Cote.bas)))
                {
                    balle.Rebond_Y();
                    test = true;
                }
                //Collision droite/gauche
                if (balle.RectangleCollision().Intersects(b.RectangleCollision(Cote.droite)) || balle.RectangleCollision().Intersects(b.RectangleCollision(Cote.gauche)))
                {
                    balle.Rebond_X();
                    test = true;
                }
            }
            if (test == true)
            {
     
                b.PrendreUnCoup();
            }
        }
    }
    Mon problème est que lorsque la balle arrive dans le coin comme ceci :



    elle part à l'exact opposé. C'est normal si la balle arrive 'face' au coin, mais quand il arrive sur le coté, ça devrait rebondir normalement.


    D'ailleurs, j'ai un autre problème, si j’essaie de mettre 2 'vie' à mes briques, il arrive parfois que les briques meurt en un seul coup au lieu de deux. Comment régler ce problème ?

  7. #7
    Responsable 2D/3D/Jeux


    Avatar de LittleWhite
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2008
    Messages
    26 826
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Mai 2008
    Messages : 26 826
    Points : 218 287
    Points
    218 287
    Billets dans le blog
    117
    Par défaut
    Je ne suis pas sur de comprendre dans quelle direction la balle part.

    Peut être que vous devriez utilisé un else if dans votre code ? Dans le sens, si une collision est détectée, alors il ne faut pas rentrer dans le cas d'une seconde collision ? (D'ailleurs, je pense que c'est pour cela que vous avez un bug avec la vie des briques).
    Vous souhaitez participer à la rubrique 2D/3D/Jeux ? Contactez-moi

    Ma page sur DVP
    Mon Portfolio

    Qui connaît l'erreur, connaît la solution.

  8. #8
    Candidat au Club
    Homme Profil pro
    Inscrit en
    Janvier 2012
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Janvier 2012
    Messages : 13
    Points : 4
    Points
    4
    Par défaut
    Bonjour,

    Merci pour votre réponse.

    Finalement, j'ai mis un else if, c'est plus simple, mais j'ai toujours le problème de 'vie' des briques qui disparaisse en une fois.

    Je comprends le problème, la balle arrive trop vite sur la brique, et le temps qu'elle "ressorte", les tests de collisions sont effectués plusieurs fois, et donc la brique "meurt".
    Cependant, je ne vois pas comment faire pour régler ce problème.

    J'ai essayé de faire une propriété "etat_collision" et "ancien_etat_collision" à ma balle pour qu'elle ne fasse pas les test de collisions plusieurs fois de suite sans "ressortir" de la brique, mais je n'arrive pas à faire fonctionner ça. Peut-être n'est-ce pas la bonne solution ?

  9. #9
    Responsable 2D/3D/Jeux


    Avatar de LittleWhite
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2008
    Messages
    26 826
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Mai 2008
    Messages : 26 826
    Points : 218 287
    Points
    218 287
    Billets dans le blog
    117
    Par défaut
    On peut faire plus simple.

    Normalement, vous avec un vecteur qui indique la direction de la balle. Il faudra donc calculer si ce vecteur entre en collision avec la brique (voir les algorithme de collision rayon / rectangle). S'il y a collision, il faut faire rebondir la balle. Pour cela, il faut multiplier la normale de la face du rectangle (son orientation) avec le vecteur de direction ... multiplier par le coefficient restant après l'intersection.

    Bon, comme ça, ça ne parait pas simple .
    On minimum, vous pouvez juste faire la détection rayon / rectangle et ainsi calculer la nouvelle direction de la balle. Ça devrait donner déjà quelque chose de bien, je pense. (Cette méthode empêche d'avoir la balle qui rentre dans le rectangle).
    Vous souhaitez participer à la rubrique 2D/3D/Jeux ? Contactez-moi

    Ma page sur DVP
    Mon Portfolio

    Qui connaît l'erreur, connaît la solution.

  10. #10
    Candidat au Club
    Homme Profil pro
    Inscrit en
    Janvier 2012
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Janvier 2012
    Messages : 13
    Points : 4
    Points
    4
    Par défaut
    Citation Envoyé par LittleWhite Voir le message
    Pour cela, il faut multiplier la normale de la face du rectangle (son orientation) avec le vecteur de direction ... multiplier par le coefficient restant après l'intersection.
    Qu'entendez vous par là ?

    Citation Envoyé par LittleWhite Voir le message
    On minimum, vous pouvez juste faire la détection rayon / rectangle et ainsi calculer la nouvelle direction de la balle. Ça devrait donner déjà quelque chose de bien, je pense. (Cette méthode empêche d'avoir la balle qui rentre dans le rectangle).
    Je ne comprends pas, la distance centre-coté et centre-coin du rectangle ne sont pas les mêmes. Alors pourquoi la balle ne rentre pas dans le rectangle ?

  11. #11
    Responsable 2D/3D/Jeux


    Avatar de LittleWhite
    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Mai 2008
    Messages
    26 826
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : Ingénieur développement logiciels

    Informations forums :
    Inscription : Mai 2008
    Messages : 26 826
    Points : 218 287
    Points
    218 287
    Billets dans le blog
    117
    Par défaut
    En fait, lors d'une intersection rayon / objet , on détermine entre autre, où l'intersection à lieu. Cette intersection est un coefficient de la longueur du rayon (distance entre le point de début et de fin). Lorsque la détection sera détecter, il faudra faire rebondir la baille du reste de la distance.

    La balle ne rentre pas, car nous allons détecter la collision, d'une, avant le déplacement physique de la balle, de deux au moment précis où la balle entre en collision.
    Vous souhaitez participer à la rubrique 2D/3D/Jeux ? Contactez-moi

    Ma page sur DVP
    Mon Portfolio

    Qui connaît l'erreur, connaît la solution.

  12. #12
    Candidat au Club
    Homme Profil pro
    Inscrit en
    Janvier 2012
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Janvier 2012
    Messages : 13
    Points : 4
    Points
    4
    Par défaut
    Je suis désolé, mais je n'ai rien compris.

    Je ne comprends pas ce que je suis censé faire avec ce test "rayon / objet"

  13. #13
    Inactif  


    Homme Profil pro
    Inscrit en
    Novembre 2008
    Messages
    5 288
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 48
    Localisation : France, Rhône (Rhône Alpes)

    Informations professionnelles :
    Secteur : Santé

    Informations forums :
    Inscription : Novembre 2008
    Messages : 5 288
    Points : 15 620
    Points
    15 620
    Par défaut
    Un peu de lecture pour comprendre la théorie ?
    Chapitre XI : Détection et gestion des collisions avec SDL
    (peut importe que ce soit pour la SDL)

  14. #14
    Candidat au Club
    Homme Profil pro
    Inscrit en
    Janvier 2012
    Messages
    13
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations forums :
    Inscription : Janvier 2012
    Messages : 13
    Points : 4
    Points
    4
    Par défaut
    Merci mais je l'ai déjà lu.

    Je n'a pas tout compris, mais mon problème de collision ne se situait pas sur la méthode, mais sur le moment où j'effectuais mes tests de collisions. J'attendais que ma balle entre en collisions avec une brique alors qu'il fallait faire le test avant le déplacement, pour vérifier si il était autorisé.

Discussions similaires

  1. Réponses: 5
    Dernier message: 06/09/2006, 10h35
  2. Collision dans un jeu de voiture
    Par japle dans le forum Physique
    Réponses: 5
    Dernier message: 21/07/2006, 15h33
  3. [Source] [SDL] Commencement d'un casse brique
    Par grincheux01 dans le forum Contribuez
    Réponses: 8
    Dernier message: 29/06/2006, 13h27
  4. Button "Start" dans un jeu de casse brique
    Par tex78 dans le forum Interfaces Graphiques en Java
    Réponses: 6
    Dernier message: 24/01/2006, 16h47
  5. [Tkinter] casse brique
    Par mamatt77 dans le forum Tkinter
    Réponses: 6
    Dernier message: 18/04/2005, 10h43

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