• Advertisement
Sign in to follow this  

Problems with timeGetTime()

This topic is 1983 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hey GameDev

I am trying to make my game run based off the delta between 2 frames, so that it will run the same speed on every computer.

I am trying to get the delta between 2 frames like this:


static DWORD lastFrameTime;
static DWORD frameDelta;
frameDelta = timeGetTime() - lastFrameTime;
d3dDevice->Clear(0, 0, D3DCLEAR_TARGET, 0x000000, 1, 0);
d3dDevice->BeginScene();
d3dSpriteMachine->Begin(D3DXSPRITE_ALPHABLEND);
Draw(sprite, frameDelta);
d3dSpriteMachine->End();
d3dDevice->EndScene();
d3dDevice->Present(NULL, NULL, NULL, NULL);
Update(mousePosition, frameDelta);
lastFrameTime = timeGetTime();


The problem is that the delta always ends up 0, or at most, 1. I tried stepping through the code and I find that when lastFrameTime is set to timeGetTime() at the end, then on the next frame the time is the same. What I mean, is that it appears to be run through one frame on say 123342342 (this is just an example) and then on the second frame, timeGetTime returns 123342342 again so the delta is set to 0. I'm obviously missing something. Any help? haha

Share this post


Link to post
Share on other sites
Advertisement
You shouldn't be calling [font=courier new,courier,monospace]timeGetTime[/font] twice per frame like that -- the result of that code is that you're not timing your Draw/Update code at all, you're only timing the code that comes between the bottom line and the top line.
You can change it to only call [font=courier new,courier,monospace]timeGetTime[/font] once per frame like this:static DWORD lastFrameTime = 0;
DWORD frameDelta;
DWORD thisFrameTime = timeGetTime();
if( lastFrameTime == 0 )//first frame!
frameDelta = 0;
else
frameDelta = thisFrameTime - lastFrameTime;
lastFrameTime = thisFrameTime;
//DoStuff


P.S. [font=courier new,courier,monospace]timeGetTime[/font] isn't very accurate, so most people use [font=courier new,courier,monospace]QueryPerformanceCounter[/font]/[font=courier new,courier,monospace]QueryPerformanceFrequency[/font] instead, or you can use someone else's ready-made high accuracy timer, such as timer_lib. Edited by Hodgman

Share this post


Link to post
Share on other sites

You shouldn't be calling [font=courier new,courier,monospace]timeGetTime[/font] twice per frame like that -- the result of that code is that you're not timing your Draw/Update code at all, you're only timing the code that comes between the bottom line and the top line.
You can change it to only call [font=courier new,courier,monospace]timeGetTime[/font] once per frame like this:static DWORD lastFrameTime;
static DWORD frameDelta;
DWORD thisFrameTime = timeGetTime();
frameDelta = thisFrameTime - lastFrameTime;
lastFrameTime = thisFrameTime;
//DoStuff


P.S. [font=courier new,courier,monospace]timeGetTime[/font] isn't very accurate, so most people use [font=courier new,courier,monospace]QueryPerformanceCounter[/font]/[font=courier new,courier,monospace]QueryPerformanceFrequency[/font] instead, or you can use someone else's ready-made high accuracy timer, such as timer_lib.


Thank you, but I'm not sure I understand. What exactly is the problem? And why shouldn't I call TimeGetTime twice?

Thanks :)

Share this post


Link to post
Share on other sites
You're measuring the time from the end of frame#1 to the beginning of frame #2.
A = get the time.
...spend a while doing stuff...
B = get the time
...loop for next frame...
C = get the time
time spent doing stuff previously = C-B (wrong)
...spend a while doing stuff...
etc


You really want to be measuring the time from the start of frame#1 to the start of frame#2.
A = get the time.
...spend a while doing stuff...
...loop for next frame...
B = get the time
time spent doing stuff previously = B-A
...spend a while doing stuff...
etc
Edited by Hodgman

Share this post


Link to post
Share on other sites

You're measuring the time from the end of frame#1 to the beginning of frame #2.
A = get the time.
...spend a while doing stuff...
B = get the time
...loop for next frame...
C = get the time
time spent doing stuff previously = C-B (wrong)
...spend a while doing stuff...
etc


You really want to be measuring the time from the start of frame#1 to the start of frame#2.
A = get the time.
...spend a while doing stuff...
...loop for next frame...
B = get the time
time spent doing stuff previously = B-A
...spend a while doing stuff...
etc



I think I understand you now.

Is this better?


static DWORD lastFrameTime;
static DWORD frameDelta;
static DWORD thisFrameTime;
thisFrameTime = timeGetTime();
if (lastFrameTime == 0)
frameDelta = 0;
else
frameDelta = thisFrameTime - lastFrameTime;
lastFrameTime = thisFrameTime;
d3dDevice->Clear(0, 0, D3DCLEAR_TARGET, 0x000000, 1, 0);
d3dDevice->BeginScene();
d3dSpriteMachine->Begin(D3DXSPRITE_ALPHABLEND);
Draw(sprite, frameDelta);
d3dSpriteMachine->End();
d3dDevice->EndScene();
d3dDevice->Present(NULL, NULL, NULL, NULL);
Update(mousePosition, frameDelta);

Share this post


Link to post
Share on other sites
You should initialize lastFrameTime to 0, otherwise there's no reason to expect it will actually be 0 for the first frame. Also, there is no reason for thisFrameTime and frameDelta to be static. You're refiguring them each loop. The reason lastFrameTime needs to be static is that you need to know it's value from the previous iteration.

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement