Forum de la communauté SFML

Aide => Graphique => Discussion démarrée par: maxia le Mai 06, 2014, 07:05:11 pm

Titre: Collision Tilemap
Posté par: maxia le Mai 06, 2014, 07:05:11 pm
Salutation,

Je viens de crée une map en utilisant le tilemapping proposé dans le tutoriel sur le site, mais maintenant, je ne sais pas comment géré les collisions .

Merci d'avance,
Cordialement,
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 06, 2014, 11:57:51 pm
Je te suggère d'utiliser un tableau de booléens de dimensions identiques au tableau que tu utilises pour ton tileMapping. Ainsi pour chaque case de ton tileMap, tu associes la valeur 0 ou 1 selon que la case correspondante est un obstacle ou non.
Tu n as alors plus qu'à implémenter une fonction booléenne qui prend en paramètres des coordonnées(x;y) et ton tableau de booléens et qui renvoie true ou false selon que les coordonnées correspondent à un obstacle ou non.
Par exemple :
int tileMap [] = {
0,1,0,
1,2,2,
1,0,2 }
 
bool masque [] = {
0,1,0,
1,1,1,
1,0,1 }

bool collision(bool masque[], int x, int y, int tailleCase)
{
      if( masque[ int(x/tailleCase) + 3*int(y/tailleCase) ] == 1)
             return true;
      return false;  
 }        
 
Titre: Re : Collision Tilemap
Posté par: maxia le Mai 07, 2014, 09:32:32 pm
Merci PtichapronRouge, mais comme mon jeu est plateformé (comme mario) et donc mon personnage ne se déplace que sur 1 axe (x) j'ai modifié ta fonction et voici ce que j'ai fait:

bool collision(bool masque[], int x, int tailleCase)
{
     
      if( masque[(x/tailleCase)] == 1)
      {
             return true;
      }
      else
      {
              return false;
      }

 }
Pourtant sa marche plus alors que ton code marchais parfaitement et je ne comprends pas pourquoi .
Merci d'avance,
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 08, 2014, 12:54:33 am
Si c est un jeu de plateforme style Mario, tu as quand même besoin des ordonnées, sinon ça veut dire que ton jeu entier est une unique ligne, pas sur que ce soit ce que tu cherches :D
Ayant déjà code un jeu "style Mario", je te garantis que tu as besoin des x comme des y ^^ (ne serait-ce que pour empêcher le personnage de passer à travers le sol)

En fait tu dis que ton personnage ne se déplace qu en x, donc il ne saute jamais ? ^^
Titre: Re : Collision Tilemap
Posté par: maxia le Mai 08, 2014, 08:12:18 pm
Tu a tous à fait raison .
Mais pourquoi tu multiplie y pas 3 ?

Merci d'avance,
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 08, 2014, 08:59:47 pm
Parce que j utilise un tableau à une dimension alors que ton monde est en 2D ^^
Il faut donc convertir des coordonnées 2D en coordonnées 1D :)
Regarde : le case (0;0) de ton monde correspond à la case 0 du tableau. La case (2;0) du monde a la case 2 du tableau. Mais la case (2;2) ? Sûrement pas à la case 4 car sinon il y aurait conflit avec la case (4;0)  ^^
En fait, si ton tableau a N colonnes, la case (x;y) du monde correspondra à la case x + N*y du tableau :)
Du coup, si tu as un monde de dimension (n;p), ton tableau sera de dimension n*p :)
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 08, 2014, 09:08:30 pm
D ailleurs je regarde le code que tu as posté, et tu écris :
if ( masque[x/tailleCase] == 1)
 
Du coup si x/tailleCase vaut 2,3 par exemple, tu demandes à ton tableau de renvoyer le valeur de la case numéro 2,3 et je suis pas sur qu il apprécie ^^
Prend plutôt la partie entière en écrivant :
if(masque[int(x/tailleCase)] == 1)
 
Ça me paraît plus sur ;)
Titre: Re : Collision Tilemap
Posté par: maxia le Mai 08, 2014, 09:29:07 pm
D'accord, s'il te plaît une des dernières question tailleCase c'est la taille d'une case ? je veux dire la taille x ou y ?

Merci d'avance,
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 08, 2014, 10:53:31 pm
J ai considéré que tu utilisais des tiles carrées, donc tailleCase est le côté d une tile en pixels (généralement 32 ou 64 pixels). Mais tu peux aussi faire ton tileMap avec de rectangles, et je te conseille alors d utiliser un vector2u qui contiendra la hauteur et la largeur d une tile :)
Titre: Re : Collision Tilemap
Posté par: maxia le Mai 09, 2014, 07:54:20 pm
Cool merci pour tous :) !
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 09, 2014, 07:57:13 pm
de rien :)
met le thread en résolu si possible ;)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 10, 2014, 04:50:09 pm
Salut, moi le problème vient plus loin, j'arrive "détecté" la collision, Mai
quelle ligne de code utiliser pour que le personnage soie "bloquer"
j'ai réussis a "bloqué" les côtés pour que mon perso ne sors pas la fênetre

Comment faire pour que la détection détecte pas toutes une ligne(ex/ y:456 puis être bloqué)
Par exemple un carre de 100 pixeles(en guise de mur) au milieu du graphique et que le personnage ne puisse pas les traverser..

Il faudrait mettre des "<" et aussi ">" ? ??? mettre un  A entre B <0 - 100>?
y'a t'il une ligne de code présice pour cela?  ???
 
Comment faire S.V.P
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 10, 2014, 05:58:43 pm
Cette fois j ai du mal à comprendre le problème ^^
Qu' est ce que A et B ? Que veut tu dire par
Comment faire pour que la détection détecte pas toutes une ligne(ex/ y:456 puis être bloqué)
?

Ensuite :
quelle ligne de code utiliser pour que le personnage soie "bloquer" ?

On ne gère pas les collisions avec une seule ligne de code, les collisions sont souvent gérées par d assez gros calculs mathématiques, tu peux lire ce tuto si ça t intéresse : http://fr.openclassrooms.com/informatique/cours/theorie-des-collisions
Enfin je ne pense pas que tu en aies besoin pour ça, mais si tu veux de l aide je vais avoir besoin de renseignements un peu plus précis :D
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 10, 2014, 07:02:49 pm
Salut oui,
wala mes lignes :

