How do I add a delay between SendInput commands in AutoHotkey? - autohotkey

I have an AutoHotkey script using SendInput which sends MouseClick commands too quickly for my program to handle. My script will send a MouseClick to focus an input field, then start typing before the field finishes focusing.
I've tried using SetKeyDelay to make my script run a bit slower, but this doesn't work with SendInput.
Note: SetKeyDelay is not obeyed by SendInput; there is no delay between keystrokes in that mode. This same is true for Send when SendMode Input is in effect.
Documentation for SetKeyDelay
My current workaround is to use sleep commands after each input, but this is less than ideal.
SendMode Input
F1::
MouseClick, left, 61, 50 ; select title field
sleep 100 ; artificial delay to prevent misfocused inputs
SendInput %user_input%{Enter} ; enter job title
sleep 100 ; artificial delay
MouseClick, left, 67, 408 ; select job
sleep 100 ; artificial delay
Return
Ideally I would like a more elegant solution for adding a delay between each SendInput command without manually using a sleep command each time.
How can I add a delay between SendInput commands in AutoHotkey without repeatedly using sleep?

Try using SendPlay instead of SendInput.
This sends text and mouse clicks with a 100ms delay following each click
user_input := "hello world"
SetMouseDelay 100, Play
SendPlay {Click 61,50}%user_input%{enter}{click 67,408}
From the documentation for SendPlay.
SendPlay
Note: SendPlay may have no effect at all if UAC is enabled, even if the script is running as an administrator. For more information, refer to the FAQ.
Like SendInput, SendPlay's keystrokes do not get interspersed with keystrokes typed by the user. Thus, if the user happens to type something during a SendPlay, those keystrokes are postponed until afterward.
Although SendPlay is considerably slower than SendInput, it is usually faster than the traditional SendEvent mode (even when KeyDelay is -1).
SendPlay does not use the standard settings of SetKeyDelay and SetMouseDelay. Instead, it defaults to no delay at all, which can be changed as shown in the following examples:
SetKeyDelay, 0, 10, Play ; Note that both 0 and -1 are the same in SendPlay mode.
SetMouseDelay, 10, Play

Related

Cant make a toggle in AutoHotkey

I'm trying to make "]" a toggle for when I press "p" its presses "e" 3 times total with 10ms spaces. Then toggle off if I just want to press "t".
I have this but set to "p" just to press "e" 3 times quickly but without a toggle, in case I want to normally type "t".
#NoEnv ; Recommended for performance and compatibility with future AutoHotkey releases.
; #Warn ; Enable warnings to assist with detecting common errors.
SendMode Input ; Recommended for new scripts due to its superior speed and reliability.
SetWorkingDir %A_ScriptDir% ; Ensures a consistent starting directory.
SetKeyDelay , 10, 10 ; first is delay between keypresses, and second is press duration
; we are using ControlSend here because Send and SendInput is not affected by SetKeyDelay.
p::
ControlSend, , e, A
ControlSend, , e, A
ControlSend, , e, A
return,
/::
ExitApp
return,
Can I get help on making a toggle?
Sounds like to me you're simply looking to toggle the hotkey being enabled.
This is very easily doable with Suspend(docs).
Also, this is false:
we are using ControlSend here because Send and SendInput is not affected by SetKeyDelay.
SetKeyDelay(docs) works on normal Send just fine. You're actually using SendMode Input(docs) to change the default sendmode to SendInput. That's why it's not working.
I know those first 4 lines are auto-generated when you non-manually create a new ahk file.
It's good to know what they're actually doing.
So don't ControlSend unless you actually need to ControlSend, switch over to normal Send.
Also, your usage of SetKeyDelay(docs) is a bit weird there.
It's intended for the ability to add delay to a single command. With your approach you might as well have Sleeps there in-between.
Fixed/revised script:
SetKeyDelay , 10, 10
p::Send, eee
]::Suspend
/::ExitApp

LButton Hotkey seems to prevent Send, {LButton}

