Jibble

Author Topic: Script dependant on game's FPS...is this a good solution?  (Read 2372 times)

Knox

  • Storm Behind The Badge
Hi,

I have a script that seems to be dependant on the game's framerate, but not too sure if my solution to overcome this is a good idea. I placed this question in the "Advanced" section since Im guessing what you guys might suggest could be complicated, but Im not sure.

Basically what Im doing is if the user presses the left arrow key down for a certain amount of time, it calls a script that will turn the car in 30º increments. The values I use for the timer that tells when to stop the rotation has been set by me manually so that the car turns left perfectly at an intersection on an isometric map. The only thing is, I tested this script on two computers where the FPS is about 98, and everything works as it should...but on a laptop where the FPS is 35, the turning "mechanism" timers no longer seem to be "in sync" and the car rotates too much (therefore missing the intersection turn)...the various values for the timer (iTurnTimer) are no longer valid when the game runs at a lower FPS:

Code: Adventure Game Studio
  1. //in the driving map room.asc:
  2. function on_key_press(int keycode)
  3. {
  4.      if (IsKeyPressed(375)) //LEFT TURN  
  5.     {
  6.       setTurnTimerValue(0);
  7.       if (bLeftKeyHOLD == false) carDrive_LEFT(eManual, 0);
  8.     }
  9. }
  10. // in my driving module:
  11. void setTurnTimerValue(int iMode)
  12. {
  13.   if (iMode == 0) //Left
  14.   {
  15.     if (fDrive_Angle == 210.0 || fDrive_Angle == 30.0) iTurnTimer = 17; //NW or SE                
  16.     else if (fDrive_Angle == 330.0 || fDrive_Angle == 150.0) iTurnTimer = 20; //NE or SW                      
  17.     else
  18.     {
  19.       iTurnTimer = 0;
  20.       return;
  21.     }  
  22.   }                                      
  23. }
  24.  
  25. function repeatedly_execute()
  26. {
  27.       if (!bAutomatic) //Manual
  28.       {
  29.         //TURN MANUAL
  30.         if (IsKeyPressed(375)) processQuickTurn_Left(1);
  31.         else
  32.         {
  33.           iHoldKeyPressLeft = 0;
  34.           if (bLeftKeyHOLD) bLeftKeyHOLD = false;
  35.         }
  36. }
  37.  
  38. #define KEYHOLD 15 //in the .ash
  39.  
  40. void processQuickTurn_Left(int iMode)
  41. {
  42.   if (iMode == 1) //Manual
  43.   {    
  44.     if (iHoldKeyPressLeft >= KEYHOLD)
  45.     {
  46.       if (!bLeftKeyHOLD) bLeftKeyHOLD = true;
  47.       //value of iTurnTimer is set in the room, at "on_key_press"
  48.       if (iHoldKeyPressLeft < iTurnTimer)
  49.       {
  50.         rotateCar_TAP(-30.0);      //script that rotates the car by 30 degree increments
  51.         iHoldKeyPressLeft++;
  52.       }
  53.     }
  54.     iHoldKeyPressLeft++;
  55.   }
  56. }
  57.  

As a solution I was thinking of using scorpiorus' script http://www.adventuregamestudio.co.uk/yabb/index.php?topic=42836.0 to detect the game's FPS, and if during the driving sequences the FPS drops to a certain amount, have the iTurnTimer values changed on the fly so that everything works as it should on slower computers.

Is that a good idea, or is there a better way?
--All that is necessary for evil to triumph is for good men to do nothing.

Where are you getting 98 from? Did you use SetGameSpeed(100) or something like that?
Because unless you change the speed to something higher than the default 40, even a very fast computer shouldn't run the game faster than 40 fps but cap them at that value.

And regarding the way you're turning the car; is the player supposed to be able to screw up turning properly? For a driving sequence à la Police Quest, shouldn't they just push left/right once at the proper time and the car turn automatically?

Knox

  • Storm Behind The Badge
I think the reason I  get 98 is because I have photoshop opened...I believe  the same happens if AfterEffects or QuickTime is opened too, the fps goes up to like 98-100...I tested having various programs like that opened at the same time as AGS, and the FPS is increased majorly.

Well I could send a clip via youtube to show what Im doing if you wish (?)...let me know!

The player can "tap" the direction keys to rotate the car in 30º increments "a la police quest 1 EGA" (so to turn at an intersection you would have to tap the left or right keys multiple times depending on your direction...the faster you go though, the harder it is to tap the perfect amount to get a nice turn without hitting the borders)...to make it easier, I implemented a system that if you hold down the left or right keys for x amount of time, it will make "the perfect turn" for you, using the iTurnTimer (automatically turning the car in the right amount of degrees so the intersection is cleared perfectly)...so you can turn using both "tap" and "hold".
--All that is necessary for evil to triumph is for good men to do nothing.

Knox

  • Storm Behind The Badge
Any ideas?
--All that is necessary for evil to triumph is for good men to do nothing.

Jakey

  • Aspiring to finish my first game.
    • I can help with making music
    • I can help with play testing
    • I can help with proof reading
    • I can help with scripting
    • I can help with story design
    • I can help with voice acting
Maybe I don't fully understand what is happening in the script but it doesn't seem correct to have "iHoldKeyPressLeft++;" possibly incrementing twice during a single call of "processQuickTurn_Left". Probably should add a return or else statement somewhere, so only one of the two executes each call.

But of course, this is very likely not the cause of your problem :P

Knox

  • Storm Behind The Badge
Yeah, thats not really the problem. Everything works fine on my faster computer, but on my laptop the timing of the turning is "off". Ill try to see if I can find a different way of doing the turn. I still dont know why fps is messing with the timing script (shouldnt the turn just be donw slower on a slower maching?)
--All that is necessary for evil to triumph is for good men to do nothing.

Andail

  • Global Moderator
  • Global Moderator
  • Mittens Viscount
  • Cultured man of mystery
    • I can help with backgrounds
    • Andail worked on one or more games that won an AGS Award!
    •  
    • Andail worked on one or more games that was nominated for an AGS Award!
What you say about the fps is rather puzzling.
Have you used the debug function to get your fps displayed on your screen while playing? If not, please do so and report back what you see.
As Khris said, the game shouldn't run faster than 40 fps even if you played it on Deep Thought, unless you manually set it to do so.

Knox

  • Storm Behind The Badge
Hmm...well could it have something to do with the keyboard press sensitivity? The script calculates how long the key is pressed down, maybe different keyboards have different sensitivities and that's what's causing the turn-timing issuea on different computers?

Ill get a clip on youtube to show what's happening.
--All that is necessary for evil to triumph is for good men to do nothing.

Hmm...well could it have something to do with the keyboard press sensitivity? The script calculates how long the key is pressed down, maybe different keyboards have different sensitivities and that's what's causing the turn-timing issuea on different computers?

Ill get a clip on youtube to show what's happening.

I don't think should affect it, I can run it on my computer and slow lap old lappy if you want to see if I have that problem.
Either way thats wierd.

Monsieur OUXX

  • Mittens Vassal
  • Cavefish
  • Mittens Half Initiate
    • I can help with proof reading
    • I can help with translating
    • I can help with voice acting
    • Monsieur OUXX worked on one or more games that won an AGS Award!
    •  
    • Monsieur OUXX worked on one or more games that was nominated for an AGS Award!
Why are there two "iHoldKeyPressLeft++;", the first one ebing conditional, and the second one occurring all the time?
at the moment I'm searching for a flaw in your timing design, but I can't put my finger on it: You seem to make both angle increments and timer increment rely on the frame being rendered, so it should be correct.
I do believe that when the framerate drops, AGS skips not only the rendering of the slow frame, but also the execution of the associated script. I hope I'm right.


EDIT: I think I might have an explanation :
- Consider that when the framerate drops to 35, a timer of 15 to 20 frames is equivalent to almost one half second (500ms).
- A half second is a rather huge time gap, and is more than enough to confuse the player (if he sees the car at a certain angle, and stops pressing the key, but the script still locks down the key for 500ms, and makes the car turn further).

You have 2 solutions :
- Either you reduce the timer's interval to check the car's state more often (but still update the sprite only once in a while, when needed)
- Or you should redesign the script in order to make it check that the car has reached the target angle rather than checking that the timer has expired. The timer expiration should be used only to match the current angle to the time elapsed, and THEN the sprite should be based on the actual angle. That second solution needs more thinking.
« Last Edit: 13 Jun 2012, 12:49 by Monsieur OUXX »
 

Knox

  • Storm Behind The Badge
Re: Script dependant on game's FPS...is this a good solution?
« Reply #10 on: 13 Jun 2012, 23:16 »
Man, I see! Ok I'll try both solutions and post what happens...it makes sense, very clever!
Thanks :)
--All that is necessary for evil to triumph is for good men to do nothing.