Citer
if ((sprite_perso.getPosition().x >= 375) &&
(sprite_perso.getPosition().x <= 450))
{
    if (sprite_perso.getPosition().x >= 375)
        {
            sprite_perso.setPosition(sf::Vector2f(375, sprite_perso.getPosition().y));
        }
    if (sprite_perso.getPosition().x >= 430)
        {
            sprite_perso.setPosition(sf::Vector2f(430, sprite_perso.getPosition().y));
        }
}

Elles marchent, mais.. séparément, comme tu le vois  le premier côte marche mais le deuxième non, vuc le premier est aussi plus grand que 375
donc je vais dans le mauvais chemain...

pour la documentation que tu ma passer je l'ai deja vue, mais je n'ai peu être pas passer ou il m'était pour "bloqué" le personnage...

Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 10, 2014, 07:30:05 pm
J'ai un peu de mal à comprendre ce que ce code est censé faire  :o certains tests sont complètement inutiles ^^'
par exemple ligne 1 tu testes si la position set supérieure a 375
if ((sprite_perso.getPosition().x >= 375) && (sprite_perso.getPosition().x <= 450))
puis si cette condition est vérifiée, tu retestes si la position est supérieure à 375 :
 if (sprite_perso.getPosition().x >= 375)
Ca ne sert à rien, autant enlever la condition de départ :
if (sprite_perso.getPosition().x >= 375)
{
     sprite_perso.setPosition(sf::Vector2f(375, sprite_perso.getPosition().y));
 }
 if (sprite_perso.getPosition().x >= 430)
 {
      sprite_perso.setPosition(sf::Vector2f(430, sprite_perso.getPosition().y));
 }
Mais même comme ça je ne vois pas ce que tu veux faire, que représentent les valeurs 450 et 375 (et 430 qui apparaît aussi, mais c est peut être une faute de frappe) ?
Essaie d'expliquer le plus clairement possible et en quelques lignes ce que tu veux faire exactement :)

PS :
comme tu le vois
Hmm je vois pas grand chose non :p
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 10, 2014, 07:48:38 pm
Re, oui je sais disant que ça fait une petite heure que je re-travaille dessus et j'ai changer le 450 et 430,
Vuc mes lignes de codes ne sont pas vraiment juste ;D

wala le prinsipe que j'aimerai faire:   
1) loader un carrer(qui serras pour ce test un mur)
2) luis inscrire la position du millieu ect..
//juste que la aucun problème  :)

3)si mon personnage fait une collision(de nimporte quelle côté) alors le personnage est bloqué
en gros comme quand tu fonce dans un mur & tu ne le traverse pas...

Comment dois-je faire cela en ligne de code ???



A aussi pour les test je les avait utilisé ce matin pour justement blocké le bord de la fenêtre afin que mon perso ne puisse en sortir...


Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 10, 2014, 07:53:18 pm
A j'oubliais, j'ai regarder aussi http://fr.openclassrooms.com/informatique/cours/theorie-des-collisions denouveau le problème comme je te le dis en haut c'est q'après j'ai stricktement aucune idée pour faire blocké le personnage... 

car envoyé un true si le perso a 0 vie ont l'amène jute a "mort" donc c'est plus simple...
Titre: Re : Collision Tilemap
Posté par: kimci86 le Mai 10, 2014, 08:14:36 pm
Bonjour,
Pour "bloquer" ton personnage, tu peux le repositionner à la limite de obstacle lorsqu'il y a une collision.
Pour savoir où est cette limite, tu peux utiliser la direction dans laquelle se déplace le personnage pour savoir de quel coté il vient et en déduire de quel coté de l'obstacle il doit être repositionné. Après, il faut utiliser les tailles de l'obstacle et du personnage.

Voilà un exemple simplifié. (Il faudrait aussi tenir compte de l'origine des objets, comme tu utilises des objets dérivant de sf::Transformable)
Je ne sais pas comment est structuré ton programme et si c'est directement applicable mais j'espère que ça te donnera des idées.

if(collision(joueur, obstacle))
{
    switch(joueur.direction)
    {
        case UP: // le joueur vient d'en bas
            joueur.y = obstacle.y + obstacle.h; // on le place en bas de l'obstacle
            break;
        case DOWN:
            joueur.y = obstacle.y - joueur.h;
            break;
        case LEFT:
            joueur.x = obstacle.x + obstacle.w;
            break;
        case RIGHT:
            joueur.x = obstacle.x - joueur.w;
            break;
    }
}
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 10, 2014, 08:22:05 pm
Salut
Citer
Pour "bloquer" ton personnage, tu peux le repositionner à la limite de obstacle lorsqu'il y a une collision.
Pour savoir où est cette limite, tu peux utiliser la direction dans laquelle se déplace le personnage pour savoir de quel coté il vient et en déduire de quel coté de l'obstacle il doit être repositionné. Après, il faut utiliser les tailles de l'obstacle et du personnage.
oui cela je le savais deja  :D

merci beaucoup pour tes lignes de codes je vais de ce pas les essayer et en redire des nouvelles ;)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 10, 2014, 08:58:01 pm
Salut merci pour ta ligne de code, mais je pense que tu n'as pas compris ma question(dsl si je l'ai mal posée)

voici toutes mes lignes de code (simplifiée)

main.cpp

Citer
#include <SFML/Graphics.hpp>
#include <iostream>
#include <string>
#include <cstdlib>
#include <cmath>
#include "Shape.h"

sf::RenderWindow window;
sf::RectangleShape rect;
int speed = 2;
sf::Vector2i positionSouris;
sf::Texture perso;
sf::Sprite sprite_perso;

enum Dir{ Down, Left, Right, Up };
sf::Vector2i anim(1, Down);
bool updateFPS = true;
int blockSize = 32;
int blockDemiSize = 16;
std::string reponse("None");
std::string rep("None");
std::string arret("None");

/**[Les Void] **/
void gestion_clavier();
void gestion_souris();
void gestion_bloque();
/**[Les Void] **/

