Un petit soucis de logique

Un petit soucis de logique - C++ - Programmation

Marsh Posté le 16-02-2008 à 22:37:16    

Bonjour,
bon alors je travail actuellement sur un p'tit jeu (FallDown pour ceux qui connaissent), le principe est de faire passer une balle dans les ouvertures des lignes qui défilent vers le haut. L'objectif étant de franchir un maximum de lignes sans atteindre le haut de la fenêtre.
 
Donc à chaque fois que ma balle se pose sur une ligne, dans ma boucle principale j'appelle une méthode de mon objet Line destinée à me dire si l'objet dont je lui passe les coordonnées se trouve dans une ouverture (ce qui me sert à la faire chuter si c'est bien le cas).
 
Cette méthode reçoit donc la position X de l'objet ainsi que sa largeur.
 
A partir de ces informations elle va parcourir la liste des ouvertures disponibles et vérifier à chaque fois si l'objet peut passer dans l'ouverture (avec une tolérance de 10px).
 
Ainsi :

Code :
  1. bool Line::inHall(float width, float posX)
  2. {
  3.     for(int i=0;i<nbHall;i++)
  4.         if ( posX >= brick[hallPos[i]].GetLeft()-10
  5.              && posX+width <= brick[hallPos[i]].GetLeft()+brick[hallPos[i]].GetWidth()+10 )
  6.              return true;
  7.     return false;
  8. }

Mais ce code pose un problème, lorsque deux ouvertures sont adjacentes, si la balle se pose au milieu des deux (sur la jointure) et bien elle ne chute pas. C'est logique.
 
Cela-dit, je ne sais pas trop comment m'en sortir... Bon c'est pas spécifique au langage, c'est plus de la logique là.
 
Bref, un coup de main serait le bien venu.
 
En vous remerciant.


Message édité par dwogsi le 17-02-2008 à 02:42:54

---------------
-- Debian -- Le système d'exploitation universel | Le gras c'est la vie! | /(bb|[^b]{2})/
Reply

Marsh Posté le 16-02-2008 à 22:37:16   

Reply

Marsh Posté le 17-02-2008 à 01:04:39    

et tu veux que la balle chute si elle e trouve sur la jointure ?

Reply

Marsh Posté le 17-02-2008 à 02:16:27    

Exactement!


---------------
-- Debian -- Le système d'exploitation universel | Le gras c'est la vie! | /(bb|[^b]{2})/
Reply

Marsh Posté le 17-02-2008 à 09:28:25    


Cherche plutot l'inverse : au lieu de verifier si tu es dans un couloir, verifie si tu es dans un mur.

Reply

Marsh Posté le 17-02-2008 à 13:06:03    

ou plutot, au lieu de faire deux trous conjoint, en faire un seul...

Reply

Marsh Posté le 17-02-2008 à 14:09:21    

Ouai c'est aussi ce que je me disais. En fait une fois que j'ai déterminer la liste de mes ouvertures, je peux les trier par ordre croissant et déterminer ensuite les ouverture adjacentes pour en créer de nouvelles plus grandes.
 
Dites moi si je me trompe, de toute façon je vais tester ça.
 
Mais avant je vais quand même voir ce que ça donne si je teste l'inverse comme proposé par Ace17.


---------------
-- Debian -- Le système d'exploitation universel | Le gras c'est la vie! | /(bb|[^b]{2})/
Reply

Marsh Posté le 18-02-2008 à 18:40:15    

J'ai réfléchi longuement à ton problème, on reponsant la problématique. Et je crois avoir trouvé la solution juste nécessaire. Sans recalculer les trous, ni ajouter de nouvelles fonctions. Et qui fonctionne dans des conditions extrèmes, par exemple :
En supposant que la largeur de la balle et des trous est déterminé au hasard, on pourrait avoir des situations avec 25 minuscules trous tous à côte les uns des autres qui définissent un grand trou.  
 
Pour cela je considère que ta balle correspond à un segment, avec 2 côtés.  
Gauche = posX  
Droit = posX + Width  
 
Je souhaite vérifier que le segement n'a en dessous de lui que du vide. Pour cela je vérifie trou par trou, jusqu'à ce qu'il n'y ai plu de zone de segment à tester. C'est à dire que pour chaque trou rencontré, je vais enlever du segment la zone au dessus du trou. Si ça passe c'est que tout le segment était au-dessus de 1 ou plusieurs trous. Sinon c'est que la balle rebondie.  
 
On cherche si Droit tombe au milieu d'un trou, si c'est le cas, il nous reste à tester le restant du segment entre gauche et le bord du trou concerné. Tout cela jusqu'à ce qu'il n'y ait plus de segment à tester
 
en Pseudo algo ça fait :
 
Fonction TombesTu(gauche , droit)
Si taille <=0  ? Retourne VRAI
Sinon
 Cherchons parmis les trous un qui est en dessous de Droit  
   (Ya un Trou) Retourne TombesTu(gauche , Trou.bordgauche)
   (Ya pas Trou) Retourne FAUX
 

Code :
  1. bool Line::inHall(float width, float posX)
  2. {
  3.   if ( width <= 0 ) return true;
  4.   for(int i=0;i<nbHall;i++)
  5.     if ( posX+width > brick[hallPos[i]].GetLeft()
  6.       && posX+width < brick[hallPos[i]].GetLeft() + brick[hallPos[i]].GetWidth())
  7.       return inHall(brick[hallPos[i]].GetLeft()-posX , posX);
  8.   return false;
  9. }

 

Reply

Marsh Posté le 19-02-2008 à 03:05:39    

il y a tres simple comme solution
faire une petite fonction de collision
un mur, c'est une zone
cette zone fait une certaine dimension en x et en y
et la balle aussi, x, y, xl, yl
une fonction de colision est tres simple à creer, il suffit de tester un objet et un tableau composé d'objets
si l'objet touche un des elements du tableau, alors il est en collision, et donc, il se passe quelque chose
le falldown, c'est pas tres sorcier, d'ailleur, je vais en coder un rien que pour voir si je dis vrai...

Reply

Sujets relatifs:

Leave a Replay

Make sure you enter the(*)required information where indicate.HTML code is not allowed