Bienvenue, Invité. Merci de vous connecter ou de vous inscrire. Avez-vous oublié d'activer ?

Voir les contributions

Cette section vous permet de consulter les contributions (messages, sujets et fichiers joints) d'un utilisateur. Vous ne pourrez voir que les contributions des zones auxquelles vous avez accès.


Messages - yovano_c

Pages: [1]
1
Général / Re : Pathfinding Problem
« le: Octobre 20, 2016, 01:54:38 am »
Je pense que je m'approche de la solution, ça ne marche toujours pas, mais en venant vous dire où j'en suit peut être que quelqu'un sauras m'aider...

Pour commencer, ma fonction getSpeed() sur un player, j'aimerais que ça correspond à la vitesse ou le joueur ira du centre d'une tile au centre de la prochaine, seulement, c'est en isométrique, et les centres des tiles voisines ne sont pas à la même distance, mais c'est pas le plus gros problème.
Ensuite, j'envois donc à la fonction update de mon player, le clock.restart().asSeconds() ...

Voici ma fonction update pour l'instant....

void Player::update(float dt, std::list<MapTile*> *path)
{

    // for (auto& tile: *path)
    // {
    //      std::cout << tile->getId() << " -> ";
    //      path->pop_front();
    // }

    if (!path->empty())
    {
        const float unitsPerTick = this->getSpeed() * dt; // Speed in Units per tick

        std::cout << unitsPerTick << std::endl;
        auto waypoint = path->front();

        sf::Vector2i movementVector = sf::Vector2i(waypoint->getPositionCenter().x - this->getPositionCenter().x,
        waypoint->getPositionCenter().y - this->getPositionCenter().y);

        std::cout << movementVector.x << "," << movementVector.y << std::endl;

        float moveVecLength = sqrt((movementVector.x * movementVector.x) + (movementVector.y * movementVector.y));

        std::cout << "moveVecLength: " << moveVecLength << std::endl;

        if (moveVecLength < unitsPerTick)
        {
            this->move(movementVector.x, movementVector.y);
            this->setCurrentTile(waypoint);
            std::cout << waypoint->getId() << " -> " << std::endl;
            path->pop_front();
        }
        else {
            movementVector.x = movementVector.x / moveVecLength;
            movementVector.y = movementVector.y / moveVecLength;

            movementVector = sf::Vector2i(movementVector.x * unitsPerTick, movementVector.y * unitsPerTick);

            this->move(movementVector.x, movementVector.y);
        }
    } else {
        counterAnimation = 0;
    }

    switch (mDirection) {
        case Up: setRect(0); break;
        case Down: setRect(0); break;
        case Left: setRect(0); break;
        case Right: setRect(0); break;
        case DownLeft: setRect(0); break;
        case UpLeft: setRect(0); break;
        case UpRight: setRect(0); break;
        case DownRight: setRect(0); break;
        default: break;
    }

    if (rand() % 4 == 1)
        this->counterAnimation++;
    if (this->counterAnimation >= (this->nbAnimation - 1))
        this->counterAnimation = 0;
}

Seulement mon personnage fait du surplace, en ayant quand même les animations de deplacements (bras et jambes qui se mettent en route), et j'obtient ceci dans mon terminal avec le std::cout de la fonction (ça tourne en rond quoi...) :

moveVecLength: 31
0.033684
0,31
moveVecLength: 31
0.035512
0,31
moveVecLength: 31
0.033396
0,31
moveVecLength: 31
0.034238
0,31
moveVecLength: 31
0.033816
0,31
moveVecLength: 31
0.03396
0,31
moveVecLength: 31
0.033524
0,31
moveVecLength: 31
0.035762
0,31
moveVecLength: 31
0.03571
0,31
moveVecLength: 31
0.30348
0,31
moveVecLength: 31

Merci beaucoup..

2
Général / Pathfinding Problem
« le: Octobre 19, 2016, 12:35:34 pm »
Bonjour à tous,
J'ai beau réfléchir depuis maintenant plusieurs jours mais je viens vous demander de l'aide car là je ne sais même pas comment 'bien' implémenter ce que je voudrais faire. Je m'explique:

Je veux juste que mon personnage suive le chemin trouvé par mon système de pathfinding, en utilisant plusieurs choses, j'ai un attribut Speed qui es propre à chaque personnage, et j'ai donc une fonction pour récupéré les coordonnées du milieu de la Tile ( sf::Vector2f getPositionCenter(); ).

Cependant, je ne sais pas vraiment ou me placer dans mon code, ni comment réellement faire ça..

Voilà où j'en suit:

Dans ma gestion d'évènements:
sf::Vector2i localPosition = sf::Mouse::getPosition(mWindow);
sf::Vector2f worldPos = mWindow.mapPixelToCoords(localPosition);

