Advertisement

ai framerate independence

Started by February 07, 2002 09:57 AM
16 comments, last by Edgware 22 years, 9 months ago
Edgware, multithreading really is the optimal solution to your original question. "a person" basically didn''t bother to really understand the question or its implications, as he states himself that his pseudocode has a "major flaw" in that it is tied to the frame rate... hence it doesn''t solve the original problem!

Multithreading *is* an advanced topic, but trying to get around it by time-slicing your program''s execution based on tick-counts is NOT the way to go.

Argus, be careful of using the word "process" to define thread, as that will promote some confusion. These are two different things... a PROCESS has its own data and code space, which is independent of other processes running on a system, and can have multiple THREADs of execution. Each thread within a process shares the same memory space (which is why thread-safety mechanisms like critical sections and mutexes are necessary). Does this make sense?
umm, maybe you misunderstood what i meant by drop in framerate. if you really dont understand the code, here is a version that does not have that problem (its is synced to the physics like it should be).

  // PSUDEO code#define TICK_MS 33 // 30 times per secondfor(;;){      curTime = gettime();   maxCnt=0;   while((curTime-time0)>=TICK_MS || maxCnt>MAX_LOOP)     {         Do_Physics()         Do_FakeSmart_Stuff();         time0+=TICK_MS;         maxCnt++;         // may want to update curtime as well      //   curTime = gettime();   }   float percentInFrame = (curTime-time0)/TICK_MS;   if(percentInFrame>1.0) // in case you bailed early      percentInFrame=1.0;   Render(percentInFrame);}  


this does not have the frameate problem. i think the major thing you missed Pyabo is the fact that the reason low framerates would kill the ai is because its not being synced to the physics (hence the gamestate). you could modfy the code to stagger the time for the ai (ie update in incremnets of physics updates). multithreading has even more issues and in the end will be a poor solution for ai in a game, especially if the ai relies on the game state. if the game state changes are based on framerate then the ai will be based on framerate no matter how you seperate it (via fixed time steps or multithreading).

here is a simple logical proof.

Given
AI is dependent upon gamestate
gamestate is dependent upon physics
physics is NOT dependent upon framerate
---
AI is NOT dependent upon framerate.

Given
AI is dependent upon gamestate
gamestate is dependent upon physics
physics is dependent upon framerate
---
AI is dependent upon framerate.


as you can see the ai is only dependent upon the framerate IF the physics is. which is why you use fixed time steps AND not multithreading with framerate dependent physics. i was hoping to break down the problem in a simply fashion and allow him to make the final connection (ie grouping physics with ai), unfortunatly i assume since YOU did not see the connection, then he probally did not see it.

btw Pyabo, please explain to me if you can, how ai can be framerate independent if the physics hence the gamestate is framerate dependent when you thread the ai.

so in the end, Pyabo, its YOU who dont really bother to comprehend the question and its implications. i probally should not have assumed that Edgware knew how ai worked (ie its linked to the gamestate no matter how you slice it).
Advertisement
Thanks Pyabo - wasn''t sure whether there was a difference.
Thanks for the replies people. I was not just after one way of seperating out the ai from the frame rate/world state so all the different opinions are great
Ummm.... OK. In the interest of diplomacy, I will concede that you are correct in all things. LOL

Actually, I apologize that I sounded so snippy in my original post, but I was somewhat aghast at someone suggesting that "multi- threading is not the answer." In fact, multi-threading is really THE ONLY answer. Here I go getting snooty again.

