Accurate Physics timing

Member
Posts: 241
Joined: 2008.07
Post: #1
I understand that NSTimer works by specifying the interval at which it will call the specified method.

I can see that time based movement would be regulated as you would expect time based movement to behave with this method.
_
Okay, the interval is 1/60, which equates to 0.016666.

So, if it takes longer than that to process a frame, what happens? Certainly, the framerate would suffer, however, movement will still be processed as though it hadn't.

Normally, you multiply the acceleration, translation, rotation or whatever physical calculation by the time between frames. With this system, even if the framerate is less than 60, it still would be multiplied by 1/60, unless you calculate the framerate and multiply by the inverse. So, this is one way to do it but isn't there another way that is the more traditional way with a regular timer that counts time between frames?

To summarize, how do I measure timing on the iPhone at a low level?

The documentation for NSTimeInterval says:
Quote: NSTimeInterval is always specified in seconds; it yields sub-millisecond precision over a range of 10,000 years.

What? Seconds or sub-miliseconds? 10k years? Huh?
Quote this message in a reply
Moderator
Posts: 3,579
Joined: 2003.06
Post: #2
bmantzey Wrote:So, if it takes longer than that to process a frame, what happens?

You need to separate your update code from your drawing code and artificially insert more updates when the frame rate is low to keep the simulation running at a constant delta time.

See: http://www.sacredsoftware.net/tutorials/...tion.xhtml
Quote this message in a reply
Member
Posts: 241
Joined: 2008.07
Post: #3
That's a standard way of doing business. Update separate from draw but I'm dealing with 3D geometry. Also, more accurate physics requires a timer.
Quote this message in a reply
⌘-R in Chief
Posts: 1,265
Joined: 2002.05
Post: #4
Quote:
Quote:NSTimeInterval is always specified in seconds; it yields sub-millisecond precision over a range of 10,000 years.

What? Seconds or sub-miliseconds? 10k years? Huh?


All that says is how precise the NSTimeInterval data type is. NSTimeInterval is a floating point number representing seconds. The data type (a double) is large enough to offer precision past milliseconds, for a value representing a time of 10,000 years. In other words, it is precise enough to represent a time specified in seconds: 10,000 years x 365 days x 24 hours x 60 minutes x 60 seconds on the left hand side of the decimal point and 0.001... on the right side.
Quote this message in a reply
Member
Posts: 241
Joined: 2008.07
Post: #5
Code:
static double lastFrameTime = 0.0;
  static double cyclesLeftOver = 0.0;
  double currentTime;
  double updateIterations;
  
  currentTime = GetCurrentTime();
  updateIterations = ((currentTime - lastFrameTime) + cyclesLeftOver);

This is what I need to implement. I know how to do it, I've done it before, just not on the iPhone.

Code:
GetCurrentTime();

This function accesses the hardware to count processor cycles, which is translated into milliseconds with some math. The milliseconds are stored and this is how the time intervals are calculated. Is there no equivalent to the above functionality and the functionality that you referred me to?
Quote this message in a reply
Moderator
Posts: 3,579
Joined: 2003.06
Post: #6
I am using 3D geometry (which has nothing to do with this) and accurate physics timing too (constant 60 ticks per second on iPhone and 110 ticks on Mac). I am skeptical you fully understood the page I linked to. Wink
Quote this message in a reply
⌘-R in Chief
Posts: 1,265
Joined: 2002.05
Post: #7
bmantzey Wrote:That's a standard way of doing business. Update separate from draw but I'm dealing with 3D geometry. Also, more accurate physics requires a timer.

No, more accurate physics requires small delta steps. If a timer does not fire for 5 seconds, and you simply calculation positions using a delta of 5 seconds, you're going to run through walls and have all kinds of trouble. Everything will be entirely wrong.

The point is regardless of *WHEN* your timer is called, you should *ALWAYS* calculate physics on a known fixed time interval. For example, if you used, 1/100th of a second, then when your timer gets called after 5 seconds of not being called, there would be 500 iterations of physics updates, each using delta of 1/100th of a second, that way all collisions and object interactions are handled appropriately.
Quote this message in a reply
Member
Posts: 241
Joined: 2008.07
Post: #8
Freaksoftware, I'm sorry, I didn't see your message before I posted a reply to Jake's message.

