SFML community forums
Help => Graphics => Topic started by: Overlord on October 03, 2011, 11:14:14 pm
-
I used trigonometric cicrcle to make ball sprite move on a circular path. It does, only thing is that the path is always moving and changing radius. Don't know if it is a float rounding error or my computer going mad, or probably a semantic error. I'd be grateful if someone took a look at code and helped my find the error.
Sry if code isn't readable. I commented only logic parts.
#include <SFML\Graphics.hpp>
#include <cmath>
int main()
{
sf::VideoMode VMode(800, 600, 32);
sf::RenderWindow Window(VMode, "Test");
sf::Texture Ball;
if (!Ball.LoadFromFile("ball.png"))
return 1;
double speed = 1;//constants and start values
long double angle = 90;
const double rad = 57.2957795;
double ang = 0;
sf::Sprite ball(Ball);
ball.SetPosition(400,300);
ball.SetScale(0.1,0.1);
sf::Event Event;
while (Window.IsOpened())
{
while (Window.PollEvent(Event))
{
if (Event.Type == sf::Event::Closed)
{
Window.Close();
break;
}
}
if (angle > 360)//if angle exceeds 360
angle -= 360;//reset it
angle += speed * Window.GetFrameTime();//angle in degrees
ang = angle/rad;//angle in radians
ball.Move(std::sin(ang),std::cos(ang));//move on a circular path
Window.Clear(sf::Color(255,0,0));
Window.Draw(ball);
Window.Display();
}
return 0;
}
-
You need to use
ball.SetPosition(radius*std::sin(ang), radius*std::cos(ang));
Set radius to something because moving on a circle radius 1 wont look that interesting for you.
Also, stylistically, you have two variables named angle and ang, both storing the same data but one is in radians, one in degrees, and the names don't reflect this at all, when your project gets bigger how are you going to remember to change one when the other changes, and how are you going to remember which is which?
-
Found the problem. It isn't graphic package. Window.GetFrameTime() returns 1 or 0. Tried with Clock class, but still the same problem. Anyone know a fix for it?
-
Window.GetFrameTime() returns 1 or 0
In recent SFML 2, it returns an integer number of milliseconds.
-
:lol: I used old revision with new docs. Back to cmake and compiling. Sry for wasting your time :lol:
-
ball.Move(std::sin(ang),std::cos(ang));
You still have the maths wrong though. The Move(x2, y2) function will move it from it's current position (x, y) to (x + x2, y + y2).
What I've found is that this will draw a circle, but the radius will depend on the frame rate.
See high framerate http://grab.by/b0lK
See low framerate http://grab.by/b0lL
If the frame rate is variable enough, then it won't even draw a circle see http://grab.by/b0lI.
If you want it to move along a fixed circle at a fixed rate, use the code I posted in my first reply