Skip to main content
gamedev.net
🔒 Locked

FPS - timebased movemet

Started by DanielH 30 replies 1.5k views
Original Post
DanielH
DanielH
How do i calculate the exact FPS, i need it for implenting timebased movement. In delphi I could use getTickCount() to get the current timestamp, but how do i do that in c++? I want c++ code!
ACAC
ACAC
The most accurate method I know of is to use

QueryPerformanceFrequency() to get the amount of ''ticks'' per second

then....use
QueryPerformanceCounter() to get the amount of ticks since the computer began..

then totalTicks/ticksperSecond = time


hope this helps
DanielH
DanielH
How do i know tickspersec?
SysOp_1101
SysOp_1101
Just like ACAC said: ''QueryPerformanceFrequency() to get the amount of ''ticks'' per second''.
SysOp_1101
DanielH
DanielH
Ah :D Missed that
erjo
erjo
GetTickCount( );
it''s in windows.h, and it doesnt actually return ticks, it returns the amount of milliseconds that has passed since the computer was started.
Just thought I would put my 0.02€ in.
DanielH
DanielH
oops

[edited by - DanielH on February 20, 2003 11:09:08 AM]
DanielH
DanielH
How do i use QueryPerformanceCounter and Frequency?

This doent work:

int counter = QueryPerformanceCounter();

and neighter does this:

int counter;
QueryPerformanceCounter(counter);
DanielH
DanielH
How do i use QueryPerformanceCounter and Frequency?

This doent work:

int counter = QueryPerformanceCounter();

and neighter does this:

int counter;
QueryPerformanceCounter(counter);
DanielH
DanielH
Doesn´t work!

This code compiles but the program crashes

void CFPSCounter:ushTime()
{
_LARGE_INTEGER counter,freq;
QueryPerformanceCounter(&counter);
QueryPerformanceFrequency(&freq);

m_Start = counter.QuadPart / freq.QuadPart;
}

void CFPSCounter:opTime()
{
_LARGE_INTEGER counter,freq;
QueryPerformanceCounter(&counter);
QueryPerformanceFrequency(&freq);

int now = counter.QuadPart / freq.QuadPart;
m_FPS = 1000 / (now-m_Start);
}
Tybalt
Tybalt
Look it up in the MSDN. I believe it returns a LARGE_INTEGER, or you pass it a pointer to one which it fills in. Either way, it''s well documented.
DanielH
DanielH
Wouldn´t it be easier if i just used GetTickCount instead?
SysOp_1101
SysOp_1101
If you don't need a high resolution timer, you can indeed use GetTickCount(). This is a code snippet that I use for quick and dirty FPS calculations in my software 3D engine:


...Initialization...
int current_tick = GetTickCount();
int fps = 0;
...Initialization...

...Main Game Loop...
if((GetTickCount() - current_tick) >= 1000) {
fps = 0;
current_tick = GetTickCount();
}
++fps;
...Main Game Loop...


There are better ways to approach it, but hopefully this will give you another possible angle to solving your problem.

HTH

[edited by - SysOp_1101 on February 20, 2003 2:11:54 PM]
SysOp_1101
Kaalot
Kaalot
be careful with now,m_Start, and m_FPS. I don''t know if they have to be large integers as well. Also, in my code, I used a combination of LARGE_INTEGER''s and __int64''s, mostly __int64''s -- dunno if that matters somehow. I''m just learning myself. Also, I was the Anon above.
evillive2
evillive2
btw, are you sure you can use QueryPerformanceCounter?
if QueryPerformanceFrequency returns 0 then your hardware does not support using this. Also, this is a huge pain to use. I stick with timeGetTime(). It works well enough for me.

This comes from the MSDN Library:

    
LARGE_INTEGER Time;

void StartTime(void)
{
QueryPerformanceCounter(&Time);
}

ULONG EndTime()
{
LARGE_INTEGER liDiff;
LARGE_INTEGER liFreq;

QueryPerformanceCounter(&liDiff);

liDiff.QuadPart -= Time.QuadPart;
liDiff.QuadPart *= 1000; // Adjust to milliseconds, shouldn't overflow...

(void)QueryPerformanceFrequency(&liFreq);

return ((ULONG)(liDiff.QuadPart / liFreq.QuadPart));
}


hope that helps.

[edited by - evillive2 on February 20, 2003 2:34:48 PM]
Evillive2
Sharky
Sharky
Take a look at the timer stuff (under the First Steps section) by following the link here. Take a look through it - hopefully it''s straightforward to understand.

Regards,
Sharky
DanielH
DanielH
[doubble post]

[edited by - DanielH on February 20, 2003 2:57:29 PM]
DanielH
DanielH
Something isn´t right here :-

  
class CFPSCounter
{
private:
float m_FPS;
int m_Start;
public:
CFPSCounter() { m_FPS = 1; };
~CFPSCounter() { };

float GetFPS() { return m_FPS; };
void PushTime();
void PopTime();
float UnitsPerSec(float n);
};

void CFPSCounter::PushTime()
{
m_Start = GetTickCount();
}

void CFPSCounter::PopTime()
{
int now = GetTickCount();
if (now-m_Start!=0)
{
m_FPS = 1000 / (now-m_Start);
}
else
{
m_FPS = 1;
}
}

float CFPSCounter::UnitsPerSec(float n)
{
return n/m_FPS;
}


[edited by - DanielH on February 20, 2003 2:58:02 PM]
DanielH
DanielH
Ok... i changed the code a bit now.


  
CFPSCounter::CFPSCounter()
{
QueryPerformanceFrequency(&m_TimerFreq);
m_Time = 0.0;
m_FPSUpdate = 0.0;
m_DeltaTime = 0.0;
m_FPS = 0.0;
m_Start = 0.0;
}

void CFPSCounter::Update()
{
QueryPerformanceCounter(&m_TimerCur);
double oldTime = m_Time;
m_Time = (double)((double)(m_TimerCur.QuadPart - m_TimerStart.QuadPart) / (double)m_TimerFreq.QuadPart);
m_DeltaTime = m_Time - oldTime;

m_FPSUpdate += m_DeltaTime;
if(m_FPSUpdate >= 1.0)
{
m_FPSUpdate = 0.0;
m_FPS = 1000 / (m_Time-oldTime);
}

}

float CFPSCounter::UnitsPerSec(float n)
{
return n/m_FPS;
}


But... m_FPS doesn´t change... why?
I guess i need to use this method anyway... or was there any erros in my last code that made the sprite movement choppy?
Expendable
Expendable
quote:
Original post by Sharky
Take a look at the timer stuff (under the First Steps section) by following the link here. Take a look through it - hopefully it''s straightforward to understand.



I''ll second Sharky''s recommendation. I looked at his QueryPerformanceCounter tutorial/class a couple of weeks ago. It works really well and is relatively easy to understand.

E-x-p-e-n-d-a-b-l-e

Topic Locked

This topic has been locked by a moderator. New replies are not allowed.

Sign in to reply to this topic.