mTileClicked = mMap.getTileWithClick(worldPos);
if (mTileClicked != nullptr)
{
     std::cout << "ID: " << mTileClicked->getId() << " - isWalkable = " << mTileClicked->isWalkable;
     std::cout << " - Position: (" << mTileClicked->getPositionOnMap().x << "," << mTileClicked->getPositionOnMap().y << ")" << std::endl;

     if (mTileClicked->isWalkable && mTileClicked != mPlayer.getCurrentTile() && mTileClicked != mPlayer.getDestinationTile())
     {
          //mPlayer.setTile(mTileClicked);
          //mPlayer.setDestinationTile(mTileClicked);
         mPath = mPathfinder.findPath(mPlayer.getCurrentTile(), mTileClicked);
     }
}


J'avais ensuite penser à implémenter ça dans ma fonction update du player que j'actualise avant chaque affichage que j'appelle du coup de la sorte

mPlayer.update(mElapsed, mPath);

et voilà ma fonction update :

void Player::update(float dt, std::list<MapTile*> path)
{

    if (!path.empty())
    {
        std::cout << path.front()->getId() << std::endl;
    }

    switch (mDirection) {
        case Up: setRect(0); break;
        case Down: setRect(0); break;
        case Left: setRect(0); break;
        case Right: setRect(0); break;
        case DownLeft: setRect(0); break;
        case UpLeft: setRect(0); break;
        case UpRight: setRect(0); break;
        case DownRight: setRect(0); break;
        default: break;
    }
}

Simplement là je segfault en appelant l'update dans la boucle.... je recupere même pas l'id dans la fonction.. c'est vraiment le mPath qui pose problème... déja voici mon premier problème, c'est où me placer dans mon code pour faire bouger mon personnage.... et ensuite j'ai rechercher mais je n'ai que du pseudocode trouver sur internet pour bouger mon personnage mais je ne le comprend pas parfaitement:

if (pathFound)
{
    // A path has been found
    const float unitsPerTick = 8; // Speed in Units per tick
    auto waypoint = waypoint_queue.front(); // The waypoint in use

    Vector2i movementVector = Vector2i(waypoint.x - this->character.getPosition().x,
        waypoint.y - this->character.getPosition().y);

    float moveVecLength = sqrt((movementVector.x * movementVector.x) + (movementVector.y * movementVector.y));

    if (moveVecLength < 0.2)
    {
        /// Move the player by the movement vector
        this->character.setPosition(this->character.getPosition().x + movementVector.x, this->character.getPosition().y + movementVector.y);    
        waypoint_queue.pop_front();
    }
    else {
        /// Normalize the movement vector          
        movementVector.x = movementVector.x / moveVecLength;
        movementVector.y = movementVector.y / moveVecLength;

        /// Scale the movement vector by the units per tick
        movementVector = Vector2i(movementVector.x * unitsPerTick, movementVector.y * unitsPerTick);

        /// Move the character by the new movement vector
        this->character.setPosition(this->character.getPosition().x + movementVector.x, this->character.getPosition().y + movementVector.y);
    }

    if (waypoint_queue.empty())
        pathFound = false;
}

PS: Comme vous pouvez le voir j'ai déjà aussi garder 2 petites variables pour garder l'avancer sur les tiles si ça peut aider, getCurrentTile() et getDestinationTile() avec les setters aussi.. j'ai pour le personnage getSpeed(), et du coup pour chaque tile getPositionCenter() mais je ne sais pas implémenter ça correctement, merci de m'aider :/

3
Graphique / Re : ConvexShape Problem
« le: Octobre 19, 2016, 12:19:48 pm »
J'ai résolu le problème. Je connais très bien mes portées de variables. C'est juste qu'il faut passer la référence au GetConvex() et GetSprite(), qui deviennent donc:

sf::Sprite& getSprite() { return mSprite; };
    sf::ConvexShape& getConvex() { return mConvex; };

4
Graphique / ConvexShape Problem
« le: Octobre 16, 2016, 07:34:25 pm »
Bonjour,

J'ai ma classe Entité comme suit :

#ifndef Entity_hpp
#define Entity_hpp

#include <vector>
#include <cmath>
#include <iostream>
#include <SFML/Graphics.hpp>

class Entity
{
public:
    Entity(int width, int height);
   
    void update();
   
    void setDimension(int width, int height);
    void setDimension(sf::Vector2i dim);
    const sf::Vector2i getDimension() { return sf::Vector2i(mSpriteWidth, mSpriteHeight); };
   
    sf::Sprite getSprite() { return mSprite; };
    sf::ConvexShape getConvex() { return mConvex; };
   
    void setPosition(sf::Vector2f position) { mPosition = position; };
    sf::Vector2f getPosition() { return mPosition; };
   
private:
    sf::Sprite mSprite;
    sf::ConvexShape mConvex;
    int mSpriteWidth = 50;
    int mSpriteHeight = 50;
    sf::Vector2f mPosition;
};

#endif /* Entity_hpp */
 

