Frame Rate Independence

Wavesonics
Posts: 71
Joined: Thu May 22, 2008 8:03 pm

Frame Rate Independence

Post by Wavesonics »

I'm having some trouble achiving frame rate independence from my physics simulation:

I've tried both:

Code: Select all

// Variable time step
m_dynamicsWorld->stepSimulation( m_frameTimer.getDeltaTime() );
// and Fixed time step
m_dynamicsWorld->stepSimulation( 1.0f/60.0f, 0 );
And neither provide the frame rate independence I am looking for, any suggestions?
User avatar
Erwin Coumans
Site Admin
Posts: 4221
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA

Re: Frame Rate Independence

Post by Erwin Coumans »

Use this version:

Code: Select all

m_dynamicsWorld->stepSimulation( m_frameTimer.getDeltaTime() );
How do you synchronize the world transform exactly?
You should get framerate independence, as long as you are using the btMotionState (or derived class such as btDefaultMotionState), and use the transform provided through btMotionState::setWorldTransform.

Thanks,
Erwin
By the way, no luck with Doxygen. Can you help with all details and Doxyfile (which version of doxygen?) that documents the btCollisionObject class etc.?
abaraba
Posts: 56
Joined: Thu Jun 19, 2008 7:54 am

Re: Frame Rate Independence

Post by abaraba »

please,

Bullet demos slow down on slower computer instead to drop frame rate... stuff should not 'free fall' sooner on some computer just because of better graphic card - gravitational rate of acceleration, measured in real-time seconds, should be independent of mass, size and *computer speed* - is that "Frame Rate Independence" we're talking about here?

how do i know if Bullet demos work in "supposed" speed or "full speed" on my computer, i guess "unaccounted" number says how much it lags, but i thought that wouldnt matter and what internal interpolation is all about - that Bullet would compensate to keep simulation in real-time?

i think we all want the same effect - physics simulation to run in real time even if that means only 1 FPS of animation, we do not want speed of simulation to go down, but only number of rendered frames, right?

so, for start, how to implement that in Bullet demos, how to make them run in real-time on slow(er) computers? how to achieve 'Frame Rate Independence' in Bullet demos?

this kind of thing doesnt seem to really work:

Code: Select all

m_dynamicsWorld->stepSimulation(m_frameTimer.getDeltaTime(), 10);
or
m_dynamicsWorld->stepSimulation(m_frameTimer.getDeltaTime(), 100);
or
m_dynamicsWorld->stepSimulation(m_frameTimer.getDeltaTime(), 1000);

Wavesonics,
did you find what was the problem, did you manage it?

i played with a timer loop and stepSimulation quite a bit in my demos and as much as i could figure in Bullet demos... my conclusion is that on fast computer i was under impression to be able to control FPS independent of simulation speed and achieve framerate independence, but on slow(er) computer i could not in any way make simulation work "fine", not even on fixed 5 or 10 FPS... not my demos nor Bullet demos... help!


cheers


p.s.
while im at it,
let me try this question here... new bunny-car demo in Bullet 2.70 - is that simulation of a Balloon? or is there something wrong with that demo... bunny floats around like on the moon, everything looks like in slow-motion and is impossible to control? sometimes it even gains speed and height while in mid-air and goes up in "space" ..also, after some time when holding "L or K" wheels would start to rotate around more then one axis like with 'gimbal lock' effect




***** continued...
edit:
solution turns out to be something we're not supposed to do:

Code: Select all

m_dynamicsWorld->stepSimulation(m_frameTimer.getDeltaTime(), 0);
zero value for 2nd argument is not supported,
but it does exactly what i was talking about and thought interpolation is supposed to be doing?

if we take CcdPhysicsDemo and change this:

Code: Select all

		//during idle mode, just run 1 simulation step maximum
		int maxSimSubSteps = m_idle ? 1 : 1;
		if (m_idle)
			dt = 1.0/420.f;

		int numSimSteps = 0;
		numSimSteps = m_dynamicsWorld->stepSimulation(dt,maxSimSubSteps);
to this:

