Jump to content

neutralize keystrokes?


Gianni
 Share

Recommended Posts

Running the script provided in the help file related to the "_WinAPI_SetWindowsHookEx" function, It seems that the keystrokes are retained(?) by the _KeyProc() function during the elaboration, and displayed into the InputBox only after(?) the returning from that function.
 I was wondering if could be possible in some way, neutralize some keys and throw them away before that them are showed  in the InputBox.
The purpose of this, is the possibility to use some InputBox allowing only the entering of certain chars and disallow some others. For example if I have an InputBox where must be entered an HEX number, I would allow only keystrokes from 0 to 9 and from A to F, neutralizing all others (but Tab anf CR).

Thanks in advance for any suggestion

here a little modified version of the script provided in the help file, that use an InputBox instead of Notepad.

#include <MsgBoxConstants.au3>
#include <StructureConstants.au3>
#include <WinAPI.au3>
#include <WindowsConstants.au3>

Global $g_hHook, $g_hStub_KeyProc, $g_sBuffer = ""

Example()

Func Example()
    OnAutoItExitRegister("Cleanup")

    Local $hMod

    $g_hStub_KeyProc = DllCallbackRegister("_KeyProc", "long", "int;wparam;lparam")
    $hMod = _WinAPI_GetModuleHandle(0)
    $g_hHook = _WinAPI_SetWindowsHookEx($WH_KEYBOARD_LL, DllCallbackGetPtr($g_hStub_KeyProc), $hMod)

    GUICreate('Test ')
    $Input1 = GUICtrlCreateInput("", 8, 8, 105, 21)
    GUISetState(@SW_SHOW)

    While 1
        Sleep(10)
    WEnd
EndFunc   ;==>Example

Func EvaluateKey($iKeycode)
    If (($iKeycode > 64) And ($iKeycode < 91)) _ ; a - z
            Or (($iKeycode > 96) And ($iKeycode < 123)) _ ; A - Z
            Or (($iKeycode > 47) And ($iKeycode < 58)) Then ; 0 - 9
        $g_sBuffer &= Chr($iKeycode)
        Switch $g_sBuffer
            Case "Jon"
                ToolTip("What can you say?")
            Case "AutoIt"
                ToolTip("AutoIt Rocks")
        EndSwitch
    ElseIf ($iKeycode > 159) And ($iKeycode < 164) Then
        Return
    ElseIf ($iKeycode = 27) Then ; esc key
        Exit
    Else
        $g_sBuffer = ""
    EndIf
EndFunc   ;==>EvaluateKey

; ===========================================================
; callback function
; ===========================================================
Func _KeyProc($nCode, $wParam, $lParam)
    Local $tKEYHOOKS
    $tKEYHOOKS = DllStructCreate($tagKBDLLHOOKSTRUCT, $lParam)
    If $nCode < 0 Then
        Return _WinAPI_CallNextHookEx($g_hHook, $nCode, $wParam, $lParam)
    EndIf
    If $wParam = $WM_KEYDOWN Then
        EvaluateKey(DllStructGetData($tKEYHOOKS, "vkCode"))
    Else
        Local $iFlags = DllStructGetData($tKEYHOOKS, "flags")
        Switch $iFlags
            Case $LLKHF_ALTDOWN
                ConsoleWrite("$LLKHF_ALTDOWN" & @CRLF)
            Case $LLKHF_EXTENDED
                ConsoleWrite("$LLKHF_EXTENDED" & @CRLF)
            Case $LLKHF_INJECTED
                ConsoleWrite("$LLKHF_INJECTED" & @CRLF)
            Case $LLKHF_UP
                ConsoleWrite("$LLKHF_UP: scanCode - " & DllStructGetData($tKEYHOOKS, "scanCode") & @TAB & "vkCode - " & DllStructGetData($tKEYHOOKS, "vkCode") & @CRLF)
        EndSwitch
    EndIf
    Return  _WinAPI_CallNextHookEx($g_hHook, $nCode, $wParam, $lParam)
EndFunc   ;==>_KeyProc

Func Cleanup()
    _WinAPI_UnhookWindowsHookEx($g_hHook)
    DllCallbackFree($g_hStub_KeyProc)
EndFunc   ;==>Cleanup

 

image.jpeg.9f1a974c98e9f77d824b358729b089b0.jpeg Chimp

small minds discuss people average minds discuss events great minds discuss ideas.... and use AutoIt....

Link to comment
Share on other sites

http://msdn.microsoft.com/en-us/library/windows/desktop/ms644985(v=vs.85).aspx

"If the hook procedure processed the message, it may return a nonzero value to prevent the system from passing the message to the rest of the hook chain or the target window procedure."

If $wParam = $WM_KEYDOWN Then
If DllStructGetData($tKEYHOOKS, "vkCode") = 65 Then ; "a"
ConsoleWrite("+ ""a"" was pressed and not passed to the program" & @CRLF)
Return 1
endif
Else
Edited by KaFu
Link to comment
Share on other sites

What about this:

 