The fact of the matter is, this kind of thing is the perfect task to apply multi-threading methodology to. Yes, multi-threading can be ugly, and yes it''s complicated at times, and yes it can also be a big pain the ass. I once spent an entire week tracking down a SINGLE bug due to a thread race condition. However, that being said... multithreading is absolutely necessary in almost any app that actually does more than one single thing, and this definitely includes games. Don''t run from multithreading because it''s difficult it... embrace it, learn it, love it.
Chaps, I have been reading what you have been saying and I think either way can work, its how you implement it.
If it were me, I would give the AI reaction times (stored in the bots class). The reaction time for each bot is incremented by 1, and when their reacion time is met (say 1.2 seconds to notice and react) (60FPS = 60 updates to the AI reaction counter, when it meets 72 it can change its action). This way you rarely call the AI code for a bot on more than once per bot. Simply set the reaction timer staggered when bots are loaded.

What happens? Ok, a bot decides through its AI to go to point X to get a gun. 1 second later, it gets jumped by a player. Low and behold, its reaction timer is reset and for 1.2 seconds its prone before it can change its action (re-run the AI). When the AI runs, it takes a single frame to process and decide what its gonna do, suddenly it dives for cover and fires at the same time.

Bingo. We have a bot that reacts. So, I would created an array of the bots (say we had 10 bots), BOT BOTARRAY[10] (BOT is my custom class with lots of information and storage for convenience and memory of moves it likes, that kinda stuff). Then, process the bots in a wrapped function
process_bots(void)
{
int i = 0;
//walk through the array for each bot
for (i = 0; i < 10; i++)
{
//is the reaction_time greater than the reaction counter?
if (BOTARRAY->reaction_time > BOTARRY->reaction_count)<br> //if so, they dont get to update<br> continue;<br> //ok, lets process its AI<br> update_ai(BOTARRAY)<br> {<br> //We could do a quick check here to see if it needs to<br> //process here, it may not want to change its action<br> //e.g run for a weapon, go for health<br> //Do all the AI stuff here<br> …<br> }<br> }<br>}<br><br>This is pretty basic and no where near indepth enough for realtime AI, but you get the idea.<br>AI is so important in FPS type games that CPU time should be given to it. I wouldnt set up a thread for it, I would make sure I only processed AI for one bot per frame, and optimise later with this in mind. </i>
Unifex
Advertisement
quote: Original post by Pyabo
Actually, I apologize that I sounded so snippy in my original post, but I was somewhat aghast at someone suggesting that "multi- threading is not the answer." In fact, multi-threading is really THE ONLY answer. Here I go getting snooty again.

The fact of the matter is, this kind of thing is the perfect task to apply multi-threading methodology to. Yes, multi-threading can be ugly, and yes it''s complicated at times, and yes it can also be a big pain the ass. I once spent an entire week tracking down a SINGLE bug due to a thread race condition. However, that being said... multithreading is absolutely necessary in almost any app that actually does more than one single thing, and this definitely includes games. Don''t run from multithreading because it''s difficult it... embrace it, learn it, love it.


Heh...I see I missed some fun whilst book editing!

I agree with Pyabo...multithreading is really the best way to handle this. If you multithread you gain immense control over your AI and your physics and you can still plug in timers to get a finer degree of control (as others have suggested) if you want. And honestly it''s not all that hard to learn; synchronization (making sure one thread isn''t trying to read a variable that another thread is in the middle of writing) is pretty easy with modern programming languages.




Ferretman

ferretman@gameai.com
www.gameai.com

From the High Mountains of Colorado

Ferretman
ferretman@gameai.com
From the High Mountains of Colorado
GameAI.Com

quote: Original post by a person
umm, if you are multithreading nearly anything you will always have some sort of semaphore


Dont multithread. its bad and messy and win32y and semaphored and all sorts. i have had hideous problems trying to multithread things even when writing something as undemanding as a midi sequencer. (that''s not realtime a game would be worse)

In the same project, i ended up using a system like the one described earlier, manually counting system ticks or game ticks or anything and doing the timing myself. and it works beautifully.

the only downside is the its very easy for your code to get messy, especially if you have several "timed processes" that run at different frequencies.

just my opinion. im a delphi coder, so im not sure how much you want to listen to me. :D
die or be died...i think

This topic is closed to new replies.

Advertisement