int main()
{
//Création de la fenêtre 800x600
window.create(sf::VideoMode(800, 600), "Test SFML");
//Modifier la position
window.setPosition(sf::Vector2i(192, 0));
window.setFramerateLimit(60);

std::cout << "Lancement du jeu" << std::endl;

rect = PB_Rect(400, 300, 48, 48);

sf::Clock time;

if (!perso.loadFromFile("resources/image.png"))
{
std::cout << "Erreur chargement de image.png" << std::endl;
}

//En pofine les FPS
perso.setSmooth(true);

sprite_perso.setTexture(perso);

//Tant que la fenêtre est ouverte...
while (window.isOpen())
{
sf::Event event;
//Test des événements
while (window.pollEvent(event))
{
//Si on clique sur fermer
if (event.type == sf::Event::Closed)
window.close(); //On ferme la fenêtre

if (event.type == sf::Event::KeyPressed)
{ /*Pour activer l'anim*/
updateFPS = true;
}
else
updateFPS = false;
anim.x = 1;

}

/**[Les Void] **/
gestion_clavier();
gestion_souris();
gestion_bloque();
/**[Les Void] **/

if (updateFPS == true)
{
if (time.getElapsedTime().asMilliseconds() >= 50)
{ /*On change d'animation toutes les 50 milli secondes*/
anim.x--;
if (anim.x * blockSize >= perso.getSize().x)
anim.x = 2;
time.restart(); /*On relance le timer*/
std::cout << sprite_perso.getPosition().x << "," << sprite_perso.getPosition().y << std::endl;
}
}
//on "coupe" les parties de l'image pour les réutiliser en animation..
sprite_perso.setTextureRect(sf::IntRect(anim.x * blockSize, anim.y * blockSize, blockSize, blockSize));

if (arret == ("stop"))
{
    return 0;
}

// On dessine, on affiche et on met à jour
window.draw(rect);
window.draw(sprite_perso);
window.display();
window.clear();
}

return 0;
}



void gestion_clavier()
{



if (sf::Keyboard::isKeyPressed(sf::Keyboard::Up))
{
anim.y = Up;
sprite_perso.move(0, -speed);
}
if (sf::Keyboard::isKeyPressed(sf::Keyboard::Down))
{
anim.y = Down;
sprite_perso.move(0, speed);
}
if (sf::Keyboard::isKeyPressed(sf::Keyboard::Left))
{
anim.y = Left;
sprite_perso.move(-speed, 0);
}
if (sf::Keyboard::isKeyPressed(sf::Keyboard::Right))
{
anim.y = Right;
sprite_perso.move(speed, 0);
}

if (sf::Keyboard::isKeyPressed(sf::Keyboard::Escape))
{
    std::cout << "[STOP]" << std::endl;
    arret = ("stop");

}
}
void gestion_souris() /** changer  "sprite" par "rect" **/
{
if (sf::Mouse::isButtonPressed(sf::Mouse::Left))
{
//On récupère les coordonnées de la souris
positionSouris = sf::Mouse::getPosition(window);
//std::cout << "Mouse.x" << positionSouris.x << "Mouse.y" << positionSouris.y << std::endl;
int mouseX = positionSouris.x;
int mouseY = positionSouris.y;
sprite_perso.setPosition(mouseX, mouseY); // On positionne le rect
}
}


void gestion_bloque()
{

/*Il va tout a gauche alors, il est bloqué*/
if (sprite_perso.getPosition().x <= 0)
{
sprite_perso.setPosition(sf::Vector2f(0, sprite_perso.getPosition().y));
}

/*Il va tout a droite alors, il est boqué*/
if (sprite_perso.getPosition().x >= 770)
{
sprite_perso.setPosition(sf::Vector2f(770, sprite_perso.getPosition().y));
}

/*Il va tout en bas alors, il est bloqué*/
if (sprite_perso.getPosition().y >= 569)
{
sprite_perso.setPosition(sf::Vector2f(sprite_perso.getPosition().x, 569));
}

/*Il va tout en haut alors, il est bloqué*/
if (sprite_perso.getPosition().y <= 0)
{
sprite_perso.setPosition(sf::Vector2f(sprite_perso.getPosition().x, 0));
}
}
(si vous avez remarqué un "void gestion_console" que j'ai supprimer pour racourcir ses lignes de codes

Shape.h
Citer
#ifndef DEF_SHAPE
#define DEF_SHAPE

#include <SFML/Graphics.hpp>


sf::RectangleShape PB_Rect(int posX, int posY, int width, int height)
{
    sf::RectangleShape rect(sf::Vector2f(width, height));
    rect.setPosition(posX, posY);
    rect.setFillColor(sf::Color(255, 0, 0, 255));

    return rect;
}
#endif // DEF_SHAPE

Wala mes deux question:

1)
Comment et ou je pourrais ajoutez ses lignes de codes :
Citer
if(collision(joueur, obstacle))
{
    switch(joueur.direction)
    {
        case UP: // le joueur vient d'en bas
            joueur.y = obstacle.y + obstacle.h; // on le place en bas de l'obstacle
            break;
        case DOWN:
            joueur.y = obstacle.y - joueur.h;
            break;
        case LEFT:
            joueur.x = obstacle.x + obstacle.w;
            break;
        case RIGHT:
            joueur.x = obstacle.x - joueur.w;
            break;
    }
}

2)
après avoir ajouter ses lignes de codes...comment je fait pour faire le test(if)

par exemple "joueur.y = obstacle.y - joueur.h;" si c'est a 0 ou plus petit je block le perso, mais ou et comment vuc il peut être de tous le côté svp? ???
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 12:02:37 am
Visiblement tu geres les événements claviers et le déplacement dans la même fonction, c est pas optimal, mais bon ^^
Enfin puisque tu fais comme ça, gère la collision dans la même fonction. Au lieu d appliquer un le déplacement à ton sprite juste après le keypressed, calcule les coordonnées qu' aurait ton sprite si tu le déplaçais, et selon qu il y a collision ou non entre le perso virtuel et l obstacle, tu déplaces ton personnage en suivant la méthode de kimci ou non. :)

Et un conseil au passage : quand tu auras résolu ce problème, reprend ton code du début et essaie de le rendre plus oriente objet, en encapsulant ton perso et tout ce qui lui est lié dans une seule classe, ça sera beaucoup beaucoup plus lisible :D
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 12:08:35 am
Citer
après avoir ajouter ses lignes de codes...comment je fait pour faire le test(if)
Regarde dans les premiers messages, j ai donné une fonction booléenne pour les collisions personnage - tileMap ;)
Après, faudra sûrement l adapter un peu, mais c est pas trop compliqué ;)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 09:28:48 am
Salut, je avoue la je suis un peux perdu  :-\

peux te me montrer un exemple concré avec les lignes de codes?

pour que je puisse apres mieu comprendre
(je comprend mieu quand j'ai les lignes de codes devant moi (=)

Citer
Et un conseil au passage : quand tu auras résolu ce problème, reprend ton code du début et essaie de le rendre plus oriente objet

Je sais que j'ai des "void" de trop et autre petit truck dégeulasse  ;D

pour les void avant je faisais toujours avec un "gestion.cpp" mais avec la sfml même si je fais tous juste (comme avant) mon compilateur m'inscrit des fichier "efbewfo.cpp" avec des fautes

et vuc c'est sensé être un test je me suis pas embété a se sujet...
 :)



Titre: Re : Collision Tilemap
Posté par: kimci86 le Mai 11, 2014, 11:13:54 am
Bonjour,
Citer
1)
Comment et ou je pourrais ajoutez ses lignes de codes

Même si le plus sage serait de tout recommencer proprement (faire des classes, ne pas utiliser de variables globales, etc), avec ton code actuel, tu peux ajouter la gestion des collisions dans la fonction gestion_bloque, après le code qui replace le personnage dans l'écran s'il en sortait.

Citer
2)
après avoir ajouter ses lignes de codes...comment je fait pour faire le test(if)

par exemple "joueur.y = obstacle.y - joueur.h;" si c'est a 0 ou plus petit je block le perso, mais ou et comment vuc il peut être de tous le côté svp? ???

Je ne suis pas sûr d'avoir bien compris ta question, mais il me semble que tu veux savoir si la gestion des collisions avec l'obstacle ne va pas faire sortir le personnage de l'écran.

En effet, si tu prends ton personnage en sandwich entre le bord de l'écran et l'obstacle et que l'obstacle est déplacé vers le bord de l'écran, le personnage va finir par se trouver "écrasé" entre les deux... On pourrait alors choisir dans ce cas de faire perdre la partie.

Pour gérer ça, tu pourrais vérifier à nouveau que le personnage est dans l'écran après la gestion des collisions.
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 11:54:32 am
yo j'ai enfin trouver pour faire la collision

:
Citer
/**[Gestion:::Collision]**/

if ((std::abs((sprite_perso.getPosition().x + 20) - (rect.getPosition().x + 20)) < blockSize) &&
(std::abs((sprite_perso.getPosition().y + 20) - (rect.getPosition().y + 20)) < blockSize))
{/*Gestion::X*/
if ((sprite_perso.getPosition().x >= 375) &&
(sprite_perso.getPosition().x <= 380))
        {
         sprite_perso.setPosition(sf::Vector2f(375, sprite_perso.getPosition().y));
        }

if ((sprite_perso.getPosition().x >= 430) &&
(sprite_perso.getPosition().x <= 440))
        {
         sprite_perso.setPosition(sf::Vector2f(440, sprite_perso.getPosition().y));
        }
/*Gestion::Y*/
if ((sprite_perso.getPosition().y >= 270) &&
(sprite_perso.getPosition().y <= 275))
{
    sprite_perso.setPosition(sf::Vector2f(sprite_perso.getPosition().x, 270));
}

if ((sprite_perso.getPosition().y >= 330) &&
(sprite_perso.getPosition().y <= 345))
{
    sprite_perso.setPosition(sf::Vector2f(sprite_perso.getPosition().x, 345));
}

}
}

même si ça marche ce n'est pas du tout au point :-\

Du coup qqn pourrais me passer ses lignes de codes(d'un mur) par exemple ou autre..


comment faire pour que le perso ne traverse pas le carre(d'une autre manière) svp ???
ou comment améliorer ce code?

Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 12:45:32 pm
Est ce que je me trompe ou tu utilise la fonction valeur absolue pour calculer une distance ? 
Citer
if ((std::abs((sprite_perso.getPosition().x + 20) - (rect.getPosition().x + 20)) < blockSize) &&
(std::abs((sprite_perso.getPosition().y + 20) - (rect.getPosition().y + 20)) < blockSize))

On a déjà fait mieux en terme de calcul de distance entre deux points  :P
Cependant tu n' en a as pas besoin a mon avis, si je comprends bien ce calcul te sert à determiner la distance entre ton perso et le carré et tu en déduis s'il y a collision c'est ca ? A ta place j'utiliserai plutot la fonction
sf::Rect::Intersects(const sf::Rect<U> &rectangle)
qui est faite pour ca ;)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 12:53:58 pm
Citer
sf::Rect::Intersects(const sf::Rect<U> &rectangle)
qui est faite pour ca ;)
Le problème est que j'ai stricktement aucune idée de comment ça marche ;D

Mon gros problème(d'apres moi) c'est que le personnage au coin gauche du carre et bas "bug"
au moment de la collision il y a comme une téléportation... :-\
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 01:01:05 pm
Pour le sf::Rect::Intersects,  voici un petit code de démo :
sf::FloatRect rect1(0,0,20,20);
sf::FloatRect rect2(10,10,30,30);
if(rect1.intersects(rect2))
     std::cout << "Collision" << std::endl;
else
     std::cout << "Pas collision" << std::endl;

Teste ce code avec differentes coordonnées, ca devrait être plus clair apres ;)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 01:17:51 pm
sf::FloatRect rect1(0,0,20,20);
sf::FloatRect rect2(10,10,30,30);
if(rect1.intersects(rect2))
     std::cout << "Collision" << std::endl;
else
     std::cout << "Pas collision" << std::endl;

Merci pour ton exemple, une dernière question :
"(0,0,20,20)" veulent dire les 4 angles de mon carrés?

si oui(ça semble logique), est-ce que je peux "blocké" mon personnage avec d'autre ligne de code(comme ::intersects) pour que mon perso je traverse pas mon rectangle..
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 01:28:15 pm
Citer
"(0,0,20,20)" veulent dire les 4 angles de mon carrés?
nope raté  :P
si c'etait ca, tu aurais 8 valeurs ;)
Ici ce sont les coordonnées du coin haut-gauche (0,0), la hauteur(20) et la largeur(20) 

