user542687
user542687

Reputation:

C++: Calculating Moving FPS

I would like to calculate the FPS of the last 2-4 seconds of a game. What would be the best way to do this?

Thanks.

Edit: To be more specific, I only have access to a timer with one second increments.

Upvotes: 7

Views: 7111

Answers (4)

Constantin
Constantin

Reputation: 8961

What you actually want is something like this (in your mainLoop):

frames++;
if(time<secondsTimer()){
  time = secondsTimer();
  printf("Average FPS from the last 2 seconds: %d",(frames+lastFrames)/2);
  lastFrames = frames;
  frames = 0;
}

If you know, how to deal with structures/arrays it should be easy for you to extend this example to i.e. 4 seconds instead of 2. But if you want more detailed help, you should really mention WHY you haven't access to an precise timer (which architecture, language) - otherwise everything is like guessing...

Upvotes: 0

EmeryBerger
EmeryBerger

Reputation: 3956

Near miss of a very recent posting. See my response there on using exponential weighted moving averages.

C++: Counting total frames in a game

Here's sample code.

Initially:

avgFps = 1.0; // Initial value should be an estimate, but doesn't matter much.

Every second (assuming the total number of frames in the last second is in framesThisSecond):

// Choose alpha depending on how fast or slow you want old averages to decay.
// 0.9 is usually a good choice.
avgFps = alpha * avgFps + (1.0 - alpha) * framesThisSecond;

Upvotes: 16

Adam Maras
Adam Maras

Reputation: 26843

Here's a solution that might work for you. I'll write this in pseudo/C, but you can adapt the idea to your game engine.

const int trackedTime = 3000; // 3 seconds
int frameStartTime; // in milliseconds
int queueAggregate = 0;
queue<int> frameLengths;

void onFrameStart()
{
    frameStartTime = getCurrentTime();
}

void onFrameEnd()
{
    int frameLength = getCurrentTime() - frameStartTime;

    frameLengths.enqueue(frameLength);
    queueAggregate += frameLength;

    while (queueAggregate > trackedTime)
    {
        int oldFrame = frameLengths.dequeue();
        queueAggregate -= oldFrame;
    }

    setAverageFps(frameLength.count() / 3); // 3 seconds
}

Upvotes: 2

david van brink
david van brink

Reputation: 3642

Could keep a circular buffer of the frame time for the last 100 frames, and average them? That'll be "FPS for the last 100 frames". (Or, rather, 99, since you won't diff the newest time and the oldest.)

Call some accurate system time, milliseconds or better.

Upvotes: 1

Related Questions