Allegro.cc - Online Community

Allegro.cc Forums » Programming Questions » install_int_ex() problem

This thread is locked; no one can reply to it. rss feed Print
install_int_ex() problem
Vasco Freitas
Member #6,904
February 2006
avatar

I'm using the method in allegro's FAQ to make my game run at the same speed on all computers.

The problem is it seems that I can't make it go any faster than 64 fps, even though I call install_int_ex() with the parameter BPS_TO_TIMER(100). I'm sure this isn't a hardware limitation, bacause without limiting the fps I can run it at about 700 fps... Could this be a install_int_ex() or BPS_TO_TIMER() limitation?

BAF
Member #2,981
December 2002
avatar

Allegro's timers don't have a very high resolution, so it sounds about right. Then again... I've never had a timer that limited my FPS, just my logic. You might be doing something wrong.

kazzmir
Member #1,786
December 2001
avatar

The logic part of your game is slowing the game down. Comment out the part the runs the logic and your fps will sky rocket.

Why do you need more than 64 fps?

Vasco Freitas
Member #6,904
February 2006
avatar

kazzmir said:

The logic part of your game is slowing the game down.

That's surely not the problem. I tried commenting out all logic and the game keeps running at 64 fps. And if I remove the "while (speed_counter > 0)" loop, it runs at 700 fps.

kazzmir said:

Why do you need more than 64 fps?

Just so the game is more smooth and responsive...

kazzmir
Member #1,786
December 2001
avatar

Paste the code you use to set up the timer.

Steve++
Member #1,816
January 2002

Quote:

Just so the game is more smooth and responsive...

As I discussed in another thread, you don't need to render beyond the monitor's refresh rate to have a smooth and responsive game (in fact this degrades responsiveness because you waste rendering time at the expense of processing gameplay). You can run a triple-buffered render loop in one thread and the game logic in another. By doing this, you're capped at rendering at the rate beyond which no one can tell the difference. Instead of the spare CPU time being shared by game logic and redundant rendering, any surplus gets completely dedicated to game logic, making it much smoother than a single-threaded approach. All you need to figure out is multithreaded programming (handy if you know already) and highly accurate timing. Both of these are usually platform-dependent (especially the latter).

By the way, that method in the Allegro FAQ is a bit outdated. It assumes you can set an arbitrary frequency, which is not the case except for DOS. Windows, Linux and any other multitasking OS take control of the timer interrupt and set it to something like 50, 60 or 100 bps. The OS's timer interrupt handler is used in preemptive multitasking and to supply a fixed low-resolution timer service to applications that may need it. Allegro uses this to simulate DOS-style arbitrary frequency timer interrupts.

The reality is that we shouldn't program games the way we used to - with absolutely everything synchronised to just one thing - such as a timer or screen refresh. So we need to separate game logic from rendering by multithreading. By triple buffering, the rendering thread synchronises itself to the screen's refresh rate. You could synchronise the game logic to something - either using the same thread as the render logic or by using the OS's timer service. But this makes for jerky gameplay because when all threads have nothing to do, the process will sleep until the OS's next multitasking 'heartbeat', even if some work must be done before this (and the OS's heartbeat is not synchronised with the monitor refresh rate). For this reason, something has to keep the game process alive. This is achieved by keeping at least one thread busy. Since we can't keep the rendering thread busy when it's synchronised to the refresh rate, the only other choice is the game logic thread. This is a big reason why we've moved away from fixed-resolution timing and integer-based geometry to delta timing and floating point-based geometry (another reason being that 3D is way less deterministic in its rendering times than 2D, so we need to cut down the choppiness by eliminating synchronisation waiting).

Just on a side note, it was mentioned in the other thread (see above) that the reason games don't take this multithreaded triple-buffered approach is that they're developed with benchmarking in mind. In my opinion, the best form of benchmark is not the number of frames per second, but the time it takes to actually render a frame. Unfortunately, the meat-head masses out there (i.e. those that own powerful computers but couldn't tell the difference between 1 and 0) prefer a metric that favours higher numbers rather than lower numbers.

I think it would be interesting actually to benchmark a game against itself on the same computer... The game could run in two modes - multithreaded triple buffered and single threaded double buffered (or whatever mode doesn't wait for vsync). Both modes would show frames per second, which would be the number of times the game logic executes every second. Using the former mode, if rendering fps is almost always at the monitor refresh rate, then gameplay fps will be much higher than that of the latter mode.

Vasco Freitas
Member #6,904
February 2006
avatar

Steve++ said:

(...)

What you say makes sense, but it seems quite complicated to implement. I assume that threads are needed so that if I'm in the middle of a logic function while the screen is refreshed, I should jump right away to a screen rendering function right? But what about the calculations I made halfway through the logic function? And what about the time it takes to render something to a buffer and then to the screen (I assume this is done with triple-buffering but I don't really understand how it works...)? I would also have to have some kind of a deltaTime variable to multiply by the movement calculations right? And is this method worse for slower PCs?

Are there any tutorials for implementing that method?

Is there a way to simply use the method I am using, but with 100 FPS (I think 100 is a reasonable amout)? Or is there another better way but without having to code threads? Or maybe a library that would make it easier to use your method...

Marco Radaelli
Member #3,028
December 2002
avatar

Steve++ said:

(...)

Sounds interesting. Threads flagged :)

Steve++
Member #1,816
January 2002

Quote:

Are there any tutorials for implementing that method?

I haven't looked for any, so I haven't found any yet. These are my own evolving thoughts. It seems so obvious that I'm sure other people have written tutorials. Try gamedev.net.

Quote:

Is there a way to simply use the method I am using, but with 100 FPS (I think 100 is a reasonable amout)?

Unfortunately if you're using that method, you are restricted to whatever the host OS is using as its timing resolution. You can still use Allegro of course; if for example you're using windows, find out what its timing resolution is (it's written somewhere in the Allegro manual) and use that. It should be a bit smoother than some arbitrary number. But bear in mind that the OS timer is not synchronised to the monitor refresh rate. For example you could have 100Hz OS timer and 85Hz screen refresh rate. So you'll either get a tearing effect, jerkiness or both.

PS. The thread I linked (above) is still active and interesting :)

Go to: