PDA

View Full Version : strange behaviour getwindowkeystate



martin
20-07-2009, 15:16
If I use getwindowkeystate it will go in an endless loop as soon as the desired key is pressed. I tried to avoid this by resetting the keyboard buffer with getwindowkeystate(cbhndl, -1) but no succes.

I saw on this forum somebody uses sleep 150 instead of this and indeed that works fine! So problem solved but I want to understand how everything works so i still wonder why the SLEEP command does work and getwindowkeystate(cbhndl, -1) don't.

Petr Schreiber
20-07-2009, 15:46
Hi Martin,

there seems to be some problem, we will look into it.

Until the fix arrives you can use this workaround function:


function customGetKey( wHandle as dword, vCode as long ) as long

if win_getForeground = wHandle then
GetAsyncKeyState(-1)
return GetAsyncKeyState(vCode)
else
return 0
end if

end function


Usage is the same as for GetWindowKeyState.
It is strange, TBGL_GetWindowKeyState seems to work ok.



uses "UI"
'uses "TBGL" ' -- For TBGL command

dim hWin as long = Canvas_Window("Window", -1, -1, 640, 480)
Canvas_Attach(hWin, 0)

do
Canvas_setPos(0,0)
Canvas_Print "Nonsense number, press ESC to quit:"+rnd(0, 100)
doevents
if customGetKey(hWin, %VK_ESCAPE) then exit do ' -- Works
' if TBGL_GetWindowKeyState(hWin, %VK_ESCAPE) then exit do ' -- Works, but not recommended
' if GetWindowKeyState(hWin, %VK_ESCAPE) then exit do ' -- Problem
loop

Canvas_Window end

function customGetKey( wHandle as dword, vCode as long ) as long

if win_getForeground = wHandle then
GetAsyncKeyState(-1)
return GetAsyncKeyState(vCode)
else
return 0
end if

end function


Petr

martin
20-07-2009, 16:32
Hmmm...maybe i will give up using key input. I get such strange behaviours (even when i use TBGL).

For example the user should be able to add records when he press CTRL+A, so I have this code in dialog callback function:

if tbgl_GetWindowmultiKeyState(cbhndl,%vk_control,%VK_A) then AddRecords


Adding records can also be done by clicking a button:

CALLBACK FUNCTION btnAddProc()
IF CBMSG = %WM_COMMAND THEN
IF CBCTLMSG = %BN_CLICKED THEN AddRecords
end if
END FUNCTION

function AddRecords()
printl "fired"
end function()

When I run the script and click the button, the function AddRecords keeps endless fired. But when I remove the tbgl_GetWindowmultiKeyState() command AddRecords is fired one time as it should be.

Strange strange strange.........or...not??.......

Anyway many thanks for your feedback Petr!

Petr Schreiber
20-07-2009, 18:25
Hi Martin,

I think I know now for what do you need it - this is usually handled using "keyboard accelerators", not GetAsyncKeyState based functions.

I checked MSDN for it, it seems to make possible to define keyboard accelerators on the fly, but it is described in Microsoft English, so I do not understand how to do it at the moment.

Here are some declarations, which may help you in case you understand what is written here:
MSDN & Keyboard accelerators (http://msdn.microsoft.com/en-us/library/ms645526%28VS.85%29.aspx)



%FVIRTKEY = 1
%FSHIFT = 4
%FCONTROL = 8
%FALT = 16
DECLARE FUNCTION CreateAcceleratorTable LIB "USER32.DLL" ALIAS "CreateAcceleratorTableA" (BYREF lpaccl AS ACCELAPI, BYVAL cEntries AS LONG ) AS LONG
DECLARE FUNCTION DestroyAcceleratorTable LIB "USER32.DLL" ALIAS "DestroyAcceleratorTable" (BYVAL hAccel AS DWORD ) AS LONG
DECLARE FUNCTION TranslateAccelerator LIB "USER32.DLL" ALIAS "TranslateAcceleratorA" (BYVAL hWnd AS DWORD , BYVAL hAccTable AS DWORD, BYREF lpMsg AS tagMSG) AS LONG

...

dim Accelerator(1) as ACCELAPI

Accelerator(1).FVIRT = %FCONTROL
Accelerator(1).KEY = ASC("A")
Accelerator(1).CMD = 1

dim hAccel as dword = CreateAcceleratorTable(Accelerator(1), 1 )

DIALOG SHOW MODAL hDlg, CALL dlgProc

DestroyAcceleratorTable(hAccel)




Petr

martin
21-07-2009, 06:48
Good morning Petr, I will check it out and let you know.