Cette fonction te permet de détecter une collision, après à toi de la gérer pour empêcher ton personnage de passer à travers un mur. Quand j'aurais l'occasion je veux bien essayer de te faire un petit code de démonstration de gestion de collision, mais d'ici là, essaie de trouver tes propres solutions, tu les retiendras mieux, tu les comprendras mieux, et ce sera plus facile de les adapter à tes futurs projets  :)
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 01:31:26 pm
Accessoirement, je te conseille d'aller faire un tour par ici : http://www.sfml-dev.org/documentation/2.1-fr/
La doc est claire, et même si elle est en anglais ça reste très compréhensible (merci Laurent). Tu ne devrais pas avoir trop de problemes :)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 01:50:53 pm
Citer
Quand j'aurais l'occasion je veux bien essayer de te faire un petit code de démonstration de gestion de collision, mais d'ici là, essaie de trouver tes propres solutions, tu les retiendras mieux, tu les comprendras mieux, et ce sera plus facile de les adapter à tes futurs projets  :)


Merci, :-*, mais je pense quand même trouver d'ici 7 heures ce soir(enfin j'éspère :D)

Citer
Ici ce sont les coordonnées du coin haut-gauche (0,0), la hauteur(20) et la largeur(20) 
Donc la en forme un cube de 20-20 au cord 0, 0 == par deault?

pourquoi ma tu passer cette page
Citer
http://www.sfml-dev.org/documentation/2.1-fr/
elle parle ni de collision ni de "blockage"  ???



 
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 02:06:04 pm
Citer
Donc la en forme un cube de 20-20 au cord 0, 0 == par deault?
c est ça :)

Citer
pourquoi ma tu passer cette page
Citer
http://www.sfml-dev.org/documentation/2.1-fr/
elle parle ni de collision ni de "blockage"  ???
parce que c'est la doc de la SFML, et qu' on y trouve plein de choses intéressantes :D
Par exemple tu peux y lire plein de choses sur la classe sf::Rect, notamment les descriptions des fonctions intersects et contains, très utiles pour les collisions ;)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 02:09:45 pm
A ok... :D

pour ce code
if(rect1.intersects(rect2))
     std::cout << "Collision" << std::endl;
else
     std::cout << "Pas collision" << std::endl;
je l'ai remplacé par:

if(sprite_perso.intersects(rect))
     std::cout << "Collision" << std::endl;
else
     std::cout << "Pas collision" << std::endl;

et mon compilateur indique que ce n'est pas possible..
comment je fais?
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 02:18:02 pm
Tiens ? Ne t'aurais-je pas envoyé un lien intéressant tout à l heure ?  :P

Regarde bien la doc, intersects est une methode de la classe sf::Rect, et il me semble que sprite_perso est un objet de type sf::Sprite non ? ^^

Essaie d'utiliser sf::Sprite::getGlobalBounds(), qui renvoie, ô miracle, un sf::FloatRect ;)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 02:30:44 pm
Je connais déjà d'autre méthode pour intercepter la collision, mais aucune sur la collision, tu ne connais pas un "principe" pour que le perso, soie blocker comme sur un mur?

je vais lire les intersects je viens de finir de manger....
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 02:40:48 pm
Ne pas faire bouger ton perso me semble être un bon moyen de le rendre immobile :)
Au lieu de faire bouger ton perso directement après après détecter les événements claviers, calcule les coordonnées qu   aurait ton perso si tu le bougeais, et vérifie si ces coordonnées provoquent une collision. Si oui, tu ne fais pas bouger le perso, sinon tu lui appliques le mouvement :)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 02:45:47 pm
Citer
Au lieu de faire bouger ton perso directement après après détecter les événements claviers, calcule les coordonnées qu   aurait ton perso si tu le bougeais, et vérifie si ces coordonnées provoquent une collision. Si oui, tu ne fais pas bouger le perso, sinon tu lui appliques le mouvement :)

Je sais cela, mais quel calcule comme(en ligne de code)
y'a t'il 20 lignes de codes pour montrer comment le perso ne traverse pas le mur sans bug... pliz ???

j'ai deja réussis a ne le faire pas traverser mais des bug se sont produis au coins droite & bas :-\
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 03:03:09 pm
Je t ai dit que je n avais pas accès à mon PC pour l instant, je ne peux pas t écrire un programme de démo comme ça depuis mon tel, donc d ici que j ai accès à mon PC, et à moins que quelqu'un d autre ne te ponde le code, tu dois chercher tes propres solutions.
Fais toi un petit projet dans lequel tu te concentres uniquement sur ce problème, relis bien tout ce qui a été dit, car beaucoup de choses utiles ont été dites, et fais tes tests. Avec de la persévérance on finit toujours par réussir :)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 03:10:38 pm
Ok merci,
(dsl je ne savais pas que tu n'avais pas de pc)
je recommence a 0...
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 06:13:04 pm
 :-\La je n'arrive pas j'ai été sous 20 forum regarder 10 vidéo englaise et française... :-\

Le problème que que je suis un débutant et je ne sais même pas par ou commencer...

qqn aurait une vingène de lignes de code pour le début pour moi svp :-\ ???

Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 06:48:58 pm
Tiens essaye ça :)
Mais je te préviens, ça marche mais ce n'est qu'un code d'exemple, dans un vrai projet il faudrait améliorer beaucoup de choses ^^

Enfin, ca te donne une idée comme ca :)

Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 06:49:14 pm
int main()
{
    sf::RenderWindow window(sf::VideoMode(600, 600), "SFML works!");
    sf::Texture texture;
    if(!texture.loadFromFile("barbare.png", sf::IntRect(0,0,64,64)))
    {
        std::cout << "erreur" << std::endl;
        window.close();
    }
    sf::Sprite perso;
    perso.setTexture(texture);
    sf::Vector2f position(0,0);

    sf::RectangleShape mur;
    mur.setSize(sf::Vector2f(64,64));
    mur.setPosition(300,300);
    mur.setFillColor(sf::Color::Red);

    while(window.isOpen())
    {
        sf::Vector2f mouvement(0,0);
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Up))
            mouvement.y -= 0.1;
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Down))
            mouvement.y += 0.1;
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Right))
            mouvement.x += 0.1;
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Left))
            mouvement.x -= 0.1;

        sf::FloatRect virtalSprite(perso.getPosition().x + mouvement.x,
                                   perso.getPosition().y + mouvement.y,
                                   perso.getGlobalBounds().height,
                                   perso.getGlobalBounds().width);

        if(!virtalSprite.intersects(mur.getGlobalBounds()))
            perso.move(mouvement);
        else
            std::cout << "collision" << std::endl;

        window.clear(sf::Color::Black);
        window.draw(mur);
        window.draw(perso);
        window.display();
    }

    return 0;
}
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 08:24:37 pm
Salut! Merci Beaucoup!!! ;D :D ;) :)

