Framerate independence?

Hello everyone! :smiley:

Iā€™ve asked this same question on this same mailing list 2 or 3 times
already. I always lose the code. >:-(

Whatā€™s the code to get framerate independence? I looked it up on Google
but the tutorials either use code from other libraries, assume you know
what such and such function is, or uses undeclared variablesā€¦ :-/

I remember something about delta timeā€¦ Anyone know what it is? Thanks! :wink:

Oh wow. Please do not do it like this. This is a busy wait which
will attempt to eat 100% of your CPU doing nothing until the appropriate
time. It is really horrible for any multitasking OS.

It is much better to use SDL_Delay as mentioned on the usingtimers.html
page.

RCAF wrote:> Hi!

Look this page:

http://www.libsdl.org/intro.en/usingtimers.html

but I prefer to do it so:

Uint32 t1, t2;
int fps = 100;
int done=1;

while (!done)
{
t1 = SDL_GetTicks(); // Initial time

// do something... input, game logic, drawing, ...

do
{
    t2 = SDL_GetTicks();  // Current time
} while ((t2 - t1) <= 1000/fps);

}

Regards!


SDL mailing list
SDL at lists.libsdl.org
http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

(Thereā€™s another problem with this code which is that it uses an integer
divide for the target timeā€¦ so it will miss for most values of the
frame time. For example, if you try to specify 60fps, you will get
something like 62.5fps. So I also wouldnā€™t recommend just trying to
insert a sleep into this code unless you really think about it.)

Jonathan B. wrote:> Oh wow. Please do not do it like this. This is a busy wait which

will attempt to eat 100% of your CPU doing nothing until the appropriate
time. It is really horrible for any multitasking OS.

It is much better to use SDL_Delay as mentioned on the usingtimers.html
page.

RCAF wrote:

Hi!

Look this page:

http://www.libsdl.org/intro.en/usingtimers.html

but I prefer to do it so:

Uint32 t1, t2;
int fps = 100;
int done=1;

while (!done)
{
t1 = SDL_GetTicks(); // Initial time

// do something... input, game logic, drawing, ...

do
{
    t2 = SDL_GetTicks();  // Current time
} while ((t2 - t1) <= 1000/fps);

}

Regards!


SDL mailing list
SDL at lists.libsdl.org
http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org


SDL mailing list
SDL at lists.libsdl.org
http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

Although delta time (dtime) is simple and convenient to implement, it
has many drawbacks:

  1. The game will behave differently each time it is run, thus making
    debugging more difficult ā€“ you will have problems reproducing the
    execution of the game in exactly the same manner.

  2. If you have hiccups in the game while it is executing, the result
    will be very obvious, as objects will jump further than normal due to
    the irregular gap in dtime.

  3. While debugging the game, if you interrupt execution, the game will
    utilize the change in dtime when you resume execution of the program,
    and the result will be very messy (dtime could be on the order of 30
    seconds).

The techniques described by David Olofson using a fixed game engine
counter and running the game at a fixed frequently, much like a CPU
clock, provide for an amazing performance. It also allows you to stop
the game and run it one clock cycle at a time during debugging (quite cool!)

Paul Lowe
paul at tetravista.net

RCAF wrote:> Another way is:

Uint32 t1, t2, dt;

while(!done)
{
t1 = SDL_GetTicks();

// Do something...

t2 = SDL_GetTicks();

// delta time
dt = t2 - t1;

x = x + vx*dt       // Use dt to calculate new position...

// drawing...

}


SDL mailing list
SDL at lists.libsdl.org
http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

Mr. Microcontroller-Esque-Named-Dude,

I would strongly encourage you to do a search in the mailinglist
archives for ā€œDavid Olofsonā€, and look for entries that match framerate
independence. I consider him an expert on the topic and he has posted
about it many times here before.

He taught me how to do framerate independence ā€“ and he knows many
different ways to do it depending on your needs ā€“ some having benefits
over others.

I suggest you take a look at his Fixed Rate Pig program (heā€™s a very
talented coder, by the way, and I envy his C programming techniques):

http://olofson.net/mixed.html

If you still canā€™t figure it out, even after reading whatā€™s already in
the mailing list archives, message me and maybe I can explain it a bit.

Best of Wishes,

Paul Lowe
paul at tetravista.net

L-28C wrote:> Hello everyone! :smiley:

Iā€™ve asked this same question on this same mailing list 2 or 3 times
already. I always lose the code. >:-(

Whatā€™s the code to get framerate independence? I looked it up on Google
but the tutorials either use code from other libraries, assume you know
what such and such function is, or uses undeclared variablesā€¦ :-/

I remember something about delta timeā€¦ Anyone know what it is? Thanks! :wink:


SDL mailing list
SDL at lists.libsdl.org
http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

L-28C wrote:

Hello everyone! :smiley:

Iā€™ve asked this same question on this same mailing list 2 or 3 times
already. I always lose the code. >:-(

Whatā€™s the code to get framerate independence? I looked it up on Google
but the tutorials either use code from other libraries, assume you know
what such and such function is, or uses undeclared variablesā€¦ :-/

I remember something about delta timeā€¦ Anyone know what it is? Thanks! :wink:


SDL mailing list
SDL at lists.libsdl.org
http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

my hint:

do it with fixed time step, or at least minimum timestep of 50Hz, opened
to the upper end to max 200Hz (if that makes any senseā€¦ as displays
are yet not that fast, despite your eyes).

code and article on how to do that:

http://www.gaffer.org/game-physics/fix-your-timestep/

an enlightening article worth reading for everyone still doing variable
time steps.

Okay, thatā€™s one of the first articles Google came up withā€¦ :stuck_out_tongue:
The problem is, whatā€™s the ā€œStateā€ class? Is it like, I have to replace
it with my own?
I would rather something to do with sleep(), as messing with my game
variablesā€¦ Well,
if thatā€™s the best option Iā€™ll do it. :stuck_out_tongue:

Is that it or must I download a State class from somewhere?

Thanks! :wink:

(PS: I have someone famous in my thread, wee! xD)

Kuon - Nicolas Goy - ??? (Goyman.com SA) wrote:> On Feb 14, 2007, at 5:35 PM, David Olofson wrote:

code and article on how to do that:

http://www.gaffer.org/game-physics/fix-your-timestep/

Yea, never read this article before, but itā€™s the technique I use in
my multithreaded engine to update the animation thread.

This article is nice, I will keep it as a reference.

Regards

Roughly translated to C++, this is what I have:

In the vars section:--------
int nextTime = 0;
int tickInt = 30;

The function:

// Gets the time left
void timeLeft()
{
int now = getTime();

 if (nextTime <= now)
 {
     nextTime = now + tickInt;
     return 0;
 }

 return nextTime - now;

} // timeLeft()

And my main loop kind of looks like this:

while (running)
{
// Handle controls and react to them here

 // Do some more reacting here

 // Render screen here
	
 sleep(timeLeft());

}

That should work, itā€™s basically what the usingtimers.html page saidā€¦
But it doesnā€™t? Am I doing something wrong maybe? I tried this on a 2
GHz laptop, a 1400+ desktop, and a ~200MHz Sony PSPā€¦

The laptop and desktop look synced at first, but then the laptop started
to go fasterā€¦ And the PSPā€™s far slower. (Note: the PSP can handle it,
since I made the game there first and it worked like a charm.)

Any ideas? :-/ Thanks! :wink:

Jonathan B. wrote:

Oh wow. Please do not do it like this. This is a busy wait which
will attempt to eat 100% of your CPU doing nothing until the appropriate
time. It is really horrible for any multitasking OS.

It is much better to use SDL_Delay as mentioned on the usingtimers.html
page.

RCAF wrote:

Hi!

Look this page:

http://www.libsdl.org/intro.en/usingtimers.html

but I prefer to do it so:

Uint32 t1, t2;
int fps = 100;
int done=1;

while (!done)
{
t1 = SDL_GetTicks(); // Initial time

// do something... input, game logic, drawing, ...

do
{
    t2 = SDL_GetTicks();  // Current time
} while ((t2 - t1) <= 1000/fps);

}

Regards!


SDL mailing list
SDL at lists.libsdl.org
http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

Iā€™m guessing that the ā€œgranularityā€ of the sleep command is whatā€™s making
them go out of sync.
Some processors cannot process a sleep event of less than 10ms - even if you
send it a lower value, it will do a 10ms sleep, and then pick up from there.
Most modern processors are fine with it 1ms increments, but some older ones,
not so much(even my P3 in my old laptop has had issues with it.) so Iā€™m
thinking your PSP might not be really sleeping the exact amount of time you
are telling it to.

-Dave Olsen> ----- Original Message -----

From: leo28c@gmail.com (Leo Cabrera)
To:
Sent: Tuesday, February 13, 2007 6:11 PM
Subject: Re: [SDL] Framerate independence?

Roughly translated to C++, this is what I have:

In the vars section:

int nextTime = 0;
int tickInt = 30;

The function:

// Gets the time left
void timeLeft()
{
int now = getTime();

if (nextTime <= now)
{
    nextTime = now + tickInt;
    return 0;
}

return nextTime - now;

} // timeLeft()

And my main loop kind of looks like this:

while (running)
{
// Handle controls and react to them here

// Do some more reacting here

// Render screen here

sleep(timeLeft());

}

That should work, itā€™s basically what the usingtimers.html page saidā€¦
But it doesnā€™t? Am I doing something wrong maybe? I tried this on a 2
GHz laptop, a 1400+ desktop, and a ~200MHz Sony PSPā€¦

The laptop and desktop look synced at first, but then the laptop started
to go fasterā€¦ And the PSPā€™s far slower. (Note: the PSP can handle it,
since I made the game there first and it worked like a charm.)

Any ideas? :-/ Thanks! :wink:

Jonathan B. wrote:

Oh wow. Please do not do it like this. This is a busy wait which
will attempt to eat 100% of your CPU doing nothing until the appropriate
time. It is really horrible for any multitasking OS.

It is much better to use SDL_Delay as mentioned on the usingtimers.html
page.

RCAF wrote:

Hi!

Look this page:

http://www.libsdl.org/intro.en/usingtimers.html

but I prefer to do it so:

Uint32 t1, t2;
int fps = 100;
int done=1;

while (!done)
{
t1 = SDL_GetTicks(); // Initial time

// do something... input, game logic, drawing, ...

do
{
    t2 = SDL_GetTicks();  // Current time
} while ((t2 - t1) <= 1000/fps);

}

Regards!


SDL mailing list
SDL at lists.libsdl.org
http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org


SDL mailing list
SDL at lists.libsdl.org
http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

Just for reference, here is how I ensure a certain framerate in our
current game engine.

In the game, I have 3 threads:

rendering (main), animation and network (itā€™s an mmorpg)

Here is how the animation test thread looks like.

The GL engine runs at about 250 fps on my computer but the objects
are updated by the animation thread only.

void AP_Animation_launch() {
AP_Log(AP_LOG_INFO, ā€œLaunching Animation threadā€);
AP_Application()->testX = 0;
AP_Animation_update();
}

void AP_Animation_update() {
Sint32 start, end;
while(1) {
start = SDL_GetTicks();

	// Setting a test angle, we don't need mutex as it is the only  

thread writing, and the write is atomic.
AP_Application()->testX += 0.01;
if(AP_Application()->testX > 360)
AP_Application()->testX = 0;

	end = SDL_GetTicks();
	// If the above block exceed 10 ms, we don't delay, but this should  

not happen as it would drop animation rate.
SDL_Delay(10 - (end - start) > 10 ? 0 : end - start);
}
}

This thread reads the input from the server (network thread), update
all relevants objects positions and sleep until next frame.

Regardsā€“
Kuon
Programmer and sysadmin.

ā€œComputers should not stop working when the usersā€™ brain does.ā€

[ā€¦]

Well, Iā€¦ This is what makes it feel worthwhile to spend time trying
to share some of what Iā€™ve learned through the years.

Thanks! :slight_smile:

//David Olofson - Programmer, Composer, Open Source Advocate

.------- http://olofson.net - Games, SDL examples -------.
| http://zeespace.net - 2.5D rendering engine |
| http://audiality.org - Music/audio engine |
| http://eel.olofson.net - Real time scripting |
ā€™-- http://www.reologica.se - Rheology instrumentation --'On Tuesday 13 February 2007 08:56, Paul Lowe wrote:

Mr. Microcontroller-Esque-Named-Dude,

I would strongly encourage you to do a search in the mailinglist
archives for ā€œDavid Olofsonā€, and look for entries that match
framerate independence. I consider him an expert on the topic and he
has posted about it many times here before.

He taught me how to do framerate independence ā€“ and he knows many
different ways to do it depending on your needs ā€“ some having
benefits over others.

I suggest you take a look at his Fixed Rate Pig program (heā€™s a very
talented coder, by the way, and I envy his C programming
techniques):

http://olofson.net/mixed.html

[ā€¦]

code and article on how to do that:

http://www.gaffer.org/game-physics/fix-your-timestep/
[ā€¦]

This is a really good article. Iā€™d strongly recommend reading this,
whether or not youā€™re going to read or use any of my code. I think it
describes the logic and reasoning behind it all in a much more
accessible way than any of my documents or code.

//David Olofson - Programmer, Composer, Open Source Advocate

.------- http://olofson.net - Games, SDL examples -------.
| http://zeespace.net - 2.5D rendering engine |
| http://audiality.org - Music/audio engine |
| http://eel.olofson.net - Real time scripting |
ā€™-- http://www.reologica.se - Rheology instrumentation --'On Tuesday 13 February 2007 14:04, Andre Krause wrote:

code and article on how to do that:

http://www.gaffer.org/game-physics/fix-your-timestep/

Yea, never read this article before, but itā€™s the technique I use in
my multithreaded engine to update the animation thread.

This article is nice, I will keep it as a reference.

RegardsOn Feb 14, 2007, at 5:35 PM, David Olofson wrote:

ā€“
Kuon
Programmer and sysadmin.

ā€œComputers should not stop working when the usersā€™ brain does.ā€

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

After reading this thread, I wanted to try writing my own timer class.
Itā€™s a quick example based on the articles I read. I think I have the
basic concept down. If anyone would care to give some feedback on my
example Iā€™d appreciate it.

Jim

sdl_timer.h


#ifndef _sdl_timer_H
#define _sdl_timer_H
#include <SDL/SDL.h>

#define DEFAULT_STEP_TIME = 50

class sdl_timer
{
public:
sdl_timer(Uint32 stepTime);
~sdl_timer();

void start();
void stop();
//returns delta time
Uint32 delay();
Uint32 timeLeft();

public://accessor methods
inline Uint32 getCurrentTime(){return current_time;};
inline Uint32 getNextTime(){return next_time;};

private:
Uint32 current_time;
Uint32 next_time;
Uint32 step_time;
};

#endif /* _sdl_timer_H */


sdl_timer.cc


#include ā€œsdl_timer.hā€

sdl_timer::sdl_timer(Uint32 stepTime)
: current_time(0),
next_time(0),
step_time(stepTime) {
}

sdl_timer::~sdl_timer() {
}

void sdl_timer::start() {
this->current_time = SDL_GetTicks();
}

void sdl_timer::stop() {
this->current_time = 0;
}

Uint32 sdl_timer::delay() {
Uint32 delay_time = this->timeLeft();
if(delay_time) {
SDL_Delay(delay_time);
}
return delay_time;
}

Uint32 sdl_timer::timeLeft() {
//current_time = SDL_GetTicks();
if ( next_time <= current_time ) {
next_time = current_time+step_time;
return(0);
}
return(next_time-current_time);
}


testTimer.cc


#include ā€œsdl_timer.hā€
#include <SDL/SDL.h>
#include
#include
void print_timer(sdl_timer& timer);
bool game_loop(sdl_timer& timer);

int main(int argc, char** argv) {
sdl_timer timer(60);
for(int x=0;x<10;++x){//ten loops
while(!game_loop(timer));
}
return (EXIT_SUCCESS);
}

bool game_loop(sdl_timer& timer) {
bool done = false;
timer.start();

print_timer(timer);

for(int x=0;x<1000;++x)  for(int y=0;y<10000;++y);//waste time,

simulate a game
Uint32 delta = timer.delay();
if(delta){
std::cout << "DELAY CALLED: " << delta << std::endl;
done = true;
}
return done;
}

void print_timer(sdl_timer& timer) {
std::cout << ā€œ************************************ā€ << std::endl;
std::cout << "current time: " << timer.getCurrentTime() << std::endl;
std::cout << "next time: " << timer.getNextTime() << std::endl;
std::cout << ā€œ************************************ā€ << std::endl;

}

-----BEGIN PGP SIGNATURE-----
Version: GnuPG v1.4.6 (GNU/Linux)

iD8DBQFF15ObQuDJiZ/QrH0RAus3AJ9XNQUtwW4/3BE4dH2Fu37ucnrPzQCgm6iG
HDqhYuyY3pSe5DFvZlKGd+E=
=rBi6
-----END PGP SIGNATURE-----

You might want to take a look at the Lazy Foo timer at
http://lazyfoo.net/SDL_tutorials/lesson13/index.php
The source is at the bottom of the page.On 2/17/07, James Barrett wrote:

-----BEGIN PGP SIGNED MESSAGE-----
Hash: SHA1

After reading this thread, I wanted to try writing my own timer class.
Itā€™s a quick example based on the articles I read. I think I have the
basic concept down. If anyone would care to give some feedback on my
example Iā€™d appreciate it.

Jim

L-28C wrote:

Whatā€™s the code to get framerate independence?
Iā€™ve written an article about that at
http://dewitters.koonsolo.com/gameloop.html
It takes a look at the different possible implementations of game loops,
and discusses the pros/cons. Itā€™s not SDL specific though, but I donā€™t
think its difficult to translate it to the SDL lib (I know I did ;-).

deWiTTERS

L-28C wrote:

Whatā€™s the code to get framerate independence?
Iā€™ve written an article about that at
http://dewitters.koonsolo.com/gameloop.html
It takes a look at the different possible implementations of game
loops,
and discusses the pros/cons. Itā€™s not SDL specific though, but I donā€™t
think its difficult to translate it to the SDL lib (I know I did ;-).

Thatā€™s a great writeup! Thank you very much for linking to it, and I
have now added it to my game-dev bookmarks! :slight_smile:

Truth be told, I hadnā€™t actually thought of the persistent framerate
with sub-frame interpolation idea! Nice, that one!

ā€“ Scott

?? Tue, 27 Mar 2007 00:49:06 -0600
Scott Harper ???:

Truth be told, I hadnā€™t actually thought of the persistent framerate
with sub-frame interpolation idea! Nice, that one!
To be honest, I think that sub-frame interpolation is wasteful. You
donā€™t really need to run game logic more than once per display
(because these extra computations wonā€™t be visible anyway - user will
see only the end result), and donā€™t need to run it less than that
(because all objects will be redisplayed at the same position several
times - user wonā€™t see this).

I would stick to one update_game() per every display_game(), and limit
FPS to something like 50FPS. The ā€˜floatā€™ precision should be enough for
smooth handling of movement, and if youā€™re doing a multi-player game
and want to avoid desyncs between different computers you anyway need
some synchronization mechanism.

Something like this (pseudocode, not tested):

int MaxFPS = 50;
ulong CurrentTime = GetCurrentTime (); // in milliseconds
ulong PreviousTime = CurrentTime; // the time of the previous frame
ulong NextTime = CurrentTime; // the time of the next frame
ulong NextFrac = 0; // the fractional part of NextTime

while (ā€¦)
{
div_t d = div (1000, MaxFPS);
NextTime += 1000 / d.quot; // this is the integer part
NextFrac += d.rem; // and accumulate the remainder

// carry the extra remainder into the integer part
while (NextFrac > d.quot)
    NextTime++, NextFrac -= d.quot;

update_game (PreviousTime - CurrentTime);
display_game ();

PreviousTime = CurrentTime;
CurrentTime = GetCurrentTime ();

// have a good sleep if we're running too fast
long delta = NextTime - CurrentTime;
if (delta > 0)
    Sleep (delta);
// drop frames if we're running too slow
else if (delta < -100)
    NextTime = CurrentTime, NextRem = 0;

}

NextTime could be a ā€˜doubleā€™ variable (to avoid keeping the fractional
part in a separate variable), but that wouldnā€™t be too safe

  • on 32-bit platforms long wraps around at 2^32 while double doesnā€™t. I
    have intentionally used NextTime of the same type as CurrentTime, and
    added another additional variable for holding the fractional part.

With this approach my app limits to any FPS with high precision (of
course, if that FPS is reachable). On the other hand,
(1000 / FRAMES_PER_SECOND) is pretty imprecise - for example, if you
want 60 FPS, you will get 62.5 instead -> (1000 / int (1000 / 60)).ā€“
Greetings,
Andrew
-------------- next part --------------
A non-text attachment was scrubbedā€¦
Name: signature.asc
Type: application/pgp-signature
Size: 189 bytes
Desc: not available
URL: http://lists.libsdl.org/pipermail/sdl-libsdl.org/attachments/20070327/ae19249c/attachment.pgp

That explains why my ball moves so choppilyā€¦ Thanks dude! :wink:

Koen Witters wrote:> L-28C wrote:

Whatā€™s the code to get framerate independence?

Iā€™ve written an article about that at
http://dewitters.koonsolo.com/gameloop.html
It takes a look at the different possible implementations of game loops,
and discusses the pros/cons. Itā€™s not SDL specific though, but I donā€™t
think its difficult to translate it to the SDL lib (I know I did ;-).

deWiTTERS


SDL mailing list
SDL at lists.libsdl.org
http://lists.libsdl.org/listinfo.cgi/sdl-libsdl.org

Why does one need a ā€˜fixedā€™ fps anyway? Afaik you want a fixed
game-flow , independant of the fps.

Drawing stuff etc, thats FPS. Keep a timer (use interupt handler, i
think SDL_Timer can do that) , and update your cycles each frame.

void gameloop() {

while (gameruns) {
handle_logic();
handle_drawing();
}

}

where handle_logic does.

void handle_logic() {
while (timer > 0) {
updatelogicbytickonsomeevent/unit. etc.
timerā€“;
}

}

Would be sufficient?