Mon problème est le suivant :

Si, dans une classe qui hérite de celle là, comme PlayerTile, IsoTile, ou quelque chose du genre, c'est une classe relativement abstraite "Entity", je recupère mon mConvex, ou mSprite, avec mon getConvex() ou getSprite() ça ne me dessinnera rien, en revanche, si je passe la variable en protected au lieu de private et que je l'utilise telle quelle tout fonctionne mais je ne comprend pas pourquoi, pourrais-t-on m'expliquer?

Merci

5
Graphique / Maps Isométriques Pathfinding
« le: Septembre 04, 2016, 03:15:28 pm »
Bonjour.

Dans ma gestion d'évènements, au clique gauche de la souris je fais :

sf::Vector2i localPosition = sf::Mouse::getPosition(window);
sf::Vector2f worldPos = window.mapPixelToCoords(localPosition);
                           
tileClicked = map.getTileWithClick(worldPos);
if (tileClicked != nullptr)
{
     std::cout << "ID: " << tileClicked->getId() << " - isWalkable = " << tileClicked->isWalkable;
     std::cout << " - Position: (" << tileClicked->getPositionOnMap().x << "," << tileClicked->getPositionOnMap().y << ")" << std::endl;
                               
     if (tileClicked->isWalkable && tileClicked != p.getMapTile() && tileClicked != p.dstTile)
     {
          p.dstTile = tileClicked;
          pf.findPath(p.getMapTile(), tileClicked);
     }
}
 

Dans ma boucle principale je veut faire en sorte que le joueur suive ce chemin calculé par le système de pathfinding. je fais donc :

 p.followPath(pf.path);

mais il n'avance que d'une seule case je ne sais pas pourquoi....
et dans la console la ligne
std::cout << mapTile->getId() << " -> ";
affiche l'id de la map suivante a parcourir mais ça tourne en boucle.. je suppose que c'est le pop_front ou quelque chose du genre qui ne supprime pas ou merci de m'aider :/
Je vous met une vidéo pour que vous compreniez. Merci -> https://vid.me/Nbom

PS:
void Player::followPath(std::list<MapTile*> path)
{
    //std::cout << mapTile->getId() << std::endl;
   
    if (!path.empty())
    {
        mapTile = path.front();
       
        //std::cout << path.front()->getId() << " -> ";
        float px = mapTile->mConvex.getPosition().x;
        float py = mapTile->mConvex.getPosition().y;
        float ex = mTile.mConvex.getPosition().x;
        float ey = mTile.mConvex.getPosition().y;
        float x = (ex - px);
        float y = (ey - py);
        float v = sqrtf((x * x) + (y * y));
        float unitx = (x / v);
        float unity = (y / v);
        float movex = -mMovementSpeed * unitx;
        float movey = -mMovementSpeed / 2 * unity;
       
        if (mTile.getPositionInWindow() != mapTile->getPositionInWindow())
        {
            if (movex < 0)
            {
                if (movey < 0)
                    move(UpLeft);
                else if (movey > 0)
                    move(DownLeft);
                else if (movey == 0)
                    move(Left);
            }
            else if (movex > 0)
            {
                if (movey < 0)
                    move(UpRight);
                else if (movey > 0)
                    move(DownRight);
                else if (movey == 0)
                    move(Right);
            }
            else if (movex == 0)
            {
                if (movey < 0)
                    move(Up);
                else if (movey > 0)
                    move(Down);
            }
        }
        else
        {
            std::cout << mapTile->getId() << " -> ";
            path.pop_front();
        }
    }
    else
    {
        counterAnimation = 0;
    }
}
 

6
Graphique / Maps Isométriques Questions
« le: Août 25, 2016, 08:44:15 pm »
Bonsoir,
J'ai eu beaucoup de problèmes avec mon implementation de maps isométriques. A première vue tout vas bien sauf que j'ai des problèmes avec les collisions.
J'aimerais pour m'aider dans les tests de collisions afficher le RectangleShape de mon tile "mur" pour l'instant. sauf que je ne comprend pas comme dessiner le RectangleShape de ces tiles isométriques sachant que mes tiles font 53*36 :

J'ai fait:

float size = sqrtf(powf((53 / 2), 2) + powf((36 / 2), 2));
mRect.setSize(sf::Vector2f(size, size));
mRect.rotate(45.f);

Mais ça me donne ça:


J'ai donc plusieurs questions:

1/ Comment dessiner mes RectangleShape des tiles isométriques en fonction de la hauteur et la largeur de ces tiles pour gérer les collisions parfaitement?
2/ Comment je pourrais implémenter mon système de collision correctement? Parce qu'en regardant dans la console (sur le screen) on voit que le player est en collision avec le tile bleu (parce qu'en effet le RectangleShape du player passe bien au dessus de celui du tile 'mur'. alors qu'en realité le player se trouve quand même beaucoup plus loin devant..

Pages: [1]