Juste une Dernière petite question :

        sf::Vector2f mouvement(0,0);
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Up))
            mouvement.y -= 0.1;
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Down))
            mouvement.y += 0.1;
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Right))
            mouvement.x += 0.1;
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Left))
            mouvement.x -= 0.1;
Je peux bien évidément transormer en "gestion_clavier" comme je l'avais fais?

&
J'ai éxaminé le code, mais a aucun moment on dit ou le personnage dois s'arreter pour pas traversé le carré? qu'elle est cette magie :o


sur ce merci beaucoup pour ton aide! ;)






edit: je ne serais pas la cet semaine j'ai une gros test de script dans ma classe sur https://aseba.wikidot.com/fr:thymio (https://aseba.wikidot.com/fr:thymio) (une programmation d'un robot de EPFL) ou je suis le plus avancé de ma classe...(par a port à la SFML ;D)
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 08:29:56 pm
Je ne lui dit jamais de s'arreter effectivement ^^
regarde ici :
 if(!virtalSprite.intersects(mur.getGlobalBounds()))
            perso.move(mouvement);

ça veut dire ça :
si la position du personnage après déplacement ne provoque pas de collision avec le mur, alors deplace le personnage.Sinon ne le bouge pas. Tout simple :)

oui tu vas pouvoir réutiliser ta fonction gestion clavier, pas de souci :)
de toute facon il y a bcp de choses a ameliorer dans ce code ^^

relis mon code, il n y a qu une seule fois
sf::RenderWindow window(sf::VideoMode(600, 600), "SFML works!");
, c est juste toi qui a foire ton ctrl-v :p
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 08:44:30 pm
Oui dsl dailleur je l'ai enlevé dec j'ai compris (bug de ctr-v) ;D

perso.move(mouvement);
Je pourrais par exemple lui inscrite "gestion_clavier" a lieu de mouvement?





Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 09:08:44 pm
Si tu modifies ta fonction gestion_clavier pour qu elle renvoie un vector2f, alors oui c est possible :)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 11, 2014, 09:21:53 pm
Okey merci,
la ligne serait ~
perso.move(gestion_clavier)
?


Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 11, 2014, 10:10:02 pm
Nope ce serait
perso.move(gestion_clavier())
 
;)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 12, 2014, 05:37:46 pm
A aussi, pourquoi mon personnage bouge avec :

        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Left))
            mouvement.x -= 1;
Normalement ça ne devrais pas être

avec Perso.x?

Citer
Nope ce serait
perso.move(gestion_clavier())
 
;)

Non Marche pas mon compilateur affichie des fautes...

Mais pour la gestion clavier on peux aire un "mouvement" sans que le personnage bouge avec ces lignes?
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 12, 2014, 07:03:25 pm
Je crois que tu n as pas vraiment compris mon code, et c est bien parce que ça risquait d arriver que je te conseillais de chercher tes propres  solutions x)

La ligne
 mouvement.x -= 1;
ne fais pas bouger le personnage, elle donne une valeur a l abscisse du vecteur mouvement.
Ensuite, on vérifie que ce mouvement ne risque pas de provoquer une collision (if virtualSprite...) et enfin on applique ce mouvement au perso avec la ligne
perso.move(mouvement)

La fonction move prend un vector2 en paramètre, est ce que tu as bien modifié ta fonction gestion_clavier() pour qu elle renvoie un vector2f ? Et est ce que tu as bien pensé à mettre un point virgule après ? ^^'
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 13, 2014, 05:26:36 pm
Oui :

Au cas ou j'aurais eu faux pour transofrmer ma gestion_clavier a un vecteur2f
je lui rajoute "sf::vector2f"?

Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 13, 2014, 07:20:49 pm
Je comprends pas trop ta question, mais de toute manière, si tu veux pouvoir passer gestion_clavier() en paramètre, tu dois avoir dans ton code :
sf::Vector2f gestion_clavier()
{
sf::Vector2f monVecteur;
//Du code

return monVecteur;
}

//Plus loin

perso.move(gestion_clavier());
Titre: Re : Collision Tilemap
Posté par: G. le Mai 14, 2014, 04:24:45 am
Mec, si t'en es à galérer pour créer une fonction triviale tu ferais mieux d'approfondir ton apprentissage du C++ avant de te remettre à la SFML. Apprendre les 2 en même temps n'est pas une bonne solution.
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 14, 2014, 01:10:37 pm
A non escuse au moment ou j'ai finis d'envoyé j'ai trouver le bug... ;D
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 24, 2014, 09:50:29 am
De Retour :-\
yo tout le monde après une semaine de script intense sur "aseba sthudio",
je me suis remis sur le projet,(certins amis m'avaient conseillé de faire plusieurs test de collision en même temps, ajouter "des murs")

bref je me suis remis a créer un porjet, animer, remettre emplace mon fameux "rect" en signe de mur,
aucun problème mon personnage et stopé par la collision quand t'il va contre le mur...

*Je recrée un "mur" qui s'appelle "rect2"*

et cette fois le personnage ne sârrette par quand t'il est dans un des murs, j'ai donc r'ajouter :
            else
            {
            std::cout << "collision" << std::endl;
            }
Quand mon personnage entre en collision le message "collision" s'affiche bien mais il ne s'arrête toujours plus,
mon compilateur ne détecte aucun bug, et normalement cela devrais fonctionner :(

Pour test, j'ai ajouter :
            {
            std::cout << "collision" << std::endl;
            collision = false;
            }

        if(collision != false)
        {
            sprite_perso.move(mouvement);
        }
}
ça marche mais qu'avec un(que si je supprime un des rect) sinon rien ne se passe, comme en haut..

Voici La gestion des collision :

void gestion_PersoCollision()
{
        sf::Vector2f mouvement(0,0);
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Up))
        {
            mouvement.y -= speed;
            anim.y = Up;
        }

        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Down))
         {
             mouvement.y += speed;
             anim.y = Down;

         }

        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Right))
         {
             mouvement.x += speed;
             anim.y = Right;
         }

        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Left))
         {
            mouvement.x -= speed;
            anim.y = Left;
         }


                sf::FloatRect test(sprite_perso.getPosition().x + mouvement.x,
                                   sprite_perso.getPosition().y + mouvement.y,
                                   sprite_perso.getGlobalBounds().height,
                                   sprite_perso.getGlobalBounds().width);

        if(!test.intersects(rect.getGlobalBounds()))
            {
            collision = true;
            }
            else
            {
            std::cout << "collision" << std::endl;
            collision = false;
            }

        if(!test.intersects(rect2.getGlobalBounds()))
            {
            collision = true;
            }
            else
            {
            std::cout << "collision" << std::endl;
            collision = false;
            }

        if(collision != false)
        {
            sprite_perso.move(mouvement);
        }
}

