|
Post by larrybtoys on Apr 22, 2022 21:48:13 GMT 1
Does anyone know how to clear the keyboard buffer prior to entering the next level of a game I am writing?
When I hold the UP ARROW key to rapid fire during a game I always seem to get 1 additional fire when the game advances to the next level. I currently have this code to stop it however it does not fix the problem.
Procedure Clr_Input
'No Keys or Mouse Pressed
Repeat
PeekEvent
Until MouseK = 0 And InKey$ = ""
EndProcedure
This routine should remove any extra keystrokes prior to moving on however it does not seem to work.
Thanks
|
|
|
Post by dragonjim on Apr 22, 2022 22:40:15 GMT 1
You're absolutely right: Inkey$ SHOULD read anything in the keyboard buffer if there is anything there to read - KeyTest should do the same. However, in the examples I have hastily put together, neither seems to detect whether a key is still depressed.
I can't help wondering if this is because of the delay in repeating a key if it is left depressed: i.e. Windows creates a delay if a key is pressed to prevent unintended multiple key presses. Hence, Inkey$ is returning "" in the delay and thus missing the next press of the key.
However, that speculation does not help you.
Have you tried instituting a short delay before allowing your program to once again respond to key presses, during which the keyboard buffer should clear itself or giving you time to take your finger off the keys?
Or, probably better, would a pop-up message box be appropriate at the juncture in the program where the key press overrun is causing a problem? If so, a simple message ("Game Over"?) and a command button (without focus so a stray Space or Enter key press doesn't inadvertently close the box) labelled "Continue" may well do the job for you.
I hope either of these suggestions are helpful.
|
|
|
Post by larrybtoys on Apr 22, 2022 23:25:22 GMT 1
It must be some sort of Windows thing because there is already a 2.5 second delay in the program at this point to inform the player they are moving to another level. I have even tried going to the procedure that determines if there is an up arrow press prior to moving to the next level of the program and loop if there is and it still fires once when it goes to the next level. Very strange indeed.
|
|
|
Post by dragonjim on Apr 23, 2022 9:56:21 GMT 1
I know the frustration: I remember having a similar problem a number of years ago with a Sudoku game; sadly, I can't find the program file at the moment to see how I got round it.
However, the code below does what you need (it's a bit rough and ready but you should be able to improve it and make it work in your program).
$Library "UpdateRT" UpdateRuntime ' Patches GfaWin23.Ocx
Global retkey%, t#
Debug.Show OpenW 1 Ocx Label lbl = "Press any key and keep presing it", 10, 10, 500, 40 : lbl.FontSize = 24 Do : Sleep : Until InKey$ <> "" t# = Timer Do : Sleep : Until Timer - t# > 2 // Keep pressing for 2 seconds lbl.Text = "" Form Center messbox = "Message", , , 200, 150 Ocx Label lbl2 = "Stop pressing the key", 20, 20, 160, 15 // Change to "Game Over"? Ocx Command cmd1 = "OK", 50, 62, 70, 25 Ocx Command cmd2 : cmd2.SetFocus // This button is not visible but will take any Enter or Space keypresses which might otherwise close the form early Do : Sleep : Until IsNothing(messbox) // This should use up all remaining keypresses in the buffer SendKeys "{esc}" // Simulate the Esc key press Do : Sleep : Until retkey% = 27 // Waits for the buffer to clear all other key presses until it comes to the Esc CloseW 1
Sub cmd1_Click messbox.Close EndSub
Sub Screen_KeyPreview(hWnd%, uMsg%, wParam%, lParam%, Cancel?) If hWnd% = Win_1.hWnd If uMsg% = WM_KEYDOWN Trace wParam% // Tracks all key presses EndIf EndIf EndSub
Sub Win_1_KeyPress(Ascii&) retkey% = Ascii& // Sets the retkey% value with the last key press Trace retkey% EndSub
I hope this helps.
|
|
|
Post by scalion on Apr 23, 2022 11:59:00 GMT 1
Hi A good way to see if the user still has one of his fingers on a key is with asynckeystate :
$Library "gfawinx" $Library "UpdateRT" UpdateRuntime ' Patches GfaWin23.Ocx FullW 1 FontSize = 20 Do Text 0, 0, "Finger on Direction key ? : " & FingerOnDirection & " " PeekEvent Loop Until Me Is Nothing
Function FingerOnDirection() As Boolean FingerOnDirection = Btst(GetAsyncKeyState(VK_RIGHT), 15) FingerOnDirection |= Btst(GetAsyncKeyState(VK_LEFT), 15) FingerOnDirection |= Btst(GetAsyncKeyState(VK_UP), 15) FingerOnDirection |= Btst(GetAsyncKeyState(VK_DOWN), 15) EndFunc
|
|
|
Post by larrybtoys on Apr 23, 2022 15:10:00 GMT 1
I will play with this code and see however for now I simply put a 1/10th second delay at the beginning of each level where the program goes through all the normal code but simply ignores any UP arrow keystrokes. Works perfectly.
|
|