Code: Select all

   
m_dynamicsWorld->stepSimulation(dt, 0);
i get what i expect stepSimulation(dt, 10) [or even stepSimulation(dt, 100); if dt gets big], but if that is not correct way, how to achieve exact same effect correctly?
Last edited by abaraba on Mon Aug 25, 2008 8:14 am, edited 1 time in total.
abaraba
Posts: 56
Joined: Thu Jun 19, 2008 7:54 am

Re: Frame Rate Independence

Post by abaraba »

http://www.bulletphysics.com/mediawiki- ... _the_World
"Stepping The World" article says this:
maxSubSteps == 0 ?

If you pass maxSubSteps=0 to the function, then it will assume a variable tick rate. Every tick, it will move the simulation along by exactly the timeStep you pass, in a single tick, instead of a number of ticks equal to fixedTimeStep.

This is not officially supported, and the death of determinism and framerate independance. Don't do it.
but it seems determinism is broken with maxSubsteps > 1 as well, at least "maxSubSteps == 0" seem to be independent of computer speed, eg. physics simulation does not slow down or speed up

how come "maxSubSteps > 1" is frame rate independent if everything slows down with slow computer ?


thankfully these opinions are diametrically opposite so this would be easy to resolve..


but,
let me continue.. next article in Bullet-online about the subject:
"Canonical Game Loop" http://www.bulletphysics.com/mediawiki- ... _Game_Loop

Code: Select all

 // Physics handling part of the loop
    /* This, like the rendering, ticks every time around.
    Bullet does the interpolation for us. */

    time_physics_curr = getMilliseconds();

    // Tick the bullet world. Keep in mind that bullet takes seconds, and we measure time in milliseconds.
    mWorld->stepSimulation(((float)(time_physics_curr - time_physics_prev))/1000.0, 10);

Bullet does the interpolation for us... everything slows down with slow speed, eg. 10 boxes fall faster than 3000 boxes ...are we making games here or what?


and finally,
this, last article on the subject: "Fix Your Timestep!"
http://www.gaffer.org/game-physics/fix-your-timestep

this makes most sense, but it does NOT mention stepSimulation() once... anyway, basic question is how all this could possibly come to agreement? ..someone must be wrong or we need to clear up terminology.. hopefully its not just me being stupid or having broken computers, tralalaa la
sparkprime
Posts: 508
Joined: Fri May 30, 2008 2:51 am
Location: Ossining, New York

Re: Frame Rate Independence

Post by sparkprime »

Personally I think the stepSimulation API is very confusing, both for beginners and especially when you want tighter control of what's going on. The last parameter does not need to be supplied every frame, and requiring it to be supplied gives the wrong impression - that modifying it each frame is a good idea. The difference between the first and last parameter is rather subtle, and the middle parameter is not important until you have a lot of things going on - i.e. for beginners not really relevant. The actual implementation of stepSimulation is complicated too, and I believe this is only due to the API it implements.

I'd rather have an API where you invoke the 5 different behaviours separately, so that it is possible to do things like disable interpolation and run the physics engine "one step at a time" which are very useful for debugging collisions and so on. Also it gets rid of the need for internal step callbacks.


Application code would look like (these are all functions on dynamicsworld):

Code: Select all

PhysicsWorld::PhysicsWorld() {
    setInternalStep(1/60.f); // not actually needed since it is the default
}
PhysicsWorld::pump () {
    while (...) {
        internalStep();
        // application-specific internal step code
    }
    clearForces();
    bool left_over_time = ...; // if desired, can integrate once more with any "left over" time
    motionCallbacks(left_over_time); // if motion callbacks actually used
}
This is simple to write, and very easy to understand if one understands the functions in question, which can be documented separately.
It gives more power, e.g. disabling the interpolation and allows to defer the motionCallbacks until e.g. the rendering thread has finished its frame. To be honest, I think a lot of people will need more than 60hz for their simulations, so there will be more physics frames than graphics frames, and thus interpolation will not provide much extra visual quality. Interpolation comes with its own problems anyway, as well as using up cycles. You can implement the "max number of internal steps" functionality with a simple counter, and you can also do more advanced things like measure how long the physics is taking and use that information to kill some of the steps.


Obviously the original stepSimulation could be either kept or reimplemented in terms of these functions... Either way providing a backwards-compatible interface.