Thanks funkey, that's an interesting link. very nice way.

 

 

http://msdn.microsoft.com/en-us/library/windows/desktop/ms644985(v=vs.85).aspx

"If the hook procedure processed the message, it may return a nonzero value to prevent the system from passing the message to the rest of the hook chain or the target window procedure."

If $wParam = $WM_KEYDOWN Then
If DllStructGetData($tKEYHOOKS, "vkCode") = 65 Then ; "a"
ConsoleWrite("+ ""a"" was pressed and not passed to the program" & @CRLF)
Return 1
endif
Else

 

Tanks KaFu,

after reading around, I have found that the way to "neutralize" the already typed "key" is to Return 1 instead of  Return _WinAPI_CallNextHookEx($g_hHook, $nCode, $wParam, $lParam)

as clearly visible also in your example.

thanks again

 

Here are also 2 more links where I got some interesting info:

http://www.codeproject.com/Articles/14485/Low-level-Windows-API-hooks-from-C-to-stop-unwante

'?do=embed' frameborder='0' data-embedContent>>

here a working example on which I was playing. It's just a draft for experiments. (it let you select which InputBox to restrict input).

#include <GUIConstantsEx.au3>
; #include <MsgBoxConstants.au3>
#include <StructureConstants.au3>
#include <WinAPI.au3>
#include <WindowsConstants.au3>

Global $sAllowedKeys = "0123456789ABCDEF" ; <-- Allowed keys in $Input1 (for hex input)

Global $g_hHook, $g_hStub_KeyProc

Example()

Func Example()
    OnAutoItExitRegister("Cleanup")

    Local $hMod
    $g_hStub_KeyProc = DllCallbackRegister("_KeyProc", "long", "int;wparam;lparam")
    $hMod = _WinAPI_GetModuleHandle(0)
    $g_hHook = _WinAPI_SetWindowsHookEx($WH_KEYBOARD_LL, DllCallbackGetPtr($g_hStub_KeyProc), $hMod)

    GUICreate('Test Trap & Block keys')
    Global $Input1 = GUICtrlCreateInput("", 8, 8, 105, 21)
    $Label1 = GUICtrlCreateLabel('<--- only "0123456789ABCDEF" keys allowed here', 120, 8, 300, 21)

    $Input2 = GUICtrlCreateInput("", 8, 40, 105, 21)
    $Label2 = GUICtrlCreateLabel("<--- free input allowed here", 120, 40, 300, 21)
    GUISetState(@SW_SHOW)

    While 1
        $Msg = GUIGetMsg()
        Switch $Msg
            Case $GUI_EVENT_CLOSE
                _Bye()
        EndSwitch
        Sleep(10)
    WEnd
EndFunc   ;==>Example

Func _GuiCtrlGetFocus($hGui = "") ; Retrieves the internal handle of the control with the focus
    Local $InputID = ControlGetHandle($hGui, "", ControlGetFocus($hGui))
    Return _ControlGetGuiID($InputID)
EndFunc   ;==>_GuiCtrlGetFocus

Func _ControlGetGuiID($hCtrl) ; Transforms from Handle to ID
    Local $Result = DllCall("user32.dll", "int", "GetDlgCtrlID", "hwnd", $hCtrl)
    If @error = 0 Then Return $Result[0]
    Return SetError(1, 0, '')
EndFunc   ;==>_ControlGetGuiID

; ===========================================================
; callback function
; ===========================================================
Func _KeyProc($nCode, $wParam, $lParam)
    Local $tKEYHOOKS
    $tKEYHOOKS = DllStructCreate($tagKBDLLHOOKSTRUCT, $lParam)
    If $nCode < 0 Then ; ??
        Return _WinAPI_CallNextHookEx($g_hHook, $nCode, $wParam, $lParam) ;
    EndIf
    If _GuiCtrlGetFocus() = $Input1 Then ; Check if focus is in target control
        If $wParam = $WM_KEYDOWN Then
            If StringInStr($sAllowedKeys, Chr(DllStructGetData($tKEYHOOKS, "vkCode"))) Then
                Return _WinAPI_CallNextHookEx($g_hHook, $nCode, $wParam, $lParam) ; key processed as usual
            Else
                Return 1 ; block that key (NEUTRALIZE THAT KEY)
            EndIf
        EndIf
    Else
        Return _WinAPI_CallNextHookEx($g_hHook, $nCode, $wParam, $lParam)
    EndIf
EndFunc   ;==>_KeyProc

Func _Bye()
    Exit
EndFunc   ;==>_Bye

Func Cleanup()
    _WinAPI_UnhookWindowsHookEx($g_hHook)
    DllCallbackFree($g_hStub_KeyProc)
    ConsoleWrite("bye bye" & @CRLF)
EndFunc   ;==>Cleanup
Edited by Chimp

 

image.jpeg.9f1a974c98e9f77d824b358729b089b0.jpeg Chimp

small minds discuss people average minds discuss events great minds discuss ideas.... and use AutoIt....

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...