Jump to content

Sky Slate Blueberry Blackcurrant Watermelon Strawberry Orange Banana Apple Emerald Chocolate
Photo

Buffered Send and SendRaw


  • Please log in to reply
7 replies to this topic
shimanov
  • Members
  • 610 posts
  • Last active: Jul 18 2006 08:35 PM
  • Joined: 25 Sep 2005
This should be self explanatory.

Basically, it's a game.

The goal is to be faster than the computer.

While Send or SendRaw is in play, you want to type as fast as possible in order to introduce interspersed characters.

Good luck.

Press F2 to start.

< Game keys >
action0-9, a-z, Shift, Enter, SpacerestartF11quitF12
Warning: Be sure to play this game in a safe area (e.g., Notepad).

; only required in training mode or on long missions
#MaxHotkeysPerInterval 1000

F2::
	Send( "Hello, World!  How are you?  Hello, World!  How are you?", false )
return

F11::
Reload

F12::
ExitApp

Send( p_data, p_send=true, p_buffer=false )
{
	static	key_buffer, hk_list

	Gosub, EnableBufferedInput
	
	; disable to leave training mode
	SetKeyDelay, 200
	if ( p_send )
		Send, %p_data%
	else
		SendRaw, %p_data%
		
	if ( p_buffer )
		StringTrimLeft, key_buffer, key_buffer, StrLen( p_data )
	
	; ensure buffered input is captured
	Sleep, -1
	
	if key_buffer!=
		Send( key_buffer, true, true )
		
	Gosub, DisableBufferedInput
return

hk_CaptureBufferedInput:
	Critical
	
	StringReplace, key, A_ThisHotkey, $*
	StringReplace, key, key, vk10 up, Shift up
	StringReplace, key, key, vk10, Shift down
	
	key_buffer = %key_buffer%{%key%}
return

EnableBufferedInput:
	if hk_list=
	{
		old_FormatInteger := A_FormatInteger
		SetFormat, Integer, Hex
		
		hk_list = $*vkD				; Enter
		hk_list = %hk_list%|$*vk10	; Shift
		hk_list = %hk_list%|$*vk20	; Space
		
		ix_b = 0x30					; 0
		ix_e = 0x39					; 9
		loop, % ix_e-ix_b+1
			hk_list := hk_list "|$*vk" ix_b+A_Index-1
		
		ix_b = 0x41					; a
		ix_e = 0x5A					; z
		loop, % ix_e-ix_b+1
			hk_list := hk_list "|$*vk" ix_b+A_Index-1
			
		StringReplace, hk_list, hk_list, 0x,, All
	
		SetFormat, Integer, %old_FormatInteger%
	}
	
	loop, Parse, hk_list, |
	{
		Hotkey, %A_LoopField%, hk_CaptureBufferedInput, on
		Hotkey, %A_LoopField% up, hk_CaptureBufferedInput, on
	}
return

DisableBufferedInput:
	loop, Parse, hk_list, |
	{
		Hotkey, %A_LoopField%, off
		Hotkey, %A_LoopField% up, off
	}
return
}


drbob
  • Members
  • 5 posts
  • Last active: Apr 04 2006 08:13 PM
  • Joined: 04 Apr 2006
Thanks very much for this if I can get it working it will be very useful, however, unfortunately I'm having problems with your script.

I tried to modify it to accept numberpad input by adding this to the section which generates hk_list:

ix_b = 0x60               ; NUM0
      ix_e = 0x69               ; NUM9
      loop, % ix_e-ix_b+1
         hk_list := hk_list "|$*vk" ix_b+A_Index-1

However if I press a numberpad key whilst a script generated shift key event is occuring, the alternative key pad function is executed (home, end, left, right, etc)

e.g If a num7 is pressed between the "shift down, w, shift up" sent to create a capital W in "Hello World!", "Home" is sent immediately instead of being buffered and lots of spurious shift events appear in the buffer.

What confuses me is that pressing the normal number keys whilst the script is sending a shift doesn't cause spurious punctuation (!"£$ etc)

I'm wondering if this is a bug in AHK or if windows is substituting the home, end, etc events at a lower level than ahk hooks the keyboard.

shimanov
  • Members
  • 610 posts
  • Last active: Jul 18 2006 08:35 PM
  • Joined: 25 Sep 2005

it will be very useful


This function should be obsolete with the introduction of SendInput.

I'm having problems with your script


The issue seems to be that Numpad{0..9} keys are not buffered. Verify this with the following code:

if key_buffer!=
	{
		MsgBox, %key_buffer%
		Send( key_buffer, true, true )
	}


  • Guests
  • Last active:
  • Joined: --
Not for my purposes, I need to buffer input during more than just a send command. I'm working on an AHK script that interacts with a program running over a slow network from a citrix server.

I need to insert sleep states and winwaits around send commands for the program to catch up with actions automated by a hotkey and I need to buffer all input between the pressing of the hotkey and the completion of the actions linked to the hotkey, to prevent keypresses interfering.

It's a data entry app, I currently use Blockinput to prevent keypresses interfering with a hotkey but it really breaks my flow to have to wait for the app to catch up every time I use a hotkey.

drbob
  • Members
  • 5 posts
  • Last active: Apr 04 2006 08:13 PM
  • Joined: 04 Apr 2006
I considered the "Input" command - but I would need a way to switch it on and off programatically (at the start and end of the hotkey sequenece) rather than relying on a timeout or a keypress + have it running in a separate thread whilst the intended hotkey action was performed. I couldn't see a way to do that.

drbob
  • Members
  • 5 posts
  • Last active: Apr 04 2006 08:13 PM
  • Joined: 04 Apr 2006

it will be very useful

The issue seems to be that Numpad{0..9} keys are not buffered. Verify this with the following code:

if key_buffer!=
	{
		MsgBox, %key_buffer%
		Send( key_buffer, true, true )
	}

See my original post - the code I added to the script adds the virtual key codes for num0 to num9 to hk_list, so it should capture the numpad keys, however some of them get misinterpreted as the alternative function of the numpad keys (e.g 4 is left and 1 is end, with numlock off).

This appears to be linked to pressing a numpad key whilst a shift key is depressed by ahk during the sending of the "Hello world" string.

Typing 1-6 on the numpad got me this as the contents of key_buffer:

Posted Image

Try it yourself, if I remove all capital letters and shifted punctuation (!, ?) from the Hello world string, then the numberpad keys are buffered correctly.

  • Guests
  • Last active:
  • Joined: --
There seems to be an issue with key recognition. Try the following and verify the discrepancy with recognized keys in the key history.

#InstallKeybdHook

F2::
	SetNumLockState, on

	SetKeyDelay, 100

	SendEvent, HHHHHHHHHHHHHHHHHH
	
	SetNumLockState, off
	
	KeyHistory
return


drbob
  • Members
  • 5 posts
  • Last active: Apr 04 2006 08:13 PM
  • Joined: 04 Apr 2006

There seems to be an issue with key recognition. Try the following and verify the discrepancy with recognized keys in the key history.

That test code doesn't replicate the issue, I think it's a problem with autohotkey telling the difference beween script generated and user generated keypresses on the numberpad. If the user presses a numberpad key whilst a script generated shift key is depressed then the alternate numberpad
key is sent (home, left, right, delete etc)