But I would wrap the above calls in an even simpler interfaace that exposes only one parameter - the real time (as recorded by the application) since last tick.

Thus newbie code only needs to look like

Code: Select all

while (!quit) {
    // game loop
    // graphics
    stepSimulation(time-last_time);
}
If they want more precise behaviour they will likely already know what the low-level functions actually do and can construct their own frame-independent simulation loop.


I know that the current interface is capable of most of these things, even disabling interpolation, but I think it's not the most intuitive interface for either beginners or experts.
chunky
Posts: 145
Joined: Tue Oct 30, 2007 9:23 pm

Re: Frame Rate Independence

Post by chunky »

m_frameTimer.getDeltaTime()
You should be passing time to bullet measured in seconds, and not milliseconds.

Code: Select all

m_dynamicsWorld->stepSimulation(m_frameTimer.getDeltaTime(), 10);
or
m_dynamicsWorld->stepSimulation(m_frameTimer.getDeltaTime(), 100);
or
m_dynamicsWorld->stepSimulation(m_frameTimer.getDeltaTime(), 1000);
Assuming you're passing time in milliseconds instead of seconds, and you're getting 60 frames per second, you need to pass 19000 substeps before it'll be framerate independant. That's gonna be some pretty hefty CPU requirements, there, and probably not what you want :-)

I have added something about units to the mentioned wiki page. Try changing the first parameter to stepSimulation to:

Code: Select all

((float)m_frameTimer.getDeltaTime)/1000.0f
Erwin:
By the way, no luck with Doxygen. Can you help with all details and Doxyfile (which version of doxygen?) that documents the btCollisionObject class etc.?
You seek the EXTRACT_ALL parameter in your Doxyfile.