Que devrais-je faire pour enlevé ce bug plutôt ennuyeux? :-\ ???

Titre: Re : Collision Tilemap
Posté par: OualidH38 le Mai 24, 2014, 11:17:53 am
C'est pas un bug, tu t'es trompé sur ton booléen "collision", tu le met à true quand il n'y a pas collision et à false quand il y a collision, alors que c'est l'inverse puisque ta dernière condition vérifie s'il y a une collision pour faire bouger ton sprite.
Ca devrait plus ressembler à ça :
 if(!test.intersects(rect.getGlobalBounds()))
            {
            collision = false;
            }
            else
            {
            std::cout << "collision" << std::endl;
            collision = true;
            }

        if(!test.intersects(rect2.getGlobalBounds()))
            {
            collision = false;
            }
            else
            {
            std::cout << "collision" << std::endl;
            collision = true;
            }

        if(!collision)
        {
            sprite_perso.move(mouvement);
        }
 
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 24, 2014, 11:26:21 am
Citer
C'est pas un bug, tu t'es trompé sur ton booléen "collision", tu le met à true quand il n'y a pas collision et à false quand il y a collision, alors que c'est l'inverse puisque ta dernière condition vérifie s'il y a une collision pour faire bouger ton sprite.
Ca devrait plus ressembler à ça :
 if(!test.intersects(rect.getGlobalBounds()))
            {
            collision = false;
            }
            else
            {
            std::cout << "collision" << std::endl;
            collision = true;
            }

        if(!test.intersects(rect2.getGlobalBounds()))
            {
            collision = false;
            }
            else
            {
            std::cout << "collision" << std::endl;
            collision = true;
            }

        if(!collision)
        {
            sprite_perso.move(mouvement);
        }
 
Oui merci est désolé j'ai script trop vite, mais ça marche toujours pas mon personnage est bloqué par le premier mur mais pas par le deuxième )=
Titre: Re : Collision Tilemap
Posté par: OualidH38 le Mai 25, 2014, 11:37:02 am
Essai ça:
if(!test.intersects(rect.getGlobalBounds()) || !test.intersects(rect2.getGlobalBounds()))
            {
            collision = false;
            }
            else
            {
            std::cout << "collision" << std::endl;
            collision = true;
            }


        if(!collision)
        {
            sprite_perso.move(mouvement);
        }
 
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 25, 2014, 01:32:45 pm
Um... non dsl, marche toujours pas :-\
 :'(

ici rien ne se passe, même le message "collision" ni viens plus,

comment dois-je faire pour ajouter ce fameux murs?

ou y'at'il une autre solutuion de collision entre certin décor?
Titre: Re : Collision Tilemap
Posté par: PtichapronRouge le Mai 26, 2014, 06:30:27 pm
Ou et comment as tu défini ton rect2 ? Il correspond bien à la boîte englobante du deuxième mur t'es sur ?
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 26, 2014, 07:24:47 pm
salut!

auffette j'ai fait tout comme le rect en rajoutant "2" :D

Mais a ce que j'ai vu, quan dje supprime "rect" le rect2 a la collision(mais du coup pas le 1)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 27, 2014, 06:07:05 pm
if(!test.intersects(rect2.getGlobalBounds()))
            {
            sprite_perso.move(mouvement);
            }
            else
            {
            std::cout << "collision" << std::endl;
            }

 if(!test.intersects(rect.getGlobalBounds()))
            {
            sprite_perso.move(mouvement);
            collision = false;
            }
            else
            {
            std::cout << "collision" << std::endl;
            }

Si je supprime "sprite_perso.move(mouvement);" à l'un ou un l'autre, mon personnage collisionne le mur
Mais, si je met les deux "sprite_perso.move(mouvement);"  le message "collision" s'affiche bien mais hélasse personnage bouge toujours...

Je vous passe toutes mes lignes de codes, car il serais alors surement possible que le bug vienne d'autre chose...

Main.cpp
#include <SFML/Graphics.hpp>
#include <iostream>
#include <string>
#include <cstdlib>
#include <cmath>
#include "Shape.h"

bool collision = false;
sf::RenderWindow window;
sf::RectangleShape rect;
sf::RectangleShape rect2;
int speed = 2;
sf::Vector2i positionSouris;
sf::Texture perso;
sf::Sprite sprite_perso;

enum Dir{ Down, Left, Right, Up };
sf::Vector2i anim(1, Down);
bool updateFPS = true;
int blockSize = 32;
int blockDemiSize = 16;

/**[Les Void] **/
void gestion_Persocollision();
void gestion_souris();
/**[Les Void] **/