NSTimeInterval says it is always specified in seconds but as you indicated, milliseconds could be retrieved from the right side of the decimal point. I'll take a closer look at this.
Quote this message in a reply
Moderator
Posts: 3,579
Joined: 2003.06
Post: #9
bmantzey Wrote:Is there no equivalent to the above functionality and the functionality that you referred me to?

You don't need to use another timer. Just do the same thing on iPhone that you've been doing -- which is actually what I was talking about, and that link too. You're technique will work perfectly on iPhone. That's what I use. In fact, that code looks mighty darn familiar Wink
Quote this message in a reply
⌘-R in Chief
Posts: 1,265
Joined: 2002.05
Post: #10
Code:
#include <mach/mach.h>
#include <mach/mach_time.h>

double GetCurrentTime()
{
    static mach_timebase_info_data_t sTimebaseInfo;
    uint64_t time = mach_absolute_time();
    uint64_t nanos;
    
    // If this is the first time we've run, get the timebase.
    // We can use denom == 0 to indicate that sTimebaseInfo is
    // uninitialised because it makes no sense to have a zero
    // denominator is a fraction.
    if ( sTimebaseInfo.denom == 0 ) {
        (void) mach_timebase_info(&sTimebaseInfo);
    }

    // Do the maths.  We hope that the multiplication doesn't
    // overflow; the price you pay for working in fixed point.
    nanos = time * sTimebaseInfo.numer / sTimebaseInfo.denom;
    return ((double)nanos / 1000000000.0);
}


You should avoid [NSDate timeIntervalSinceReferenceDate] and other methods because they're not accurate. If the clock is changed when your game is running, for example, you'll get wacky results.
Quote this message in a reply
Moderator
Posts: 3,579
Joined: 2003.06
Post: #11
Sheesh! This is like a chat room in here! I can't keep up LOL
Quote this message in a reply
Moderator
Posts: 3,579
Joined: 2003.06
Post: #12
This works on iPhone too:

Code:
#import <sys/time.h>
double GetCurrentTime(void)
{
    struct timeval time;
    
    gettimeofday(&time, nil);
    return (double)time.tv_sec + (0.000001 * (double)time.tv_usec);
}
Quote this message in a reply
Member
Posts: 749
Joined: 2003.01
Post: #13
AnotherJake Wrote:You need to separate your update code from your drawing code and artificially insert more updates when the frame rate is low to keep the simulation running at a constant delta time.

If I understand it correctly that only works when the bottleneck is the graphics and not the physics?

©h€ck øut µy stuƒƒ åt ragdollsoft.com
New game in development Rubber Ninjas - Mac Games Downloads
Quote this message in a reply
Member
Posts: 241
Joined: 2008.07
Post: #14
AnotherJake Wrote:I am using 3D geometry (which has nothing to do with this) and accurate physics timing too (constant 60 ticks per second on iPhone and 110 ticks on Mac). I am skeptical you fully understood the page I linked to. Wink

No, I do understand it. I'm trying to achieve time based motion. If I translate my geometry (which is 3D) by, say, 5.0f, that may appear slower or faster based on frame rate. That's why you're supposed to multiply the translation by the time between each frame. I understand that the draw function is only being called every 1/60 IF the frame rate is sustained at 60. If you don't multiply your translations and rotations by the time between each frame, you may have slowed down animation, because it's frame based.
Quote this message in a reply
Member
Posts: 241
Joined: 2008.07
Post: #15
FreakSoftware Wrote:No, more accurate physics requires small delta steps. If a timer does not fire for 5 seconds, and you simply calculation positions using a delta of 5 seconds, you're going to run through walls and have all kinds of trouble. Everything will be entirely wrong.

The point is regardless of *WHEN* your timer is called, you should *ALWAYS* calculate physics on a known fixed time interval. For example, if you used, 1/100th of a second, then when your timer gets called after 5 seconds of not being called, there would be 500 iterations of physics updates, each using delta of 1/100th of a second, that way all collisions and object interactions are handled appropriately.

I agree, that's what the Variable interval time-based physics solves. I'm asking about a timer. Rasp
Quote this message in a reply
Post Reply 

Possibly Related Threads...
Thread: Author Replies: Views: Last Post
  Timing issues markhula 8 4,916 Sep 29, 2010 07:56 AM
Last Post: mariocaprino
  Raster timing bars markhula 23 7,347 Sep 28, 2010 12:56 PM
Last Post: markhula