Gary (-;
abaraba
Posts: 56
Joined: Thu Jun 19, 2008 7:54 am

Re: Frame Rate Independence

Post by abaraba »

sparkprime,
im not quite sure what is it you're saying in regard to "Frame Rate Independence", except that stepSimulation() is confusing...

- does that mean you agree with "my" definition here of "Frame Rate Independence" and you too are unable to achieve that effect with neither your or Bullet demos and so unable to really answer these questions, just like myself?

in that case... glade im not the only one
The last parameter does not need to be supplied every frame, and requiring it to be supplied gives the wrong impression - that modifying it each frame is a good idea.
sorry, what are you referring to? ...where/who suggests that it is required for last parameter to be supplied and to what effect was that all about?
The difference between the first and last parameter is rather subtle, and the middle parameter is not important...
i dont agree... do have a look:
"Stepping The World"
http://www.bulletphysics.com/mediawiki- ... _the_World
"Canonical Game Loop"
http://www.bulletphysics.com/mediawiki- ... _Game_Loop

Code: Select all

I'd rather have an API...
i think two of us do not understand this current API, so chances are its too early to be devising a new one... so, you think this is a bug?

well,
i dont really believe its a bug, kind of expect to hear some minimum requirements and minimum low fixed frame rates - basically some numbers, limits where interpolation works and where and how it fails. it seems, if you can push every scene at 60 FPS with some time to spare everything is ok, maybe even fixed 30FPS, but fixed 5-10FPS or even worse - variable low frame rates or low-high, just might, for some reason, not be interpolated right or by trying so you accumulate extra time so it falls out of sync..

cheers
User avatar
Erwin Coumans
Site Admin
Posts: 4221
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA

Re: Frame Rate Independence

Post by Erwin Coumans »

Bullet supports all features as discussed in the the article "Fix Your Timestep!" and in this topic.
  • The first argument is always the deltaTime in seconds.
  • The third argument is the internal fixed timestep. It is optional, and it is best to leave it at 60 hertz. For higher quality simulation, you can consider to descrease the internal fixed timestep to 120 or 240 hertz.The second argument clamps the maximum number of internal timesteps. By default it clamps it to 60 hertz (1 internal fixed timestep). From 'Fix your Timestep':
    make sure that you clamp the deltaTime passed in from the timer to some maximum value like 0.25 seconds
    This would be similar to clamping to 2 or 3 internal substeps, as second argument. Let's increase the default value of the second argument to 3 to use a more relaxed clamping value.
  • If a computer is too slow to compute all required simulation time steps in real-time, I suggest to either buy a faster CPU, improve the physics simulation performance or simplify the simulation.
  • Variable timestep is unsupported, although the interface allows it, when passing 0 as second argument.
  • Interpolation is automatically supported when using the motion state to synchronizing the world transforms.
What suggestions do you have to document this interface better?
Thanks,
Erwin
chunky
Posts: 145
Joined: Tue Oct 30, 2007 9:23 pm

Re: Frame Rate Independence

Post by chunky »

Personally, I disagree that stepSimulation is very complicated. On the other hand, I do feel one thing about it:

Should the default maxSubSteps be changed to 10 or so?
I realise that it's currently 1, because that way bullet will do exactly what those of us that like specificity expect, but I think that for beginners it needs to be something a bit higher. I strongly feel that for beginners, just passing stepSimulation(time-since-last-frame) should magically do what they expect it to, which it currently doesn't.

The engineer in me wants it to stay at 1, but the pragmatist says that something higher would be better.
Interpolation is automatically supported when using the motion state to synchronizing the world transforms.
And when maxSubSteps>1, I think?

abaraba: Did you try dividing the first parameter to stepSimulation by 1000, yet?

Gary (-;
abaraba
Posts: 56
Joined: Thu Jun 19, 2008 7:54 am

Re: Frame Rate Independence

Post by abaraba »

chunky,

Code: Select all

Assuming you're passing time in milliseconds instead of seconds...
they say assumption is mother of all fuk-ups ;-)

but seriously, you might be right for all i know,
i have no idea about that function i just copy/pasted it as it was already used as example, illustrating that i tried different 2nd parameter

i also used CcdPhysicsDemo as example, i think it was mentioned this demo is best used for template/starting point and i trust Bullet demos calculate dt correctly ...which is assumption as well and i really should check that out too, thanks


let me try to guess from your message, am i correct:
- you agree with "my" definition here of "Frame Rate Independence", BUT you actually can make everything work all right, so you, in effect, could practically tell us, in several lines of code, how exactly you use your timer loop and call stepSimulation()? and/or how to modify CcdPhysicsDemo or any other Bullet demo to be frame-rate independent, to work on slow computers as i described above?


im glad you came along,
i was wondering about this thread you started:
"Experiments in framerate independence"
http://www.bulletphysics.com/Bullet/php ... +framerate

so, you start by kind of proving that indeed there is NO "Frame Rate Independence"
Your ideal graphs should all be dead flat lines, indicating that no matter how you futzed the numbers, the body fell the same distance... Welcome to computers. The lines are always flat for a certain distance, then suddenly change
..then there is conversation about some bug being fixed, you comment how everything is ok, but your last set of graphs are still curved lines - whats the conclusion: is there or is there not "Frame Rate Independence" ?

this is really simple and basic question, lets keep it simple, make it crystal clear and demonstrate implementation by providing few lines of code


thank you
stenyak
Posts: 29
Joined: Fri Aug 12, 2005 4:59 pm

Re: Frame Rate Independence

Post by stenyak »

I'm migrating from ODE to Bullet, and i find Bullet API documentation a little confusing.
Basically, i want to handle wall-clock vs. simulation-clock myself (just like i used to with ODE), however the documentation says "This is not officially supported, and the death of determinism and framerate independance. Don't do it.". Which i find confusing. At first sight, i think this prevents me from doing a fast-forward or a slow motion replay of a simulation, for example.

Can someone please point out how to make Bullet compute a single step of 1/frequency units of time while letting me handle the rest? I'm not sure which (or whether any) of these is correct:

Code: Select all

stepSimulation(1/frequency);
stepSimulation(1/frequency, 0);
stepSimulation(1/frequency, 0, 1/frequency);
stepSimulation(1/frequency, 1);
stepSimulation(1/frequency, 1, 1/frequency);
Thanks!
User avatar
Erwin Coumans
Site Admin
Posts: 4221
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA

Re: Frame Rate Independence

Post by Erwin Coumans »

Fast-forward or a slow motion is already possible with the current stepSimulation interface. Slow motion is automatically handled by MotionState interpolation. Fast-forward can be done by calling the stepSimulation multiple times, or by using a large time step in combination with a very large allowed number of internal substeps (second argument).


If you really want to manage the call to each single internal simulation substep, similar to Open Dynamics Engine, you can pass in 0 as second argument:

Code: Select all

stepSimulation(1./frequency, 0);
As long as you use a fixed timestep as first argument that should work out fine.
"This is not officially supported, and the death of determinism and framerate independance. Don't do it.".
It should be more specific: "passing in a variable timestep in combination with 0 as second argument is not supported". If you manage your simulation loop yourself, it will be your responsibility to pass in a fixed timestep, and not a variable time step as first argument, in combination with 0 as second argument. In other words: just keep in mind that Bullet doesn't support variable-size internal simulation steps. Therefore avoid a changing/variable timestep as first argument in combination with 0 as second argument.
Hope this helps,
Erwin
chunky
Posts: 145
Joined: Tue Oct 30, 2007 9:23 pm

Re: Frame Rate Independence

Post by chunky »

but seriously, you might be right for all i know,
So try it. Divide your first parameter to stepSimulation by 1000.0f.
you agree with "my" definition here of "Frame Rate Independence", BUT you actually can make everything work all right, so you, in effect, could practically tell us, in several lines of code, how exactly you use your timer loop and call stepSimulation()?
I could. And in fact, you've already seen it, since I also wrote the Canonical Game Loop page on the wiki. The code you see there is directly ripped from my engine, that I wrote and am working on. [that I wrote after reading that gaffer-on-games article you see linked there]

The top bottom paragraph of the top section talks about the units used, and they're important.
so, you start by kind of proving that indeed there is NO "Frame Rate Independence" [...]
is there or is there not "Frame Rate Independence" ?
There *is* framerate independance, and I prove it, but you need to make sure that you're passing appropriate parameters to stepSimulation. Parameters such that the inequality listed at the top of the Stepping the World wiki page is met. If you are passing milliseconds to the function, then you aren't meeting that inequality unless you pass 19000 as maxSubSteps.

Gary (-;
sparkprime
Posts: 508
Joined: Fri May 30, 2008 2:51 am
Location: Ossining, New York

Re: Frame Rate Independence

Post by sparkprime »

Frame Rate Independence is most of what stepSimulation tries to achieve, so that's why I posted here. On second thoughts I would rather have made a new thread to keep it from getting lost. I use stepSimulation in contrived ways in my own project, and I've read the code and hacked it a bit to work around some btMotionState issues in the google tracker.
Erwin Coumans wrote:
  • The first argument is always the deltaTime in seconds.
This is the most important thing, and I believe the only thing a new user needs to know about. Since this is one of the first functions they ever call, it has to be simple. On the other hand, for everyone else it has to be powerful and this conflict of interest is causing the problem.
Erwin Coumans wrote:
  • The third argument is the internal fixed timestep. It is optional, and it is best to leave it at 60 hertz...
I've had no success at all with 60hz, I think a large number of people will need to use 100hz or more. When you have worked on commercial games, how many have used bullet for dynamics (not just collisions) and what have they clocked the simulation to?
  • Variable timestep is unsupported, although the interface allows it, when passing 0 as second argument.
And also by just changing the 3rd parameter. If variable timestep isn't supported, I think it would be better set outside of the function with a setTimeStep(1/60.f) call. People who want to change it still can.

There is also a lot of redundancy, and I personally find redundancy to be one of the easiest ways to confuse people:

for all A,X:
stepSimulation(A,0,X) == stepSimulation(A,X,A) == stepSimulation(X*A,1,A)

There is actually no reason for the special max_steps==0 behaviour at all. I don't like it when a function provides wildly different behaviours depending on its arguments anyway.

Erwin Coumans wrote:
  • Interpolation is automatically supported when using the motion state to synchronizing the world transforms.
Sometimes, depending on how you call stepSimulation :)

I actually use stepSimulation as follows:

Normal game play:

Code: Select all

stepSimulation(recorded_time, 100, 0.01);
No interpolation, useful for debugging jitter and penetration:

Code: Select all

stepSimulation(0.01*floor(recorded_time/0.01), 100, 0.01);

One-tick-per-frame mode, useful for debugging and recording movies:

Code: Select all

 stepSimulation(0.01, 100, 0.01); 
And I also have a mode where I can step they physics a frame at a time by pressing F12, and I can also pause/continue it and speed up / slow it down, all while keeping the fixed timestep. All this I wanted just to have a nice debug environment! I may need even more in the future, when I use bullet in a background thread for instance.

Now tell me it's not complicated :)
Erwin Coumans wrote: What suggestions do you have to document this interface better?
I would prefer a different interface entirely because this is not a simple thing and attempting to "encode" it into a single call does not make it simple. In fact I think it does more damage than exposing a more broken-down API. I'm happy to put a patch together sometime in the next few weeks. There are also some issues to do with interpolation and btMotionState in the tracker, I could fix them at the same time. I already have hacked workarounds in my own copy of the tree. I believe it will be be less buggy, faster, more intuitive, more newbie-friendly, more powerful, and backwards compatible :)
Last edited by sparkprime on Mon Aug 25, 2008 6:36 pm, edited 3 times in total.
abaraba
Posts: 56
Joined: Thu Jun 19, 2008 7:54 am

Re: Frame Rate Independence

Post by abaraba »

Code: Select all

If a computer is too slow to compute all required simulation time steps in real-time, I suggest to either buy a faster CPU, improve the physics simulation performance or simplify the simulation.
computer is 2ghz with ati Xpress and latest drivers and im talking about simple Bullet demos like "CcdPhysicsDemo", tho i agree it might be some weired computer hardware or driver issue thats why i insist to confirm if anyone else is experiencing the same thing..

but,
stepSimulation(dt, 0) works great! everything runs on about 30-50fps, while normally Bullet demos just run in slow-motion, hows that?

why would it not run ok on say, fixed 30FPS or 15FPS or even 1FPS as thats still enough for physics to do its job to keep it real-time? ..and, again stepSimulation(dt, 0) can do it..

im just looking for the correct way to do what stepSimulation(dt, 0) does, and its not stepSimulation(dt, n>1) as chunky and some other documentation suggests

is correct way to implement "Frame Rate Independence" demonstrated in any of Bullet demos?

are you guys saying that all of these are frame rate independent ?
1.)

