-
Bonjour,
Ayant récemment installé la SFML je fais quelques tests de programme.
Mais j'ai un problème pour le déplacement d'un personnage, en effet dès que je reste appuyer sur la touche 'Z' par exemple mon sprite ne bouge qu'au bout d'un moment (comme dans un éditeur de texte lorsque l'on reste appuyer sur une lettre) . Comment régler le problème ?
Voici mon code :
#include <SFML/Graphics.hpp>
int main()
{
sf::RenderWindow window(sf::VideoMode(400, 400), "SFML Test");
sf::Texture tPerso;
sf::Sprite sPerso;
sf::Image iPerso;
if(!iPerso.loadFromFile("Personnage.png"))
{
}
sf::Color fond=iPerso.getPixel(0,0);
iPerso.createMaskFromColor(fond);
tPerso.loadFromImage(iPerso);
sPerso.setTexture(tPerso);
window.setKeyRepeatEnabled(true);
while (window.isOpen())
{
sf::Event event;
while (window.pollEvent(event))
{
if (event.type == sf::Event::Closed)
window.close();
if(event.type==sf::Event::KeyPressed)
{
switch(event.key.code)
{
case sf::Keyboard::Z:
sPerso.move(0,-1);
break;
case sf::Keyboard::Q:
sPerso.move(-1,0);
break;
case sf::Keyboard::S:
sPerso.move(0,1);
break;
case sf::Keyboard::D:
sPerso.move(1,0);
break;
default: break;
}
}
}
window.clear(sf::Color::White);
window.draw(sPerso);
window.display();
}
return 0;
}
-
Merci de lire les tutoriels avant de poster.
Parfois, les gens utilisent l'évènement KeyPressed pour gérer des mouvements continus. Or, cela ne produira pas des mouvements continus mais plutôt saccadés : lorsque vous maintenez une touche vous n'obtenez en effet que quelques évènements (souvenez-vous du délai de répétition). Les mouvements fluides peuvent être obtenus en utilisant les entrées temps réel avec sf::Keyboard (voir le tutoriel dédié).
(oui, c'est aussi écrit en rouge dans le tutoriel)
-
Voici ce que j'avais fait avant de changer
while (window.pollEvent(event))
{
if (event.type == sf::Event::Closed)
window.close();
if(event.type==sf::Event::KeyPressed)
{
if(sf::Keyboard::isKeyPressed(sf::Keyboard::Z))
sPerso.move(0,-1);
if(sf::Keyboard::isKeyPressed(sf::Keyboard::Q))
sPerso.move(-1,0);
if(sf::Keyboard::isKeyPressed(sf::Keyboard::S))
sPerso.move(0,1);
if(sf::Keyboard::isKeyPressed(sf::Keyboard::D))
sPerso.move(1,0);
else;
}
}
window.clear(sf::Color::White);
window.draw(sPerso);
window.display();
}
et ça ne marchait pas non plus. Ou alors j'ai mal lu le tuto
-
Si tu utilises ces fonctions dans la boucle d'évènements tu perds tout l'intérêt. Elles existent justement pour ne pas être lié aux évènements, et pouvoir savoir à tout moment l'état de ton clavier.
Là avec ce code tu ne vas quand même bouger que si un évènement survient, donc tu n'as rien gagné du tout par rapport à ton précédent code.
-
excuse moi mais j'ai du mal à comprendre, où devrais je donc mettre ces conditions ?
-
Tu veux bouger ton sprite quand ? Quand un évènement clavier survient, ou bien tout le temps en continu ? Tout le temps en continu -> donc tu mets ce code directement dans ta boucle de jeu, hors de la boucle d'évènements ;)
-
je viens de le faire mais maintenant le personnage ne bouge plus quoi que je fasse.
while (window.isOpen())
{
sf::Event event;
while (window.pollEvent(event))
{
if (event.type == sf::Event::Closed)
window.close();
}
if(event.type==sf::Event::KeyPressed)
{
if(sf::Keyboard::isKeyPressed(sf::Keyboard::Z))
sPerso.move(0,-1);
if(sf::Keyboard::isKeyPressed(sf::Keyboard::Q))
sPerso.move(-1,0);
if(sf::Keyboard::isKeyPressed(sf::Keyboard::S))
sPerso.move(0,1);
if(sf::Keyboard::isKeyPressed(sf::Keyboard::D))
sPerso.move(1,0);
else;
}
window.clear(sf::Color::White);
window.draw(sPerso);
window.display();
}
-
Tu n'es plus dans la boucle d'évènements, donc il ne faut plus utiliser ton sf::Event.
-
Merci, ça marche.
Sinon vu qu'il se déplaçait rapidement j'ai fait window.setFramerateLimit(30); est ce la bonne méthode ?
-
Mieux vaut définir une vitesse et faire un déplacement en fonction du temps écoulé ; comme ça tu as du code qui est indépendant du framerate.
const float speed = 100; // 100 unités / seconde
sf::Clock clock;
while (window.isOpen())
{
...
float elapsed = clock.restart().asSeconds();
if (sf::Keyboard::isKeyPressed(sf::Keyboard::D))
sprite.move(speed * elapsed, 0);
...
}
-
Ah oui ! c'est vraiment pas mal, j'y aurais pas pensé. Merci!