Skip to main content
gamedev.net
🔒 Locked

FPS problems

Started by Devil_Inside Jan 18, 2005 at 7:39 PM 13 replies 2.2k views
Original Post
Devil_Inside
Devil_Inside
I'm doing a Arkanoid style game. I've got an Athlon 2500+ and a GeForce 4 MX 440 64MB and the FPS is always about 60. When I tested this game on Athlon 3000+, AtiRadeon9800 PRO 128MB, the FPS started to jump from 400 to 1200. So, my "Time Based Movement" failed. I don't know what's the problem with FPS, but on the second PC it's impossible to play, the speed amplitude variates too much. Can Someone explain me why does the FPS jumps that much?
================= No Brain - No Pain =================
Armand
Armand
My first guess would be Vsync.
If your using open GL or DirectX check the driver options for that api set for Vsync enabled/disabled.

60 fps sounds like it's on. 400 fps would be off. if you enable it (for the default setting) on the 400fps mechine then it should work as expected.

Hope this helps.
Armand -------------------------It is a good day to code.
_Flecko
_Flecko
--------------Trans2D - 2D library for C# / Managed DirectX
Devil_Inside
Devil_Inside
How can I enable VSYNC inside the game? Is it possible?
================= No Brain - No Pain =================
Drew_Benton
Drew_Benton
Quote:
Original post by Devil_Inside
I'm doing a Arkanoid style game. I've got an Athlon 2500+ and a GeForce 4 MX 440 64MB and the FPS is always about 60. When I tested this game on Athlon 3000+, AtiRadeon9800 PRO 128MB, the FPS started to jump from 400 to 1200. So, my "Time Based Movement" failed. I don't know what's the problem with FPS, but on the second PC it's impossible to play, the speed amplitude variates too much. Can Someone explain me why does the FPS jumps that much?


That sounds about right to me. I have a Radeon 9600 Pro, 8x AGP, 128 MB and my fps are well over the 1200 fps mark when I ran the Time Based Movement tutorial formerly on GameTutorials. I also had a old Geforce Similar to that one that had low fps - but I think Armand is right about the VSync. I also think you time based movement function may have a problem - did you make it yourself for model it from somewhere else?
Devil_Inside
Devil_Inside
I would say that I did it myself from the examples. I use a common style:
At the beginning of the main loop I do:
float Now=timeGetTime()*0.001f
float Spf=Now-LastTime;
float Fps=1/Spf; //(For Printig Fps to the screen)
float DT=Spf*60; //(That's the Time I use to multiply my movement to)

Can I enable the VSync at my game start inside my program? Or the only way is through the driver's options?
================= No Brain - No Pain =================
Devil_Inside
Devil_Inside
Come on guys, i have no idea what to do now. I couldn't find the VSync switch in the options of the video driver. My old GeForce had it, i know 100%, but the new Radeon 9800 doesn't have it. I've got Catalyst Control Center ver 1.0.1733.17262. Catalyst (driver) ver: 04.10. Can you tell where is it if it's still there.

And my main problem is not that the FPS > 60. Time Based Movement solves this problem. My main problem is that the FPS jumps(!) from 1200 to 500-400 allmost every 1-10 seconds. This way, even without any visual difference between 60, 400 and 1200 FPS, the speed due to the Time Based Movement changes a lot. So, the first second the ball moves with a speed, and the next second it can move 3 times faster (if FPS drops down from 1200 to 400 for example). Then, there could be a pause in FPS changing, it stays at 1000 (for example), and then once again, it drops to 600, then jumps up to 1156. And so on, and so on....

If there is a way to solve that... Thanks in advance!!!
P.S. If there is a way to turn on the VSync in my game, could You tell my exactly how to do it. Thanks again!
================= No Brain - No Pain =================
mozie
mozie
Quote:

This way, even without any visual difference between 60, 400 and 1200 FPS, the speed due to the Time Based Movement changes a lot. So, the first second the ball moves with a speed, and the next second it can move 3 times faster (if FPS drops down from 1200 to 400 for example).


This really makes me think the problem lies in the time based movement. I also built my own time based movement method, its nothing original. But I do wonder what you are doing the 'timeGetTime()*0.001f' for. Why scale it down like that? I think that could also could make an effect on the math that you use to calculate the fps, ie the fps might not even be true.

oh wait! timeGetTime returns an int, in ms. Thaaaaats right.

It could be returning 0 ms on the high end system.

0 ms = 1000+ fps
1 ms = 1000 fps
2 ms = 500 fps
3 ms = 333 fps
4 ms = 250 fps

if you dont have better percision than 1 ms, your numbers will not be accurate when the time is very low (small number). the difference from 1 ms to 2 ms as far as FPS is concerned, is huge. even the 400-1200 is only less than 3 ms, but still a big factor for percision, if you are using the stuff for movement.

Good luck

kaysik
kaysik
Firstly if you've got changing framerates and your game objects aren't moving at constant speeds then your time-based movement isn't working right. Working timebased movement should be able to handle and frame-rate you throw at it - thats the whole point.

Despite that you don't need vsync to lock your update times - just do it manually. This way will also make sure that even if one comp has a refresh of 60 htz and another has 85htz etc then you'll still get a minimum gap between game updates (which should solve your timebased movement woes).

For 60htz each tick must have at least a 16ms break befor the next update, so just create one:

while (!done){   // get the current time   curTime = getTime();   // work out how much time has passed since last update   deltaT = curTime - lastTime;   if (deltaT > 16) // only update if at least 16ms have passed   {      lastTime = curTime;      update(deltaT);   }   render();}



Edit:
Its also quite easy to add a maximum update time so you can never have an update with a huge time gap.

//All you need todo is change the line: lastTime = curTime; to:if (deltaT > MAX_TIME){   deltaT = MAX_TIME;   lastTime += MAX_TIME;}else   lastTime = curTime;}


This will make sure that if your deltaT has been more than the maximum time allowed (200ms is a decent value), then it will cap it. On very old computers this may cause your game to run slowly (because every update will take longer so its calculatios will never catch up), but thats alot better than having units fall through the world IMHO.

[Edited by - kaysik on January 19, 2005 8:17:55 PM]
Devil_Inside
Devil_Inside
Thanks a lot. It's working now.
================= No Brain - No Pain =================
fireye
fireye
Quote:
Original post by Devil_Inside
Can I enable the VSync at my game start inside my program? Or the only way is through the driver's options?


On OS X with OpenGL, you can use aglSetInteger(ctx, AGL_SWAP_INTERVAL, 1) to enable vsyncing. Pass 0 instead of 1 to turn it off.
Devil_Inside
Devil_Inside
Another question. Does every card starting from GeForce 4 Mx supports wglSwapInervalEXT extension? Or there could be some video card that don't support it. And what do i do in this situation?
================= No Brain - No Pain =================
Devil_Inside
Devil_Inside
I've allready thought about differences between refresh rates. I'm using the method:
DT=60/UsersRefreshRate; // I do this only once, at the beggining. This removes the strange speed increase/reduction after a FPS dropdown.
Then I,for example, do:
Ball.x+=Ball.mx*DT;
That compensates the differences in framerates.

I think that on unsupported video cards i'll calculate DT using another ecuation:
DT=60/UsersFPS; //I'll do this every frame;

Thanks For Your Help!

[Edited by - Devil_Inside on January 22, 2005 6:28:54 AM]
================= No Brain - No Pain =================

Topic Locked

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

Sign in to reply to this topic.