Code: Select all

//*** fixing fps at 60, knowing we will always have time to spare
while( dTime < 1/60 )
  getDeltaTime( dTime ) // dTime = time in seconds since last frame was rendered

stepSimulation(1/60, 1);
or even maybe
stepSimulation(dTime, 5); // note that dTime is not exactly 1/60
2.)

Code: Select all

//*** fixing fps at 10, knowing we will always have time to spare
while( dTime < 1/10 )
  getDeltaTime( dTime ) // dTime = time in seconds since last frame was rendered

stepSimulation(1/10, 10);
3.)

Code: Select all

getDeltaTime( dTime ) // dTime = time in seconds since last frame was rendered
stepSimulation(dTime, 100);
but please, just make this 1 thing clear for me,
- on your, or any other "proper" and fast computer when you're rendering a scene that sometimes (moving camera) takes more than 1/60 of second, say scene is so intensive that dt goes up to 1/10 - are you saying your physics simulation does NOT slow down or you saying avoid scenes that might drop your framerates below 60FPS?
What suggestions do you have to document this interface better?
i think everything is pretty clear here: "Stepping The World"
http://www.bulletphysics.com/mediawiki- ... _the_World

its just that Bullet demos, say CcdPhysicsDemo, dont drop frame rate as i understand it should happen but everything just goes slower, slow-motion like and the only thing we're not supposed to do actually does what i want to happen: stepSimulation(dt, 0) ...am i repeating myself, sorry


thanks

p.s.
hope i didnt give wrong impression - i do like Bullet a lot and i didnt mean to sound as if i question the way things are done, im simply too stupid for that, im truly asking all these questions and looking forward to hear answer to as many as possible, i hope i explained enough the way i misunderstand things so i can be more easily corrected... and most of all i hope this is not some stupid driver/hardware problem
Last edited by abaraba on Mon Aug 25, 2008 8:25 pm, edited 14 times in total.