I'm at a loss here. As soon as I add the LButton hotkey, the Send, {LButton} doesn't seem to work, but they show up in recently executed lines.
Env. Windows 7x64, Disabled Touchpad, AHK v1.1.31.01.
I try to emulate the Wink application (from DebugMode) to capture screenshots for training purposes. For that reason, I want to capture a screenshot just before a mouse click. This looks easy, and I even vaguely remember doing similar mouse hotkeys in the past. However I can't get this to work.
Step 1: I just reduced it to this simple script:
#InstallKeybdHook
#InstallMouseHook
#UseHook
#Persistent
Return
a::
Send, {LButton}
Return
q::
ExitApp
When using this script, I can simulate clicking the Left Mouse Button through the a key. Nothing special.
However as soon as I add either a line with "Hotkey, $LButton, MySendClick", or "$LButton::" the previously working a hotkey no longer works. In the recently executed lines, you can see the "Send, {LButton}" lines, but nothing is being send. Unexpectedly, the a hotkey actually causes the "$LButton::" hotkey to trigger (without it sending {LButton}). When I change the a hotkey to send "RButton" and the $LButton:: to $RButton::, then Send {Click} works perfectly (eventhough the a hotkey should never be able to trigger $RButton::).
Originally I just wanted to have the following HotKey:
$LButton::
SoundBeep, 300, 150 ; For testing only
; Send, ^{PrintScreen} ; To trigger Greenshot in the background
Sleep, 100
Send, {LButton}
Return
I upgraded from AHK v1.1.22.04 to v1.1.31.01. No improvement.
I tried "Click", "sendInput, {LButton}", "Send {Click}", "MouseClick, Left".
I tried "$LButton::", "vk01sc000::", "Hotkey, $LButton, MyClick".
Is this an issue with my specific Windows 7 configuration or an "undocumented AHK feature"?
#InstallKeybdHook
#InstallMouseHook
#UseHook
#Persistent
Return
a::
Send, {LButton}
Return
$LButton::
SoundBeep, 300, 150 ; Should be Send, ^{PrintScreen} ; To trigger Greenshot in the background
MouseClick, Left
Return
q::
ExitApp
In this last test example, When $LButton:: is disabled, the a hotkey works like a charm, but as soon as I enable $LButton::, the a hotkey triggers $LButton:: and no mouse click is being sent to the windows applications.
I would appreciate it when other Windows 7 users could quickly test this issue.
In my experience, using keys that you still want the input to pass through need the Tilde prefix.
https://www.autohotkey.com/docs/Hotkeys.htm#Tilde
~LButton::
SoundBeep, 300, 150 ; Should be Send, ^{PrintScreen} ; To trigger Greenshot in the background
KeyWait, LButton ; Wait for lbutton to be released.
Return

What in this script is causing my window to minimize?

