Optikal Posted August 29, 2003 Posted August 29, 2003 If you use time-based algorithms (animations, physics, AI, etc) then they will run at the exact same speed regardless of framerate. This is the way almost all modern games operate. Quote
Ctaesis Posted August 30, 2003 Posted August 30, 2003 Does anyone know what the article is talking about here: For flipping sprites you would do the same. You would have to declare a float variable that keeps track of the current frame. Also, you would limit the frames drawn per second. sprite.fcurrentframe+=sprite.framespersecond*frametime; if(sprite.fcurrentframe>sprite.totalframes) { int isoverby=sprite.fcurrentframe/sprite.totalframes; sprite.fcurrentframe-=mesprite.totalframes*isoverby; } sprite.icurrentframe=(int)sprite.fcurrentframe; sprite_draw(&sprite); This skips frames if you have a slow PC, and on a fast PC it will run every frame but no more than sprite.framespersecond. It seems to be missing something.... I want to be able to skip the rendering stage of my game loop when the FPS limit is reached - I understood the first part of the article about how to limit the movement of game objects, but this second half has me baffled. Ideas? Quote
apanjocko Posted September 3, 2003 Posted September 3, 2003 i HAVE to agree with Optikal here. I have to spoil everyones fun here even if this IS an OK way to do it the current "state-of-the-art" way is to do a deterministic game-loop using "time-frames" or should i call it "time-step-based" game-loop that allows for unlimited fps but same speed on all computers. you basically every time the loop goes around you update the game-state in loops of X milliseconds. so on a slow computer 42 milliseconds passed since last loop, and you have physics and everything on 10ms, you loop while 10*X<42 and save the last 2 fot next loop. i have read an article on this on gamasutra (have no link sorry, and you have to register) and i HIGHLY recommend people that are intreseted in this to read up on it. thanks :) i love this topic it's very intreseting. Quote
apanjocko Posted September 3, 2003 Posted September 3, 2003 i found it for ya! http://www.gamasutra.com/features/20010713/dickinson_01.htm really readworthy! :) Quote
smremde Posted October 10, 2003 Posted October 10, 2003 Problems i copied your class, adding Imports System.Runtime.InteropServicesto the top and i get exceptions: An unhandled exception of type 'System.InvalidProgramException' occurred in xfengine.dll Additional information: Error: PInvoke item (field,method) must be Static. The program '[1588] XF2.exe' has exited with code 0 (0x0). xfengine.dll is my class library containing the high resolution timer and XF2.exe is the console app using xfengine.dll any help much appreciated Stephen Quote
wyrd Posted October 18, 2003 Posted October 18, 2003 (edited) Like everyone else, I programmed my own Performance Timer class. I used this in a game loop to test it, and it works perfectly. I found the others that were provided a little disjointing to use, which is why I programmed my own. Maybe it'll help those who still don't fully understand how it's working *shrug* A few reminders about how this all comes together: To base game movements off pixels per second multiplied by the current ticks per second, and for animation multiply frames per second by the current ticks per second. If you add up the ticks per second for a full second, the total will come out to 1. This is because TicksPerSecond will give you a fractional time based off of 1 second. The current frames per second is the inverse of the ticks per second (1.0/timer.TicksPerSecond) using System; using System.Runtime.InteropServices; namespace DDUtil { /// <summary> /// A high performance timer. /// </summary> public class PerfTimer { #region Imported Methods /// <summary> /// The current system ticks (count). /// </summary> /// <param name="lpPerformanceCount">Current performance count of the system.</param> /// <returns>False on failure.</returns> [DllImport("Kernel32.dll")] private static extern bool QueryPerformanceCounter(out long lpPerformanceCount); /// <summary> /// Ticks per second (frequency) that the high performance counter performs. /// </summary> /// <param name="lpFrequency">Frequency the higher performance counter performs.</param> /// <returns>False if the high performance counter is not supported.</returns> [DllImport("Kernel32.dll")] private static extern bool QueryPerformanceFrequency(out long lpFrequency); #endregion #region Member Variables private long _startTime = 0; private long _recordTime = 0; private double _ticksPerSecond = 0; #endregion #region Constructor /// <summary> /// Creates a new PerfTimer. /// </summary> public PerfTimer() { // No need to do anything. } #endregion #region Methods /// <summary> /// Records stop time and ticks per second from when this PerfTimer was started. /// </summary> public void Record() { // Record when the timer was recorded and the ticks per second. _recordTime = PerfTimer.Counter; _ticksPerSecond = (double) (_recordTime - _startTime) / (double) PerfTimer.Frequency; } /// <summary> /// Starts this PerfTimer at the specified tick count. /// </summary> /// <param name="ticks">Tick count to start at.</param> public void Start(long ticks) { // Record when the timer was started. _startTime = ticks; } #endregion #region Properties /// <summary> /// Gets the number of ticks per second based off the current start and record times. /// </summary> public double TicksPerSecond { get { return _ticksPerSecond; } } /// <summary> /// Gets the tick count of when this PerfTimer was started. /// </summary> public long StartTime { get { return _startTime; } } /// <summary> /// Gets the tick count of when this PerfTimer was last recorded. /// </summary> public long RecordTime { get { return _recordTime; } } /// <summary> /// Gets the frequency that this PerfTimer performs at. /// </summary> public static long Frequency { get { long freq = 0; QueryPerformanceFrequency(out freq); return freq; } } /// <summary> /// Gets the current system ticks. /// </summary> public static long Counter { get { long ticks = 0; QueryPerformanceCounter(out ticks); return ticks; } } #endregion } } Sample on how to use it (it's almost too simple); PerfTimer timer = new PerfTimer(); timer.Start(PerfTimer.Counter) while (_playGame) { timer.Record(); // ... update game objects with object.Update(timer.TicksPerSecond). // ... display fps with 1.0/timer.TicksPerSecond. timer.Start(timer.RecordTime); } Edited October 18, 2003 by wyrd Quote Gamer extraordinaire. Programmer wannabe.
Recommended Posts
Join the conversation
You can post now and register later. If you have an account, sign in now to post with your account.