int main()
{
//Création de la fenêtre 800x600
window.create(sf::VideoMode(800, 600), "Test SFML");
//Modifier la position
window.setPosition(sf::Vector2i(192, 0));
window.setFramerateLimit(60);

std::cout << "Lancement du jeu" << std::endl;

rect = PB_Rect(400, 300, 100, 100);
rect2 = PB_Rect(100, 300, 100, 100);

sf::Clock time;

if (!perso.loadFromFile("resources/image.png"))
{
std::cout << "Erreur chargement de image.png" << std::endl;
}

//En pofine les FPS
perso.setSmooth(true);

sprite_perso.setTexture(perso);

//Tant que la fenêtre est ouverte...
while (window.isOpen())
{
sf::Event event;
//Test des événements
while (window.pollEvent(event))
{
//Si on clique sur fermer
if (event.type == sf::Event::Closed)
window.close(); //On ferme la fenêtre

if (event.type == sf::Event::KeyPressed)
{ /*Pour activer l'anim*/
updateFPS = true;
}
else
updateFPS = false;
anim.x = 1;

}

/**[Les Void] **/
gestion_Persocollision();
gestion_souris();
/**[Les Void] **/

if (updateFPS == true)
{
if (time.getElapsedTime().asMilliseconds() >= 50)
{ /*On change d'animation toutes les 50 milli secondes*/
anim.x--;
if (anim.x * blockSize >= perso.getSize().x)
anim.x = 2;
time.restart(); /*On relance le timer*/
std::cout << "X: " << sprite_perso.getPosition().x << " Y: " << sprite_perso.getPosition().y << std::endl;
}
}
//on "coupe" les parties de l'image pour les réutiliser en animation..
sprite_perso.setTextureRect(sf::IntRect(anim.x * blockSize, anim.y * blockSize, blockSize, blockSize));

// On dessine, on affiche et on met à jour
window.draw(rect);
window.draw(rect2);
window.draw(sprite_perso);
window.display();
window.clear();
}

return 0;
}




void gestion_souris() /** changer  "sprite" par "rect" **/
{
if (sf::Mouse::isButtonPressed(sf::Mouse::Left))
{
//On récupère les coordonnées de la souris
positionSouris = sf::Mouse::getPosition(window);
//std::cout << "Mouse.x" << positionSouris.x << "Mouse.y" << positionSouris.y << std::endl;
int mouseX = positionSouris.x;
int mouseY = positionSouris.y;
sprite_perso.setPosition(mouseX, mouseY); // On positionne le rect
}
}

void gestion_Persocollision()
{
        sf::Vector2f mouvement(0,0);
        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Up))
        {
            mouvement.y -= speed;
            anim.y = Up;
        }

        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Down))
         {
             mouvement.y += speed;
             anim.y = Down;

         }

        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Right))
         {
             mouvement.x += speed;
             anim.y = Right;
         }

        if(sf::Keyboard::isKeyPressed(sf::Keyboard::Left))
         {
            mouvement.x -= speed;
            anim.y = Left;
         }


                sf::FloatRect test(sprite_perso.getPosition().x + mouvement.x,
                                   sprite_perso.getPosition().y + mouvement.y,
                                   sprite_perso.getGlobalBounds().height,
                                   sprite_perso.getGlobalBounds().width);

if(!test.intersects(rect2.getGlobalBounds()))
            {
            sprite_perso.move(mouvement);
            collision = false;
            }
            else
            {
            std::cout << "collision" << std::endl;
            }

 if(!test.intersects(rect.getGlobalBounds()))
            {
            sprite_perso.move(mouvement);
            collision = false;
            }
            else
            {
            std::cout << "collision" << std::endl;
            }
}

 

Shape.h
#ifndef DEF_SHAPE
#define DEF_SHAPE

#include <SFML/Graphics.hpp>


sf::RectangleShape PB_Rect(int posX, int posY, int width, int height)
{
    sf::RectangleShape rect(sf::Vector2f(width, height));
    rect.setPosition(posX, posY);
    rect.setFillColor(sf::Color(255, 0, 0, 255));

    return rect;
}
#endif // DEF_SHAPE
 
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 28, 2014, 02:07:50 pm
Bonjours je crois avoir trouver mon problème :

sprite_perso.move(mouvement); //Je l'ai mis plus loins juste avant que l'on affiche (window.draw(..)

 if(!test.intersects(rect.getGlobalBounds()))
            {
            rect.setFillColor(sf::Color::Blue);
            }
            else
            {
            rect.setFillColor(sf::Color::Red);
            }

 if(!test.intersects(rect2.getGlobalBounds()))
            {
            rect2.setFillColor(sf::Color::Blue);
            }
            else
            {
            rect2.setFillColor(sf::Color::Red);
            }
}

Quand je collisionne un des deux carrés, il se met en rouge.

Donc mon problème vien de mon "sprite_perso" car il bouge que sur un carré, est t'il possible que ça vienne de ce sprite?
Titre: Re : Collision Tilemap
Posté par: OualidH38 le Mai 28, 2014, 07:02:29 pm
Essai ça:

if(test.intersects(rect2.getGlobalBounds()) || test.intersects(rect.getGlobalBounds()))
            {
            std::cout << "collision" << std::endl;
            }
 else
            {
             sprite_perso.move(mouvement);
            }
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 29, 2014, 11:12:34 am
Super merci!
ça marche!

Mais pourquoi avant ça ne marchiat pas c'est la SFML qui a buger, je supose?
Vus dans plein de forum en conseil de mettre "si tu n'intersecte pas" il y aurais pas un "sprite_perso.dontMove(mouvement)"  ;D
Titre: Re : Collision Tilemap
Posté par: OualidH38 le Mai 29, 2014, 11:37:53 am
Non le problème venait de tes conditions if, tu avais une première condition qui disait :
- Si il n'y a pas de collision entre test et rect2 -> alors on fait bouger le sprite.
- Sinon -> écrit "collision" en console.

Et la deuxième condition qui disait :
- Si il n'y a pas de collision entre test et rect -> alors on fait bouger le perso.
- Sinon -> écrit "collision" en console.

Le problème il est là, imagine que "test" soit en collision avec "rect2" mais pas avec "rect", que va t-il se passer?

La première condition va dire :
"test est en collision avec "rect2", donc on affiche "collision" en console sans faire bouger le sprite.
La seconde condition va dire :
"test" n'est pas en collision avec "rect", donc on fait bouger le sprite.

Donc même s'il y avait collision entre test et l'un des rect le sprite bouger toujours.

Le code qui fonctionne dit seulement:
- S'il y a collision entre "test" et "rect2" ou entre "test" et "rect" -> alors affiche "collision" en console.
- Sinon -> faire bouger le sprite.

Donc s'il y a collision avec "rect2" ou bien "rect" le sprite ne bougera pas.

Hésite pas à poser des questions si tu n'as pas compris  ;)
Titre: Re : Collision Tilemap
Posté par: spyker18 le Mai 29, 2014, 04:53:08 pm
Ok merci :)