The goal of this simple script is to detect an idle interval when a specific program is in focus and then send a simple keystroke when that idle interval has passed. I'm running this script on 4 PC's and I'm getting unexpected results. Some PC's minimize the window when the script runs. Other PC's run it as expected. The script is identical on each PC.
I'm invoking this script by right clicking on the script (that is, not running a compiled exe version of it). Running it as administrator seems to achieve better results on some clients, on one it makes no difference and minimizes the window.
As stated, on some PC's the script works as intended. There are no error messages, it just causes my window to minimize. Nothing in that code, to my newb eyes, should cause the window to minimize.
#Persistent
SetTimer, Timer_check,3000
Timer_check:
if WinActive("ahk_exe gta5.exe")
{
if (A_TimeIdlePhysical > 31301 && WinActive("ahk_exe gta5.exe")) {
Gosub, keepActive
ToolTip, We're currently idle TimeIdle is %A_TimeIdle% and TimeIdlePhysical is %A_TimeIdlePhysical%
sleep 1000
ToolTip
}
if (A_TimeIdle < 31301) {
ToolTip
}
}
return
keepActive: ; keep active sub.
if WinActive("ahk_exe gta5.exe")
{
Send, {` down} ; Press the ` key to keep us active. It holds the key for 0.2 seconds.
Sleep 200
Send, {` up}
}
return```
You're trying to send the accent/backtick, which is default escape character in AHK (`). To fix this, send a different character or escape the escape character, like so:
Send, {`` down}
Sleep 200
Send, {`` up}
Without it being escaped, it just sends the down- and up-keys. The WinKey+down combination minimizes a non-maximized window and that may somehow be related to why you're seeing the game window occasionally minimized.
https://www.autohotkey.com/docs/commands/_EscapeChar.htm
Edit: Added script for testing
#Persistent
SetTimer, Timer_check, 3000
Timer_check:
If WinActive("ahk_exe gta5.exe") {
If (A_TimeIdlePhysical > 31301 && WinActive("ahk_exe gta5.exe")) {
Send , z
ToolTip, We're currently idle TimeIdle is %A_TimeIdle% and TimeIdlePhysical is %A_TimeIdlePhysical%
sleep 1000
ToolTip
}
If (A_TimeIdle < 31301)
ToolTip
}
Return

AHK Prevent Multiple Hotkey Triggers

It's a quite simple code.
I just want my Mousewheeldown to Send P only once.
Even if I scroll it like 3 times, I only want it to send P only once every 100ms or sth.
Here is my really small bit of code so far:
SetKeyDelay , -1, 50
#NoTrayIcon
#NoEnv
#persistent
#MaxMem 2
WheelDown::
Send {p}
return
Sleeping a bit after sending the keystroke would solve this problem.
WheelDown:
Send, p
Sleep, 100
return
Also, you do not need to put the p between {}-s (curly braces), as it is not a special key.
The sleep command takes it's parameter as milliseconds, so if for example you would want to allow it only one 'p' in a second, you would write Sleep, 1000.

Send, SendInput, SendEvent functions entering single key multiple times

I have created a script in AutoHotKey.I have to Enter the entire file path to be opened in the
file browser.i have used send function but it passes the same keys multiple times. I tried using the function SetKeyDelay but still it enters the keys multiple times. I tried other alternatives as sendInput and SendEvent but still it didnt work.
Even if i terminate the script in between and if the control switches to some Input box or Editor, it starts entering the values into that area. Send function keeps on entering the keys even after the script execution is terminated.
Script:
;Open Adobe Acrobat 8.
run Acrobat.exe sleep, 1000
WinWait, Adobe Acrobat Professional,
Sleep, 1000
;Open Compare Documents Window
send, {ALT}A
Sleep, 1000
send, U
WinWait, Compare Documents,
;Enter File Path
IfWinNotActive, Compare Documents,
WinActivate, Compare Documents,
WinWaitActive, Compare Documents,
Sleep, 1000
send, !H
WinWaitActive, Open,,1000
sleep, 1000
SendEvent, "D:\Sample\a.pdf"
It Enters text something like this
CCCC:::::\\DDDDiiiiii
Things to try:
Update AutoHotkey to the latest version.
Don't use SendEvent. It allows other input to interrupt the text as it is being entered. Use SendInput instead. It is recommended to put the following at the top of all your scripts:
#NoEnv ; Recommended for performance and compatibility with future AutoHotkey releases.
SendMode Input ; Recommended for new scripts due to its superior speed and reliability.
SetWorkingDir %A_ScriptDir% ; Ensures a consistent starting directory.
SendMode Input changes Send to use SendInput instead of SendEvent. It buffers the input and sends it all at once instead of letting other keyboard/scripts interrupt the text. See: Send for more information.
Restart your computer and make sure that there are no other AutoHotkey programs running, or that there isn't multiple instances of your Autohotkey script running. This is especially a problem when testing, as you might have launched the same script multiple times, and if the thread hasn't been properly terminated, you may have multiple instances there waiting for the Open window to be activated. Once the Open window has been activated, then you may have 4+ dormant scripts all trying to type at the same time, which would give you the output that you are describing.